summaryrefslogtreecommitdiffstats
path: root/html.c
diff options
context:
space:
mode:
authorKristaps Dzonsons <kristaps@bsd.lv>2009-09-17 23:35:41 +0000
committerKristaps Dzonsons <kristaps@bsd.lv>2009-09-17 23:35:41 +0000
commit0aaccad53ac39301c6f465c362365aa638aa67de (patch)
treeff505e204b9a46ee9e53b78a0b2bdd5743e47bd1 /html.c
parent3a350dac5953341e374453754c54ede07c25fac8 (diff)
downloadmandoc-0aaccad53ac39301c6f465c362365aa638aa67de.tar.gz
Consider html fixes, most importantly -tag and -hang (breaks in IE6, apparently).
Diffstat (limited to 'html.c')
-rw-r--r--html.c528
1 files changed, 438 insertions, 90 deletions
diff --git a/html.c b/html.c
index 76e5b9a0..88e3abb0 100644
--- a/html.c
+++ b/html.c
@@ -32,6 +32,7 @@
#define INDENT 5
#define HALFINDENT 3
+#define PX_MULT 8
enum htmltag {
TAG_HTML,
@@ -51,6 +52,9 @@ enum htmltag {
TAG_COL,
TAG_TR,
TAG_TD,
+ TAG_LI,
+ TAG_UL,
+ TAG_OL,
TAG_MAX
};
@@ -94,6 +98,9 @@ static const struct htmldata htmltags[TAG_MAX] = {
{"col", HTML_CLRLINE | HTML_NOSTACK}, /* TAG_COL */
{"tr", HTML_CLRLINE}, /* TAG_TR */
{"td", HTML_CLRLINE}, /* TAG_TD */
+ {"li", HTML_CLRLINE}, /* TAG_LI */
+ {"ul", HTML_CLRLINE}, /* TAG_UL */
+ {"ol", HTML_CLRLINE}, /* TAG_OL */
};
static const char *const htmlattrs[ATTR_MAX] = {
@@ -164,22 +171,36 @@ static void print_spec(struct html *, const char *, int);
static int a2width(const char *);
static int a2offs(const char *);
-static int mdoc_list_pre(MDOC_ARGS);
+static int mdoc_list_pre(MDOC_ARGS, int);
+static int mdoc_listitem_pre(MDOC_ARGS);
static int mdoc_root_pre(MDOC_ARGS);
-static int mdoc_hang_pre(MDOC_ARGS);
+static int mdoc_tbl_pre(MDOC_ARGS, int);
+static int mdoc_tbl_block_pre(MDOC_ARGS, int, int, int);
+static int mdoc_tbl_body_pre(MDOC_ARGS, int, int);
+static int mdoc_tbl_head_pre(MDOC_ARGS, int, int);
static int mdoc_ar_pre(MDOC_ARGS);
static int mdoc_bl_pre(MDOC_ARGS);
+static int mdoc_d1_pre(MDOC_ARGS);
+static void mdoc_dq_post(MDOC_ARGS);
+static int mdoc_dq_pre(MDOC_ARGS);
static int mdoc_fl_pre(MDOC_ARGS);
+static int mdoc_em_pre(MDOC_ARGS);
+static int mdoc_ex_pre(MDOC_ARGS);
static int mdoc_it_pre(MDOC_ARGS);
static int mdoc_nd_pre(MDOC_ARGS);
static int mdoc_nm_pre(MDOC_ARGS);
static int mdoc_ns_pre(MDOC_ARGS);
-static int mdoc_op_pre(MDOC_ARGS);
static void mdoc_op_post(MDOC_ARGS);
+static int mdoc_op_pre(MDOC_ARGS);
static int mdoc_pp_pre(MDOC_ARGS);
+static void mdoc_pq_post(MDOC_ARGS);
+static int mdoc_pq_pre(MDOC_ARGS);
static int mdoc_sh_pre(MDOC_ARGS);
+static void mdoc_sq_post(MDOC_ARGS);
+static int mdoc_sq_pre(MDOC_ARGS);
static int mdoc_ss_pre(MDOC_ARGS);
+static int mdoc_sx_pre(MDOC_ARGS);
static int mdoc_xr_pre(MDOC_ARGS);
static int mdoc_xx_pre(MDOC_ARGS);
@@ -196,8 +217,8 @@ static const struct htmlmdoc mdocs[MDOC_MAX] = {
{mdoc_sh_pre, NULL }, /* Sh */
{mdoc_ss_pre, NULL }, /* Ss */
{mdoc_pp_pre, NULL}, /* Pp */
- {NULL, NULL}, /* D1 */
- {NULL, NULL}, /* Dl */
+ {mdoc_d1_pre, NULL}, /* D1 */
+ {mdoc_d1_pre, NULL}, /* Dl */
{NULL, NULL}, /* Bd */
{NULL, NULL}, /* Ed */
{mdoc_bl_pre, NULL}, /* Bl */
@@ -211,7 +232,7 @@ static const struct htmlmdoc mdocs[MDOC_MAX] = {
{NULL, NULL}, /* Dv */
{NULL, NULL}, /* Er */
{NULL, NULL}, /* Ev */
- {NULL, NULL}, /* Ex */
+ {mdoc_ex_pre, NULL}, /* Ex */
{NULL, NULL}, /* Fa */
{NULL, NULL}, /* Fd */
{mdoc_fl_pre, NULL}, /* Fl */
@@ -254,10 +275,10 @@ static const struct htmlmdoc mdocs[MDOC_MAX] = {
{NULL, NULL}, /* Db */
{NULL, NULL}, /* Dc */
{NULL, NULL}, /* Do */
- {NULL, NULL}, /* Dq */
+ {mdoc_dq_pre, mdoc_dq_post}, /* Dq */
{NULL, NULL}, /* Ec */
{NULL, NULL}, /* Ef */
- {NULL, NULL}, /* Em */
+ {mdoc_em_pre, NULL}, /* Em */
{NULL, NULL}, /* Eo */
{mdoc_xx_pre, NULL}, /* Fx */
{NULL, NULL}, /* Ms */
@@ -267,8 +288,8 @@ static const struct htmlmdoc mdocs[MDOC_MAX] = {
{mdoc_xx_pre, NULL}, /* Ox */
{NULL, NULL}, /* Pc */
{NULL, NULL}, /* Pf */
- {NULL, NULL}, /* Po */
- {NULL, NULL}, /* Pq */
+ {mdoc_pq_pre, mdoc_pq_post}, /* Po */
+ {mdoc_pq_pre, mdoc_pq_post}, /* Pq */
{NULL, NULL}, /* Qc */
{NULL, NULL}, /* Ql */
{NULL, NULL}, /* Qo */
@@ -276,10 +297,10 @@ static const struct htmlmdoc mdocs[MDOC_MAX] = {
{NULL, NULL}, /* Re */
{NULL, NULL}, /* Rs */
{NULL, NULL}, /* Sc */
- {NULL, NULL}, /* So */
- {NULL, NULL}, /* Sq */
+ {mdoc_sq_pre, mdoc_sq_post}, /* So */
+ {mdoc_sq_pre, mdoc_sq_post}, /* Sq */
{NULL, NULL}, /* Sm */
- {NULL, NULL}, /* Sx */
+ {mdoc_sx_pre, NULL}, /* Sx */
{NULL, NULL}, /* Sy */
{NULL, NULL}, /* Tn */
{mdoc_xx_pre, NULL}, /* Ux */
@@ -406,7 +427,7 @@ print_gen_head(struct html *h)
meta0[0].key = ATTR_HTTPEQUIV;
meta0[0].val = "Content-Type";
meta0[1].key = ATTR_CONTENT;
- meta0[1].val = "text/html; charest-utf-8";
+ meta0[1].val = "text/html; charset=utf-8";
meta1[0].key = ATTR_NAME;
meta1[0].val = "resource-type";
@@ -663,11 +684,24 @@ print_encode(struct html *h, const char *p)
{
for (; *p; p++) {
- if ('\\' != *p) {
- putchar(*p);
+ if ('\\' == *p) {
+ print_escape(h, &p);
continue;
}
- print_escape(h, &p);
+ switch (*p) {
+ case ('<'):
+ printf("&lt;");
+ break;
+ case ('>'):
+ printf("&gt;");
+ break;
+ case ('&'):
+ printf("&amp;");
+ break;
+ default:
+ putchar(*p);
+ break;
+ }
}
}
@@ -885,11 +919,18 @@ mdoc_root_pre(MDOC_ARGS)
static int
mdoc_ss_pre(MDOC_ARGS)
{
+ struct htmlpair tag[2];
+
+ tag[0].key = ATTR_CLASS;
+ tag[0].val = "ssec";
+
+ tag[1].key = ATTR_STYLE;
+ tag[1].val = "margin-left: -20px;";
if (MDOC_BODY == n->type)
- print_otag(h, TAG_DIV, 0, NULL);
+ print_otag(h, TAG_DIV, 1, &tag);
if (MDOC_HEAD == n->type)
- print_otag(h, TAG_H2, 0, NULL);
+ print_otag(h, TAG_SPAN, 1, &tag);
return(1);
}
@@ -914,9 +955,13 @@ mdoc_fl_pre(MDOC_ARGS)
static int
mdoc_pp_pre(MDOC_ARGS)
{
+ struct htmlpair tag;
- print_otag(h, TAG_BR, 0, NULL);
- print_otag(h, TAG_BR, 0, NULL);
+ tag.key = ATTR_STYLE;
+ tag.val = "clear: both;";
+
+ print_otag(h, TAG_BR, 1, &tag);
+ print_otag(h, TAG_BR, 1, &tag);
return(0);
}
@@ -981,11 +1026,15 @@ mdoc_nm_pre(MDOC_ARGS)
static int
mdoc_sh_pre(MDOC_ARGS)
{
+ struct htmlpair tag;
+
+ tag.key = ATTR_CLASS;
+ tag.val = "sec";
if (MDOC_BODY == n->type)
- print_otag(h, TAG_DIV, 0, NULL);
+ print_otag(h, TAG_DIV, 1, &tag);
if (MDOC_HEAD == n->type)
- print_otag(h, TAG_H1, 0, NULL);
+ print_otag(h, TAG_SPAN, 1, &tag);
return(1);
}
@@ -1074,91 +1123,231 @@ mdoc_xx_pre(MDOC_ARGS)
static int
-mdoc_hang_pre(MDOC_ARGS)
+mdoc_tbl_block_pre(MDOC_ARGS, int w, int o, int c)
{
- int i, width, offs;
- struct htmlpair tag;
- char buf[BUFSIZ];
- const struct mdoc_node *bl;
+ struct htmlpair tag;
+ char buf[BUFSIZ];
- if (MDOC_BODY == n->type) {
- print_otag(h, TAG_DIV, 0, NULL);
- return(1);
+ buf[BUFSIZ - 1] = 0;
+
+ snprintf(buf, BUFSIZ - 1, "margin-left: %dpx; "
+ "clear: both;", w + o);
+
+ if ( ! c)
+ (void)strlcat(buf, " padding-top: 1em;", BUFSIZ);
+
+ tag.key = ATTR_STYLE;
+ tag.val = buf;
+
+ print_otag(h, TAG_DIV, 1, &tag);
+ return(1);
+}
+
+
+static int
+mdoc_tbl_body_pre(MDOC_ARGS, int t, int w)
+{
+ struct htmlpair tag;
+ char buf[BUFSIZ];
+ int i;
+
+ buf[BUFSIZ - 1] = 0;
+ i = 0;
+
+ switch (t) {
+ case (MDOC_Tag):
+ i++;
+ (void)snprintf(buf, BUFSIZ - 1,
+ "clear: right; float: left; "
+ "width: 100%%;");
+ tag.key = ATTR_STYLE;
+ tag.val = buf;
+ break;
+ default:
+ break;
}
+ print_otag(h, TAG_DIV, i, &tag);
+ return(1);
+}
+
+
+static int
+mdoc_tbl_head_pre(MDOC_ARGS, int type, int w)
+{
+ struct htmlpair tag;
+ char buf[BUFSIZ];
+ int i;
+
+ buf[BUFSIZ - 1] = 0;
+ i = 0;
+
+ switch (type) {
+ case (MDOC_Tag):
+ i++;
+ (void)snprintf(buf, BUFSIZ - 1,
+ "clear: left; float: left; "
+ "padding-right: 1em; "
+ "margin-left: -%dpx;", w);
+ tag.key = ATTR_STYLE;
+ tag.val = buf;
+ break;
+ default:
+ i++;
+ (void)snprintf(buf, BUFSIZ - 1,
+ "clear: left; float: left; "
+ "margin-left: -%dpx; "
+ "padding-right: 1em;", w);
+ tag.key = ATTR_STYLE;
+ tag.val = buf;
+ break;
+ }
+
+ print_otag(h, TAG_DIV, i, &tag);
+ return(1);
+}
+
+
+static int
+mdoc_tbl_pre(MDOC_ARGS, int type)
+{
+ int i, w, o, c;
+ const struct mdoc_node *bl;
+
bl = n->parent->parent;
if (MDOC_BLOCK != n->type)
bl = bl->parent;
+ /* FIXME: fmt_vspace() equivalent. */
+
assert(bl->args);
- for (width = i = 0; i < (int)bl->args->argc; i++)
+ w = o = c = 0;
+
+ for (i = 0; i < (int)bl->args->argc; i++)
if (MDOC_Width == bl->args->argv[i].arg) {
assert(bl->args->argv[i].sz);
- width = a2width(bl->args->argv[i].value[0]);
- break;
+ w = a2width(bl->args->argv[i].value[0]);
} else if (MDOC_Offset == bl->args->argv[i].arg) {
assert(bl->args->argv[i].sz);
- offs = a2offs(bl->args->argv[i].value[0]);
- break;
- }
+ o = a2offs(bl->args->argv[i].value[0]);
+ } else if (MDOC_Compact == bl->args->argv[i].arg)
+ c = 1;
+
+ if (0 == w)
+ w = 10;
- if (0 == width)
- width = 10;
+ w *= PX_MULT;
+ o *= PX_MULT;
+
+ switch (n->type) {
+ case (MDOC_BLOCK):
+ break;
+ case (MDOC_HEAD):
+ return(mdoc_tbl_head_pre(m, n, h, type, w));
+ case (MDOC_BODY):
+ return(mdoc_tbl_body_pre(m, n, h, type, w));
+ default:
+ abort();
+ /* NOTREACHED */
+ }
- width *= 10;
+ return(mdoc_tbl_block_pre(m, n, h, w, o, c));
+}
- if (MDOC_BLOCK == n->type)
- snprintf(buf, BUFSIZ - 1, "margin-left: %dpx; "
- "clear: both;", width);
- else
- snprintf(buf, BUFSIZ - 1, "float: left; "
- "margin-left: -%dpx;", width);
+
+/* ARGSUSED */
+static int
+mdoc_listitem_pre(MDOC_ARGS)
+{
+ int i, w, o, c;
+ const struct mdoc_node *bl;
+ struct htmlpair tag;
+ char buf[BUFSIZ];
+
+ /* FIXME: fmt_vspace() equivalent. */
+
+ if (MDOC_BLOCK != n->type)
+ return(1);
+
+ bl = n->parent->parent;
+ assert(bl);
+
+ w = o = c = 0;
+
+ for (i = 0; i < (int)bl->args->argc; i++)
+ if (MDOC_Width == bl->args->argv[i].arg) {
+ assert(bl->args->argv[i].sz);
+ w = a2width(bl->args->argv[i].value[0]);
+ } else if (MDOC_Offset == bl->args->argv[i].arg) {
+ assert(bl->args->argv[i].sz);
+ o = a2offs(bl->args->argv[i].value[0]);
+ } else if (MDOC_Compact == bl->args->argv[i].arg)
+ c = 1;
+
+ o *= PX_MULT;
+ w *= PX_MULT;
+
+ buf[BUFSIZ - 1] = 0;
+
+ snprintf(buf, BUFSIZ - 1, "margin-left: %dpx;", o);
+
+ if ( ! c)
+ (void)strlcat(buf, " padding-top: 1em;", BUFSIZ);
tag.key = ATTR_STYLE;
tag.val = buf;
- print_otag(h, TAG_DIV, 1, &tag);
-
+ print_otag(h, TAG_LI, 1, &tag);
return(1);
}
+/* ARGSUSED */
static int
-mdoc_list_pre(MDOC_ARGS)
+mdoc_list_pre(MDOC_ARGS, int type)
{
- /* TODO */
- return(0);
+ switch (type) {
+ case (MDOC_Enum):
+ print_otag(h, TAG_OL, 0, NULL);
+ break;
+ case (MDOC_Bullet):
+ print_otag(h, TAG_UL, 0, NULL);
+ break;
+ default:
+ break;
+ }
+
+ return(1);
}
static int
-mdoc_it_pre(MDOC_ARGS)
+mdoc_bl_pre(MDOC_ARGS)
{
- int i, len;
- const struct mdoc_node *bl;
+ int i, len, type;
- if (MDOC_BLOCK == n->type)
- bl = n->parent->parent;
- else
- bl = n->parent->parent->parent;
+ if (MDOC_BLOCK != n->type)
+ return(1);
- assert(bl->args);
- len = (int)bl->args->argc;
+ assert(n->args);
+ len = (int)n->args->argc;
for (i = 0; i < len; i++)
- switch (bl->args->argv[i].arg) {
+ switch ((type = n->args->argv[i].arg)) {
+ case (MDOC_Enum):
+ /* FALLTHROUGH */
case (MDOC_Bullet):
+ return(mdoc_list_pre(m, n, h, type));
+ case (MDOC_Tag):
/* FALLTHROUGH */
- case (MDOC_Dash):
+ case (MDOC_Hang):
/* FALLTHROUGH */
- case (MDOC_Enum):
+ case (MDOC_Dash):
/* FALLTHROUGH */
case (MDOC_Hyphen):
- return(0); /* TODO */
- case (MDOC_Tag):
- return(0);
+ /* FALLTHROUGH */
case (MDOC_Inset):
/* FALLTHROUGH */
case (MDOC_Diag):
@@ -1167,14 +1356,10 @@ mdoc_it_pre(MDOC_ARGS)
/* FALLTHROUGH */
case (MDOC_Column):
/* FALLTHROUGH */
- case (MDOC_Hang):
- return(mdoc_hang_pre(m, n, h));
- /* FALLTHROUGH */
case (MDOC_Ohang):
- return(0); /* TODO */
+ return(1);
default:
- abort();
- /* NOTREACHED */
+ break;
}
abort();
@@ -1183,28 +1368,33 @@ mdoc_it_pre(MDOC_ARGS)
static int
-mdoc_bl_pre(MDOC_ARGS)
+mdoc_it_pre(MDOC_ARGS)
{
- int i, len;
+ int i, len, type;
+ const struct mdoc_node *bl;
- if (MDOC_BLOCK != n->type)
- return(1);
+ if (MDOC_BLOCK == n->type)
+ bl = n->parent->parent;
+ else
+ bl = n->parent->parent->parent;
- assert(n->args);
- len = (int)n->args->argc;
+ assert(bl->args);
+ len = (int)bl->args->argc;
for (i = 0; i < len; i++)
- switch (n->args->argv[i].arg) {
- case (MDOC_Bullet):
- /* FALLTHROUGH */
- case (MDOC_Dash):
+ switch ((type = bl->args->argv[i].arg)) {
+ case (MDOC_Tag):
/* FALLTHROUGH */
+ case (MDOC_Hang):
+ return(mdoc_tbl_pre(m, n, h, type));
case (MDOC_Enum):
/* FALLTHROUGH */
+ case (MDOC_Bullet):
+ return(mdoc_listitem_pre(m, n, h));
+ case (MDOC_Dash):
+ /* FALLTHROUGH */
case (MDOC_Hyphen):
- return(mdoc_list_pre(m, n, h));
- case (MDOC_Tag):
- return(0);
+ /* FALLTHROUGH */
case (MDOC_Inset):
/* FALLTHROUGH */
case (MDOC_Diag):
@@ -1213,15 +1403,173 @@ mdoc_bl_pre(MDOC_ARGS)
/* FALLTHROUGH */
case (MDOC_Column):
/* FALLTHROUGH */
- case (MDOC_Hang):
- return(1);
case (MDOC_Ohang):
- return(0); /* TODO */
+ return(0);
default:
- abort();
- /* NOTREACHED */
+ break;
}
abort();
/* NOTREACHED */
}
+
+
+/* ARGSUSED */
+static int
+mdoc_ex_pre(MDOC_ARGS)
+{
+ const struct mdoc_node *nn;
+ struct tag *t;
+ struct htmlpair tag;
+
+ print_text(h, "The");
+
+ tag.key = ATTR_CLASS;
+ tag.val = "utility";
+
+ for (nn = n->child; nn; nn = nn->next) {
+ t = print_otag(h, TAG_SPAN, 1, &tag);
+ print_text(h, nn->string);
+ print_tagq(h, t);
+
+ h->flags |= HTML_NOSPACE;
+
+ if (nn->next && NULL == nn->next->next)
+ print_text(h, ", and");
+ else if (nn->next)
+ print_text(h, ",");
+ else
+ h->flags &= ~HTML_NOSPACE;
+ }
+
+ if (n->child->next)
+ print_text(h, "utilities exit");
+ else
+ print_text(h, "utility exits");
+
+ print_text(h, "0 on success, and >0 if an error occurs.");
+ return(0);
+}
+
+
+/* ARGSUSED */
+static int
+mdoc_dq_pre(MDOC_ARGS)
+{
+
+ if (MDOC_BODY != n->type)
+ return(1);
+ print_text(h, "\\(lq");
+ h->flags |= HTML_NOSPACE;
+ return(1);
+}
+
+
+/* ARGSUSED */
+static void
+mdoc_dq_post(MDOC_ARGS)
+{
+
+ if (MDOC_BODY != n->type)
+ return;
+ h->flags |= HTML_NOSPACE;
+ print_text(h, "\\(rq");
+}
+
+
+/* ARGSUSED */
+static int
+mdoc_pq_pre(MDOC_ARGS)
+{
+
+ if (MDOC_BODY != n->type)
+ return(1);
+ print_text(h, "\\&(");
+ h->flags |= HTML_NOSPACE;
+ return(1);
+}
+
+
+/* ARGSUSED */
+static void
+mdoc_pq_post(MDOC_ARGS)
+{
+
+ if (MDOC_BODY != n->type)
+ return;
+ print_text(h, ")");
+}
+
+
+/* ARGSUSED */
+static int
+mdoc_sq_pre(MDOC_ARGS)
+{
+
+ if (MDOC_BODY != n->type)
+ return(1);
+ print_text(h, "\\(oq");
+ h->flags |= HTML_NOSPACE;
+ return(1);
+}
+
+
+/* ARGSUSED */
+static void
+mdoc_sq_post(MDOC_ARGS)
+{
+
+ if (MDOC_BODY != n->type)
+ return;
+ h->flags |= HTML_NOSPACE;
+ print_text(h, "\\(aq");
+}
+
+
+/* ARGSUSED */
+static int
+mdoc_em_pre(MDOC_ARGS)
+{
+ struct htmlpair tag;
+
+ tag.key = ATTR_CLASS;
+ tag.val = "emph";
+
+ print_otag(h, TAG_SPAN, 1, &tag);
+ return(1);
+}
+
+
+/* ARGSUSED */
+static int
+mdoc_d1_pre(MDOC_ARGS)
+{
+ struct htmlpair tag;
+ char buf[BUFSIZ];
+
+ if (MDOC_BLOCK != n->type)
+ return(1);
+
+ (void)snprintf(buf, BUFSIZ - 1, "margin-left: %dpx",
+ INDENT * PX_MULT);
+
+ tag.key = ATTR_STYLE;
+ tag.val = buf;
+
+ print_otag(h, TAG_DIV, 1, &tag);
+ return(1);
+}
+
+
+/* ARGSUSED */
+static int
+mdoc_sx_pre(MDOC_ARGS)
+{
+ struct htmlpair tag;
+
+ tag.key = ATTR_HREF;
+ tag.val = "#";
+
+ print_otag(h, TAG_A, 1, &tag);
+ return(1);
+}