00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #ifdef G4UI_BUILD_XM_SESSION
00034
00035 #include "G4Types.hh"
00036
00037 #include <string.h>
00038
00039 #include <X11/Intrinsic.h>
00040 #include <X11/Shell.h>
00041 #include <X11/keysym.h>
00042
00043 #include <Xm/Xm.h>
00044 #include <Xm/Command.h>
00045 #include <Xm/RowColumn.h>
00046 #include <Xm/Form.h>
00047 #include <Xm/PushB.h>
00048 #include <Xm/CascadeB.h>
00049 #include <Xm/Text.h>
00050
00051 #include "G4UIXm.hh"
00052 #include "G4UImanager.hh"
00053 #include "G4StateManager.hh"
00054 #include "G4UIcommandTree.hh"
00055 #include "G4UIcommandStatus.hh"
00056
00057 #include "G4Xt.hh"
00058
00059 #include <stdlib.h>
00060
00061 static void XmTextAppendString (Widget,char*);
00062
00063 static void clearButtonCallback (Widget,XtPointer,XtPointer);
00064
00065 static char* XmConvertCompoundStringToString (XmString,int);
00066 static G4bool ConvertStringToInt(const char*,int&);
00067 static void ExecuteChangeSizeFunction(Widget);
00068
00069 static G4bool exitSession = true;
00070 static G4bool exitPause = true;
00071 static G4bool exitHelp = true;
00072
00073 G4UIXm::G4UIXm (
00074 int argc
00075 ,char** argv
00076 )
00077 :shell(NULL)
00078 ,command(NULL)
00079 ,menuBar(NULL)
00080 ,text(NULL)
00081 ,fHelp(false)
00082 ,fHelpChoice(0)
00083
00085 {
00086 G4UImanager* UI = G4UImanager::GetUIpointer();
00087 if(UI!=NULL) UI->SetSession(this);
00088
00089 G4Xt* interactorManager = G4Xt::getInstance (argc,argv,(char*)"Xm");
00090
00091 Widget top = (Widget)interactorManager->GetMainInteractor();
00092
00093 if(getenv("XENVIRONMENT")==NULL) {
00094 XrmDatabase database = XrmGetDatabase(XtDisplay(top));
00095 if(database!=NULL) {
00096 XrmPutLineResource(&database,"*topShadowColor:white");
00097 XrmPutLineResource(&database,"*bottomShadowColor:black");
00098 XrmPutLineResource(&database,"*foreground:black");
00099 XrmPutLineResource(&database,"*background:lightgrey");
00100 XrmPutLineResource(&database,"*borderColor:lightgrey");
00101 XrmPutLineResource(&database,"*fontList:-*-helvetica-bold-r-*-*-*-120-*-*-*-*-iso8859-1");
00102 XrmPutLineResource(&database,"*text.background:white");
00103 XrmPutLineResource(&database,"*text.fontList:*courier*-r-*--14-*");
00104 XrmPutLineResource(&database,"*text.maxLength:8000");
00105 }
00106 }
00107
00108 Arg args[9];
00109 XtSetArg(args[0],XmNkeyboardFocusPolicy,XmPOINTER);
00110 shell = XtAppCreateShell ("G4UIXm","G4UIXm",
00111 topLevelShellWidgetClass,XtDisplay(top),
00112 args,1);
00113 form = XmCreateForm (shell,(char*)"form",NULL,0);
00114 XtManageChild (form);
00115
00116 XtSetArg(args[0],XmNtopAttachment ,XmATTACH_FORM);
00117 XtSetArg(args[1],XmNleftAttachment ,XmATTACH_FORM);
00118 XtSetArg(args[2],XmNrightAttachment ,XmATTACH_FORM);
00119 menuBar = XmCreateMenuBar (form,(char*)"menuBar",args,3);
00120
00121 XtSetArg(args[0],XmNtopAttachment ,XmATTACH_NONE);
00122 XtSetArg(args[1],XmNleftAttachment ,XmATTACH_FORM);
00123 XtSetArg(args[2],XmNrightAttachment ,XmATTACH_FORM);
00124 XtSetArg(args[3],XmNbottomAttachment ,XmATTACH_FORM);
00125 command = XmCreateCommand (form,(char*)"command",args,4);
00126 XtManageChild (command);
00127
00128 XtSetArg(args[0],XmNtopAttachment ,XmATTACH_NONE);
00129 XtSetArg(args[1],XmNleftAttachment ,XmATTACH_FORM);
00130 XtSetArg(args[2],XmNrightAttachment ,XmATTACH_FORM);
00131 XtSetArg(args[3],XmNbottomAttachment,XmATTACH_WIDGET);
00132 XtSetArg(args[4],XmNbottomWidget ,command);
00133 XmString cps = XmStringLtoRCreate((char*)"Clear",XmSTRING_DEFAULT_CHARSET);
00134 XtSetArg (args[5],XmNlabelString,cps);
00135 Widget clearButton = XmCreatePushButton(form,(char*)"clearButton",args,6);
00136 XmStringFree (cps);
00137 XtManageChild (clearButton);
00138
00139 XtSetArg(args[0],XmNtopAttachment ,XmATTACH_WIDGET);
00140 XtSetArg(args[1],XmNtopWidget ,menuBar);
00141 XtSetArg(args[2],XmNleftAttachment ,XmATTACH_FORM);
00142 XtSetArg(args[3],XmNrightAttachment ,XmATTACH_FORM);
00143 XtSetArg(args[4],XmNbottomAttachment,XmATTACH_WIDGET);
00144 XtSetArg(args[5],XmNbottomWidget ,clearButton);
00145 XtSetArg(args[6],XmNeditMode ,XmMULTI_LINE_EDIT);
00146 XtSetArg(args[7],XmNrows ,12);
00147 XtSetArg(args[8],XmNcolumns ,80);
00148 text = XmCreateScrolledText (form,(char*)"text",args,9);
00149 XtManageChild (text);
00150
00151 XtAddCallback(clearButton,XmNactivateCallback,
00152 clearButtonCallback,(XtPointer)text);
00153 XtAddCallback(command,XmNcommandEnteredCallback,
00154 CommandEnteredCallback,(XtPointer)this);
00155
00156 Widget commandText = XmCommandGetChild(command,XmDIALOG_COMMAND_TEXT);
00157 XtAddEventHandler(commandText,KeyPressMask,False,keyHandler,(XtPointer)this);
00158
00159 XtRealizeWidget(shell);
00160 XtMapWidget(shell);
00161
00162 if(UI!=NULL) UI->SetCoutDestination(this);
00163 }
00164
00165 G4UIXm::~G4UIXm(
00166 )
00167
00169 {
00170 G4UImanager* UI = G4UImanager::GetUIpointer();
00171 if(UI!=NULL) {
00172 UI->SetSession(NULL);
00173 UI->SetCoutDestination(NULL);
00174 }
00175 XtDestroyWidget(shell);
00176 }
00177
00178 G4UIsession* G4UIXm::SessionStart (
00179 )
00180
00182 {
00183 G4Xt* interactorManager = G4Xt::getInstance ();
00184 Prompt("session");
00185 exitSession = false;
00186 interactorManager->DisableSecondaryLoop ();
00187 void* event;
00188 while((event = interactorManager->GetEvent())!=NULL) {
00189 interactorManager->DispatchEvent(event);
00190 if(exitSession==true) break;
00191 }
00192 interactorManager->EnableSecondaryLoop ();
00193 return this;
00194 }
00195
00196 void G4UIXm::Prompt (
00197 G4String aPrompt
00198 )
00199
00201 {
00202 Arg args[1];
00203 char* str = (char*)XtNewString(aPrompt.data());
00204 XmString cps = XmStringLtoRCreate(str,XmSTRING_DEFAULT_CHARSET);
00205 XtFree(str);
00206 XtSetArg(args[0],XmNpromptString,cps);
00207 XtSetValues(command,args,1);
00208 XmStringFree(cps);
00209 }
00210
00211 void G4UIXm::SessionTerminate (
00212 )
00213
00215 {
00216 }
00217
00218 void G4UIXm::PauseSessionStart (
00219 const G4String& a_state
00220 )
00221
00223 {
00224 if(a_state=="G4_pause> ") {
00225 SecondaryLoop ("Pause, type continue to exit this state");
00226 }
00227
00228 if(a_state=="EndOfEvent") {
00229
00230 SecondaryLoop ("End of event, type continue to exit this state");
00231 }
00232 }
00233
00234 void G4UIXm::SecondaryLoop (
00235 G4String a_prompt
00236 )
00237
00239 {
00240 G4Xt* interactorManager = G4Xt::getInstance ();
00241 Prompt(a_prompt);
00242 exitPause = false;
00243 void* event;
00244 while((event = interactorManager->GetEvent())!=NULL) {
00245 interactorManager->DispatchEvent(event);
00246 if(exitPause==true) break;
00247 }
00248 Prompt("session");
00249 }
00250
00251 G4int G4UIXm::ReceiveG4cout (
00252 const G4String& a_string
00253 )
00254
00256 {
00257 XmTextAppendString(text,(char*)a_string.data());
00258 return 0;
00259 }
00260
00261 G4int G4UIXm::ReceiveG4cerr (
00262 const G4String& a_string
00263 )
00264
00266 {
00267 XmTextAppendString(text,(char*)a_string.data());
00268 return 0;
00269 }
00270
00271 G4bool G4UIXm::GetHelpChoice(
00272 G4int& aInt
00273 )
00274
00276 {
00277 fHelp = true;
00278
00279 G4Xt* interactorManager = G4Xt::getInstance ();
00280 Prompt("Help");
00281 exitHelp = false;
00282 void* event;
00283 while((event = interactorManager->GetEvent())!=NULL) {
00284 interactorManager->DispatchEvent(event);
00285 if(exitHelp==true) break;
00286 }
00287 Prompt("session");
00288
00289 if(fHelp==false) return false;
00290 aInt = fHelpChoice;
00291 fHelp = false;
00292 return true;
00293 }
00294
00295 void G4UIXm::ExitHelp(
00296 ) const
00297
00299 {
00300 }
00301
00302 void G4UIXm::AddMenu (
00303 const char* a_name
00304 ,const char* a_label
00305 )
00306
00308 {
00309 if(menuBar==NULL) return;
00310 if(a_name==NULL) return;
00311 if(a_label==NULL) return;
00312 XtManageChild (menuBar);
00313
00314 Widget widget;
00315 widget = XmCreatePulldownMenu (menuBar,(char*)a_name,NULL,0);
00316 AddInteractor (a_name,(G4Interactor)widget);
00317
00318 Arg args[2];
00319 XmString cps = XmStringLtoRCreate((char*)a_label,XmSTRING_DEFAULT_CHARSET);
00320 XtSetArg (args[0],XmNlabelString,cps);
00321 XtSetArg (args[1],XmNsubMenuId,widget);
00322 widget = XmCreateCascadeButton (menuBar,(char*)a_name,args,2);
00323 XmStringFree (cps);
00324 XtManageChild (widget);
00325 ExecuteChangeSizeFunction(form);
00326 }
00327
00328 void G4UIXm::AddButton (
00329 const char* a_menu
00330 ,const char* a_label
00331 ,const char* a_command
00332 )
00333
00335 {
00336 if(a_menu==NULL) return;
00337 if(a_label==NULL) return;
00338 if(a_command==NULL) return;
00339 Widget parent = (Widget)GetInteractor(a_menu);
00340 if(parent==NULL) return;
00341 Widget widget = XmCreatePushButton(parent,(char*)a_label,NULL,0);
00342 XtManageChild (widget);
00343 XtAddCallback (widget,XmNactivateCallback,ButtonCallback,(XtPointer)this);
00344 commands[widget] = a_command;
00345 }
00346
00347 G4String G4UIXm::GetCommand (
00348 Widget a_widget
00349 )
00350
00352 {
00353 return commands[a_widget];
00354 }
00355
00356
00357
00358 void G4UIXm::CommandEnteredCallback (
00359 Widget
00360 ,XtPointer a_tag
00361 ,XtPointer a_data
00362 )
00363
00365 {
00366 G4UIXm* This = (G4UIXm*)a_tag;
00367
00368 XmString cps = ((XmCommandCallbackStruct*)a_data)->value;
00369 char* ss = XmConvertCompoundStringToString(cps,0);
00370 G4String command (ss);
00371 XtFree (ss);
00372
00373 if(This->fHelp==true) {
00374 exitHelp = true;
00375 This->fHelp = ConvertStringToInt(command.data(),This->fHelpChoice);
00376 } else {
00377 This->ApplyShellCommand (command,exitSession,exitPause);
00378 }
00379
00380
00381 a_tag = NULL;
00382 }
00383
00384 void G4UIXm::keyHandler (
00385 Widget a_widget
00386 ,XtPointer a_tag
00387 ,XEvent* a_event
00388 ,Boolean*
00389 )
00390
00392 {
00393 KeySym keySym;
00394 XLookupString(&(a_event->xkey),NULL,0,&keySym,NULL);
00395 if(keySym!=XK_Tab) return;
00396 G4UIXm* This = (G4UIXm*)a_tag;
00397 char* s = XmTextGetString(a_widget);
00398 G4String ss = This->Complete(s);
00399 XmTextSetString(a_widget,(char*)ss.data());
00400 XtFree(s);
00401 XmTextSetInsertionPosition(a_widget,XmTextGetLastPosition(a_widget));
00402 }
00403
00404 void clearButtonCallback (
00405 Widget
00406 ,XtPointer a_tag
00407 ,XtPointer
00408 )
00409
00411 {
00412 XmTextSetString((Widget)a_tag,(char*)"");
00413 }
00414
00415 void G4UIXm::ButtonCallback (
00416 Widget a_widget
00417 ,XtPointer a_tag
00418 ,XtPointer
00419 )
00420
00422 {
00423 G4UIXm* This = (G4UIXm*)a_tag;
00424 if(This->fHelp==true) return;
00425 G4String ss = This->GetCommand (a_widget);
00426
00427 This->ApplyShellCommand(ss,exitSession,exitPause);
00428 }
00429
00430
00431
00432 char* XmConvertCompoundStringToString (
00433 XmString a_cps
00434 ,int a_number
00435 )
00436
00438 {
00439 if(a_cps==NULL) return NULL;
00440 char* ss = NULL;
00441 XmStringContext context;
00442 XmStringInitContext(&context,a_cps);
00443 int icount = 0;
00444 Boolean Done = False;
00445 while(Done==False) {
00446 char* text = NULL;
00447 XmStringCharSet charset = NULL;
00448 XmStringDirection direct;
00449 Boolean sep;
00450 if(XmStringGetNextSegment(context,&text,&charset,&direct,&sep)==True) {
00451 XtFree(charset);
00452 if(sep==True) Done = True;
00453 if(icount==a_number) {
00454 ss = text;
00455 break;
00456 }
00457 icount++;
00458 XtFree(text);
00459 }
00460 else
00461 Done = True;
00462 }
00463 XmStringFreeContext(context);
00464 return ss;
00465 }
00466
00467 void XmTextAppendString (
00468 Widget This
00469 ,char* a_string
00470 )
00471
00473 {
00474 if(This==NULL) return;
00475 if(!XtIsSubclass(This,xmTextWidgetClass)) return;
00476 if(a_string==NULL) return;
00477 XmTextPosition lastpos = XmTextGetLastPosition(This);
00478 XmTextReplace(This,lastpos,lastpos,a_string);
00479 XmTextSetInsertionPosition(This,XmTextGetLastPosition(This));
00480 }
00482 G4bool ConvertStringToInt(
00483 const char* aString
00484 ,int& aInt
00485 )
00488 {
00489 aInt = 0;
00490 if(aString==NULL) return false;
00491 char* s;
00492 long value = strtol(aString,&s,10);
00493 if(s==aString) return false;
00494 aInt = value;
00495 return true;
00496 }
00497 #include <X11/IntrinsicP.h>
00499 void ExecuteChangeSizeFunction (
00500 Widget aWidget
00501 )
00504 {
00505 if(aWidget==NULL) return;
00506 if(aWidget->core.widget_class->core_class.resize==NULL) return;
00507 (aWidget->core.widget_class->core_class.resize)(aWidget);
00508 }
00509
00510
00511 #endif