Merge branch 'master' into cde-next
[oweals/cde.git] / cde / lib / DtHelp / XUICreate.c
1 /*
2  * CDE - Common Desktop Environment
3  *
4  * Copyright (c) 1993-2012, The Open Group. All rights reserved.
5  *
6  * These libraries and programs are free software; you can
7  * redistribute them and/or modify them under the terms of the GNU
8  * Lesser General Public License as published by the Free Software
9  * Foundation; either version 2 of the License, or (at your option)
10  * any later version.
11  *
12  * These libraries and programs are distributed in the hope that
13  * they will be useful, but WITHOUT ANY WARRANTY; without even the
14  * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15  * PURPOSE. See the GNU Lesser General Public License for more
16  * details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with these libraries and programs; if not, write
20  * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21  * Floor, Boston, MA 02110-1301 USA
22  */
23 /* $TOG: XUICreate.c /main/22 1997/06/18 17:33:46 samborn $ */
24 /************************************<+>*************************************
25  ****************************************************************************
26  **
27  **   File:        XUICreate.c
28  **
29  **   Project:     Cde Help System
30  **
31  **   Description: Builds a GUI containing a Drawn Button with scroll
32  **                bars and wraps it around a canvas.
33  **
34  ****************************************************************************
35  ************************************<+>*************************************/
36 /*
37  * (c) Copyright 1996 Digital Equipment Corporation.
38  * (c) Copyright 1987, 1988, 1989, 1990, 1991, 1992,
39                  1993, 1994, 1996 Hewlett-Packard Company.
40  * (c) Copyright 1993, 1994, 1996 International Business Machines Corp.
41  * (c) Copyright 1993, 1994, 1996 Sun Microsystems, Inc.
42  * (c) Copyright 1993, 1994, 1996 Novell, Inc. 
43  * (c) Copyright 1996 FUJITSU LIMITED.
44  * (c) Copyright 1996 Hitachi.
45  */
46
47 /*
48  * system includes
49  */
50 #include <stdlib.h>
51 #include <string.h>
52 #include <Xm/Xm.h>
53 #include <Xm/XmP.h>
54 #include <Xm/AtomMgr.h>
55 #include <Xm/DrawnB.h>
56 #include <Xm/Form.h>
57 #include <Xm/ScrollBar.h>
58 #include <Xm/XmPrivate.h>
59
60 /*
61  * Canvas Engine
62  */
63 #include "CanvasP.h"
64 #include "CanvasSegP.h"
65
66 /*
67  * private includes
68  */
69 #include "bufioI.h"
70 #include "Access.h"
71 #include "DisplayAreaP.h"
72 #include "CallbacksI.h"
73 #include "XUICreateI.h"
74 #include "FontI.h"
75 #include "FontAttrI.h"
76 #include "DestroyI.h"
77 #include "FormatUtilI.h"
78 #include "SetListI.h"
79 #include "XInterfaceI.h"
80 #include "Lock.h"
81
82 #ifdef NLS16
83 #endif
84
85 /********    Private Function Declarations    ********/
86 static  Boolean    get_fontsetproperty(
87                         XFontSet        fontset,
88                         Atom            atom,
89                         unsigned long   *value_return);
90 /********    End Private Function Declarations    ********/
91
92 /********    Private Variables    ********/
93
94 static  _DtCvVirtualInfo DefVirtFunctions =
95   {
96         _DtHelpDAGetCvsMetrics,         /* void (*_DtCvGetMetrics)()     */
97         _DtHelpDARenderElem,            /* void (*_DtCvRenderElem)()     */
98         _DtHelpDAGetStrWidth,           /* _DtCvUnit (*_DtCvGetElemWidth)()  */
99         _DtHelpDAGetFontMetrics,        /* void (*_DtCvGetFontMetrics)() */
100         _DtHelpDABuildSelection,        /* void (*_DtCvBuildSelection)() */
101         NULL,                           /* _DtCvStatus (*_DtCvFilterExecCmd)()*/
102   };
103
104 /********    End Private Variables  ********/
105
106 /********    Semi-Private Variables    ********/
107 /********    End Semi-Private Variables  ********/
108
109 /******************************************************************************
110  *
111  * Here are the type and variable declarations for finding view subresources.
112  *
113  *****************************************************************************/
114
115 /*
116  * These are used to parse subresources for the text display areas.
117  */
118
119 typedef struct 
120   {
121     int    marginWidth;
122     int    marginHeight;
123     int    leading;
124     int    moveThreshold;
125     int    initialDelay;
126     int    repeatDelay;
127
128     XmFontList userFont;
129     Pixel  search_color;
130   }
131   DAArgs, *DAArgsPtr;
132
133 static XtResource Resources[] = {
134    {
135      "leading", "Leading", XmRInt, sizeof(int),
136      XtOffset(DAArgsPtr, leading), XmRImmediate, (XtPointer) 1
137    },
138     
139    {
140      XmNmarginWidth, XmCMarginWidth, XmRInt, sizeof(int),
141      XtOffset(DAArgsPtr, marginWidth), XmRImmediate, (XtPointer) 5
142    },
143     
144    {
145      XmNmarginHeight, XmCMarginHeight, XmRInt, sizeof(int),
146      XtOffset(DAArgsPtr, marginHeight), XmRImmediate, (XtPointer) 5
147    },
148
149    {
150      "moveThreshold", "MoveThreshold", XmRInt, sizeof(int),
151      XtOffset(DAArgsPtr, moveThreshold), XmRImmediate, (XtPointer) 10
152    },
153     
154    {
155      XmNinitialDelay, XmCInitialDelay, XmRInt, sizeof(int),
156      XtOffset(DAArgsPtr, initialDelay), XmRImmediate, (XtPointer) 250
157    },
158     
159    {
160      XmNrepeatDelay, XmCRepeatDelay, XmRInt, sizeof(int),
161      XtOffset(DAArgsPtr, repeatDelay), XmRImmediate, (XtPointer) 50
162    },
163     
164    {
165      "userFont", XmCFontList, XmRFontList, sizeof (XmFontList),
166      XtOffset(DAArgsPtr, userFont), XmRString, "Fixed"
167    },
168
169    {
170      "searchColor", "SearchColor", XtRPixel, sizeof (Pixel),
171      XtOffset(DAArgsPtr, search_color), XmRString, "blue"
172    },
173
174 };
175
176 static String       DrawnBTransTable = "\
177 ~s    ~m ~a <Key>Return:      ActivateLink()\n\
178 ~s  c ~m ~a <Key>backslash:   DeSelectAll()\n\
179 ~s  c ~m ~a <Key>slash:       SelectAll()\n\
180 ~s    ~m ~a <Key>space:       ActivateLink()\n\
181             <Key>osfActivate: ActivateLink()\n\
182             <Key>osfCopy:     CopyToClipboard()\n\
183    ~c       <Key>osfDown:     NextLink(1)\n\
184     c       <Key>osfDown:     PageUpOrDown(1)\n\
185 ~s  c ~m ~a <Key>osfInsert:   CopyToClipboard()\n\
186    ~c       <Key>osfLeft:      NextLink(0)\n\
187     c       <Key>osfLeft:      PageLeftOrRight(0)\n\
188    ~c       <Key>osfPageDown:  PageUpOrDown(1)\n\
189     c       <Key>osfPageDown:  PageLeftOrRight(1)\n\
190             <Key>osfPageLeft:  PageLeftOrRight(0)\n\
191             <Key>osfPageRight: PageLeftOrRight(1)\n\
192    ~c       <Key>osfPageUp:    PageUpOrDown(0)\n\
193     c       <Key>osfPageUp:    PageLeftOrRight(0)\n\
194    ~c       <Key>osfRight:     NextLink(1)\n\
195     c       <Key>osfRight:     PageLeftOrRight(1)\n\
196 ~s ~c       <Key>osfSelect:    ActivateLink()\n\
197    ~c       <Key>osfUp:        NextLink(0)\n\
198     c       <Key>osfUp:        PageUpOrDown(0)\n\
199     c       <Key>osfBeginLine: NextLink(2)\n\
200     c       <Key>osfEndLine:   NextLink(3)\
201 ";
202
203 static  XtTranslations  DrawnBTrans = NULL;
204
205 /*********************************************************************
206  *              Private Functions
207  *********************************************************************/
208 /* This function returns the max value of XGetFontProperty calls for each
209  * font in the fontset.
210  */
211 static Boolean
212 get_fontsetproperty(
213         XFontSet fontset,
214         Atom atom,
215         unsigned long *value_return)
216 {
217     int numfont;
218     XFontStruct **font_list;
219     char **name_list;
220     int i;
221     Bool ret = FALSE;
222     unsigned long value;
223
224     numfont=XFontsOfFontSet(fontset,&font_list,&name_list);
225     for(i = 0; i < numfont; i++) {
226         if(XGetFontProperty(font_list[i], atom, &value) == TRUE) {
227             if(ret == FALSE) {
228                 *value_return = value;
229                 ret = TRUE;
230             }
231             else {
232                 if(value > *value_return)
233                     *value_return = value;
234             }
235         }
236     }
237     return(ret);
238 }
239
240 /*
241  * This function returns the underline distance and size for the base
242  * font.
243  */
244 static  void
245 GetUnderLineInfo (
246         Display                 *dpy,
247         DtHelpDispAreaStruct    *pDAS,
248         int                     *ret_underThick )
249 {
250     int   idx;
251     XtPointer myFont;
252     XFontSetExtents *extents;
253
254     /*
255      * cast the parameter as a pointer to a long though the value
256      * returned is really a int.
257      */
258     idx = __DtHelpDefaultFontIndexGet(pDAS);
259     if (idx < 0)
260       {
261         myFont = (XtPointer)__DtHelpFontSetGet(pDAS->font_info, idx);
262         if (get_fontsetproperty((XFontSet)myFont, XA_UNDERLINE_POSITION,
263                 ((unsigned long *) &(pDAS->underLine))) == FALSE)
264           {
265             extents = XExtentsOfFontSet((XFontSet)myFont);
266             pDAS->underLine = ((int)(extents->max_ink_extent.height +
267                                extents->max_ink_extent.y)) / 2;
268           }
269       }
270     else
271       {
272         myFont = (XtPointer)__DtHelpFontStructGet(pDAS->font_info, idx);
273         if (XGetFontProperty((XFontStruct *)myFont, XA_UNDERLINE_POSITION, 
274                              ((unsigned long *) &(pDAS->underLine))) == FALSE)
275             pDAS->underLine = ((XFontStruct *)myFont)->max_bounds.descent / 2;
276       }
277
278     /*
279      * if we do not find an underline thickness for the font
280      * use 15% of the font height.
281      *
282      * cast the parameter to a pointer to a long though the value
283      * returned is really a unsigned int.
284      */
285     if (idx < 0)
286       {
287         if (get_fontsetproperty((XFontSet)myFont, XA_UNDERLINE_THICKNESS,
288                 ((unsigned long *) ret_underThick)) == FALSE)
289             *ret_underThick = pDAS->lineHeight * 15 / 100;
290       }
291     else
292       {
293         if (XGetFontProperty((XFontStruct *)myFont, XA_UNDERLINE_THICKNESS, 
294                              ((unsigned long *) ret_underThick)) == FALSE)
295             *ret_underThick = pDAS->lineHeight * 15 / 100;
296       }
297
298
299     /*
300      * now adjust the underline depth so that the when the underline is
301      * drawn the top of the line is UNDERLINE_POSITION pixels below
302      * the base line.
303      */
304 /*
305  * SYSTEM - ifdef this for other architectures.
306  * an example of Hewlett-Packard's implementation is given for reference.
307  */
308                 /* On Hewlett-Packard machines lines are */
309                 /* drawn like this:                      */
310                 /*                                       */
311                 /*  line width 1:  y-> ****************  */
312                 /*                                       */
313                 /*                     ****************  */
314                 /*  line width 2:  y-> ****************  */
315                 /*                                       */
316                 /*                     ****************  */
317                 /*  line width 3:  y-> ****************  */
318                 /*                     ****************  */
319                 /*                                       */
320                 /*                     ****************  */
321                 /*                     ****************  */
322                 /*  line width 4:  y-> ****************  */
323                 /*                     ****************  */
324                 /*                                       */
325                 /*                     ****************  */
326                 /*                     ****************  */
327                 /*  line width 5:  y-> ****************  */
328                 /*                     ****************  */
329                 /*                     ****************  */
330                 /* etc......                             */
331                 /*                                       */
332     pDAS->underLine = pDAS->underLine + (*ret_underThick) / 2;
333
334 }
335
336 /*********************************************************************
337  *              Public Functions
338  *********************************************************************/
339 /*********************************************************************
340  * Function: CreateDA
341  *
342  *    CreateDA creates a Text Graphic area with the appropriate scroll bars.
343  *
344  *********************************************************************/
345 static XtPointer
346 HelpCreateDA(
347     Widget       parent,
348     char        *name,
349     short        vert_flag,
350     short        horz_flag,
351     Boolean      traversal_flag,
352     _DtCvValue   honor_size,
353     _DtCvRenderType render_type,
354     int          rows,
355     int          columns,
356     unsigned short media_resolution,
357     void        (*hyperTextCB)(),
358     void        (*resizeCB)(),
359     int         (*exec_ok_routine)(),
360     XtPointer    client_data,
361     XmFontList   default_list )
362 {
363     DtHelpDispAreaStruct *pDAS;
364     DAArgs DA_args;
365     Arg args[20];
366     int n;
367     int maxFontAscent;
368     int maxFontDescent;
369     int maxFontCharWidth;
370   
371     short margin_width;
372     short margin_height;
373     short shadowThick, highThick;
374     Dimension hBarHeight = 0;
375     Dimension vBarWidth  = 0;
376     Dimension width;
377     Boolean   value;
378
379     Widget form;
380     Display *dpy = XtDisplay(parent);
381     Screen      *retScr = XtScreen(parent);
382     int          screen = XScreenNumberOfScreen(retScr);
383
384     Colormap colormap;
385
386     Pixmap               tile;
387     XGCValues            gcValues;
388     unsigned long        gcMask;
389
390     unsigned long char_width;
391
392     Atom xa_ave_width;
393
394     XFontStruct *tmpFont = NULL;
395     XtPointer    default_font = NULL;
396     XRectangle   rectangle[1];
397
398     XmFontContext       fontContext;
399     XmFontListEntry     fontEntry;
400     XmFontType          fontType;
401
402     /* Allocate the Display Area. */
403     pDAS = (DtHelpDispAreaStruct *) XtMalloc(sizeof(DtHelpDispAreaStruct));
404
405    /*
406      * get the resources
407      */
408     XtGetSubresources(parent, &DA_args, name, "XmDrawnButton",
409                     Resources, XtNumber(Resources), NULL, 0);
410
411     if (rows <= 0)
412         rows = 1;
413     if (columns <= 0)
414         columns = 1;
415
416     /*
417      * initialize the structure variables.
418      */
419     pDAS->text_selected = False;
420     pDAS->primary       = False;
421     pDAS->select_state  = _DtHelpNothingDoing;
422     pDAS->toc_y         = 0;
423     pDAS->toc_base      = 0;
424     pDAS->toc_flag      = 0;
425     if (traversal_flag)
426         pDAS->toc_flag  = _DT_HELP_SHADOW_TRAVERSAL | _DT_HELP_NOT_INITIALIZED;
427
428     pDAS->max_spc       = 0;
429     pDAS->cur_spc       = 0;
430     pDAS->maxX          = 0;
431     pDAS->virtualX      = 0;
432     pDAS->firstVisible  = 0;
433     pDAS->visibleCount  = rows;
434     pDAS->maxYpos       = 0;
435     pDAS->neededFlags   = 0;
436     pDAS->vert_init_scr = DA_args.initialDelay;
437     pDAS->vert_rep_scr  = DA_args.repeatDelay;
438     pDAS->horz_init_scr = DA_args.initialDelay;
439     pDAS->horz_rep_scr  = DA_args.repeatDelay;
440     pDAS->moveThreshold = DA_args.moveThreshold;
441     pDAS->marginWidth   = DA_args.marginWidth;
442     pDAS->marginHeight  = DA_args.marginHeight;
443     pDAS->searchColor   = DA_args.search_color;
444     pDAS->depth         = 0;
445     pDAS->spc_chars     = NULL;
446     pDAS->scr_timer_id  = 0;
447     pDAS->def_pix       = 0;
448     pDAS->context       = NULL;
449     pDAS->vertIsMapped  = False;
450     pDAS->horzIsMapped  = False;
451     pDAS->lst_topic     = NULL;
452     pDAS->nextNonVisible = 0;
453     pDAS->media_resolution = media_resolution;
454     pDAS->honor_size = honor_size;
455     pDAS->render_type = render_type;
456     pDAS->dtinfo = 0;
457     pDAS->stipple = None;
458
459     /*
460      * locale dependant information
461      */
462     pDAS->nl_to_space      = 1;
463     pDAS->cant_begin_chars = NULL;
464     pDAS->cant_end_chars   = NULL;
465     if (1 < MB_CUR_MAX)
466         _DtHelpLoadMultiInfo (&(pDAS->cant_begin_chars),
467                                 &(pDAS->cant_end_chars), &(pDAS->nl_to_space));
468
469     /*
470      * initialize the hypertext callback pointer
471      */
472     pDAS->exec_filter = exec_ok_routine;
473     pDAS->hyperCall   = hyperTextCB;
474     pDAS->resizeCall  = resizeCB;
475     pDAS->clientData  = client_data;
476
477     /*
478      * zero out other callback fields
479      */
480     pDAS->vScrollNotify = NULL ;
481     pDAS->armCallback = NULL ;
482
483     /*
484      * create the atoms needed
485      */
486     xa_ave_width = XmInternAtom(dpy, "AVERAGE_WIDTH"     , False);
487
488     /*
489      * Malloc for the default font.
490      */
491     (void) XmeRenderTableGetDefaultFont(DA_args.userFont, &tmpFont);
492     if (default_list != NULL &&
493                 XmFontListInitFontContext (&fontContext, default_list))
494       {
495         fontEntry = XmFontListNextEntry (fontContext);
496         if (fontEntry != NULL)
497             default_font = XmFontListEntryGetFont (fontEntry, &fontType);
498
499         XmFontListFreeFontContext (fontContext);
500       }
501
502     /*
503      * fake out the next call by using the parent as the display widget
504      */
505     pDAS->dispWid = parent;
506     __DtHelpFontDatabaseInit (pDAS, default_font, fontType, tmpFont);
507
508     /*
509      * Get the base font meterics.
510      */
511     __DtHelpFontMetrics (pDAS->font_info, __DtHelpDefaultFontIndexGet(pDAS),
512                         &maxFontAscent, &maxFontDescent, &maxFontCharWidth,
513                         NULL, NULL);
514
515     pDAS->leading    = DA_args.leading;
516     pDAS->fontAscent = maxFontAscent;
517     pDAS->lineHeight = maxFontAscent + maxFontDescent + pDAS->leading + 1;
518
519     n = __DtHelpDefaultFontIndexGet(pDAS);
520     if (n < 0)
521         value = get_fontsetproperty(__DtHelpFontSetGet(pDAS->font_info, n),
522                         xa_ave_width, ((unsigned long *) &(pDAS->charWidth)));
523     else
524         value = XGetFontProperty(__DtHelpFontStructGet(pDAS->font_info, n),
525                         xa_ave_width, ((unsigned long *) &(pDAS->charWidth)));
526
527     if (False == value || 0 == pDAS->charWidth)
528       {
529         int len = maxFontCharWidth;
530
531         if (n < 0)
532             len += XmbTextEscapement(
533                                 __DtHelpFontSetGet(pDAS->font_info,n),"1",1);
534         else
535             len += XTextWidth(__DtHelpFontStructGet(pDAS->font_info, n),"1",1);
536
537         pDAS->charWidth = 10 * len / 2;
538       }
539
540     /*
541      * Create the form to manage the window and scroll bars.
542      */
543     n = 0;
544     XtSetArg(args[n], XmNresizePolicy      , XmRESIZE_ANY);             ++n;
545     XtSetArg(args[n], XmNshadowType     , XmSHADOW_OUT);                ++n;
546     form = XmCreateForm(parent, "DisplayAreaForm", args, n);
547     XtManageChild(form);
548
549     /*
550      * force the shadowThickness to zero. The XmManager will try to set
551      * this to one.
552      */
553     n = 0;
554     XtSetArg(args[n], XmNshadowThickness   , 0);                        ++n;
555     XtSetArg(args[n], XmNhighlightThickness, 0);                        ++n;
556     XtSetValues (form, args, n);
557
558     /*
559      * get the colors and margin widths and heights
560      */
561     n = 0;
562     XtSetArg (args[n], XmNmarginWidth , &margin_width);         ++n;
563     XtSetArg (args[n], XmNmarginHeight, &margin_height);        ++n;
564     XtSetArg (args[n], XmNcolormap    , &colormap);             ++n;
565     XtGetValues(form, args, n);
566
567     /* Create the vertical scrollbar. */
568     pDAS->vertScrollWid = NULL;
569     if (vert_flag != _DtHelpNONE)
570       {
571         if (vert_flag == _DtHelpSTATIC)
572             pDAS->vertIsMapped = True;
573
574         n = 0;
575         XtSetArg(args[n], XmNtopAttachment     , XmATTACH_FORM);        ++n;
576         XtSetArg(args[n], XmNtopOffset         , 0);                    ++n;
577         XtSetArg(args[n], XmNbottomAttachment  , XmATTACH_FORM);        ++n;
578         XtSetArg(args[n], XmNbottomOffset      , margin_height);        ++n;
579         XtSetArg(args[n], XmNrightAttachment   , XmATTACH_FORM);        ++n;
580         XtSetArg(args[n], XmNrightOffset       , 0);                    ++n;
581         XtSetArg(args[n], XmNorientation       , XmVERTICAL);           ++n;
582         XtSetArg(args[n], XmNtraversalOn       , True);                 ++n;
583         XtSetArg(args[n], XmNhighlightThickness, 1);                    ++n;
584         XtSetArg(args[n], XmNshadowType        , XmSHADOW_IN);          ++n;
585         XtSetArg(args[n], XmNvalue             , 0);                    ++n;
586         XtSetArg(args[n], XmNminimum           , 0);                    ++n;
587         /* fake out the scrollbar manager, who will init dims to 100 */
588         XtSetArg(args[n], XmNheight            , 1);                    ++n;
589         XtSetArg(args[n], XmNmaximum           , 1);                    ++n;
590         XtSetArg(args[n], XmNincrement         , 1);                    ++n;
591         XtSetArg(args[n], XmNpageIncrement     , 1);                    ++n;
592         XtSetArg(args[n], XmNsliderSize        , 1);                    ++n;
593         XtSetArg(args[n], XtNmappedWhenManaged , pDAS->vertIsMapped);   ++n;
594         pDAS->vertScrollWid = XmCreateScrollBar(form,
595                                         "DisplayDtHelpVertScrollBar", args, n);
596
597         XtManageChild(pDAS->vertScrollWid);
598         if (vert_flag != _DtHelpSTATIC)
599             pDAS->neededFlags = _DtHelpSET_AS_NEEDED (pDAS->neededFlags,
600                                                 _DtHelpVERTICAL_SCROLLBAR);
601   
602         XtAddCallback(pDAS->vertScrollWid, XmNdragCallback,
603                                         _DtHelpVertScrollCB, (XtPointer) pDAS);
604         XtAddCallback(pDAS->vertScrollWid, XmNincrementCallback,
605                                         _DtHelpVertScrollCB, (XtPointer) pDAS);
606         XtAddCallback(pDAS->vertScrollWid, XmNdecrementCallback,
607                                         _DtHelpVertScrollCB, (XtPointer) pDAS);
608         XtAddCallback(pDAS->vertScrollWid, XmNpageIncrementCallback,
609                                         _DtHelpVertScrollCB, (XtPointer) pDAS);
610         XtAddCallback(pDAS->vertScrollWid, XmNpageDecrementCallback,
611                                         _DtHelpVertScrollCB, (XtPointer) pDAS);
612         XtAddCallback(pDAS->vertScrollWid, XmNtoBottomCallback,
613                                         _DtHelpVertScrollCB, (XtPointer) pDAS);
614         XtAddCallback(pDAS->vertScrollWid, XmNtoTopCallback,
615                                         _DtHelpVertScrollCB, (XtPointer) pDAS);
616         XtAddCallback(pDAS->vertScrollWid, XmNvalueChangedCallback,
617                                         _DtHelpVertScrollCB, (XtPointer) pDAS);
618
619         XtAddEventHandler (pDAS->vertScrollWid, ButtonPressMask, True,
620                         (XtEventHandler)_DtHelpMoveBtnFocusCB,(XtPointer) pDAS);
621
622       }
623
624     /* Create the horizontal scrollbar. */
625     pDAS->horzScrollWid = NULL;
626     if (horz_flag != _DtHelpNONE)
627       {
628         if (horz_flag == _DtHelpSTATIC)
629             pDAS->horzIsMapped = True;
630
631         n = 0;
632         XtSetArg(args[n], XmNbottomAttachment  , XmATTACH_FORM);        ++n;
633         XtSetArg(args[n], XmNbottomOffset      , 0);                    ++n;
634         XtSetArg(args[n], XmNrightAttachment   , XmATTACH_FORM);        ++n;
635         XtSetArg(args[n], XmNrightOffset       , margin_width);         ++n;
636         XtSetArg(args[n], XmNleftAttachment    , XmATTACH_FORM);        ++n;
637         XtSetArg(args[n], XmNleftOffset        , 0);                    ++n;
638         XtSetArg(args[n], XmNorientation       , XmHORIZONTAL);         ++n;
639         XtSetArg(args[n], XmNtraversalOn       , True);                 ++n;
640         XtSetArg(args[n], XmNhighlightThickness, 1);                    ++n;
641         XtSetArg(args[n], XmNshadowType        , XmSHADOW_IN);          ++n;
642         XtSetArg(args[n], XmNvalue             , 0);                    ++n;
643         XtSetArg(args[n], XmNminimum           , 0);                    ++n;
644         XtSetArg(args[n], XmNmaximum           , (pDAS->charWidth/10)); ++n;
645         /* fake out the scrollbar manager, who will init dims to 100 */
646         XtSetArg(args[n], XmNwidth             , 1);                    ++n;
647         XtSetArg(args[n], XmNincrement         , (pDAS->charWidth/10)); ++n;
648         XtSetArg(args[n], XmNpageIncrement     , (pDAS->charWidth/10)); ++n;
649         XtSetArg(args[n], XmNsliderSize        , (pDAS->charWidth/10)); ++n;
650         XtSetArg(args[n], XtNmappedWhenManaged , pDAS->horzIsMapped);   ++n;
651         pDAS->horzScrollWid = XmCreateScrollBar(form,
652                                         "DisplayHorzScrollBar", args, n);
653         XtManageChild(pDAS->horzScrollWid);
654         if (horz_flag != _DtHelpSTATIC)
655             pDAS->neededFlags = _DtHelpSET_AS_NEEDED (pDAS->neededFlags,
656                                                 _DtHelpHORIZONTAL_SCROLLBAR);
657   
658         XtAddCallback(pDAS->horzScrollWid, XmNdragCallback,
659                                         _DtHelpHorzScrollCB, (XtPointer) pDAS);
660         XtAddCallback(pDAS->horzScrollWid, XmNincrementCallback,
661                                         _DtHelpHorzScrollCB, (XtPointer) pDAS);
662         XtAddCallback(pDAS->horzScrollWid, XmNdecrementCallback,
663                                         _DtHelpHorzScrollCB, (XtPointer) pDAS);
664         XtAddCallback(pDAS->horzScrollWid, XmNpageIncrementCallback,
665                                         _DtHelpHorzScrollCB, (XtPointer) pDAS);
666         XtAddCallback(pDAS->horzScrollWid, XmNpageDecrementCallback,
667                                         _DtHelpHorzScrollCB, (XtPointer) pDAS);
668         XtAddCallback(pDAS->horzScrollWid, XmNtoBottomCallback,
669                                         _DtHelpHorzScrollCB, (XtPointer) pDAS);
670         XtAddCallback(pDAS->horzScrollWid, XmNtoTopCallback,
671                                         _DtHelpHorzScrollCB, (XtPointer) pDAS);
672         XtAddCallback(pDAS->horzScrollWid, XmNvalueChangedCallback,
673                                         _DtHelpHorzScrollCB, (XtPointer) pDAS);
674       }
675
676     /*
677      * check for the horizontal attachments
678      */
679     n = 0;
680     if (horz_flag == _DtHelpSTATIC)
681       {
682         XtSetArg(args[n], XmNbottomAttachment  , XmATTACH_WIDGET);      ++n;
683         XtSetArg(args[n], XmNbottomWidget      , pDAS->horzScrollWid);  ++n;
684       }
685     else
686       {
687         XtSetArg(args[n], XmNbottomAttachment  , XmATTACH_FORM);        ++n;
688       }
689
690     /*
691      * check for the vertical attachments
692      */
693     if (vert_flag == _DtHelpSTATIC)
694       {
695         XtSetArg(args[n], XmNrightAttachment   , XmATTACH_WIDGET);      ++n;
696         XtSetArg(args[n], XmNrightWidget       , pDAS->vertScrollWid);  ++n;
697       }
698     else
699       {
700         XtSetArg(args[n], XmNrightAttachment  , XmATTACH_FORM);         ++n;
701       }
702
703     /*
704      * do the rest of the arguments
705      */
706     XtSetArg(args[n], XmNbottomOffset      , margin_height);            ++n;
707     XtSetArg(args[n], XmNrightOffset       , margin_width);             ++n;
708     XtSetArg(args[n], XmNtopAttachment     , XmATTACH_FORM);            ++n;
709     XtSetArg(args[n], XmNtopOffset         , 0);                        ++n;
710     XtSetArg(args[n], XmNleftAttachment    , XmATTACH_FORM);            ++n;
711     XtSetArg(args[n], XmNleftOffset        , 0);                        ++n;
712     XtSetArg(args[n], XmNrecomputeSize     , False);                    ++n;
713     XtSetArg(args[n], XmNpushButtonEnabled , False);                    ++n;
714     XtSetArg(args[n], XmNtraversalOn       , True);                     ++n;
715     XtSetArg(args[n], XmNhighlightThickness, 1);                        ++n;
716     XtSetArg(args[n], XmNshadowType        , XmSHADOW_IN);              ++n;
717     XtSetArg(args[n], XmNmultiClick        , XmMULTICLICK_DISCARD);     ++n;
718     XtSetArg(args[n], XmNuserData          , pDAS);                     ++n;
719     pDAS->dispWid = XmCreateDrawnButton(form, name, args, n);
720     XtManageChild(pDAS->dispWid);
721   
722     XtAddCallback(pDAS->dispWid, XmNexposeCallback, _DtHelpExposeCB,
723                                                 (XtPointer) pDAS);
724     XtAddCallback(pDAS->dispWid, XmNresizeCallback, _DtHelpResizeCB,
725                                                 (XtPointer) pDAS);
726     XtAddCallback(pDAS->dispWid, XmNarmCallback, _DtHelpClickOrSelectCB,
727                                                 (XtPointer) pDAS);
728     XtAddCallback(pDAS->dispWid, XmNdisarmCallback, _DtHelpEndSelectionCB,
729                                                 (XtPointer) pDAS);
730
731     XtAddEventHandler (pDAS->dispWid, Button1MotionMask, True,
732                         (XtEventHandler)_DtHelpMouseMoveCB, (XtPointer) pDAS);
733
734     /*
735      * add my actions
736      * parse the translations.
737      */
738     _DtHelpProcessLock();
739     if (DrawnBTrans == NULL)
740         DrawnBTrans = XtParseTranslationTable(DrawnBTransTable);
741
742      /*
743      * override the translations
744     XtSetArg(args[n], XmNtranslations      , DrawnBTrans);              ++n;
745      */
746     if (DrawnBTrans != NULL)
747         XtOverrideTranslations(pDAS->dispWid, DrawnBTrans);
748     _DtHelpProcessUnlock();
749   
750     if (_XmGetFocusPolicy(parent) == XmPOINTER)
751       {
752         XtAddEventHandler (pDAS->dispWid, EnterWindowMask, True,
753                         (XtEventHandler)_DtHelpEnterLeaveCB, (XtPointer) pDAS);
754         XtAddEventHandler (pDAS->dispWid, LeaveWindowMask, True,
755                         (XtEventHandler)_DtHelpEnterLeaveCB, (XtPointer) pDAS);
756       }
757     else
758         XtAddEventHandler (pDAS->dispWid, FocusChangeMask, True,
759                         (XtEventHandler)_DtHelpFocusCB, (XtPointer) pDAS);
760
761     XtAddEventHandler (pDAS->dispWid, VisibilityChangeMask, True,
762                         (XtEventHandler)_DtHelpVisibilityCB, (XtPointer) pDAS);
763   
764
765     /* Add a destroy callback so that the display area can clean up prior to
766      * the help widget getting destroyed (e.g. display area's parent) 
767      */
768     XtAddCallback(pDAS->dispWid, XmNdestroyCallback,
769                                 _DtHelpDisplayAreaDestroyCB, (XtPointer) pDAS);
770   
771     n = 0;
772     XtSetArg(args[n], XmNshadowThickness   , &shadowThick);     ++n;
773     XtSetArg(args[n], XmNhighlightThickness, &highThick);       ++n;
774     XtSetArg(args[n], XmNforeground    , &(pDAS->foregroundColor)); ++n;
775     XtSetArg(args[n], XmNbackground    , &(pDAS->backgroundColor)); ++n;
776     XtSetArg(args[n], XmNhighlightColor, &(pDAS->traversalColor) ); ++n;
777     XtSetArg(args[n], XmNdepth         , &(pDAS->depth)          ); ++n;
778     XtGetValues(pDAS->dispWid, args, n);
779     pDAS->decorThickness = shadowThick + highThick;
780
781     /*
782      * Get the underline information
783      */
784     GetUnderLineInfo (dpy, pDAS, &(pDAS->lineThickness));
785
786     /*
787      * get the tiling pattern.
788      */
789     tile = XmGetPixmap (XtScreen(pDAS->dispWid), "50_foreground",
790                                 pDAS->foregroundColor, pDAS->backgroundColor);
791
792     /*
793      * Get the data for the graphics contexts and create the GC's.
794      */
795     gcMask = (GCFunction   | GCPlaneMask   | GCForeground  |
796                 GCBackground  | GCLineWidth   | GCLineStyle   |
797                 GCClipXOrigin | GCClipYOrigin | GCClipMask);
798
799     gcValues.function      = GXcopy;
800     gcValues.plane_mask    = AllPlanes;
801     gcValues.foreground    = pDAS->foregroundColor;
802     gcValues.background    = pDAS->backgroundColor;
803     gcValues.line_style    = LineSolid;
804     gcValues.line_width    = pDAS->lineThickness;
805     gcValues.clip_x_origin = 0;
806     gcValues.clip_y_origin = 0;
807     gcValues.clip_mask     = None;
808     if (tile)
809       {
810         gcMask |= GCTile;
811         gcValues.tile = tile;
812       }
813  
814     pDAS->normalGC = XCreateGC(dpy,
815                 RootWindowOfScreen(XtScreen(pDAS->dispWid)), gcMask, &gcValues);
816
817     gcMask &= (~GCTile);
818     pDAS->pixmapGC = XCreateGC(dpy,
819                 RootWindowOfScreen(XtScreen(pDAS->dispWid)), gcMask, &gcValues);
820   
821     gcValues.foreground = pDAS->backgroundColor;
822     gcValues.background = pDAS->foregroundColor;
823     pDAS->invertGC = XCreateGC(dpy,
824                 RootWindowOfScreen(XtScreen(pDAS->dispWid)), gcMask, &gcValues);
825   
826     /*
827      * Set the size of the text view area to the requested
828      * number of columns and lines.
829      */
830     char_width          = pDAS->charWidth * columns;
831
832     /*
833      * Make sure the margins include enough room for a traversal line
834      */
835     if (((int) pDAS->marginWidth) < pDAS->lineThickness)
836         pDAS->marginWidth = pDAS->lineThickness;
837     if (((int) pDAS->marginHeight) < pDAS->lineThickness)
838         pDAS->marginHeight = pDAS->lineThickness;
839     if (pDAS->leading < pDAS->lineThickness)
840         pDAS->leading = pDAS->lineThickness;
841
842     /*
843      * get the scrollbar widths.
844      */
845     if (NULL != pDAS->horzScrollWid)
846       {
847         n = 0;
848         XtSetArg(args[n], XmNheight      , &hBarHeight); n++;
849         XtSetArg(args[n], XmNinitialDelay, &(pDAS->horz_init_scr)); n++;
850         XtSetArg(args[n], XmNrepeatDelay , &(pDAS->horz_rep_scr));  n++;
851         XtGetValues(pDAS->horzScrollWid, args, n);
852       }
853
854     if (NULL != pDAS->vertScrollWid)
855       {
856         n = 0;
857         XtSetArg(args[n], XmNwidth       , &vBarWidth);             n++;
858         XtSetArg(args[n], XmNinitialDelay, &(pDAS->vert_init_scr)); n++;
859         XtSetArg(args[n], XmNrepeatDelay , &(pDAS->vert_rep_scr));  n++;
860         XtGetValues(pDAS->vertScrollWid, args, n);
861       }
862
863     /*
864      * calculate the display area height/width
865      */
866     pDAS->dispUseWidth  = ((int) (char_width / 10 + (char_width % 10 ? 1 : 0)))
867                                               + 2 * pDAS->marginWidth;
868     if (vert_flag != _DtHelpSTATIC && pDAS->dispUseWidth < vBarWidth)
869         pDAS->dispUseWidth = vBarWidth;
870     pDAS->dispWidth     = pDAS->dispUseWidth  + 2 * pDAS->decorThickness;
871
872     pDAS->dispUseHeight = pDAS->lineHeight * rows;
873     if (horz_flag != _DtHelpSTATIC && pDAS->dispUseHeight < hBarHeight)
874         pDAS->dispUseHeight = hBarHeight;
875     pDAS->dispHeight    = pDAS->dispUseHeight + 2 * pDAS->decorThickness;
876
877     /*
878      * Truncate the width and height to the size of the display.
879      * This will prevent an X protocal error when it is asked for
880      * a too large size. Besides, any decent window manager will
881      * force the overall size to the height and width of the display.
882      * This simply refines the size down to a closer (but not perfect)
883      * fit.
884      */
885     if (((int) pDAS->dispWidth) > XDisplayWidth (dpy, screen)) {
886         pDAS->dispWidth = XDisplayWidth (dpy, screen);
887     }
888     if (((int) pDAS->dispHeight) > XDisplayHeight (dpy, screen)) {
889         pDAS->dispHeight = XDisplayHeight (dpy, screen);
890     }
891
892     n = 0;
893     pDAS->formWidth  = 0;
894     pDAS->formHeight = 0;
895     XtSetArg(args[n], XmNwidth, pDAS->dispWidth);               ++n;
896     XtSetArg(args[n], XmNheight, pDAS->dispHeight);             ++n;
897     XtSetValues(pDAS->dispWid, args, n);
898
899     /*
900      * set the scroll bar values
901      */
902     if (pDAS->vertScrollWid != NULL)
903       {
904         n = 0;
905         XtSetArg(args[n], XmNmaximum           , pDAS->dispUseHeight);  ++n;
906         XtSetArg(args[n], XmNincrement         , pDAS->lineHeight);     ++n;
907         XtSetArg(args[n], XmNpageIncrement     , pDAS->lineHeight);     ++n;
908         XtSetArg(args[n], XmNsliderSize        , pDAS->dispUseHeight);  ++n;
909         XtSetValues(pDAS->vertScrollWid, args, n);
910       }
911   
912     if (pDAS->resizeCall)
913         (*(pDAS->resizeCall)) (pDAS->clientData);
914
915     /*
916      * calculate the offset for the right edge of the
917      * horizontal scrollbar.
918      */
919     if (vert_flag == _DtHelpSTATIC && pDAS->horzScrollWid)
920       {
921         width = vBarWidth + margin_width;
922
923         XtSetArg(args[0], XmNrightOffset , width);
924         XtSetValues(pDAS->horzScrollWid, args, 1);
925       }
926
927     /*
928      * calculate the offset for the bottom end of the
929      * vertical scrollbar.
930      */
931     if (horz_flag == _DtHelpSTATIC && pDAS->vertScrollWid)
932       {
933         width = hBarHeight + margin_height;
934
935         XtSetArg(args[0], XmNbottomOffset , width);
936         XtSetValues(pDAS->vertScrollWid, args, 1);
937       }
938
939     rectangle[0].x      = pDAS->decorThickness;
940     rectangle[0].y      = pDAS->decorThickness;
941     rectangle[0].width  = pDAS->dispUseWidth;
942     rectangle[0].height = pDAS->dispUseHeight;
943     XSetClipRectangles(XtDisplay(pDAS->dispWid), pDAS->normalGC, 0, 0,
944                                                 rectangle, 1, Unsorted);
945     XSetClipRectangles(XtDisplay(pDAS->dispWid), pDAS->invertGC, 0, 0,
946                                                 rectangle, 1, Unsorted);
947
948     /*
949      * get the colormap and the visual
950      */
951     if (!XtIsShell(parent) && XtParent(parent) != NULL)
952         parent = XtParent(parent);
953
954     pDAS->visual = NULL;
955
956     n = 0;
957     XtSetArg (args[n], XmNcolormap, &(pDAS->colormap)); n++;
958     XtSetArg (args[n], XmNvisual  , &(pDAS->visual  )); n++;
959     XtGetValues (parent, args, n);
960
961     if (pDAS->visual == NULL)
962         pDAS->visual = XDefaultVisualOfScreen(XtScreen(pDAS->dispWid));
963
964     /*
965      * set up the canvas
966      */
967     _DtHelpProcessLock();
968     DefVirtFunctions.exec_cmd_filter = exec_ok_routine;
969
970     pDAS->canvas = _DtCanvasCreate (DefVirtFunctions, (_DtCvPointer) pDAS);
971     _DtHelpProcessUnlock();
972
973     return (XtPointer) pDAS;
974
975 }  /* End _DtHelpCreateDA */
976
977
978 /*********************************************************************
979  * Function: CreateDisplayArea
980  *
981  *    Creates a Text Graphic area with the appropriate scroll bars.
982  *    specifying the size with rows and columns
983  *
984  *********************************************************************/
985 XtPointer
986 _DtHelpCreateDisplayArea(
987     Widget       parent,
988     char        *name,
989     short        vert_flag,
990     short        horz_flag,
991     Boolean      traversal_flag,
992     int          rows,
993     int          columns,
994     void        (*hyperTextCB)(),
995     void        (*resizeCB)(),
996     int         (*exec_ok_routine)(),
997     XtPointer    client_data,
998     XmFontList   default_list )
999 {
1000     return HelpCreateDA(parent, name,
1001                         vert_flag, horz_flag,
1002                         traversal_flag,
1003                         _DtCvIGNORE_BOUNDARY, _DtCvRENDER_PARTIAL,
1004                         rows, columns, 100,
1005                         hyperTextCB, resizeCB, exec_ok_routine,
1006                         client_data, default_list);
1007 }
1008
1009 /*********************************************************************
1010  * Function: CreateOutputArea
1011  *
1012  *    Creates a Text Graphic area with the appropriate scroll bars.
1013  *    specifying the size with width and height
1014  *
1015  *********************************************************************/
1016 XtPointer
1017 _DtHelpCreateOutputArea(
1018     Widget       parent,
1019     char        *name,
1020     short        vert_flag,
1021     short        horz_flag,
1022     Boolean      traversal_flag,
1023     _DtCvValue   honor_size,
1024     _DtCvRenderType render_type,
1025     Dimension    width,
1026     Dimension    height,
1027     unsigned short media_resolution,
1028     void        (*hyperTextCB)(),
1029     void        (*resizeCB)(),
1030     int         (*exec_ok_routine)(),
1031     XtPointer    client_data,
1032     XmFontList   default_list )
1033 {
1034     DtHelpDispAreaStruct *pDAS;
1035
1036     pDAS = HelpCreateDA(parent, name,
1037                         vert_flag, horz_flag,
1038                         traversal_flag, honor_size, render_type,
1039                         1, 1, media_resolution,
1040                         hyperTextCB, resizeCB, exec_ok_routine,
1041                         client_data, default_list);
1042     /* if area created successfully, then resize it to the given size */
1043     if (pDAS)
1044         _DtHelpSetScrollBars(pDAS, width, height);
1045
1046     return pDAS;
1047 }