]> git.cameronkatri.com Git - mandoc.git/blobdiff - man_term.c
First check-in of PostScript output. This does not change any logic
[mandoc.git] / man_term.c
index c15354c3919facdad81f571e4ce47060eb8d85b8..a7a1a652243e3182ca21941cad596a53e3884930 100644 (file)
@@ -1,4 +1,4 @@
-/*     $Id: man_term.c,v 1.57 2010/03/23 11:30:48 kristaps Exp $ */
+/*     $Id: man_term.c,v 1.73 2010/06/07 20:57:09 kristaps Exp $ */
 /*
  * Copyright (c) 2008, 2009 Kristaps Dzonsons <kristaps@kth.se>
  *
@@ -26,6 +26,7 @@
 #include <stdlib.h>
 #include <string.h>
 
+#include "mandoc.h"
 #include "out.h"
 #include "man.h"
 #include "term.h"
@@ -72,12 +73,10 @@ struct      termact {
 static int               a2width(const struct man_node *);
 static int               a2height(const struct man_node *);
 
-static void              print_man_head(struct termp *, 
-                               const struct man_meta *);
+static void              print_man_head(struct termp *, const void *);
 static void              print_man_nodelist(DECL_ARGS);
 static void              print_man_node(DECL_ARGS);
-static void              print_man_foot(struct termp *, 
-                               const struct man_meta *);
+static void              print_man_foot(struct termp *, const void *);
 static void              print_bvspace(struct termp *, 
                                const struct man_node *);
 
@@ -142,6 +141,7 @@ static      const struct termact termacts[MAN_MAX] = {
        { pre_sp, NULL, MAN_NOTEXT }, /* Sp */
        { pre_nf, NULL, 0 }, /* Vb */
        { pre_fi, NULL, 0 }, /* Ve */
+       { pre_ign, NULL, 0 }, /* AT */
 };
 
 
@@ -156,10 +156,14 @@ terminal_man(void *arg, const struct man *man)
 
        p = (struct termp *)arg;
 
+       p->overstep = 0;
+       p->maxrmargin = p->defrmargin;
+
+       term_begin(p, print_man_head, print_man_foot, man_meta(man));
+
        if (NULL == p->symtab)
                switch (p->enc) {
                case (TERMENC_ASCII):
-                       p->maxrmargin = 65;
                        p->symtab = chars_init(CHARS_ASCII);
                        break;
                default:
@@ -170,7 +174,6 @@ terminal_man(void *arg, const struct man *man)
        n = man_node(man);
        m = man_meta(man);
 
-       print_man_head(p, m);
        p->flags |= TERMP_NOSPACE;
 
        mt.fl = 0;
@@ -179,7 +182,8 @@ terminal_man(void *arg, const struct man *man)
 
        if (n->child)
                print_man_nodelist(p, &mt, n->child, m);
-       print_man_foot(p, m);
+
+       term_end(p);
 }
 
 
@@ -252,7 +256,6 @@ static int
 pre_fi(DECL_ARGS)
 {
 
-       p->rmargin = p->maxrmargin = 65;
        mt->fl &= ~MANT_LITERAL;
        return(1);
 }
@@ -263,10 +266,7 @@ static int
 pre_nf(DECL_ARGS)
 {
 
-       p->rmargin = p->maxrmargin = 78;
-       term_newln(p);
        mt->fl |= MANT_LITERAL;
-
        return(MAN_Vb != n->tok);
 }
 
@@ -365,7 +365,7 @@ pre_sp(DECL_ARGS)
 
        if (0 == len)
                term_newln(p);
-       for (i = 0; i < len; i++)
+       for (i = 0; i <= len; i++)
                term_vspace(p);
 
        return(0);
@@ -480,7 +480,6 @@ pre_IP(DECL_ARGS)
                break;
        case (MAN_HEAD):
                p->flags |= TERMP_NOBREAK;
-               p->flags |= TERMP_TWOSPACE;
                break;
        case (MAN_BLOCK):
                print_bvspace(p, n);
@@ -541,7 +540,6 @@ post_IP(DECL_ARGS)
        case (MAN_HEAD):
                term_flushln(p);
                p->flags &= ~TERMP_NOBREAK;
-               p->flags &= ~TERMP_TWOSPACE;
                p->rmargin = p->maxrmargin;
                break;
        case (MAN_BODY):
