/* file misc.c * Main routine and initialization for the application */ /* XTrkCad - Model Railroad CAD * Copyright (C) 2005 Dave Bullis * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ #include #include #ifndef WINDOWS #include #include #endif #ifdef HAVE_MALLOC_H #include #endif #include #include #include #include #ifdef WINDOWS #include #include #include "getopt.h" #define R_OK (02) #define access _access #if _MSC_VER >1300 #define strdup _strdup #endif #else #include #endif #include #include #include #include "cjoin.h" #include "common.h" #include "compound.h" #include "cselect.h" #include "cundo.h" #include "custom.h" #include "draw.h" #include "fileio.h" #include "i18n.h" #include "layout.h" #include "messages.h" #include "misc.h" #include "param.h" #include "include/paramfilelist.h" #include "paths.h" #include "smalldlg.h" #include "track.h" #include "utility.h" #define DEFAULT_SCALE ("N") char *userLocale = NULL; extern wBalloonHelp_t balloonHelp[]; static wMenuToggle_p mapShowMI; static wMenuToggle_p magnetsMI; #ifdef DEBUG #define CHECK_BALLOONHELP /*#define CHECK_UNUSED_BALLOONHELP*/ #endif #ifdef CHECK_UNUSED_BALLOONHELP static void ShowUnusedBalloonHelp(void); #endif void DoCarDlg(void); /**************************************************************************** * EXPORTED VARIABLES * */ EXPORT int foobar = 0; EXPORT int log_error; static int log_command; EXPORT wWin_p mainW; EXPORT wIndex_t changed = 0; EXPORT char message[STR_HUGE_SIZE]; static char message2[STR_LONG_SIZE]; EXPORT REGION_T curRegion = 0; EXPORT long paramVersion = -1; EXPORT coOrd zero = { 0.0, 0.0 }; EXPORT wBool_t extraButtons = FALSE; EXPORT long onStartup; /**< controls behaviour after startup: load last layout if zero, else start with blank canvas */ EXPORT wButton_p undoB; EXPORT wButton_p redoB; EXPORT wButton_p zoomUpB; EXPORT wButton_p zoomDownB; wButton_p mapShowB; wButton_p magnetsB; wButton_p backgroundB; EXPORT wIndex_t checkPtMark = 0; EXPORT wMenu_p demoM; EXPORT wMenu_p popup1M, popup2M; EXPORT wMenu_p popup1aM, popup2aM; EXPORT wMenu_p popup1mM, popup2mM; static wIndex_t curCommand = 0; EXPORT void * commandContext; EXPORT wIndex_t cmdGroup; EXPORT wIndex_t joinCmdInx; EXPORT wIndex_t modifyCmdInx; EXPORT long rightClickMode = 0; EXPORT long selectMode = 0; EXPORT long selectZero = 1; EXPORT DIST_T easementVal = 0.0; EXPORT DIST_T easeR = 0.0; EXPORT DIST_T easeL = 0.0; EXPORT coOrd cmdMenuPos; EXPORT wPos_t DlgSepLeft = 12; EXPORT wPos_t DlgSepMid = 18; EXPORT wPos_t DlgSepRight = 12; EXPORT wPos_t DlgSepTop = 12; EXPORT wPos_t DlgSepBottom = 12; EXPORT wPos_t DlgSepNarrow = 6; EXPORT wPos_t DlgSepWide = 12; EXPORT wPos_t DlgSepFrmLeft = 4; EXPORT wPos_t DlgSepFrmRight = 4; EXPORT wPos_t DlgSepFrmTop = 4; EXPORT wPos_t DlgSepFrmBottom = 4; static int verbose = 0; static wMenuList_p winList_mi; static BOOL_T inMainW = TRUE; static long stickySet = 0; static long stickyCnt = 0; static char * stickyLabels[33]; #define TOOLBARSET_INIT (0xFFFF) EXPORT long toolbarSet = TOOLBARSET_INIT; EXPORT wPos_t toolbarHeight = 0; static wPos_t toolbarWidth = 0; static wMenuList_p messageList_ml; static BOOL_T messageListEmpty = TRUE; #define MESSAGE_LIST_EMPTY N_("No Messages") #define NUM_FILELIST (5) extern long curTurnoutEp; static wIndex_t printCmdInx; static wIndex_t gridCmdInx; static paramData_t menuPLs[101] = { { PD_LONG, &toolbarSet, "toolbarset" }, { PD_LONG, &curTurnoutEp, "cur-turnout-ep" } }; static paramGroup_t menuPG = { "misc", PGO_RECORD, menuPLs, 2 }; extern wBool_t wDrawDoTempDraw; /**************************************************************************** * * LOCAL UTILITIES * */ EXPORT long totalMallocs = 0; EXPORT long totalMalloced = 0; EXPORT long totalRealloced = 0; EXPORT long totalReallocs = 0; EXPORT long totalFreeed = 0; EXPORT long totalFrees = 0; static unsigned long guard0 = 0xDEADBEEF; static unsigned long guard1 = 0xAF00BA8A; static int log_malloc; EXPORT void * MyMalloc(long size) { void * p; totalMallocs++; totalMalloced += size; #if defined(WINDOWS) && ! defined(WIN32) if ( size > 65500L ) { AbortProg( "mallocing > 65500 bytes" ); } #endif p = malloc((size_t) size + sizeof(size_t) + 2 * sizeof(unsigned long)); if (p == NULL) AbortProg("No memory"); LOG1(log_malloc, ( "Malloc(%ld) = %lx (%lx-%lx)\n", size, (long)((char*)p+sizeof (size_t) + sizeof (unsigned long)), (long)p, (long)((char*)p+size+sizeof (size_t) + 2 * sizeof(unsigned long)) )); *(size_t*) p = (size_t) size; p = (char*) p + sizeof(size_t); *(unsigned long*) p = guard0; p = (char*) p + sizeof(unsigned long); *(unsigned long*) ((char*) p + size) = guard1; memset(p, 0, (size_t )size); return p; } EXPORT void * MyRealloc(void * old, long size) { size_t oldSize; void * new; if (old == NULL) return MyMalloc(size); totalReallocs++; totalRealloced += size; #if defined(WINDOWS) && ! defined(WIN32) if ( size > 65500L ) { AbortProg( "reallocing > 65500 bytes" ); } #endif if (*(unsigned long*) ((char*) old - sizeof(unsigned long)) != guard0) { AbortProg("Guard0 is hosed"); } oldSize = *(size_t*) ((char*) old - sizeof(unsigned long) - sizeof(size_t)); if (*(unsigned long*) ((char*) old + oldSize) != guard1) { AbortProg("Guard1 is hosed"); } LOG1(log_malloc, ("Realloc(%lx,%ld) was %d\n", (long)old, size, oldSize )) if ((long) oldSize == size) { return old; } if (size == 0) { free((char*) old - sizeof *(long*) 0 - sizeof *(size_t*) 0); return NULL; } new = MyMalloc(size); if (new == NULL && size) AbortProg("No memory"); memcpy(new, old, min((size_t )size, oldSize)); MyFree(old); return new; } EXPORT void MyFree(void * ptr) { size_t oldSize; totalFrees++; if (ptr) { if (*(unsigned long*) ((char*) ptr - sizeof(unsigned long)) != guard0) { AbortProg("Guard0 is hosed"); } oldSize = *(size_t*) ((char*) ptr - sizeof(unsigned long) - sizeof(size_t)); if (*(unsigned long*) ((char*) ptr + oldSize) != guard1) { AbortProg("Guard1 is hosed"); } LOG1(log_malloc, ("Free %d at %lx (%lx-%lx)\n", oldSize, (long)ptr, (long)((char*)ptr-sizeof *(size_t*)0-sizeof *(long*)0), (long)((char*)ptr+oldSize+sizeof *(long*)0))) totalFreeed += oldSize; free((char*) ptr - sizeof *(long*) 0 - sizeof *(size_t*) 0); } } EXPORT void * memdup(void * src, size_t size) { void * p; p = MyMalloc(size); if (p == NULL) AbortProg("No memory"); memcpy(p, src, size); return p; } EXPORT char * MyStrdup(const char * str) { char * ret; ret = (char*) MyMalloc(strlen(str) + 1); strcpy(ret, str); return ret; } /* * Convert Text into the equivalent form that can be written to a file or put in a text box by adding escape characters * * The following special characters are produced - * \n for LineFeed 0x0A * \t for Tab 0x09 * "" for " This is so that a CSV conformant type program can interpret the file output * */ EXPORT char * ConvertToEscapedText(const char * text) { int text_i = 0; int add = 0; //extra chars for escape while (text[text_i]) { switch (text[text_i]) { case '\n': add++; break; case '\t': add++; break; case '\\': add++; break; case '\"': add++; break; } text_i++; } unsigned cnt = strlen(text) + 1 + add; #ifdef WINDOWS cnt *= 2; #endif char * cout = MyMalloc(cnt); int cout_i = 0; text_i = 0; while (text[text_i]) { char c = text[text_i]; switch (c) { case '\n': cout[cout_i] = '\\'; cout_i++; cout[cout_i] = 'n'; cout_i++; break; // Line Feed case '\t': cout[cout_i] = '\\'; cout_i++; cout[cout_i] = 't'; cout_i++; break; // Tab case '\\': cout[cout_i] = '\\'; cout_i++; cout[cout_i] = '\\'; cout_i++; break; // BackSlash case '\"': cout[cout_i] = '\"'; cout_i++; cout[cout_i] = '\"'; cout_i++; break; // Double Quotes default: cout[cout_i] = c; cout_i++; } text_i++; } cout[cout_i] = '\0'; #ifdef WINDOWS wSystemToUTF8(cout, cout, cnt); #endif // WINDOWS return cout; } /* * Convert Text that has embedded escape characters into the equivalent form that can be shown on the screen * * The following special characters are supported - * \n = LineFeed 0x0A * \t = Tab 0x09 * \\ = \ The way to still produce backslash * */ EXPORT char * ConvertFromEscapedText(const char * text) { enum { CHARACTER, ESCAPE } state = CHARACTER; char * cout = MyMalloc(strlen(text) + 1); //always equal to or shorter than int text_i = 0; int cout_i = 0; int c; while (text[text_i]) { c = text[text_i]; switch (state) { case CHARACTER: if (c == '\\') { state = ESCAPE; } else { cout[cout_i] = c; cout_i++; } break; case ESCAPE: switch (c) { case '\\': cout[cout_i] = '\\'; cout_i++; break; // "\\" = "\" case 'n': cout[cout_i] = '\n'; cout_i++; break; // LF case 't': cout[cout_i] = '\t'; cout_i++; break; // TAB } state = CHARACTER; break; } text_i++; } cout[cout_i] = '\0'; return cout; } EXPORT void AbortProg(char * msg, ...) { static BOOL_T abort2 = FALSE; int rc; va_list ap; va_start(ap, msg); vsprintf(message, msg, ap); va_end(ap); if (abort2) { wNoticeEx( NT_ERROR, message, _("ABORT"), NULL); } else { strcat(message, _("\nDo you want to save your layout?")); rc = wNoticeEx( NT_ERROR, message, _("Ok"), _("ABORT")); if (rc) { DoSaveAs((doSaveCallBack_p) abort); } else { abort(); } } } EXPORT char * Strcpytrimed(char * dst, char * src, BOOL_T double_quotes) { char * cp; while (*src && isspace((unsigned char) *src)) src++; if (!*src) return dst; cp = src + strlen(src) - 1; while (cp > src && isspace((unsigned char) *cp)) cp--; while (src <= cp) { if (*src == '"' && double_quotes) *dst++ = '"'; *dst++ = *src++; } *dst = '\0'; return dst; } static char * directory; #ifdef WINDOWS #define F_OK (0) #endif EXPORT wBool_t CheckHelpTopicExists(const char * topic) { char * htmlFile; // Check the file exits in the distro if (!directory) directory = malloc(BUFSIZ); if (directory == NULL) return 0; sprintf(directory, "%s/html/", wGetAppLibDir()); htmlFile = malloc(strlen(directory)+strlen(topic) + 6); sprintf(htmlFile, "%s%s.html", directory, topic); if( access( htmlFile, F_OK ) == -1 ) { printf("Missing help topic %s\n",topic); free(htmlFile); return 0; } free(htmlFile); return 1; } EXPORT char * BuildTrimedTitle(char * cp, char * sep, char * mfg, char * desc, char * partno) { cp = Strcpytrimed(cp, mfg, FALSE); strcpy(cp, sep); cp += strlen(cp); cp = Strcpytrimed(cp, desc, FALSE); strcpy(cp, sep); cp += strlen(cp); cp = Strcpytrimed(cp, partno, FALSE); return cp; } static void ShowMessageHelp(int index, const char * label, void * data) { char msgKey[STR_SIZE], *cp, *msgSrc; msgSrc = (char*) data; if (!msgSrc) return; cp = strchr(msgSrc, '\t'); if (cp == NULL) { sprintf(msgKey, _("No help for %s"), msgSrc); wNoticeEx( NT_INFORMATION, msgKey, _("Ok"), NULL); return; } memcpy(msgKey, msgSrc, cp - msgSrc); msgKey[cp - msgSrc] = 0; wHelp(msgKey); } static char * ParseMessage(char *msgSrc) { char *cp1 = NULL, *cp2 = NULL; static char shortMsg[STR_SIZE]; cp1 = strchr(_(msgSrc), '\t'); if (cp1) { cp2 = strchr(cp1 + 1, '\t'); if (cp2) { cp1++; memcpy(shortMsg, cp1, cp2 - cp1); shortMsg[cp2 - cp1] = 0; cp1 = shortMsg; cp2++; } else { cp1++; cp2 = cp1; } if (messageListEmpty) { wMenuListDelete(messageList_ml, _(MESSAGE_LIST_EMPTY)); messageListEmpty = FALSE; } wMenuListAdd(messageList_ml, 0, cp1, _(msgSrc)); return cp2; } else { return _(msgSrc); } } EXPORT void InfoMessage(char * format, ...) { va_list ap; va_start(ap, format); format = ParseMessage(format); vsprintf(message2, format, ap); va_end(ap); /*InfoSubstituteControl( NULL, NULL );*/ if (inError) return; SetMessage(message2); } EXPORT void ErrorMessage(char * format, ...) { va_list ap; va_start(ap, format); format = ParseMessage(format); vsprintf(message2, format, ap); va_end(ap); InfoSubstituteControls( NULL, NULL); SetMessage(message2); wBeep(); inError = TRUE; } EXPORT int NoticeMessage(char * format, char * yes, char * no, ...) { va_list ap; va_start(ap, no); format = ParseMessage(format); vsprintf(message2, format, ap); va_end(ap); return wNotice(message2, yes, no); } EXPORT int NoticeMessage2(int playbackRC, char * format, char * yes, char * no, ...) { va_list ap; if (inPlayback) return playbackRC; va_start(ap, no); format = ParseMessage(format); vsprintf(message2, format, ap); va_end(ap); return wNoticeEx( NT_INFORMATION, message2, yes, no); } /** * Set the file's changed flag and update the window title. */ void FileIsChanged(void) { changed++; SetWindowTitle(); } /***************************************************************************** * * MAIN BUTTON HANDLERS * */ /** * Confirm a requested operation in case of possible loss of changes. * * \param label2 IN operation to be cancelled, unused at the moment * \param after IN function to be executed on positive confirmation * \return true if proceed, false if cancel operation */ /** TODO: make sensible messages when requesting confirmation */ bool Confirm(char * label2, doSaveCallBack_p after) { int rc = -1; if (changed) { rc = wNotice3(_("Save changes to the layout design before closing?\n\n" "If you don't save now, your unsaved changes will be discarded."), _("&Save"), _("&Cancel"), _("&Don't Save")); } switch (rc) { case -1: /* do not save */ after(); break; case 0: /* cancel operation */ break; case 1: /* save */ LayoutBackGroundInit(FALSE); LayoutBackGroundSave(); DoSave(after); break; } return(rc != 0); } static void ChkLoad(void) { Confirm(_("Load"), DoLoad); } static void ChkExamples( void ) { Confirm(_("examples"), DoExamples); } static void ChkRevert(void) { int rc; if (changed) { rc = wNoticeEx(NT_WARNING, _("Do you want to return to the last saved state?\n\n" "Revert will cause all changes done since last save to be lost."), _("&Revert"), _("&Cancel")); if (rc) { /* load the file */ char *filename = GetLayoutFullPath(); LoadTracks(1, &filename, NULL); } } } static char * fileListPathName; static void AfterFileList(void) { DoFileList(0, NULL, fileListPathName); } static void ChkFileList(int index, const char * label, void * data) { fileListPathName = (char*) data; Confirm(_("Load"), AfterFileList); } /** * Save information about current files and some settings to preferences file. */ EXPORT void SaveState(void) { wPos_t width, height; const char * fileName; void * pathName; char file[6]; int inx; wWinGetSize(mainW, &width, &height); wPrefSetInteger("draw", "mainwidth", width); wPrefSetInteger("draw", "mainheight", height); SaveParamFileList(); ParamUpdatePrefs(); wPrefSetString( "misc", "lastlayout", GetLayoutFullPath()); wPrefSetInteger( "misc", "lastlayoutexample", bExample ); if (fileList_ml) { strcpy(file, "file"); file[5] = 0; for (inx = 0; inx < NUM_FILELIST; inx++) { fileName = wMenuListGet(fileList_ml, inx, &pathName); if (fileName) { file[4] = '0' + inx; sprintf(message, "%s", (char* )pathName); wPrefSetString("filelist", file, message); } } } wPrefFlush(); LogClose(); } /* * Clean up before quitting */ static void DoQuitAfter(void) { changed = 0; SaveState(); CleanupFiles(); } /** * Process shutdown request. This function is called when the user requests * to close the application. Before shutting down confirmation is gotten to * prevent data loss. */ void DoQuit(void) { if (Confirm(_("Quit"), DoQuitAfter)) { #ifdef CHECK_UNUSED_BALLOONHELP ShowUnusedBalloonHelp(); #endif LogClose(); wExit(0); } } static void DoClearAfter(void) { Reset(); ClearTracks(); /* set all layers to their default properties and set current layer to 0 */ DoLayout(NULL); checkPtMark = changed = 0; DoChangeNotification( CHANGE_MAIN|CHANGE_MAP ); bReadOnly = TRUE; EnableCommands(); SetLayoutFullPath(""); SetWindowTitle(); LayoutBackGroundInit(TRUE); } static void DoClear(void) { Confirm(_("Clear"), DoClearAfter); } /** * Toggle visibility state of map window. */ void MapWindowToggleShow(void) { MapWindowShow(!mapVisible); } /** * Set visibility state of map window. * * \param state IN TRUE if visible, FALSE if hidden */ void MapWindowShow(int state) { mapVisible = state; wPrefSetInteger("misc", "mapVisible", mapVisible); wMenuToggleSet(mapShowMI, mapVisible); if (mapVisible) { DoChangeNotification(CHANGE_MAP); } wWinShow(mapW, mapVisible); wButtonSetBusy(mapShowB, (wBool_t) mapVisible); } /** * Set magnets state */ int MagneticSnap(int state) { int oldState = magneticSnap; magneticSnap = state; wPrefSetInteger("misc", "magnets", magneticSnap); wMenuToggleSet(magnetsMI, magneticSnap); wButtonSetBusy(magnetsB, (wBool_t) magneticSnap); return oldState; } /** * Toggle magnets on/off */ void MagneticSnapToggle(void) { MagneticSnap(!magneticSnap); } static void DoShowWindow(int index, const char * name, void * data) { if (data == mapW) { if (mapVisible == FALSE) { MapWindowShow( TRUE); return; } } wWinShow((wWin_p) data, TRUE); } static dynArr_t demoWindows_da; #define demoWindows(N) DYNARR_N( wWin_p, demoWindows_da, N ) EXPORT void wShow(wWin_p win) { int inx; if (inPlayback && win != demoW) { wWinSetBusy(win, TRUE); for (inx = 0; inx < demoWindows_da.cnt; inx++) if ( demoWindows(inx) == win) break; if (inx >= demoWindows_da.cnt) { for (inx = 0; inx < demoWindows_da.cnt; inx++) if ( demoWindows(inx) == NULL) break; if (inx >= demoWindows_da.cnt) { DYNARR_APPEND(wWin_p, demoWindows_da, 10); inx = demoWindows_da.cnt - 1; } demoWindows(inx) = win; } } if (win != mainW) wMenuListAdd(winList_mi, -1, wWinGetTitle(win), win); wWinShow(win, TRUE); } EXPORT void wHide(wWin_p win) { int inx; wWinShow(win, FALSE); wWinSetBusy(win, FALSE); if (inMainW && win == aboutW) return; wMenuListDelete(winList_mi, wWinGetTitle(win)); if (inPlayback) for (inx = 0; inx < demoWindows_da.cnt; inx++) if ( demoWindows(inx) == win) demoWindows(inx) = NULL; } EXPORT void CloseDemoWindows(void) { int inx; for (inx = 0; inx < demoWindows_da.cnt; inx++) if ( demoWindows(inx) != NULL) wHide(demoWindows(inx)); demoWindows_da.cnt = 0; } EXPORT void DefaultProc(wWin_p win, winProcEvent e, void * data) { switch (e) { case wClose_e: wMenuListDelete(winList_mi, wWinGetTitle(win)); if (data != NULL) ConfirmReset( FALSE); wWinDoCancel(win); break; default: break; } } static void NextWindow(void) { } EXPORT void SelectFont(void) { wSelectFont(_("XTrackCAD Font")); } /***************************************************************************** * * COMMAND * */ #define COMMAND_MAX (170) #define BUTTON_MAX (170) #define NUM_CMDMENUS (4) static struct { wControl_p control; wBool_t enabled; wPos_t x, y; long options; int group; wIndex_t cmdInx; } buttonList[BUTTON_MAX]; static int buttonCnt = 0; static struct { procCommand_t cmdProc; char * helpKey; wIndex_t buttInx; char * labelStr; wIcon_p icon; int reqLevel; wBool_t enabled; long options; long stickyMask; long acclKey; wMenuPush_p menu[NUM_CMDMENUS]; void * context; } commandList[COMMAND_MAX]; static int commandCnt = 0; #ifdef CHECK_UNUSED_BALLOONHELP int * balloonHelpCnts; #endif EXPORT const char * GetBalloonHelpStr(char * helpKey) { wBalloonHelp_t * bh; #ifdef CHECK_UNUSED_BALLOONHELP if ( balloonHelpCnts == NULL ) { for ( bh=balloonHelp; bh->name; bh++ ); balloonHelpCnts = (int*)malloc( (sizeof *(int*)0) * (bh-balloonHelp) ); memset( balloonHelpCnts, 0, (sizeof *(int*)0) * (bh-balloonHelp) ); } #endif for (bh = balloonHelp; bh->name; bh++) { if (strcmp(bh->name, helpKey) == 0) { #ifdef CHECK_UNUSED_BALLOONHELP balloonHelpCnts[(bh-balloonHelp)]++; #endif return _(bh->value); } } #ifdef CHECK_BALLOONHELP fprintf( stderr, _("No balloon help for %s\n"), helpKey ); #endif return _("No Help"); } #ifdef CHECK_UNUSED_BALLOONHELP static void ShowUnusedBalloonHelp( void ) { int cnt; for ( cnt=0; balloonHelp[cnt].name; cnt++ ) if ( balloonHelpCnts[cnt] == 0 ) fprintf( stderr, "unused BH %s\n", balloonHelp[cnt].name ); } #endif EXPORT const char* GetCurCommandName() { return commandList[curCommand].helpKey; } EXPORT void EnableCommands(void) { int inx, minx; wBool_t enable; LOG(log_command, 5, ( "COMMAND enable S%d M%d\n", selectedTrackCount, programMode )) for (inx = 0; inx < commandCnt; inx++) { if (commandList[inx].buttInx) { if ((commandList[inx].options & IC_SELECTED) && selectedTrackCount <= 0) enable = FALSE; else if ((programMode == MODE_TRAIN && (commandList[inx].options & (IC_MODETRAIN_TOO | IC_MODETRAIN_ONLY)) == 0) || (programMode != MODE_TRAIN && (commandList[inx].options & IC_MODETRAIN_ONLY) != 0)) enable = FALSE; else enable = TRUE; if (commandList[inx].enabled != enable) { if (commandList[inx].buttInx >= 0) wControlActive(buttonList[commandList[inx].buttInx].control, enable); for (minx = 0; minx < NUM_CMDMENUS; minx++) if (commandList[inx].menu[minx]) wMenuPushEnable(commandList[inx].menu[minx], enable); commandList[inx].enabled = enable; } } } for (inx = 0; inx < menuPG.paramCnt; inx++) { if (menuPLs[inx].control == NULL) continue; if ((menuPLs[inx].option & IC_SELECTED) && selectedTrackCount <= 0) enable = FALSE; else if ((programMode == MODE_TRAIN && (menuPLs[inx].option & (IC_MODETRAIN_TOO | IC_MODETRAIN_ONLY)) == 0) || (programMode != MODE_TRAIN && (menuPLs[inx].option & IC_MODETRAIN_ONLY) != 0)) enable = FALSE; else enable = TRUE; wMenuPushEnable((wMenuPush_p) menuPLs[inx].control, enable); } for (inx = 0; inx < buttonCnt; inx++) { if (buttonList[inx].cmdInx < 0 && (buttonList[inx].options & IC_SELECTED)) wControlActive(buttonList[inx].control, selectedTrackCount > 0); } } EXPORT wIndex_t GetCurrentCommand() { return curCommand; } static wIndex_t autosave_count = 0; EXPORT void Reset(void) { if (recordF) { fprintf(recordF, "RESET\n"); fflush(recordF); } LOG(log_command, 2, ( "COMMAND CANCEL %s\n", commandList[curCommand].helpKey )) commandList[curCommand].cmdProc( C_CANCEL, zero); if (commandList[curCommand].buttInx >= 0) wButtonSetBusy( (wButton_p) buttonList[commandList[curCommand].buttInx].control, FALSE); curCommand = (preSelect ? selectCmdInx : describeCmdInx); wSetCursor(mainD.d, preSelect ? defaultCursor : wCursorQuestion); commandContext = commandList[curCommand].context; if (commandList[curCommand].buttInx >= 0) wButtonSetBusy( (wButton_p) buttonList[commandList[curCommand].buttInx].control, TRUE); tempSegs_da.cnt = 0; if (checkPtInterval > 0 && changed >= checkPtMark + (wIndex_t) checkPtInterval && !inPlayback) { DoCheckPoint(); checkPtMark = changed; autosave_count++; if ((autosaveChkPoints>0) && (autosave_count>=autosaveChkPoints)) { DoSave(NULL); InfoMessage(_("File AutoSaved")); autosave_count = 0; } } ClrAllTrkBits( TB_UNDRAWN ); DoRedraw(); // Reset EnableCommands(); ResetMouseState(); LOG(log_command, 1, ( "COMMAND RESET %s\n", commandList[curCommand].helpKey )) (void) commandList[curCommand].cmdProc( C_START, zero); } static BOOL_T CheckClick(wAction_t *action, coOrd *pos, BOOL_T checkLeft, BOOL_T checkRight) { static long time0; static coOrd pos0; long time1; long timeDelta; DIST_T distDelta; switch (*action) { case C_LDOUBLE: if (!checkLeft) return TRUE; time0 = 0; break; case C_DOWN: if (!checkLeft) return TRUE; time0 = wGetTimer() - adjTimer; pos0 = *pos; return FALSE; case C_MOVE: if (!checkLeft) return TRUE; if (time0 != 0) { time1 = wGetTimer() - adjTimer; timeDelta = time1 - time0; distDelta = FindDistance(*pos, pos0); if (timeDelta > dragTimeout || distDelta > dragDistance) { time0 = 0; *pos = pos0; *action = C_DOWN; } else { return FALSE; } } break; case C_UP: if (!checkLeft) return TRUE; if (time0 != 0) { time1 = wGetTimer() - adjTimer; timeDelta = time1 - time0; distDelta = FindDistance(*pos, pos0); time0 = 0; *action = C_LCLICK; } break; case C_RDOWN: if (!checkRight) return TRUE; time0 = wGetTimer() - adjTimer; pos0 = *pos; return FALSE; case C_RMOVE: if (!checkRight) return TRUE; if (time0 != 0) { time1 = wGetTimer() - adjTimer; timeDelta = time1 - time0; distDelta = FindDistance(*pos, pos0); if (timeDelta > dragTimeout || distDelta > dragDistance) { time0 = 0; *pos = pos0; *action = C_RDOWN; } else { return FALSE; } } break; case C_RUP: if (!checkRight) return TRUE; if (time0 != 0) { time0 = 0; *action = C_RCLICK; } break; } return TRUE; } EXPORT wBool_t DoCurCommand(wAction_t action, coOrd pos) { wAction_t rc; int mode; wBool_t bExit = FALSE; if (action == wActionMove) { if ((commandList[curCommand].options & IC_WANT_MOVE) == 0) { bExit = TRUE; } } else if ((action&0xFF) == wActionModKey) { if ((commandList[curCommand].options & IC_WANT_MODKEYS) == 0) { bExit = TRUE; } } else if (!CheckClick(&action, &pos, (int) (commandList[curCommand].options & IC_LCLICK), TRUE)) { bExit = TRUE; } else if (action == C_RCLICK && (commandList[curCommand].options & IC_RCLICK) == 0) { if (!inPlayback) { mode = MyGetKeyState(); if ((mode & (~WKEY_SHIFT)) != 0) { wBeep(); bExit = TRUE; } else if (((mode & WKEY_SHIFT) == 0) == (rightClickMode == 0)) { if (selectedTrackCount > 0) { if (commandList[curCommand].options & IC_CMDMENU) { } wMenuPopupShow(popup2M); } else { wMenuPopupShow(popup1M); } bExit = TRUE; } else if ((commandList[curCommand].options & IC_CMDMENU)) { cmdMenuPos = pos; action = C_CMDMENU; } else { wBeep(); bExit = TRUE; } } else { bExit = TRUE; } } if ( bExit ) { TempRedraw(); // DoCurCommand: precommand return C_CONTINUE; } LOG(log_command, 2, ( "COMMAND MOUSE %s %d @ %0.3f %0.3f\n", commandList[curCommand].helpKey, (int)action, pos.x, pos.y )) rc = commandList[curCommand].cmdProc(action, pos); LOG(log_command, 4, ( " COMMAND returns %d\n", rc )) switch ( action & 0xFF ) { case wActionMove: case wActionModKey: case C_DOWN: case C_MOVE: case C_UP: case C_RDOWN: case C_RMOVE: case C_RUP: case C_LCLICK: case C_RCLICK: case C_TEXT: case C_OK: if (rc== C_TERMINATE) MainRedraw(); else TempRedraw(); // DoCurCommand: postcommand break; default: break; } if ((rc == C_TERMINATE || rc == C_INFO) && (commandList[curCommand].options & IC_STICKY) && (commandList[curCommand].stickyMask & stickySet)) { tempSegs_da.cnt = 0; UpdateAllElevations(); if (commandList[curCommand].options & IC_NORESTART) { return C_CONTINUE; } LOG(log_command, 1, ( "COMMAND START %s\n", commandList[curCommand].helpKey )) rc = commandList[curCommand].cmdProc( C_START, pos); LOG(log_command, 4, ( " COMMAND returns %d\n", rc )) switch (rc) { case C_CONTINUE: break; case C_ERROR: Reset(); #ifdef VERBOSE lprintf( "Start returns Error"); #endif break; case C_TERMINATE: InfoMessage(""); case C_INFO: Reset(); break; } } return rc; } EXPORT void ConfirmReset(BOOL_T retry) { wAction_t rc; if (curCommand != describeCmdInx && curCommand != selectCmdInx) { LOG(log_command, 3, ( "COMMAND CONFIRM %s\n", commandList[curCommand].helpKey )) rc = commandList[curCommand].cmdProc( C_CONFIRM, zero); LOG(log_command, 4, ( " COMMAND returns %d\n", rc )) if (rc == C_ERROR) { if (retry) rc = wNotice3( _( "Cancelling the current command will undo the changes\n" "you are currently making. Do you want to update?"), _("Yes"), _("No"), _("Cancel")); else rc = wNoticeEx( NT_WARNING, _( "Cancelling the current command will undo the changes\n" "you are currently making. Do you want to update?"), _("Yes"), _("No")); if (rc == 1) { LOG(log_command, 3, ( "COMMAND OK %s\n", commandList[curCommand].helpKey )) commandList[curCommand].cmdProc( C_OK, zero); return; } else if (rc == -1) { return; } } else if (rc == C_TERMINATE) { return; } } if (retry) { /* because user pressed esc */ SetAllTrackSelect( FALSE); } Reset(); LOG(log_command, 1, ( "COMMAND RESET %s\n", commandList[curCommand].helpKey )) commandList[curCommand].cmdProc( C_START, zero); } EXPORT BOOL_T IsCurCommandSticky(void) { if ((commandList[curCommand].options & IC_STICKY) != 0 && (commandList[curCommand].stickyMask & stickySet) != 0) return TRUE; return FALSE; } EXPORT void ResetIfNotSticky(void) { if ((commandList[curCommand].options & IC_STICKY) == 0 || (commandList[curCommand].stickyMask & stickySet) == 0) Reset(); } EXPORT void DoCommandB(void * data) { wIndex_t inx = (wIndex_t) (long) data; STATUS_T rc; static coOrd pos = { 0, 0 }; static int inDoCommandB = FALSE; wIndex_t buttInx; if (inDoCommandB) return; inDoCommandB = TRUE; if (inx < 0 || inx >= commandCnt) { ASSERT(FALSE); inDoCommandB = FALSE; return; } if ((!inPlayback) && (!commandList[inx].enabled)) { ErrorMessage(MSG_COMMAND_DISABLED); inx = describeCmdInx; } InfoMessage(""); if (curCommand != selectCmdInx) { LOG(log_command, 3, ( "COMMAND FINISH %s\n", commandList[curCommand].helpKey )) rc = commandList[curCommand].cmdProc( C_FINISH, zero); LOG(log_command, 3, ( "COMMAND CONFIRM %s\n", commandList[curCommand].helpKey )) rc = commandList[curCommand].cmdProc( C_CONFIRM, zero); LOG(log_command, 4, ( " COMMAND returns %d\n", rc )) if (rc == C_ERROR) { rc = wNotice3( _("Cancelling the current command will undo the changes\n" "you are currently making. Do you want to update?"), _("Yes"), _("No"), _("Cancel")); if (rc == 1) commandList[curCommand].cmdProc( C_OK, zero); else if (rc == -1) { inDoCommandB = FALSE; return; } } LOG(log_command, 3, ( "COMMAND CANCEL %s\n", commandList[curCommand].helpKey )) commandList[curCommand].cmdProc( C_CANCEL, pos); tempSegs_da.cnt = 0; } if (commandList[curCommand].buttInx >= 0) wButtonSetBusy( (wButton_p) buttonList[commandList[curCommand].buttInx].control, FALSE); if (recordF) { fprintf(recordF, "COMMAND %s\n", commandList[inx].helpKey + 3); fflush(recordF); } curCommand = inx; commandContext = commandList[curCommand].context; if ((buttInx = commandList[curCommand].buttInx) >= 0) { if (buttonList[buttInx].cmdInx != curCommand) { wButtonSetLabel((wButton_p) buttonList[buttInx].control, (char*) commandList[curCommand].icon); wControlSetHelp(buttonList[buttInx].control, GetBalloonHelpStr(commandList[curCommand].helpKey)); wControlSetContext(buttonList[buttInx].control, (void*) (intptr_t) curCommand); buttonList[buttInx].cmdInx = curCommand; } wButtonSetBusy( (wButton_p) buttonList[commandList[curCommand].buttInx].control, TRUE); } LOG(log_command, 1, ( "COMMAND START %s\n", commandList[curCommand].helpKey )) rc = commandList[curCommand].cmdProc( C_START, pos); LOG(log_command, 4, ( " COMMAND returns %d\n", rc )) TempRedraw(); // DoCommandB switch (rc) { case C_CONTINUE: break; case C_ERROR: Reset(); #ifdef VERBOSE lprintf( "Start returns Error"); #endif break; case C_TERMINATE: case C_INFO: if (rc == C_TERMINATE) InfoMessage(""); Reset(); break; } inDoCommandB = FALSE; } static void DoCommandBIndirect(void * cmdInxP) { wIndex_t cmdInx; cmdInx = *(wIndex_t*) cmdInxP; DoCommandB((void*) (intptr_t) cmdInx); } EXPORT void LayoutSetPos(wIndex_t inx) { wPos_t w, h, offset; static wPos_t toolbarRowHeight = 0; static wPos_t width; static int lastGroup; static wPos_t gap; static int layerButtCnt; int currGroup; if (inx == 0) { lastGroup = 0; wWinGetSize(mainW, &width, &h); gap = 5; toolbarWidth = width - 20 + 5; layerButtCnt = 0; toolbarHeight = 0; } if (buttonList[inx].control) { if (toolbarRowHeight <= 0) toolbarRowHeight = wControlGetHeight(buttonList[inx].control); currGroup = buttonList[inx].group & ~BG_BIGGAP; if (currGroup != lastGroup && (buttonList[inx].group & BG_BIGGAP)) { gap = 15; } if ((toolbarSet & (1 << currGroup)) && (programMode != MODE_TRAIN || (buttonList[inx].options & (IC_MODETRAIN_TOO | IC_MODETRAIN_ONLY))) && (programMode == MODE_TRAIN || (buttonList[inx].options & IC_MODETRAIN_ONLY) == 0) && ((buttonList[inx].group & ~BG_BIGGAP) != BG_LAYER || layerButtCnt++ <= layerCount)) { if (currGroup != lastGroup) { toolbarWidth += gap; lastGroup = currGroup; gap = 5; } w = wControlGetWidth(buttonList[inx].control); h = wControlGetHeight(buttonList[inx].control); if (h width - 20) { toolbarWidth = 0; toolbarHeight += h + 5; } wControlSetPos(buttonList[inx].control, toolbarWidth, toolbarHeight - (h + 5 +offset)); buttonList[inx].x = toolbarWidth; buttonList[inx].y = toolbarHeight - (h + 5 + offset); toolbarWidth += wControlGetWidth(buttonList[inx].control); wControlShow(buttonList[inx].control, TRUE); } else { wControlShow(buttonList[inx].control, FALSE); } } } EXPORT void LayoutToolBar( void * data ) { int inx; for (inx = 0; inx < buttonCnt; inx++) { LayoutSetPos(inx); } if (toolbarSet&(1<= COMMAND_MAX - 1) { AbortProg("addCommand: too many commands"); } commandList[commandCnt].labelStr = MyStrdup(nameStr); commandList[commandCnt].helpKey = MyStrdup(helpKey); commandList[commandCnt].cmdProc = cmdProc; commandList[commandCnt].icon = icon; commandList[commandCnt].reqLevel = reqLevel; commandList[commandCnt].enabled = TRUE; commandList[commandCnt].options = options; commandList[commandCnt].acclKey = acclKey; commandList[commandCnt].context = context; commandList[commandCnt].buttInx = -1; commandList[commandCnt].menu[0] = NULL; commandList[commandCnt].menu[1] = NULL; commandList[commandCnt].menu[2] = NULL; commandList[commandCnt].menu[3] = NULL; commandCnt++; return commandCnt - 1; } EXPORT void AddToolbarControl(wControl_p control, long options) { if (buttonCnt >= COMMAND_MAX - 1) { AbortProg("addToolbarControl: too many buttons"); } buttonList[buttonCnt].enabled = TRUE; buttonList[buttonCnt].options = options; buttonList[buttonCnt].group = cmdGroup; buttonList[buttonCnt].x = 0; buttonList[buttonCnt].y = 0; buttonList[buttonCnt].control = control; buttonList[buttonCnt].cmdInx = -1; LayoutSetPos(buttonCnt); buttonCnt++; } EXPORT wButton_p AddToolbarButton(char * helpStr, wIcon_p icon, long options, wButtonCallBack_p action, void * context) { wButton_p bb; wIndex_t inx; GetBalloonHelpStr(helpStr); if (context == NULL) { for (inx = 0; inx < menuPG.paramCnt; inx++) { if (action != DoCommandB && menuPLs[inx].valueP == (void*) action) { context = &menuPLs[inx]; action = ParamMenuPush; menuPLs[inx].context = (void*) (intptr_t) buttonCnt; menuPLs[inx].option |= IC_PLAYBACK_PUSH; break; } } } bb = wButtonCreate(mainW, 0, 0, helpStr, (char*) icon, BO_ICON/*|((options&IC_CANCEL)?BB_CANCEL:0)*/, 0, action, context); AddToolbarControl((wControl_p) bb, options); return bb; } EXPORT void PlaybackButtonMouse(wIndex_t buttInx) { wPos_t cmdX, cmdY; if (buttInx < 0 || buttInx >= buttonCnt) return; if (buttonList[buttInx].control == NULL) return; cmdX = buttonList[buttInx].x + 17; cmdY = toolbarHeight - (buttonList[buttInx].y + 17) + (wPos_t) (mainD.size.y / mainD.scale * mainD.dpi) + 30; MovePlaybackCursor(&mainD, cmdX, cmdY,TRUE,buttonList[buttInx].control); if (playbackTimer == 0) { wButtonSetBusy((wButton_p) buttonList[buttInx].control, TRUE); wFlush(); wPause(500); wButtonSetBusy((wButton_p) buttonList[buttInx].control, FALSE); wFlush(); } } #include "bitmaps/openbutt.xpm" static char * buttonGroupMenuTitle; static char * buttonGroupHelpKey; static char * buttonGroupStickyLabel; static wMenu_p buttonGroupPopupM; EXPORT void ButtonGroupBegin(char * menuTitle, char * helpKey, char * stickyLabel) { buttonGroupMenuTitle = menuTitle; buttonGroupHelpKey = helpKey; buttonGroupStickyLabel = stickyLabel; buttonGroupPopupM = NULL; } EXPORT void ButtonGroupEnd(void) { buttonGroupMenuTitle = NULL; buttonGroupHelpKey = NULL; buttonGroupPopupM = NULL; } EXPORT wIndex_t AddMenuButton(wMenu_p menu, procCommand_t command, char * helpKey, char * nameStr, wIcon_p icon, int reqLevel, long options, long acclKey, void * context) { wIndex_t buttInx = -1; wIndex_t cmdInx; BOOL_T newButtonGroup = FALSE; wMenu_p tm, p1m, p2m; static wIcon_p openbuttIcon = NULL; static wMenu_p commandsSubmenu; static wMenu_p popup1Submenu; static wMenu_p popup2Submenu; if (icon) { if (buttonGroupPopupM != NULL) { buttInx = buttonCnt - 2; } else { buttInx = buttonCnt; AddToolbarButton(helpKey, icon, options, (wButtonCallBack_p) DoCommandB, (void*) (intptr_t) commandCnt); buttonList[buttInx].cmdInx = commandCnt; } if (buttonGroupMenuTitle != NULL && buttonGroupPopupM == NULL) { if (openbuttIcon == NULL) openbuttIcon = wIconCreatePixMap(openbutt_xpm); buttonGroupPopupM = wMenuPopupCreate(mainW, buttonGroupMenuTitle); AddToolbarButton(buttonGroupHelpKey, openbuttIcon, IC_ABUT, (wButtonCallBack_p) wMenuPopupShow, (void*) buttonGroupPopupM); newButtonGroup = TRUE; commandsSubmenu = wMenuMenuCreate(menu, "", buttonGroupMenuTitle); if (options & IC_POPUP2) { popup1Submenu = wMenuMenuCreate(popup1aM, "", buttonGroupMenuTitle); popup2Submenu = wMenuMenuCreate(popup2aM, "", buttonGroupMenuTitle); } else if (options & IC_POPUP3) { popup1Submenu= wMenuMenuCreate(popup1mM, "", buttonGroupMenuTitle); popup2Submenu = wMenuMenuCreate(popup2mM, "", buttonGroupMenuTitle); } else { popup1Submenu = wMenuMenuCreate(popup1M, "", buttonGroupMenuTitle); popup2Submenu = wMenuMenuCreate(popup2M, "", buttonGroupMenuTitle); } } } cmdInx = AddCommand(command, helpKey, nameStr, icon, reqLevel, options, acclKey, context); commandList[cmdInx].buttInx = buttInx; if (nameStr[0] == '\0') return cmdInx; if (commandList[cmdInx].options & IC_STICKY) { if (buttonGroupPopupM == NULL || newButtonGroup) { if (stickyCnt > 32) AbortProg("stickyCnt>32"); stickyCnt++; } if (buttonGroupPopupM == NULL) { stickyLabels[stickyCnt - 1] = nameStr; } else { stickyLabels[stickyCnt - 1] = buttonGroupStickyLabel; } stickyLabels[stickyCnt] = NULL; long stickyMask = 1L<<(stickyCnt-1); commandList[cmdInx].stickyMask = stickyMask; if ( ( commandList[cmdInx].options & IC_INITNOTSTICKY ) == 0 ) stickySet |= stickyMask; } if (buttonGroupPopupM) { commandList[cmdInx].menu[0] = wMenuPushCreate(buttonGroupPopupM, helpKey, GetBalloonHelpStr(helpKey), 0, DoCommandB, (void*) (intptr_t) cmdInx); tm = commandsSubmenu; p1m = popup1Submenu; p2m = popup2Submenu; } else { tm = menu; p1m = (options & IC_POPUP2) ? popup1aM : (options & IC_POPUP3) ? popup1mM : popup1M; p2m = (options & IC_POPUP2) ? popup2aM : (options & IC_POPUP3) ? popup2mM : popup2M; } commandList[cmdInx].menu[1] = wMenuPushCreate(tm, helpKey, nameStr, acclKey, DoCommandB, (void*) (intptr_t) cmdInx); if ((options & (IC_POPUP | IC_POPUP2 | IC_POPUP3))) { if (!(options & IC_SELECTED)) { commandList[cmdInx].menu[2] = wMenuPushCreate(p1m, helpKey, nameStr, 0, DoCommandB, (void*) (intptr_t) cmdInx); } commandList[cmdInx].menu[3] = wMenuPushCreate(p2m, helpKey, nameStr, 0, DoCommandB, (void*) (intptr_t) cmdInx); } return cmdInx; } EXPORT wIndex_t InitCommand(wMenu_p menu, procCommand_t command, char * nameStr, char * bits, int reqLevel, long options, long acclKey) { char helpKey[STR_SHORT_SIZE]; wIcon_p icon = NULL; if (bits) icon = wIconCreateBitMap(16, 16, bits, wDrawColorBlack); strcpy(helpKey, "cmd"); strcat(helpKey, nameStr); return AddMenuButton(menu, command, helpKey, _(nameStr), icon, reqLevel, options, acclKey, NULL); } /*--------------------------------------------------------------------*/ EXPORT void PlaybackCommand(char * line, wIndex_t lineNum) { wIndex_t inx; wIndex_t buttInx; int len1, len2; len1 = strlen(line + 8); for (inx = 0; inx < commandCnt; inx++) { len2 = strlen(commandList[inx].helpKey + 3); if (len1 == len2 && strncmp(line + 8, commandList[inx].helpKey + 3, len2) == 0) { break; } } if (inx >= commandCnt) { fprintf(stderr, "Unknown playback COMMAND command %d : %s\n", lineNum, line); } else { wPos_t cmdX, cmdY; if ((buttInx = commandList[inx].buttInx) >= 0) { cmdX = buttonList[buttInx].x + 17; cmdY = toolbarHeight - (buttonList[buttInx].y + 17) + (wPos_t) (mainD.size.y / mainD.scale * mainD.dpi) + 30; MovePlaybackCursor(&mainD, cmdX, cmdY,TRUE,buttonList[buttInx].control); } if (strcmp(line + 8, "Undo") == 0) { if (buttInx > 0 && playbackTimer == 0) { wButtonSetBusy((wButton_p) buttonList[buttInx].control, TRUE); wFlush(); wPause(500); wButtonSetBusy((wButton_p) buttonList[buttInx].control, FALSE); wFlush(); } UndoUndo(); } else if (strcmp(line + 8, "Redo") == 0) { if (buttInx >= 0 && playbackTimer == 0) { wButtonSetBusy((wButton_p) buttonList[buttInx].control, TRUE); wFlush(); wPause(500); wButtonSetBusy((wButton_p) buttonList[buttInx].control, FALSE); wFlush(); } UndoRedo(); } else { if (buttInx >= 0 && playbackTimer == 0) { wButtonSetBusy((wButton_p) buttonList[buttInx].control, TRUE); wFlush(); wPause(500); wButtonSetBusy((wButton_p) buttonList[buttInx].control, FALSE); wFlush(); } DoCommandB((void*) (intptr_t) inx); } } } /*--------------------------------------------------------------------*/ typedef struct { char * label; wMenu_p menu; } menuTrace_t, *menuTrace_p; static dynArr_t menuTrace_da; #define menuTrace(N) DYNARR_N( menuTrace_t, menuTrace_da, N ) static void DoMenuTrace(wMenu_p menu, const char * label, void * data) { /*printf( "MENUTRACE: %s/%s\n", (char*)data, label );*/ if (recordF) { fprintf(recordF, "MOUSE 1 %0.3f %0.3f\n", oldMarker.x, oldMarker.y); fprintf(recordF, "MENU %0.3f %0.3f \"%s\" \"%s\"\n", oldMarker.x, oldMarker.y, (char*) data, label); } } EXPORT wMenu_p MenuRegister(char * label) { wMenu_p m; menuTrace_p mt; m = wMenuPopupCreate(mainW, label); DYNARR_APPEND(menuTrace_t, menuTrace_da, 10); mt = &menuTrace(menuTrace_da.cnt - 1); mt->label = strdup(label); mt->menu = m; wMenuSetTraceCallBack(m, DoMenuTrace, mt->label); return m; } void MenuPlayback(char * line) { char * menuName, *itemName; coOrd pos; wPos_t x, y; menuTrace_p mt; if (!GetArgs(line, "pqq", &pos, &menuName, &itemName)) return; for (mt = &menuTrace(0); mt < &menuTrace(menuTrace_da.cnt); mt++) { if (strcmp(mt->label, menuName) == 0) { mainD.CoOrd2Pix(&mainD, pos, &x, &y); MovePlaybackCursor(&mainD, x, y, FALSE, NULL); oldMarker = cmdMenuPos = pos; wMenuAction(mt->menu, _(itemName)); return; } } AbortProg("menuPlayback: %s not found", menuName); } /*--------------------------------------------------------------------*/ static wWin_p stickyW; static void StickyOk(void *); static paramData_t stickyPLs[] = { { PD_TOGGLE, &stickySet, "set", 0, stickyLabels } }; static paramGroup_t stickyPG = { "sticky", PGO_RECORD, stickyPLs, sizeof stickyPLs / sizeof stickyPLs[0] }; static void StickyOk(void * junk) { wHide(stickyW); } static void DoSticky(void) { if (!stickyW) stickyW = ParamCreateDialog(&stickyPG, MakeWindowTitle(_("Sticky Commands")), _("Ok"), StickyOk, wHide, TRUE, NULL, 0, NULL); ParamLoadControls(&stickyPG); wShow(stickyW); } /*--------------------------------------------------------------------*/ /* * These array control the choices available in the Toolbar setup. * For each choice, the text is given and the respective mask is * specified in the following array. * Note: text and choices must be given in the same order. */ static char *AllToolbarLabels[] = { N_("File Buttons"), N_("Import/Export Buttons"), N_("Zoom Buttons"), N_( "Undo Buttons"), N_("Easement Button"), N_("SnapGrid Buttons"), N_( "Create Track Buttons"), N_("Layout Control Elements"), N_( "Modify Track Buttons"), N_("Properties/Select"), N_( "Track Group Buttons"), N_("Train Group Buttons"), N_( "Create Misc Buttons"), N_("Ruler Button"), N_("Layer Buttons"), N_( "Hot Bar"), NULL }; static long AllToolbarMasks[] = { 1 << BG_FILE, 1<< BG_EXPORTIMPORT, 1 << BG_ZOOM, 1 << BG_UNDO, 1 << BG_EASE, 1 << BG_SNAP, 1 << BG_TRKCRT, 1 << BG_CONTROL, 1 << BG_TRKMOD, 1 << BG_SELECT, 1 << BG_TRKGRP, 1 << BG_TRAIN, 1 << BG_MISCCRT, 1 << BG_RULER, 1 << BG_LAYER, 1 << BG_HOTBAR }; static void ToolbarAction(wBool_t set, void * data) { long mask = (long) data; if (set) toolbarSet |= mask; else toolbarSet &= ~mask; wPrefSetInteger( "misc", "toolbarset", toolbarSet ); MainProc( mainW, wResize_e, NULL, NULL ); if (recordF) fprintf(recordF, "PARAMETER %s %s %ld", "misc", "toolbarset", toolbarSet); } /** * Create the Toolbar configuration submenu. Based on two arrays of descriptions and * masks, the toolbar submenu is created dynamically. * * \param toolbarM IN menu to which the toogles will be added */ static void CreateToolbarM(wMenu_p toolbarM) { int inx, cnt; long *masks; char **labels; wBool_t set; cnt = sizeof(AllToolbarMasks) / sizeof(AllToolbarMasks[0]); masks = AllToolbarMasks; labels = AllToolbarLabels; for (inx = 0; inx < cnt; inx++, masks++, labels++) { set = (toolbarSet & *masks) != 0; wMenuToggleCreate(toolbarM, "toolbarM", _(*labels), 0, set, ToolbarAction, (void*) *masks); } } /*--------------------------------------------------------------------*/ static wWin_p addElevW; #define addElevF (wFloat_p)addElevPD.control EXPORT DIST_T addElevValueV; static void DoAddElev(void *); static paramFloatRange_t rn1000_1000 = { -1000.0, 1000.0 }; static paramData_t addElevPLs[] = { { PD_FLOAT, &addElevValueV, "value", PDO_DIM, &rn1000_1000, NULL, 0 } }; static paramGroup_t addElevPG = { "addElev", 0, addElevPLs, sizeof addElevPLs / sizeof addElevPLs[0] }; static void DoAddElev(void * junk) { ParamLoadData(&addElevPG); AddElevations(addElevValueV); wHide(addElevW); } static void ShowAddElevations(void) { if (selectedTrackCount <= 0) { ErrorMessage(MSG_NO_SELECTED_TRK); return; } if (addElevW == NULL) addElevW = ParamCreateDialog(&addElevPG, MakeWindowTitle(_("Change Elevations")), _("Change"), DoAddElev, wHide, FALSE, NULL, 0, NULL); wShow(addElevW); } /*--------------------------------------------------------------------*/ static wWin_p rotateW; static wWin_p moveW; static double rotateValue; static coOrd moveValue; static rotateDialogCallBack_t rotateDialogCallBack; static moveDialogCallBack_t moveDialogCallBack; static void RotateEnterOk(void *); static paramFloatRange_t rn360_360 = { -360.0, 360.0, 80.0 }; static paramData_t rotatePLs[] = { { PD_FLOAT, &rotateValue, "rotate", PDO_ANGLE, &rn360_360, N_("Angle:") } }; static paramGroup_t rotatePG = { "rotate", 0, rotatePLs, sizeof rotatePLs / sizeof rotatePLs[0] }; static paramFloatRange_t r_1000_1000 = { -1000.0, 1000.0, 80 }; static void MoveEnterOk(void *); static paramData_t movePLs[] = { { PD_FLOAT, &moveValue.x, "moveX", PDO_DIM, &r_1000_1000, N_("Move X:") }, { PD_FLOAT, &moveValue.y, "moveY", PDO_DIM, &r_1000_1000, N_("Move Y:") } }; static paramGroup_t movePG = { "move", 0, movePLs, sizeof movePLs / sizeof movePLs[0] }; EXPORT void StartRotateDialog(rotateDialogCallBack_t func) { if (rotateW == NULL) rotateW = ParamCreateDialog(&rotatePG, MakeWindowTitle(_("Rotate")), _("Ok"), RotateEnterOk, wHide, FALSE, NULL, 0, NULL); ParamLoadControls(&rotatePG); rotateDialogCallBack = func; wShow(rotateW); } EXPORT void StartMoveDialog(moveDialogCallBack_t func) { if (moveW == NULL) moveW = ParamCreateDialog(&movePG, MakeWindowTitle(_("Move")), _("Ok"), MoveEnterOk, wHide, FALSE, NULL, 0, NULL); ParamLoadControls(&movePG); moveDialogCallBack = func; moveValue = zero; wShow(moveW); } static void MoveEnterOk(void * junk) { ParamLoadData(&movePG); moveDialogCallBack((void*) &moveValue); wHide(moveW); } static void RotateEnterOk(void * junk) { ParamLoadData(&rotatePG); if (angleSystem == ANGLE_POLAR) rotateDialogCallBack((void*) (long)(rotateValue*1000)); else rotateDialogCallBack((void*) (long)(-rotateValue*1000)); wHide(rotateW); } static void RotateDialogInit(void) { ParamRegister(&rotatePG); } static void MoveDialogInit(void) { ParamRegister(&movePG); } EXPORT void AddMoveMenu(wMenu_p m, moveDialogCallBack_t func) { wMenuPushCreate(m, "", _("Enter Move ..."), 0, (wMenuCallBack_p) StartMoveDialog, (void*) func); } //All values multipled by 100 to support decimal points from PD_FLOAT EXPORT void AddRotateMenu(wMenu_p m, rotateDialogCallBack_t func) { wMenuPushCreate(m, "", _("180 "), 0, func, (void*) 180000); wMenuPushCreate(m, "", _("90 CW"), 0, func, (void*) (long) (90000)); wMenuPushCreate(m, "", _("45 CW"), 0, func, (void*) (long) (45000)); wMenuPushCreate(m, "", _("30 CW"), 0, func, (void*) (long) (30000)); wMenuPushCreate(m, "", _("15 CW"), 0, func, (void*) (long) (15000)); wMenuPushCreate(m, "", _("15 CCW"), 0, func, (void*) (long) (360000 - 15000)); wMenuPushCreate(m, "", _("30 CCW"), 0, func, (void*) (long) (360000 - 30000)); wMenuPushCreate(m, "", _("45 CCW"), 0, func, (void*) (long) (360000 - 45000)); wMenuPushCreate(m, "", _("90 CCW"), 0, func, (void*) (long) (360000 - 90000)); wMenuPushCreate(m, "", _("Enter Angle ..."), 0, (wMenuCallBack_p) StartRotateDialog, (void*) func); } /***************************************************************************** * * INITIALIZATON * */ static wWin_p debugW; static int debugCnt = 0; static paramIntegerRange_t r0_100 = { 0, 100, 80 }; static void DebugOk(void * junk); static paramData_t debugPLs[30]; static long debug_values[30]; static int debug_index[30]; static paramGroup_t debugPG = { "debug", 0, debugPLs, 0 }; static void DebugOk(void * junk) { for (int i = 0; i= sizeof debugPLs / sizeof debugPLs[0]) AbortProg("Too many debug flags"); memset(&debugPLs[debugCnt], 0, sizeof debugPLs[debugCnt]); debugPLs[debugCnt].type = PD_LONG; debugPLs[debugCnt].valueP = valueP; debugPLs[debugCnt].nameStr = label; debugPLs[debugCnt].winData = &r0_100; debugPLs[debugCnt].winLabel = label; debugCnt++; } void RecomputeElevations(void); static void MiscMenuItemCreate(wMenu_p m1, wMenu_p m2, char * name, char * label, long acclKey, void * func, long option, void * context) { wMenuPush_p mp; mp = wMenuPushCreate(m1, name, label, acclKey, ParamMenuPush, &menuPLs[menuPG.paramCnt]); if (m2) wMenuPushCreate(m2, name, label, acclKey, ParamMenuPush, &menuPLs[menuPG.paramCnt]); menuPLs[menuPG.paramCnt].control = (wControl_p) mp; menuPLs[menuPG.paramCnt].type = PD_MENUITEM; menuPLs[menuPG.paramCnt].valueP = func; menuPLs[menuPG.paramCnt].nameStr = name; menuPLs[menuPG.paramCnt].option = option; menuPLs[menuPG.paramCnt].context = context; if (name) GetBalloonHelpStr(name); menuPG.paramCnt++; } static char * accelKeyNames[] = { "Del", "Ins", "Home", "End", "Pgup", "Pgdn", "Up", "Down", "Right", "Left", "Back", "F1", "F2", "F3", "F4", "F5", "F6", "F7", "F8", "F9", "F10", "F11", "F12", "NumpadAdd", "NumpadSub" }; static void SetAccelKey(char * prefName, wAccelKey_e key, int mode, wAccelKeyCallBack_p func, void * context) { int mode1 = 0; int inx; const char * prefValue = wPrefGetString("accelKey", prefName); if (prefValue != NULL) { while (prefValue[1] == '-') { switch (prefValue[0]) { case 'S': mode1 |= WKEY_SHIFT; break; case 'C': mode1 |= WKEY_CTRL; break; case 'A': mode1 |= WKEY_ALT; break; default: ; } prefValue += 2; } for (inx = 0; inx < sizeof accelKeyNames / sizeof accelKeyNames[0]; inx++) { if (strcmp(prefValue, accelKeyNames[inx]) == 0) { key = inx + 1; mode = mode1; break; } } } wAttachAccelKey(key, mode, func, context); } #include "bitmaps/zoomin.xpm" #include "bitmaps/zoom.xpm" #include "bitmaps/zoomout.xpm" #include "bitmaps/edit-undo.xpm" #include "bitmaps/edit-redo.xpm" #include "bitmaps/partlist.xpm" #include "bitmaps/document-export.xpm" #include "bitmaps/document-exportdxf.xpm" #include "bitmaps/document-import.xpm" #include "bitmaps/document-importmod.xpm" #include "bitmaps/document-new.xpm" #include "bitmaps/document-save.xpm" #include "bitmaps/document-open.xpm" #include "bitmaps/document-print.xpm" #include "bitmaps/map.xpm" #include "bitmaps/magnet.xpm" static void CreateMenus(void) { wMenu_p fileM, editM, viewM, optionM, windowM, macroM, helpM, toolbarM, messageListM, manageM, addM, changeM, drawM; wMenu_p zoomM, zoomSubM; wMenuPush_p zoomInM, zoomOutM; fileM = wMenuBarAdd(mainW, "menuFile", _("&File")); editM = wMenuBarAdd(mainW, "menuEdit", _("&Edit")); viewM = wMenuBarAdd(mainW, "menuView", _("&View")); addM = wMenuBarAdd(mainW, "menuAdd", _("&Add")); changeM = wMenuBarAdd(mainW, "menuChange", _("&Change")); drawM = wMenuBarAdd(mainW, "menuDraw", _("&Draw")); manageM = wMenuBarAdd(mainW, "menuManage", _("&Manage")); optionM = wMenuBarAdd(mainW, "menuOption", _("&Options")); macroM = wMenuBarAdd(mainW, "menuMacro", _("&Macro")); windowM = wMenuBarAdd(mainW, "menuWindow", _("&Window")); helpM = wMenuBarAdd(mainW, "menuHelp", _("&Help")); /* * POPUP MENUS */ /* Select Commands */ /* Select All */ /* Select All Current */ /* Common View Commands Menu */ /* Zoom In/Out */ /* Snap Grid Menu */ /* Show/Hide Map */ /* Show/Hide Background */ /* Selected Commands */ /*--------------*/ /* DeSelect All */ /* Select All */ /* Select All Current */ /*--------------*/ /* Quick Move */ /* Quick Rotate */ /* Quick Align */ /*--------------*/ /* Move To Current Layer */ /* Move/Rotate Cmds */ /* Cut/Paste/Delete */ /* Group/Un-group Selected */ /*----------*/ /* Thick/Thin */ /* Bridge/Tunnel */ /* Ties/NoTies */ /*-----------*/ /* More Commands */ popup1M = wMenuPopupCreate(mainW, _("Context Commands")); popup2M = wMenuPopupCreate(mainW, _("Shift Context Commands")); MiscMenuItemCreate(popup1M, popup2M, "cmdUndo", _("Undo"), 0, (void*) (wMenuCallBack_p) UndoUndo, 0, (void *) 0); MiscMenuItemCreate(popup1M, popup2M, "cmdRedo", _("Redo"), 0, (void*) (wMenuCallBack_p) UndoRedo, 0, (void *) 0); /* Zoom */ wMenuPushCreate(popup1M, "cmdZoomIn", _("Zoom In"), 0, (wMenuCallBack_p) DoZoomUp, (void*) 1); wMenuPushCreate(popup2M, "cmdZoomIn", _("Zoom In"), 0, (wMenuCallBack_p) DoZoomUp, (void*) 1); wMenuPushCreate(popup1M, "cmdZoomOut", _("Zoom Out"), 0, (wMenuCallBack_p) DoZoomDown, (void*) 1); wMenuPushCreate(popup2M, "cmdZoomOut", _("Zoom Out"), 0, (wMenuCallBack_p) DoZoomDown, (void*) 1); /* Display */ MiscMenuItemCreate(popup1M, popup2M, "cmdGridEnable", _("Enable SnapGrid"), 0, (void*) (wMenuCallBack_p) SnapGridEnable, 0, (void *) 0); MiscMenuItemCreate(popup1M, popup2M, "cmdGridShow", _("SnapGrid Show"), 0, (void*) (wMenuCallBack_p) SnapGridShow, 0, (void *) 0); MiscMenuItemCreate(popup1M, popup2M, "cmdMagneticSnap", _(" Enable Magnetic Snap"), 0, (void*) (wMenuCallBack_p) MagneticSnapToggle, 0, (void *) 0); MiscMenuItemCreate(popup1M, popup2M, "cmdMapShow", _("Show/Hide Map"), 0, (void*) (wMenuCallBack_p) MapWindowToggleShow, 0, (void *) 0); MiscMenuItemCreate(popup1M, popup2M, "cmdBackgroundShow", _("Show/Hide Background"), 0, (void*) (wMenuCallBack_p) BackgroundToggleShow, 0, (void *) 0); wMenuSeparatorCreate(popup1M); wMenuSeparatorCreate(popup2M); /* Copy/Paste */ MiscMenuItemCreate(popup2M, NULL, "cmdCut", _("Cut"), 0, (void*) (wMenuCallBack_p) EditCut, 0, (void *) 0); MiscMenuItemCreate(popup2M, NULL, "cmdCopy", _("Copy"), 0, (void*) (wMenuCallBack_p) EditCopy, 0, (void *) 0); MiscMenuItemCreate(popup1M, popup2M, "cmdPaste", _("Paste"), 0, (void*) (wMenuCallBack_p) EditPaste, 0, (void *) 0); MiscMenuItemCreate(popup2M, NULL, "cmdClone", _("Clone"), 0, (void*) (wMenuCallBack_p) EditClone, 0, (void *) 0); /*Select*/ MiscMenuItemCreate(popup1M, popup2M, "cmdSelectAll", _("Select All"), 0, (void*) (wMenuCallBack_p) SetAllTrackSelect, 0, (void *) 1); MiscMenuItemCreate(popup1M, popup2M, "cmdSelectCurrentLayer", _("Select Current Layer"), 0, (void*) (wMenuCallBack_p) SelectCurrentLayer, 0, (void *) 0); MiscMenuItemCreate(popup2M, NULL, "cmdDeselectAll", _("Deselect All"), 0, (void*) (wMenuCallBack_p) SetAllTrackSelect, 0, (void *) 0); /* Modify */ wMenuPushCreate(popup2M, "cmdMove", _("Move"), 0, (wMenuCallBack_p) DoCommandBIndirect, &moveCmdInx); wMenuPushCreate(popup2M, "cmdRotate", _("Rotate"), 0, (wMenuCallBack_p) DoCommandBIndirect, &rotateCmdInx); wMenuSeparatorCreate(popup1M); wMenuSeparatorCreate(popup2M); MiscMenuItemCreate(popup2M, NULL, "cmdDelete", _("Delete"), 0, (void*) (wMenuCallBack_p) SelectDelete, 0, (void *) 0); wMenuSeparatorCreate(popup2M); popup1aM = wMenuMenuCreate(popup1M, "", _("Add...")); popup2aM = wMenuMenuCreate(popup2M, "", _("Add...")); wMenuSeparatorCreate(popup2M); wMenuSeparatorCreate(popup1M); popup1mM = wMenuMenuCreate(popup1M, "", _("More...")); popup2mM = wMenuMenuCreate(popup2M, "", _("More...")); cmdGroup = BG_FILE; AddToolbarButton("menuFile-clear", wIconCreatePixMap(document_new), IC_MODETRAIN_TOO, (addButtonCallBack_t) DoClear, NULL); AddToolbarButton("menuFile-load", wIconCreatePixMap(document_open), IC_MODETRAIN_TOO, (addButtonCallBack_t) ChkLoad, NULL); AddToolbarButton("menuFile-save", wIconCreatePixMap(document_save), IC_MODETRAIN_TOO, (addButtonCallBack_t) DoSave, NULL); InitCmdExport(); cmdGroup = BG_ZOOM; zoomUpB = AddToolbarButton("cmdZoomIn", wIconCreatePixMap(zoomin_xpm), IC_MODETRAIN_TOO, (addButtonCallBack_t) DoZoomUp, NULL); zoomM = wMenuPopupCreate(mainW, ""); AddToolbarButton("cmdZoom", wIconCreatePixMap(zoom_xpm), IC_MODETRAIN_TOO, (wButtonCallBack_p) wMenuPopupShow, zoomM); zoomDownB = AddToolbarButton("cmdZoomOut", wIconCreatePixMap(zoomout_xpm), IC_MODETRAIN_TOO, (addButtonCallBack_t) DoZoomDown, NULL); cmdGroup = BG_UNDO; undoB = AddToolbarButton("cmdUndo", wIconCreatePixMap(edit_undo), 0, (addButtonCallBack_t) UndoUndo, NULL); redoB = AddToolbarButton("cmdRedo", wIconCreatePixMap(edit_redo), 0, (addButtonCallBack_t) UndoRedo, NULL); wControlActive((wControl_p) undoB, FALSE); wControlActive((wControl_p) redoB, FALSE); /* * FILE MENU */ MiscMenuItemCreate(fileM, NULL, "menuFile-clear", _("&New ..."), ACCL_NEW, (void*) (wMenuCallBack_p) DoClear, 0, (void *) 0); wMenuPushCreate(fileM, "menuFile-load", _("&Open ..."), ACCL_OPEN, (wMenuCallBack_p) ChkLoad, NULL); wMenuSeparatorCreate(fileM); wMenuPushCreate(fileM, "menuFile-save", _("&Save"), ACCL_SAVE, (wMenuCallBack_p) DoSave, NULL); wMenuPushCreate(fileM, "menuFile-saveAs", _("Save &As ..."), ACCL_SAVEAS, (wMenuCallBack_p) DoSaveAs, NULL); wMenuPushCreate(fileM, "menuFile-revert", _("Revert"), ACCL_REVERT, (wMenuCallBack_p) ChkRevert, NULL); wMenuSeparatorCreate(fileM); MiscMenuItemCreate(fileM, NULL, "printSetup", _("P&rint Setup ..."), ACCL_PRINTSETUP, (void*) (wMenuCallBack_p) wPrintSetup, 0, (void *) 0); printCmdInx = InitCmdPrint(fileM); wMenuSeparatorCreate(fileM); MiscMenuItemCreate(fileM, NULL, "cmdImport", _("&Import"), ACCL_IMPORT, (void*) (wMenuCallBack_p) DoImport, 0, (void *) 0); MiscMenuItemCreate(fileM, NULL, "cmdImportModule", _("Import &Module"), ACCL_IMPORT_MOD, (void*) (wMenuCallBack_p) DoImport, 0, (void *) 1); MiscMenuItemCreate(fileM, NULL, "cmdOutputbitmap", _("Export to &Bitmap"), ACCL_PRINTBM, (void*) (wMenuCallBack_p) OutputBitMapInit(), 0, (void *) 0); MiscMenuItemCreate(fileM, NULL, "cmdExport", _("E&xport"), ACCL_EXPORT, (void*) (wMenuCallBack_p) DoExport, IC_SELECTED, (void *) 0); MiscMenuItemCreate(fileM, NULL, "cmdExportDXF", _("Export D&XF"), ACCL_EXPORTDXF, (void*) (wMenuCallBack_p) DoExportDXF, IC_SELECTED, (void *) 0); wMenuSeparatorCreate(fileM); MiscMenuItemCreate(fileM, NULL, "cmdPrmfile", _("Parameter &Files ..."), ACCL_PARAMFILES, (void*) ParamFilesInit(), 0, (void *) 0); MiscMenuItemCreate(fileM, NULL, "cmdFileNote", _("No&tes ..."), ACCL_NOTES, (void*) (wMenuCallBack_p) DoNote, 0, (void *) 0); wMenuSeparatorCreate(fileM); fileList_ml = wMenuListCreate(fileM, "menuFileList", NUM_FILELIST, ChkFileList); wMenuSeparatorCreate(fileM); wMenuPushCreate(fileM, "menuFile-quit", _("E&xit"), 0, (wMenuCallBack_p) DoQuit, NULL); /* * EDIT MENU */ MiscMenuItemCreate(editM, NULL, "cmdUndo", _("&Undo"), ACCL_UNDO, (void*) (wMenuCallBack_p) UndoUndo, 0, (void *) 0); MiscMenuItemCreate(editM, NULL, "cmdRedo", _("R&edo"), ACCL_REDO, (void*) (wMenuCallBack_p) UndoRedo, 0, (void *) 0); wMenuSeparatorCreate(editM); MiscMenuItemCreate(editM, NULL, "cmdCut", _("Cu&t"), ACCL_CUT, (void*) (wMenuCallBack_p) EditCut, IC_SELECTED, (void *) 0); MiscMenuItemCreate(editM, NULL, "cmdCopy", _("&Copy"), ACCL_COPY, (void*) (wMenuCallBack_p) EditCopy, IC_SELECTED, (void *) 0); MiscMenuItemCreate(editM, NULL, "cmdPaste", _("&Paste"), ACCL_PASTE, (void*) (wMenuCallBack_p) EditPaste, 0, (void *) 0); MiscMenuItemCreate(editM, NULL, "cmdClone", _("C&lone"), ACCL_CLONE, (void*) (wMenuCallBack_p) EditClone, 0, (void *) 0); MiscMenuItemCreate(editM, NULL, "cmdDelete", _("De&lete"), ACCL_DELETE, (void*) (wMenuCallBack_p) SelectDelete, IC_SELECTED, (void *) 0); MiscMenuItemCreate(editM, NULL, "cmdMoveToCurrentLayer", _("Move To Current Layer"), ACCL_MOVCURLAYER, (void*) (wMenuCallBack_p) MoveSelectedTracksToCurrentLayer, IC_SELECTED, (void *) 0); wMenuSeparatorCreate( editM ); menuPLs[menuPG.paramCnt].context = (void*)1; MiscMenuItemCreate( editM, NULL, "cmdSelectAll", _("Select &All"), ACCL_SELECTALL, (void*)(wMenuCallBack_p)SetAllTrackSelect, 0, (void *)1 ); MiscMenuItemCreate( editM, NULL, "cmdSelectCurrentLayer", _("Select Current Layer"), ACCL_SETCURLAYER, (void*)(wMenuCallBack_p)SelectCurrentLayer, 0, (void *)0 ); MiscMenuItemCreate( editM, NULL, "cmdDeselectAll", _("&Deselect All"), ACCL_DESELECTALL, (void*)(wMenuCallBack_p)SetAllTrackSelect, 0, (void *)0 ); MiscMenuItemCreate( editM, NULL, "cmdSelectInvert", _("&Invert Selection"), 0L, (void*)(wMenuCallBack_p)InvertTrackSelect, 0, (void *)0 ); MiscMenuItemCreate( editM, NULL, "cmdSelectOrphaned", _("Select Stranded Track"), 0L, (void*)(wMenuCallBack_p)OrphanedTrackSelect, 0, (void *)0 ); wMenuSeparatorCreate( editM ); MiscMenuItemCreate( editM, NULL, "cmdTunnel", _("Tu&nnel"), ACCL_TUNNEL, (void*)(wMenuCallBack_p)SelectTunnel, IC_SELECTED, (void *)0 ); MiscMenuItemCreate( editM, NULL, "cmdBridge", _("B&ridge"), ACCL_BRIDGE, (void*)(wMenuCallBack_p)SelectBridge, IC_SELECTED, (void *)0); MiscMenuItemCreate( editM, NULL, "cmdTies", _("Ties/NoTies"), ACCL_TIES, (void*)(wMenuCallBack_p)SelectTies, IC_SELECTED, (void *)0); MiscMenuItemCreate( editM, NULL, "cmdAbove", _("Move to &Front"), ACCL_ABOVE, (void*)(wMenuCallBack_p)SelectAbove, IC_SELECTED, (void *)0 ); MiscMenuItemCreate( editM, NULL, "cmdBelow", _("Move to &Back"), ACCL_BELOW, (void*)(wMenuCallBack_p)SelectBelow, IC_SELECTED, (void *)0 ); wMenuSeparatorCreate( editM ); MiscMenuItemCreate( editM, NULL, "cmdWidth0", _("Thin Tracks"), ACCL_THIN, (void*)(wMenuCallBack_p)SelectTrackWidth, IC_SELECTED, (void *)0 ); MiscMenuItemCreate( editM, NULL, "cmdWidth2", _("Medium Tracks"), ACCL_MEDIUM, (void*)(wMenuCallBack_p)SelectTrackWidth, IC_SELECTED, (void *)2 ); MiscMenuItemCreate( editM, NULL, "cmdWidth3", _("Thick Tracks"), ACCL_THICK, (void*)(wMenuCallBack_p)SelectTrackWidth, IC_SELECTED, (void *)3 ); /* * VIEW MENU */ zoomInM = wMenuPushCreate(viewM, "menuEdit-zoomIn", _("Zoom &In"), ACCL_ZOOMIN, (wMenuCallBack_p) DoZoomUp, (void*) 1); zoomSubM = wMenuMenuCreate(viewM, "menuEdit-zoomTo", _("&Zoom")); zoomOutM = wMenuPushCreate(viewM, "menuEdit-zoomOut", _("Zoom &Out"), ACCL_ZOOMOUT, (wMenuCallBack_p) DoZoomDown, (void*) 1); wMenuSeparatorCreate(viewM); InitCmdZoom(zoomM, zoomSubM, NULL, NULL); /* these menu choices and toolbar buttons are synonymous and should be treated as such */ wControlLinkedSet((wControl_p) zoomInM, (wControl_p) zoomUpB); wControlLinkedSet((wControl_p) zoomOutM, (wControl_p) zoomDownB); wMenuPushCreate(viewM, "menuEdit-redraw", _("&Redraw"), ACCL_REDRAW, (wMenuCallBack_p) MainRedraw, NULL); wMenuPushCreate(viewM, "menuEdit-redraw", _("Redraw All"), ACCL_REDRAWALL, (wMenuCallBack_p) DoRedraw, NULL); wMenuSeparatorCreate(viewM); snapGridEnableMI = wMenuToggleCreate(viewM, "cmdGridEnable", _("Enable SnapGrid"), ACCL_SNAPENABLE, 0, (wMenuToggleCallBack_p) SnapGridEnable, NULL); snapGridShowMI = wMenuToggleCreate(viewM, "cmdGridShow", _("Show SnapGrid"), ACCL_SNAPSHOW, FALSE, (wMenuToggleCallBack_p) SnapGridShow, NULL); gridCmdInx = InitGrid(viewM); // visibility toggle for anchors // get the start value long anchors_long; wPrefGetInteger("misc", "anchors", (long *)&anchors_long, 1); magneticSnap = anchors_long ? TRUE : FALSE; magnetsMI = wMenuToggleCreate(viewM, "cmdMagneticSnap", _("Enable Magnetic Snap"), 0, magneticSnap, (wMenuToggleCallBack_p)MagneticSnapToggle, NULL); // visibility toggle for map window // get the start value long mapVisible_long; wPrefGetInteger("misc", "mapVisible", (long *) &mapVisible_long, 1); mapVisible = mapVisible_long ? TRUE : FALSE; mapShowMI = wMenuToggleCreate(viewM, "cmdMapShow", _("Show/Hide Map"), ACCL_MAPSHOW, mapVisible, (wMenuToggleCallBack_p) MapWindowToggleShow, NULL); wMenuSeparatorCreate(viewM); toolbarM = wMenuMenuCreate(viewM, "toolbarM", _("&Tool Bar")); CreateToolbarM(toolbarM); cmdGroup = BG_EASE; InitCmdEasement(); cmdGroup = BG_SNAP; InitSnapGridButtons(); magnetsB = AddToolbarButton("cmdMagneticSnap", wIconCreatePixMap(magnet_xpm), IC_MODETRAIN_TOO, (addButtonCallBack_t) MagneticSnapToggle, NULL); wControlLinkedSet((wControl_p) magnetsMI, (wControl_p) magnetsB); wButtonSetBusy(magnetsB, (wBool_t) magneticSnap); mapShowB = AddToolbarButton("cmdMapShow", wIconCreatePixMap(map_xpm), IC_MODETRAIN_TOO, (addButtonCallBack_t) MapWindowToggleShow, NULL); wControlLinkedSet((wControl_p) mapShowMI, (wControl_p) mapShowB); wButtonSetBusy(mapShowB, (wBool_t) mapVisible); /* * ADD MENU */ cmdGroup = BG_TRKCRT | BG_BIGGAP; InitCmdStraight(addM); InitCmdCurve(addM); InitCmdParallel(addM); InitCmdTurnout(addM); InitCmdHandLaidTurnout(addM); InitCmdStruct(addM); InitCmdHelix(addM); InitCmdTurntable(addM); cmdGroup = BG_CONTROL; ButtonGroupBegin( _("Control Element"), "cmdControlElements", _("Control Element") ); InitCmdBlock(addM); InitCmdSwitchMotor(addM); InitCmdSignal(addM); InitCmdControl(addM); InitCmdSensor(addM); ButtonGroupEnd(); /* * CHANGE MENU */ cmdGroup = BG_SELECT; InitCmdDescribe(changeM); InitCmdSelect(changeM); InitCmdPan(changeM); wMenuSeparatorCreate(changeM); cmdGroup = BG_TRKGRP; InitCmdMove(changeM); InitCmdDelete(); InitCmdTunnel(); InitCmdBridge(); InitCmdAboveBelow(); cmdGroup = BG_TRKMOD; if (extraButtons) MiscMenuItemCreate(changeM, NULL, "loosen", _("&Loosen Tracks"), ACCL_LOOSEN, (void*) (wMenuCallBack_p) LoosenTracks, IC_SELECTED, (void *) 0); InitCmdModify(changeM); InitCmdJoin(changeM); InitCmdPull(changeM); InitCmdSplit(changeM); InitCmdMoveDescription(changeM); wMenuSeparatorCreate(changeM); MiscMenuItemCreate(changeM, NULL, "cmdAddElevations", _("Raise/Lower Elevations"), ACCL_CHGELEV, (void*) (wMenuCallBack_p) ShowAddElevations, IC_SELECTED, (void *) 0); InitCmdElevation(changeM); InitCmdProfile(changeM); MiscMenuItemCreate(changeM, NULL, "cmdClearElevations", _("Clear Elevations"), ACCL_CLRELEV, (void*) (wMenuCallBack_p) ClearElevations, IC_SELECTED, (void *) 0); MiscMenuItemCreate(changeM, NULL, "cmdElevation", _("Recompute Elevations"), 0, (void*) (wMenuCallBack_p) RecomputeElevations, 0, (void *) 0); ParamRegister(&addElevPG); wMenuSeparatorCreate(changeM); MiscMenuItemCreate(changeM, NULL, "cmdRescale", _("Change Scale"), 0, (void*) (wMenuCallBack_p) DoRescale, IC_SELECTED, (void *) 0); wMenuSeparatorCreate(changeM); InitCmdCornu(changeM); /* * DRAW MENU */ cmdGroup = BG_MISCCRT; InitCmdDraw(drawM); InitCmdText(drawM); InitTrkNote(drawM); cmdGroup = BG_RULER; InitCmdRuler(drawM); /* * OPTION MENU */ MiscMenuItemCreate(optionM, NULL, "cmdLayout", _("L&ayout ..."), ACCL_LAYOUTW, (void*) LayoutInit(), IC_MODETRAIN_TOO, (void *) 0); MiscMenuItemCreate(optionM, NULL, "cmdDisplay", _("&Display ..."), ACCL_DISPLAYW, (void*) DisplayInit(), IC_MODETRAIN_TOO, (void *) 0); MiscMenuItemCreate(optionM, NULL, "cmdCmdopt", _("Co&mmand ..."), ACCL_CMDOPTW, (void*) CmdoptInit(), IC_MODETRAIN_TOO, (void *) 0); MiscMenuItemCreate(optionM, NULL, "cmdEasement", _("&Easements ..."), ACCL_EASEW, (void*) (wMenuCallBack_p) DoEasementRedir, IC_MODETRAIN_TOO, (void *) 0); MiscMenuItemCreate(optionM, NULL, "fontSelW", _("&Fonts ..."), ACCL_FONTW, (void*) (wMenuCallBack_p) SelectFont, IC_MODETRAIN_TOO, (void *) 0); MiscMenuItemCreate(optionM, NULL, "cmdSticky", _("Stic&ky ..."), ACCL_STICKY, (void*) (wMenuCallBack_p) DoSticky, IC_MODETRAIN_TOO, (void *) 0); if (extraButtons) { menuPLs[menuPG.paramCnt].context = debugW; MiscMenuItemCreate(optionM, NULL, "cmdDebug", _("&Debug ..."), 0, (void*) (wMenuCallBack_p) DebugInit, IC_MODETRAIN_TOO, (void *) 0); } MiscMenuItemCreate(optionM, NULL, "cmdPref", _("&Preferences ..."), ACCL_PREFERENCES, (void*) PrefInit(), IC_MODETRAIN_TOO, (void *) 0); MiscMenuItemCreate(optionM, NULL, "cmdColor", _("&Colors ..."), ACCL_COLORW, (void*) ColorInit(), IC_MODETRAIN_TOO, (void *) 0); /* * MACRO MENU */ wMenuPushCreate(macroM, "cmdRecord", _("&Record ..."), ACCL_RECORD, DoRecord, NULL); wMenuPushCreate(macroM, "cmdDemo", _("&Play Back ..."), ACCL_PLAYBACK, DoPlayBack, NULL); /* * WINDOW MENU */ wMenuPushCreate(windowM, "menuWindow", _("Main window"), 0, (wMenuCallBack_p) wShow, mainW); winList_mi = wMenuListCreate(windowM, "menuWindow", -1, DoShowWindow); /* * HELP MENU */ /* main help window */ wMenuAddHelp(helpM); /* help on recent messages */ wMenuSeparatorCreate(helpM); messageListM = wMenuMenuCreate(helpM, "menuHelpRecentMessages", _("Recent Messages")); messageList_ml = wMenuListCreate(messageListM, "messageListM", 10, ShowMessageHelp); wMenuListAdd(messageList_ml, 0, _(MESSAGE_LIST_EMPTY), NULL); /* tip of the day */ wMenuSeparatorCreate( helpM ); wMenuPushCreate( helpM, "cmdTip", _("Tip of the Day..."), 0, (wMenuCallBack_p)ShowTip, (void *)(SHOWTIP_FORCESHOW | SHOWTIP_NEXTTIP)); demoM = wMenuMenuCreate( helpM, "cmdDemo", _("&Demos") ); wMenuPushCreate( helpM, "cmdExamples", _("Examples..."), 0, (wMenuCallBack_p)ChkExamples, (void *)0); /* about window */ wMenuSeparatorCreate(helpM); wMenuPushCreate(helpM, "about", _("About"), 0, (wMenuCallBack_p) CreateAboutW, NULL); /* * MANAGE MENU */ cmdGroup = BG_TRAIN | BG_BIGGAP; InitCmdTrain(manageM); wMenuSeparatorCreate(manageM); InitNewTurn( wMenuMenuCreate(manageM, "cmdTurnoutNew", _("Tur&nout Designer..."))); MiscMenuItemCreate(manageM, NULL, "cmdContmgm", _("Layout &Control Elements"), ACCL_CONTMGM, (void*) ControlMgrInit(), 0, (void*) 0); MiscMenuItemCreate(manageM, NULL, "cmdGroup", _("&Group"), ACCL_GROUP, (void*) (wMenuCallBack_p) DoGroup, IC_SELECTED, (void *) 0); MiscMenuItemCreate(manageM, NULL, "cmdUngroup", _("&Ungroup"), ACCL_UNGROUP, (void*) (wMenuCallBack_p) DoUngroup, IC_SELECTED, (void *) 0); MiscMenuItemCreate(manageM, NULL, "cmdCustmgm", _("Custom defined parts..."), ACCL_CUSTMGM, (void*) CustomMgrInit(), 0, (void *) 0); MiscMenuItemCreate(manageM, NULL, "cmdRefreshCompound", _("Update Turnouts and Structures"), 0, (void*) (wMenuCallBack_p) DoRefreshCompound, 0, (void *) 0); MiscMenuItemCreate(manageM, NULL, "cmdCarInventory", _("Car Inventory"), ACCL_CARINV, (void*) (wMenuCallBack_p) DoCarDlg, IC_MODETRAIN_TOO, (void *) 0); wMenuSeparatorCreate(manageM); MiscMenuItemCreate(manageM, NULL, "cmdLayer", _("Layers ..."), ACCL_LAYERS, (void*) InitLayersDialog(), 0, (void *) 0); wMenuSeparatorCreate(manageM); MiscMenuItemCreate(manageM, NULL, "cmdEnumerate", _("Parts &List ..."), ACCL_PARTSLIST, (void*) (wMenuCallBack_p) EnumerateTracks, 0, (void *) 0); MiscMenuItemCreate(manageM, NULL, "cmdPricelist", _("Price List..."), ACCL_PRICELIST, (void*) PriceListInit(), 0, (void *) 0); cmdGroup = BG_LAYER | BG_BIGGAP; InitCmdSelect2(changeM); InitCmdDescribe2(changeM); InitCmdPan2(changeM); InitLayers(); cmdGroup = BG_HOTBAR; InitHotBar(); #ifdef LATER #ifdef WINDOWS wAttachAccelKey( wAccelKey_Pgdn, 0, (wAccelKeyCallBack_p)DoZoomUp, (void*)1 ); wAttachAccelKey( wAccelKey_Pgup, 0, (wAccelKeyCallBack_p)DoZoomDown, (void*)1 ); wAttachAccelKey( wAccelKey_F5, 0, (wAccelKeyCallBack_p)MainRedraw, (void*)1 ); #endif wAttachAccelKey( wAccelKey_Ins, WKEY_CTRL, (wAccelKeyCallBack_p)EditCopy, 0 ); wAttachAccelKey( wAccelKey_Ins, WKEY_SHIFT, (wAccelKeyCallBack_p)EditPaste, 0 ); wAttachAccelKey( wAccelKey_Back, WKEY_SHIFT, (wAccelKeyCallBack_p)UndoUndo, 0 ); wAttachAccelKey( wAccelKey_Del, WKEY_SHIFT, (wAccelKeyCallBack_p)EditCut, 0 ); wAttachAccelKey( wAccelKey_F6, 0, (wAccelKeyCallBack_p)NextWindow, 0 ); #endif SetAccelKey("zoomUp", wAccelKey_Pgdn, 0, (wAccelKeyCallBack_p) DoZoomUp, (void*) 1); SetAccelKey("zoomDown", wAccelKey_Pgup, 0, (wAccelKeyCallBack_p) DoZoomDown, (void*) 1); SetAccelKey("redraw", wAccelKey_F5, 0, (wAccelKeyCallBack_p) MainRedraw, (void*) 1); SetAccelKey("delete", wAccelKey_Del, 0, (wAccelKeyCallBack_p) SelectDelete, (void*) 1); SetAccelKey("copy", wAccelKey_Ins, WKEY_CTRL, (wAccelKeyCallBack_p) EditCopy, 0); SetAccelKey("paste", wAccelKey_Ins, WKEY_SHIFT, (wAccelKeyCallBack_p) EditPaste, 0); SetAccelKey("undo", wAccelKey_Back, WKEY_SHIFT, (wAccelKeyCallBack_p) UndoUndo, 0); SetAccelKey("cut", wAccelKey_Del, WKEY_SHIFT, (wAccelKeyCallBack_p) EditCut, 0); SetAccelKey("nextWindow", wAccelKey_F6, 0, (wAccelKeyCallBack_p) NextWindow, 0); SetAccelKey("zoomUp", wAccelKey_Numpad_Add, WKEY_CTRL, (wAccelKeyCallBack_p) DoZoomUp, (void*) 1); SetAccelKey("zoomDown", wAccelKey_Numpad_Subtract, WKEY_CTRL, (wAccelKeyCallBack_p) DoZoomDown, (void*) 1); SetAccelKey("help", wAccelKey_F1, WKEY_SHIFT, (wAccelKeyCallBack_p) wDoAccelHelp, (void*) 1); SetAccelKey("help-context", wAccelKey_F1, 0, (wAccelKeyCallBack_p) wDoAccelHelp, (void*) 3); InitBenchDialog(); wPrefGetInteger( "DialogItem", "sticky-set", &stickySet, stickySet ); } static void LoadFileList(void) { char file[6]; int inx; const char * cp; const char *fileName, *pathName; strcpy(file, "fileX"); for (inx = NUM_FILELIST - 1; inx >= 0; inx--) { file[4] = '0' + inx; cp = wPrefGetString("filelist", file); if (!cp) continue; pathName = MyStrdup(cp); fileName = FindFilename((char *) pathName); if (fileName) wMenuListAdd(fileList_ml, 0, fileName, pathName); } } EXPORT void InitCmdEnumerate(void) { AddToolbarButton("cmdEnumerate", wIconCreatePixMap(partlist_xpm), IC_SELECTED | IC_ACCLKEY, (addButtonCallBack_t) EnumerateTracks, NULL); } EXPORT void InitCmdExport(void) { ButtonGroupBegin( _("Import/Export"), "cmdExportImportSetCmd", _("Import/Export") ); cmdGroup = BG_EXPORTIMPORT; AddToolbarButton("cmdExport", wIconCreatePixMap(export_xpm), IC_SELECTED | IC_ACCLKEY, (addButtonCallBack_t) DoExport, NULL); AddToolbarButton("cmdExportDXF", wIconCreatePixMap(export_dxf_xpm), IC_SELECTED | IC_ACCLKEY, (addButtonCallBack_t)DoExportDXF, (void*)1); AddToolbarButton("cmdImport", wIconCreatePixMap(import_xpm), IC_ACCLKEY, (addButtonCallBack_t) DoImport, (void*)0); AddToolbarButton("cmdImportModule", wIconCreatePixMap(importmod_xpm), IC_ACCLKEY, (addButtonCallBack_t) DoImport, (void*)1); ButtonGroupEnd(); } /* Give user the option to continue work after crash. This function gives the user * the option to load the checkpoint file to continue working after a crash. * * \param none * \return TRUE for resume, FALSE otherwise * */ static int OfferCheckpoint( void ) { int ret = FALSE; /* sProdName */ ret = wNotice3( _( "Program was not terminated properly. Do you want to resume working on the previous trackplan?"), _("Resume"), _("Resume with New Name"), _("Ignore Checkpoint")); //ret==1 Same, ret==-1 New, ret==0 Ignore if (ret == 1) printf(_("Reload Checkpoint Selected\n")); else if (ret == -1) printf(_("Reload Checkpoint With New Name Selected\n")); else printf(_("Ignore Checkpoint Selected\n")); if (ret>=0) { /* load the checkpoint file */ LoadCheckpoint(ret==1); ret = TRUE; } return (ret>=0); } EXPORT wWin_p wMain(int argc, char * argv[]) { int c; int resumeWork; char * logFileName = NULL; int log_init = 0; int initialZoom = 0; char * initialFile = NULL; const char * pref; coOrd roomSize; long oldToolbarMax; long newToolbarMax; char *cp; char *oldLocale = NULL; char buffer[STR_SIZE]; unsigned int i; wPos_t displayWidth; wPos_t displayHeight; strcpy(buffer, sProdNameLower); /* Initialize application name */ wInitAppName(buffer); /* Initialize gettext */ InitGettext(); /* Save user locale */ oldLocale = setlocale(LC_ALL, NULL); if (oldLocale) userLocale = strdup(oldLocale); /* * ARGUMENTS */ opterr = 0; while ((c = getopt(argc, argv, "vl:d:c:m")) != -1) switch (c) { case 'c': /* configuration name */ /* test for valid filename */ for (i = 0; i < strlen(optarg); i++) { if (!isalnum((unsigned char) optarg[i]) && optarg[i] != '.') { NoticeMessage(MSG_BAD_OPTION, _("Ok"), NULL, optarg); exit(1); } } /* append delimiter and argument to configuration name */ if (strlen(optarg) < STR_SIZE - strlen(";") - strlen(buffer) - 1) { strcat(buffer, ";"); strcat(buffer, optarg); } else { NoticeMessage(MSG_BAD_OPTION, _("Ok"), NULL, optarg); exit(1); } break; case 'v': /* verbose flag */ verbose++; break; case 'd': /* define loglevel for a group */ cp = strchr(optarg, '='); if (cp != NULL) { *cp++ = '\0'; LogSet(optarg, atoi(cp)); } else { LogSet(optarg, 1); } break; case 'l': /* define log filename */ logFileName = strdup(optarg); break; case '?': NoticeMessage(MSG_BAD_OPTION, _("Ok"), NULL, argv[optind - 1]); exit(1); case 'm': // temporary: use MainRedraw instead of TempRedraw wDrawDoTempDraw = FALSE; break; case ':': NoticeMessage("Missing parameter for %s", _("Ok"), NULL, argv[optind - 1]); exit(1); break; default: abort(); } if (optind < argc) initialFile = strdup(argv[optind]); extraButtons = (getenv(sEnvExtra) != NULL); LogOpen(logFileName); log_init = LogFindIndex("init"); log_malloc = LogFindIndex("malloc"); log_error = LogFindIndex("error"); log_command = LogFindIndex("command"); LOG1(log_init, ( "initCustom\n" )) InitCustom(); /* * MAIN WINDOW */ LOG1(log_init, ( "create main window\n" )) SetLayoutTitle(sProdName); sprintf(message, _("Unnamed Trackplan - %s(%s)"), sProdName, sVersion); wSetBalloonHelp(balloonHelp); wGetDisplaySize(&displayWidth, &displayHeight); mainW = wWinMainCreate(buffer, (displayWidth * 2) / 3, (displayHeight * 2) / 3, "xtrkcadW", message, "main", F_RESIZE | F_MENUBAR | F_NOTAB | F_RECALLPOS | F_RECALLSIZE | F_HIDE, MainProc, NULL); if (mainW == NULL) return NULL; InitAppDefaults(); drawColorBlack = wDrawFindColor( wRGB( 0, 0, 0) ); drawColorWhite = wDrawFindColor( wRGB(255,255,255) ); drawColorRed = wDrawFindColor( wRGB(255, 0, 0) ); drawColorBlue = wDrawFindColor( wRGB( 0, 0,255) ); drawColorGreen = wDrawFindColor( wRGB( 0,255, 0) ); drawColorAqua = wDrawFindColor( wRGB( 0,255,255) ); // Last component of spectial color must be > 3 drawColorPreviewSelected = wDrawFindColor( wRGB ( 6, 6, 255) ); //Special Blue drawColorPreviewUnselected = wDrawFindColor( wRGB( 255, 215, 6)); //Special Yellow drawColorPowderedBlue = wDrawFindColor( wRGB(129, 212, 250) ); drawColorPurple = wDrawFindColor( wRGB(255, 0,255) ); drawColorGold = wDrawFindColor( wRGB(255,215, 0) ); drawColorGrey10 = wDrawFindColor( wRGB(26,26,26) ); drawColorGrey20 = wDrawFindColor( wRGB(51,51,51) ); drawColorGrey30 = wDrawFindColor( wRGB(72,72,72) ); drawColorGrey40 = wDrawFindColor( wRGB(102,102,102) ); drawColorGrey50 = wDrawFindColor( wRGB(128,128,128) ); drawColorGrey60 = wDrawFindColor( wRGB(153,153,153) ); drawColorGrey70 = wDrawFindColor( wRGB(179,179,179) ); drawColorGrey80 = wDrawFindColor( wRGB(204,204,204) ); drawColorGrey90 = wDrawFindColor( wRGB(230,230,230) ); snapGridColor = drawColorGreen; markerColor = drawColorRed; borderColor = drawColorBlack; crossMajorColor = drawColorRed; crossMinorColor = drawColorBlue; selectedColor = drawColorRed; normalColor = drawColorBlack; elevColorIgnore = drawColorBlue; elevColorDefined = drawColorGold; profilePathColor = drawColorPurple; exceptionColor = wDrawFindColor(wRGB(255, 89, 0 )); tieColor = wDrawFindColor(wRGB(153, 89, 68)); newToolbarMax = (1 << BG_COUNT) - 1; wPrefGetInteger("misc", "toolbarset", &toolbarSet, newToolbarMax); wPrefGetInteger("misc", "max-toolbarset", &oldToolbarMax, 0); toolbarSet |= newToolbarMax & ~oldToolbarMax; wPrefSetInteger("misc", "max-toolbarset", newToolbarMax); wPrefSetInteger("misc", "toolbarset", toolbarSet); LOG1(log_init, ( "fontInit\n")) wInitializeFonts(); LOG1(log_init, ( "fileInit\n" )) FileInit(); wCreateSplash(sProdName, sVersion); if (!initialFile) { WDOUBLE_T tmp; LOG1(log_init, ( "set roomsize\n" )) wPrefGetFloat("draw", "roomsizeX", &tmp, 96.0); roomSize.x = tmp; wPrefGetFloat("draw", "roomsizeY", &tmp, 48.0); roomSize.y = tmp; SetRoomSize(roomSize); } /* * INITIALIZE */ LOG1(log_init, ( "initInfoBar\n" )) InitInfoBar(); wSetSplashInfo("Misc2 Init..."); LOG1(log_init, ( "misc2Init\n" )) Misc2Init(); RotateDialogInit(); MoveDialogInit(); wSetSplashInfo(_("Initializing commands")); LOG1(log_init, ( "paramInit\n" )) ParamInit(); LOG1(log_init, ( "initTrkTrack\n" )) InitTrkTrack(); /* * MENUS */ wSetSplashInfo(_("Initializing menus")); LOG1(log_init, ( "createMenus\n" )) CreateMenus(); LOG1(log_init, ( "initialize\n" )) if (!Initialize()) return NULL; ParamRegister(&menuPG); ParamRegister(&stickyPG); /* initialize the layers */ DefaultLayerProperties(); LOG1(log_init, ( "loadFileList\n" )) LoadFileList(); AddPlaybackProc("MENU", MenuPlayback, NULL); //CreateDebugW(); /* * TIDY UP */ curCommand = 0; commandContext = commandList[curCommand].context; /* * READ PARAMETERS */ if (toolbarSet&(1<