]> diplodocus.org Git - nmh/commitdiff
Create new mh-format function %(ordinal)
authorKen Hornstein <kenh@pobox.com>
Mon, 8 Jul 2019 13:59:15 +0000 (09:59 -0400)
committerKen Hornstein <kenh@pobox.com>
Mon, 8 Jul 2019 13:59:15 +0000 (09:59 -0400)
Implement a new mh-format function %(ordinal).  This will output
the appropriate ordinal prefix (st, nd, rd, st) based on the value
of the "num" register.

docs/pending-release-notes
h/fmt_compile.h
man/mh-format.man
sbr/fmt_compile.c
sbr/fmt_scan.c
uip/fmtdump.c
uip/fmttest.c

index 980ee83..5ee7d81 100644 (file)
@@ -10,6 +10,9 @@ NEW FEATURES
 - inc(1)/msgchk(1) now support STARTTLS for the POP protocol.
 - All TLS-supported protocols now will send the SNI (server name indicator)
   TLS extension.
 - inc(1)/msgchk(1) now support STARTTLS for the POP protocol.
 - All TLS-supported protocols now will send the SNI (server name indicator)
   TLS extension.
+- A new mh-format function %(ordinal) has been implemented to output the
+  appropriate ordinal suffix for numbers.  Example: "%(num 22)%(ordinal)"
+  will output "22nd".
 
 -----------------
 OBSOLETE FEATURES
 
 -----------------
 OBSOLETE FEATURES
index 532ccd1..470085f 100644 (file)
 #define FT_LS_PRETTY     38      /* set "str" to pretty (?) date str         */
 #define FT_LS_KILO       39      /* set "str" to "<value>[KMGT]"             */
 #define FT_LS_KIBI       40      /* set "str" to "<value>[KMGT]"             */
 #define FT_LS_PRETTY     38      /* set "str" to pretty (?) date str         */
 #define FT_LS_KILO       39      /* set "str" to "<value>[KMGT]"             */
 #define FT_LS_KIBI       40      /* set "str" to "<value>[KMGT]"             */