@@ -706,6 +704,9 @@ pre_SH(DECL_ARGS)
                if (n->prev && MAN_SH == n->prev->tok)
                        if (NULL == n->prev->body->child)
                                break;
+               /* If the first macro, no vspae. */
+               if (NULL == n->prev)
+                       break;
                term_vspace(p);
                break;
        case (MAN_HEAD):
@@ -783,6 +784,8 @@ post_RS(DECL_ARGS)
        case (MAN_BLOCK):
                mt->offset = mt->lmargin = INDENT;
                break;
+       case (MAN_HEAD):
+               break;
        default:
                term_newln(p);
                p->offset = INDENT;
@@ -794,6 +797,7 @@ post_RS(DECL_ARGS)
 static void
 print_man_node(DECL_ARGS)
 {
+       size_t           rm, rmax;
        int              c;
 
        c = 1;
@@ -810,8 +814,13 @@ print_man_node(DECL_ARGS)
                /* FIXME: this means that macro lines are munged!  */
 
                if (MANT_LITERAL & mt->fl) {
+                       rm = p->rmargin;
+                       rmax = p->maxrmargin;
+                       p->rmargin = p->maxrmargin = TERM_MAXMARGIN;
                        p->flags |= TERMP_NOSPACE;
                        term_flushln(p);
+                       p->rmargin = rm;
+                       p->maxrmargin = rmax;
                }
                break;
        default:
@@ -831,6 +840,9 @@ print_man_node(DECL_ARGS)
                if ( ! (MAN_NOTEXT & termacts[n->tok].flags))
                        term_fontrepl(p, TERMFONT_NONE);
        }
+
+       if (MAN_EOS & n->flags)
+               p->flags |= TERMP_SENTENCE;
 }
 
 
@@ -846,15 +858,23 @@ print_man_nodelist(DECL_ARGS)
 
 
 static void
-print_man_foot(struct termp *p, const struct man_meta *meta)
+print_man_foot(struct termp *p, const void *arg)
 {
        char            buf[DATESIZ];
+       const struct man_meta *meta;
+
+       meta = (const struct man_meta *)arg;
 
        term_fontrepl(p, TERMFONT_NONE);
 
-       time2a(meta->date, buf, DATESIZ);
+       if (meta->rawdate)
+               strlcpy(buf, meta->rawdate, DATESIZ);
+       else
+               time2a(meta->date, buf, DATESIZ);
 
        term_vspace(p);
+       term_vspace(p);
+       term_vspace(p);
 
        p->flags |= TERMP_NOSPACE | TERMP_NOBREAK;
        p->rmargin = p->maxrmargin - strlen(buf);
@@ -877,12 +897,22 @@ print_man_foot(struct termp *p, const struct man_meta *meta)
 
 
 static void
-print_man_head(struct termp *p, const struct man_meta *m)
+print_man_head(struct termp *p, const void *arg)
 {
        char            buf[BUFSIZ], title[BUFSIZ];
        size_t          buflen, titlen;
+       const struct man_meta *m;
+
+       m = (const struct man_meta *)arg;
+
+       /*
+        * Note that old groff would spit out some spaces before the
+        * header.  We discontinue this strange behaviour, but at one
+        * point we did so here.
+        */
 
        p->rmargin = p->maxrmargin;
+
        p->offset = 0;
        buf[0] = title[0] = '\0';
 
@@ -890,7 +920,7 @@ print_man_head(struct termp *p, const struct man_meta *m)
                strlcpy(buf, m->vol, BUFSIZ);
        buflen = strlen(buf);
 
-       snprintf(title, BUFSIZ, "%s(%d)", m->title, m->msec);
+       snprintf(title, BUFSIZ, "%s(%s)", m->title, m->msec);
        titlen = strlen(title);
 
        p->offset = 0;
@@ -922,4 +952,13 @@ print_man_head(struct termp *p, const struct man_meta *m)
        p->rmargin = p->maxrmargin;
        p->offset = 0;
        p->flags &= ~TERMP_NOSPACE;
+
+       /* 
+        * Groff likes to have some leading spaces before content.  Well
+        * that's fine by me.
+        */
+
+       term_vspace(p);
+       term_vspace(p);
+       term_vspace(p);
 }