Annotation of src/usr.bin/mandoc/man_html.c, Revision 1.28
1.28 ! schwarze 1: /* $Id: man_html.c,v 1.27 2010/12/25 13:23:03 schwarze Exp $ */
1.1 schwarze 2: /*
1.17 schwarze 3: * Copyright (c) 2008, 2009, 2010 Kristaps Dzonsons <kristaps@bsd.lv>
1.1 schwarze 4: *
5: * Permission to use, copy, modify, and distribute this software for any
6: * purpose with or without fee is hereby granted, provided that the above
7: * copyright notice and this permission notice appear in all copies.
8: *
9: * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10: * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11: * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12: * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13: * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14: * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15: * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16: */
17: #include <sys/types.h>
18:
19: #include <assert.h>
20: #include <ctype.h>
21: #include <stdio.h>
22: #include <stdlib.h>
23: #include <string.h>
24:
1.14 schwarze 25: #include "mandoc.h"
1.1 schwarze 26: #include "out.h"
27: #include "html.h"
28: #include "man.h"
29: #include "main.h"
30:
31: /* TODO: preserve ident widths. */
1.2 schwarze 32: /* FIXME: have PD set the default vspace width. */
1.1 schwarze 33:
34: #define INDENT 5
35: #define HALFINDENT 3
36:
37: #define MAN_ARGS const struct man_meta *m, \
38: const struct man_node *n, \
1.18 schwarze 39: struct mhtml *mh, \
1.1 schwarze 40: struct html *h
41:
1.18 schwarze 42: struct mhtml {
43: int fl;
44: #define MANH_LITERAL (1 << 0) /* literal context */
45: };
46:
1.1 schwarze 47: struct htmlman {
48: int (*pre)(MAN_ARGS);
49: int (*post)(MAN_ARGS);
50: };
51:
52: static void print_man(MAN_ARGS);
53: static void print_man_head(MAN_ARGS);
54: static void print_man_nodelist(MAN_ARGS);
55: static void print_man_node(MAN_ARGS);
56:
57: static int a2width(const struct man_node *,
58: struct roffsu *);
59:
60: static int man_alt_pre(MAN_ARGS);
61: static int man_br_pre(MAN_ARGS);
62: static int man_ign_pre(MAN_ARGS);
1.18 schwarze 63: static int man_in_pre(MAN_ARGS);
64: static int man_literal_pre(MAN_ARGS);
1.1 schwarze 65: static void man_root_post(MAN_ARGS);
66: static int man_root_pre(MAN_ARGS);
67: static int man_B_pre(MAN_ARGS);
68: static int man_HP_pre(MAN_ARGS);
69: static int man_I_pre(MAN_ARGS);
70: static int man_IP_pre(MAN_ARGS);
71: static int man_PP_pre(MAN_ARGS);
72: static int man_RS_pre(MAN_ARGS);
73: static int man_SH_pre(MAN_ARGS);
74: static int man_SM_pre(MAN_ARGS);
75: static int man_SS_pre(MAN_ARGS);
76:
77: static const struct htmlman mans[MAN_MAX] = {
78: { man_br_pre, NULL }, /* br */
79: { NULL, NULL }, /* TH */
80: { man_SH_pre, NULL }, /* SH */
81: { man_SS_pre, NULL }, /* SS */
82: { man_IP_pre, NULL }, /* TP */
83: { man_PP_pre, NULL }, /* LP */
84: { man_PP_pre, NULL }, /* PP */
85: { man_PP_pre, NULL }, /* P */
86: { man_IP_pre, NULL }, /* IP */
87: { man_HP_pre, NULL }, /* HP */
88: { man_SM_pre, NULL }, /* SM */
1.26 schwarze 89: { man_SM_pre, NULL }, /* SB */
1.1 schwarze 90: { man_alt_pre, NULL }, /* BI */
91: { man_alt_pre, NULL }, /* IB */
92: { man_alt_pre, NULL }, /* BR */
93: { man_alt_pre, NULL }, /* RB */
94: { NULL, NULL }, /* R */
95: { man_B_pre, NULL }, /* B */
96: { man_I_pre, NULL }, /* I */
97: { man_alt_pre, NULL }, /* IR */
98: { man_alt_pre, NULL }, /* RI */
99: { NULL, NULL }, /* na */
100: { man_br_pre, NULL }, /* sp */
1.18 schwarze 101: { man_literal_pre, NULL }, /* nf */
102: { man_literal_pre, NULL }, /* fi */
1.1 schwarze 103: { NULL, NULL }, /* RE */
104: { man_RS_pre, NULL }, /* RS */
105: { man_ign_pre, NULL }, /* DT */
106: { man_ign_pre, NULL }, /* UC */
1.2 schwarze 107: { man_ign_pre, NULL }, /* PD */
1.13 schwarze 108: { man_ign_pre, NULL }, /* AT */
1.18 schwarze 109: { man_in_pre, NULL }, /* in */
1.19 schwarze 110: { NULL, NULL }, /* TS */
111: { NULL, NULL }, /* TE */
1.23 schwarze 112: { man_ign_pre, NULL }, /* ft */
1.1 schwarze 113: };
114:
115:
116: void
117: html_man(void *arg, const struct man *m)
118: {
119: struct html *h;
120: struct tag *t;
1.18 schwarze 121: struct mhtml mh;
1.1 schwarze 122:
123: h = (struct html *)arg;
124:
1.5 schwarze 125: print_gen_decls(h);
1.1 schwarze 126:
1.18 schwarze 127: memset(&mh, 0, sizeof(struct mhtml));
128:
1.1 schwarze 129: t = print_otag(h, TAG_HTML, 0, NULL);
1.18 schwarze 130: print_man(man_meta(m), man_node(m), &mh, h);
1.1 schwarze 131: print_tagq(h, t);
132:
133: printf("\n");
134: }
135:
136:
137: static void
138: print_man(MAN_ARGS)
139: {
140: struct tag *t;
141:
142: t = print_otag(h, TAG_HEAD, 0, NULL);
1.18 schwarze 143: print_man_head(m, n, mh, h);
1.1 schwarze 144: print_tagq(h, t);
1.25 schwarze 145:
1.1 schwarze 146: t = print_otag(h, TAG_BODY, 0, NULL);
1.18 schwarze 147: print_man_nodelist(m, n, mh, h);
1.1 schwarze 148: print_tagq(h, t);
149: }
150:
151:
152: /* ARGSUSED */
153: static void
154: print_man_head(MAN_ARGS)
155: {
156:
157: print_gen_head(h);
158: bufinit(h);
1.10 schwarze 159: buffmt(h, "%s(%s)", m->title, m->msec);
1.1 schwarze 160:
161: print_otag(h, TAG_TITLE, 0, NULL);
162: print_text(h, h->buf);
163: }
164:
165:
166: static void
167: print_man_nodelist(MAN_ARGS)
168: {
169:
1.18 schwarze 170: print_man_node(m, n, mh, h);
1.1 schwarze 171: if (n->next)
1.18 schwarze 172: print_man_nodelist(m, n->next, mh, h);
1.1 schwarze 173: }
174:
175:
176: static void
177: print_man_node(MAN_ARGS)
178: {
179: int child;
180: struct tag *t;
181:
182: child = 1;
1.2 schwarze 183: t = h->tags.head;
1.1 schwarze 184:
185: bufinit(h);
186:
1.7 schwarze 187: /*
188: * FIXME: embedded elements within next-line scopes (e.g., `br'
189: * within an empty `B') will cause formatting to be forgotten
190: * due to scope closing out.
191: */
192:
1.1 schwarze 193: switch (n->type) {
194: case (MAN_ROOT):
1.18 schwarze 195: child = man_root_pre(m, n, mh, h);
1.1 schwarze 196: break;
197: case (MAN_TEXT):
198: print_text(h, n->string);
1.18 schwarze 199:
200: if (MANH_LITERAL & mh->fl)
201: print_otag(h, TAG_BR, 0, NULL);
202:
1.4 schwarze 203: return;
1.1 schwarze 204: default:
1.4 schwarze 205: /*
206: * Close out scope of font prior to opening a macro
207: * scope. Assert that the metafont is on the top of the
208: * stack (it's never nested).
209: */
1.27 schwarze 210: if (HTMLFONT_NONE != h->metac) {
211: h->metal = h->metac;
212: h->metac = HTMLFONT_NONE;
1.4 schwarze 213: }
1.1 schwarze 214: if (mans[n->tok].pre)
1.18 schwarze 215: child = (*mans[n->tok].pre)(m, n, mh, h);
1.1 schwarze 216: break;
217: }
218:
219: if (child && n->child)
1.18 schwarze 220: print_man_nodelist(m, n->child, mh, h);
1.1 schwarze 221:
1.4 schwarze 222: /* This will automatically close out any font scope. */
1.1 schwarze 223: print_stagq(h, t);
224:
225: bufinit(h);
226:
227: switch (n->type) {
228: case (MAN_ROOT):
1.18 schwarze 229: man_root_post(m, n, mh, h);
1.1 schwarze 230: break;
231: case (MAN_TEXT):
232: break;
233: default:
234: if (mans[n->tok].post)
1.18 schwarze 235: (*mans[n->tok].post)(m, n, mh, h);
1.1 schwarze 236: break;
237: }
238: }
239:
240:
241: static int
242: a2width(const struct man_node *n, struct roffsu *su)
243: {
244:
245: if (MAN_TEXT != n->type)
246: return(0);
247: if (a2roffsu(n->string, su, SCALE_BU))
248: return(1);
249:
250: return(0);
251: }
252:
253:
254: /* ARGSUSED */
255: static int
256: man_root_pre(MAN_ARGS)
257: {
1.26 schwarze 258: struct htmlpair tag[3];
1.1 schwarze 259: struct tag *t, *tt;
260: char b[BUFSIZ], title[BUFSIZ];
261:
262: b[0] = 0;
263: if (m->vol)
264: (void)strlcat(b, m->vol, BUFSIZ);
265:
1.10 schwarze 266: snprintf(title, BUFSIZ - 1, "%s(%s)", m->title, m->msec);
1.1 schwarze 267:
1.26 schwarze 268: PAIR_SUMMARY_INIT(&tag[0], "Document Header");
269: PAIR_CLASS_INIT(&tag[1], "head");
270: if (NULL == h->style) {
271: PAIR_INIT(&tag[2], ATTR_WIDTH, "100%");
272: t = print_otag(h, TAG_TABLE, 3, tag);
273: PAIR_INIT(&tag[0], ATTR_WIDTH, "30%");
274: print_otag(h, TAG_COL, 1, tag);
275: print_otag(h, TAG_COL, 1, tag);
276: print_otag(h, TAG_COL, 1, tag);
277: } else
278: t = print_otag(h, TAG_TABLE, 2, tag);
279:
280: print_otag(h, TAG_TBODY, 0, NULL);
1.3 schwarze 281:
1.1 schwarze 282: tt = print_otag(h, TAG_TR, 0, NULL);
283:
1.25 schwarze 284: PAIR_CLASS_INIT(&tag[0], "head-ltitle");
1.1 schwarze 285: print_otag(h, TAG_TD, 1, tag);
1.25 schwarze 286:
1.1 schwarze 287: print_text(h, title);
288: print_stagq(h, tt);
289:
1.25 schwarze 290: PAIR_CLASS_INIT(&tag[0], "head-vol");
1.26 schwarze 291: if (NULL == h->style) {
292: PAIR_INIT(&tag[1], ATTR_ALIGN, "center");
293: print_otag(h, TAG_TD, 2, tag);
294: } else
295: print_otag(h, TAG_TD, 1, tag);
1.25 schwarze 296:
1.1 schwarze 297: print_text(h, b);
298: print_stagq(h, tt);
299:
1.25 schwarze 300: PAIR_CLASS_INIT(&tag[0], "head-rtitle");
1.26 schwarze 301: if (NULL == h->style) {
302: PAIR_INIT(&tag[1], ATTR_ALIGN, "right");
303: print_otag(h, TAG_TD, 2, tag);
304: } else
305: print_otag(h, TAG_TD, 1, tag);
1.25 schwarze 306:
1.1 schwarze 307: print_text(h, title);
308: print_tagq(h, t);
309: return(1);
310: }
311:
312:
313: /* ARGSUSED */
314: static void
315: man_root_post(MAN_ARGS)
316: {
1.26 schwarze 317: struct htmlpair tag[3];
1.1 schwarze 318: struct tag *t, *tt;
1.2 schwarze 319: char b[DATESIZ];
1.1 schwarze 320:
1.15 schwarze 321: if (m->rawdate)
322: strlcpy(b, m->rawdate, DATESIZ);
323: else
324: time2a(m->date, b, DATESIZ);
1.1 schwarze 325:
1.26 schwarze 326: PAIR_SUMMARY_INIT(&tag[0], "Document Footer");
327: PAIR_CLASS_INIT(&tag[1], "foot");
328: if (NULL == h->style) {
329: PAIR_INIT(&tag[2], ATTR_WIDTH, "100%");
330: t = print_otag(h, TAG_TABLE, 3, tag);
331: PAIR_INIT(&tag[0], ATTR_WIDTH, "50%");
332: print_otag(h, TAG_COL, 1, tag);
333: print_otag(h, TAG_COL, 1, tag);
334: } else
335: t = print_otag(h, TAG_TABLE, 2, tag);
1.3 schwarze 336:
1.1 schwarze 337: tt = print_otag(h, TAG_TR, 0, NULL);
338:
1.25 schwarze 339: PAIR_CLASS_INIT(&tag[0], "foot-date");
1.1 schwarze 340: print_otag(h, TAG_TD, 1, tag);
1.25 schwarze 341:
1.1 schwarze 342: print_text(h, b);
343: print_stagq(h, tt);
344:
1.25 schwarze 345: PAIR_CLASS_INIT(&tag[0], "foot-os");
1.26 schwarze 346: if (NULL == h->style) {
347: PAIR_INIT(&tag[1], ATTR_ALIGN, "right");
348: print_otag(h, TAG_TD, 2, tag);
349: } else
350: print_otag(h, TAG_TD, 1, tag);
1.25 schwarze 351:
1.1 schwarze 352: if (m->source)
353: print_text(h, m->source);
354: print_tagq(h, t);
355: }
356:
357:
358:
359: /* ARGSUSED */
360: static int
361: man_br_pre(MAN_ARGS)
362: {
363: struct roffsu su;
364: struct htmlpair tag;
365:
366: SCALE_VS_INIT(&su, 1);
367:
1.21 schwarze 368: if (MAN_sp == n->tok) {
1.8 schwarze 369: if (n->child)
370: a2roffsu(n->child->string, &su, SCALE_VS);
1.21 schwarze 371: } else
1.1 schwarze 372: su.scale = 0;
373:
374: bufcat_su(h, "height", &su);
375: PAIR_STYLE_INIT(&tag, h);
376: print_otag(h, TAG_DIV, 1, &tag);
1.4 schwarze 377:
1.3 schwarze 378: /* So the div isn't empty: */
379: print_text(h, "\\~");
380:
1.1 schwarze 381: return(0);
382: }
383:
384:
385: /* ARGSUSED */
386: static int
387: man_SH_pre(MAN_ARGS)
388: {
1.25 schwarze 389: struct htmlpair tag;
1.1 schwarze 390:
1.25 schwarze 391: if (MAN_BLOCK == n->type) {
392: PAIR_CLASS_INIT(&tag, "section");
393: print_otag(h, TAG_DIV, 1, &tag);
1.1 schwarze 394: return(1);
1.25 schwarze 395: } else if (MAN_BODY == n->type)
1.1 schwarze 396: return(1);
397:
1.25 schwarze 398: print_otag(h, TAG_H1, 0, NULL);
1.1 schwarze 399: return(1);
400: }
401:
402:
403: /* ARGSUSED */
404: static int
405: man_alt_pre(MAN_ARGS)
406: {
407: const struct man_node *nn;
1.27 schwarze 408: int i;
409: enum htmltag fp;
410: struct tag *t;
1.1 schwarze 411:
412: for (i = 0, nn = n->child; nn; nn = nn->next, i++) {
1.27 schwarze 413: t = NULL;
1.1 schwarze 414: switch (n->tok) {
415: case (MAN_BI):
1.27 schwarze 416: fp = i % 2 ? TAG_I : TAG_B;
1.1 schwarze 417: break;
418: case (MAN_IB):
1.27 schwarze 419: fp = i % 2 ? TAG_B : TAG_I;
1.1 schwarze 420: break;
421: case (MAN_RI):
1.27 schwarze 422: fp = i % 2 ? TAG_I : TAG_MAX;
1.1 schwarze 423: break;
424: case (MAN_IR):
1.27 schwarze 425: fp = i % 2 ? TAG_MAX : TAG_I;
1.1 schwarze 426: break;
427: case (MAN_BR):
1.27 schwarze 428: fp = i % 2 ? TAG_MAX : TAG_B;
1.1 schwarze 429: break;
430: case (MAN_RB):
1.27 schwarze 431: fp = i % 2 ? TAG_B : TAG_MAX;
1.1 schwarze 432: break;
433: default:
434: abort();
435: /* NOTREACHED */
436: }
437:
438: if (i)
439: h->flags |= HTML_NOSPACE;
440:
1.27 schwarze 441: if (TAG_MAX != fp)
442: t = print_otag(h, fp, 0, NULL);
443:
1.18 schwarze 444: print_man_node(m, nn, mh, h);
1.27 schwarze 445:
446: if (t)
447: print_tagq(h, t);
1.1 schwarze 448: }
449:
450: return(0);
451: }
452:
453:
454: /* ARGSUSED */
455: static int
1.26 schwarze 456: man_SM_pre(MAN_ARGS)
1.1 schwarze 457: {
458:
1.27 schwarze 459: print_otag(h, TAG_SMALL, 0, NULL);
1.26 schwarze 460: if (MAN_SB == n->tok)
1.27 schwarze 461: print_otag(h, TAG_B, 0, NULL);
1.1 schwarze 462: return(1);
463: }
464:
465:
466: /* ARGSUSED */
467: static int
468: man_SS_pre(MAN_ARGS)
469: {
1.25 schwarze 470: struct htmlpair tag;
1.1 schwarze 471:
1.25 schwarze 472: if (MAN_BLOCK == n->type) {
473: PAIR_CLASS_INIT(&tag, "subsection");
474: print_otag(h, TAG_DIV, 1, &tag);
1.1 schwarze 475: return(1);
1.25 schwarze 476: } else if (MAN_BODY == n->type)
1.1 schwarze 477: return(1);
478:
1.25 schwarze 479: print_otag(h, TAG_H2, 0, NULL);
1.1 schwarze 480: return(1);
481: }
482:
483:
484: /* ARGSUSED */
485: static int
486: man_PP_pre(MAN_ARGS)
487: {
488:
1.22 schwarze 489: if (MAN_HEAD == n->type)
490: return(0);
1.26 schwarze 491: else if (MAN_BODY == n->type && n->prev)
492: print_otag(h, TAG_P, 0, NULL);
1.22 schwarze 493:
1.1 schwarze 494: return(1);
495: }
496:
497:
498: /* ARGSUSED */
499: static int
500: man_IP_pre(MAN_ARGS)
501: {
502: struct roffsu su;
503: struct htmlpair tag;
504: const struct man_node *nn;
505: int width;
506:
507: /*
508: * This scattering of 1-BU margins and pads is to make sure that
509: * when text overruns its box, the subsequent text isn't flush
510: * up against it. However, the rest of the right-hand box must
511: * also be adjusted in consideration of this 1-BU space.
512: */
513:
514: if (MAN_BODY == n->type) {
1.26 schwarze 515: print_otag(h, TAG_TD, 0, NULL);
1.1 schwarze 516: return(1);
517: }
518:
519: nn = MAN_BLOCK == n->type ?
520: n->head->child : n->parent->head->child;
521:
522: SCALE_HS_INIT(&su, INDENT);
523: width = 0;
524:
1.28 ! schwarze 525: /* Width is the second token. */
1.7 schwarze 526:
1.1 schwarze 527: if (MAN_IP == n->tok && NULL != nn)
1.28 ! schwarze 528: if (NULL != (nn = nn->next))
1.1 schwarze 529: width = a2width(nn, &su);
530:
1.7 schwarze 531: /* Width is the first token. */
532:
533: if (MAN_TP == n->tok && NULL != nn) {
534: /* Skip past non-text children. */
535: while (nn && MAN_TEXT != nn->type)
536: nn = nn->next;
537: if (nn)
538: width = a2width(nn, &su);
539: }
1.1 schwarze 540:
541: if (MAN_BLOCK == n->type) {
1.26 schwarze 542: print_otag(h, TAG_P, 0, NULL);
543: print_otag(h, TAG_TABLE, 0, NULL);
544: bufcat_su(h, "width", &su);
1.1 schwarze 545: PAIR_STYLE_INIT(&tag, h);
1.26 schwarze 546: print_otag(h, TAG_COL, 1, &tag);
547: print_otag(h, TAG_COL, 0, NULL);
548: print_otag(h, TAG_TBODY, 0, NULL);
549: print_otag(h, TAG_TR, 0, NULL);
1.1 schwarze 550: return(1);
551: }
552:
1.26 schwarze 553: print_otag(h, TAG_TD, 0, NULL);
1.1 schwarze 554:
1.28 ! schwarze 555: /* For IP, only print the first header element. */
1.1 schwarze 556:
1.28 ! schwarze 557: if (MAN_IP == n->tok && n->child)
! 558: print_man_node(m, n->child, mh, h);
1.7 schwarze 559:
1.28 ! schwarze 560: /* For TP, only print next-line header elements. */
1.1 schwarze 561:
562: if (MAN_TP == n->tok)
1.28 ! schwarze 563: for (nn = n->child; nn; nn = nn->next)
! 564: if (nn->line > n->line)
! 565: print_man_node(m, nn, mh, h);
1.1 schwarze 566:
567: return(0);
568: }
569:
570:
571: /* ARGSUSED */
572: static int
573: man_HP_pre(MAN_ARGS)
574: {
1.26 schwarze 575: struct htmlpair tag;
576: struct roffsu su;
577: const struct man_node *np;
1.1 schwarze 578:
1.26 schwarze 579: np = MAN_BLOCK == n->type ?
580: n->head->child :
581: n->parent->head->child;
1.1 schwarze 582:
1.26 schwarze 583: if (NULL == np || ! a2width(np, &su))
584: SCALE_HS_INIT(&su, INDENT);
1.1 schwarze 585:
1.26 schwarze 586: if (MAN_HEAD == n->type) {
587: print_otag(h, TAG_TD, 0, NULL);
588: return(0);
589: } else if (MAN_BLOCK == n->type) {
590: print_otag(h, TAG_P, 0, NULL);
591: print_otag(h, TAG_TABLE, 0, NULL);
592: bufcat_su(h, "width", &su);
1.1 schwarze 593: PAIR_STYLE_INIT(&tag, h);
1.26 schwarze 594: print_otag(h, TAG_COL, 1, &tag);
595: print_otag(h, TAG_COL, 0, NULL);
596: print_otag(h, TAG_TBODY, 0, NULL);
597: print_otag(h, TAG_TR, 0, NULL);
1.1 schwarze 598: return(1);
599: }
600:
1.26 schwarze 601: su.scale = -su.scale;
1.1 schwarze 602: bufcat_su(h, "text-indent", &su);
603: PAIR_STYLE_INIT(&tag, h);
1.26 schwarze 604: print_otag(h, TAG_TD, 1, &tag);
1.1 schwarze 605: return(1);
606: }
607:
608:
609: /* ARGSUSED */
610: static int
611: man_B_pre(MAN_ARGS)
612: {
613:
1.27 schwarze 614: print_otag(h, TAG_B, 0, NULL);
1.1 schwarze 615: return(1);
616: }
617:
618:
619: /* ARGSUSED */
620: static int
621: man_I_pre(MAN_ARGS)
622: {
1.4 schwarze 623:
1.27 schwarze 624: print_otag(h, TAG_I, 0, NULL);
1.1 schwarze 625: return(1);
1.18 schwarze 626: }
627:
628:
629: /* ARGSUSED */
630: static int
631: man_literal_pre(MAN_ARGS)
632: {
633:
1.21 schwarze 634: if (MAN_nf == n->tok) {
1.18 schwarze 635: print_otag(h, TAG_BR, 0, NULL);
636: mh->fl |= MANH_LITERAL;
1.21 schwarze 637: } else
1.18 schwarze 638: mh->fl &= ~MANH_LITERAL;
639:
640: return(1);
641: }
642:
643:
644: /* ARGSUSED */
645: static int
646: man_in_pre(MAN_ARGS)
647: {
648:
649: print_otag(h, TAG_BR, 0, NULL);
650: return(0);
1.1 schwarze 651: }
652:
653:
654: /* ARGSUSED */
655: static int
656: man_ign_pre(MAN_ARGS)
657: {
658:
659: return(0);
660: }
661:
662:
663: /* ARGSUSED */
664: static int
665: man_RS_pre(MAN_ARGS)
666: {
667: struct htmlpair tag;
668: struct roffsu su;
669:
670: if (MAN_HEAD == n->type)
671: return(0);
672: else if (MAN_BODY == n->type)
673: return(1);
674:
675: SCALE_HS_INIT(&su, INDENT);
1.26 schwarze 676: if (n->head->child)
1.1 schwarze 677: a2width(n->head->child, &su);
678:
1.26 schwarze 679: bufcat_su(h, "margin-left", &su);
1.1 schwarze 680: PAIR_STYLE_INIT(&tag, h);
681: print_otag(h, TAG_DIV, 1, &tag);
682: return(1);
683: }