-#define FT_LV_SEC        41      /* set "value" to tws second                */
-#define FT_LV_MIN        42      /* set "value" to tws minute                */
-#define FT_LV_HOUR       43      /* set "value" to tws hour                  */
-#define FT_LV_MDAY       44      /* set "value" to tws day of month          */
-#define FT_LV_MON        45      /* set "value" to tws month                 */
-#define FT_LV_YEAR       46      /* set "value" to tws year                  */
-#define FT_LV_YDAY       47      /* set "value" to tws day of year           */
-#define FT_LV_WDAY       48      /* set "value" to tws weekday               */
-#define FT_LV_ZONE       49      /* set "value" to tws timezone              */
-#define FT_LV_CLOCK      50      /* set "value" to tws clock                 */
-#define FT_LV_RCLOCK     51      /* set "value" to now - tws clock           */
-#define FT_LV_DAYF       52      /* set "value" to tws day flag              */
-#define FT_LV_DST        53      /* set "value" to tws daylight savings flag */
-#define FT_LV_ZONEF      54      /* set "value" to tws timezone flag         */
+#define FT_LS_ORDINAL    41      /* set "str" to ordinal suffix of value     */
+#define FT_LV_SEC        42      /* set "value" to tws second                */
+#define FT_LV_MIN        43      /* set "value" to tws minute                */
+#define FT_LV_HOUR       44      /* set "value" to tws hour                  */
+#define FT_LV_MDAY       45      /* set "value" to tws day of month          */
+#define FT_LV_MON        46      /* set "value" to tws month                 */
+#define FT_LV_YEAR       47      /* set "value" to tws year                  */
+#define FT_LV_YDAY       48      /* set "value" to tws day of year           */
+#define FT_LV_WDAY       49      /* set "value" to tws weekday               */
+#define FT_LV_ZONE       50      /* set "value" to tws timezone              */
+#define FT_LV_CLOCK      51      /* set "value" to tws clock                 */
+#define FT_LV_RCLOCK     52      /* set "value" to now - tws clock           */
+#define FT_LV_DAYF       53      /* set "value" to tws day flag              */
+#define FT_LV_DST        54      /* set "value" to tws daylight savings flag */
+#define FT_LV_ZONEF      55      /* set "value" to tws timezone flag         */
 
 
-#define FT_LS_PERS       55      /* set "str" to person part of addr    */
-#define FT_LS_MBOX       56      /* set "str" to mbox part of addr      */
-#define FT_LS_HOST       57      /* set "str" to host part of addr      */
-#define FT_LS_PATH       58      /* set "str" to route part of addr     */
-#define FT_LS_GNAME      59      /* set "str" to group part of addr     */
-#define FT_LS_NOTE       60      /* set "str" to comment part of addr   */
-#define FT_LS_ADDR       61      /* set "str" to mbox@host              */
-#define FT_LS_822ADDR    62      /* set "str" to 822 format addr        */
-#define FT_LS_FRIENDLY   63      /* set "str" to "friendly" format addr */
-#define FT_LV_HOSTTYPE   64      /* set "value" to addr host type       */
-#define FT_LV_INGRPF     65      /* set "value" to addr in-group flag   */
-#define FT_LS_UNQUOTE    66      /* remove RFC 2822 quotes from "str"   */
-#define FT_LV_NOHOSTF    67      /* set "value" to addr no-host flag */
+#define FT_LS_PERS       56      /* set "str" to person part of addr    */
+#define FT_LS_MBOX       57      /* set "str" to mbox part of addr      */
+#define FT_LS_HOST       58      /* set "str" to host part of addr      */
+#define FT_LS_PATH       59      /* set "str" to route part of addr     */
+#define FT_LS_GNAME      60      /* set "str" to group part of addr     */
+#define FT_LS_NOTE       61      /* set "str" to comment part of addr   */
+#define FT_LS_ADDR       62      /* set "str" to mbox@host              */
+#define FT_LS_822ADDR    63      /* set "str" to 822 format addr        */
+#define FT_LS_FRIENDLY   64      /* set "str" to "friendly" format addr */
+#define FT_LV_HOSTTYPE   65      /* set "value" to addr host type       */
+#define FT_LV_INGRPF     66      /* set "value" to addr in-group flag   */
+#define FT_LS_UNQUOTE    67      /* remove RFC 2822 quotes from "str"   */
+#define FT_LV_NOHOSTF    68      /* set "value" to addr no-host flag */
 
 /* Date Coercion */
 
 /* Date Coercion */
-#define FT_LOCALDATE     68      /* Coerce date to local timezone */
-#define FT_GMTDATE       69      /* Coerce date to GMT            */
+#define FT_LOCALDATE     69      /* Coerce date to local timezone */
+#define FT_GMTDATE       70      /* Coerce date to GMT            */
 
 /* pre-format processing */
 
 /* pre-format processing */
-#define FT_PARSEDATE     70      /* parse comp into a date (tws) struct */
-#define FT_PARSEADDR     71      /* parse comp into a mailaddr struct   */
-#define FT_FORMATADDR    72      /* let external routine format addr    */
-#define FT_CONCATADDR    73      /* formataddr w/out duplicate removal  */
-#define FT_MYMBOX        74      /* do "mymbox" test on comp            */
-#define FT_GETMYMBOX     75      /* return "mymbox" mailbox string      */
-#define FT_GETMYADDR     76      /* return "mymbox" addr string         */
+#define FT_PARSEDATE     71      /* parse comp into a date (tws) struct */
+#define FT_PARSEADDR     72      /* parse comp into a mailaddr struct   */
+#define FT_FORMATADDR    73      /* let external routine format addr    */
+#define FT_CONCATADDR    74      /* formataddr w/out duplicate removal  */
+#define FT_MYMBOX        75      /* do "mymbox" test on comp            */
+#define FT_GETMYMBOX     76      /* return "mymbox" mailbox string      */
+#define FT_GETMYADDR     77      /* return "mymbox" addr string         */
 
 /* conditionals & control flow (must be last) */
 
 /* conditionals & control flow (must be last) */
