Path: utzoo!attcan!uunet!husc6!bloom-beacon!ardent.UUCP!mlp From: mlp@ardent.UUCP (Mark Patrick) Newsgroups: comp.windows.x Subject: (none) Message-ID: <8805241853.AA06776@gr.ardent.com> Date: 24 May 88 18:53:07 GMT Sender: daemon@bloom-beacon.MIT.EDU Organization: The Internet Lines: 361 I am trying to write a simple toolkit application and am getting nowhere. I would be grateful for any help. I enclose a copy of the code. However It is not a pretty sight since it bears the scars of battling with the toolkit and my lack of familiarity with the toolkit. Mark Patrick Ardent Computer uunet!ardent!mlp THE TASK: The task is to provide a form which gets displayed upon application request. The form displays an application specified prompt (a text string of say 20 or 30 characters), a typein area which allows a user to enter a single line response and a scrollable history region which displays previously provided prompts and the corresponding user supplied replies. CURRENT STATE: I have a routine which calls XtCreatePopupShell and creates a shell of class transientShellWidgetClass. This has a single child a form of class formWidgetClass which has three children: A multiline text widget of class asciiStringWidgetClass and edittype XttextAppend used to display the history. A label of class labelWidgetClass used to display the prompt. a single line text widget of class asciiStringWidgetClass used to obtain the users response to the prompt. I have used XtOverrideTranslations to specify an action routine which gets called when the user presses the return key. This routine does indeed get called at this point. I have set the keyboard focus of the shell to the text entry widget using XtSetKeyboardFocus so that the user can type anywhere within the shell and still get text going to the entry widget, this seems to work fine. PROBLEMS: I have encountered the following problems: XtGetValues does not work for me in the following situations: 1. Before realizing the shell I wanted to determine the height and width of characters used in the different component widgets. I set up the parmeters to get the font (as per spec) and called XtGetValues it appeared that nothing got stored (trying to dereference the font information caused a core dump). 2. In the callback after a return was entered by the user I tried to get the length of the string entered by the user using the following code fragment: int i, n, length; n=0; length = -1 ; XtSetArg(args[n], XtNlength, &length); n++; XtGetValues(w, args, n); printf("length is %d\n", length); It allways printed -1. I can't work out from the Text Widget Doc how to append text to the history widget (what values should I give to start_pos and end_pos in XtTextReplace. More generally how are characters numbered (do we number the charcters or the spaces between characters?). It would be really nice if the application had access to all the text editing functions. I understand that the maximum length of the buffer in an asciiStringWidgetClass is fixed and can not grow. If this is true then I suppose I need to write my own source for the history buffer since I don't know how big to make it. Unfortunately there is now doc on how to do this. I have looked at the source in Xaw/StringSrc.c and am really confused by the code for StringReplaceText. Partly this is because I'm not sure how XtTextPosition's. However I don't see any checking on the validity of the startPos, endPos parameters or indeed how a client can determine what values are valid. It is also less then clear whether substituting one piece of text for another (when the delta in length is < 0 actually works). text color: in many applications (including xmh, and help in xmore) appears black. I understand that this is a known bug but I would like to obtain a fix for it if one is known. If anyone has any ideas would they please let me know. When will there be a set of patches available to fix known bugs in the intrinsics and toolkit? THE CODE: # include # include # include # include # include # include # include # include # include # include # include static int default_border = 2; extern do_return(); typedef struct { int width, height; Widget shell; Widget form; Widget history; Widget label; Widget entry; char *history_buff; int history_size; char entry_buff[80]; int cur_pos; } Dialog ; static XtActionsRec text_actions[] = { { "do_return", do_return } }; static String text_translations = "CtrlM: do_return() \n\ 0xff0d: do_return() \n"; static Bool not_done; static Dialog *cur_dialog; static XtTranslations text_trans; static Arg args[25]; static Widget main_shell; static Dialog Dialog_Default; Error(message) char *message; { fprintf(stderr, "Dialog: %s\n", message); fflush(stderr); exit(1); } /* need to get history buffer */ do_return(w) Widget w; { XtTextBlock tb; int i, n, length; char *tmp = "Have a Nice Day\n"; tb.firstPos = 0; tb.length = strlen(tmp); tb.ptr = tmp; printf("edit status = %d\n", XtTextReplace(cur_dialog->history, cur_dialog->cur_pos, cur_dialog->cur_pos, &tb)); /* n = strlen(cur_dialog->entry_buff); printf("got string '%s' length %d\n", cur_dialog->entry_buff, n); for ( i = 0 ; i < n; i++ ) cur_dialog->entry_buff[i] = ' '; cur_dialog->entry_buff[0] = 0; n=0; XtSetArg(args[n], XtNinsertPosition, 0); n++; XtSetArg(args[n], XtNlength, 0); n++; XtSetValues(w, args, n); tb.firstPos = 0; tb.length = 0; tb.ptr = NULL; XtTextReplace(w, 0, 9, &tb); n=0; length = -1 ; XtSetArg(args[n], XtNlength, &length); n++; XtGetValues(w, args, n); printf("length is %d\n", length); */ } Display * DialogInitialize(argc, argv) int argc; char **argv; { int n; n = 0; XtSetArg(args[n], XtNborderWidth, 0); n++; main_shell = XtInitialize(NULL, "biodesign", args, n, &argc, argv ); if ( !main_shell ) Error("Could Not Create Main Shell") ; XtAddActions(&text_actions[0], XtNumber(text_actions)); text_trans = XtParseTranslationTable(text_translations); return XtDisplay(main_shell); } Dialog * CreateDialog(name, xmin, ymin, width, height) char *name; int xmin, ymin; int width, height; { int n; Dialog *dialog; Display *dpy = XtDisplay(main_shell); /* allocate space for dialog structure */ dialog = (Dialog *)malloc(sizeof(Dialog)); if (!dialog) Error("could not allocate dialog structure\n"); dialog->width = width; dialog->height = height; /* create top level shell widget */ n = 0; XtSetArg(args[n], XtNx, xmin); n++; XtSetArg(args[n], XtNy, ymin); n++; XtSetArg(args[n], XtNwidth, (XtArgVal) width); n++; XtSetArg(args[n], XtNheight, (XtArgVal) height); n++; dialog->shell = XtCreatePopupShell (name, transientShellWidgetClass, main_shell, args, n); /* create form widget */ n = 0; XtSetArg(args[n], XtNborderWidth, (XtArgVal) 0); n++; XtSetArg(args[n], XtNinternalWidth, (XtArgVal) 0); n++; XtSetArg(args[n], XtNdefaultDistance, (XtArgVal) 0); n++; dialog->form = XtCreateManagedWidget("topForm", formWidgetClass, dialog->shell, (ArgList) args, n); /* create history widget */ dialog->history_size = 1024 ; dialog->history_buff = (char *)malloc(1024) ; dialog->cur_pos = 0; n=0; XtSetArg(args[n], XtNforeground, WhitePixel(dpy, DefaultScreen(dpy))); n++; XtSetArg(args[n], XtNeditType, (XtArgVal) XttextEdit); n++; XtSetArg(args[n], XtNstring, dialog->history_buff); n++; XtSetArg(args[n], XtNmaximumLength, dialog->history_size); n++; XtSetArg(args[n], XtNlength, dialog->history_size); n++; XtSetArg(args[n], XtNfromVert, 0); n++; XtSetArg(args[n], XtNcallback, (XtArgVal) NULL); n++; XtSetArg(args[n], XtNhorizDistance, 0); n++; XtSetArg(args[n], XtNwidth, width); n++; XtSetArg(args[n], XtNheight, height-50); n++; XtSetArg(args[n], XtNtextOptions, (XtArgVal) (scrollVertical)); n++; dialog->history= XtCreateManagedWidget("history", asciiStringWidgetClass, dialog->form, (ArgList) args, n) ; /* create label */ n = 0; XtSetArg(args[n], XtNfromVert, dialog->history); n++; XtSetArg(args[n], XtNlabel, "hi there:"); n++; XtSetArg(args[n], XtNborderWidth, (XtArgVal) 0); n++; dialog->label= XtCreateManagedWidget("label", labelWidgetClass, dialog->form, args, n); /* create text entry field */ n=0; dialog->entry_buff[0]=0; XtSetArg(args[n], XtNstring, dialog->entry_buff); n++; XtSetArg(args[n], XtNforeground, WhitePixel(dpy, DefaultScreen(dpy))); n++; XtSetArg(args[n], XtNeditType, (XtArgVal) XttextEdit); n++; XtSetArg(args[n], XtNmaximumLength, (XtArgVal) 80); n++; XtSetArg(args[n], XtNlength, 80); n++; XtSetArg(args[n], XtNfromVert, dialog->label); n++; XtSetArg(args[n], XtNcallback, (XtArgVal) NULL); n++; XtSetArg(args[n], XtNwidth, dialog->width); n++; XtSetArg(args[n], XtNinsertPosition, 0); n++; dialog->entry= XtCreateManagedWidget("entry", asciiStringWidgetClass, dialog->form, (ArgList) args, n) ; XtOverrideTranslations(dialog->entry, text_trans); XtSetKeyboardFocus(dialog->shell, dialog->entry); XtRealizeWidget(dialog->shell); return dialog; } DoDialog(dialog, prompt, result) Dialog *dialog; char *prompt; char **result; { XEvent event; Display *dpy = XtDisplay(main_shell); int n; printf("starting loop\n"); cur_dialog = dialog; XtMapWidget(dialog->shell); not_done = TRUE; while ( not_done ) { XtNextEvent(&event); XtDispatchEvent(&event); } cur_dialog = NULL; XtUnmapWidget(dialog->shell); printf("done loop\n"); *result = dialog->entry_buff; } main(argc, argv) int argc; char **argv; { Dialog *dialog; char *result; DialogInitialize(argc, argv) ; dialog = CreateDialog("Foo", 0, 0, 400, 400); while (1) { DoDialog(dialog, "this is the prompt:", &result); printf("got reply %s\n", result); } }