]> git.saurik.com Git - wxWidgets.git/blob - utils/tex2rtf/src/htmlutil.cpp
added APPEXTRADEFS var so things like tex2rtf can pass their own flags to the make...
[wxWidgets.git] / utils / tex2rtf / src / htmlutil.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: htmlutil.cpp
3 // Purpose: Converts Latex to HTML
4 // Author: Julian Smart
5 // Modified by:
6 // Created: 7.9.93
7 // RCS-ID: $Id$
8 // Copyright: (c) Julian Smart
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
11
12 #ifdef __GNUG__
13 #pragma implementation
14 #endif
15
16 // For compilers that support precompilation, includes "wx.h".
17 #include "wx/wxprec.h"
18
19 #ifdef __BORLANDC__
20 #pragma hdrstop
21 #endif
22
23 #ifndef WX_PRECOMP
24 #include "wx/wx.h"
25 #endif
26
27 #include "tex2any.h"
28 #include "tex2rtf.h"
29 #include "table.h"
30
31 extern void DecToHex(int, char *);
32 void GenerateHTMLIndexFile(char *fname);
33
34 void GenerateHTMLWorkshopFiles(char *fname);
35 void HTMLWorkshopAddToContents(int level, char *s, char *file);
36 void HTMLWorkshopStartContents();
37 void HTMLWorkshopEndContents();
38
39 void OutputContentsFrame(void);
40
41 #include "readshg.h" // Segmented hypergraphics parsing
42
43 char *ChaptersName = NULL;
44 char *SectionsName = NULL;
45 char *SubsectionsName = NULL;
46 char *SubsubsectionsName = NULL;
47 char *TitlepageName = NULL;
48 char *lastFileName = NULL;
49 char *lastTopic = NULL;
50 char *currentFileName = NULL;
51 char *contentsFrameName = NULL;
52
53 static TexChunk *descriptionItemArg = NULL;
54 static TexChunk *helpRefFilename = NULL;
55 static TexChunk *helpRefText = NULL;
56 static int indentLevel = 0;
57 static int citeCount = 1;
58 extern FILE *Contents;
59 FILE *FrameContents = NULL;
60 FILE *Titlepage = NULL;
61 // FILE *FrameTitlepage = NULL;
62 int fileId = 0;
63 bool subsectionStarted = FALSE;
64
65 // Which column of a row are we in? (Assumes no nested tables, of course)
66 int currentColumn = 0;
67
68 // Are we in verbatim mode? If so, format differently.
69 static bool inVerbatim = FALSE;
70
71 // Need to know whether we're in a table or figure for benefit
72 // of listoffigures/listoftables
73 static bool inFigure = FALSE;
74 static bool inTable = FALSE;
75
76 // This is defined in the Tex2Any library.
77 extern char *BigBuffer;
78
79 class HyperReference: public wxObject
80 {
81 public:
82 char *refName;
83 char *refFile;
84 HyperReference(char *name, char *file)
85 {
86 if (name) refName = copystring(name);
87 if (file) refFile = copystring(file);
88 }
89 };
90
91 class TexNextPage: public wxObject
92 {
93 public:
94 char *label;
95 char *filename;
96 TexNextPage(char *theLabel, char *theFile)
97 {
98 label = copystring(theLabel);
99 filename = copystring(theFile);
100 }
101 ~TexNextPage(void)
102 {
103 delete[] label;
104 delete[] filename;
105 }
106 };
107
108 wxHashTable TexNextPages(wxKEY_STRING);
109
110 static char *CurrentChapterName = NULL;
111 static char *CurrentChapterFile = NULL;
112 static char *CurrentSectionName = NULL;
113 static char *CurrentSectionFile = NULL;
114 static char *CurrentSubsectionName = NULL;
115 static char *CurrentSubsectionFile = NULL;
116 static char *CurrentSubsubsectionName = NULL;
117 static char *CurrentSubsubsectionFile = NULL;
118 static char *CurrentTopic = NULL;
119
120 static void SetCurrentTopic(char *s)
121 {
122 if (CurrentTopic) delete[] CurrentTopic;
123 CurrentTopic = copystring(s);
124 }
125
126 void SetCurrentChapterName(char *s, char *file)
127 {
128 if (CurrentChapterName) delete[] CurrentChapterName;
129 CurrentChapterName = copystring(s);
130 if (CurrentChapterFile) delete[] CurrentChapterFile;
131 CurrentChapterFile = copystring(file);
132
133 currentFileName = CurrentChapterFile;
134
135 SetCurrentTopic(s);
136 }
137 void SetCurrentSectionName(char *s, char *file)
138 {
139 if (CurrentSectionName) delete[] CurrentSectionName;
140 CurrentSectionName = copystring(s);
141 if (CurrentSectionFile) delete[] CurrentSectionFile;
142 CurrentSectionFile = copystring(file);
143
144 currentFileName = CurrentSectionFile;
145 SetCurrentTopic(s);
146 }
147 void SetCurrentSubsectionName(char *s, char *file)
148 {
149 if (CurrentSubsectionName) delete[] CurrentSubsectionName;
150 CurrentSubsectionName = copystring(s);
151 if (CurrentSubsectionFile) delete[] CurrentSubsectionFile;
152 CurrentSubsectionFile = copystring(file);
153 currentFileName = CurrentSubsectionFile;
154 SetCurrentTopic(s);
155 }
156 void SetCurrentSubsubsectionName(char *s, char *file)
157 {
158 if (CurrentSubsubsectionName) delete[] CurrentSubsubsectionName;
159 CurrentSubsubsectionName = copystring(s);
160 if (CurrentSubsubsectionFile) delete[] CurrentSubsubsectionFile;
161 CurrentSubsubsectionFile = copystring(file);
162 currentFileName = CurrentSubsubsectionFile;
163 SetCurrentTopic(s);
164 }
165
166 /*
167 * Close former filedescriptor and reopen using another filename.
168 *
169 */
170
171 void ReopenFile(FILE **fd, char **fileName)
172 {
173 if (*fd)
174 {
175 fprintf(*fd, "\n</BODY></HTML>\n");
176 fclose(*fd);
177 }
178 fileId ++;
179 char buf[400];
180 if (truncateFilenames)
181 sprintf(buf, "%s%d.htm", FileRoot, fileId);
182 else
183 sprintf(buf, "%s%d.html", FileRoot, fileId);
184 if (*fileName) delete[] *fileName;
185 *fileName = copystring(FileNameFromPath(buf));
186 *fd = fopen(buf, "w");
187 fprintf(*fd, "<HTML>\n");
188 }
189
190 /*
191 * Reopen section contents file, i.e. the index appended to each section
192 * in subsectionCombine mode
193 */
194
195 static char *SectionContentsFilename = NULL;
196 static FILE *SectionContentsFD = NULL;
197
198 void ReopenSectionContentsFile(void)
199 {
200 if ( SectionContentsFD )
201 {
202 fclose(SectionContentsFD);
203 }
204 if ( SectionContentsFilename )
205 delete[] SectionContentsFilename;
206 SectionContentsFD = NULL;
207 SectionContentsFilename = NULL;
208
209 // Create the name from the current section filename
210 if ( CurrentSectionFile )
211 {
212 char buf[256];
213 strcpy(buf, CurrentSectionFile);
214 wxStripExtension(buf);
215 strcat(buf, ".con");
216 SectionContentsFilename = copystring(buf);
217
218 SectionContentsFD = fopen(SectionContentsFilename, "w");
219 }
220 }
221
222
223 /*
224 * Given a TexChunk with a string value, scans through the string
225 * converting Latex-isms into HTML-isms, such as 2 newlines -> <P>.
226 *
227 */
228
229 void ProcessText2HTML(TexChunk *chunk)
230 {
231 bool changed = FALSE;
232 int ptr = 0;
233 int i = 0;
234 char ch = 1;
235 int len = strlen(chunk->value);
236 while (ch != 0)
237 {
238 ch = chunk->value[i];
239
240 // 2 newlines means \par
241 if (!inVerbatim && chunk->value[i] == 10 && ((len > i+1 && chunk->value[i+1] == 10) ||
242 ((len > i+1 && chunk->value[i+1] == 13) &&
243 (len > i+2 && chunk->value[i+2] == 10))))
244 {
245 BigBuffer[ptr] = 0; strcat(BigBuffer, "<P>\n\n"); ptr += 5;
246 i += 2;
247 changed = TRUE;
248 }
249 else if (!inVerbatim && ch == '`' && (len >= i+1 && chunk->value[i+1] == '`'))
250 {
251 BigBuffer[ptr] = '"'; ptr ++;
252 i += 2;
253 changed = TRUE;
254 }
255 else if (!inVerbatim && ch == '`') // Change ` to '
256 {
257 BigBuffer[ptr] = 39; ptr ++;
258 i += 1;
259 changed = TRUE;
260 }
261 else if (ch == '<') // Change < to &lt
262 {
263 BigBuffer[ptr] = 0;
264 strcat(BigBuffer, "&lt;");
265 ptr += 4;
266 i += 1;
267 changed = TRUE;
268 }
269 else if (ch == '>') // Change > to &gt
270 {
271 BigBuffer[ptr] = 0;
272 strcat(BigBuffer, "&gt;");
273 ptr += 4;
274 i += 1;
275 changed = TRUE;
276 }
277 else
278 {
279 BigBuffer[ptr] = ch;
280 i ++;
281 ptr ++;
282 }
283 }
284 BigBuffer[ptr] = 0;
285
286 if (changed)
287 {
288 delete chunk->value;
289 chunk->value = copystring(BigBuffer);
290 }
291 }
292
293 /*
294 * Scan through all chunks starting from the given one,
295 * calling ProcessText2HTML to convert Latex-isms to RTF-isms.
296 * This should be called after Tex2Any has parsed the file,
297 * and before TraverseDocument is called.
298 *
299 */
300
301 void Text2HTML(TexChunk *chunk)
302 {
303 Tex2RTFYield();
304 if (stopRunning) return;
305
306 switch (chunk->type)
307 {
308 case CHUNK_TYPE_MACRO:
309 {
310 TexMacroDef *def = chunk->def;
311
312 if (def && def->ignore)
313 return;
314
315 if (def && (def->macroId == ltVERBATIM || def->macroId == ltVERB || def->macroId == ltSPECIAL))
316 inVerbatim = TRUE;
317
318 wxNode *node = chunk->children.First();
319 while (node)
320 {
321 TexChunk *child_chunk = (TexChunk *)node->Data();
322 Text2HTML(child_chunk);
323 node = node->Next();
324 }
325
326 if (def && (def->macroId == ltVERBATIM || def->macroId == ltVERB || def->macroId == ltSPECIAL))
327 inVerbatim = FALSE;
328
329 break;
330 }
331 case CHUNK_TYPE_ARG:
332 {
333 wxNode *node = chunk->children.First();
334 while (node)
335 {
336 TexChunk *child_chunk = (TexChunk *)node->Data();
337 Text2HTML(child_chunk);
338 node = node->Next();
339 }
340
341 break;
342 }
343 case CHUNK_TYPE_STRING:
344 {
345 if (chunk->value)
346 ProcessText2HTML(chunk);
347 break;
348 }
349 }
350 }
351
352 /*
353 * Add appropriate browse buttons to this page.
354 *
355 */
356
357 void AddBrowseButtons(char *upLabel, char *upFilename,
358 char *previousLabel, char *previousFilename,
359 char *thisLabel, char *thisFilename)
360 {
361 char contentsReferenceBuf[80];
362 char upReferenceBuf[80];
363 char backReferenceBuf[80];
364 char forwardReferenceBuf[80];
365 if (htmlBrowseButtons == HTML_BUTTONS_NONE)
366 return;
367
368 char *contentsReference = NULL;
369 if (htmlBrowseButtons == HTML_BUTTONS_TEXT)
370 contentsReference = ContentsNameString;
371 else
372 {
373 // contentsReference = "<img align=center src=\"contents.gif\" BORDER=0 ALT=\"Contents\">";
374 contentsReference = contentsReferenceBuf;
375 sprintf(contentsReference, "<img align=center src=\"%s\" BORDER=0 ALT=\"Contents\">", ConvertCase("contents.gif"));
376 }
377
378 char *upReference = NULL;
379 if (htmlBrowseButtons == HTML_BUTTONS_TEXT)
380 upReference = UpNameString;
381 else
382 {
383 // upReference = "<img align=center src=\"up.gif\" ALT=\"Up\">";
384 upReference = upReferenceBuf;
385 sprintf(upReference, "<img align=center src=\"%s\" BORDER=0 ALT=\"Up\">", ConvertCase("up.gif"));
386 }
387
388 char *backReference = NULL;
389 if (htmlBrowseButtons == HTML_BUTTONS_TEXT)
390 backReference = "&lt;&lt;";
391 else
392 {
393 // backReference = "<img align=center src=\"back.gif\" ALT=\"Previous\">";
394 backReference = backReferenceBuf;
395 sprintf(backReference, "<img align=center src=\"%s\" BORDER=0 ALT=\"Previous\">", ConvertCase("back.gif"));
396 }
397
398 char *forwardReference = NULL;
399 if (htmlBrowseButtons == HTML_BUTTONS_TEXT)
400 forwardReference = "&gt;&gt;";
401 else
402 {
403 // forwardReference = "<img align=center src=\"forward.gif\" ALT=\"Next\">";
404 forwardReference = forwardReferenceBuf;
405 sprintf(forwardReference, "<img align=center src=\"%s\" BORDER=0 ALT=\"Next\">", ConvertCase("forward.gif"));
406 }
407
408 TexOutput("<CENTER>");
409
410 char buf[200];
411
412 /*
413 * Contents button
414 *
415 */
416
417 if (truncateFilenames)
418 {
419 char buf1[80];
420 strcpy(buf1, ConvertCase(FileNameFromPath(FileRoot)));
421 sprintf(buf, "\n<A HREF=\"%s.%s\">%s</A> ", buf1, ConvertCase("htm"), contentsReference);
422 }
423 else
424 {
425 char buf1[80];
426 strcpy(buf1, ConvertCase(FileNameFromPath(FileRoot)));
427 sprintf(buf, "\n<A HREF=\"%s%s\">%s</A> ", buf1, ConvertCase("_contents.html"), contentsReference);
428 }
429 // TexOutput("<NOFRAMES>");
430 TexOutput(buf);
431 // TexOutput("</NOFRAMES>");
432
433 /*
434 * Up button
435 *
436 */
437
438 if (upLabel && upFilename)
439 {
440 if (strlen(upLabel) > 0)
441 sprintf(buf, "<A HREF=\"%s#%s\">%s</A> ", ConvertCase(upFilename), upLabel, upReference);
442 else
443 sprintf(buf, "<A HREF=\"%s\">%s</A> ", ConvertCase(upFilename), upReference);
444 if (strcmp(upLabel, "contents") == 0)
445 {
446 // TexOutput("<NOFRAMES>");
447 TexOutput(buf);
448 // TexOutput("</NOFRAMES>");
449 }
450 else
451 TexOutput(buf);
452 }
453
454 /*
455 * << button
456 *
457 */
458
459 if (previousLabel && previousFilename)
460 {
461 sprintf(buf, "<A HREF=\"%s#%s\">%s</A> ", ConvertCase(previousFilename), previousLabel, backReference);
462 if (strcmp(previousLabel, "contents") == 0)
463 {
464 // TexOutput("<NOFRAMES>");
465 TexOutput(buf);
466 // TexOutput("</NOFRAMES>");
467 }
468 else
469 TexOutput(buf);
470 }
471 else
472 {
473 // A placeholder so the buttons don't keep moving position
474 sprintf(buf, "%s ", backReference);
475 TexOutput(buf);
476 }
477
478 char *nextLabel = NULL;
479 char *nextFilename = NULL;
480
481 // Get the next page, and record the previous page's 'next' page
482 // (i.e. this page)
483 TexNextPage *nextPage = (TexNextPage *)TexNextPages.Get(thisLabel);
484 if (nextPage)
485 {
486 nextLabel = nextPage->label;
487 nextFilename = nextPage->filename;
488 }
489 if (previousLabel && previousFilename)
490 {
491 TexNextPage *oldNextPage = (TexNextPage *)TexNextPages.Get(previousLabel);
492 if (oldNextPage)
493 {
494 delete oldNextPage;
495 TexNextPages.Delete(previousLabel);
496 }
497 TexNextPage *newNextPage = new TexNextPage(thisLabel, thisFilename);
498 TexNextPages.Put(previousLabel, newNextPage);
499 }
500
501 /*
502 * >> button
503 *
504 */
505
506 if (nextLabel && nextFilename)
507 {
508 sprintf(buf, "<A HREF=\"%s#%s\">%s</A> ", ConvertCase(nextFilename), nextLabel, forwardReference);
509 TexOutput(buf);
510 }
511 else
512 {
513 // A placeholder so the buttons don't keep moving position
514 sprintf(buf, "%s ", forwardReference);
515 TexOutput(buf);
516 }
517
518 /*
519 * Horizontal rule to finish it off nicely.
520 *
521 */
522 TexOutput("</CENTER>");
523 TexOutput("<HR>\n");
524
525 // Update last topic/filename
526 if (lastFileName)
527 delete[] lastFileName;
528 lastFileName = copystring(thisFilename);
529 if (lastTopic)
530 delete[] lastTopic;
531 lastTopic = copystring(thisLabel);
532 }
533
534 // A colour string is either 3 numbers separated by semicolons (RGB),
535 // or a reference to a GIF. Return the filename or a hex string like #934CE8
536 char *ParseColourString(char *bkStr, bool *isPicture)
537 {
538 static char resStr[300];
539 strcpy(resStr, bkStr);
540 char *tok1 = strtok(resStr, ";");
541 char *tok2 = strtok(NULL, ";");
542 if (tok1)
543 {
544 if (!tok2)
545 {
546 *isPicture = TRUE;
547 return resStr;
548 }
549 else
550 {
551 *isPicture = FALSE;
552 char *tok3 = strtok(NULL, ";");
553 if (tok3)
554 {
555 // Now convert 3 strings into decimal numbers, and then hex numbers.
556 int red = atoi(tok1);
557 int green = atoi(tok2);
558 int blue = atoi(tok3);
559
560 strcpy(resStr, "#");
561
562 char buf[3];
563 DecToHex(red, buf);
564 strcat(resStr, buf);
565 DecToHex(green, buf);
566 strcat(resStr, buf);
567 DecToHex(blue, buf);
568 strcat(resStr, buf);
569 return resStr;
570 }
571 else return NULL;
572 }
573 }
574 else return NULL;
575 }
576
577 // Output start of <BODY> block
578 void OutputBodyStart(void)
579 {
580 TexOutput("\n<BODY");
581 if (backgroundImageString)
582 {
583 bool isPicture = FALSE;
584 char *s = ParseColourString(backgroundImageString, &isPicture);
585 if (s)
586 {
587 TexOutput(" BACKGROUND=\""); TexOutput(s); TexOutput("\"");
588 }
589 }
590 if (backgroundColourString)
591 {
592 bool isPicture = FALSE;
593 char *s = ParseColourString(backgroundColourString, &isPicture);
594 if (s)
595 {
596 TexOutput(" BGCOLOR="); TexOutput(s);
597 }
598 }
599
600 // Set foreground text colour, if one is specified
601 if (textColourString)
602 {
603 bool isPicture = FALSE;
604 char *s = ParseColourString(textColourString, &isPicture);
605 if (s)
606 {
607 TexOutput(" TEXT="); TexOutput(s);
608 }
609 }
610 // Set link text colour, if one is specified
611 if (linkColourString)
612 {
613 bool isPicture = FALSE;
614 char *s = ParseColourString(linkColourString, &isPicture);
615 if (s)
616 {
617 TexOutput(" LINK="); TexOutput(s);
618 }
619 }
620 // Set followed link text colour, if one is specified
621 if (followedLinkColourString)
622 {
623 bool isPicture = FALSE;
624 char *s = ParseColourString(followedLinkColourString, &isPicture);
625 if (s)
626 {
627 TexOutput(" VLINK="); TexOutput(s);
628 }
629 }
630 TexOutput(">\n");
631 }
632
633 // Called on start/end of macro examination
634 void HTMLOnMacro(int macroId, int no_args, bool start)
635 {
636 switch (macroId)
637 {
638 case ltCHAPTER:
639 case ltCHAPTERSTAR:
640 case ltCHAPTERHEADING:
641 {
642 if (!start)
643 {
644 sectionNo = 0;
645 figureNo = 0;
646 subsectionNo = 0;
647 subsubsectionNo = 0;
648 if (macroId != ltCHAPTERSTAR)
649 chapterNo ++;
650
651 SetCurrentOutput(NULL);
652 startedSections = TRUE;
653
654 char *topicName = FindTopicName(GetNextChunk());
655 ReopenFile(&Chapters, &ChaptersName);
656 AddTexRef(topicName, ChaptersName, ChapterNameString);
657
658 SetCurrentChapterName(topicName, ChaptersName);
659 if (htmlWorkshopFiles) HTMLWorkshopAddToContents(0, topicName, ChaptersName);
660
661 SetCurrentOutput(Chapters);
662
663 TexOutput("<head><title>");
664 OutputCurrentSection(); // Repeat section header
665 TexOutput("</title></head>\n");
666 OutputBodyStart();
667
668 char titleBuf[200];
669 if (truncateFilenames)
670 sprintf(titleBuf, "%s.htm", FileNameFromPath(FileRoot));
671 else
672 sprintf(titleBuf, "%s_contents.html", FileNameFromPath(FileRoot));
673
674 fprintf(Chapters, "<A NAME=\"%s\"></A>", topicName);
675
676 AddBrowseButtons("", titleBuf, // Up
677 lastTopic, lastFileName, // Last topic
678 topicName, ChaptersName); // This topic
679
680 fprintf(Contents, "\n<LI><A HREF=\"%s#%s\">", ConvertCase(ChaptersName), topicName);
681
682 if (htmlFrameContents && FrameContents)
683 {
684 SetCurrentOutput(FrameContents);
685 fprintf(FrameContents, "\n<LI><A HREF=\"%s#%s\" TARGET=\"mainwindow\">", ConvertCase(ChaptersName), topicName);
686 OutputCurrentSection();
687 fprintf(FrameContents, "</A>\n");
688 }
689
690 SetCurrentOutputs(Contents, Chapters);
691 fprintf(Chapters, "\n<H2>");
692 OutputCurrentSection();
693 fprintf(Contents, "</A>\n");
694 fprintf(Chapters, "</H2>\n");
695
696 SetCurrentOutput(Chapters);
697
698 // Add this section title to the list of keywords
699 if (htmlIndex)
700 {
701 OutputCurrentSectionToString(wxBuffer);
702 AddKeyWordForTopic(topicName, wxBuffer, ConvertCase(currentFileName));
703 }
704 }
705 break;
706 }
707 case ltSECTION:
708 case ltSECTIONSTAR:
709 case ltSECTIONHEADING:
710 case ltGLOSS:
711 {
712 if (!start)
713 {
714 subsectionNo = 0;
715 subsubsectionNo = 0;
716 subsectionStarted = FALSE;
717
718 if (macroId != ltSECTIONSTAR)
719 sectionNo ++;
720
721 SetCurrentOutput(NULL);
722 startedSections = TRUE;
723
724 char *topicName = FindTopicName(GetNextChunk());
725 ReopenFile(&Sections, &SectionsName);
726 AddTexRef(topicName, SectionsName, SectionNameString);
727
728 SetCurrentSectionName(topicName, SectionsName);
729 if (htmlWorkshopFiles) HTMLWorkshopAddToContents(1, topicName, SectionsName);
730
731 SetCurrentOutput(Sections);
732 TexOutput("<head><title>");
733 OutputCurrentSection();
734 TexOutput("</title></head>\n");
735 OutputBodyStart();
736
737 fprintf(Sections, "<A NAME=\"%s\"></A>", topicName);
738 AddBrowseButtons(CurrentChapterName, CurrentChapterFile, // Up
739 lastTopic, lastFileName, // Last topic
740 topicName, SectionsName); // This topic
741
742 FILE *jumpFrom = ((DocumentStyle == LATEX_ARTICLE) ? Contents : Chapters);
743
744 SetCurrentOutputs(jumpFrom, Sections);
745 if (DocumentStyle == LATEX_ARTICLE)
746 fprintf(jumpFrom, "\n<LI><A HREF=\"%s#%s\">", ConvertCase(SectionsName), topicName);
747 else
748 fprintf(jumpFrom, "\n<A HREF=\"%s#%s\"><B>", ConvertCase(SectionsName), topicName);
749
750 fprintf(Sections, "\n<H2>");
751 OutputCurrentSection();
752
753 if (DocumentStyle == LATEX_ARTICLE)
754 fprintf(jumpFrom, "</A>\n");
755 else
756 fprintf(jumpFrom, "</B></A><BR>\n");
757 fprintf(Sections, "</H2>\n");
758
759 SetCurrentOutput(Sections);
760 // Add this section title to the list of keywords
761 if (htmlIndex)
762 {
763 OutputCurrentSectionToString(wxBuffer);
764 AddKeyWordForTopic(topicName, wxBuffer, currentFileName);
765 }
766 }
767 break;
768 }
769 case ltSUBSECTION:
770 case ltSUBSECTIONSTAR:
771 case ltMEMBERSECTION:
772 case ltFUNCTIONSECTION:
773 {
774 if (!start)
775 {
776 if (!Sections)
777 {
778 OnError("You cannot have a subsection before a section!");
779 }
780 else
781 {
782 subsubsectionNo = 0;
783
784 if (macroId != ltSUBSECTIONSTAR)
785 subsectionNo ++;
786
787 if ( combineSubSections && !subsectionStarted )
788 {
789 // Read old .con file in at this point
790 char buf[256];
791 strcpy(buf, CurrentSectionFile);
792 wxStripExtension(buf);
793 strcat(buf, ".con");
794 FILE *fd = fopen(buf, "r");
795 if ( fd )
796 {
797 int ch = getc(fd);
798 while (ch != EOF)
799 {
800 putc(ch, Sections);
801 ch = getc(fd);
802 }
803 fclose(fd);
804 }
805 fprintf(Sections, "<P>\n");
806
807 // Close old file, create a new file for the sub(sub)section contents entries
808 ReopenSectionContentsFile();
809 }
810
811 startedSections = TRUE;
812 subsectionStarted = TRUE;
813
814 char *topicName = FindTopicName(GetNextChunk());
815
816 if ( !combineSubSections )
817 {
818 SetCurrentOutput(NULL);
819 ReopenFile(&Subsections, &SubsectionsName);
820 AddTexRef(topicName, SubsectionsName, SubsectionNameString);
821 SetCurrentSubsectionName(topicName, SubsectionsName);
822 if (htmlWorkshopFiles) HTMLWorkshopAddToContents(2, topicName, SubsectionsName);
823 SetCurrentOutput(Subsections);
824
825 TexOutput("<head><title>");
826 OutputCurrentSection();
827 TexOutput("</title></head>\n");
828 OutputBodyStart();
829
830 fprintf(Subsections, "<A NAME=\"%s\"></A>", topicName);
831 AddBrowseButtons(CurrentSectionName, CurrentSectionFile, // Up
832 lastTopic, lastFileName, // Last topic
833 topicName, SubsectionsName); // This topic
834
835 SetCurrentOutputs(Sections, Subsections);
836 fprintf(Sections, "\n<A HREF=\"%s#%s\"><B>", ConvertCase(SubsectionsName), topicName);
837
838 fprintf(Subsections, "\n<H3>");
839 OutputCurrentSection();
840 fprintf(Sections, "</B></A><BR>\n");
841 fprintf(Subsections, "</H3>\n");
842
843 SetCurrentOutput(Subsections);
844 }
845 else
846 {
847 AddTexRef(topicName, SectionsName, SubsectionNameString);
848 SetCurrentSubsectionName(topicName, SectionsName);
849
850 // if ( subsectionNo != 0 )
851 fprintf(Sections, "\n<HR>\n");
852
853 // We're putting everything into the section file
854 fprintf(Sections, "<A NAME=\"%s\"></A>", topicName);
855 fprintf(Sections, "\n<H3>");
856 OutputCurrentSection();
857 fprintf(Sections, "</H3>\n");
858
859 SetCurrentOutput(SectionContentsFD);
860 fprintf(SectionContentsFD, "<A HREF=\"#%s\">", topicName);
861 OutputCurrentSection();
862 TexOutput("</A><BR>\n");
863
864 if (htmlWorkshopFiles) HTMLWorkshopAddToContents(2, topicName, SectionsName);
865 SetCurrentOutput(Sections);
866 }
867 // Add this section title to the list of keywords
868 if (htmlIndex)
869 {
870 OutputCurrentSectionToString(wxBuffer);
871 AddKeyWordForTopic(topicName, wxBuffer, currentFileName);
872 }
873
874 }
875 }
876 break;
877 }
878 case ltSUBSUBSECTION:
879 case ltSUBSUBSECTIONSTAR:
880 {
881 if (!start)
882 {
883 if (!Subsections && !combineSubSections)
884 {
885 OnError("You cannot have a subsubsection before a subsection!");
886 }
887 else
888 {
889 if (macroId != ltSUBSUBSECTIONSTAR)
890 subsubsectionNo ++;
891
892 startedSections = TRUE;
893
894 char *topicName = FindTopicName(GetNextChunk());
895
896 if ( !combineSubSections )
897 {
898 SetCurrentOutput(NULL);
899 ReopenFile(&Subsubsections, &SubsubsectionsName);
900 AddTexRef(topicName, SubsubsectionsName, SubsubsectionNameString);
901 SetCurrentSubsubsectionName(topicName, SubsubsectionsName);
902 if (htmlWorkshopFiles) HTMLWorkshopAddToContents(3, topicName, SubsubsectionsName);
903
904 SetCurrentOutput(Subsubsections);
905 TexOutput("<head><title>");
906 OutputCurrentSection();
907 TexOutput("</title></head>\n");
908 OutputBodyStart();
909
910 fprintf(Subsubsections, "<A NAME=\"%s\"></A>", topicName);
911
912 AddBrowseButtons(CurrentSubsectionName, CurrentSubsectionFile, // Up
913 lastTopic, lastFileName, // Last topic
914 topicName, SubsubsectionsName); // This topic
915
916 SetCurrentOutputs(Subsections, Subsubsections);
917 fprintf(Subsections, "\n<A HREF=\"%s#%s\"><B>", ConvertCase(SubsubsectionsName), topicName);
918
919 fprintf(Subsubsections, "\n<H3>");
920 OutputCurrentSection();
921 fprintf(Subsections, "</B></A><BR>\n");
922 fprintf(Subsubsections, "</H3>\n");
923 }
924 else
925 {
926 AddTexRef(topicName, SectionsName, SubsubsectionNameString);
927 SetCurrentSubsectionName(topicName, SectionsName);
928 fprintf(Sections, "\n<HR>\n");
929
930 // We're putting everything into the section file
931 fprintf(Sections, "<A NAME=\"%s\"></A>", topicName);
932 fprintf(Sections, "\n<H3>");
933 OutputCurrentSection();
934 fprintf(Sections, "</H3>\n");
935 /* TODO: where do we put subsubsection contents entry - indented, with subsection entries?
936 SetCurrentOutput(SectionContentsFD);
937 fprintf(SectionContentsFD, "<A HREF=\"#%s\">", topicName);
938 OutputCurrentSection();
939 TexOutput("</A><BR>");
940 */
941 if (htmlWorkshopFiles) HTMLWorkshopAddToContents(2, topicName, SectionsName);
942 SetCurrentOutput(Sections);
943 }
944
945 // Add this section title to the list of keywords
946 if (htmlIndex)
947 {
948 OutputCurrentSectionToString(wxBuffer);
949 AddKeyWordForTopic(topicName, wxBuffer, currentFileName);
950 }
951 }
952 }
953 break;
954 }
955 case ltFUNC:
956 case ltPFUNC:
957 {
958 if ( !combineSubSections )
959 SetCurrentOutput(Subsections);
960 else
961 SetCurrentOutput(Sections);
962 if (start)
963 {
964 }
965 else
966 {
967 }
968 break;
969 }
970 case ltCLIPSFUNC:
971 {
972 if ( !combineSubSections )
973 SetCurrentOutput(Subsections);
974 else
975 SetCurrentOutput(Sections);
976 if (start)
977 {
978 }
979 else
980 {
981 }
982 break;
983 }
984 case ltMEMBER:
985 {
986 if ( !combineSubSections )
987 SetCurrentOutput(Subsections);
988 else
989 SetCurrentOutput(Sections);
990 if (start)
991 {
992 }
993 else
994 {
995 }
996 break;
997 }
998 case ltVOID:
999 // if (start)
1000 // TexOutput("<B>void</B>");
1001 break;
1002 case ltHARDY:
1003 if (start)
1004 TexOutput("HARDY");
1005 break;
1006 case ltWXCLIPS:
1007 if (start)
1008 TexOutput("wxCLIPS");
1009 break;
1010 case ltAMPERSAND:
1011 if (start)
1012 TexOutput("&amp;");
1013 break;
1014 case ltSPECIALAMPERSAND:
1015 {
1016 if (start)
1017 {
1018 if (inTabular)
1019 {
1020 // End cell, start cell
1021 TexOutput("</TD>");
1022
1023 // Start new row and cell, setting alignment for the first cell.
1024 if (currentColumn < noColumns)
1025 currentColumn ++;
1026
1027 char buf[100];
1028 if (TableData[currentColumn].justification == 'c')
1029 sprintf(buf, "\n<TD ALIGN=CENTER>");
1030 else if (TableData[currentColumn].justification == 'r')
1031 sprintf(buf, "\n<TD ALIGN=RIGHT>");
1032 else if (TableData[currentColumn].absWidth)
1033 {
1034 // Convert from points * 20 into pixels.
1035 int points = TableData[currentColumn].width / 20;
1036
1037 // Say the display is 100 DPI (dots/pixels per inch).
1038 // There are 72 pts to the inch. So 1pt = 1/72 inch, or 100 * 1/72 dots.
1039 int pixels = (int)(points * 100.0 / 72.0);
1040 sprintf(buf, "<TD ALIGN=CENTER WIDTH=%d>", pixels);
1041 }
1042 else
1043 sprintf(buf, "\n<TD ALIGN=LEFT>");
1044 TexOutput(buf);
1045 }
1046 else
1047 TexOutput("&amp;");
1048 }
1049 break;
1050 }
1051 case ltBACKSLASHCHAR:
1052 {
1053 if (start)
1054 {
1055 if (inTabular)
1056 {
1057 // End row. In fact, tables without use of \row or \ruledrow isn't supported for
1058 // HTML: the syntax is too different (e.g. how do we know where to put the first </TH>
1059 // if we've ended the last row?). So normally you wouldn't use \\ to end a row.
1060 TexOutput("</TR>\n");
1061 }
1062 else
1063 TexOutput("<BR>\n");
1064 }
1065 break;
1066 }
1067 case ltROW:
1068 case ltRULEDROW:
1069 {
1070 if (start)
1071 {
1072 currentColumn = 0;
1073
1074 // Start new row and cell, setting alignment for the first cell.
1075 char buf[100];
1076 if (TableData[currentColumn].justification == 'c')
1077 sprintf(buf, "<TR>\n<TD ALIGN=CENTER>");
1078 else if (TableData[currentColumn].justification == 'r')
1079 sprintf(buf, "<TR>\n<TD ALIGN=RIGHT>");
1080 else if (TableData[currentColumn].absWidth)
1081 {
1082 // Convert from points * 20 into pixels.
1083 int points = TableData[currentColumn].width / 20;
1084
1085 // Say the display is 100 DPI (dots/pixels per inch).
1086 // There are 72 pts to the inch. So 1pt = 1/72 inch, or 100 * 1/72 dots.
1087 int pixels = (int)(points * 100.0 / 72.0);
1088 sprintf(buf, "<TR>\n<TD ALIGN=CENTER WIDTH=%d>", pixels);
1089 }
1090 else
1091 sprintf(buf, "<TR>\n<TD ALIGN=LEFT>");
1092 TexOutput(buf);
1093 }
1094 else
1095 {
1096 // End cell and row
1097 // Start new row and cell
1098 TexOutput("</TD>\n</TR>\n");
1099 }
1100 break;
1101 }
1102 // HTML-only: break until the end of the picture (both margins are clear).
1103 case ltBRCLEAR:
1104 {
1105 if (start)
1106 TexOutput("<BR CLEAR=ALL>");
1107 break;
1108 }
1109 case ltRTFSP: // Explicit space, RTF only
1110 break;
1111 case ltSPECIALTILDE:
1112 {
1113 if (start)
1114 {
1115 if (inVerbatim)
1116 TexOutput("~");
1117 else
1118 TexOutput(" ");
1119 }
1120 break;
1121 }
1122 case ltINDENTED :
1123 {
1124 if ( start )
1125 TexOutput("<UL><UL>\n");
1126 else
1127 TexOutput("</UL></UL>\n");
1128 break;
1129 }
1130 case ltITEMIZE:
1131 case ltENUMERATE:
1132 case ltDESCRIPTION:
1133 // case ltTWOCOLLIST:
1134 {
1135 if (start)
1136 {
1137 indentLevel ++;
1138
1139 int listType;
1140 if (macroId == ltENUMERATE)
1141 listType = LATEX_ENUMERATE;
1142 else if (macroId == ltITEMIZE)
1143 listType = LATEX_ITEMIZE;
1144 else
1145 listType = LATEX_DESCRIPTION;
1146
1147 itemizeStack.Insert(new ItemizeStruc(listType));
1148 switch (listType)
1149 {
1150 case LATEX_ITEMIZE:
1151 TexOutput("<UL>\n");
1152 break;
1153 case LATEX_ENUMERATE:
1154 TexOutput("<OL>\n");
1155 break;
1156 case LATEX_DESCRIPTION:
1157 default:
1158 TexOutput("<DL>\n");
1159 break;
1160 }
1161 }
1162 else
1163 {
1164 indentLevel --;
1165 if (itemizeStack.First())
1166 {
1167 ItemizeStruc *struc = (ItemizeStruc *)itemizeStack.First()->Data();
1168 switch (struc->listType)
1169 {
1170 case LATEX_ITEMIZE:
1171 TexOutput("</UL>\n");
1172 break;
1173 case LATEX_ENUMERATE:
1174 TexOutput("</OL>\n");
1175 break;
1176 case LATEX_DESCRIPTION:
1177 default:
1178 TexOutput("</DL>\n");
1179 break;
1180 }
1181
1182 delete struc;
1183 delete itemizeStack.First();
1184 }
1185 }
1186 break;
1187 }
1188 case ltTWOCOLLIST :
1189 {
1190 if ( start )
1191 TexOutput("\n<TABLE>\n");
1192 else
1193 TexOutput("\n</TABLE>\n");
1194 break;
1195 }
1196 case ltPAR:
1197 {
1198 if (start)
1199 TexOutput("<P>\n");
1200 break;
1201 }
1202 /* For footnotes we need to output the text at the bottom of the page and
1203 * insert a reference to it. Is it worth the trouble...
1204 case ltFOOTNOTE:
1205 case ltFOOTNOTEPOPUP:
1206 {
1207 if (start)
1208 {
1209 TexOutput("<FN>);
1210 }
1211 else TexOutput("</FN>");
1212 break;
1213 }
1214 */
1215 case ltVERB:
1216 {
1217 if (start)
1218 TexOutput("<TT>");
1219 else TexOutput("</TT>");
1220 break;
1221 }
1222 case ltVERBATIM:
1223 {
1224 if (start)
1225 {
1226 char buf[100];
1227 sprintf(buf, "<PRE>\n");
1228 TexOutput(buf);
1229 }
1230 else TexOutput("</PRE>\n");
1231 break;
1232 }
1233 case ltCENTERLINE:
1234 case ltCENTER:
1235 {
1236 if (start)
1237 {
1238 TexOutput("<CENTER>");
1239 }
1240 else TexOutput("</CENTER>");
1241 break;
1242 }
1243 case ltFLUSHLEFT:
1244 {
1245 /*
1246 if (start)
1247 {
1248 TexOutput("{\\ql ");
1249 }
1250 else TexOutput("}\\par\\pard\n");
1251 */
1252 break;
1253 }
1254 case ltFLUSHRIGHT:
1255 {
1256 /*
1257 if (start)
1258 {
1259 TexOutput("{\\qr ");
1260 }
1261 else TexOutput("}\\par\\pard\n");
1262 */
1263 break;
1264 }
1265 case ltSMALL:
1266 {
1267 if (start)
1268 {
1269 // Netscape extension
1270 TexOutput("<FONT SIZE=2>");
1271 }
1272 else TexOutput("</FONT>");
1273 break;
1274 }
1275 case ltTINY:
1276 {
1277 if (start)
1278 {
1279 // Netscape extension
1280 TexOutput("<FONT SIZE=1>");
1281 }
1282 else TexOutput("</FONT>");
1283 break;
1284 }
1285 case ltNORMALSIZE:
1286 {
1287 if (start)
1288 {
1289 // Netscape extension
1290 TexOutput("<FONT SIZE=3>");
1291 }
1292 else TexOutput("</FONT>");
1293 break;
1294 }
1295 case ltlarge:
1296 {
1297 if (start)
1298 {
1299 // Netscape extension
1300 TexOutput("<FONT SIZE=4>");
1301 }
1302 else TexOutput("</FONT>");
1303 break;
1304 }
1305 case ltLarge:
1306 {
1307 if (start)
1308 {
1309 // Netscape extension
1310 TexOutput("<FONT SIZE=5>");
1311 }
1312 else TexOutput("</FONT>");
1313 break;
1314 }
1315 case ltLARGE:
1316 {
1317 if (start)
1318 {
1319 // Netscape extension
1320 TexOutput("<FONT SIZE=6>");
1321 }
1322 else TexOutput("</FONT>");
1323 break;
1324 }
1325 case ltBFSERIES:
1326 case ltTEXTBF:
1327 case ltBF:
1328 {
1329 if (start)
1330 {
1331 TexOutput("<B>");
1332 }
1333 else TexOutput("</B>");
1334 break;
1335 }
1336 case ltITSHAPE:
1337 case ltTEXTIT:
1338 case ltIT:
1339 {
1340 if (start)
1341 {
1342 TexOutput("<I>");
1343 }
1344 else TexOutput("</I>");
1345 break;
1346 }
1347 case ltEMPH:
1348 case ltEM:
1349 {
1350 if (start)
1351 {
1352 TexOutput("<EM>");
1353 }
1354 else TexOutput("</EM>");
1355 break;
1356 }
1357 case ltUNDERLINE:
1358 {
1359 if (start)
1360 {
1361 TexOutput("<UL>");
1362 }
1363 else TexOutput("</UL>");
1364 break;
1365 }
1366 case ltTTFAMILY:
1367 case ltTEXTTT:
1368 case ltTT:
1369 {
1370 if (start)
1371 {
1372 TexOutput("<TT>");
1373 }
1374 else TexOutput("</TT>");
1375 break;
1376 }
1377 case ltCOPYRIGHT:
1378 {
1379 if (start)
1380 TexOutput("&copy;", TRUE);
1381 break;
1382 }
1383 case ltREGISTERED:
1384 {
1385 if (start)
1386 TexOutput("&reg;", TRUE);
1387 break;
1388 }
1389 // Arrows
1390 case ltLEFTARROW:
1391 {
1392 if (start) TexOutput("&lt;--");
1393 break;
1394 }
1395 case ltLEFTARROW2:
1396 {
1397 if (start) TexOutput("&lt;==");
1398 break;
1399 }
1400 case ltRIGHTARROW:
1401 {
1402 if (start) TexOutput("--&gt;");
1403 break;
1404 }
1405 case ltRIGHTARROW2:
1406 {
1407 if (start) TexOutput("==&gt;");
1408 break;
1409 }
1410 case ltLEFTRIGHTARROW:
1411 {
1412 if (start) TexOutput("&lt;--&gt;");
1413 break;
1414 }
1415 case ltLEFTRIGHTARROW2:
1416 {
1417 if (start) TexOutput("&lt;==&gt;");
1418 break;
1419 }
1420 /*
1421 case ltSC:
1422 {
1423 break;
1424 }
1425 */
1426 case ltITEM:
1427 {
1428 if (!start)
1429 {
1430 wxNode *node = itemizeStack.First();
1431 if (node)
1432 {
1433 ItemizeStruc *struc = (ItemizeStruc *)node->Data();
1434 struc->currentItem += 1;
1435 if (struc->listType == LATEX_DESCRIPTION)
1436 {
1437 if (descriptionItemArg)
1438 {
1439 TexOutput("<DT> ");
1440 TraverseChildrenFromChunk(descriptionItemArg);
1441 TexOutput("\n");
1442 descriptionItemArg = NULL;
1443 }
1444 TexOutput("<DD>");
1445 }
1446 else
1447 TexOutput("<LI>");
1448 }
1449 }
1450 break;
1451 }
1452 case ltMAKETITLE:
1453 {
1454 if (start && DocumentTitle && DocumentAuthor)
1455 {
1456 // Add a special label for the contents page.
1457 // TexOutput("<CENTER>\n");
1458 TexOutput("<A NAME=\"contents\">");
1459 TexOutput("<H2 ALIGN=CENTER>\n");
1460 TraverseChildrenFromChunk(DocumentTitle);
1461 TexOutput("</H2>");
1462 TexOutput("<P>");
1463 TexOutput("</A>\n");
1464 TexOutput("<P>\n\n");
1465 TexOutput("<H3 ALIGN=CENTER>");
1466 TraverseChildrenFromChunk(DocumentAuthor);
1467 TexOutput("</H3><P>\n\n");
1468 if (DocumentDate)
1469 {
1470 TexOutput("<H3 ALIGN=CENTER>");
1471 TraverseChildrenFromChunk(DocumentDate);
1472 TexOutput("</H3><P>\n\n");
1473 }
1474 // TexOutput("\n</CENTER>\n");
1475 TexOutput("\n<P><HR><P>\n");
1476
1477 /*
1478 // Now do optional frame contents page
1479 if (htmlFrameContents && FrameContents)
1480 {
1481 SetCurrentOutput(FrameContents);
1482
1483 // Add a special label for the contents page.
1484 TexOutput("<CENTER>\n");
1485 TexOutput("<H3>\n");
1486 TraverseChildrenFromChunk(DocumentTitle);
1487 TexOutput("</H3>");
1488 TexOutput("<P>");
1489 TexOutput("</A>\n");
1490 TexOutput("<P>\n\n");
1491 TexOutput("<H3>");
1492 TraverseChildrenFromChunk(DocumentAuthor);
1493 TexOutput("</H3><P>\n\n");
1494 if (DocumentDate)
1495 {
1496 TexOutput("<H4>");
1497 TraverseChildrenFromChunk(DocumentDate);
1498 TexOutput("</H4><P>\n\n");
1499 }
1500 TexOutput("\n</CENTER>\n");
1501 TexOutput("<P><HR><P>\n");
1502
1503 SetCurrentOutput(Titlepage);
1504 }
1505 */
1506 }
1507 break;
1508 }
1509 case ltHELPREF:
1510 case ltHELPREFN:
1511 case ltPOPREF:
1512 case ltURLREF:
1513 {
1514 if (start)
1515 {
1516 helpRefFilename = NULL;
1517 helpRefText = NULL;
1518 }
1519 break;
1520 }
1521 case ltBIBLIOGRAPHY:
1522 {
1523 if (start)
1524 {
1525 DefaultOnMacro(macroId, no_args, start);
1526 }
1527 else
1528 {
1529 DefaultOnMacro(macroId, no_args, start);
1530 TexOutput("</DL>\n");
1531 }
1532 break;
1533 }
1534 case ltHRULE:
1535 {
1536 if (start)
1537 {
1538 TexOutput("<HR>\n");
1539 }
1540 break;
1541 }
1542 case ltRULE:
1543 {
1544 if (start)
1545 {
1546 TexOutput("<HR>\n");
1547 }
1548 break;
1549 }
1550 case ltTABLEOFCONTENTS:
1551 {
1552 if (start)
1553 {
1554 FILE *fd = fopen(ContentsName, "r");
1555 if (fd)
1556 {
1557 int ch = getc(fd);
1558 while (ch != EOF)
1559 {
1560 putc(ch, Titlepage);
1561 ch = getc(fd);
1562 }
1563 fclose(fd);
1564 }
1565 else
1566 {
1567 TexOutput("RUN TEX2RTF AGAIN FOR CONTENTS PAGE\n");
1568 OnInform("Run Tex2RTF again to include contents page.");
1569 }
1570 }
1571 break;
1572 }
1573 case ltLANGLEBRA:
1574 {
1575 if (start)
1576 TexOutput("&lt;");
1577 break;
1578 }
1579 case ltRANGLEBRA:
1580 {
1581 if (start)
1582 TexOutput("&gt;");
1583 break;
1584 }
1585 case ltQUOTE:
1586 case ltQUOTATION:
1587 {
1588 if (start)
1589 TexOutput("<BLOCKQUOTE>");
1590 else
1591 TexOutput("</BLOCKQUOTE>");
1592 break;
1593 }
1594 case ltCAPTION:
1595 case ltCAPTIONSTAR:
1596 {
1597 if (start)
1598 {
1599 if (inTabular)
1600 TexOutput("\n<CAPTION>");
1601
1602 char figBuf[40];
1603
1604 if ( inFigure )
1605 {
1606 figureNo ++;
1607
1608 if (DocumentStyle != LATEX_ARTICLE)
1609 sprintf(figBuf, "%s %d.%d: ", FigureNameString, chapterNo, figureNo);
1610 else
1611 sprintf(figBuf, "%s %d: ", FigureNameString, figureNo);
1612 }
1613 else
1614 {
1615 tableNo ++;
1616
1617 if (DocumentStyle != LATEX_ARTICLE)
1618 sprintf(figBuf, "%s %d.%d: ", TableNameString, chapterNo, tableNo);
1619 else
1620 sprintf(figBuf, "%s %d: ", TableNameString, tableNo);
1621 }
1622
1623 TexOutput(figBuf);
1624 }
1625 else
1626 {
1627 if (inTabular)
1628 TexOutput("\n</CAPTION>\n");
1629
1630 char *topicName = FindTopicName(GetNextChunk());
1631
1632 int n = inFigure ? figureNo : tableNo;
1633
1634 AddTexRef(topicName, NULL, NULL,
1635 ((DocumentStyle != LATEX_ARTICLE) ? chapterNo : n),
1636 ((DocumentStyle != LATEX_ARTICLE) ? n : 0));
1637 }
1638 break;
1639 }
1640 case ltSS:
1641 {
1642 if (start) TexOutput("&szlig;");
1643 break;
1644 }
1645 case ltFIGURE:
1646 {
1647 if (start) inFigure = TRUE;
1648 else inFigure = FALSE;
1649 break;
1650 }
1651 case ltTABLE:
1652 {
1653 if (start) inTable = TRUE;
1654 else inTable = FALSE;
1655 break;
1656 }
1657 default:
1658 DefaultOnMacro(macroId, no_args, start);
1659 break;
1660 }
1661 }
1662
1663 // Called on start/end of argument examination
1664 bool HTMLOnArgument(int macroId, int arg_no, bool start)
1665 {
1666 switch (macroId)
1667 {
1668 case ltCHAPTER:
1669 case ltCHAPTERSTAR:
1670 case ltCHAPTERHEADING:
1671 case ltSECTION:
1672 case ltSECTIONSTAR:
1673 case ltSECTIONHEADING:
1674 case ltSUBSECTION:
1675 case ltSUBSECTIONSTAR:
1676 case ltSUBSUBSECTION:
1677 case ltSUBSUBSECTIONSTAR:
1678 case ltGLOSS:
1679 case ltMEMBERSECTION:
1680 case ltFUNCTIONSECTION:
1681 {
1682 if (!start && (arg_no == 1))
1683 currentSection = GetArgChunk();
1684 return FALSE;
1685 break;
1686 }
1687 case ltFUNC:
1688 {
1689 if (start && (arg_no == 1))
1690 TexOutput("<B>");
1691
1692 if (!start && (arg_no == 1))
1693 TexOutput("</B> ");
1694
1695 if (start && (arg_no == 2))
1696 {
1697 if (!suppressNameDecoration) TexOutput("<B>");
1698 currentMember = GetArgChunk();
1699 }
1700 if (!start && (arg_no == 2))
1701 {
1702 if (!suppressNameDecoration) TexOutput("</B>");
1703 }
1704
1705 if (start && (arg_no == 3))
1706 TexOutput("(");
1707 if (!start && (arg_no == 3))
1708 TexOutput(")");
1709 break;
1710 }
1711 case ltCLIPSFUNC:
1712 {
1713 if (start && (arg_no == 1))
1714 TexOutput("<B>");
1715 if (!start && (arg_no == 1))
1716 TexOutput("</B> ");
1717
1718 if (start && (arg_no == 2))
1719 {
1720 if (!suppressNameDecoration) TexOutput("( ");
1721 currentMember = GetArgChunk();
1722 }
1723 if (!start && (arg_no == 2))
1724 {
1725 }
1726
1727 if (!start && (arg_no == 3))
1728 TexOutput(")");
1729 break;
1730 }
1731 case ltPFUNC:
1732 {
1733 if (!start && (arg_no == 1))
1734 TexOutput(" ");
1735
1736 if (start && (arg_no == 2))
1737 TexOutput("(*");
1738 if (!start && (arg_no == 2))
1739 TexOutput(")");
1740
1741 if (start && (arg_no == 2))
1742 currentMember = GetArgChunk();
1743
1744 if (start && (arg_no == 3))
1745 TexOutput("(");
1746 if (!start && (arg_no == 3))
1747 TexOutput(")");
1748 break;
1749 }
1750 case ltPARAM:
1751 {
1752 if (start && (arg_no == 1))
1753 TexOutput("<B>");
1754 if (!start && (arg_no == 1))
1755 TexOutput("</B>");
1756 if (start && (arg_no == 2))
1757 {
1758 TexOutput("<I>");
1759 }
1760 if (!start && (arg_no == 2))
1761 {
1762 TexOutput("</I>");
1763 }
1764 break;
1765 }
1766 case ltCPARAM:
1767 {
1768 if (start && (arg_no == 1))
1769 TexOutput("<B>");
1770 if (!start && (arg_no == 1))
1771 TexOutput("</B> "); // This is the difference from param - one space!
1772 if (start && (arg_no == 2))
1773 {
1774 TexOutput("<I>");
1775 }
1776 if (!start && (arg_no == 2))
1777 {
1778 TexOutput("</I>");
1779 }
1780 break;
1781 }
1782 case ltMEMBER:
1783 {
1784 if (!start && (arg_no == 1))
1785 TexOutput(" ");
1786
1787 if (start && (arg_no == 2))
1788 currentMember = GetArgChunk();
1789 break;
1790 }
1791 case ltREF:
1792 {
1793 if (start)
1794 {
1795 char *sec = NULL;
1796
1797 char *refName = GetArgData();
1798 if (refName)
1799 {
1800 TexRef *texRef = FindReference(refName);
1801 if (texRef)
1802 {
1803 sec = texRef->sectionNumber;
1804 }
1805 }
1806 if (sec)
1807 {
1808 TexOutput(sec);
1809 }
1810 return FALSE;
1811 }
1812 break;
1813 }
1814 case ltURLREF:
1815 {
1816 if (IsArgOptional())
1817 return FALSE;
1818 else if ((GetNoArgs() - arg_no) == 1)
1819 {
1820 if (start)
1821 helpRefText = GetArgChunk();
1822 return FALSE;
1823 }
1824 else if ((GetNoArgs() - arg_no) == 0) // Arg = 2, or 3 if first is optional
1825 {
1826 if (start)
1827 {
1828 TexChunk *ref = GetArgChunk();
1829 TexOutput("<A HREF=\"");
1830 inVerbatim = TRUE;
1831 TraverseChildrenFromChunk(ref);
1832 inVerbatim = FALSE;
1833 TexOutput("\">");
1834 if (helpRefText)
1835 TraverseChildrenFromChunk(helpRefText);
1836 TexOutput("</A>");
1837 }
1838 return FALSE;
1839 }
1840 break;
1841 }
1842 case ltHELPREF:
1843 case ltHELPREFN:
1844 case ltPOPREF:
1845 {
1846 if (IsArgOptional())
1847 {
1848 if (start)
1849 helpRefFilename = GetArgChunk();
1850 return FALSE;
1851 }
1852 if ((GetNoArgs() - arg_no) == 1)
1853 {
1854 if (start)
1855 helpRefText = GetArgChunk();
1856 return FALSE;
1857 }
1858 else if ((GetNoArgs() - arg_no) == 0) // Arg = 2, or 3 if first is optional
1859 {
1860 if (start)
1861 {
1862 char *refName = GetArgData();
1863 char *refFilename = NULL;
1864
1865 if (refName)
1866 {
1867 TexRef *texRef = FindReference(refName);
1868 if (texRef)
1869 {
1870 if (texRef->refFile && strcmp(texRef->refFile, "??") != 0)
1871 refFilename = texRef->refFile;
1872
1873 TexOutput("<A HREF=\"");
1874 // If a filename is supplied, use it, otherwise try to
1875 // use the filename associated with the reference (from this document).
1876 if (helpRefFilename)
1877 {
1878 TraverseChildrenFromChunk(helpRefFilename);
1879 TexOutput("#");
1880 }
1881 else if (refFilename)
1882 {
1883 TexOutput(ConvertCase(refFilename));
1884 TexOutput("#");
1885 }
1886 TexOutput(refName);
1887 TexOutput("\">");
1888 if (helpRefText)
1889 TraverseChildrenFromChunk(helpRefText);
1890 TexOutput("</A>");
1891 }
1892 else
1893 {
1894 if (helpRefText)
1895 TraverseChildrenFromChunk(helpRefText);
1896 TexOutput(" (REF NOT FOUND)");
1897 }
1898 }
1899 else TexOutput("??");
1900 }
1901 return FALSE;
1902 }
1903 break;
1904 }
1905 case ltIMAGE:
1906 case ltIMAGEL:
1907 case ltIMAGER:
1908 case ltPSBOXTO:
1909 {
1910 if (arg_no == 2)
1911 {
1912 if (start)
1913 {
1914 char *alignment = "";
1915 if (macroId == ltIMAGEL)
1916 alignment = " align=left";
1917 else if (macroId == ltIMAGER)
1918 alignment = " align=right";
1919
1920 // Try to find an XBM or GIF image first.
1921 char *filename = copystring(GetArgData());
1922 char buf[500];
1923
1924 strcpy(buf, filename);
1925 StripExtension(buf);
1926 strcat(buf, ".xbm");
1927 wxString f = TexPathList.FindValidPath(buf);
1928
1929 if (f == "") // Try for a GIF instead
1930 {
1931 strcpy(buf, filename);
1932 StripExtension(buf);
1933 strcat(buf, ".gif");
1934 f = TexPathList.FindValidPath(buf);
1935 }
1936
1937 if (f == "") // Try for a JPEG instead
1938 {
1939 strcpy(buf, filename);
1940 StripExtension(buf);
1941 strcat(buf, ".jpg");
1942 f = TexPathList.FindValidPath(buf);
1943 }
1944
1945 if (f == "") // Try for a PNG instead
1946 {
1947 strcpy(buf, filename);
1948 StripExtension(buf);
1949 strcat(buf, ".png");
1950 f = TexPathList.FindValidPath(buf);
1951 }
1952
1953 if (f != "")
1954 {
1955 char *inlineFilename = copystring(f);
1956 #if 0
1957 char *originalFilename = TexPathList.FindValidPath(filename);
1958 // If we have found the existing filename, make the inline
1959 // image point to the original file (could be PS, for example)
1960 if (originalFilename && (strcmp(inlineFilename, originalFilename) != 0))
1961 {
1962 TexOutput("<A HREF=\"");
1963 TexOutput(ConvertCase(originalFilename));
1964 TexOutput("\">");
1965 TexOutput("<img src=\"");
1966 TexOutput(ConvertCase(wxFileNameFromPath(inlineFilename)));
1967 TexOutput("\""); TexOutput(alignment); TexOutput("></A>");
1968 }
1969 else
1970 #endif
1971 {
1972 TexOutput("<img src=\"");
1973 TexOutput(ConvertCase(wxFileNameFromPath(inlineFilename)));
1974 TexOutput("\""); TexOutput(alignment); TexOutput("></A>");
1975 delete[] inlineFilename;
1976 }
1977 }
1978 else
1979 {
1980 // Last resort - a link to a PS file.
1981 TexOutput("<A HREF=\"");
1982 TexOutput(ConvertCase(wxFileNameFromPath(filename)));
1983 TexOutput("\">Picture</A>\n");
1984 sprintf(buf, "Warning: could not find an inline XBM/GIF for %s.", filename);
1985 OnInform(buf);
1986 }
1987 }
1988 }
1989 return FALSE;
1990 break;
1991 }
1992 // First arg is PSBOX spec (ignored), second is image file, third is map name.
1993 case ltIMAGEMAP:
1994 {
1995 static char *imageFile = NULL;
1996 if (start && (arg_no == 2))
1997 {
1998 // Try to find an XBM or GIF image first.
1999 char *filename = copystring(GetArgData());
2000 char buf[500];
2001
2002 strcpy(buf, filename);
2003 StripExtension(buf);
2004 strcat(buf, ".xbm");
2005 wxString f = TexPathList.FindValidPath(buf);
2006
2007 if (f == "") // Try for a GIF instead
2008 {
2009 strcpy(buf, filename);
2010 StripExtension(buf);
2011 strcat(buf, ".gif");
2012 f = TexPathList.FindValidPath(buf);
2013 }
2014 if (f == "")
2015 {
2016 char buf[300];
2017 sprintf(buf, "Warning: could not find an inline XBM/GIF for %s.", filename);
2018 OnInform(buf);
2019 }
2020 delete[] filename;
2021 if (imageFile)
2022 delete[] imageFile;
2023 imageFile = NULL;
2024 if (!f.IsEmpty())
2025 {
2026 imageFile = copystring(f);
2027 }
2028 }
2029 else if (start && (arg_no == 3))
2030 {
2031 if (imageFile)
2032 {
2033 // First, try to find a .shg (segmented hypergraphics file)
2034 // that we can convert to a map file
2035 char buf[256];
2036 strcpy(buf, imageFile);
2037 StripExtension(buf);
2038 strcat(buf, ".shg");
2039 wxString f = TexPathList.FindValidPath(buf);
2040
2041 if (f != "")
2042 {
2043 // The default HTML file to go to is THIS file (so a no-op)
2044 SHGToMap((char*) (const char*) f, currentFileName);
2045 }
2046
2047 char *mapName = GetArgData();
2048 TexOutput("<A HREF=\"/cgi-bin/imagemap/");
2049 if (mapName)
2050 TexOutput(mapName);
2051 else
2052 TexOutput("unknown");
2053 TexOutput("\">");
2054 TexOutput("<img src=\"");
2055 TexOutput(ConvertCase(wxFileNameFromPath(imageFile)));
2056 TexOutput("\" ISMAP></A><P>");
2057 delete[] imageFile;
2058 imageFile = NULL;
2059 }
2060 }
2061 return FALSE;
2062 break;
2063 }
2064 case ltINDENTED :
2065 {
2066 if ( arg_no == 1 )
2067 return FALSE;
2068 else
2069 {
2070 return TRUE;
2071 }
2072 }
2073 case ltITEM:
2074 {
2075 if (start)
2076 {
2077 descriptionItemArg = GetArgChunk();
2078 return FALSE;
2079 }
2080 }
2081 case ltTWOCOLITEM:
2082 case ltTWOCOLITEMRULED:
2083 {
2084 /*
2085 if (start && (arg_no == 1))
2086 TexOutput("\n<DT> ");
2087 if (start && (arg_no == 2))
2088 TexOutput("<DD> ");
2089 */
2090 if (arg_no == 1)
2091 {
2092 if ( start )
2093 TexOutput("\n<TR><TD VALIGN=TOP>\n");
2094 else
2095 TexOutput("\n</TD>\n");
2096 }
2097 if (arg_no == 2)
2098 {
2099 if ( start )
2100 TexOutput("\n<TD VALIGN=TOP>\n");
2101 else
2102 TexOutput("\n</TD></TR>\n");
2103 }
2104 return TRUE;
2105 break;
2106 }
2107 case ltNUMBEREDBIBITEM:
2108 {
2109 if (arg_no == 1 && start)
2110 {
2111 TexOutput("\n<DT> ");
2112 }
2113 if (arg_no == 2 && !start)
2114 TexOutput("<P>\n");
2115 break;
2116 }
2117 case ltBIBITEM:
2118 {
2119 char buf[100];
2120 if (arg_no == 1 && start)
2121 {
2122 char *citeKey = GetArgData();
2123 TexRef *ref = (TexRef *)TexReferences.Get(citeKey);
2124 if (ref)
2125 {
2126 if (ref->sectionNumber) delete[] ref->sectionNumber;
2127 sprintf(buf, "[%d]", citeCount);
2128 ref->sectionNumber = copystring(buf);
2129 }
2130
2131 sprintf(buf, "\n<DT> [%d] ", citeCount);
2132 TexOutput(buf);
2133 citeCount ++;
2134 return FALSE;
2135 }
2136 if (arg_no == 2 && !start)
2137 TexOutput("<P>\n");
2138 return TRUE;
2139 break;
2140 }
2141 case ltMARGINPAR:
2142 case ltMARGINPARODD:
2143 case ltMARGINPAREVEN:
2144 case ltNORMALBOX:
2145 case ltNORMALBOXD:
2146 {
2147 if (start)
2148 {
2149 TexOutput("<HR>\n");
2150 return TRUE;
2151 }
2152 else
2153 TexOutput("<HR><P>\n");
2154 break;
2155 }
2156 /*
2157 * Accents
2158 *
2159 */
2160 case ltACCENT_GRAVE:
2161 {
2162 if (start)
2163 {
2164 char *val = GetArgData();
2165 if (val)
2166 {
2167 switch (val[0])
2168 {
2169 case 'a':
2170 TexOutput("&agrave;");
2171 break;
2172 case 'e':
2173 TexOutput("&egrave;");
2174 break;
2175 case 'i':
2176 TexOutput("&igrave;");
2177 break;
2178 case 'o':
2179 TexOutput("&ograve;");
2180 break;
2181 case 'u':
2182 TexOutput("&ugrave;");
2183 break;
2184 case 'A':
2185 TexOutput("&Agrave;");
2186 break;
2187 case 'E':
2188 TexOutput("&Egrave;");
2189 break;
2190 case 'I':
2191 TexOutput("&Igrave;");
2192 break;
2193 case 'O':
2194 TexOutput("&Ograve;");
2195 break;
2196 case 'U':
2197 TexOutput("&Igrave;");
2198 break;
2199 default:
2200 break;
2201 }
2202 }
2203 }
2204 return FALSE;
2205 break;
2206 }
2207 case ltACCENT_ACUTE:
2208 {
2209 if (start)
2210 {
2211 char *val = GetArgData();
2212 if (val)
2213 {
2214 switch (val[0])
2215 {
2216 case 'a':
2217 TexOutput("&aacute;");
2218 break;
2219 case 'e':
2220 TexOutput("&eacute;");
2221 break;
2222 case 'i':
2223 TexOutput("&iacute;");
2224 break;
2225 case 'o':
2226 TexOutput("&oacute;");
2227 break;
2228 case 'u':
2229 TexOutput("&uacute;");
2230 break;
2231 case 'y':
2232 TexOutput("&yacute;");
2233 break;
2234 case 'A':
2235 TexOutput("&Aacute;");
2236 break;
2237 case 'E':
2238 TexOutput("&Eacute;");
2239 break;
2240 case 'I':
2241 TexOutput("&Iacute;");
2242 break;
2243 case 'O':
2244 TexOutput("&Oacute;");
2245 break;
2246 case 'U':
2247 TexOutput("&Uacute;");
2248 break;
2249 case 'Y':
2250 TexOutput("&Yacute;");
2251 break;
2252 default:
2253 break;
2254 }
2255 }
2256 }
2257 return FALSE;
2258 break;
2259 }
2260 case ltACCENT_CARET:
2261 {
2262 if (start)
2263 {
2264 char *val = GetArgData();
2265 if (val)
2266 {
2267 switch (val[0])
2268 {
2269 case 'a':
2270 TexOutput("&acirc;");
2271 break;
2272 case 'e':
2273 TexOutput("&ecirc;");
2274 break;
2275 case 'i':
2276 TexOutput("&icirc;");
2277 break;
2278 case 'o':
2279 TexOutput("&ocirc;");
2280 break;
2281 case 'u':
2282 TexOutput("&ucirc;");
2283 break;
2284 case 'A':
2285 TexOutput("&Acirc;");
2286 break;
2287 case 'E':
2288 TexOutput("&Ecirc;");
2289 break;
2290 case 'I':
2291 TexOutput("&Icirc;");
2292 break;
2293 case 'O':
2294 TexOutput("&Ocirc;");
2295 break;
2296 case 'U':
2297 TexOutput("&Icirc;");
2298 break;
2299 default:
2300 break;
2301 }
2302 }
2303 }
2304 return FALSE;
2305 break;
2306 }
2307 case ltACCENT_TILDE:
2308 {
2309 if (start)
2310 {
2311 char *val = GetArgData();
2312 if (val)
2313 {
2314 switch (val[0])
2315 {
2316 case ' ':
2317 TexOutput("~");
2318 break;
2319 case 'a':
2320 TexOutput("&atilde;");
2321 break;
2322 case 'n':
2323 TexOutput("&ntilde;");
2324 break;
2325 case 'o':
2326 TexOutput("&otilde;");
2327 break;
2328 case 'A':
2329 TexOutput("&Atilde;");
2330 break;
2331 case 'N':
2332 TexOutput("&Ntilde;");
2333 break;
2334 case 'O':
2335 TexOutput("&Otilde;");
2336 break;
2337 default:
2338 break;
2339 }
2340 }
2341 }
2342 return FALSE;
2343 break;
2344 }
2345 case ltACCENT_UMLAUT:
2346 {
2347 if (start)
2348 {
2349 char *val = GetArgData();
2350 if (val)
2351 {
2352 switch (val[0])
2353 {
2354 case 'a':
2355 TexOutput("&auml;");
2356 break;
2357 case 'e':
2358 TexOutput("&euml;");
2359 break;
2360 case 'i':
2361 TexOutput("&iuml;");
2362 break;
2363 case 'o':
2364 TexOutput("&ouml;");
2365 break;
2366 case 'u':
2367 TexOutput("&uuml;");
2368 break;
2369 case 'y':
2370 TexOutput("&yuml;");
2371 break;
2372 case 'A':
2373 TexOutput("&Auml;");
2374 break;
2375 case 'E':
2376 TexOutput("&Euml;");
2377 break;
2378 case 'I':
2379 TexOutput("&Iuml;");
2380 break;
2381 case 'O':
2382 TexOutput("&Ouml;");
2383 break;
2384 case 'U':
2385 TexOutput("&Uuml;");
2386 break;
2387 case 'Y':
2388 TexOutput("&Yuml;");
2389 break;
2390 default:
2391 break;
2392 }
2393 }
2394 }
2395 return FALSE;
2396 break;
2397 }
2398 case ltACCENT_DOT:
2399 {
2400 if (start)
2401 {
2402 char *val = GetArgData();
2403 if (val)
2404 {
2405 switch (val[0])
2406 {
2407 case 'a':
2408 TexOutput("&aring;");
2409 break;
2410 case 'A':
2411 TexOutput("&Aring;");
2412 break;
2413 default:
2414 break;
2415 }
2416 }
2417 }
2418 return FALSE;
2419 break;
2420 }
2421 case ltBACKGROUND:
2422 {
2423 if (start)
2424 {
2425 char *val = GetArgData();
2426 if (val)
2427 {
2428 bool isPicture = FALSE;
2429 char *s = ParseColourString(val, &isPicture);
2430 if (isPicture)
2431 {
2432 if (backgroundImageString)
2433 delete[] backgroundImageString;
2434 backgroundImageString = copystring(val);
2435 }
2436 else
2437 {
2438 if (backgroundColourString)
2439 delete[] backgroundColourString;
2440 backgroundColourString = copystring(val);
2441 }
2442 }
2443 }
2444 return FALSE;
2445 break;
2446 }
2447 case ltBACKGROUNDIMAGE:
2448 {
2449 if (start)
2450 {
2451 char *val = GetArgData();
2452 if (val)
2453 {
2454 if (backgroundImageString)
2455 delete[] backgroundImageString;
2456 backgroundImageString = copystring(val);
2457 }
2458 }
2459 return FALSE;
2460 break;
2461 }
2462 case ltBACKGROUNDCOLOUR:
2463 {
2464 if (start)
2465 {
2466 char *val = GetArgData();
2467 if (val)
2468 {
2469 if (backgroundColourString)
2470 delete[] backgroundColourString;
2471 backgroundColourString = copystring(val);
2472 }
2473 }
2474 return FALSE;
2475 break;
2476 }
2477 case ltTEXTCOLOUR:
2478 {
2479 if (start)
2480 {
2481 char *val = GetArgData();
2482 if (val)
2483 {
2484 if (textColourString)
2485 delete[] textColourString;
2486 textColourString = copystring(val);
2487 }
2488 }
2489 return FALSE;
2490 break;
2491 }
2492 case ltLINKCOLOUR:
2493 {
2494 if (start)
2495 {
2496 char *val = GetArgData();
2497 if (val)
2498 {
2499 if (linkColourString)
2500 delete[] linkColourString;
2501 linkColourString = copystring(val);
2502 }
2503 }
2504 return FALSE;
2505 break;
2506 }
2507 case ltFOLLOWEDLINKCOLOUR:
2508 {
2509 if (start)
2510 {
2511 char *val = GetArgData();
2512 if (val)
2513 {
2514 if (followedLinkColourString)
2515 delete[] followedLinkColourString;
2516 followedLinkColourString = copystring(val);
2517 }
2518 }
2519 return FALSE;
2520 break;
2521 }
2522 case ltACCENT_CADILLA:
2523 {
2524 if (start)
2525 {
2526 char *val = GetArgData();
2527 if (val)
2528 {
2529 switch (val[0])
2530 {
2531 case 'c':
2532 TexOutput("&ccedil;");
2533 break;
2534 case 'C':
2535 TexOutput("&Ccedil;");
2536 break;
2537 default:
2538 break;
2539 }
2540 }
2541 }
2542 return FALSE;
2543 break;
2544 }
2545 /*
2546 case ltFOOTNOTE:
2547 case ltFOOTNOTEPOPUP:
2548 {
2549 if (arg_no == 1)
2550 return TRUE;
2551 else
2552 return FALSE;
2553 break;
2554 }
2555 */
2556 case ltTABULAR:
2557 case ltSUPERTABULAR:
2558 {
2559 if (arg_no == 1)
2560 {
2561 if (start)
2562 {
2563 currentRowNumber = 0;
2564 inTabular = TRUE;
2565 startRows = TRUE;
2566 tableVerticalLineLeft = FALSE;
2567 tableVerticalLineRight = FALSE;
2568 int currentWidth = 0;
2569
2570 char *alignString = copystring(GetArgData());
2571 ParseTableArgument(alignString);
2572
2573 TexOutput("<TABLE BORDER>\n");
2574
2575 // Write the first row formatting for compatibility
2576 // with standard Latex
2577 if (compatibilityMode)
2578 {
2579 TexOutput("<TR>\n<TD>");
2580 /*
2581 for (int i = 0; i < noColumns; i++)
2582 {
2583 currentWidth += TableData[i].width;
2584 sprintf(buf, "\\cellx%d", currentWidth);
2585 TexOutput(buf);
2586 }
2587 TexOutput("\\pard\\intbl\n");
2588 */
2589 }
2590 delete[] alignString;
2591
2592 return FALSE;
2593 }
2594 }
2595 else if (arg_no == 2 && !start)
2596 {
2597 TexOutput("</TABLE>\n");
2598 inTabular = FALSE;
2599 }
2600 break;
2601 }
2602 case ltTHEBIBLIOGRAPHY:
2603 {
2604 if (start && (arg_no == 1))
2605 {
2606 ReopenFile(&Chapters, &ChaptersName);
2607 AddTexRef("bibliography", ChaptersName, "bibliography");
2608 SetCurrentSubsectionName("bibliography", ChaptersName);
2609
2610 citeCount = 1;
2611
2612 SetCurrentOutput(Chapters);
2613
2614 char titleBuf[150];
2615 if (truncateFilenames)
2616 sprintf(titleBuf, "%s.htm", FileNameFromPath(FileRoot));
2617 else
2618 sprintf(titleBuf, "%s_contents.html", FileNameFromPath(FileRoot));
2619
2620 TexOutput("<head><title>");
2621 TexOutput(ReferencesNameString);
2622 TexOutput("</title></head>\n");
2623 OutputBodyStart();
2624
2625 fprintf(Chapters, "<A NAME=\"%s\">\n<H2>%s", "bibliography", ReferencesNameString);
2626 AddBrowseButtons("contents", titleBuf, // Up
2627 lastTopic, lastFileName, // Last topic
2628 "bibliography", ChaptersName); // This topic
2629
2630 SetCurrentOutputs(Contents, Chapters);
2631 fprintf(Contents, "\n<LI><A HREF=\"%s#%s\">", ConvertCase(ChaptersName), "bibliography");
2632
2633 fprintf(Contents, "%s</A>\n", ReferencesNameString);
2634 fprintf(Chapters, "</H2>\n</A>\n");
2635
2636 SetCurrentOutput(Chapters);
2637 return FALSE;
2638 }
2639 if (!start && (arg_no == 2))
2640 {
2641 }
2642 return TRUE;
2643 break;
2644 }
2645 case ltINDEX:
2646 {
2647 /* Build up list of keywords associated with topics */
2648 if (start)
2649 {
2650 // char *entry = GetArgData();
2651 char buf[300];
2652 OutputChunkToString(GetArgChunk(), buf);
2653 if (CurrentTopic)
2654 {
2655 AddKeyWordForTopic(CurrentTopic, buf, currentFileName);
2656 }
2657 }
2658 return FALSE;
2659 break;
2660 }
2661 case ltFCOL:
2662 // case ltBCOL:
2663 {
2664 if (start)
2665 {
2666 switch (arg_no)
2667 {
2668 case 1:
2669 {
2670 char *name = GetArgData();
2671 char buf2[10];
2672 if (!FindColourHTMLString(name, buf2))
2673 {
2674 strcpy(buf2, "#000000");
2675 char buf[100];
2676 sprintf(buf, "Could not find colour name %s", name);
2677 OnError(buf);
2678 }
2679 TexOutput("<FONT COLOR=\"");
2680 TexOutput(buf2);
2681 TexOutput("\">");
2682 break;
2683 }
2684 case 2:
2685 {
2686 return TRUE;
2687 break;
2688 }
2689 default:
2690 break;
2691 }
2692 }
2693 else
2694 {
2695 if (arg_no == 2) TexOutput("</FONT>");
2696 }
2697 return FALSE;
2698 break;
2699 }
2700 case ltINSERTATLEVEL:
2701 {
2702 // This macro allows you to insert text at a different level
2703 // from the current level, e.g. into the Sections from within a subsubsection.
2704 if (useWord)
2705 return FALSE;
2706 static int currentLevelNo = 1;
2707 static FILE* oldLevelFile = Chapters;
2708 if (start)
2709 {
2710 switch (arg_no)
2711 {
2712 case 1:
2713 {
2714 oldLevelFile = CurrentOutput1;
2715
2716 char *str = GetArgData();
2717 currentLevelNo = atoi(str);
2718 FILE* outputFile;
2719 // TODO: cope with article style (no chapters)
2720 switch (currentLevelNo)
2721 {
2722 case 1:
2723 {
2724 outputFile = Chapters;
2725 break;
2726 }
2727 case 2:
2728 {
2729 outputFile = Sections;
2730 break;
2731 }
2732 case 3:
2733 {
2734 outputFile = Subsections;
2735 break;
2736 }
2737 case 4:
2738 {
2739 outputFile = Subsubsections;
2740 break;
2741 }
2742 default:
2743 {
2744 outputFile = NULL;
2745 break;
2746 }
2747 }
2748 if (outputFile)
2749 CurrentOutput1 = outputFile;
2750 return FALSE;
2751 break;
2752 }
2753 case 2:
2754 {
2755 return TRUE;
2756 break;
2757 }
2758 default:
2759 break;
2760 }
2761 return TRUE;
2762 }
2763 else
2764 {
2765 if (arg_no == 2)
2766 {
2767 CurrentOutput1 = oldLevelFile;
2768 }
2769 return TRUE;
2770 }
2771 }
2772 default:
2773 return DefaultOnArgument(macroId, arg_no, start);
2774 break;
2775 }
2776 return TRUE;
2777 }
2778
2779 bool HTMLGo(void)
2780 {
2781 fileId = 0;
2782 inVerbatim = FALSE;
2783 indentLevel = 0;
2784 inTabular = FALSE;
2785 startRows = FALSE;
2786 tableVerticalLineLeft = FALSE;
2787 tableVerticalLineRight = FALSE;
2788 noColumns = 0;
2789
2790 if (InputFile && OutputFile)
2791 {
2792 // Do some HTML-specific transformations on all the strings,
2793 // recursively
2794 Text2HTML(GetTopLevelChunk());
2795
2796 char buf[300];
2797 if (truncateFilenames)
2798 sprintf(buf, "%s.htm", FileRoot);
2799 else
2800 sprintf(buf, "%s_contents.html", FileRoot);
2801 if (TitlepageName) delete[] TitlepageName;
2802 TitlepageName = copystring(buf);
2803 Titlepage = fopen(buf, "w");
2804
2805 if (truncateFilenames)
2806 sprintf(buf, "%s_fc.htm", FileRoot);
2807 else
2808 sprintf(buf, "%s_fcontents.html", FileRoot);
2809
2810 contentsFrameName = copystring(buf);
2811
2812 Contents = fopen(TmpContentsName, "w");
2813
2814 if (htmlFrameContents)
2815 {
2816 // FrameContents = fopen(TmpFrameContentsName, "w");
2817 FrameContents = fopen(contentsFrameName, "w");
2818 fprintf(FrameContents, "<HTML>\n<UL>\n");
2819 }
2820
2821 if (!Titlepage || !Contents)
2822 {
2823 OnError("Cannot open output file!");
2824 return FALSE;
2825 }
2826 AddTexRef("contents", FileNameFromPath(TitlepageName), ContentsNameString);
2827
2828 fprintf(Contents, "<P><P><H2>%s</H2><P><P>\n", ContentsNameString);
2829
2830 fprintf(Contents, "<UL>\n");
2831
2832 SetCurrentOutput(Titlepage);
2833 if (htmlWorkshopFiles) HTMLWorkshopStartContents();
2834 OnInform("Converting...");
2835
2836 TraverseDocument();
2837 fprintf(Contents, "</UL>\n\n");
2838
2839 // SetCurrentOutput(Titlepage);
2840 fclose(Titlepage);
2841
2842 if (Contents)
2843 {
2844 // fprintf(Titlepage, "\n</BODY></HTML>\n");
2845 fclose(Contents);
2846 Contents = NULL;
2847 }
2848
2849 if (FrameContents)
2850 {
2851 fprintf(FrameContents, "\n</UL>\n");
2852 fprintf(FrameContents, "</HTML>\n");
2853 fclose(FrameContents);
2854 FrameContents = NULL;
2855 }
2856
2857 if (Chapters)
2858 {
2859 fprintf(Chapters, "\n</BODY></HTML>\n");
2860 fclose(Chapters);
2861 Chapters = NULL;
2862 }
2863 if (Sections)
2864 {
2865 fprintf(Sections, "\n</BODY></HTML>\n");
2866 fclose(Sections);
2867 Sections = NULL;
2868 }
2869 if (Subsections && !combineSubSections)
2870 {
2871 fprintf(Subsections, "\n</BODY></HTML>\n");
2872 fclose(Subsections);
2873 Subsections = NULL;
2874 }
2875 if (Subsubsections && !combineSubSections)
2876 {
2877 fprintf(Subsubsections, "\n</BODY></HTML>\n");
2878 fclose(Subsubsections);
2879 Subsubsections = NULL;
2880 }
2881 if ( SectionContentsFD )
2882 {
2883 fclose(SectionContentsFD);
2884 SectionContentsFD = NULL;
2885 }
2886
2887 // Create a temporary file for the title page header, add some info,
2888 // and concat the titlepage just generated.
2889 // This is necessary in order to put the title of the document
2890 // at the TOP of the file within <HEAD>, even though we only find out
2891 // what it is later on.
2892 FILE *tmpTitle = fopen("title.tmp", "w");
2893 if (tmpTitle)
2894 {
2895 if (DocumentTitle)
2896 {
2897 SetCurrentOutput(tmpTitle);
2898 TexOutput("\n<HTML>\n<HEAD><TITLE>");
2899 TraverseChildrenFromChunk(DocumentTitle);
2900 TexOutput("</TITLE></HEAD>\n");
2901 }
2902 else
2903 {
2904 SetCurrentOutput(tmpTitle);
2905 if (contentsString)
2906 fprintf(tmpTitle, "<HEAD><TITLE>%s</TITLE></HEAD>\n\n", contentsString);
2907 else
2908 fprintf(tmpTitle, "<HEAD><TITLE>%s</TITLE></HEAD>\n\n", FileNameFromPath(FileRoot));
2909 }
2910
2911 // Output frame information
2912 if (htmlFrameContents)
2913 {
2914 char firstFileName[300];
2915 if (truncateFilenames)
2916 sprintf(firstFileName, "%s1.htm", FileRoot);
2917 else
2918 sprintf(firstFileName, "%s1.html", FileRoot);
2919
2920 fprintf(tmpTitle, "<FRAMESET COLS=\"30%%,70%%\">\n");
2921
2922 fprintf(tmpTitle, "<FRAME SRC=\"%s\">\n", ConvertCase(FileNameFromPath(contentsFrameName)));
2923 fprintf(tmpTitle, "<FRAME SRC=\"%s\" NAME=\"mainwindow\">\n", ConvertCase(FileNameFromPath(firstFileName)));
2924 fprintf(tmpTitle, "</FRAMESET>\n");
2925
2926 fprintf(tmpTitle, "<NOFRAMES>\n");
2927 }
2928
2929 // Output <BODY...> to temporary title page
2930 OutputBodyStart();
2931
2932 // Concat titlepage
2933 FILE *fd = fopen(TitlepageName, "r");
2934 if (fd)
2935 {
2936 int ch = getc(fd);
2937 while (ch != EOF)
2938 {
2939 putc(ch, tmpTitle);
2940 ch = getc(fd);
2941 }
2942 fclose(fd);
2943 }
2944
2945 fprintf(tmpTitle, "\n</BODY>\n");
2946
2947 if (htmlFrameContents)
2948 {
2949 fprintf(tmpTitle, "\n</NOFRAMES>\n");
2950 }
2951 fprintf(tmpTitle, "\n</HTML>\n");
2952
2953 fclose(tmpTitle);
2954 if (FileExists(TitlepageName)) wxRemoveFile(TitlepageName);
2955 if (!wxRenameFile("title.tmp", TitlepageName))
2956 {
2957 wxCopyFile("title.tmp", TitlepageName);
2958 wxRemoveFile("title.tmp");
2959 }
2960 }
2961
2962 if (lastFileName) delete[] lastFileName;
2963 lastFileName = NULL;
2964 if (lastTopic) delete[] lastTopic;
2965 lastTopic = NULL;
2966
2967 if (FileExists(ContentsName)) wxRemoveFile(ContentsName);
2968
2969 if (!wxRenameFile(TmpContentsName, ContentsName))
2970 {
2971 wxCopyFile(TmpContentsName, ContentsName);
2972 wxRemoveFile(TmpContentsName);
2973 }
2974
2975 // Generate .htx file if requested
2976 if (htmlIndex)
2977 {
2978 char htmlIndexName[300];
2979 sprintf(htmlIndexName, "%s.htx", FileRoot);
2980 GenerateHTMLIndexFile(htmlIndexName);
2981 }
2982
2983 // Generate HTML Help Workshop files if requested
2984 if (htmlWorkshopFiles)
2985 {
2986 HTMLWorkshopEndContents();
2987 GenerateHTMLWorkshopFiles(FileRoot);
2988 }
2989
2990
2991 return TRUE;
2992 }
2993
2994 return FALSE;
2995 }
2996
2997 // Output .htx index file
2998 void GenerateHTMLIndexFile(char *fname)
2999 {
3000 FILE *fd = fopen(fname, "w");
3001 if (!fd)
3002 return;
3003
3004 TopicTable.BeginFind();
3005 wxNode *node = NULL;
3006 while ((node = TopicTable.Next()))
3007 {
3008 TexTopic *texTopic = (TexTopic *)node->Data();
3009 const char *topicName = node->GetKeyString();
3010 if (texTopic->filename && texTopic->keywords)
3011 {
3012 wxNode *node1 = texTopic->keywords->First();
3013 while (node1)
3014 {
3015 char *s = (char *)node1->Data();
3016 fprintf(fd, "%s|%s|%s\n", topicName, texTopic->filename, s);
3017 node1 = node1->Next();
3018 }
3019 }
3020 }
3021 fclose(fd);
3022 }
3023
3024
3025
3026
3027
3028
3029
3030 // output .hpp, .hhc and .hhk files:
3031
3032
3033 void GenerateHTMLWorkshopFiles(char *fname)
3034 {
3035 FILE *f;
3036 char buf[300];
3037
3038 /* Generate project file : */
3039
3040 sprintf(buf, "%s.hhp", fname);
3041 f = fopen(buf, "wt");
3042 fprintf(f,
3043 "[OPTIONS]\n"
3044 "Compatibility=1.1\n"
3045 "Full-text search=Yes\n"
3046 "Contents file=%s.hhc\n"
3047 "Compiled file=%s.chm\n"
3048 "Default Window=%sHelp\n"
3049 "Default topic=%s\n"
3050 "Index file=%s.hhk\n"
3051 "Title=",
3052 FileNameFromPath(fname),
3053 FileNameFromPath(fname),
3054 FileNameFromPath(fname),
3055 FileNameFromPath(TitlepageName),
3056 FileNameFromPath(fname)
3057 );
3058
3059 if (DocumentTitle) {
3060 SetCurrentOutput(f);
3061 TraverseChildrenFromChunk(DocumentTitle);
3062 }
3063 else fprintf(f, "(unknown)");
3064
3065 fprintf(f, "\n\n[WINDOWS]\n"
3066 "%sHelp=,\"%s.hhc\",\"%s.hhk\",\"%s\",,,,,,0x2420,,0x380e,,,,,0,,,",
3067 FileNameFromPath(fname),
3068 FileNameFromPath(fname),
3069 FileNameFromPath(fname),
3070 FileNameFromPath(TitlepageName));
3071
3072
3073 fprintf(f, "\n\n[FILES]\n");
3074 fprintf(f, "%s\n", FileNameFromPath(TitlepageName));
3075 for (int i = 1; i <= fileId; i++) {
3076 if (truncateFilenames)
3077 sprintf(buf, "%s%d.htm", FileNameFromPath(FileRoot), i);
3078 else
3079 sprintf(buf, "%s%d.html", FileNameFromPath(FileRoot), i);
3080 fprintf(f, "%s\n", buf);
3081 }
3082 fclose(f);
3083
3084 /* Generate index file : */
3085
3086 sprintf(buf, "%s.hhk", fname);
3087 f = fopen(buf, "wt");
3088
3089 fprintf(f,
3090 "<!DOCTYPE HTML PUBLIC \"-//IETF//DTD HTML//EN\">\n"
3091 "<HTML>\n"
3092 "<HEAD>\n"
3093 "<meta name=\"GENERATOR\" content=\"tex2rtf\">\n"
3094 "<!-- Sitemap 1.0 -->\n"
3095 "</HEAD><BODY>\n"
3096 "<OBJECT type=\"text/site properties\">\n"
3097 " <param name=\"ImageType\" value=\"Folder\">\n"
3098 "</OBJECT>\n"
3099 "<UL>\n");
3100
3101 TopicTable.BeginFind();
3102 wxNode *node = NULL;
3103 while ((node = TopicTable.Next()))
3104 {
3105 TexTopic *texTopic = (TexTopic *)node->Data();
3106 const char *topicName = node->GetKeyString();
3107 if (texTopic->filename && texTopic->keywords)
3108 {
3109 wxNode *node1 = texTopic->keywords->First();
3110 while (node1)
3111 {
3112 char *s = (char *)node1->Data();
3113 fprintf(f,
3114 " <LI> <OBJECT type=\"text/sitemap\">\n"
3115 " <param name=\"Local\" value=\"%s#%s\">\n"
3116 " <param name=\"Name\" value=\"%s\">\n"
3117 " </OBJECT>\n",
3118 texTopic->filename, topicName, s);
3119 node1 = node1->Next();
3120 }
3121 }
3122 }
3123
3124 fprintf(f, "</UL>\n");
3125 fclose(f);
3126 }
3127
3128
3129
3130 static FILE *HTMLWorkshopContents = NULL;
3131 static int HTMLWorkshopLastLevel = 0;
3132
3133 void HTMLWorkshopAddToContents(int level, char *s, char *file)
3134 {
3135 int i;
3136
3137 if (level > HTMLWorkshopLastLevel)
3138 for (i = HTMLWorkshopLastLevel; i < level; i++)
3139 fprintf(HTMLWorkshopContents, "<UL>");
3140 if (level < HTMLWorkshopLastLevel)
3141 for (i = level; i < HTMLWorkshopLastLevel; i++)
3142 fprintf(HTMLWorkshopContents, "</UL>");
3143
3144 SetCurrentOutput(HTMLWorkshopContents);
3145 fprintf(HTMLWorkshopContents,
3146 " <LI> <OBJECT type=\"text/sitemap\">\n"
3147 " <param name=\"Local\" value=\"%s#%s\">\n"
3148 " <param name=\"Name\" value=\"",
3149 file, s);
3150 OutputCurrentSection();
3151 fprintf(HTMLWorkshopContents,
3152 "\">\n"
3153 " </OBJECT>\n");
3154 HTMLWorkshopLastLevel = level;
3155 }
3156
3157
3158 void HTMLWorkshopStartContents()
3159 {
3160 char buf[300];
3161 sprintf(buf, "%s.hhc", FileRoot);
3162 HTMLWorkshopContents = fopen(buf, "wt");
3163 HTMLWorkshopLastLevel = 0;
3164
3165 fprintf(HTMLWorkshopContents,
3166 "<!DOCTYPE HTML PUBLIC \"-//IETF//DTD HTML//EN\">\n"
3167 "<HTML>\n"
3168 "<HEAD>\n"
3169 "<meta name=\"GENERATOR\" content=\"tex2rtf\">\n"
3170 "<!-- Sitemap 1.0 -->\n"
3171 "</HEAD><BODY>\n"
3172 "<OBJECT type=\"text/site properties\">\n"
3173 " <param name=\"ImageType\" value=\"Folder\">\n"
3174 "</OBJECT>\n"
3175 "<UL>\n"
3176 "<LI> <OBJECT type=\"text/sitemap\">\n"
3177 "<param name=\"Local\" value=\"%s\">\n"
3178 "<param name=\"Name\" value=\"Contents\">\n</OBJECT>\n",
3179 FileNameFromPath(TitlepageName)
3180 );
3181
3182 }
3183
3184
3185 void HTMLWorkshopEndContents()
3186 {
3187 for (int i = HTMLWorkshopLastLevel; i >= 0; i--)
3188 fprintf(HTMLWorkshopContents, "</UL>\n");
3189 fclose(HTMLWorkshopContents);
3190 }