Annotation of mandoc/eqn_html.c, Revision 1.10
1.10 ! schwarze 1: /* $Id: eqn_html.c,v 1.9 2014/10/10 14:27:46 schwarze Exp $ */
1.1 kristaps 2: /*
1.9 schwarze 3: * Copyright (c) 2011, 2014 Kristaps Dzonsons <kristaps@bsd.lv>
1.1 kristaps 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 "config.h"
1.4 schwarze 18:
19: #include <sys/types.h>
1.1 kristaps 20:
21: #include <assert.h>
22: #include <stdio.h>
23: #include <stdlib.h>
24: #include <string.h>
25:
26: #include "mandoc.h"
27: #include "out.h"
28: #include "html.h"
29:
1.8 kristaps 30: static void
31: eqn_box(struct html *p, const struct eqn_box *bp)
1.1 kristaps 32: {
1.8 kristaps 33: struct tag *post, *row, *cell, *t;
1.5 kristaps 34: struct htmlpair tag[2];
1.8 kristaps 35: const struct eqn_box *child, *parent;
36: size_t i, j, rows;
1.5 kristaps 37:
38: if (NULL == bp)
1.8 kristaps 39: return;
1.5 kristaps 40:
1.8 kristaps 41: post = NULL;
1.5 kristaps 42:
43: /*
1.8 kristaps 44: * Special handling for a matrix, which is presented to us in
45: * column order, but must be printed in row-order.
1.5 kristaps 46: */
1.8 kristaps 47: if (EQN_MATRIX == bp->type) {
48: if (NULL == bp->first)
49: goto out;
1.10 ! schwarze 50: if (EQN_LIST != bp->first->type) {
! 51: eqn_box(p, bp->first);
! 52: goto out;
! 53: }
1.8 kristaps 54: if (NULL == (parent = bp->first->first))
55: goto out;
56: /* Estimate the number of rows, first. */
57: if (NULL == (child = parent->first))
58: goto out;
1.9 schwarze 59: for (rows = 0; NULL != child; rows++)
1.8 kristaps 60: child = child->next;
61: /* Print row-by-row. */
62: post = print_otag(p, TAG_MTABLE, 0, NULL);
63: for (i = 0; i < rows; i++) {
64: parent = bp->first->first;
65: row = print_otag(p, TAG_MTR, 0, NULL);
66: while (NULL != parent) {
67: child = parent->first;
68: for (j = 0; j < i; j++) {
69: if (NULL == child)
70: break;
71: child = child->next;
72: }
73: cell = print_otag
74: (p, TAG_MTD, 0, NULL);
1.9 schwarze 75: /*
1.8 kristaps 76: * If we have no data for this
77: * particular cell, then print a
78: * placeholder and continue--don't puke.
79: */
1.9 schwarze 80: if (NULL != child)
1.8 kristaps 81: eqn_box(p, child->first);
82: print_tagq(p, cell);
83: parent = parent->next;
84: }
85: print_tagq(p, row);
86: }
87: goto out;
1.6 kristaps 88: }
1.5 kristaps 89:
90: switch (bp->pos) {
1.6 kristaps 91: case (EQNPOS_TO):
1.7 kristaps 92: post = print_otag(p, TAG_MOVER, 0, NULL);
93: break;
1.5 kristaps 94: case (EQNPOS_SUP):
95: post = print_otag(p, TAG_MSUP, 0, NULL);
96: break;
97: case (EQNPOS_FROM):
1.7 kristaps 98: post = print_otag(p, TAG_MUNDER, 0, NULL);
99: break;
1.5 kristaps 100: case (EQNPOS_SUB):
101: post = print_otag(p, TAG_MSUB, 0, NULL);
102: break;
103: case (EQNPOS_OVER):
104: post = print_otag(p, TAG_MFRAC, 0, NULL);
105: break;
1.6 kristaps 106: case (EQNPOS_FROMTO):
1.7 kristaps 107: post = print_otag(p, TAG_MUNDEROVER, 0, NULL);
108: break;
1.5 kristaps 109: case (EQNPOS_SUBSUP):
110: post = print_otag(p, TAG_MSUBSUP, 0, NULL);
1.8 kristaps 111: break;
112: case (EQNPOS_SQRT):
113: post = print_otag(p, TAG_MSQRT, 0, NULL);
1.5 kristaps 114: break;
115: default:
116: break;
117: }
118:
1.8 kristaps 119: if (bp->top || bp->bottom) {
120: assert(NULL == post);
121: if (bp->top && NULL == bp->bottom)
122: post = print_otag(p, TAG_MOVER, 0, NULL);
123: else if (bp->top && bp->bottom)
124: post = print_otag(p, TAG_MUNDEROVER, 0, NULL);
125: else if (bp->bottom)
126: post = print_otag(p, TAG_MUNDER, 0, NULL);
127: }
128:
129: if (EQN_PILE == bp->type) {
130: assert(NULL == post);
1.10 ! schwarze 131: if (bp->first != NULL && bp->first->type == EQN_LIST)
! 132: post = print_otag(p, TAG_MTABLE, 0, NULL);
! 133: } else if (bp->type == EQN_LIST &&
! 134: bp->parent && bp->parent->type == EQN_PILE) {
1.8 kristaps 135: assert(NULL == post);
136: post = print_otag(p, TAG_MTR, 0, NULL);
137: print_otag(p, TAG_MTD, 0, NULL);
138: }
1.5 kristaps 139:
140: if (NULL != bp->text) {
1.8 kristaps 141: assert(NULL == post);
142: post = print_otag(p, TAG_MI, 0, NULL);
143: print_text(p, bp->text);
1.9 schwarze 144: } else if (NULL == post) {
1.5 kristaps 145: if (NULL != bp->left || NULL != bp->right) {
146: PAIR_INIT(&tag[0], ATTR_OPEN,
1.9 schwarze 147: NULL == bp->left ? "" : bp->left);
1.5 kristaps 148: PAIR_INIT(&tag[1], ATTR_CLOSE,
1.9 schwarze 149: NULL == bp->right ? "" : bp->right);
1.8 kristaps 150: post = print_otag(p, TAG_MFENCED, 2, tag);
1.9 schwarze 151: }
1.8 kristaps 152: if (NULL == post)
153: post = print_otag(p, TAG_MROW, 0, NULL);
154: else
1.5 kristaps 155: print_otag(p, TAG_MROW, 0, NULL);
156: }
157:
1.8 kristaps 158: eqn_box(p, bp->first);
159:
160: out:
161: if (NULL != bp->bottom) {
162: t = print_otag(p, TAG_MO, 0, NULL);
163: print_text(p, bp->bottom);
164: print_tagq(p, t);
1.9 schwarze 165: }
1.8 kristaps 166: if (NULL != bp->top) {
167: t = print_otag(p, TAG_MO, 0, NULL);
168: print_text(p, bp->top);
169: print_tagq(p, t);
170: }
171:
172: if (NULL != post)
1.5 kristaps 173: print_tagq(p, post);
174:
1.8 kristaps 175: eqn_box(p, bp->next);
176: }
177:
178: void
179: print_eqn(struct html *p, const struct eqn *ep)
180: {
181: struct htmlpair tag;
182: struct tag *t;
183:
184: PAIR_CLASS_INIT(&tag, "eqn");
185: t = print_otag(p, TAG_MATH, 1, &tag);
186:
187: p->flags |= HTML_NONOSPACE;
188: eqn_box(p, ep->root);
189: p->flags &= ~HTML_NONOSPACE;
1.5 kristaps 190:
1.8 kristaps 191: print_tagq(p, t);
1.1 kristaps 192: }
CVSweb