/***************************************************************************** # Copyright (C) 1994-2008 by David Gordon. # All rights reserved. # # This software is part of a beta-test version of the Consed/Autofinish # package. It should not be redistributed or # used for any commercial purpose, including commercially funded # sequencing, without written permission from the author and the # University of Washington. # # This software is provided ``AS IS'' and any express or implied # warranties, including, but not limited to, the implied warranties of # merchantability and fitness for a particular purpose, are disclaimed. # In no event shall the authors or the University of Washington be # liable for any direct, indirect, incidental, special, exemplary, or # consequential damages (including, but not limited to, procurement of # substitute goods or services; loss of use, data, or profits; or # business interruption) however caused and on any theory of liability, # whether in contract, strict liability, or tort (including negligence # or otherwise) arising in any way out of the use of this software, even # if advised of the possibility of such damage. # # Building Consed from source is error prone and not simple which is # why I provide executables. Due to time limitations I cannot # provide any assistance in building Consed. Even if you do not # modify the source, you may introduce errors due to using a # different version of the compiler, a different version of motif, # different versions of other libraries than I used, etc. For this # reason, if you discover Consed bugs, I can only offer help with # those bugs if you first reproduce those bugs with an executable # provided by me--not an executable you have built. # # Modifying Consed is also difficult. Although Consed is modular, # some modules are used by many other modules. Thus making a change # in one place can have unforeseen effects on many other features. # It may takes months for you to notice these other side-effects # which may not seen connected at all. It is not feasable for me to # provide help with modifying Consed sources because of the # potentially huge amount of time involved. # #*****************************************************************************/ // // guiapp.cpp // // implementation for guiapp.h // // #include #include #include #include #include #include "guiapp.h" #include "assert.h" #include "colorDefaults.h" #include "guiTopWindow.h" #include "consedParameters.h" #include "tagTypes.h" #include "consed.h" #include "nPrimerFalseMatchScoreArray.h" #include "popupInfoOrErrorMessageNoFormat.h" #include "decisionbox.h" #include "fileselector.h" #include "consedResources.h" #include "guitedwin.h" #include "bGuiGetAnswerYesNo.h" #include "colormode.h" #include "hp_exception_kludge.h" // // static class members // GuiApp* GuiApp::pGlobalGuiApp_ = 0; bool GuiApp::bGuiAppCreated_ = false; // specifies the fallback (i.e. default) values // of these resources for this application static String aszFallbackResources[] = { // "system" font, used on labels, buttons, menus, etc. // "consed*fontList: helvetica", // drawing font used in contigwin "consed*font: -misc-fixed-medium-r-normal--15-140-75-75-c-90-iso8859-1", "consed*fontList: -misc-fixed-bold-r-normal--13-100-100-100-c-70-iso8859-1", "consed*foreground: Black", // colors and shadows // "consed*troughColor: Grey45", "consed*troughColor: Black", "consed*background: Grey77", "consed*topShadowColor: Grey88", "consed*bottomShadowColor: Grey45", "consed*shadowThickness: 2", // these need to be reversed appearance consistent with diboxes, etc. "consed*mainwin.topShadowColor: Grey45", "consed*mainwin.bottomShadowColor: Grey88", // colors in trace window "consed*scaleDrawingArea.background: black", "consed*consensusDrawingArea.background: black", "consed*editableBasesDrawingArea.background: black", "consed*tagsDrawingArea.background: black", "consed*phredCalledBasesDrawingArea.background: black", "consed*ABICalledBasesDrawingArea.background: black", "consed*tracesDrawingArea.background: black", // "consed*assemblyView*assemblyViewDrawingArea.background: white", // time in milliseconds--very long time for recognizing double clicks "consed*doubleClickInterval: 400", // "consed*contigwin.background: Black", // "consed*scaleNumbers.foreground: Yellow", // "consed*scaleGraphics.foreground: Yellow", // scale widgets require messing with for some obscure reason "consed*verticalScale.height: 18", "consed*horizontalScale.height: 18", // not sure this belongs here, but users will probably want // to mess with these ranges and defaults "consed*verticalScale.value: 100", "consed*verticalScale.maximum: 400", "consed*verticalScale.minimum: 1", "consed*horizontalScale.value: 10", "consed*horizontalScale.maximum: 50", "consed*horizontalScale.minimum: 3", // infobuttons are used to display current filename, fragment, etc. // pressing (usually) them supplies more info // "consed*infobutton.fontList: helvetica", // "consed*textfield.fontList: helvetica", "consed*textfield.background: Grey70", // for textbox object "consed*textBox.fontList: -misc-fixed-medium-r-normal--15-140-75-75-c-90-iso8859-1", "consed*navtextfield*fontList: -misc-fixed-medium-r-normal--15-140-75-75-c-90-iso8859-1", "consed*navigator*fontList: -misc-fixed-medium-r-normal--15-140-75-75-c-90-iso8859-1", "consed.title: Consed Main Window", //FOR COPIES //"consed*scaleDrawingArea.background: grey70", //"consed*consensusDrawingArea.background: grey70", // "consed*editableBasesDrawingArea.background: grey70", // "consed*tagsDrawingArea.background: grey70", // "consed*phredCalledBasesDrawingArea.background: grey70", // "consed*ABICalledBasesDrawingArea.background: grey70", // "consed*tracesDrawingArea.background: grey70", // "consed*contigwin.background: grey70", // "consed*scaleNumbers.foreground: grey70", // "consed*scaleGraphics.foreground: grey70", "consed*contigwin.background: black", "consed*scaleNumbers.foreground: black", "consed*scaleGraphics.foreground: black", NULL // list is null-terminated }; // struct into which returned application resources // will be written typedef struct { XFontStruct *pFont; // The font struct } AppDataType, *AppDataPtrType; AppDataType appData; // specifies the list of resources to be returned by // the call to XtGetApplicationResources static XtResource appResources[] = { { XtNfont, XtCFont, XtRFontStruct, sizeof( XFontStruct *), XtOffset(AppDataPtrType, pFont), XtRString, (char*) "" } }; int nErrorHandler( Display* pDisplay, XErrorEvent* pErrorEvent ) { assert( false ); return( 1 ); } void GuiApp :: maybeSetXKeySymDB() { #ifdef LINUX_COMPILE char* szXKeySymDB = getenv( "XKEYSYMDB" ); if ( szXKeySymDB ) { fprintf( stderr, "XKEYSYMDB is already set to %s so not setting it again--that's ok\n", szXKeySymDB ); return; } FileName filXKeySymDBPath; if ( pCP->filMaybeXKEYSYMDBPath_.bFileByThisNameExists() ) filXKeySymDBPath = pCP->filMaybeXKEYSYMDBPath_; else if ( pCP->filMaybeXKEYSYMDBPath2_.bFileByThisNameExists() ) filXKeySymDBPath = pCP->filMaybeXKEYSYMDBPath2_; else { fprintf( stderr, "not setting XKEYSYMDB. This is ok if you don't get any errors saying something about \"Warning: translation table...\"" ); fflush( stderr ); return; } // fprintf( stderr, "setting XKEYSYMBDB to %s\n", filXKeySymDBPath.data() ); // the 1 means to overwrite assert( setenv( "XKEYSYMDB", filXKeySymDBPath.data(), 1 ) == 0 ); // check that it was set char* szXKeySymDB2 = getenv( "XKEYSYMDB" ); if ( szXKeySymDB2 ) { RWCString soTemp( szXKeySymDB2 ); // fprintf( stderr, "set XKEYSYMDB to %s\n", szXKeySymDB2 ); // fflush( stderr ); } else { fprintf( stderr, "tried but failed to set XKEYSYMDB" ); fflush( stderr ); } #endif } GuiApp :: GuiApp(const char* szName, int argc, char* argv[], const bool bTopWindow ) { // // fail crudely if one already exists - we may not have // a gui at all yet // if (bGuiAppCreated_) { cerr << "Fatal program error: GuiApp ctor called twice." << endl; cerr.flush(); exit(-1); } // flag true forever bGuiAppCreated_ = true; // save ptr to self in static global member pGlobalGuiApp_ = this; // only do this for linux #ifdef LINUX_COMPILE maybeSetXKeySymDB(); #endif // // create the toplevel widget // widTopLevel_ = XtAppInitialize(&ctxAppContext_, szName, NULL, 0, (int *)&argc, argv, aszFallbackResources, NULL, (Cardinal )0); // XSetErrorHandler( nErrorHandler ); Arg aArg[20]; int nArgs; nArgs = 0; XtSetArg( aArg[nArgs], XmNallowShellResize, True ); nArgs++; XtSetValues( widTopLevel_, aArg, nArgs ); // // pick up the application resources // XtGetApplicationResources( widTopLevel_, &appData, appResources, XtNumber(appResources), NULL, (Cardinal) 0 ); bool bEnoughRoomInColormap = true; saveColors( bEnoughRoomInColormap ); if (!bEnoughRoomInColormap) { cout << "There is some other application that is a color hog." << endl; cout << "It might be netscape" << endl; cout << "Consed can continue, but will use its own colormap" << endl; cout << "which will cause some flashing when moving the mouse" << endl; cout << "between different windows. If you don't like this, " << endl; cout << "you should restart netscape as netscape -install " << endl; cout << "and then restart consed." << endl; } setUpColormap( bEnoughRoomInColormap ); // // save a copy of the font struct as private data // pXfsDrawFont_ = appData.pFont; // // calculate some font information // // here's a text containing most of what we care about char* szSampleFragment = "gg**aaccttAGAACATGCTCCTTTAGCTC**GGAGAAGTTTGTTATTACG"; int nDir; int nAscent; int nDescent; XCharStruct xCharStruct; XTextExtents(appData.pFont, szSampleFragment, strlen(szSampleFragment), &nDir, &nAscent, &nDescent, &xCharStruct); nFontAscent_ = nAscent; nFontHeight_ = nAscent + nDescent; nFontDescent_ = nDescent; nFontWidth_ = xCharStruct.width / strlen( szSampleFragment ); nFontLBearing_ = xCharStruct.lbearing; nFontRBearing_ = xCharStruct.rbearing - ( nFontWidth_ * (strlen( szSampleFragment ) - 1 ) ); xmFontList_ = XmFontListCreate( pXfsDrawFont_, XmSTRING_DEFAULT_CHARSET ); if ( bTopWindow ) { pGuiTopWindow_ = new guiTopWindow(); } } void GuiApp :: makeVisible() { XtRealizeWidget(widTopLevel_); // set initial input focus to first read name box // why isn't this done in guiTopWindow ctor? Because it only works // after the XtRealizeWidget above XmProcessTraversal( pGuiTopWindow_->widReadWithAsterisks_, XmTRAVERSE_CURRENT ); // unmap doesn't keep the brick unmapped when a dialog pops up // XtUnmapWidget( widTopLevel_ ); // iconify iconifies all dialogs, too, so users can't see them // XIconifyWindow( XtDisplay( widTopLevel_ ), XtWindow( widTopLevel_ ), // 0 ); XtVaSetValues( widTopLevel_, XmNcolormap, cmap_, NULL ); Display* pDisplay = XtDisplay( widTopLevel_ ); XSetWindowColormap( pDisplay, XtWindow( widTopLevel_ ), cmap_ ); } // This macro makes saveColorAndCheckColorMap( ColorHighlightBackground ) // // into: // // ColorDefaults::pGetColorDefaults()->soColorHighlightBackground_ = // appData.szColorHighlightBackground; // // if (bEnoughRoomInColormap) { // int nStatus = XAllocNamedColor( pDisplay, // colormap, // soColorHighlightBackground_, // &xcolor, // &xcolorHardware ); // if (nStatus != 1 ) // bEnoughRoomInColormap = false; // } #define saveColorAndCheckColormap( ColorName ) \ \ ColorDefaults::pGetColorDefaults()->so ## ColorName ## _ = \ consedResources::pCurrentResources_->so ## ColorName ## _; \ if (bEnoughRoomInColormap) { \ int nStatus = XAllocNamedColor( \ pDisplay, \ cmapDefault, \ ColorDefaults::pGetColorDefaults()->so ## ColorName ## _, \ &xcolor, \ &xcolorHardware ); \ \ if (nStatus != 1 ) \ bEnoughRoomInColormap = false; \ } void GuiApp :: saveColors( bool& bEnoughRoomInColormap ) { ColorDefaults* pTempColorDefaults = new ColorDefaults(); Display* pDisplay = XtDisplay( widTopLevel_ ); int nScreen = DefaultScreen(pDisplay); Colormap cmapDefault = DefaultColormap( pDisplay, nScreen); XColor xcolor; XColor xcolorHardware; bEnoughRoomInColormap = true; #include "saveColors.cpp.part2" // now try to check for some other colors used by Motif justCheckColormap( "Grey77", bEnoughRoomInColormap ); justCheckColormap( "Grey88", bEnoughRoomInColormap ); justCheckColormap( "Grey45", bEnoughRoomInColormap ); justCheckColormap( "Black", bEnoughRoomInColormap ); // These are just to make sure there is enough room for the // the user to customize his colors. justCheckColormap( "seashell", bEnoughRoomInColormap ); justCheckColormap( "honeydew", bEnoughRoomInColormap ); justCheckColormap( "mint cream", bEnoughRoomInColormap ); justCheckColormap( "navy blue", bEnoughRoomInColormap ); justCheckColormap( "coral", bEnoughRoomInColormap ); justCheckColormap( "RosyBrown", bEnoughRoomInColormap ); justCheckColormap( "dark salmon", bEnoughRoomInColormap ); justCheckColormap( "SlateGray3", bEnoughRoomInColormap ); pColorOfRestrictionFragmentPairTooFarApart_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorRestrictionFragmentPairTooFarApart_, "black" ); pColorOfUnmatchedRestrictionFragment_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorUnmatchedRestrictionFragment_, "black" ); pColorOfRestrictionFragmentInContig_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorRestrictionFragmentInContig_, "black" ); // I don't see this being using for anything, so // I'm not making it configurable pColorOfRestrictionFragmentPartlyOffContig_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorRestrictionFragmentPartlyOffContig_, "black" ); pColorOfRestrictionFragmentEntirelyOffContig_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorRestrictionFragmentEntirelyOffContig_, "black" ); pColorOfActualGelRestrictionFragment_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorActualGelRestrictionFragment_, "black" ); pColorOfRestrictionDigestScale_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorRestrictionDigestScale_, "black" ); pColorOfRestrictionDigestCursorIndicator_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorRestrictionDigestCursorIndicator_, "black" ); pColorOfRestrictionFragmentsOnTopOfEachOther_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorRestrictionFragmentsOnTopOfEachOther_, "black" ); pColorReadPrefixDefault_ = new GuiColorText( ColorDefaults::pGetColorDefaults()->soColorReadPrefixDefault_, "white" ); pColorMeansMatch_ = new ColorMeansMatch( ); pColorMeansQuality_ = new ColorMeansQuality( ); pColorMeansEdited_ = new ColorMeansEdited( ); pColorMeansQualityAndTags_ = new ColorMeansQualityAndTags( ); pColorMeansEditedAndTags_ = new ColorMeansEditedAndTags( ); } void GuiApp :: getFallbackResources( RWCString& soFallbackResources ) { soFallbackResources = ""; bool bFirstTime = true; int n = 0; while( aszFallbackResources[n] != NULL ) { if (bFirstTime) bFirstTime = false; else soFallbackResources += "\n"; soFallbackResources += aszFallbackResources[n]; ++n; } } void GuiApp :: mainLoop() { XEvent xevent; for(;;) { XtAppNextEvent( ctxAppContext_, &xevent ); XtDispatchEvent( &xevent ); // removed this. Otherwise on Gnome the popup windows would // often be grey with no text. // if ( (xevent.type == Expose ) && ( xevent.xexpose.count > 0 ) ) { // cerr << "ignoring expose event at " << time( NULL ) << endl; // } // else } } //////////////////////////////////////////////////////////// // // PURPOSE: error message // // HOW TO USE IT: Just like printf // // // INPUTS: a format string and arguments // // REV: (David Gordon) May 1995 // //////////////////////////////////////////////////////////// // this is in the guiapp namespace void GuiApp :: popupErrorMessage( const char *szErrorFormat, ... ) { char szErrorMessage[10000]; va_list args; va_start(args, szErrorFormat); vsprintf( szErrorMessage, szErrorFormat, args ); va_end(args); popupInfoOrErrorMessageNoFormat( NULL, // shell of parent true, // error message not info szErrorMessage ); } // variant for infobox void GuiApp :: popupInfoMessage( const char *szErrorFormat, ... ) { char szErrorMessage[10000]; va_list args; va_start(args, szErrorFormat); vsprintf( szErrorMessage, szErrorFormat, args ); va_end(args); if ( !consedParameters::pGetConsedParameters()->bOKToUseGui_ ) return; popupInfoOrErrorMessageNoFormat( NULL, // shell of parent false, // bErrorNotInfoMessage szErrorMessage ); } char cbSelectionConversion( Widget wid, Atom* pSelection, Atom* pTarget, Atom* pReturnType, XtPointer* pValue, unsigned long* pLength, int* pFormat ) { Atom COMPOUND_TEXT = XmInternAtom( XtDisplay( wid), "COMPOUND_TEXT", False ); Atom TARGETS = XmInternAtom( XtDisplay( wid ), "TARGETS", False ); XSelectionRequestEvent *pEvent = XtGetSelectionRequest( wid, *pSelection, (XtRequestId) NULL ); if ( *pTarget == XA_STRING ) { char **pszValue; XTextProperty xprop; int status = 0; XmString *xmsSelectedItems; int nSelectedCount = 1; int i; pszValue = (char**) XtMalloc( ( nSelectedCount + 1) * sizeof( char* ) ); pszValue[0] = (char*) GuiApp:: pGetGuiApp()->soSelectedBasesForPasting_.data(); pszValue[1] = NULL; status = XmbTextListToTextProperty( XtDisplay( wid ), pszValue, nSelectedCount, (XICCEncodingStyle) XStringStyle, &xprop ); if (status == Success || status > 0 ) { *pReturnType = XA_STRING; *pFormat = 8; *pValue = (XtPointer) XtMalloc( (unsigned) xprop.nitems ); memcpy( (void*) *pValue, (void*) xprop.value, (unsigned) xprop.nitems); XFree( (char*) xprop.value ); *pLength = xprop.nitems; return True; } else { return False; } } else if ( *pTarget == TARGETS ) { Atom *pTargets; *pLength = 2; *pValue = (XtPointer)XtMalloc( sizeof(Atom) * (*pLength) ); pTargets = *(Atom**) pValue; *pTargets++ = TARGETS; *pTargets++ = XA_STRING; *pReturnType = XA_ATOM; *pFormat = 32; return True; } else return False; } void cbLoseSelectionOwnership( Widget wid, Atom *pSelection ) { } void GuiApp :: makeSelectionForPasting( const RWCString& soBasesToPaste ) { soSelectedBasesForPasting_ = soBasesToPaste; Time time2 = XtLastTimestampProcessed( XtDisplay( widTopLevel_ ) ); bool b = XtOwnSelection( widTopLevel_, XA_PRIMARY, time2, cbSelectionConversion, cbLoseSelectionOwnership, NULL ); if ( !b ) { cerr << "Warning--didn't get selection so cut/paste may not have worked\nPlease try again" << endl; } } void GuiApp :: setUpColormap( const bool bEnoughRoomInColormap ) { Display* pDisplay = XtDisplay( widTopLevel_ ); int nScreen = DefaultScreen(pDisplay); if ( bEnoughRoomInColormap ) { cmap_ = DefaultColormap( pDisplay, nScreen); } else { Window winRoot = DefaultRootWindow( pDisplay ); cmap_ = XCreateColormap( pDisplay, winRoot, DefaultVisual( pDisplay, DefaultScreen( pDisplay )), AllocNone ); XtVaSetValues( widTopLevel_, XmNcolormap, cmap_, NULL ); copyABunchOfColormapCells(); } } void GuiApp :: copyABunchOfColormapCells() { Display* pDisplay = XtDisplay( widTopLevel_ ); int nScreen = DefaultScreen(pDisplay); Colormap cmapDefault = DefaultColormap( pDisplay, nScreen); const int nNumberOfColorCellsToCopy = 100; for( int nCell = 0; nCell < nNumberOfColorCellsToCopy; ++nCell ) { XColor xc; xc.pixel = nCell; XQueryColor( pDisplay, cmapDefault, &xc ); XAllocColor( pDisplay, cmap_, &xc ); } } void GuiApp :: justCheckColormap( char* szColorName, bool& bEnoughRoomInColormap ) { if (bEnoughRoomInColormap) { Display* pDisplay = XtDisplay( widTopLevel_ ); int nScreen = DefaultScreen(pDisplay); Colormap cmapDefault = DefaultColormap( pDisplay, nScreen); XColor xcolor; XColor xcolorHardware; int nStatus = XAllocNamedColor( pDisplay, cmapDefault, szColorName, &xcolor, &xcolorHardware ); if (nStatus != 1 ) bEnoughRoomInColormap = false; else { unsigned long pixels[1]; pixels[0] = xcolorHardware.pixel; XFreeColors( pDisplay, cmapDefault, pixels, 1, // # of colors to free 0 // # of planes ); } } } //////////////////////////////////////////////////////////// // // PURPOSE: To force the user to acknowledge a question // and respond before the program continues. // (It does not prevent the user from using other // applications!) // // HOW TO USE IT: Just like printf // // // INPUTS: a format string and arguments // RETURNS: boolean true user pressed "OK", false otherwise // // REV: (David Gordon) May 1995 // now uses DecisionBox object. chrisa 17-may-95 // wish it didn't (DG) // //////////////////////////////////////////////////////////// // this is in the guiapp namespace bool GuiApp::popupDecisionMessage( const char *szErrorFormat, ... ) { char szDecisionMessage[10000]; va_list args; va_start(args, szErrorFormat); vsprintf( szDecisionMessage, szErrorFormat, args ); va_end(args); DecisionBox db(szDecisionMessage); db.makeVisible(); // blocks here till user acks return db.bUserPressedOk(); } // wrapper in the GuiApp namespace FileName GuiApp::popupFileSelector(const char* szTitle, const char* szDirMask, const char* szFileName) { FileSelector fs; return fs.popUpAndGetFilePath(szTitle, szDirMask, szFileName); } void GuiApp :: findTopWindow() { // removed Oct 2008 because UWGC has XWin32 on multiple window // causes window manager handle to be removed so the window // can't be moved // XtUnmapWidget( widTopLevel_ ); XtMapWidget( widTopLevel_ ); XRaiseWindow( XtDisplay( widTopLevel_ ), XtWindow( widTopLevel_ ) ); } void GuiApp :: changeDefaultToLightBackground() { Display* pDisplay = XtDisplay( widTopLevel_ ); XrmDatabase xrmdb = XrmGetDatabase( pDisplay ); XrmPutLineResource( &xrmdb, "consed*contigwin.background: black" ); XrmPutLineResource( &xrmdb, "consed*scaleDrawingArea.background: grey70" ); XrmPutLineResource( &xrmdb, "consed*consensusDrawingArea.background: grey70" ); XrmPutLineResource( &xrmdb, "consed*editableBasesDrawingArea.background: grey70" ); XrmPutLineResource( &xrmdb, "consed*tagsDrawingArea.background: grey70" ); XrmPutLineResource( &xrmdb, "consed*phredCalledBasesDrawingArea.background: grey70" ); XrmPutLineResource( &xrmdb, "consed*ABICalledBasesDrawingArea.background: grey70" ); XrmPutLineResource( &xrmdb, "consed*tracesDrawingArea.background: grey70" ); XrmPutLineResource( &xrmdb, "consed*contigwin.background: grey70" ); XrmPutLineResource( &xrmdb, "consed*scaleNumbers.foreground: grey70" ); XrmPutLineResource( &xrmdb, "consed*scaleGraphics.foreground: grey70" ); ColorDefaults::pGetColorDefaults()->soColorTracesA_ = "chartreuse"; ColorDefaults::pGetColorDefaults()->soColorTracesC_ = "royal blue"; ColorDefaults::pGetColorDefaults()->soColorTracesG_ = "Black"; ColorDefaults::pGetColorDefaults()->soColorTracesT_ = "Red"; ColorDefaults::pGetColorDefaults()->soColorSequencingDirectionArrow_ = "Blue"; ColorDefaults::pGetColorDefaults()->soColorConsensusLabel_ = "Blue"; ColorDefaults::pGetColorDefaults()->soColorConsensusLabelBackground_ = "Grey70"; ColorDefaults::pGetColorDefaults()->soColorScale_ = "Black"; ColorDefaults::pGetColorDefaults()->soColorScaleBackground_ = "Grey70"; GuiTedWin::allocateColors(); GuiTedWin::pGuiColorTextA_->changeLineWidth( 3 ); GuiTedWin::pGuiColorTextC_->changeLineWidth( 3 ); GuiTedWin::pGuiColorTextG_->changeLineWidth( 3 ); GuiTedWin::pGuiColorTextT_->changeLineWidth( 3 ); } void GuiApp :: printWindow( ) { bGuiGetAnswerYesNo( pCP->soPrintWindowInstructions_.data() ); int nReturnStatus = system( pCP->soPrintWindowCommand_.data() ); if ( nReturnStatus != 0 ) { char* szErrorMessage = strerror( nReturnStatus ); if ( szErrorMessage ) { popupErrorMessage( "Something went wrong running %s. Gave error code %d which means %s", pCP->soPrintWindowCommand_.data(), nReturnStatus, szErrorMessage ); } else { popupErrorMessage( "Something went wrong running %s. Gave error code %d. See xterm for more details", pCP->soPrintWindowCommand_.data(), nReturnStatus ); } } } bool GuiApp :: bGetGuiColorTextForReadPrefixByColor( GuiColorText*& pGuiColorText, const RWCString& soForegroundColor ) { RWCString soColorToFind = soForegroundColor; soColorToFind.toLower(); for( int nColor = 0; nColor < aColorNamesForReadPrefixes_.length(); ++nColor ) { if ( soColorToFind == aColorNamesForReadPrefixes_[ nColor ] ) { pGuiColorText = aGuiColorTextForReadPrefixes_[ nColor ]; return( true ); } } return( false ); } GuiColorText* GuiApp :: pGetGuiColorTextForReadPrefixColor( const RWCString& soForegroundColor ) { GuiColorText* pGuiColorText = NULL; if ( bGetGuiColorTextForReadPrefixByColor( pGuiColorText, soForegroundColor ) ) return( pGuiColorText ); RWCString soColor = soForegroundColor; soColor.toLower(); pGuiColorText = new GuiColorText( soColor, "white" ); aGuiColorTextForReadPrefixes_.insert( pGuiColorText ); aColorNamesForReadPrefixes_.insert( soColor ); return( pGuiColorText ); } // // cursor blink interval, in milliseconds // static const int nBlinkOnInterval = 900; // a slow 4/4 time... static const int nBlinkOffInterval = 100; void xtBlinkCallback(XtPointer clientData, // params ignored XtIntervalId* pId) { TRY_CATCH_WRAPPER( GuiApp::pGetGuiApp()->blinkAgain() ); } void GuiApp :: blinkAgain() { // toggle the blink state bBlinkState_ = ! bBlinkState_; // reset the timer XtAppAddTimeOut( ctxGetAppContext(), ( bBlinkState_ ? nBlinkOnInterval : nBlinkOffInterval ), xtBlinkCallback, 0); // no user data needed ConsEd::pGetConsEd()->blinkAllCursors( bBlinkState_ ); } void GuiApp :: startBlinking() { bBlinkState_ = false; XtAppAddTimeOut( ctxGetAppContext(), nBlinkOnInterval, xtBlinkCallback, 0 ); // no user data needed }