1.13. Your last Motif Program   

You can now create your last Motif program (see later to retrieve it):

    #include <Xm/MainW.h>

#include <Xm/Label.h>
#include <Xm/MessageB.h>
#include <Xm/FileSB.h>
static void File_cb(), View_cb(), Help_help_cb(), Help_cb();
main(argc, argv)
int argc;
char *argv[];
{
Widget label;
Widget toplevel;
Widget main_window, menubar, menu, widget;
XtAppContext app;
Pixmap pixmap;
XmString file,edit,view,select,options,help;
XmString new,open,insert,save,saveas,print,quit;
XmString undo, redo, cut, copy, paste, delete;
XmString d1,d2,d3,d4,d5,d6,d7,d8,d9,d10,d11;
XmString label_string;
char *main_window_label = \
"This is the mainwindow working area. It can be used for any kind of X\n\
Windows feature. In this case it is a simple label with a very long\n\
message in it. \n\
This should then let us have a nice area perhaps with scrolly bits.\n\
Notice the menubar along the top with various menus which will fall from it\n\
as you click on them. You may move along them and the next menu will also\n\
pop down. Note as well that there are accelerators for the menu entries.\n\
(Select and Options will not work because they have no menus underneath them because\n\
I am lazy!) Note as well that the Help menu is offset from the rest.\n\
";
toplevel = XtVaAppInitialize(&app, "XMainwindow", NULL, 0, &argc, argv, NULL,
NULL);
main_window = XtVaCreateManagedWidget("main_window", xmMainWindowWidgetClass, toplevel,
XmNscrollBarDisplayPolicy, XmAS_NEEDED,
XmNwidth,500,
XmNscrollingPolicy,XmAUTOMATIC,
NULL);
/* Create a simple MenuBar that contains three menus */
file = XmStringCreateLocalized("File");
edit = XmStringCreateLocalized("Edit");
view = XmStringCreateLocalized("View");
select = XmStringCreateLocalized("Select");
options = XmStringCreateLocalized("Options");
help = XmStringCreateLocalized("Help");
menubar = XmVaCreateSimpleMenuBar(main_window, "menubar",
XmVaCASCADEBUTTON, file, 'F',
XmVaCASCADEBUTTON, edit, 'E',
XmVaCASCADEBUTTON, view, 'V',
XmVaCASCADEBUTTON, select, 'S',
XmVaCASCADEBUTTON, options, 'O',
XmVaCASCADEBUTTON, help, 'H',
NULL);
XmStringFree(file);
XmStringFree(edit);
XmStringFree(view);
XmStringFree(select);
XmStringFree(options);
/* Tell the menubar which button is the help menu */
if (widget = XtNameToWidget (menubar, "button_5"))
XtVaSetValues (menubar,
XmNmenuHelpWidget, widget,
NULL);
/* First menu is the File menu with callback == File_cb() */
new = XmStringCreateLocalized("New");
open = XmStringCreateLocalized("Open...");
insert = XmStringCreateLocalized("Insert from File...");
save = XmStringCreateLocalized("Save");
saveas = XmStringCreateLocalized("Save as...");
print = XmStringCreateLocalized("Print...");
quit = XmStringCreateLocalized("Exit");
XmVaCreateSimplePulldownMenu(menubar, "file_menu", 0, File_cb,
XmVaPUSHBUTTON, new, 'N', NULL, NULL,
XmVaPUSHBUTTON, open, 'O', NULL, NULL,
XmVaPUSHBUTTON, insert, 'I', NULL, NULL,
XmVaSEPARATOR,
XmVaPUSHBUTTON, save, 'S', NULL, NULL,
XmVaPUSHBUTTON, saveas, 'A', NULL, NULL,
XmVaSEPARATOR,
XmVaPUSHBUTTON, print, 'P', NULL, NULL,
XmVaSEPARATOR,
XmVaPUSHBUTTON, quit, 'Q', NULL, NULL,
NULL);
XmStringFree(new);
XmStringFree(open);
XmStringFree(insert);
XmStringFree(save);
XmStringFree(saveas);
XmStringFree(print);
XmStringFree(quit);
/* Second menu is the Edit menu -- callback is NULL */
undo = XmStringCreateLocalized("Undo");
redo = XmStringCreateLocalized("Redo");
cut = XmStringCreateLocalized("Cut");
copy = XmStringCreateLocalized("Copy");
paste = XmStringCreateLocalized("Paste");
delete = XmStringCreateLocalized("Delete");
XmVaCreateSimplePulldownMenu(menubar, "edit_menu", 1, NULL,
XmVaPUSHBUTTON, undo, 'U', NULL, NULL,
XmVaPUSHBUTTON, redo, 'R', NULL, NULL,
XmVaSEPARATOR,
XmVaPUSHBUTTON, cut, 'X', NULL, NULL,
XmVaPUSHBUTTON, copy, 'C', NULL, NULL,
XmVaPUSHBUTTON, paste, 'V', NULL, NULL,
XmVaPUSHBUTTON, delete, ' 10', NULL, NULL,
NULL);
XmStringFree(undo); XmStringFree(redo); XmStringFree(cut);
XmStringFree(copy); XmStringFree(paste); XmStringFree(delete);
/* Third menu is the View menu -- callback is View_cb */
d1= XmStringCreateLocalized("bulletin board dialog");
d2= XmStringCreateLocalized("error dialog");
d4= XmStringCreateLocalized("form dialog");
d5= XmStringCreateLocalized("information dialog");
d6= XmStringCreateLocalized("message dialog");
d7= XmStringCreateLocalized("prompt dialog");
d8= XmStringCreateLocalized("question dialog");
d9= XmStringCreateLocalized("selection dialog");
d10= XmStringCreateLocalized("warning dialog");
d11= XmStringCreateLocalized("working dialog");
XmVaCreateSimplePulldownMenu(menubar, "view_menu", 2, View_cb,
XmVaPUSHBUTTON, d1, NULL, NULL, NULL,
XmVaPUSHBUTTON, d2, NULL, NULL, NULL,
XmVaPUSHBUTTON, d4, NULL, NULL, NULL,
XmVaPUSHBUTTON, d5, NULL, NULL, NULL,
XmVaPUSHBUTTON, d6, NULL, NULL, NULL,
XmVaPUSHBUTTON, d7, NULL, NULL, NULL,
XmVaPUSHBUTTON, d8, NULL, NULL, NULL,
XmVaPUSHBUTTON, d9, NULL, NULL, NULL,
XmVaPUSHBUTTON, d10, NULL, NULL, NULL,
XmVaPUSHBUTTON, d11, NULL, NULL, NULL,
NULL);
XmStringFree(d1); XmStringFree(d2); XmStringFree(d4); XmStringFree(d5);
XmStringFree(d6); XmStringFree(d7); XmStringFree(d8); XmStringFree(d9);
XmStringFree(d10); XmStringFree(d11);
/* Last menu is the help menu -- callback is Help_cb() */
XmVaCreateSimplePulldownMenu (menubar, "help_menu", 5, Help_cb,
XmVaPUSHBUTTON, help, 'H', NULL, NULL,
NULL);
XmStringFree (help); /* we're done with it; now we can free it */
XtManageChild (menubar);
label_string=XmStringCreateLtoR(main_window_label, XmSTRING_DEFAULT_CHARSET);
/* Now create label using pixmap */
label = XtVaCreateManagedWidget ("label", xmLabelWidgetClass, main_window,
XmNlabelType, XmSTRING,
XmNalignment, XmALIGNMENT_BEGINNING,
XmNlabelString,label_string,
NULL);
/* set the label as the "work area" of the main window */
XtVaSetValues (main_window,
XmNmenuBar, menubar,
XmNworkWindow, label,
NULL);
XtRealizeWidget (toplevel);
XtAppMainLoop (app);
}
/* Any item the user selects from the File menu calls this function.
* It will either be "Open" (item_no == 0) or "Quit" (item_no == 1).
*/
static void
File_cb(widget_cb, client_data, call_data)
Widget widget_cb; /* menu item that was selected */
XtPointer client_data; /* the index into the menu */
XtPointer call_data; /* unused */
{
static Widget dialog; /* make it static for reuse */
int item_no = (int) client_data;
Widget toplevel;
if (item_no == 6) /* Exit */
exit (0);
/* File Op required. Create a Motif FileSelectionDialog w/callback */
if (!dialog)
{
for (toplevel=widget_cb;
!XtIsSubclass(toplevel,applicationShellWidgetClass);
toplevel= XtParent(toplevel))
;
dialog = XmCreateFileSelectionDialog (toplevel, "file_sel", NULL, 0);
XtAddCallback (dialog, XmNcancelCallback, XtUnmanageChild, NULL);
XtSetSensitive(XmFileSelectionBoxGetChild(dialog,XmDIALOG_HELP_BUTTON),False);
}
XtManageChild (dialog);
XtPopup (XtParent (dialog), XtGrabNone);
}
#define HELP_MSG \
"Use the Exit entry in the File pulldown to exit.\n\
Use the View entries to look at various types of dialog boxes.\n\
Use the entries in the File Pulldown to look at the (dubious)\n\
Motif FileSelectionBox Widget.\n"
/* The help button in the help menu from the menubar was selected.
* Display help information defined above for how to use the program.
* This is done by creating a Motif information dialog box. Again,
* make the dialog static so we can reuse it.
*/
static void
Help_cb(widget_cb, client_data, call_data)
Widget widget_cb;
XtPointer client_data;
XtPointer call_data;
{
static Widget dialog;
Widget toplevel;
if (!dialog)
{
Arg args[5];
int n = 0;
XmString msg = XmStringCreateLtoR (HELP_MSG, XmFONTLIST_DEFAULT_TAG);
for (toplevel=widget_cb;
!XtIsSubclass(toplevel,applicationShellWidgetClass);
toplevel= XtParent(toplevel))
;
XtSetArg (args[n], XmNmessageString, msg); n++;
XtSetArg (args[n], XmNdialogStyle, XmDIALOG_FULL_APPLICATION_MODAL); n++;
dialog = XmCreateInformationDialog (toplevel, "help_dialog", args, n);
XtAddCallback(dialog,XmNhelpCallback,Help_help_cb,dialog);
}
XtManageChild (dialog);
XtPopup (XtParent (dialog), XtGrabNone);
}
#define HELP_HELP_MSG "You have had all the help I can give.!"
/* The help button in the help dialog popup was selected.
*/
static void
Help_help_cb(widget_cb, client_data, call_data)
Widget widget_cb;
XtPointer client_data;
XtPointer call_data;
{
static Widget dialog;
Widget toplevel;
if (!dialog)
{
Arg args[5];
int n = 0;
XmString msg = XmStringCreateLtoR (HELP_HELP_MSG, XmFONTLIST_DEFAULT_TAG);
for (toplevel=widget_cb;
!XtIsSubclass(toplevel,applicationShellWidgetClass);
toplevel= XtParent(toplevel))
;
XtSetArg (args[n], XmNmessageString, msg); n++;
XtSetArg (args[n], XmNdialogStyle, XmDIALOG_SYSTEM_MODAL); n++;
dialog = XmCreateInformationDialog (toplevel, "help_dialog", args, n);
XtAddCallback(dialog,XmNhelpCallback,Help_help_cb,dialog);
XtUnmanageChild(XmMessageBoxGetChild(dialog,XmDIALOG_CANCEL_BUTTON) );
XtUnmanageChild(XmMessageBoxGetChild(dialog,XmDIALOG_HELP_BUTTON) );
}
XtManageChild (dialog);
XtPopup (XtParent (dialog), XtGrabNone);
}
static void
Destroy_cb(widget_cb, client_data, call_data)
Widget widget_cb; /* menu item that was selected */
XtPointer client_data; /* the index into the menu */
XtPointer call_data; /* widget specific */
{
XtDestroyWidget ((XtParent (widget_cb)));
}
/* Any item the user selects from the View menu calls this function.
*/
static void
View_cb(widget_cb, client_data, call_data)
Widget widget_cb; /* menu item that was selected */
XtPointer client_data; /* the index into the menu */
XtPointer call_data; /* unused */
{
int item_no = (int) client_data;
Widget dialog,toplevel;
XmString xm_label_string;
Arg args[5];
int n = 0;
for (toplevel=widget_cb;
!XtIsSubclass(toplevel,applicationShellWidgetClass);
toplevel= XtParent(toplevel))
;
XtVaGetValues(widget_cb,
XmNlabelString, &xm_label_string,
NULL);
XtSetArg (args[n], XmNmessageString, xm_label_string); n++;
/* Create dialog box.
*/
switch (item_no)
{
case 0:
XtSetArg (args[n], XmNwidth, 100); n++;
XtSetArg (args[n], XmNheight, 100); n++;
dialog = XmCreateBulletinBoardDialog (toplevel, "dialog_box", args, n);
break;
case 1:
dialog = XmCreateErrorDialog(toplevel,"error_dialog",args,n);
break;
case 2:
XtSetArg (args[n], XmNwidth, 100); n++;
XtSetArg (args[n], XmNheight, 100); n++;
dialog = XmCreateFormDialog(toplevel,"form_dialog",args,n);
break;
case 3:
dialog = XmCreateInformationDialog(toplevel,"Information_dialog",args,n);
break;
case 4:
dialog = XmCreateMessageDialog(toplevel,"Message_dialog",args,n);
break;
case 5:
dialog = XmCreatePromptDialog(toplevel,"Prompt_dialog",args,n);
break;
case 6:
dialog = XmCreateQuestionDialog(toplevel,"Question_dialog",args,n);
break;
case 7:
dialog = XmCreateSelectionDialog(toplevel,"Selection_dialog",args,n);
break;
case 8:
dialog = XmCreateWarningDialog(toplevel,"Warning_dialog",args,n);
break;
case 9:
dialog = XmCreateWorkingDialog(toplevel,"Working_dialog",args,n);
break;
default:
printf("xmmainwidow: huh? Funny dialog request passed\n");
exit();
break;
}
if((item_no ==0) || (item_no == 2) ) ; /* do not have buttons... */
else
{
XtAddCallback(dialog,XmNokCallback,Destroy_cb,dialog);
XtAddCallback(dialog,XmNcancelCallback,Destroy_cb,dialog);
}
XtManageChild (dialog);
XtPopup (XtParent (dialog), XtGrabNone);
}

You will also need to have an Imakefile:

    #include <Motif.tmpl>

LOCAL_LIBRARIES = $(XMLIB) $(SYSLIBS)
FILE = xmhello
SRCS = $(FILE).c
OBJS = $(FILE).o
PROGRAM = $(FILE)
ComplexProgramTarget($(FILE))

The alternative would be for you to grab the source code (via ) and compile it on your machine.
Imakefile xmainwindow.c

After retrieving and saving the code plus Imakefile, you should be able to type:
xmkmf -a ; make FILE=xmainwindow
This will produce the executable called xmainwindow.

It is possible to execute a (different) xmainwindow program and display it on your screen. To run it, your system must be running X and the server control is set to xhost . Also it will not work if you are using a proxy server or you are running your browser on a machine different from the one you are displaying it on. Many example programs are available