]> git.saurik.com Git - wxWidgets.git/blame - utils/tex2rtf/src/tex2rtf.cpp
corrections to dynamic loading for Darwin
[wxWidgets.git] / utils / tex2rtf / src / tex2rtf.cpp
CommitLineData
9a29912f
JS
1/////////////////////////////////////////////////////////////////////////////
2// Name: tex2rtf.cpp
3// Purpose: Converts Latex to linear/WinHelp RTF, HTML, wxHelp.
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#ifndef NO_GUI
4538b3f1
GD
28#include "wx/help.h"
29#include "wx/timer.h"
9a29912f
JS
30#endif
31
ffaaaacb 32#if defined(NO_GUI) || defined(__UNIX__)
9a29912f
JS
33#if wxUSE_IOSTREAMH
34#include <iostream.h>
35#include <fstream.h>
36#else
37#include <iostream>
38#include <fstream>
39#endif
40#endif
41
42#include <ctype.h>
43#include <stdlib.h>
44#include "tex2any.h"
45#include "tex2rtf.h"
46#include "rtfutils.h"
47
610c6ded 48#if (defined(__WXGTK__) || defined(__WXMOTIF__) || defined(__WXMAC__)) && !defined(NO_GUI)
9a29912f
JS
49#include "tex2rtf.xpm"
50#endif
51
52const float versionNo = 2.0;
53
54TexChunk *currentMember = NULL;
55bool startedSections = FALSE;
56char *contentsString = NULL;
57bool suppressNameDecoration = FALSE;
58bool OkToClose = TRUE;
59int passNumber = 1;
63ad540d 60int errorCount = 0;
9a29912f
JS
61
62#ifndef NO_GUI
ffaaaacb 63
71599f0a
GT
64extern char *BigBuffer;
65extern char *TexFileRoot;
66extern char *TexBibName; // Bibliography output file name
67extern char *TexTmpBibName; // Temporary bibliography output file name
68extern wxList ColourTable;
69extern TexChunk *TopLevel;
3924dd22
GT
70extern char *PageStyle;
71extern char *BibliographyStyleString;
72extern char *DocumentStyleString;
73extern char *bitmapMethod;
74extern char *backgroundColourString;
75extern char *ContentsNameString;
76extern char *AbstractNameString;
77extern char *GlossaryNameString;
78extern char *ReferencesNameString;
79extern char *FiguresNameString;
80extern char *TablesNameString;
81extern char *FigureNameString;
82extern char *TableNameString;
83extern char *IndexNameString;
84extern char *ChapterNameString;
85extern char *SectionNameString;
86extern char *SubsectionNameString;
87extern char *SubsubsectionNameString;
88extern char *UpNameString;
89
90
71599f0a 91
ffaaaacb 92#if wxUSE_HELP
9a29912f 93wxHelpController *HelpInstance = NULL;
ffaaaacb 94#endif // wxUSE_HELP
9a29912f
JS
95
96#ifdef __WXMSW__
97static char *ipc_buffer = NULL;
98static char Tex2RTFLastStatus[100];
99Tex2RTFServer *TheTex2RTFServer = NULL;
100#endif
101#endif
102
103char *bulletFile = NULL;
104
105FILE *Contents = NULL; // Contents page
106FILE *Chapters = NULL; // Chapters (WinHelp RTF) or rest of file (linear RTF)
107FILE *Sections = NULL;
108FILE *Subsections = NULL;
109FILE *Subsubsections = NULL;
110FILE *Popups = NULL;
111FILE *WinHelpContentsFile = NULL;
112
113char *InputFile = NULL;
114char *OutputFile = NULL;
115char *MacroFile = copystring("tex2rtf.ini");
116
117char *FileRoot = NULL;
118char *ContentsName = NULL; // Contents page from last time around
119char *TmpContentsName = NULL; // Current contents page
120char *TmpFrameContentsName = NULL; // Current frame contents page
121char *WinHelpContentsFileName = NULL; // WinHelp .cnt file
ad781c23 122char *RefFileName = NULL; // Reference file name
9a29912f
JS
123
124char *RTFCharset = copystring("ansi");
125
126#ifdef __WXMSW__
127int BufSize = 100; // Size of buffer in K
128#else
129int BufSize = 500;
130#endif
131
132bool Go(void);
133void ShowOptions(void);
134
135#ifdef NO_GUI
c4c794e1 136
f6bcfd97
BP
137#if wxUSE_GUI || !defined(__UNIX__)
138// wxBase for Unix does not have wxBuffer
139extern
140#endif
141char *wxBuffer; // we must init it, otherwise tex2rtf will crash
c4c794e1 142
9a29912f
JS
143int main(int argc, char **argv)
144#else
145wxMenuBar *menuBar = NULL;
146MyFrame *frame = NULL;
147
148// DECLARE_APP(MyApp)
149IMPLEMENT_APP(MyApp)
150
151// `Main program' equivalent, creating windows and returning main app frame
152bool MyApp::OnInit()
153#endif
154{
155 // Use default list of macros defined in tex2any.cc
156 DefineDefaultMacros();
157 AddMacroDef(ltHARDY, "hardy", 0);
158
159 FileRoot = new char[300];
160 ContentsName = new char[300];
161 TmpContentsName = new char[300];
162 TmpFrameContentsName = new char[300];
163 WinHelpContentsFileName = new char[300];
ad781c23 164 RefFileName = new char[300];
9a29912f 165
71599f0a
GT
166 ColourTable.DeleteContents(TRUE);
167
9a29912f 168 int n = 1;
ffaaaacb 169
9a29912f
JS
170 // Read input/output files
171 if (argc > 1)
172 {
173 if (argv[1][0] != '-')
174 {
175 InputFile = argv[1];
176 n ++;
177
178 if (argc > 2)
179 {
180 if (argv[2][0] != '-')
181 {
182 OutputFile = argv[2];
183 n ++;
184 }
185 }
186 }
187 }
188
189#ifdef NO_GUI
c4c794e1
VS
190 wxBuffer = new char[1500];
191 // this is done in wxApp, but NO_GUI version doesn't call it :-(
192
9a29912f
JS
193 if (!InputFile || !OutputFile)
194 {
219f4a6d 195 wxSTD cout << "Tex2RTF: input or output file is missing.\n";
9a29912f
JS
196 ShowOptions();
197 exit(1);
198 }
c4c794e1 199
9a29912f
JS
200#endif
201 if (InputFile)
202 {
203 TexPathList.EnsureFileAccessible(InputFile);
204 }
205 if (!InputFile || !OutputFile)
206 isInteractive = TRUE;
207
f6bcfd97
BP
208 int i;
209 for (i = n; i < argc;)
9a29912f
JS
210 {
211 if (strcmp(argv[i], "-winhelp") == 0)
212 {
213 i ++;
214 convertMode = TEX_RTF;
215 winHelp = TRUE;
216 }
217#ifndef NO_GUI
218 else if (strcmp(argv[i], "-interactive") == 0)
219 {
220 i ++;
221 isInteractive = TRUE;
222 }
223#endif
224 else if (strcmp(argv[i], "-sync") == 0) // Don't yield
225 {
226 i ++;
227 isSync = TRUE;
228 }
229 else if (strcmp(argv[i], "-rtf") == 0)
230 {
231 i ++;
232 convertMode = TEX_RTF;
233 }
234 else if (strcmp(argv[i], "-html") == 0)
235 {
236 i ++;
237 convertMode = TEX_HTML;
238 }
239 else if (strcmp(argv[i], "-xlp") == 0)
240 {
241 i ++;
242 convertMode = TEX_XLP;
243 }
244 else if (strcmp(argv[i], "-twice") == 0)
245 {
246 i ++;
247 runTwice = TRUE;
248 }
249 else if (strcmp(argv[i], "-macros") == 0)
250 {
251 i ++;
252 if (i < argc)
253 {
254 MacroFile = copystring(argv[i]);
255 i ++;
256 }
257 }
258 else if (strcmp(argv[i], "-bufsize") == 0)
259 {
260 i ++;
261 if (i < argc)
262 {
263 BufSize = atoi(argv[i]);
264 i ++;
265 }
266 }
267 else if (strcmp(argv[i], "-charset") == 0)
268 {
269 i ++;
270 if (i < argc)
271 {
272 char *s = argv[i];
273 i ++;
274 if (strcmp(s, "ansi") == 0 || strcmp(s, "pc") == 0 || strcmp(s, "mac") == 0 ||
275 strcmp(s, "pca") == 0)
276 RTFCharset = copystring(s);
277 else
278 {
279 OnError("Incorrect argument for -charset");
3f8e5072 280 return FALSE;
9a29912f
JS
281 }
282 }
283 }
fad535ee
GT
284 else if (strcmp(argv[i], "-checkcurleybraces") == 0)
285 {
286 i ++;
287 checkCurleyBraces = TRUE;
288 }
289 else if (strcmp(argv[i], "-checksyntax") == 0)
290 {
291 i ++;
292 checkSyntax = TRUE;
293 }
9a29912f
JS
294 else
295 {
63ad540d
GT
296 wxString buf;
297 buf.Printf("Invalid switch %s.\n", argv[i]);
298 OnError((char *)buf.c_str());
9a29912f
JS
299 i++;
300#ifdef NO_GUI
301 ShowOptions();
302 exit(1);
303#endif
3f8e5072 304 return FALSE;
9a29912f
JS
305 }
306 }
307
308#if defined(__WXMSW__) && !defined(NO_GUI)
309 wxDDEInitialize();
310 Tex2RTFLastStatus[0] = 0; // DDE connection return value
311 TheTex2RTFServer = new Tex2RTFServer;
312 TheTex2RTFServer->Create("TEX2RTF");
313#endif
314
315#if defined(__WXMSW__) && defined(__WIN16__)
316 // Limit to max Windows array size
317 if (BufSize > 64) BufSize = 64;
318#endif
319
320 TexInitialize(BufSize);
321 ResetContentsLevels(0);
322
323#ifndef NO_GUI
324
325 if (isInteractive)
326 {
327 char buf[100];
328
329 // Create the main frame window
330 frame = new MyFrame(NULL, -1, "Tex2RTF", wxPoint(-1, -1), wxSize(400, 300));
331 frame->CreateStatusBar(2);
332
333 // Give it an icon
334 // TODO: uncomment this when we have tex2rtf.xpm
335 frame->SetIcon(wxICON(tex2rtf));
336
337 if (InputFile)
338 {
339 sprintf(buf, "Tex2RTF [%s]", FileNameFromPath(InputFile));
340 frame->SetTitle(buf);
341 }
342
343 // Make a menubar
344 wxMenu *file_menu = new wxMenu;
345 file_menu->Append(TEX_GO, "&Go", "Run converter");
346 file_menu->Append(TEX_SET_INPUT, "Set &Input File", "Set the LaTeX input file");
347 file_menu->Append(TEX_SET_OUTPUT, "Set &Output File", "Set the output file");
348 file_menu->AppendSeparator();
349 file_menu->Append(TEX_VIEW_LATEX, "View &LaTeX File", "View the LaTeX input file");
350 file_menu->Append(TEX_VIEW_OUTPUT, "View Output &File", "View output file");
351 file_menu->Append(TEX_SAVE_FILE, "&Save log file", "Save displayed text into file");
352 file_menu->AppendSeparator();
353 file_menu->Append(TEX_QUIT, "E&xit", "Exit Tex2RTF");
354
355 wxMenu *macro_menu = new wxMenu;
356
357 macro_menu->Append(TEX_LOAD_CUSTOM_MACROS, "&Load Custom Macros", "Load custom LaTeX macro file");
358 macro_menu->Append(TEX_VIEW_CUSTOM_MACROS, "View &Custom Macros", "View custom LaTeX macros");
359
360 wxMenu *mode_menu = new wxMenu;
361
362 mode_menu->Append(TEX_MODE_RTF, "Output linear &RTF", "Wordprocessor-compatible RTF");
363 mode_menu->Append(TEX_MODE_WINHELP, "Output &WinHelp RTF", "WinHelp-compatible RTF");
364 mode_menu->Append(TEX_MODE_HTML, "Output &HTML", "HTML World Wide Web hypertext file");
365 mode_menu->Append(TEX_MODE_XLP, "Output &XLP", "wxHelp hypertext help file");
366
fad535ee
GT
367 wxMenu *options_menu = new wxMenu;
368
369 options_menu->Append(TEX_OPTIONS_CURELY_BRACE, "Curley brace matching", "Checks for mismatched curley braces",TRUE);
370 options_menu->Append(TEX_OPTIONS_SYNTAX_CHECKING, "Syntax checking", "Syntax checking for common errors",TRUE);
371
372 options_menu->Check(TEX_OPTIONS_CURELY_BRACE, checkCurleyBraces);
373 options_menu->Check(TEX_OPTIONS_SYNTAX_CHECKING, checkSyntax);
374
9a29912f
JS
375 wxMenu *help_menu = new wxMenu;
376
377 help_menu->Append(TEX_HELP, "&Help", "Tex2RTF Contents Page");
378 help_menu->Append(TEX_ABOUT, "&About Tex2RTF", "About Tex2RTF");
379
380 menuBar = new wxMenuBar;
381 menuBar->Append(file_menu, "&File");
382 menuBar->Append(macro_menu, "&Macros");
383 menuBar->Append(mode_menu, "&Conversion Mode");
fad535ee 384 menuBar->Append(options_menu, "&Options");
9a29912f
JS
385 menuBar->Append(help_menu, "&Help");
386
387 frame->SetMenuBar(menuBar);
388 frame->textWindow = new wxTextCtrl(frame, -1, "", wxPoint(-1, -1), wxSize(-1, -1), wxTE_READONLY|wxTE_MULTILINE);
389
390 (*frame->textWindow) << "Welcome to Julian Smart's LaTeX to RTF converter.\n";
ffaaaacb 391// ShowOptions();
9a29912f 392
ffaaaacb 393#if wxUSE_HELP
9a29912f
JS
394 HelpInstance = new wxHelpController();
395 HelpInstance->Initialize("tex2rtf");
ffaaaacb 396#endif // wxUSE_HELP
9a29912f
JS
397
398 /*
399 * Read macro/initialisation file
400 *
401 */
ffaaaacb 402
9a29912f
JS
403 wxString path;
404 if ((path = TexPathList.FindValidPath(MacroFile)) != "")
405 ReadCustomMacros((char*) (const char*) path);
406
407 strcpy(buf, "In ");
408
409 if (winHelp && (convertMode == TEX_RTF))
410 strcat(buf, "WinHelp RTF");
411 else if (!winHelp && (convertMode == TEX_RTF))
412 strcat(buf, "linear RTF");
413 else if (convertMode == TEX_HTML) strcat(buf, "HTML");
414 else if (convertMode == TEX_XLP) strcat(buf, "XLP");
415 strcat(buf, " mode.");
416 frame->SetStatusText(buf, 1);
ffaaaacb 417
9a29912f
JS
418 frame->Show(TRUE);
419 return TRUE;
420 }
421 else
422#endif // NO_GUI
423 {
424 /*
425 * Read macro/initialisation file
426 *
427 */
ffaaaacb 428
9a29912f
JS
429 wxString path;
430 if ((path = TexPathList.FindValidPath(MacroFile)) != "")
431 ReadCustomMacros((char*) (const char*) path);
432
433 Go();
3924dd22
GT
434 if (runTwice)
435 {
436 Go();
437 }
9a29912f
JS
438#ifdef NO_GUI
439 return 0;
440#else
441 return NULL;
442#endif
443 }
444
445#ifndef NO_GUI
446 // Return the main frame window
447 return TRUE;
448#else
c4c794e1 449 delete[] wxBuffer;
9a29912f
JS
450 return FALSE;
451#endif
452}
453
c4c794e1 454#ifndef NO_GUI
9a29912f
JS
455int MyApp::OnExit()
456{
457 wxNode *node = CustomMacroList.First();
458 while (node)
459 {
460 CustomMacro *macro = (CustomMacro *)node->Data();
461 delete macro;
462 delete node;
463 node = CustomMacroList.First();
464 }
465 MacroDefs.BeginFind();
466 node = MacroDefs.Next();
467 while (node)
468 {
469 TexMacroDef* def = (TexMacroDef*) node->Data();
470 delete def;
471 node = MacroDefs.Next();
472 }
473 MacroDefs.Clear();
474#ifdef __WXMSW__
475 delete TheTex2RTFServer;
23016fdd 476 wxDDECleanUp();
9a29912f 477#endif
ffaaaacb
VZ
478
479#if wxUSE_HELP
9a29912f 480 delete HelpInstance;
ffaaaacb 481#endif // wxUSE_HELP
9a29912f 482
71599f0a
GT
483 if (BigBuffer)
484 {
485 delete BigBuffer;
486 BigBuffer = NULL;
487 }
488 if (currentArgData)
489 {
490 delete currentArgData;
491 currentArgData = NULL;
492 }
493 if (TexFileRoot)
494 {
495 delete TexFileRoot;
496 TexFileRoot = NULL;
497 }
498 if (TexBibName)
499 {
500 delete TexBibName;
501 TexBibName = NULL;
502 }
503 if (TexTmpBibName)
504 {
505 delete TexTmpBibName;
506 TexTmpBibName = NULL;
507 }
508 if (FileRoot)
509 {
510 delete FileRoot;
511 FileRoot = NULL;
512 }
513 if (ContentsName)
514 {
515 delete ContentsName;
516 ContentsName = NULL;
517 }
518 if (TmpContentsName)
519 {
520 delete TmpContentsName;
521 TmpContentsName = NULL;
522 }
523 if (TmpFrameContentsName)
524 {
525 delete TmpFrameContentsName;
526 TmpFrameContentsName = NULL;
527 }
528 if (WinHelpContentsFileName)
529 {
530 delete WinHelpContentsFileName;
531 WinHelpContentsFileName = NULL;
532 }
ad781c23 533 if (RefFileName)
71599f0a 534 {
ad781c23
GD
535 delete RefFileName;
536 RefFileName = NULL;
71599f0a
GT
537 }
538 if (TopLevel)
539 {
540 delete TopLevel;
541 TopLevel = NULL;
542 }
543 if (MacroFile)
544 {
545 delete MacroFile;
546 MacroFile = NULL;
547 }
548 if (RTFCharset)
549 {
550 delete RTFCharset;
551 RTFCharset = NULL;
552 }
553
3924dd22
GT
554 delete [] PageStyle;
555 delete [] BibliographyStyleString;
556 delete [] DocumentStyleString;
557 delete [] bitmapMethod;
558 delete [] backgroundColourString;
559 delete [] ContentsNameString;
560 delete [] AbstractNameString;
561 delete [] GlossaryNameString;
562 delete [] ReferencesNameString;
563 delete [] FiguresNameString;
564 delete [] TablesNameString;
565 delete [] FigureNameString;
566 delete [] TableNameString;
567 delete [] IndexNameString;
568 delete [] ChapterNameString;
569 delete [] SectionNameString;
570 delete [] SubsectionNameString;
571 delete [] SubsubsectionNameString;
572 delete [] UpNameString;
573 if (winHelpTitle)
574 delete[] winHelpTitle;
575
9a29912f
JS
576 // TODO: this simulates zero-memory leaks!
577 // Otherwise there are just too many...
12a44087 578#ifndef __WXGTK__
fad535ee 579#if (defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING) || wxUSE_DEBUG_CONTEXT
9a29912f 580 wxDebugContext::SetCheckpoint();
fad535ee 581#endif
12a44087 582#endif
9a29912f
JS
583
584 return 0;
585}
c4c794e1 586#endif
9a29912f
JS
587void ShowOptions(void)
588{
589 char buf[100];
590 sprintf(buf, "Tex2RTF version %.2f", versionNo);
591 OnInform(buf);
592 OnInform("Usage: tex2rtf [input] [output] [switches]\n");
593 OnInform("where valid switches are");
610c6ded 594#ifndef NO_GUI
9a29912f 595 OnInform(" -interactive");
610c6ded 596#endif
9a29912f
JS
597 OnInform(" -bufsize <size in K>");
598 OnInform(" -charset <pc | pca | ansi | mac> (default ansi)");
599 OnInform(" -twice");
600 OnInform(" -sync");
8efab359
VZ
601 OnInform(" -checkcurleybraces");
602 OnInform(" -checksyntax");
9a29912f
JS
603 OnInform(" -macros <filename>");
604 OnInform(" -winhelp");
605 OnInform(" -rtf");
606 OnInform(" -html");
607 OnInform(" -xlp\n");
608}
609
610#ifndef NO_GUI
611
612BEGIN_EVENT_TABLE(MyFrame, wxFrame)
613 EVT_CLOSE(MyFrame::OnCloseWindow)
614 EVT_MENU(TEX_QUIT, MyFrame::OnExit)
615 EVT_MENU(TEX_GO, MyFrame::OnGo)
616 EVT_MENU(TEX_SET_INPUT, MyFrame::OnSetInput)
617 EVT_MENU(TEX_SET_OUTPUT, MyFrame::OnSetOutput)
618 EVT_MENU(TEX_SAVE_FILE, MyFrame::OnSaveFile)
619 EVT_MENU(TEX_VIEW_LATEX, MyFrame::OnViewLatex)
620 EVT_MENU(TEX_VIEW_OUTPUT, MyFrame::OnViewOutput)
621 EVT_MENU(TEX_VIEW_CUSTOM_MACROS, MyFrame::OnShowMacros)
622 EVT_MENU(TEX_LOAD_CUSTOM_MACROS, MyFrame::OnLoadMacros)
623 EVT_MENU(TEX_MODE_RTF, MyFrame::OnModeRTF)
624 EVT_MENU(TEX_MODE_WINHELP, MyFrame::OnModeWinHelp)
625 EVT_MENU(TEX_MODE_HTML, MyFrame::OnModeHTML)
626 EVT_MENU(TEX_MODE_XLP, MyFrame::OnModeXLP)
fad535ee
GT
627 EVT_MENU(TEX_OPTIONS_CURELY_BRACE, MyFrame::OnOptionsCurleyBrace)
628 EVT_MENU(TEX_OPTIONS_SYNTAX_CHECKING, MyFrame::OnOptionsSyntaxChecking)
9a29912f
JS
629 EVT_MENU(TEX_HELP, MyFrame::OnHelp)
630 EVT_MENU(TEX_ABOUT, MyFrame::OnAbout)
631END_EVENT_TABLE()
632
633// My frame constructor
634MyFrame::MyFrame(wxFrame *frame, wxWindowID id, const wxString& title, const wxPoint& pos, const wxSize& size):
635 wxFrame(frame, id, title, pos, size)
636{}
637
638void MyFrame::OnCloseWindow(wxCloseEvent& event)
639{
640 if (!stopRunning && !OkToClose)
641 {
642 stopRunning = TRUE;
643 runTwice = FALSE;
644 return;
645 }
646 else if (OkToClose)
647 {
9a29912f
JS
648 this->Destroy();
649 }
650}
651
652void MyFrame::OnExit(wxCommandEvent& event)
653{
71599f0a
GT
654 Close();
655// this->Destroy();
9a29912f
JS
656}
657
658void MyFrame::OnGo(wxCommandEvent& event)
659{
f6bcfd97 660 passNumber = 1;
63ad540d 661 errorCount = 0;
9a29912f
JS
662 menuBar->EnableTop(0, FALSE);
663 menuBar->EnableTop(1, FALSE);
664 menuBar->EnableTop(2, FALSE);
665 menuBar->EnableTop(3, FALSE);
666 textWindow->Clear();
667 Tex2RTFYield(TRUE);
668 Go();
669
04b9c5bb
GT
670 if (stopRunning)
671 {
672 SetStatusText("Build aborted!");
673 wxString errBuf;
674 errBuf.Printf("\nErrors encountered during this pass: %lu\n", errorCount);
675 OnInform((char *)errBuf.c_str());
676 }
677
678
679 if (runTwice && !stopRunning)
9a29912f
JS
680 {
681 Tex2RTFYield(TRUE);
682 Go();
683 }
684 menuBar->EnableTop(0, TRUE);
685 menuBar->EnableTop(1, TRUE);
686 menuBar->EnableTop(2, TRUE);
687 menuBar->EnableTop(3, TRUE);
688}
689
690void MyFrame::OnSetInput(wxCommandEvent& event)
691{
692 ChooseInputFile(TRUE);
693}
694
695void MyFrame::OnSetOutput(wxCommandEvent& event)
696{
697 ChooseOutputFile(TRUE);
698}
699
700void MyFrame::OnSaveFile(wxCommandEvent& event)
701{
702 wxString s = wxFileSelector("Save text to file", "", "", "txt", "*.txt");
703 if (s != "")
704 {
705 textWindow->SaveFile(s);
706 char buf[350];
707 sprintf(buf, "Saved text to %s", (const char*) s);
708 frame->SetStatusText(buf, 0);
709 }
710}
711
712void MyFrame::OnViewOutput(wxCommandEvent& event)
713{
714 ChooseOutputFile();
715 if (OutputFile && wxFileExists(OutputFile))
716 {
717 textWindow->LoadFile(OutputFile);
718 char buf[300];
719 wxString str(wxFileNameFromPath(OutputFile));
720 sprintf(buf, "Tex2RTF [%s]", (const char*) str);
721 frame->SetTitle(buf);
722 }
723}
724
725void MyFrame::OnViewLatex(wxCommandEvent& event)
726{
727 ChooseInputFile();
728 if (InputFile && wxFileExists(InputFile))
729 {
730 textWindow->LoadFile(InputFile);
731 char buf[300];
732 wxString str(wxFileNameFromPath(OutputFile));
733 sprintf(buf, "Tex2RTF [%s]", (const char*) str);
734 frame->SetTitle(buf);
735 }
736}
737
738void MyFrame::OnLoadMacros(wxCommandEvent& event)
739{
740 textWindow->Clear();
741 wxString s = wxFileSelector("Choose custom macro file", wxPathOnly(MacroFile), wxFileNameFromPath(MacroFile), "ini", "*.ini");
742 if (s != "" && wxFileExists(s))
743 {
744 MacroFile = copystring(s);
745 ReadCustomMacros((char*) (const char*) s);
746 ShowCustomMacros();
747 }
748}
749
750void MyFrame::OnShowMacros(wxCommandEvent& event)
751{
752 textWindow->Clear();
753 Tex2RTFYield(TRUE);
754 ShowCustomMacros();
755}
756
757void MyFrame::OnModeRTF(wxCommandEvent& event)
758{
759 convertMode = TEX_RTF;
760 winHelp = FALSE;
761 InputFile = NULL;
762 OutputFile = NULL;
763 SetStatusText("In linear RTF mode.", 1);
764}
765
766void MyFrame::OnModeWinHelp(wxCommandEvent& event)
767{
768 convertMode = TEX_RTF;
769 winHelp = TRUE;
770 InputFile = NULL;
771 OutputFile = NULL;
772 SetStatusText("In WinHelp RTF mode.", 1);
773}
774
775void MyFrame::OnModeHTML(wxCommandEvent& event)
776{
777 convertMode = TEX_HTML;
778 winHelp = FALSE;
779 InputFile = NULL;
780 OutputFile = NULL;
781 SetStatusText("In HTML mode.", 1);
782}
783
784void MyFrame::OnModeXLP(wxCommandEvent& event)
785{
786 convertMode = TEX_XLP;
787 InputFile = NULL;
788 OutputFile = NULL;
789 SetStatusText("In XLP mode.", 1);
790}
791
fad535ee
GT
792void MyFrame::OnOptionsCurleyBrace(wxCommandEvent& event)
793{
794 checkCurleyBraces = !checkCurleyBraces;
795 if (checkCurleyBraces)
796 {
797 SetStatusText("Checking curley braces: YES", 1);
798 }
799 else
800 {
801 SetStatusText("Checking curley braces: NO", 1);
802 }
803}
804
805
806void MyFrame::OnOptionsSyntaxChecking(wxCommandEvent& event)
807{
808 checkSyntax = !checkSyntax;
809 if (checkSyntax)
810 {
811 SetStatusText("Checking syntax: YES", 1);
812 }
813 else
814 {
815 SetStatusText("Checking syntax: NO", 1);
816 }
817}
818
819
9a29912f
JS
820void MyFrame::OnHelp(wxCommandEvent& event)
821{
ffaaaacb 822#if wxUSE_HELP
9a29912f
JS
823 HelpInstance->LoadFile();
824 HelpInstance->DisplayContents();
ffaaaacb 825#endif // wxUSE_HELP
9a29912f
JS
826}
827
828void MyFrame::OnAbout(wxCommandEvent& event)
829{
830 char buf[300];
831#ifdef __WIN32__
832 char *platform = " (32-bit)";
833#else
834#ifdef __WXMSW__
835 char *platform = " (16-bit)";
836#else
837 char *platform = "";
838#endif
839#endif
840 sprintf(buf, "Tex2RTF Version %.2f%s\nLaTeX to RTF, WinHelp, HTML and wxHelp Conversion\n\n(c) Julian Smart 1999", versionNo, platform);
841 wxMessageBox(buf, "About Tex2RTF");
842}
843
844void ChooseInputFile(bool force)
845{
846 if (force || !InputFile)
847 {
848 wxString s = wxFileSelector("Choose LaTeX input file", wxPathOnly(InputFile), wxFileNameFromPath(InputFile), "tex", "*.tex");
849 if (s != "")
850 {
851 // Different file, so clear index entries.
852 ClearKeyWordTable();
853 ResetContentsLevels(0);
854 passNumber = 1;
63ad540d
GT
855 errorCount = 0;
856
9a29912f
JS
857 InputFile = copystring(s);
858 wxString str = wxFileNameFromPath(InputFile);
63ad540d
GT
859 wxString buf;
860 buf.Printf("Tex2RTF [%s]", str.c_str());
861 frame->SetTitle((char *)buf.c_str());
9a29912f
JS
862 OutputFile = NULL;
863 }
864 }
865}
866
867void ChooseOutputFile(bool force)
868{
869 char extensionBuf[10];
870 char wildBuf[10];
871 strcpy(wildBuf, "*.");
aed0ed3c 872 wxString path;
9a29912f
JS
873 if (OutputFile)
874 path = wxPathOnly(OutputFile);
875 else if (InputFile)
876 path = wxPathOnly(InputFile);
ffaaaacb 877
9a29912f
JS
878 switch (convertMode)
879 {
880 case TEX_RTF:
881 {
882 strcpy(extensionBuf, "rtf");
883 strcat(wildBuf, "rtf");
884 break;
885 }
886 case TEX_XLP:
887 {
888 strcpy(extensionBuf, "xlp");
889 strcat(wildBuf, "xlp");
890 break;
891 }
892 case TEX_HTML:
893 {
894#if defined(__WXMSW__) && defined(__WIN16__)
895 strcpy(extensionBuf, "htm");
896 strcat(wildBuf, "htm");
897#else
898 strcpy(extensionBuf, "html");
899 strcat(wildBuf, "html");
900#endif
901 break;
902 }
903 }
904 if (force || !OutputFile)
905 {
906 wxString s = wxFileSelector("Choose output file", path, wxFileNameFromPath(OutputFile),
907 extensionBuf, wildBuf);
908 if (s != "")
909 OutputFile = copystring(s);
910 }
911}
912#endif
913
914bool Go(void)
915{
916#ifndef NO_GUI
917 ChooseInputFile();
918 ChooseOutputFile();
919#endif
920
04b9c5bb 921 if (!InputFile || !OutputFile || stopRunning)
9a29912f
JS
922 return FALSE;
923
924#ifndef NO_GUI
925 if (isInteractive)
926 {
927 char buf[300];
928 wxString str = wxFileNameFromPath(InputFile);
929
930 sprintf(buf, "Tex2RTF [%s]", (const char*) str);
931 frame->SetTitle(buf);
932 }
933
934 wxStartTimer();
935#endif
936
937 // Find extension-less filename
938 strcpy(FileRoot, OutputFile);
939 StripExtension(FileRoot);
940
941 if (truncateFilenames && convertMode == TEX_HTML)
942 {
943 // Truncate to five characters. This ensures that
944 // we can generate DOS filenames such as thing999. But 1000 files
945 // may not be enough, of course...
946 char* sName = wxFileNameFromPath( FileRoot); // this Julian's method is non-destructive reference
947
948 if(sName)
949 if(strlen( sName) > 5)
950 sName[5] = '\0'; // that should do!
951 }
ffaaaacb 952
9a29912f
JS
953 sprintf(ContentsName, "%s.con", FileRoot);
954 sprintf(TmpContentsName, "%s.cn1", FileRoot);
955 sprintf(TmpFrameContentsName, "%s.frc", FileRoot);
956 sprintf(WinHelpContentsFileName, "%s.cnt", FileRoot);
ad781c23 957 sprintf(RefFileName, "%s.ref", FileRoot);
9a29912f
JS
958
959 TexPathList.EnsureFileAccessible(InputFile);
960 if (!bulletFile)
961 {
962 wxString s = TexPathList.FindValidPath("bullet.bmp");
963 if (s != "")
964 {
965 wxString str = wxFileNameFromPath(s);
966 bulletFile = copystring(str);
967 }
968 }
969
ad781c23
GD
970 if (wxFileExists(RefFileName))
971 ReadTexReferences(RefFileName);
ffaaaacb 972
9a29912f
JS
973 bool success = FALSE;
974
975 if (InputFile && OutputFile)
976 {
977 if (!FileExists(InputFile))
978 {
979 OnError("Cannot open input file!");
980 TexCleanUp();
981 return FALSE;
982 }
983#ifndef NO_GUI
984 if (isInteractive)
985 {
63ad540d 986 wxString buf;
fad535ee 987 buf.Printf("Working, pass %d...Click CLOSE to abort", passNumber);
63ad540d 988 frame->SetStatusText((char *)buf.c_str());
9a29912f
JS
989 }
990#endif
991 OkToClose = FALSE;
992 OnInform("Reading LaTeX file...");
993 TexLoadFile(InputFile);
994
04b9c5bb 995 if (stopRunning)
e4941e3d
GT
996 {
997 OkToClose = TRUE;
04b9c5bb 998 return FALSE;
e4941e3d 999 }
04b9c5bb 1000
9a29912f
JS
1001 switch (convertMode)
1002 {
1003 case TEX_RTF:
1004 {
1005 success = RTFGo();
1006 break;
1007 }
1008 case TEX_XLP:
1009 {
1010 success = XLPGo();
1011 break;
1012 }
1013 case TEX_HTML:
1014 {
1015 success = HTMLGo();
1016 break;
1017 }
1018 }
1019 }
1020 if (stopRunning)
1021 {
1022 OnInform("*** Aborted by user.");
1023 success = FALSE;
1024 stopRunning = FALSE;
e4941e3d 1025 OkToClose = TRUE;
9a29912f
JS
1026 }
1027
1028 if (success)
1029 {
ad781c23 1030 WriteTexReferences(RefFileName);
9a29912f
JS
1031 TexCleanUp();
1032 startedSections = FALSE;
1033
63ad540d 1034 wxString buf;
9a29912f
JS
1035#ifndef NO_GUI
1036 long tim = wxGetElapsedTime();
63ad540d
GT
1037 buf.Printf("Finished PASS #%d in %ld seconds.\n", passNumber, (long)(tim/1000.0));
1038 OnInform((char *)buf.c_str());
1039
1040 if (errorCount)
1041 {
1042 buf.Printf("Errors encountered during this pass: %lu\n", errorCount);
1043 OnInform((char *)buf.c_str());
1044 }
1045
9a29912f
JS
1046 if (isInteractive)
1047 {
63ad540d
GT
1048 buf.Printf("Done, %d %s.", passNumber, (passNumber > 1) ? "passes" : "pass");
1049 frame->SetStatusText((char *)buf.c_str());
9a29912f
JS
1050 }
1051#else
63ad540d
GT
1052 buf.Printf("Done, %d %s.", passNumber, (passNumber > 1) ? "passes" : "pass");
1053 OnInform((char *)buf.c_str());
1054 if (errorCount)
1055 {
1056 buf.Printf("Errors encountered during this pass: %lu\n", errorCount);
1057 OnInform((char *)buf.c_str());
1058 }
9a29912f
JS
1059#endif
1060 passNumber ++;
63ad540d 1061 errorCount = 0;
9a29912f
JS
1062 OkToClose = TRUE;
1063 return TRUE;
1064 }
1065
1066 TexCleanUp();
1067 startedSections = FALSE;
1068
8efab359 1069#ifndef NO_GUI
fad535ee 1070 frame->SetStatusText("Aborted by user.");
8efab359 1071#endif // GUI
fad535ee 1072
9a29912f
JS
1073 OnInform("Sorry, unsuccessful.");
1074 OkToClose = TRUE;
1075 return FALSE;
1076}
1077
4538b3f1 1078void OnError(const char *msg)
9a29912f 1079{
63ad540d
GT
1080 errorCount++;
1081
9a29912f 1082#ifdef NO_GUI
219f4a6d
GD
1083 wxSTD cerr << "Error: " << msg << "\n";
1084 wxSTD cerr.flush();
9a29912f 1085#else
3f8e5072 1086 if (isInteractive && frame)
9a29912f
JS
1087 (*frame->textWindow) << "Error: " << msg << "\n";
1088 else
1089#ifdef __UNIX__
1090 {
219f4a6d
GD
1091 wxSTD cerr << "Error: " << msg << "\n";
1092 wxSTD cerr.flush();
9a29912f
JS
1093 }
1094#endif
63ad540d 1095
9a29912f
JS
1096#ifdef __WXMSW__
1097 wxError(msg);
1098#endif
1099 Tex2RTFYield(TRUE);
1100#endif // NO_GUI
1101}
1102
4538b3f1 1103void OnInform(const char *msg)
9a29912f
JS
1104{
1105#ifdef NO_GUI
219f4a6d
GD
1106 wxSTD cout << msg << "\n";
1107 wxSTD cout.flush();
9a29912f 1108#else
3f8e5072 1109 if (isInteractive && frame)
9a29912f 1110 (*frame->textWindow) << msg << "\n";
fad535ee
GT
1111/* This whole block of code is just wrong I think. It would behave
1112 completely wrong under anything other than MSW due to the ELSE
1113 with no statement, and the cout calls would fail under MSW, as
1114 the code in this block is compiled if !NO_GUI This code has been
1115 here since v1.1 of this file too. - gt
9a29912f
JS
1116 else
1117#ifdef __WXMSW__
1118 {
219f4a6d
GD
1119 wxSTD cout << msg << "\n";
1120 wxSTD cout.flush();
9a29912f
JS
1121 }
1122#endif
1123#ifdef __WXMSW__
1124 {}
1125#endif
fad535ee 1126*/
9a29912f
JS
1127 if (isInteractive)
1128 {
1129 Tex2RTFYield(TRUE);
1130 }
1131#endif // NO_GUI
1132}
1133
1134void OnMacro(int macroId, int no_args, bool start)
1135{
1136 switch (convertMode)
1137 {
1138 case TEX_RTF:
1139 {
1140 RTFOnMacro(macroId, no_args, start);
1141 break;
1142 }
1143 case TEX_XLP:
1144 {
1145 XLPOnMacro(macroId, no_args, start);
1146 break;
1147 }
1148 case TEX_HTML:
1149 {
1150 HTMLOnMacro(macroId, no_args, start);
1151 break;
1152 }
1153 }
1154}
1155
1156bool OnArgument(int macroId, int arg_no, bool start)
1157{
1158 switch (convertMode)
1159 {
1160 case TEX_RTF:
1161 {
1162 return RTFOnArgument(macroId, arg_no, start);
1163 break;
1164 }
1165 case TEX_XLP:
1166 {
1167 return XLPOnArgument(macroId, arg_no, start);
1168 break;
1169 }
1170 case TEX_HTML:
1171 {
1172 return HTMLOnArgument(macroId, arg_no, start);
1173 break;
1174 }
1175 }
1176 return TRUE;
1177}
1178
1179/*
1180 * DDE Stuff
1181 */
1182#if defined(__WXMSW__) && !defined(NO_GUI)
1183
1184/*
1185 * Server
1186 */
1187
1188wxConnectionBase *Tex2RTFServer::OnAcceptConnection(const wxString& topic)
1189{
1190 if (topic == "TEX2RTF")
1191 {
1192 if (!ipc_buffer)
1193 ipc_buffer = new char[1000];
ffaaaacb 1194
9a29912f
JS
1195 return new Tex2RTFConnection(ipc_buffer, 4000);
1196 }
1197 else
1198 return NULL;
1199}
1200
1201 /*
1202 * Connection
1203 */
ffaaaacb 1204
9a29912f
JS
1205Tex2RTFConnection::Tex2RTFConnection(char *buf, int size):wxDDEConnection(buf, size)
1206{
1207}
1208
1209Tex2RTFConnection::~Tex2RTFConnection(void)
1210{
1211}
1212
1213bool SplitCommand(char *data, char *firstArg, char *secondArg)
1214{
1215 firstArg[0] = 0;
1216 secondArg[0] = 0;
1217 int i = 0;
1218 int len = strlen(data);
1219 bool stop = FALSE;
1220 // Find first argument (command name)
1221 while (!stop)
1222 {
1223 if (data[i] == ' ' || data[i] == 0)
1224 stop = TRUE;
1225 else
1226 {
1227 firstArg[i] = data[i];
1228 i ++;
1229 }
1230 }
1231 firstArg[i] = 0;
1232 if (data[i] == ' ')
1233 {
1234 // Find second argument
1235 i ++;
1236 int j = 0;
1237 while (data[i] != 0)
1238 {
1239 secondArg[j] = data[i];
1240 i ++;
1241 j ++;
1242 }
1243 secondArg[j] = 0;
1244 }
1245 return TRUE;
1246}
1247
1248bool Tex2RTFConnection::OnExecute(const wxString& topic, char *data, int size, int format)
1249{
1250 strcpy(Tex2RTFLastStatus, "OK");
1251
1252 char firstArg[50];
1253 char secondArg[300];
1254 if (SplitCommand(data, firstArg, secondArg))
1255 {
1256 bool hasArg = (strlen(secondArg) > 0);
1257 if (strcmp(firstArg, "INPUT") == 0 && hasArg)
1258 {
1259 if (InputFile) delete[] InputFile;
1260 InputFile = copystring(secondArg);
1261 if (frame)
1262 {
1263 char buf[100];
1264 wxString str = wxFileNameFromPath(InputFile);
1265 sprintf(buf, "Tex2RTF [%s]", (const char*) str);
1266 frame->SetTitle(buf);
1267 }
1268 }
1269 else if (strcmp(firstArg, "OUTPUT") == 0 && hasArg)
1270 {
1271 if (OutputFile) delete[] OutputFile;
1272 OutputFile = copystring(secondArg);
1273 }
1274 else if (strcmp(firstArg, "GO") == 0)
1275 {
1276 strcpy(Tex2RTFLastStatus, "WORKING");
1277 if (!Go())
1278 strcpy(Tex2RTFLastStatus, "CONVERSION ERROR");
1279 else
1280 strcpy(Tex2RTFLastStatus, "OK");
1281 }
1282 else if (strcmp(firstArg, "EXIT") == 0)
1283 {
e3065973 1284 if (frame) frame->Close();
9a29912f
JS
1285 }
1286 else if (strcmp(firstArg, "MINIMIZE") == 0 || strcmp(firstArg, "ICONIZE") == 0)
1287 {
1288 if (frame)
1289 frame->Iconize(TRUE);
1290 }
1291 else if (strcmp(firstArg, "SHOW") == 0 || strcmp(firstArg, "RESTORE") == 0)
1292 {
1293 if (frame)
1294 {
1295 frame->Iconize(FALSE);
1296 frame->Show(TRUE);
1297 }
1298 }
1299 else
1300 {
1301 // Try for a setting
1302 strcpy(Tex2RTFLastStatus, RegisterSetting(firstArg, secondArg, FALSE));
1303#ifndef NO_GUI
1304 if (frame && strcmp(firstArg, "conversionMode") == 0)
1305 {
1306 char buf[100];
1307 strcpy(buf, "In ");
1308
1309 if (winHelp && (convertMode == TEX_RTF))
1310 strcat(buf, "WinHelp RTF");
1311 else if (!winHelp && (convertMode == TEX_RTF))
1312 strcat(buf, "linear RTF");
1313 else if (convertMode == TEX_HTML) strcat(buf, "HTML");
1314 else if (convertMode == TEX_XLP) strcat(buf, "XLP");
1315 strcat(buf, " mode.");
1316 frame->SetStatusText(buf, 1);
1317 }
1318#endif
1319 }
1320 }
1321 return TRUE;
1322}
1323
1324char *Tex2RTFConnection::OnRequest(const wxString& topic, const wxString& item, int *size, int format)
1325{
1326 return Tex2RTFLastStatus;
1327}
1328
1329#endif
1330
c4c794e1 1331#ifndef NO_GUI
17867d61 1332#ifndef __WXGTK__
dd107c50 1333//void wxObject::Dump(wxSTD ostream& str)
7cf496bf
RS
1334//{
1335// if (GetClassInfo() && GetClassInfo()->GetClassName())
1336// str << GetClassInfo()->GetClassName();
1337// else
1338// str << "unknown object class";
1339//}
1340#endif
17867d61 1341#endif