-#define FT_SAVESTR       77      /* save current str reg               */
-#define FT_DONE          78      /* stop formatting                    */
-#define FT_PAUSE         79      /* pause                              */
-#define FT_NOP           80      /* no-op                              */
-#define FT_GOTO          81      /* (relative) goto                    */
-#define FT_IF_S_NULL     82      /* test if "str" null                 */
-#define FT_IF_S          83      /* test if "str" non-null             */
-#define FT_IF_V_EQ       84      /* test if "value" = literal          */
-#define FT_IF_V_NE       85      /* test if "value" != literal         */
-#define FT_IF_V_GT       86      /* test if "value" > literal          */
-#define FT_IF_MATCH      87      /* test if "str" contains literal     */
-#define FT_IF_AMATCH     88      /* test if "str" starts with literal  */
-#define FT_S_NULL        89      /* V = 1 if "str" null                */
-#define FT_S_NONNULL     90      /* V = 1 if "str" non-null            */
-#define FT_V_EQ          91      /* V = 1 if "value" = literal         */
-#define FT_V_NE          92      /* V = 1 if "value" != literal        */
-#define FT_V_GT          93      /* V = 1 if "value" > literal         */
-#define FT_V_MATCH       94      /* V = 1 if "str" contains literal    */
-#define FT_V_AMATCH      95      /* V = 1 if "str" starts with literal */
+#define FT_SAVESTR       78      /* save current str reg               */
+#define FT_DONE          79      /* stop formatting                    */
+#define FT_PAUSE         80      /* pause                              */
+#define FT_NOP           81      /* no-op                              */
+#define FT_GOTO          82      /* (relative) goto                    */
+#define FT_IF_S_NULL     83      /* test if "str" null                 */
+#define FT_IF_S          84      /* test if "str" non-null             */
+#define FT_IF_V_EQ       85      /* test if "value" = literal          */
+#define FT_IF_V_NE       86      /* test if "value" != literal         */
+#define FT_IF_V_GT       87      /* test if "value" > literal          */
+#define FT_IF_MATCH      88      /* test if "str" contains literal     */
+#define FT_IF_AMATCH     89      /* test if "str" starts with literal  */
+#define FT_S_NULL        90      /* V = 1 if "str" null                */
+#define FT_S_NONNULL     91      /* V = 1 if "str" non-null            */
+#define FT_V_EQ          92      /* V = 1 if "value" = literal         */
+#define FT_V_NE          93      /* V = 1 if "value" != literal        */
+#define FT_V_GT          94      /* V = 1 if "value" > literal         */
+#define FT_V_MATCH       95      /* V = 1 if "str" contains literal    */
+#define FT_V_AMATCH      96      /* V = 1 if "str" starts with literal */
 
 #define IF_FUNCS FT_S_NULL       /* start of "if" functions */
 
 #define IF_FUNCS FT_S_NULL       /* start of "if" functions */
index 59972d7..63bb04a 100644 (file)
@@ -290,6 +290,8 @@ kilo        expr    string  express in SI units: 15.9K, 2.3M, etc.
                        %(kilo) scales by factors of 1000,
 kibi   expr    string  express in IEC units: 15.5Ki, 2.2Mi.
                        %(kibi) scales by factors of 1024.
                        %(kilo) scales by factors of 1000,
 kibi   expr    string  express in IEC units: 15.5Ki, 2.2Mi.
                        %(kibi) scales by factors of 1024.
+ordinal        expr    string  Output ordinal suffix based on value
+                       of \fInum\fR (st, nd, rd, th)
 putstr expr            print \fIstr\fR
 putstrf        expr            print \fIstr\fR in a fixed width
 putnum expr            print \fInum\fR
 putstr expr            print \fIstr\fR
 putstrf        expr            print \fIstr\fR in a fixed width
 putnum expr            print \fInum\fR
