/* * CDE - Common Desktop Environment * * Copyright (c) 1993-2012, The Open Group. All rights reserved. * * These libraries and programs are free software; you can * redistribute them and/or modify them under the terms of the GNU * Lesser General Public License as published by the Free Software * Foundation; either version 2 of the License, or (at your option) * any later version. * * These libraries and programs are distributed in the hope that * they will be useful, but WITHOUT ANY WARRANTY; without even the * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR * PURPOSE. See the GNU Lesser General Public License for more * details. * * You should have received a copy of the GNU Lesser General Public * License along with these libraries and programs; if not, write * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth * Floor, Boston, MA 02110-1301 USA */ /* $XConsortium: HelpDialog.c /main/16 1996/11/22 12:24:49 cde-hp $ */ /************************************<+>************************************* **************************************************************************** ** ** File: HelpDialog.c ** ** Project: Cde Help 1.0 Project ** ** Description: ** ** (c) Copyright 1987, 1988, 1989, 1990, 1991, 1992 Hewlett-Packard Company ** ** (c) Copyright 1993, 1994 Hewlett-Packard Company ** (c) Copyright 1993, 1994 International Business Machines Corp. ** (c) Copyright 1993, 1994 Sun Microsystems, Inc. ** (c) Copyright 1993, 1994 Novell, Inc. ** **************************************************************************** ************************************<+>*************************************/ #include #include #include /* R_OK */ #include #include #include /* These includes work in R4 and R5 */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include /* Copied from Xm/GeoUtilsI.h */ extern XmGeoMatrix _XmGeoMatrixAlloc( unsigned int numRows, unsigned int numBoxes, unsigned int extSize) ; /* Canvas Engine */ #include "CanvasP.h" /* for AccessI.h */ /* Help Dialog Widget Includes */ #include "Access.h" #include "bufioI.h" #include "AccessI.h" #include "ActionsI.h" #include "DisplayAreaI.h" #include "DisplayAreaP.h" #include
#include "HelpI.h" #include "HelpP.h" #include "StringFuncsI.h" #include "HelposI.h" #include "HelpDialog.h" #include "HelpDialogI.h" #include "HelpDialogP.h" #include "HistoryI.h" #include "HelpUtilI.h" #include "PathAreaI.h" #include "HelpAccessI.h" #include "HourGlassI.h" #include "HyperTextI.h" #include "FileUtilsI.h" #include "Lock.h" /* search dialogs */ #include "GlobSearchI.h" /* print dialogs */ #include "PrintI.h" /* Error Messages Includes */ #include "MessagesP.h" /* Quick Help Widget Inlcudes */ #include "HelpQuickD.h" /* Display Area Includes */ #include "XUICreateI.h" #include "CallbacksI.h" #include "DestroyI.h" #include "FormatI.h" #include "FormatManI.h" #include "SetListI.h" #include "ResizeI.h" /*********** Global Variables **********/ /******** Messages *********/ /* Help Dialog Error message Defines */ #define HDMessage0 _DtHelpMsg_0000 #define HDMessage1 _DtHelpMsg_0001 #define HDMessage2 _DtHelpMsg_0002 #define HDMessage3 _DtHelpMsg_0003 #define HDMessage4 _DtHelpMsg_0004 #define HDMessage5 _DtHelpMsg_0005 #define HDMessage6 _DtHelpMsg_0006 #define HDMessage7 _DtHelpMsg_0007 #define HDMessage8 _DtHelpMsg_0008 #define HDMessage9 _DtHelpMsg_0009 /******** Static Function Declarations ********/ static void NavigationTypeDefault( Widget widget, int offset, XrmValue *value) ; static void ClassPartInitialize( WidgetClass wc) ; static void ClassInitialize( void) ; static void Initialize( Widget rw, Widget nw, ArgList args, Cardinal *num_args); static void Destroy( Widget w ); static Boolean SetValues( Widget cw, Widget rw, Widget nw, ArgList args, Cardinal *num_args); static void CloseHelpCB ( Widget w, XtPointer clientData, XtPointer callData); static void BuildDisplayArea( Widget parent, DtHelpDialogWidget nw); static void ProcessJumpBack( DtHelpDialogWidget nw); static void VariableInitialize( DtHelpDialogWidget nw); static void CleanUpHelpDialog( Widget nw, int cleanUpKind); static void CatchClose(Widget widget); static void DisplayTopLevelCB( Widget w, XtPointer client_data, XtPointer call_data ); static void CopyTextCB( Widget w, XtPointer clientData, XtPointer callData ); static void DisplayPrintCB( Widget w, XtPointer client_data, XtPointer call_data ); static void ProcessBMenuBackCB( Widget w, XtPointer clientData, XButtonEvent * event, Boolean *continueToDispatch); static void ProcessJumpReuse( Widget nw, DtHelpHyperTextStruct *hyperData); static Widget SetupHelpDialogMenus( Widget parent); static Widget CreatePopupMenu( Widget parent); static void ResizeHelpDialogCB ( XtPointer clientData); static void InitialPopupCB( Widget w, XtPointer clientData, XtPointer callData); /******** End Static Function Declarations ********/ /* Static variables */ /* Supported resources for the HelpDialog Widget */ static XtResource resources[] = { { DtNshowNewWindowButton, DtCShowNewWindowButton, XmRBoolean, sizeof(Boolean), XtOffset (DtHelpDialogWidget, help_dialog.menu.showDupBtn), XmRImmediate, (XtPointer) False }, { DtNshowTopLevelButton, DtCShowTopLevelButton, XmRBoolean, sizeof(Boolean), XtOffset (DtHelpDialogWidget, help_dialog.browser.showTopLevelBtn), XmRImmediate, (XtPointer) False }, { DtNscrollBarPolicy, DtCScrollBarPolicy, DtRDtScrollBarPolicy, sizeof (unsigned char), XtOffset (DtHelpDialogWidget, help_dialog.display.scrollBarPolicy), XmRImmediate, (XtPointer) DtHELP_AS_NEEDED_SCROLLBARS }, { DtNexecutionPolicy, DtCExecutionPolicy, DtRDtExecutionPolicy, sizeof (unsigned char), XtOffset (DtHelpDialogWidget, help_dialog.display.executionPolicy), XmRImmediate, (XtPointer) DtHELP_EXECUTE_QUERY_UNALIASED }, { DtNcolumns, DtCColumns, XmRShort, sizeof(short), XtOffset (DtHelpDialogWidget, help_dialog.display.textColumns), XmRImmediate, (XtPointer) 70 }, { DtNrows, DtCRows, XmRShort, sizeof(short), XtOffset (DtHelpDialogWidget, help_dialog.display.textRows), XmRImmediate, (XtPointer) 25 }, { DtNmarginWidth, DtCMarginWidth, XmRHorizontalDimension, sizeof (Dimension), XtOffset (DtHelpDialogWidget, help_dialog.ghelp.marginWidth), XmRImmediate, (XtPointer) 1 }, { DtNmarginHeight, DtCMarginHeight, XmRVerticalDimension, sizeof (Dimension), XtOffset (DtHelpDialogWidget, help_dialog.ghelp.marginHeight), XmRImmediate, (XtPointer) 4 }, { DtNvisiblePathCount, DtCVisiblePathCount, XmRInt, sizeof(int), XtOffset (DtHelpDialogWidget, help_dialog.browser.visiblePathCount), XmRImmediate, (XtPointer) 7 }, { DtNlocationId, DtCLocationId, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.display.locationId), XmRImmediate, (XtPointer) _DtHelpDefaultLocationId }, { DtNhelpPrint, DtCHelpPrint, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.print.helpPrint), XmRImmediate, (XtPointer) _DtHelpDefaultHelpPrint }, { DtNprinter, DtCPrinter, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.print.printer), XmRImmediate, (XtPointer) NULL }, { DtNpaperSize, DtCPaperSize, DtRDtPaperSize, sizeof (unsigned char), XtOffset (DtHelpDialogWidget, help_dialog.print.paperSize), XmRImmediate, (XtPointer) DtHELP_PAPERSIZE_LETTER }, { DtNsrchHitPrefixFont, DtCSrchHitPrefixFont, XmRString, sizeof (char *), XtOffset (DtHelpDialogWidget, help_dialog.srch.hitPrefixFont), XmRImmediate, (XtPointer) _DtHelpDefaultSrchHitPrefixFont }, { DtNhelpVolume, DtCHelpVolume, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.display.helpVolume), XmRImmediate, (XtPointer) NULL }, { DtNmanPage, DtCManPage, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.display.manPage), XmRImmediate, (XtPointer) NULL }, { DtNstringData, DtCStringData, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.display.stringData), XmRImmediate, (XtPointer) NULL }, { DtNhelpFile, DtCHelpFile, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.display.helpFile), XmRImmediate, (XtPointer) NULL }, { DtNtopicTitle, DtCTopicTitle, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.display.topicTitleStr), XmRImmediate, (XtPointer) NULL }, { DtNhelpOnHelpVolume, DtCHelpOnHelpVolume, XmRString, sizeof (char*), XtOffset (DtHelpDialogWidget, help_dialog.help.helpOnHelpVolume), XmRImmediate, (XtPointer) _DtHelpDefaultHelp4HelpVolume }, { DtNhelpType, DtCHelpType, DtRDtHelpType, sizeof(unsigned char), XtOffset (DtHelpDialogWidget, help_dialog.display.helpType), XmRImmediate, (XtPointer) DtHELP_TYPE_TOPIC }, { DtNhyperLinkCallback, DtCHyperLinkCallback, XmRCallback, sizeof (XtCallbackList), XtOffset (DtHelpDialogWidget, help_dialog.display.hyperLinkCallback), XmRImmediate, (XtPointer) NULL }, { DtNcloseCallback, DtCCloseCallback, XmRCallback, sizeof (XtCallbackList), XtOffset (DtHelpDialogWidget, help_dialog.ghelp.closeCallback), XmRImmediate, (XtPointer) NULL }, { XmNnavigationType, XmCNavigationType, XmRNavigationType, sizeof(unsigned char), XtOffsetOf (XmManagerRec, manager.navigation_type), XmRCallProc, (XtPointer) NavigationTypeDefault }, }; /* * attach the action list to the widget. Then it does not * matter which Xt[App]Initialize an application does. */ static XtActionsRec DrawnBActions[] = { {"DeSelectAll" , _DtHelpDeSelectAll }, {"SelectAll" , _DtHelpSelectAll }, {"ActivateLink" , _DtHelpActivateLink }, {"CopyToClipboard", _DtHelpCopyAction }, {"PageUpOrDown" , _DtHelpPageUpOrDown }, {"PageLeftOrRight", _DtHelpPageLeftOrRight}, {"NextLink" , _DtHelpNextLink } }; /**************************************************************** * * Full class record constant * ****************************************************************/ externaldef( dthelpdialogwidgetclassrec) DtHelpDialogWidgetClassRec dtHelpDialogWidgetClassRec = { { /* core_class fields */ (WidgetClass) &xmBulletinBoardClassRec, /* superclass */ "DtHelpDialog", /* class_name */ sizeof(DtHelpDialogWidgetRec), /* widget_size */ ClassInitialize, /* class_initialize */ ClassPartInitialize, /* class_part_init */ FALSE, /* class_inited */ Initialize, /* initialize */ NULL, /* initialize_hook */ XtInheritRealize, /* realize */ DrawnBActions, /* actions */ XtNumber(DrawnBActions), /* num_actions */ resources, /* resources */ XtNumber(resources), /* num_resources */ NULLQUARK, /* xrm_class */ TRUE, /* compress_motion */ XtExposeCompressMaximal, /* compress_exposure */ FALSE, /* compress_enterlv */ FALSE, /* visible_interest */ Destroy, /* destroy */ XtInheritResize, /* resize */ XtInheritExpose, /* expose */ SetValues, /* set_values */ NULL, /* set_values_hook */ XtInheritSetValuesAlmost, /* set_values_almost */ NULL, /* get_values_hook */ XtInheritAcceptFocus, /* enter_focus */ XtVersion, /* version */ NULL, /* callback_private */ XtInheritTranslations, /* tm_table */ XtInheritQueryGeometry, /* query_geometry */ NULL, /* display_accelerator*/ NULL, /* extension */ }, { /* composite_class fields */ XtInheritGeometryManager, /* geometry_manager */ XtInheritChangeManaged, /* change_managed */ XtInheritInsertChild, /* insert_child */ XtInheritDeleteChild, /* delete_child */ NULL, /* extension */ }, { /* constraint_class fields */ NULL, /* resource list */ 0, /* num resources */ 0, /* constraint size */ NULL, /* init proc */ NULL, /* destroy proc */ NULL, /* set values proc */ NULL, /* extension */ }, { /* manager_class fields */ XmInheritTranslations, /* translations */ NULL, /* syn_resources */ 0, /* num_syn_resources */ NULL, /* syn_cont_resources */ 0, /* num_syn_cont_resources */ XmInheritParentProcess, /* parent_process */ NULL, /* extension */ }, { /* bulletinBoard class */ TRUE, /*always_install_accelerators*/ _DtHelpDialogWidgetGeoMatrixCreate, /* geo__matrix_create */ XmInheritFocusMovedProc, /* focus_moved_proc */ NULL /* extension */ }, { /* messageBox class - none */ 0 /* mumble */ } }; externaldef( dthelpdialogwidgetclass) WidgetClass dtHelpDialogWidgetClass = (WidgetClass) &dtHelpDialogWidgetClassRec; static char *HelpTypeNames[] = { "help_type_topic", "help_type_string", "help_type_man_page", "help_type_file", "help_type_dynamic_string" }; static char *ScrollBarValueNames[] = { "help_no_scrollbars", "help_static_scrollbars", "help_as_needed_scrollbars" }; static char *ExecutionValueNames[] = { "help_execute_none", "help_execute_query_all", "help_execute_query_unaliased", "help_execute_all" }; /* the _DtHelpPaperSizeNames[] are in Print.c */ #define NUM_NAMES( list ) (sizeof( list) / sizeof( char *)) /********************************************************************* * * NavigationTypeDefault * * *********************************************************************/ static void NavigationTypeDefault( Widget widget, int offset, /* unused */ XrmValue *value ) { static XmNavigationType navigation_type; Widget parent = XtParent(widget) ; value->addr = (XPointer) &navigation_type; if (XtIsShell(parent)) { navigation_type = XmSTICKY_TAB_GROUP; } else { navigation_type = XmTAB_GROUP; } } /***************************************************************************** * Function: static void ClassInitialize ( * void) * * Parameters: Void. * * * Return Value: Void. * * Purpose: Register our representation types here * *****************************************************************************/ static void ClassInitialize(void) { XmRepTypeId checkId; /* First check to see if these have already been registered */ checkId = XmRepTypeGetId(DtRDtScrollBarPolicy); if (checkId == XmREP_TYPE_INVALID) { /* Register the help representation types here */ XmRepTypeRegister(DtRDtHelpType, HelpTypeNames, NULL, NUM_NAMES(HelpTypeNames)) ; XmRepTypeRegister(DtRDtScrollBarPolicy, ScrollBarValueNames, NULL, NUM_NAMES(ScrollBarValueNames)) ; XmRepTypeRegister(DtRDtExecutionPolicy, ExecutionValueNames, NULL, NUM_NAMES(ExecutionValueNames)) ; XmRepTypeRegister(DtRDtPaperSize, _DtHelpPaperSizeNames, NULL, _DtHelpPaperSizeNamesCnt) ; } return ; } /***************************************************************************** * Function: static void ClassPartInitialize ( * WidgetClass widgetClass) * * Parameters: WidgetClass * * * Return Value: Void. * * Purpose: * *****************************************************************************/ static void ClassPartInitialize( WidgetClass widgetClass) { return ; } /***************************************************************************** * Function: static void VariableInitialize() * * * Return Value: Void. * * Purpose: This routine initializes all global variables to valid * starting values. * *****************************************************************************/ static void VariableInitialize( DtHelpDialogWidget nw) { DtHelpDialogWidget hw = (DtHelpDialogWidget) nw ; /* Set our current topic variables to initial values */ _DtHelpCommonHelpInit(&hw->help_dialog.help); /* Make local copies of all resource strings assigned by the user */ if (hw->help_dialog.display.locationId != NULL) hw->help_dialog.display.locationId = XtNewString(hw->help_dialog.display.locationId); if (hw->help_dialog.display.helpVolume != NULL) hw->help_dialog.display.helpVolume = XtNewString(hw->help_dialog.display.helpVolume); if (hw->help_dialog.display.manPage != NULL) hw->help_dialog.display.manPage = XtNewString(hw->help_dialog.display.manPage); if (hw->help_dialog.display.stringData != NULL) hw->help_dialog.display.stringData = XtNewString(hw->help_dialog.display.stringData); if (hw->help_dialog.display.helpFile != NULL) hw->help_dialog.display.helpFile = XtNewString(hw->help_dialog.display.helpFile); /* * Initialize the topic title variables. */ hw->help_dialog.display.count = 1; hw->help_dialog.display.topicTitleLbl = NULL; if (hw->help_dialog.display.topicTitleStr != NULL) hw->help_dialog.display.topicTitleStr = XtNewString(hw->help_dialog.display.topicTitleStr); else hw->help_dialog.display.topicTitleStr = XtNewString((char *)_DTGETMESSAGE(2, 70, "Nonexistent Topic Title.")); /* * create the XmString version */ if (hw->help_dialog.display.topicTitleStr != NULL) hw->help_dialog.display.topicTitleLbl = XmStringCreateLocalized( hw->help_dialog.display.topicTitleStr); if (hw->help_dialog.print.printer != NULL) hw->help_dialog.print.printer = XtNewString(hw->help_dialog.print.printer); if (hw->help_dialog.print.helpPrint != _DtHelpDefaultHelpPrint) hw->help_dialog.print.helpPrint = XtNewString(hw->help_dialog.print.helpPrint); hw->bulletin_board.auto_unmanage = FALSE; hw->bulletin_board.resize_policy = XmRESIZE_NONE; /* Setup some of our generic widget variables */ hw->help_dialog.print.printVolume = NULL; /* Set our volume handle to an NULL initial value */ hw->help_dialog.display.volumeHandle = NULL; hw->help_dialog.ghelp.volumeFlag = FALSE; _DtHelpGlobSrchInitVars(&hw->help_dialog.srch); /* Set our print display stuff to initial values */ hw->help_dialog.print.printForm = NULL; /* Set our map flag: true after we hit our popup callback, * false otherwise */ hw->help_dialog.display.firstTimePopupFlag = FALSE; /* Set our history display stuff to initial vlaues */ hw->help_dialog.history.historyWidget = NULL; hw->help_dialog.history.volumeList = NULL; hw->help_dialog.history.topicList = NULL; hw->help_dialog.history.pHistoryListHead = NULL; /* Set our path display stuff to initial values */ hw->help_dialog.history.pPathListHead = NULL; hw->help_dialog.history.pPathListTale = NULL; hw->help_dialog.history.totalPathNodes = 0; /* Set our jump list display stuff to initial values */ hw->help_dialog.backtr.pJumpListHead = NULL; hw->help_dialog.backtr.pJumpListTale = NULL; hw->help_dialog.backtr.totalJumpNodes = 0; hw->help_dialog.backtr.scrollPosition = -1; /* Set our help dialog widgets to NULL starting values */ hw->help_dialog.menu.menuBar = NULL; hw->help_dialog.browser.panedWindow = NULL; hw->help_dialog.browser.pathArea = NULL; hw->help_dialog.menu.topBtn = NULL; hw->help_dialog.menu.popupTopBtn = NULL; hw->help_dialog.menu.keyBtn = NULL; hw->help_dialog.menu.backBtn = NULL; hw->help_dialog.menu.popupBackBtn = NULL; hw->help_dialog.menu.historyBtn = NULL; hw->help_dialog.menu.printBtn = NULL; hw->help_dialog.menu.closeBtn = NULL; hw->help_dialog.menu.helpBtn = NULL; hw->help_dialog.ghelp.definitionBox = NULL; hw->help_dialog.menu.newWindowBtn = NULL; hw->help_dialog.browser.btnBoxBackBtn = NULL; hw->help_dialog.browser.btnBoxHistoryBtn = NULL; hw->help_dialog.browser.btnBoxIndexBtn = NULL; /* Set our parentId to a null starting value */ hw->help_dialog.ghelp.parentId = NULL; } /***************************************************************************** * Function: static void Initialize ( * WidgetClass widgetClass) * * Parameters: WidgetClass * * * Return Value: Void. * * Purpose: This is the Help Dialog widget initialize routine. This * routine is responsible for the following: * 1) Validate all resources the user passed in. * 2) Over ride any invalid resources. * 3) Build the internal UI component for the Help Dialog. * 4) Add any internal callbacks for the UI components. * *****************************************************************************/ static void Initialize( Widget rw, Widget nw, ArgList args_init, Cardinal *num_args) { Arg args[10]; /* arg list */ int n; /* arg count */ DtHelpDialogWidget hw = (DtHelpDialogWidget) nw ; /* Local variables */ DtHelpListStruct *pHelpInfo; /* Initialize all global variables */ VariableInitialize(hw); /* Validate the incoming arguments to make sure they are ok */ /* Build the Menus bar */ hw->help_dialog.menu.menuBar = SetupHelpDialogMenus((Widget)hw); /* Build the Paned Window to hold the path area and display area */ n = 0; XtSetArg (args[n], XmNspacing, 10); ++n; hw->help_dialog.browser.panedWindow = XmCreatePanedWindow ((Widget)hw, "panedWindow", args, n); XtManageChild (hw->help_dialog.browser.panedWindow); /* Call the setup routine to build the actual path area */ _DtHelpBuildPathArea(hw->help_dialog.browser.panedWindow, hw); /* Force our keyboard traversal to start within the path area */ /* * NOTE 04/25/96 : pathArea is NOT set by _DtHelpBuildPathArea(). * The test for NULL is a work-around for defect CDExc20246; but * the proper widget should be given to XmProcessTraversal() someday. */ if (hw->help_dialog.browser.pathArea != (Widget)NULL) XmProcessTraversal(hw->help_dialog.browser.pathArea, XmTRAVERSE_HOME); /* We build our display area last because we need the other UI * components created first. */ /* Call the setup routine to build the display area */ BuildDisplayArea(hw->help_dialog.browser.panedWindow, hw); /* Add the proper help callback to the top level shell of our dialog */ /* Add all our help callbacks for each of the created widgets */ pHelpInfo = _DtHelpListAdd(DtHELP_dialogShell_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback((Widget) hw, XmNhelpCallback, _DtHelpCB, (XtPointer) pHelpInfo); /* Just for fun, lets make sure our sizes are correct */ XtAddCallback (XtParent(hw), XmNpopupCallback, (XtCallbackProc) InitialPopupCB, (XtPointer) hw); return; } /**************************************************************************** * Function: static XtCallbackProc InitialPopupCB * * * * Parameters: * * Return Value: Void. * * Purpose: We do some last minute sizing of our dialog on its first * mapping, then we remove the callback. * ****************************************************************************/ static void InitialPopupCB( Widget w, XtPointer clientData, XtPointer callData) { DtHelpDialogWidget hw = (DtHelpDialogWidget) clientData; /* set our firstTimePopupFlag to TRUE because we map it right after this call */ hw->help_dialog.display.firstTimePopupFlag = TRUE; _DtHelpResizeDisplayArea (XtParent(hw), hw->help_dialog.help.pDisplayArea, hw->help_dialog.display.textRows, hw->help_dialog.display.textColumns); XtRemoveCallback (XtParent(hw), XmNpopupCallback, (XtCallbackProc) InitialPopupCB, (XtPointer) hw); } /***************************************************************************** * Function: static Boolean SetValues( * Widget cw, * Widget rw, * Widget nw, * ArgList args, * Cardinal *num_args ) * * Parameters: cw Specifies the current working widget. * rw Specifies the replacement working widget. * nw Specifies the new widget. * args Specifies the arguments to be applied to the * New widget. * numArgs Number of argument/value pars in args. * * Return Value: * * Purpose: Set the attributes of the Help Dialog widget. * *****************************************************************************/ static Boolean SetValues( Widget cw, Widget rw, Widget nw, ArgList args, Cardinal *numArgs) { DtHelpDialogWidget hw = (DtHelpDialogWidget) nw ; DtHelpDialogWidget current = (DtHelpDialogWidget) cw ; Boolean updateRequest=FALSE; Boolean newTitle=FALSE; /* Validate the incoming arguments to make sure they are ok */ /* Setup some initial argument values we know we need on the B-board */ hw->bulletin_board.auto_unmanage = FALSE; hw->bulletin_board.resize_policy = XmRESIZE_NONE; /* Check DtNcolumns & or DtNrows resource for change */ if ((current->help_dialog.display.textRows != hw->help_dialog.display.textRows) || (current->help_dialog.display.textColumns != hw->help_dialog.display.textColumns)) { /* Perform a resize on our display area */ _DtHelpResizeDisplayArea (XtParent(hw), hw->help_dialog.help.pDisplayArea, hw->help_dialog.display.textRows, hw->help_dialog.display.textColumns); } /* Check DtNhelpVolume resource for change */ if (current->help_dialog.display.helpVolume != hw->help_dialog.display.helpVolume) { hw->help_dialog.display.helpVolume = XtNewString(hw->help_dialog.display.helpVolume); XtFree(current->help_dialog.display.helpVolume); /* Update our volumeFlag so we know to resolve our new help volume */ hw->help_dialog.ghelp.volumeFlag=FALSE; updateRequest = TRUE; } /* Check DtNlocationId resource for change */ if (current->help_dialog.display.locationId != hw->help_dialog.display.locationId) { hw->help_dialog.display.locationId = XtNewString(hw->help_dialog.display.locationId); XtFree(current->help_dialog.display.locationId); updateRequest = TRUE; } /* set the printing resources */ _DtHelpPrintSetValues(¤t->help_dialog.print,&hw->help_dialog.print, &hw->help_dialog.display,&hw->help_dialog.help); /* Check XmhelpOnHelpVolume resource for change */ if (current->help_dialog.help.helpOnHelpVolume != hw->help_dialog.help.helpOnHelpVolume) { hw->help_dialog.help.helpOnHelpVolume = XtNewString(hw->help_dialog.help.helpOnHelpVolume); if (current->help_dialog.help.helpOnHelpVolume != _DtHelpDefaultHelp4HelpVolume) XtFree(current->help_dialog.help.helpOnHelpVolume); } /* Check DtNmanPage resource for change */ if (current->help_dialog.display.manPage != hw->help_dialog.display.manPage) { hw->help_dialog.display.manPage = XtNewString(hw->help_dialog.display.manPage); XtFree(current->help_dialog.display.manPage); updateRequest = TRUE; newTitle = TRUE; } /* Check DtNstringData resource for change */ if (current->help_dialog.display.stringData != hw->help_dialog.display.stringData) { hw->help_dialog.display.stringData = XtNewString(hw->help_dialog.display.stringData); XtFree(current->help_dialog.display.stringData); updateRequest = TRUE; newTitle = TRUE; } /* Check DtNhelpFile resource for change */ if (current->help_dialog.display.helpFile != hw->help_dialog.display.helpFile) { hw->help_dialog.display.helpFile = XtNewString(hw->help_dialog.display.helpFile); XtFree(current->help_dialog.display.helpFile); updateRequest = TRUE; newTitle = TRUE; } /* Check DtNtopicTitle resource for change */ if (hw->help_dialog.display.topicTitleStr != NULL && current->help_dialog.display.topicTitleStr != hw->help_dialog.display.topicTitleStr) { /* * copy the string and make a XmString version. */ hw->help_dialog.display.topicTitleStr = XtNewString(hw->help_dialog.display.topicTitleStr); XtFree(current->help_dialog.display.topicTitleStr); updateRequest = TRUE; newTitle = TRUE; } else if (newTitle == True) { /* * A new file, string or man page has been specified. * But XmNtopicTitle has not been set or set to null (otherwise * the if stmt would have been true). Therefore, create a new * title for this entry for history and topic labels. */ int len; char *str; str = (char *)_DTGETMESSAGE(2, 70, "Nonexistent Topic Title."); len = strlen(str); hw->help_dialog.display.topicTitleStr = XtMalloc(sizeof(char)*(len+10)); if (NULL != hw->help_dialog.display.topicTitleStr) { sprintf(hw->help_dialog.display.topicTitleStr, "%s%d", str, hw->help_dialog.display.count++); newTitle = TRUE; } } /* * Turn the string into an XmString and free the old */ if (newTitle == TRUE) { hw->help_dialog.display.topicTitleLbl = XmStringCreateLocalized( hw->help_dialog.display.topicTitleStr); if (current->help_dialog.display.topicTitleLbl != NULL) XmStringFree(current->help_dialog.display.topicTitleLbl); } /* Check the help type for change */ if (current->help_dialog.display.helpType != hw->help_dialog.display.helpType || updateRequest) { /* Setup and display our new topic */ _DtHelpSetupDisplayType(hw, TRUE, DtHISTORY_AND_JUMP); } return(FALSE); } /***************************************************************************** * Function: static void Destroy(Widget w ); * * Parameters: w Specifies the widget to be destroyed. * * Return Value: * * Purpose: Destroy any internally malloced memory. * *****************************************************************************/ static void Destroy( Widget w) { DtHelpDialogWidget hw = (DtHelpDialogWidget) w; /* This routine will clean up all malloc'ed stuff in our instance * structure. It does not remove any callbacks or delete any of the * widgets created in this instance of the help dialog. */ CleanUpHelpDialog((Widget) hw, DtCLEAN_FOR_DESTROY); /* Remove any of the callbacks added to the help dialog ??? */ } /***************************************************************************** * Function: static void MenuBarFix( * XmGeoMatrix geoSpec, * int action, * XmGeoRowLayout layoutPtr, * XmKidGeometry rowPtr) * * * * Parameters: * * Return Value: * * Purpose: This routine is a fixup routine which can be used for rows * which consist of a single MenuBar RowColumn. The effect of * this routine is to have the RowColumn ignore the margin * width and height. * *****************************************************************************/ static void MenuBarFix( XmGeoMatrix geoSpec, int action, XmGeoMajorLayout layoutPtr, XmKidGeometry rowPtr ) { Dimension marginW ; Dimension marginH ; Dimension twoMarginW ; marginW = geoSpec->margin_w ; twoMarginW = (marginW << 1) ; marginH = geoSpec->margin_h ; switch( action ) { case XmGEO_PRE_SET: { rowPtr->box.x -= marginW ; rowPtr->box.width += twoMarginW ; rowPtr->box.y -= marginH ; break ; } default: { if( rowPtr->box.width > twoMarginW ) { /* Avoid subtracting a margin from box width which would * result in underflow. */ rowPtr->box.x += marginW ; rowPtr->box.width -= twoMarginW ; } if( action == XmGET_PREFERRED_SIZE ) { /* Set width to some small value so it does not * effect total width of matrix. */ rowPtr->box.width = 1 ; } break ; } } return ; } /***************************************************************************** * Function: XmGeoMatrix _DtHelpDialogWidgeGeoMatrixCreate( * Widget wid, * Widget instigator, * XtWidgetGeometry *desired) * * Parameters: * * Return Value: * * Purpose: This routine is responsible for all the positioning of the * the internal Help Dialog widgets. * *****************************************************************************/ XmGeoMatrix _DtHelpDialogWidgetGeoMatrixCreate( Widget wid, Widget instigator, XtWidgetGeometry *desired ) { DtHelpDialogWidget hw = (DtHelpDialogWidget) wid ; XmGeoMatrix geoSpec ; XmGeoRowLayout layoutPtr ; XmKidGeometry boxPtr ; geoSpec = _XmGeoMatrixAlloc( TB_MAX_WIDGETS_VERT, TB_MAX_NUM_WIDGETS, 0) ; geoSpec->composite = (Widget) hw ; geoSpec->instigator = (Widget) instigator ; if( desired ) { geoSpec->instig_request = *desired ; } geoSpec->margin_w = hw->help_dialog.ghelp.marginWidth + hw->manager.shadow_thickness ; geoSpec->margin_h = hw->help_dialog.ghelp.marginHeight + hw->manager.shadow_thickness ; geoSpec->no_geo_request = _DtHelpDialogWidgetNoGeoRequest ; layoutPtr = (XmGeoRowLayout) geoSpec->layouts ; boxPtr = geoSpec->boxes ; /* Menubar setup stuff */ if( _XmGeoSetupKid( boxPtr, hw->help_dialog.menu.menuBar)) { layoutPtr->fix_up = MenuBarFix; boxPtr += 2; ++layoutPtr; } /* Display area setup stuff */ if( _XmGeoSetupKid(boxPtr, hw->help_dialog.browser.panedWindow)) { layoutPtr->space_above = 0; layoutPtr->stretch_height = TRUE ; layoutPtr->min_height = 100 ; boxPtr += 2 ; /* For new row, add 2. */ ++layoutPtr ; /* For new row. */ } layoutPtr->space_above = hw->help_dialog.ghelp.marginWidth; layoutPtr->end = TRUE ; /* Mark the last row. */ return( geoSpec) ; } /***************************************************************************** * Function: Boolean _DtHelpDialogWidgetNoGeoRequest(geoSpec) * XmGeoMatrix geoSpec) * * * Parameters: * * Return Value: * * Purpose: * ****************************************************************************/ Boolean _DtHelpDialogWidgetNoGeoRequest(XmGeoMatrix geoSpec) { if( BB_InSetValues( geoSpec->composite) && (XtClass( geoSpec->composite) == dtHelpDialogWidgetClass) ) { return( TRUE) ; } return( FALSE) ; } /***************************************************************************** * Function: static void DisplayTopLevelCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: causes the top level topic to be displayed. * ****************************************************************************/ static void DisplayTopLevelCB( Widget w, XtPointer client_data, XtPointer call_data ) { DtHelpDialogWidget hw = (DtHelpDialogWidget) client_data; /* Display the top level topic */ if (hw->help_dialog.help.topLevelId != NULL) _DtHelpUpdateDisplayArea(hw->help_dialog.help.topLevelId, hw, TRUE, DtHISTORY_AND_JUMP, DtHELP_TYPE_TOPIC); else _DtHelpUpdateDisplayArea(NULL, hw, TRUE, DtHISTORY_AND_JUMP, DtHELP_TYPE_TOPIC); } /***************************************************************************** * Function: extern void _DtHelpDisplayBackCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: This routine will cause the top element in the jump * stack to be displayed. * ****************************************************************************/ void _DtHelpDisplayBackCB( Widget w, XtPointer client_data, XtPointer call_data) { DtHelpDialogWidget hw = (DtHelpDialogWidget) client_data; ProcessJumpBack(hw); } /***************************************************************************** * Function: extern void _DtHelpDuplicateWindowCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: This routine creates a new help widget by forcing the * equivelent of a Jump New hyper text call * ****************************************************************************/ void _DtHelpDuplicateWindowCB( Widget w, XtPointer clientData, XtPointer callData) { DtHelpDialogWidget hw = (DtHelpDialogWidget) clientData; DtHelpDialogCallbackStruct callDataStruct; /* Setup the DtHelpHyperProcStruct to pass back * to the client as callData */ _DtHelpTurnOnHourGlass(XtParent(hw)); if (hw->help_dialog.display.hyperLinkCallback != NULL) { /* Use the old one */ callDataStruct.helpVolume = XtNewString (hw->help_dialog.display.helpVolume); callDataStruct.reason = DtCR_HELP_LINK_ACTIVATE; callDataStruct.event = NULL; /* should be hyperData->event */ callDataStruct.locationId = XtNewString (hw->help_dialog.display.locationId); callDataStruct.specification = NULL; callDataStruct.hyperType = DtHELP_LINK_TOPIC; callDataStruct.windowHint = DtHELP_NEW_WINDOW; XtCallCallbackList((Widget)hw,hw->help_dialog.display.hyperLinkCallback, &callDataStruct); } else { /* The application did not register a hypertext callback so * we must generate the proper warning message and continue! */ XmeWarning((Widget)hw, (char*) HDMessage6); } _DtHelpTurnOffHourGlass(XtParent(hw)); } /***************************************************************************** * Function: static void CopyTextCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: This routine will cause the display area to copy text to * the clip-board. * ****************************************************************************/ static void CopyTextCB( Widget w, XtPointer clientData, XtPointer callData) { DtHelpDialogWidget hw = (DtHelpDialogWidget) clientData; _DtHelpInitiateClipboard(hw->help_dialog.help.pDisplayArea); } /***************************************************************************** * Function: static void ProcessBMenuBackCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: This routine will cause the top element in the jump * stack to be displayed, if their is a top element. * ****************************************************************************/ static void ProcessBMenuBackCB( Widget w, XtPointer clientData, XButtonEvent * event, Boolean *continueToDispatch) { DtHelpDialogWidget hw = (DtHelpDialogWidget) clientData; XmMenuPosition(hw->help_dialog.menu.popupMenu, event); XtManageChild(hw->help_dialog.menu.popupMenu); } /***************************************************************************** * Function: extern void _DtHelpDisplayHistoryCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: This routine will cause the history dialog to be * posted. * ****************************************************************************/ void _DtHelpDisplayHistoryCB( Widget w, XtPointer client_data, XtPointer call_data ) { DtHelpDialogWidget hw = (DtHelpDialogWidget) client_data; XmUpdateDisplay((Widget) hw); _DtHelpTurnOnHourGlass(XtParent(hw)); _DtHelpDisplayHistoryInfo((Widget)hw); _DtHelpTurnOffHourGlass(XtParent(hw)); } /***************************************************************************** * Function: void _DtHelpDisplayBrowserHomeCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: This routine will cause the top level of the browser.hv * help volume to be displayed. * ****************************************************************************/ void _DtHelpDisplayBrowserHomeCB( Widget w, XtPointer client_data, XtPointer call_data ) { DtHelpDialogWidget hw = (DtHelpDialogWidget) client_data; XmUpdateDisplay((Widget) hw); /* ??? Check to see if help volume is always fully expanded at this point * ??? if so, we will never have a match. */ if ( hw->help_dialog.display.helpVolume == NULL || strstr (hw->help_dialog.display.helpVolume, DtBROWSER_NAME) == NULL) { XtFree(hw->help_dialog.display.helpVolume); hw->help_dialog.display.helpVolume = XtNewString(DtBROWSER_NAME); /* Set our help volume flag so we open the proper volume */ hw->help_dialog.ghelp.volumeFlag = FALSE; } XtFree(hw->help_dialog.display.locationId); hw->help_dialog.display.locationId = XtNewString(DtBROWSER_HOME); hw->help_dialog.display.helpType = DtHELP_TYPE_TOPIC; _DtHelpSetupDisplayType(hw, TRUE, DtHISTORY_AND_JUMP); } /***************************************************************************** * Function: void _DtHelpDisplayIndexCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: This routine will cause the index dialog to be * posted. * ****************************************************************************/ void _DtHelpDisplayIndexCB( Widget w, XtPointer client_data, XtPointer call_data ) { DtHelpDialogWidget hw = (DtHelpDialogWidget) client_data; XmUpdateDisplay((Widget) hw); _DtHelpTurnOnHourGlass(XtParent(hw)); /* display the index search dialog */ _DtHelpGlobSrchDisplayDialog((Widget)hw,NULL,hw->help_dialog.display.helpVolume); _DtHelpTurnOffHourGlass(XtParent(hw)); } /***************************************************************************** * Function: static void DisplayPrintCB( * Widget w, * XtPointer client_data, * XtPointer call_data); * * Parameters: * * Return Value: * * Purpose: This routine will cause the history dialog to be * posted. * ****************************************************************************/ static void DisplayPrintCB( Widget w, XtPointer client_data, XtPointer call_data ) { DtHelpDialogWidget hw = (DtHelpDialogWidget) client_data; XmUpdateDisplay((Widget) hw); _DtHelpTurnOnHourGlass(XtParent(hw)); /* display the print dialog */ _DtHelpDisplayPrintDialog((Widget) hw,&hw->help_dialog.print, &hw->help_dialog.display,&hw->help_dialog.help); _DtHelpTurnOffHourGlass(XtParent(hw)); } /***************************************************************************** * Function: Widget DtCreateHelpDialog(Widget parent, * String name, * ArgList arglist, * Cardinal argcount); * * Parameters: parent Specifies the parent widget ID. * name Specifies the name of the created dialog * shell widget. * arglis Specifies the argument list. * argcount Specifies the number of attribute/value pairs * in the argument list (arglist). * * Return Value: Returns a Help Dialog shell widget ID. * * Purpose: Create an instance of a Help Dialog. * *****************************************************************************/ Widget DtCreateHelpDialog( Widget parent, char *name, ArgList al, Cardinal ac) { Widget w; _DtHelpWidgetToAppContext(parent); _DtHelpAppLock(app); w = XmeCreateClassDialog (dtHelpDialogWidgetClass, parent, name, al, ac); /* Add the CatchClose here so we catch the window manager close requests */ CatchClose(w); _DtHelpAppUnlock(app); return w; } /***************************************************************************** * Function: _DtHelpFilterExecCmdCB * * clientData: The general help dialog widget * cmdStr: cmd string to filter * ret_filteredCmdStr: string after filtering. NULL if exec denied * * Return Value: 0: ok, < 0: error * * Purpose: filter an execution command using executionPolicy rsrc * * Memory: * The caller must free memory allocated for the ret_filteredCmdStr *****************************************************************************/ int _DtHelpFilterExecCmdCB( void * clientData, const char * cmdStr, char * * ret_filteredCmdStr) { DtHelpDialogWidget hw; char *hv_path; hw = (DtHelpDialogWidget) _DtHelpDisplayAreaData(clientData); hv_path = _DtHelpFileLocate(DtHelpVOLUME_TYPE, hw->help_dialog.display.helpVolume, _DtHelpFileSuffixList, False, R_OK); return _DtHelpFilterExecCmd((Widget) hw, cmdStr, hw->help_dialog.display.executionPolicy, True, &hw->help_dialog.help, ret_filteredCmdStr, hv_path); } /***************************************************************************** * Function: void BuildDisplayArea(Widget parent, * DtHelpDialogWidget nw); * * * Parameters: parent Specifies the widget ID of the help dialog you * want to set the topic in. * nw Specifies the current help dialog widget. * * Return Value: Void. * * Purpose: Creates the Display area in the help dialog. * *****************************************************************************/ static void BuildDisplayArea( Widget parent, DtHelpDialogWidget nw) { Arg args[2]; int n; XmFontList defaultList; DtHelpDialogWidget hw = (DtHelpDialogWidget) nw ; /* Get our current fontlist value */ n = 0; XtSetArg (args[n], XmNfontList, &(defaultList)); ++n; XtGetValues (hw->help_dialog.menu.topBtn, args, n); /* Build the Display Area */ hw->help_dialog.help.pDisplayArea = _DtHelpCreateDisplayArea(parent, "DisplayArea", ((short) hw->help_dialog.display.scrollBarPolicy), ((short) hw->help_dialog.display.scrollBarPolicy), False, ((int) hw->help_dialog.display.textRows), ((int) hw->help_dialog.display.textColumns), _DtHelpDialogHypertextCB, ResizeHelpDialogCB, _DtHelpFilterExecCmdCB, (XtPointer) hw, defaultList); /* Build the popup menu item for inside the display area */ hw->help_dialog.menu.popupMenu = CreatePopupMenu((Widget)hw); /* Determin what type of info we are going to display */ _DtHelpSetupDisplayType(hw, TRUE, DtHISTORY_AND_JUMP); } /***************************************************************************** * Function: void _DtHelpSetupDisplayType(DtHelpDialogWidget nw, * int updateType); * * * Parameters: nw Specifies the current help dialog widget. * * Return Value: Void. * * Purpose: Determins the type of topic the user want's to display * in the current help dialog and sets it up for display. * *****************************************************************************/ void _DtHelpSetupDisplayType( DtHelpDialogWidget nw, Boolean vol_changed, int updateType) { char *templocationId; Boolean validAccessPath=FALSE; XtPointer topicHandle; DtHelpDialogWidget hw = (DtHelpDialogWidget) nw ; int status=VALID_STATUS; char *tmpMessage; char *tmpError; char *locTitle; char *volumeTitle; DtTopicListStruct *tmpPtr; Boolean adjustTopicTitle=TRUE; /* This is a local flag that we use to determine * if we need to re-adjust the topic volume title * at the end of this * Function: True == Modify title, False == leave alone. */ Boolean didWeHaveAnError=FALSE; XmString labelString; Arg args[10]; int n=0; /* Here we need to store away our current scroll position as the currentlly * displayed item is about replaced w/a new item. * We already have placed this item in the jump stack, and now are just adding * the proper value for our scrollPosition. */ if (hw->help_dialog.backtr.pJumpListHead != NULL) { tmpPtr = hw->help_dialog.backtr.pJumpListHead; tmpPtr->scrollPosition = _DtHelpGetScrollbarValue(hw->help_dialog.help.pDisplayArea); } /* Here we set our UP, and Home Topic buttons to FALSE, they should be * true then the following code will set them correctly. */ XtSetSensitive(hw->help_dialog.menu.topBtn, FALSE); XtSetSensitive(hw->help_dialog.menu.popupTopBtn, FALSE); switch (hw->help_dialog.display.helpType) { case DtHELP_TYPE_TOPIC: /* Expand the helpVolume resource if needed */ if ((hw->help_dialog.ghelp.volumeFlag) && (hw->help_dialog.display.volumeHandle != NULL)) validAccessPath = TRUE; else if (hw->help_dialog.display.helpVolume != NULL) validAccessPath = _DtHelpExpandHelpVolume((Widget)hw, &hw->help_dialog.display, &hw->help_dialog.help, &hw->help_dialog.print); /* If the developer gave us a valid Access Path then we can continue * else, we will do nothing */ if (validAccessPath) { #if 0 /* Update our keyword search dialog if needed */ if ( FALSE == hw->help_dialog.ghelp.volumeFlag) _DtHelpGlobSrchUpdateCurVol((Widget) hw); /* We now set this to true after we update our volumeTitle * value in _DtHelpUpdateDisplayArea. */ /* hw->help_dialog.ghelp.volumeFlag = TRUE;*/ #endif /* Setup all the proper lists and display area with the * topic string */ templocationId = XtNewString(hw->help_dialog.display.locationId); /* Set the initial locationId into the display area */ _DtHelpUpdateDisplayArea(templocationId, hw, vol_changed, updateType, DtHELP_TYPE_TOPIC); XtFree(templocationId); adjustTopicTitle = FALSE; } else { if (hw->help_dialog.display.helpVolume == NULL) { didWeHaveAnError=TRUE; tmpError = XtNewString((char *)_DTGETMESSAGE(2, 60, "No help volume specified.")); _DtHelpDisplayFormatError(hw->help_dialog.help.pDisplayArea, (Widget)hw, tmpError, NULL); _DtHelpUpdateJumpList(tmpError, DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); hw->help_dialog.display.helpType = DtHELP_TYPE_DYNAMIC_STRING; hw->help_dialog.display.stringData = XtNewString(tmpError); XtFree(tmpError); } else { /* We cannot find our HelpVolume so display the proper error * message in the help dialog and continue. */ didWeHaveAnError=TRUE; tmpMessage = XtNewString((char *)_DTGETMESSAGE(2, 58, "The requested online help is either not installed " "or not in the proper help search path. For " "information on installing online help, consult " "the documentation for the product.\n")); locTitle = XtNewString((char *)_DTGETMESSAGE(2, 62, "Location ID:")); volumeTitle = XtNewString((char *)_DTGETMESSAGE(2, 61, "Help Volume:")); tmpError = XtMalloc(strlen(tmpMessage) + strlen(locTitle) + strlen(volumeTitle) + strlen(hw->help_dialog.display.locationId) + strlen(hw->help_dialog.display.helpVolume) + 4); (void) strcpy(tmpError, tmpMessage); (void) strcat(tmpError, volumeTitle); (void) strcat(tmpError, " "); (void) strcat(tmpError, hw->help_dialog.display.helpVolume); (void) strcat(tmpError,"\n"); (void) strcat(tmpError, locTitle); (void) strcat(tmpError, " "); (void) strcat(tmpError, hw->help_dialog.display.locationId); /* Set current path area to null by giving it a null id */ _DtHelpUpdatePathArea(NULL, hw); _DtHelpDisplayFormatError(hw->help_dialog.help.pDisplayArea, (Widget)hw, tmpError, NULL); _DtHelpUpdateJumpList(tmpError,DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); hw->help_dialog.display.helpType = DtHELP_TYPE_DYNAMIC_STRING; hw->help_dialog.display.stringData = XtNewString(tmpError); XtFree(tmpError); XtFree(tmpMessage); XtFree(locTitle); XtFree(volumeTitle); } } break; case DtHELP_TYPE_STRING: _DtHelpUpdatePathArea(NULL, hw); /* Set the string to the current help dialog */ status = _DtHelpFormatAsciiString(hw->help_dialog.help.pDisplayArea, hw->help_dialog.display.stringData, &topicHandle); if (status >= VALID_STATUS) { /* Update the History and Jump Lists */ if (updateType == DtHISTORY_AND_JUMP) _DtHelpUpdateJumpList(hw->help_dialog.display.stringData, DtHELP_TYPE_STRING, (Widget) hw); _DtHelpUpdateHistoryList(hw->help_dialog.display.stringData, DtHELP_TYPE_STRING, TRUE, (Widget)hw); _DtHelpDisplayAreaSetList (hw->help_dialog.help.pDisplayArea, topicHandle, FALSE, hw->help_dialog.backtr.scrollPosition); } else { didWeHaveAnError=TRUE; tmpError = XtNewString((char *)_DTGETMESSAGE(2, 50, "String data could not be formatted.")); _DtHelpDisplayFormatError(hw->help_dialog.help.pDisplayArea, (Widget)hw, tmpError, (char*)HDMessage0); _DtHelpUpdateJumpList(tmpError, DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); hw->help_dialog.display.helpType = DtHELP_TYPE_DYNAMIC_STRING; hw->help_dialog.display.stringData = XtNewString(tmpError); XtFree(tmpError); } break; case DtHELP_TYPE_DYNAMIC_STRING: _DtHelpUpdatePathArea(NULL, hw); /* Set the string to the current help dialog */ status = _DtHelpFormatAsciiStringDynamic( hw->help_dialog.help.pDisplayArea, hw->help_dialog.display.stringData, &topicHandle); if (status >= VALID_STATUS) { /* Update the History and Jump Lists */ if (updateType == DtHISTORY_AND_JUMP) _DtHelpUpdateJumpList(hw->help_dialog.display.stringData, DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); _DtHelpUpdateHistoryList(hw->help_dialog.display.stringData, DtHELP_TYPE_DYNAMIC_STRING, TRUE, (Widget)hw); _DtHelpDisplayAreaSetList (hw->help_dialog.help.pDisplayArea, topicHandle, FALSE, hw->help_dialog.backtr.scrollPosition); } else { didWeHaveAnError=TRUE; tmpError = XtNewString((char *)_DTGETMESSAGE(2, 51, "Dynamic string data could not be formatted.")); _DtHelpUpdateJumpList(tmpError, DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); hw->help_dialog.display.helpType = DtHELP_TYPE_DYNAMIC_STRING; hw->help_dialog.display.stringData = XtNewString(tmpError); _DtHelpDisplayFormatError(hw->help_dialog.help.pDisplayArea,(Widget)hw, tmpError, (char*) HDMessage1); XtFree(tmpError); } break; case DtHELP_TYPE_MAN_PAGE: _DtHelpUpdatePathArea(NULL, hw); /* Set the string to the current help dialog */ status = _DtHelpFormatManPage( hw->help_dialog.help.pDisplayArea, hw->help_dialog.display.manPage, &topicHandle); if (status >= VALID_STATUS) { /* Update the History and Jump Lists */ if (updateType == DtHISTORY_AND_JUMP) _DtHelpUpdateJumpList(hw->help_dialog.display.manPage, DtHELP_TYPE_MAN_PAGE, (Widget)hw); _DtHelpUpdateHistoryList(hw->help_dialog.display.manPage, DtHELP_TYPE_MAN_PAGE, TRUE, (Widget)hw); _DtHelpDisplayAreaSetList (hw->help_dialog.help.pDisplayArea, topicHandle, FALSE, hw->help_dialog.backtr.scrollPosition); } else { didWeHaveAnError=TRUE; tmpError = XtNewString((char *)_DTGETMESSAGE(2, 52, "Man Page could not be formatted. The requested Man Page is either not present, or corrupt.")); _DtHelpUpdateJumpList(tmpError, DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); hw->help_dialog.display.helpType = DtHELP_TYPE_DYNAMIC_STRING; hw->help_dialog.display.stringData = XtNewString(tmpError); _DtHelpDisplayFormatError(hw->help_dialog.help.pDisplayArea, (Widget)hw, tmpError, (char*) HDMessage2); XtFree(tmpError); } break; case DtHELP_TYPE_FILE: _DtHelpUpdatePathArea(NULL, hw); /* Set the string to the current help dialog */ status = _DtHelpFormatAsciiFile(hw->help_dialog.help.pDisplayArea, hw->help_dialog.display.helpFile, &topicHandle); if (status >= VALID_STATUS) { /* Update the History and Jump Lists */ if (updateType == DtHISTORY_AND_JUMP) _DtHelpUpdateJumpList(hw->help_dialog.display.helpFile, DtHELP_TYPE_FILE,(Widget)hw); _DtHelpUpdateHistoryList(hw->help_dialog.display.helpFile, DtHELP_TYPE_FILE, TRUE, (Widget)hw); _DtHelpDisplayAreaSetList (hw->help_dialog.help.pDisplayArea, topicHandle, FALSE, hw->help_dialog.backtr.scrollPosition); } else { didWeHaveAnError=TRUE; tmpError = XtNewString((char *)_DTGETMESSAGE(2, 53, "Text file data could not be formatted. The requested text file is either not present, or corrupt.")); _DtHelpUpdateJumpList(tmpError, DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); hw->help_dialog.display.helpType = DtHELP_TYPE_DYNAMIC_STRING; hw->help_dialog.display.stringData = XtNewString(tmpError); _DtHelpDisplayFormatError(hw->help_dialog.help.pDisplayArea, (Widget)hw, tmpError, (char*) HDMessage3); XtFree(tmpError); } break; default: /* ERROR-MESSAGE */ /* This means the user used the wrong help type */ didWeHaveAnError=TRUE; tmpError = XtNewString((char *)_DTGETMESSAGE(2, 80, "The specified help type is invalid.")); _DtHelpUpdateJumpList(tmpError, DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); hw->help_dialog.display.helpType = DtHELP_TYPE_DYNAMIC_STRING; hw->help_dialog.display.stringData = XtNewString(tmpError); _DtHelpDisplayFormatError(hw->help_dialog.help.pDisplayArea, (Widget)hw, tmpError, (char*) HDMessage4); XtFree(tmpError); break; } /* End Switch Statement */ if ((adjustTopicTitle == TRUE) && (didWeHaveAnError == FALSE)) { /* We have a valid HelpType other than a volume and * no error condition, so lets update the Topics title. */ XtSetArg(args[0], XmNlabelString, hw->help_dialog.display.topicTitleLbl); XtSetValues (hw->help_dialog.browser.volumeLabel, args, 1); } else if (didWeHaveAnError) { /* error messages displayed, clear out the topics title */ n=0; labelString = XmStringCreateLocalized(" "); XtSetArg (args[n], XmNlabelString, labelString); n++; XtSetValues (hw->help_dialog.browser.volumeLabel, args, n); XmStringFree(labelString); if (hw->help_dialog.history.topicList != NULL) XmListDeselectAllItems(hw->help_dialog.history.topicList); if (hw->help_dialog.history.volumeList != NULL) XmListDeselectAllItems(hw->help_dialog.history.volumeList); /* Set current path area to null by giving it a null id */ _DtHelpUpdatePathArea(NULL, hw); } /* Update our keyword search dialog */ _DtHelpGlobSrchUpdateCurVol((Widget) hw); /* Update the print dialog */ _DtHelpUpdatePrintDialog(&hw->help_dialog.print, &hw->help_dialog.display,&hw->help_dialog.help,False); /* covers error states and non-help topics; case of help topic but in/not in the top-level volume is covered elsewhere */ if ( hw->help_dialog.browser.showTopLevelBtn == TRUE && hw->help_dialog.display.helpType != DtHELP_TYPE_TOPIC) XtSetSensitive(hw->help_dialog.browser.btnBoxTopLevelBtn, TRUE); } /***************************************************************************** * Function: void _DtHelpUpdateDisplayArea(char *locationId, * DtHelpDialogWidget nw, * int listUpdateType, * int topicUpdateType); * * * Parameters: locationId Specifies the ID string for the new topic we * are going to display in the HelpDialog widget. * * nw Specifies the current help dialog widget. * * Return Value: Void. * * Purpose: Updates the Display area with a new Cache Creek Topic. * *****************************************************************************/ void _DtHelpUpdateDisplayArea( char *locationId, DtHelpDialogWidget nw, Boolean vol_changed, int listUpdateType, int topicUpdateType) { XtPointer topicHandle; Boolean validlocationId=FALSE; int status=NON_VALID_STATUS; char *userErrorStr=NULL; char *sysErrorStr=NULL; char *tmpMsg=NULL; XmString labelString; Arg args[10]; int n=0; DtHelpDialogWidget hw = (DtHelpDialogWidget) nw; _DtHelpTurnOnHourGlass(XtParent(hw)); validlocationId = False; /* default */ /* If we have a null idString, assign the top level topic to it */ if (locationId == NULL && hw->help_dialog.help.topLevelId != NULL) { locationId = XtNewString(hw->help_dialog.help.topLevelId); } if (locationId != NULL) { XmUpdateDisplay((Widget)hw); /* format the initial locationId info to display */ status = _DtHelpFormatTopic ( hw->help_dialog.help.pDisplayArea, hw->help_dialog.display.volumeHandle, locationId, True, &topicHandle); /* unless locationId not found, the topic is valid */ if (status != -2) validlocationId = True; } /* if existing loc id, try to format it */ if (status == 0) /* success */ { if (hw->help_dialog.ghelp.volumeFlag == FALSE) { XmFontList fontList; Boolean mod = False; XtSetArg(args[0], XmNfontList, &fontList); XtGetValues(hw->help_dialog.browser.volumeLabel, args, 1); /* We have a new volume, so update the volume title */ _DtHelpFormatVolumeTitle(hw->help_dialog.help.pDisplayArea, hw->help_dialog.display.volumeHandle, &labelString, &fontList, &mod); if(labelString == NULL && NULL != hw->help_dialog.display.helpVolume) labelString = XmStringCreateLocalized( hw->help_dialog.display.helpVolume); if (NULL != labelString) { n = 0; XtSetArg (args[n], XmNlabelString, labelString); n++; if (mod == True) { XtSetArg (args[n], XmNfontList, fontList); n++; } XtSetValues (hw->help_dialog.browser.volumeLabel, args, n); XmStringFree(labelString); } if (True == mod) XmFontListFree(fontList); /* Update our volumeFlag because we know that its we have just, * opened a new volume. It will get set to false when we need * to process a different help volume, and remain true while * processing the current help volume. */ hw->help_dialog.ghelp.volumeFlag = TRUE; } /* if volumeFlag == False */ /* Update our history and jump lists */ if (listUpdateType == DtHISTORY_AND_JUMP) { _DtHelpUpdateHistoryList(locationId, topicUpdateType, vol_changed, (Widget)hw); _DtHelpUpdateJumpList(locationId, topicUpdateType,(Widget) hw); } else if (listUpdateType == DtHISTORY_ONLY) _DtHelpUpdateHistoryList(locationId, topicUpdateType, vol_changed, (Widget)hw); else if (listUpdateType == DtJUMP_ONLY) _DtHelpUpdateJumpList(locationId, topicUpdateType,(Widget)hw); /* Adjust our "Top Level" browser home buttons */ if (hw->help_dialog.browser.showTopLevelBtn == TRUE) { if (strstr (hw->help_dialog.display.helpVolume, DtBROWSER_NAME) != NULL) { /* FIX: get top topic of the current volume & compare with locationId */ if (strcmp (hw->help_dialog.display.locationId, DtBROWSER_HOME)== 0) XtSetSensitive(hw->help_dialog.browser.btnBoxTopLevelBtn, FALSE); else XtSetSensitive(hw->help_dialog.browser.btnBoxTopLevelBtn, TRUE); } else XtSetSensitive(hw->help_dialog.browser.btnBoxTopLevelBtn, TRUE); } /* if showTopLevelBtn */ /* Check to see if we are going to display the top level is so */ if (_DtHelpCeIsTopTopic(hw->help_dialog.display.volumeHandle, hw->help_dialog.display.locationId) == 0) { XtSetSensitive(hw->help_dialog.menu.topBtn, FALSE); XtSetSensitive(hw->help_dialog.menu.popupTopBtn, FALSE); } else { XtSetSensitive(hw->help_dialog.menu.topBtn, TRUE); XtSetSensitive(hw->help_dialog.menu.popupTopBtn, TRUE); } /* Change the widget instance record locationId field to * represent the new locationId being desplayed. */ XtFree(hw->help_dialog.display.locationId); hw->help_dialog.display.locationId = XtNewString(locationId); /* Update the current path area for the given topic */ _DtHelpUpdatePathArea(hw->help_dialog.display.locationId, hw); _DtHelpDisplayAreaSetList (hw->help_dialog.help.pDisplayArea, topicHandle, FALSE, hw->help_dialog.backtr.scrollPosition); } /* if status == 0 */ if (status < 0) { /* Invalid idString */ /* Clear the current volume title label */ /* ??? Is this the best way to null out a label gadget ??? */ labelString = XmStringCreateLocalized(" "); XtSetArg (args[n], XmNlabelString, labelString); XtSetValues (hw->help_dialog.browser.volumeLabel, args, 1); XmStringFree(labelString); /* Clear our history dialog selected items */ if (hw->help_dialog.history.topicList != NULL) XmListDeselectAllItems(hw->help_dialog.history.topicList); if (hw->help_dialog.history.volumeList != NULL) XmListDeselectAllItems(hw->help_dialog.history.volumeList); /* Set current path area to null by giving it a null idStirng */ _DtHelpUpdatePathArea(NULL, hw); /* De-sensatize our buttons, they do not work * with out valid topics. */ XtSetSensitive(hw->help_dialog.menu.topBtn, FALSE); XtSetSensitive(hw->help_dialog.menu.popupTopBtn, FALSE); if (hw->help_dialog.history.pHistoryListHead == NULL) { XtSetSensitive(hw->help_dialog.menu.historyBtn, FALSE); XtSetSensitive(hw->help_dialog.browser.btnBoxHistoryBtn, FALSE); } else { /* in case they were desensitized for any reason */ XtSetSensitive(hw->help_dialog.menu.historyBtn, TRUE); XtSetSensitive(hw->help_dialog.browser.btnBoxHistoryBtn, TRUE); } if (hw->help_dialog.backtr.pJumpListHead != NULL) { XtSetSensitive(hw->help_dialog.menu.backBtn, TRUE); XtSetSensitive(hw->help_dialog.menu.popupBackBtn, TRUE); XtSetSensitive(hw->help_dialog.browser.btnBoxBackBtn, TRUE); } /* Determin the proper error message to give */ if (!validlocationId) { if (locationId == NULL) { tmpMsg = (char *)_DTGETMESSAGE(2, 59, "No location ID specified."); userErrorStr = XtNewString(tmpMsg); } else { tmpMsg = (char *)_DTGETMESSAGE(2, 55, "Nonexistent location ID:"); userErrorStr = XtMalloc(strlen(tmpMsg) + strlen(hw->help_dialog.display.locationId)+ 2); (void) strcpy(userErrorStr, tmpMsg); (void) strcat(userErrorStr, " "); (void) strcat(userErrorStr, hw->help_dialog.display.locationId); sysErrorStr = XtNewString(HDMessage9); } } else { tmpMsg = (char*)_DTGETMESSAGE(2, 54, "Help topic could not be formatted."); userErrorStr = XtNewString(tmpMsg); sysErrorStr = XtNewString(HDMessage5); } _DtHelpUpdateJumpList(userErrorStr, DtHELP_TYPE_DYNAMIC_STRING, (Widget) hw); hw->help_dialog.display.helpType = DtHELP_TYPE_DYNAMIC_STRING; hw->help_dialog.display.stringData = XtNewString(userErrorStr); _DtHelpDisplayFormatError(hw->help_dialog.help.pDisplayArea, (Widget) hw, userErrorStr, sysErrorStr); XtFree(userErrorStr); XtFree(sysErrorStr); } /* if (status < 0) */ _DtHelpTurnOffHourGlass(XtParent(hw)); } /***************************************************************************** * Function: void _DtHelpUpdateJumpList(char *topicInfo, * int topicType, * DtHelpDialogWidget nw); * * * Parameters: topicInfo Specifies the * int Specifies the topicInfo type. * * nw Specifies the current help dialog widget. * * Return Value: Void. * * Purpose: Updates the Jump List with the new topic. * *****************************************************************************/ void _DtHelpUpdateJumpList( char *topicInfo, int topicType, Widget nw) { DtHelpDialogWidget hw = (DtHelpDialogWidget) nw ; /* Add the new topic to the top of the jump list */ /* We add a -1 for the scrollbar position value, and will replace it with the * actual value just prior to changing the window to the new topic. */ _DtHelpTopicListAddToHead(topicInfo, hw->help_dialog.display.topicTitleLbl, topicType, DtJUMP_LIST_MAX, hw->help_dialog.display.helpVolume, &hw->help_dialog.backtr.pJumpListHead, &hw->help_dialog.backtr.pJumpListTale, &hw->help_dialog.backtr.totalJumpNodes, -1); if (hw->help_dialog.backtr.totalJumpNodes <= 1) { XtSetSensitive(hw->help_dialog.menu.backBtn, FALSE); XtSetSensitive(hw->help_dialog.menu.popupBackBtn, FALSE); XtSetSensitive(hw->help_dialog.browser.btnBoxBackBtn, FALSE); } else { XtSetSensitive(hw->help_dialog.menu.backBtn, TRUE); XtSetSensitive(hw->help_dialog.menu.popupBackBtn, TRUE); XtSetSensitive(hw->help_dialog.browser.btnBoxBackBtn, TRUE); } } /***************************************************************************** * Function: void ProcessJumpBack(DtHelpDialogWidget nw); * * * Parameters: helpDialogWidget Specifies the current help dialog widget. * * Return Value: Void. * * Purpose: Pops the top element in the jump list off the stack * and jumps * * back to that topic. * *****************************************************************************/ static void ProcessJumpBack( DtHelpDialogWidget nw) { DtHelpDialogWidget hw = (DtHelpDialogWidget) nw ; DtTopicListStruct *pTemp= NULL; /* Pop the top element off our jump list and display the new top element */ _DtHelpTopicListDeleteHead(&hw->help_dialog.backtr.pJumpListHead, &hw->help_dialog.backtr.pJumpListTale, &hw->help_dialog.backtr.totalJumpNodes); /* Assign pTemp to the current head pointer for or jump list */ pTemp = hw->help_dialog.backtr.pJumpListHead; if (hw->help_dialog.backtr.totalJumpNodes <= 1) { XtSetSensitive(hw->help_dialog.menu.backBtn, FALSE); XtSetSensitive(hw->help_dialog.menu.popupBackBtn, FALSE); XtSetSensitive(hw->help_dialog.browser.btnBoxBackBtn, FALSE); } else { XtSetSensitive(hw->help_dialog.menu.backBtn, TRUE); XtSetSensitive(hw->help_dialog.menu.popupBackBtn, TRUE); XtSetSensitive(hw->help_dialog.browser.btnBoxBackBtn, TRUE); } /* Assign the jump values to or instance structure variables */ if (NULL != pTemp->helpVolume && strcmp (hw->help_dialog.display.helpVolume, pTemp->helpVolume) != 0) { XtFree(hw->help_dialog.display.helpVolume); hw->help_dialog.display.helpVolume = XtNewString(pTemp->helpVolume); /* Set our help volume flag so we open the proper volume */ hw->help_dialog.ghelp.volumeFlag = FALSE; } /* grab the current backtracs's topic title value */ XmStringFree(hw->help_dialog.display.topicTitleLbl); hw->help_dialog.display.topicTitleLbl = XmStringCopy(pTemp->topicTitleLbl); /* Assign our scrollbar value to our instance structure so we jump to the * proper location */ hw->help_dialog.backtr.scrollPosition = pTemp->scrollPosition; hw->help_dialog.display.helpType = pTemp->topicType; switch (pTemp->topicType) { case DtHELP_TYPE_TOPIC: /* Update our help dialog with top jump element */ XtFree(hw->help_dialog.display.locationId); hw->help_dialog.display.locationId = XtNewString(pTemp->locationId); _DtHelpSetupDisplayType(hw, TRUE, DtHISTORY_ONLY); break; case DtHELP_TYPE_STRING: case DtHELP_TYPE_DYNAMIC_STRING: XtFree(hw->help_dialog.display.stringData); hw->help_dialog.display.stringData = XtNewString(pTemp->locationId); _DtHelpSetupDisplayType(hw, TRUE, DtHISTORY_ONLY); break; case DtHELP_TYPE_MAN_PAGE: XtFree(hw->help_dialog.display.manPage); hw->help_dialog.display.manPage = XtNewString(pTemp->locationId); _DtHelpSetupDisplayType(hw, TRUE, DtHISTORY_ONLY); break; case DtHELP_TYPE_FILE: XtFree(hw->help_dialog.display.helpFile); hw->help_dialog.display.helpFile = XtNewString(pTemp->locationId); _DtHelpSetupDisplayType(hw, TRUE, DtHISTORY_ONLY); break; default: /* ERROR-MESSAGE */ /* This means the user used the worng help type */ XmeWarning((Widget)hw, (char*) HDMessage4); break; } /* End Switch Statement */ /* reset our scrollPosition back to its default here so in any other case, * we jump to the top of the topic */ hw->help_dialog.backtr.scrollPosition = -1; } /***************************************************************************** * Function: void _DtHelpDialogHypertextCB( * XtPointer pDisplayAreaStruct, * XtPointer clientData, * DtHelpHyperTextStruct *hyperData.) * * Parameters: pDisplayAreaStruct Specifies the curretn display are info. * * clientData Specifies the client data passed into * the hypertext callback. * * hyperData Specifies the current hypertext info * structure. * * Return Value: Void. * * Purpose: Process all hypertext requests in a given Help Dialogs * display area. * ****************************************************************************/ void _DtHelpDialogHypertextCB ( XtPointer pDisplayAreaStruct, XtPointer clientData, DtHelpHyperTextStruct *hyperData) { char *pTempAccessPath; char *pTempLocationId; DtHelpDialogCallbackStruct callData; char *tmpErrorMsg; DtHelpDialogWidget hw = (DtHelpDialogWidget) clientData ; /* We allow users to force a new window and override the jump-reuse * hyper type and force a new window to be used */ if ( ( ButtonRelease == hyperData->event->type && hyperData->event->xbutton.state & (ControlMask|ShiftMask)) || ( KeyPress == hyperData->event->type && hyperData->event->xkey.state & (ControlMask|ShiftMask))) hyperData->window_hint = _DtCvWindowHint_NewWindow; switch (hyperData->hyper_type) { case _DtCvLinkType_SameVolume: case _DtCvLinkType_CrossLink: switch (hyperData->window_hint) { case _DtCvWindowHint_CurrentWindow: ProcessJumpReuse((Widget)hw, hyperData); break; case _DtCvWindowHint_NewWindow: _DtHelpTurnOnHourGlass(XtParent(hw)); if (hw->help_dialog.display.hyperLinkCallback != NULL) { pTempAccessPath = _DtHelpParseAccessFile(hyperData->specification); if (pTempAccessPath != NULL) /* Use the New one */ callData.helpVolume = pTempAccessPath; else /* Use the old one */ callData.helpVolume = XtNewString(hw->help_dialog.display.helpVolume); callData.reason = DtCR_HELP_LINK_ACTIVATE; callData.event = hyperData->event; callData.locationId = _DtHelpParseIdString (hyperData->specification); callData.specification = NULL; callData.hyperType = DtHELP_LINK_TOPIC; callData.windowHint = DtHELP_NEW_WINDOW; /* Now, envoke the apps hyper callback */ XtCallCallbackList( (Widget)hw,hw->help_dialog.display.hyperLinkCallback,&callData); } else { /* The application did not register a hypertext callback so * we must generate the proper warning message and * continue! */ XmeWarning((Widget)hw, (char*) HDMessage6); /* Call jump-reuse procedure for default */ ProcessJumpReuse((Widget)hw, hyperData); } _DtHelpTurnOffHourGlass(XtParent(hw)); break; case _DtCvWindowHint_PopupWindow: _DtHelpTurnOnHourGlass(XtParent(hw)); pTempAccessPath = _DtHelpParseAccessFile(hyperData->specification); if (pTempAccessPath == NULL) /* Use the old one */ pTempAccessPath = XtNewString(hw->help_dialog.display.helpVolume); pTempLocationId = _DtHelpParseIdString(hyperData->specification); _DtHelpDisplayDefinitionBox((Widget)hw, (Widget **)&(hw->help_dialog.ghelp.definitionBox), pTempAccessPath, pTempLocationId); XtFree(pTempLocationId); XtFree(pTempAccessPath); _DtHelpTurnOffHourGlass(XtParent(hw)); break; default: /* Non valid window hint generage the proper * error message. */ /* ERROR-MESSAGE */ break; } /* End Window_hint Switch Statement */ break; case _DtCvLinkType_Execute: _DtHelpExecFilteredCmd((Widget) hw, hyperData->specification, DtHELP_ExecutionPolicy_STR, &hw->help_dialog.display, &hw->help_dialog.help); break; case _DtCvLinkType_ManPage: case _DtCvLinkType_AppDefine: case _DtCvLinkType_TextFile: /* Process Application Man page link or App Defined link types */ _DtHelpTurnOnHourGlass(XtParent(hw)); /* If the application registered a hypertext callback use it! */ if (hw->help_dialog.display.hyperLinkCallback != NULL) { /* Setup the DtHyperProcStructer to pass back to the * client as callData. */ callData.reason = DtCR_HELP_LINK_ACTIVATE; callData.event = hyperData->event; callData.locationId = NULL; callData.helpVolume = NULL; if (_DtCvLinkType_AppDefine == hyperData->hyper_type) { callData.locationId = _DtHelpParseIdString(hyperData->specification); callData.helpVolume = XtNewString(hw->help_dialog.display.helpVolume); } callData.specification = hyperData->specification; callData.hyperType = hyperData->hyper_type; callData.windowHint = hyperData->window_hint; XtCallCallbackList ((Widget) hw, hw->help_dialog.display.hyperLinkCallback, &callData); } else { /* The application did not register a hypertext * callback so we must generate the proper error * message and continue! */ XmeWarning((Widget)hw, (char*) HDMessage8); if (hyperData->hyper_type == DtHELP_LINK_APP_DEFINE) { tmpErrorMsg = XtNewString((char *)_DTGETMESSAGE(2, 56, "The selected Hypertext link is not supported within this application.")); _DtHelpErrorDialog(XtParent(hw),tmpErrorMsg); } else { tmpErrorMsg = XtNewString((char *)_DTGETMESSAGE(2, 57, "Links to Man Pages are not supported by this application.")); _DtHelpErrorDialog(XtParent(hw),tmpErrorMsg); } XtFree(tmpErrorMsg); } _DtHelpTurnOffHourGlass(XtParent(hw)); break; default: /* This catches bogus link types */ /* Non valid link type so we are dropping it and are generating * the proper error message. */ /* ERROR-MESSAGE */ XmeWarning((Widget)hw, (char*) HDMessage7); break; } /* End Switch Statement */ } /* End _DtHelpDialogHypertextCB */ /***************************************************************************** * Function: void ResizeHelpDialogCB() * * * Return Value: Void. * * Purpose: Adjust the widget instance values for rows and columns. * ****************************************************************************/ static void ResizeHelpDialogCB ( XtPointer clientData) { DtHelpDialogWidget hw = (DtHelpDialogWidget) clientData ; /* Re-Set our rows and colums values */ if ((hw->help_dialog.help.pDisplayArea != NULL) && hw->help_dialog.display.firstTimePopupFlag == TRUE) _DtHelpDisplayAreaDimensionsReturn (hw->help_dialog.help.pDisplayArea, &(hw->help_dialog.display.textRows), &(hw->help_dialog.display.textColumns)); } /***************************************************************************** * Function: static void ProcessJumpReuse(nw, hyperData) * Widget nw; * DtHelpHyperTextStruct *hyperData; * * Parameters: nw Specifies the widget ID of the current help dialog * widget. * * hyperData Specifies the hypertext data callback struct. * * Return Value: Void. * * Purpose: Process the jump-reuse hypertext link data. * *****************************************************************************/ static void ProcessJumpReuse( Widget nw, DtHelpHyperTextStruct *hyperData) { DtHelpDialogWidget hw = (DtHelpDialogWidget) nw; char *pTempAccessPath; char *pTempLocationId; /* Parse our specification into the proper fields in our instance * record. */ pTempAccessPath = _DtHelpParseAccessFile(hyperData->specification); if (pTempAccessPath != NULL) { /* Free the old one and assign the new path */ XtFree(hw->help_dialog.display.helpVolume); hw->help_dialog.display.helpVolume = pTempAccessPath; hw->help_dialog.ghelp.volumeFlag = FALSE; } /* Free old copy first ??? */ pTempLocationId = _DtHelpParseIdString(hyperData->specification); XtFree(hw->help_dialog.display.locationId); hw->help_dialog.display.locationId = pTempLocationId; hw->help_dialog.display.helpType = DtHELP_TYPE_TOPIC; _DtHelpSetupDisplayType(hw, TRUE, DtHISTORY_AND_JUMP); } /***************************************************************************** * Function: void _DtHelpTopicListFree (DtTopicListStruct *pHead); * * * Parameters: pHead Specifies the head pointer to the topic list. * * Return Value: Void. * * Purpose: Frees all elements in a Topic List. * *****************************************************************************/ void _DtHelpTopicListFree( DtTopicListStruct *pHead) { DtTopicListStruct *pTemp=NULL; while (pHead != NULL) { /* Free up each element in the current node */ pTemp = pHead; pHead = pHead->pNext; pTemp->pNext = NULL; pTemp->pPrevious = NULL; /* Free the id String and AccessPath elements */ XtFree(pTemp->locationId); XtFree(pTemp->helpVolume); XmStringFree(pTemp->topicTitleLbl); /* Now, free the whole node */ XtFree((char *)pTemp); } } /***************************************************************************** * Function: void CleanUpHelpDialog(DtHelpDialogWidget nw, * int cleanUpKind); * * * Parameters: nw Specifies the current help dialog widget. * cleanUpKind Specifies the type of clean up we are doing, * celan up and reuse or clean up and destroy. * * Return Value: Void. * * Purpose: This function will re-initializes a Help Dialog Widget to * known good starting values or clean up in prepretion for * an impending destroy. * *****************************************************************************/ static void CleanUpHelpDialog( Widget nw, int cleanUpKind) { Arg args[10]; DtHistoryListStruct *pTempVolume=NULL; DtHistoryListStruct *pTempVolumeCurrent=NULL; DtHelpDialogWidget hw = (DtHelpDialogWidget) nw; XtFree(hw->help_dialog.print.printVolume); hw->help_dialog.print.printVolume = NULL; /* must clean volume list and topic list from history */ pTempVolume = hw->help_dialog.history.pHistoryListHead; while (pTempVolume != NULL) { _DtHelpTopicListFree(pTempVolume->pTopicHead); pTempVolumeCurrent = pTempVolume; pTempVolume = pTempVolume->pNext; XmStringFree(pTempVolumeCurrent->itemTitle); XtFree((char *)pTempVolumeCurrent); } hw->help_dialog.history.pHistoryListHead = NULL; _DtHelpTopicListFree(hw->help_dialog.history.pPathListHead); hw->help_dialog.history.pPathListHead = NULL; hw->help_dialog.history.pPathListTale = NULL; hw->help_dialog.history.totalPathNodes = 0; /* Free our jump list display stuff */ _DtHelpTopicListFree(hw->help_dialog.backtr.pJumpListHead); hw->help_dialog.backtr.pJumpListHead = NULL; hw->help_dialog.backtr.pJumpListTale = NULL; hw->help_dialog.backtr.totalJumpNodes = 0; /* do nothing for index search dialog on a Clean for Reuse */ /* Close our current help volume */ if (hw->help_dialog.display.volumeHandle != NULL) { _DtHelpCloseVolume(hw->help_dialog.display.volumeHandle); hw->help_dialog.display.volumeHandle = NULL; } /* Depending on weither we are just closing this help dialog or destroying * it we will do the following! */ if (cleanUpKind == DtCLEAN_FOR_DESTROY) { /* Free any remaining char * values we malloc'ed in our help dialog */ XtFree(hw->help_dialog.display.locationId); XtFree(hw->help_dialog.display.helpVolume); XtFree(hw->help_dialog.display.manPage); XtFree(hw->help_dialog.display.stringData); XtFree(hw->help_dialog.display.helpFile); XtFree(hw->help_dialog.display.topicTitleStr); if (hw->help_dialog.display.topicTitleLbl != NULL) XmStringFree(hw->help_dialog.display.topicTitleLbl); XtFree(hw->help_dialog.ghelp.parentId); XtFree(hw->help_dialog.print.printer); if (hw->help_dialog.print.helpPrint != _DtHelpDefaultHelpPrint) XtFree(hw->help_dialog.print.helpPrint); /* Clean and close and destroy (True) our index search dialog */ _DtHelpGlobSrchCleanAndClose(&hw->help_dialog.srch,True); /* Set our current topic variables to initial values */ _DtHelpCommonHelpClean(&hw->help_dialog.help,True); } else { /* Reset our buttons to the proper state */ XtSetSensitive(hw->help_dialog.menu.backBtn, FALSE); XtSetSensitive(hw->help_dialog.menu.popupBackBtn, FALSE); XtSetSensitive(hw->help_dialog.browser.btnBoxBackBtn, FALSE); /* Clean and close our index search dialog */ _DtHelpGlobSrchCleanAndClose(&hw->help_dialog.srch,False); if (hw->help_dialog.history.historyWidget != NULL) { XtUnmanageChild(hw->help_dialog.history.historyWidget); } if (hw->help_dialog.print.printForm != NULL) { XtUnmanageChild(hw->help_dialog.print.printForm); } /* Free our history display stuff */ if (hw->help_dialog.history.volumeList != NULL) { XtSetArg(args[0], XmNitems, NULL); XtSetArg(args[1], XmNitemCount, 0); XtSetValues(hw->help_dialog.history.volumeList, args, 2); } if (hw->help_dialog.history.topicList != NULL) { XtSetArg(args[0], XmNitems, NULL); XtSetArg(args[1], XmNitemCount, 0); XtSetValues(hw->help_dialog.history.topicList, args, 2); } /* Set our toc areay area to a null starting vlaues */ _DtHelpDisplayAreaClean(hw->help_dialog.browser.pTocArea); /* Set our current topic variables to initial values */ _DtHelpCommonHelpClean(&hw->help_dialog.help,False); } } /**************************************************************************** * Function: CatchClose( Widget w); * * Parameters: * * Return Value: Void. * * Purpose: Catches the window manager close requests and assigns our * CloseHelpCB to handel them. * ***************************************************************************/ static void CatchClose ( Widget widget) { Atom wm_delete_window; Arg args[2]; /* Grab the window mgr close */ wm_delete_window = XmInternAtom(XtDisplay(XtParent(widget)), "WM_DELETE_WINDOW", FALSE); XtSetArg(args[0], XmNdeleteResponse, XmDO_NOTHING); /* Current Help Dialog Window */ XmAddWMProtocolCallback(XtParent(widget),wm_delete_window, (XtCallbackProc)CloseHelpCB, (XtPointer) widget); XtSetValues(XtParent(widget), args, 1); } /************************************************************************ * Function: CloseHelpCB() * * Close the Help Dialog Window * ************************************************************************/ static void CloseHelpCB ( Widget w, XtPointer clientData, XtPointer callData) { DtHelpDialogWidget hw = (DtHelpDialogWidget) clientData; DtHelpDialogCallbackStruct callDataInfo; XmPushButtonCallbackStruct *callbackStruct = (XmPushButtonCallbackStruct*) callData; /* * Check to see if a selection is in process. * If so, cancel the selection and don't close the dialog */ if (_DtHelpCancelSelection(hw->help_dialog.help.pDisplayArea) == True) return; /* No selection in progress. Close the dialog. * * ??? By definition, when a user closes a Help Dialog if it is * used again by the application the state will be new. So we should * flush out any info currently in the help, history, and search dialogs. */ CleanUpHelpDialog((Widget)hw, DtCLEAN_FOR_REUSE); /* Look to see if they registered their own close callback */ if (hw->help_dialog.ghelp.closeCallback != NULL) { callDataInfo.reason = DtCR_HELP_CLOSE; callDataInfo.event = callbackStruct->event; callDataInfo.locationId = NULL; callDataInfo.helpVolume = NULL; callDataInfo.specification = NULL; callDataInfo.hyperType = 0; /* All we do is envoke the applications close callback */ XtCallCallbackList((Widget)hw,hw->help_dialog.ghelp.closeCallback, (XtPointer) &callDataInfo); } else XtUnmanageChild((Widget)hw); } /********************************************************************* * Function: SetupHelpDialogMenus * * This procedure build the menubar pulldows buttons for the Index * Browser and the Topic Viewer. * * Called by: MakeIndexWindow, and MakeTopicWindow. *********************************************************************/ static Widget SetupHelpDialogMenus( Widget parent) { Widget menuBar; Widget c[10]; Widget cascadeB5; Widget menupane1, menupane2, menupane3, menupane4, menupane5; Widget helpBtn1, helpBtn2, helpBtn3, helpBtn4, helpBtn5, helpBtn6; Arg args[10]; int n; XmString labelStr; char *mnemonic; DtHelpListStruct *pHelpInfo; DtHelpDialogWidget hw = (DtHelpDialogWidget) parent; /* Build the menubar */ n = 0; menuBar = XmCreateMenuBar (parent, "menuBar", args, n); XtManageChild (menuBar); /******************************************************* * Menupane: Close, and related buttons *******************************************************/ n = 0; XtSetArg(args[n], XmNmarginWidth, 0); ++n; XtSetArg(args[n], XmNmarginHeight, 0); ++n; menupane1 = XmCreatePulldownMenu(menuBar, "fileMenu", args, n); /* Add callback for File Menu */ pHelpInfo = _DtHelpListAdd(DtHELP_FileMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback((Widget) menupane1, XmNhelpCallback, _DtHelpCB, (XtPointer) pHelpInfo); /* Print button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 1,"Print..."))); mnemonic = ((char *)_DTGETMESSAGE(2, 2,"P")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[0] = hw->help_dialog.menu.printBtn = XmCreatePushButtonGadget(menupane1, "print", args, n); XtAddCallback(hw->help_dialog.menu.printBtn,XmNactivateCallback, DisplayPrintCB, (XtPointer) hw); XmStringFree(labelStr); if (hw->help_dialog.menu.showDupBtn == True) { /* Duplicate button */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 5,"New Window..."))); mnemonic = ((char *)_DTGETMESSAGE(2, 6,"W")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[1] = hw->help_dialog.menu.newWindowBtn = XmCreatePushButtonGadget(menupane1,"newWindowBtn", args, n); XtAddCallback(hw->help_dialog.menu.newWindowBtn,XmNactivateCallback, _DtHelpDuplicateWindowCB, (XtPointer) hw); XmStringFree(labelStr); /* Exit button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 3,"Close"))); mnemonic = ((char *)_DTGETMESSAGE(2, 4,"C")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[2] = hw->help_dialog.menu.closeBtn = XmCreatePushButtonGadget(menupane1,"close", args, n); XtAddCallback(hw->help_dialog.menu.closeBtn,XmNactivateCallback, CloseHelpCB, (XtPointer) hw); XmStringFree(labelStr); /* set the cancel button (for KCancel) */ hw->bulletin_board.cancel_button= hw->help_dialog.menu.closeBtn; /* Manage the children for the File menu pane */ XtManageChildren(c, 3); } else { /* Exit button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 3,"Close"))); mnemonic = ((char *)_DTGETMESSAGE(2, 4,"C")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[1] = hw->help_dialog.menu.closeBtn = XmCreatePushButtonGadget(menupane1,"close", args, n); XtAddCallback(hw->help_dialog.menu.closeBtn,XmNactivateCallback, CloseHelpCB, (XtPointer) hw); XmStringFree(labelStr); /* set the cancel button (for KCancel) */ hw->bulletin_board.cancel_button= hw->help_dialog.menu.closeBtn; /* Manage the children for the File menu pane */ XtManageChildren(c, 2); } /******************************************************* * Menupane: Edit, (Copy) *******************************************************/ n = 0; XtSetArg(args[n], XmNmarginWidth, 0); ++n; XtSetArg(args[n], XmNmarginHeight, 0); ++n; menupane2 = XmCreatePulldownMenu(menuBar, "editMenu", args, n); /* Add callback for Edit Menu */ pHelpInfo = _DtHelpListAdd(DtHELP_EditMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback((Widget) menupane2, XmNhelpCallback, _DtHelpCB, (XtPointer) pHelpInfo); /* Edit button */ labelStr = XmStringCreateLocalized(( (char *)_DTGETMESSAGE(2,7,"Copy"))); mnemonic = ((char *)_DTGETMESSAGE(2, 8,"C")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[0] = hw->help_dialog.menu.copyBtn = XmCreatePushButtonGadget (menupane2, "copy", args, n); XtAddCallback(hw->help_dialog.menu.copyBtn,XmNactivateCallback, CopyTextCB, (XtPointer) hw); XmStringFree(labelStr); XtManageChildren(c, 1); /******************************************************* * Menupane: Search, (Topic Index) *******************************************************/ n = 0; XtSetArg(args[n], XmNmarginWidth, 0); ++n; XtSetArg(args[n], XmNmarginHeight, 0); ++n; menupane3 = XmCreatePulldownMenu(menuBar, "searchMenu", args, n); /* Add callback for Search Menu */ pHelpInfo = _DtHelpListAdd(DtHELP_SearchMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback((Widget) menupane3, XmNhelpCallback, _DtHelpCB, (XtPointer) pHelpInfo); /* Search button */ labelStr = XmStringCreateLocalized(( (char *)_DTGETMESSAGE(2, 9,"Index..."))); mnemonic = ((char *)_DTGETMESSAGE(2, 10,"I")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[0] = hw->help_dialog.menu.keyBtn = XmCreatePushButtonGadget (menupane3, "keyword", args, n); XtAddCallback(hw->help_dialog.menu.keyBtn,XmNactivateCallback, _DtHelpDisplayIndexCB, (XtPointer) hw); XmStringFree(labelStr); XtManageChildren(c, 1); /******************************************************* * Menupane: Navigate, and related buttons *******************************************************/ n = 0; XtSetArg(args[n], XmNmarginWidth, 0); ++n; XtSetArg(args[n], XmNmarginHeight, 0); ++n; menupane4 = XmCreatePulldownMenu(menuBar, "navigateMenu", args, n); /* Add callback for Navigate Menu */ pHelpInfo = _DtHelpListAdd(DtHELP_NavigateMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback((Widget) menupane4 , XmNhelpCallback, _DtHelpCB, (XtPointer) pHelpInfo); /* Back Button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 13,"Backtrack"))); mnemonic = ((char *)_DTGETMESSAGE(2, 14,"B")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[0] = hw->help_dialog.menu.backBtn = XmCreatePushButtonGadget(menupane4, "backTrack", args, n); XtAddCallback(hw->help_dialog.menu.backBtn,XmNactivateCallback, _DtHelpDisplayBackCB, (XtPointer) hw); XtSetSensitive(hw->help_dialog.menu.backBtn, FALSE); XmStringFree(labelStr); /* Top Button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 11,"Home Topic"))); mnemonic = ((char *)_DTGETMESSAGE(2, 12,"T")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[1] = hw->help_dialog.menu.topBtn = XmCreatePushButtonGadget(menupane4, "homeTopic", args, n); XtAddCallback(hw->help_dialog.menu.topBtn,XmNactivateCallback, DisplayTopLevelCB, (XtPointer) hw); XmStringFree(labelStr); /* Place a menu break here */ n = 0; c[2] = XmCreateSeparatorGadget(menupane4, "seporator",args, n); /* History Button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 15,"History..."))); mnemonic = ((char *)_DTGETMESSAGE(2, 16,"H")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[3] = hw->help_dialog.menu.historyBtn = XmCreatePushButtonGadget(menupane4, "history",args, n); XtAddCallback(hw->help_dialog.menu.historyBtn,XmNactivateCallback, _DtHelpDisplayHistoryCB, (XtPointer) hw); XmStringFree(labelStr); /* Manage all the children of this manu pane */ XtManageChildren(c, 4); /******************************************************* * Menupane: Help, and related buttons *******************************************************/ n = 0; XtSetArg(args[n], XmNmarginWidth, 0); ++n; XtSetArg(args[n], XmNmarginHeight, 0); ++n; menupane5 = XmCreatePulldownMenu(menuBar, "helpMenu", args, n); /* Add callback for Help Menu */ pHelpInfo = _DtHelpListAdd(DtHELP_HelpMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback((Widget) menupane5, XmNhelpCallback, _DtHelpCB, (XtPointer) pHelpInfo); /* On HELP button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 17,"Overview - Using Help"))); mnemonic = ((char *)_DTGETMESSAGE(2, 18,"v")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[0] = helpBtn1 = XmCreatePushButtonGadget(menupane5, "usingHelp", args, n); pHelpInfo = _DtHelpListAdd(DtHELP_onHelpMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback(helpBtn1, XmNactivateCallback, _DtHelpCB, (XtPointer) pHelpInfo); XmStringFree(labelStr); /* Place a menu break here */ n = 0; c[1] = XmCreateSeparatorGadget(menupane5, "seporator",args, n); /* On Table Of Contents Help button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2,19,"Table Of Contents"))); mnemonic = ((char *)_DTGETMESSAGE(2, 20, "C")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[2] = helpBtn2 = XmCreatePushButtonGadget(menupane5, "tableOfContents", args, n); pHelpInfo = _DtHelpListAdd(DtHELP_onTableOfContenseMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback(helpBtn2, XmNactivateCallback, _DtHelpCB, (XtPointer) pHelpInfo); XmStringFree(labelStr); /* On Tasks Help button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 21,"Tasks"))); mnemonic = ((char *)_DTGETMESSAGE(2, 22, "T")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[3] = helpBtn3 = XmCreatePushButtonGadget(menupane5, "tasks", args, n); pHelpInfo = _DtHelpListAdd(DtHELP_onTasksMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback(helpBtn3, XmNactivateCallback, _DtHelpCB, (XtPointer) pHelpInfo); XmStringFree(labelStr); /* On Reference button */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 23,"Reference"))); mnemonic = ((char *)_DTGETMESSAGE(2, 24,"R")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[4] = helpBtn4 = XmCreatePushButtonGadget(menupane5, "reference",args, n); pHelpInfo = _DtHelpListAdd(DtHELP_onReferenceMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback(helpBtn4, XmNactivateCallback, _DtHelpCB, (XtPointer) pHelpInfo); XmStringFree(labelStr); /* On Mouse & Keyboard button */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 25,"Mouse and Keyboard"))); mnemonic = ((char *)_DTGETMESSAGE(2, 26,"M")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[5] = helpBtn5 = XmCreatePushButtonGadget(menupane5, "reference",args, n); pHelpInfo = _DtHelpListAdd(DtHELP_onMouseAndKeysMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback(helpBtn5, XmNactivateCallback, _DtHelpCB, (XtPointer) pHelpInfo); XmStringFree(labelStr); /* Place a menu break here */ n = 0; c[6] = XmCreateSeparatorGadget(menupane5, "seporator",args, n); /* On Version */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 27,"About Help"))); mnemonic = ((char *)_DTGETMESSAGE(2, 28,"A")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[7] = helpBtn6 = XmCreatePushButtonGadget(menupane5, "reference",args, n); pHelpInfo = _DtHelpListAdd(DtHELP_onVersionMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback(helpBtn6, XmNactivateCallback, _DtHelpCB, (XtPointer) pHelpInfo); XmStringFree(labelStr); /* Manage the children for the Help menu pane */ XtManageChildren(c, 8); /* Create Cascade buttons for menubar */ /* File Menu */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 29,"File"))); mnemonic = ((char *)_DTGETMESSAGE(2, 30,"F")); n = 0; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; XtSetArg(args[n], XmNsubMenuId, menupane1); n++; XtSetArg(args[n], XmNlabelString, labelStr); n++; c[0] = XmCreateCascadeButton(menuBar,"file",args, n); XmStringFree(labelStr); /* Edit Menu */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 37,"Edit"))); mnemonic = ((char *)_DTGETMESSAGE(2, 38,"E")); n = 0; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; XtSetArg(args[n], XmNsubMenuId, menupane2); n++; XtSetArg(args[n], XmNlabelString, labelStr); n++; c[1] = XmCreateCascadeButton(menuBar, "edit", args, n); XmStringFree(labelStr); /* Search Menu */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 31,"Search"))); mnemonic = ((char *)_DTGETMESSAGE(2, 32,"S")); n = 0; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; XtSetArg(args[n], XmNsubMenuId, menupane3); n++; XtSetArg(args[n], XmNlabelString, labelStr); n++; c[2] = XmCreateCascadeButton(menuBar, "search", args, n); XmStringFree(labelStr); /* Navigate Menu */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 33,"Navigate"))); mnemonic = ((char *)_DTGETMESSAGE(2, 34,"N")); n = 0; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; XtSetArg(args[n], XmNsubMenuId, menupane4); n++; XtSetArg(args[n], XmNlabelString, labelStr); n++; c[3] = XmCreateCascadeButton(menuBar, "navigate", args, n); XmStringFree(labelStr); /* Help Menu */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 35,"Help"))); mnemonic = ((char *)_DTGETMESSAGE(2, 36,"H")); n = 0; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; XtSetArg(args[n], XmNsubMenuId, menupane5); n++; XtSetArg(args[n], XmNlabelString, labelStr); n++; c[4] = cascadeB5 = XmCreateCascadeButton(menuBar, "help", args, n); XmStringFree(labelStr); XtManageChildren(c, 5); /* Attaches the Help menupane to the right side */ n = 0; XtSetArg (args[n], XmNmenuHelpWidget, cascadeB5); n++; XtSetValues (menuBar, args, n); return(menuBar); } /* End SetupHelpDialogMenus */ /********************************************************************* * Function: CreatePopupMenu * * This procedure builds the popup menu for the display area * **********************************************************************/ static Widget CreatePopupMenu( Widget nw) { Widget popup; Widget c[10]; Arg args[10]; int n; XmString labelStr; DtHelpDialogWidget hw = (DtHelpDialogWidget) nw; DtHelpListStruct *pHelpInfo; char *mnemonic; int numButtons = XGetPointerMapping(XtDisplay(nw),(unsigned char *)NULL, 0); /* Build the popup */ /* If no Btn3 then use Btn2 to post the menu */ n = 0; if (numButtons < 3) { XtSetArg(args[n], XmNwhichButton, Button2); n++; } popup = XmCreatePopupMenu ( _DtHelpDisplayAreaWidget(hw->help_dialog.help.pDisplayArea), "popup", args, n); /* Add our button three event handler to our newly created display area */ XtAddEventHandler( _DtHelpDisplayAreaWidget(hw->help_dialog.help.pDisplayArea), ButtonPressMask, FALSE, (XtEventHandler)ProcessBMenuBackCB, hw); /* Add Help callback for Popup Menu */ pHelpInfo = _DtHelpListAdd(DtHELP_PopupMenu_STR, (Widget) hw, &hw->help_dialog.help, &hw->help_dialog.help.pHelpListHead); XtAddCallback((Widget) popup, XmNhelpCallback, _DtHelpCB, (XtPointer) pHelpInfo); /* Build the popup menu items */ /* Popup Label*/ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(3, 4,"Help"))); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; c[0] = XmCreateLabelGadget(popup, "popupLabel", args, n); XmStringFree(labelStr); /* Place a menu break here */ n = 0; c[1] = XmCreateSeparatorGadget(popup, "seporator",args, n); /* Back Button */ labelStr = XmStringCreateLocalized(((char *) _DTGETMESSAGE(2, 13,"Backtrack"))); mnemonic = ((char *)_DTGETMESSAGE(2, 14,"B")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[2] = hw->help_dialog.menu.popupBackBtn = XmCreatePushButtonGadget(popup, "backTrack", args, n); XmStringFree(labelStr); XtAddCallback(hw->help_dialog.menu.popupBackBtn,XmNactivateCallback, _DtHelpDisplayBackCB, (XtPointer) hw); XtSetSensitive(hw->help_dialog.menu.popupBackBtn, FALSE); /* Top Button */ labelStr = XmStringCreateLocalized(((char *)_DTGETMESSAGE(2, 11,"Home Topic"))); mnemonic = ((char *)_DTGETMESSAGE(2, 12,"T")); n = 0; XtSetArg(args[n], XmNlabelString, labelStr); n++; XtSetArg(args[n], XmNmnemonic, mnemonic[0]); n++; c[3] = hw->help_dialog.menu.popupTopBtn = XmCreatePushButtonGadget(popup, "homeTopic", args, n); XmStringFree(labelStr); XtAddCallback(hw->help_dialog.menu.popupTopBtn,XmNactivateCallback, DisplayTopLevelCB, (XtPointer) hw); XtManageChildren(c, 4); return(popup); }