index 925a063..97dc1fc 100644 (file)
@@ -163,6 +163,7 @@ static struct ftable functable[] = {
      { "trimr",      TF_EXPR,  FT_LS_TRIM,     0,              TFL_PUTS },
      { "kilo",       TF_EXPR,  FT_LS_KILO,     0,              TFL_PUTS },
      { "kibi",       TF_EXPR,  FT_LS_KIBI,     0,              TFL_PUTS },
      { "trimr",      TF_EXPR,  FT_LS_TRIM,     0,              TFL_PUTS },
      { "kilo",       TF_EXPR,  FT_LS_KILO,     0,              TFL_PUTS },
      { "kibi",       TF_EXPR,  FT_LS_KIBI,     0,              TFL_PUTS },
+     { "ordinal",    TF_EXPR,   FT_LS_ORDINAL,  0,             TFL_PUTS },
      { "compval",    TF_COMP,  FT_LV_COMP,     0,              TFL_PUTN },
      { "compflag",   TF_COMP,  FT_LV_COMPFLAG, 0,              TFL_PUTN },
      { "num",        TF_NUM,   FT_LV_LIT,      0,              TFL_PUTN },
      { "compval",    TF_COMP,  FT_LV_COMP,     0,              TFL_PUTN },
      { "compflag",   TF_COMP,  FT_LV_COMPFLAG, 0,              TFL_PUTN },
      { "num",        TF_NUM,   FT_LV_LIT,      0,              TFL_PUTN },
index c75a161..436b1ec 100644 (file)
@@ -576,6 +576,29 @@ fmt_scan (struct format *format, charstring_t scanlp, int width, int *dat,
                str = buffer;
            }
            break;
                str = buffer;
            }
            break;
+       case FT_LS_ORDINAL:
+           {
+               int digit = value % 10;
+               const char *suffix;
+
+               switch (digit) {
+               case 1:
+                   suffix = "st";
+                   break;
+               case 2:
+                   suffix = "nd";
+                   break;
+               case 3:
+                   suffix = "rd";
+                   break;
+               default:
+                   suffix = "th";
+               }
+
+               strncpy(buffer, suffix, sizeof(buffer));
+               str = buffer;
+           }
+           break;
        case FT_NUMF:
            cpnumber (scanlp, value, fmt->f_width, fmt->f_fill,
                      max - charstring_chars (scanlp));
        case FT_NUMF:
            cpnumber (scanlp, value, fmt->f_width, fmt->f_fill,
                      max - charstring_chars (scanlp));
index b5a4660..18c356a 100644 (file)
@@ -386,6 +386,7 @@ f_typestr(int t)
        case FT_LS_PRETTY: return "LS_PRETTY";
        case FT_LS_KILO: return "LS_KILO";
        case FT_LS_KIBI: return "LS_KIBI";
        case FT_LS_PRETTY: return "LS_PRETTY";
        case FT_LS_KILO: return "LS_KILO";
        case FT_LS_KIBI: return "LS_KIBI";
+       case FT_LS_ORDINAL: return "LS_ORDINAL";
        case FT_LV_SEC: return "LV_SEC";
        case FT_LV_MIN: return "LV_MIN";
        case FT_LV_HOUR: return "LV_HOUR";
        case FT_LV_SEC: return "LV_SEC";
        case FT_LV_MIN: return "LV_MIN";
        case FT_LV_HOUR: return "LV_HOUR";
index 49f2104..50804c9 100644 (file)
@@ -1083,6 +1083,7 @@ f_typestr(int t)
        X(LS_PRETTY);
        X(LS_KILO);
        X(LS_KIBI);
        X(LS_PRETTY);
        X(LS_KILO);
        X(LS_KIBI);
+       X(LS_ORDINAL);
        X(LV_SEC);
        X(LV_MIN);
        X(LV_HOUR);
        X(LV_SEC);
        X(LV_MIN);
        X(LV_HOUR);