dtfile: Add missing prototypes
[oweals/cde.git] / cde / programs / dtwm / Button.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 librararies 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 /* $XConsortium: Button.c /main/7 1995/11/14 10:03:27 rswiston $ */
24 #ifdef REV_INFO
25 #ifndef lint
26 static char SCCSID[] = "OSF/Motif: @(#)Button.c 1.19 95/05/01";
27 #endif /* lint */
28 #endif /* REV_INFO */
29 /******************************************************************************
30 *******************************************************************************
31 *
32 *  (c) Copyright 1992 HEWLETT-PACKARD COMPANY
33 *  ALL RIGHTS RESERVED
34 *  
35 *******************************************************************************
36 ******************************************************************************/
37 #include <stdio.h>
38 #include <X11/cursorfont.h>
39 #include "ButtonP.h"
40 #include <Xm/ManagerP.h>
41 #include <Xm/DrawP.h>
42 #include <Dt/Control.h>
43 #include <Dt/MacrosP.h>
44 #include <Dt/DtStrDefs.h>
45
46 #include "DtSvcInternal.h"   /* _DtGetMask */
47 #include <Xm/XmPrivate.h>    /* _XmFocusInGadget, _XmFocusOutGadget, _XmSocorro */
48
49 #define DELAY_DEFAULT 100       
50
51 static void Initialize( 
52                         Widget request_w,
53                         Widget new_w) ;
54 static void GetGCs( 
55                         Widget w) ;
56 static void UpdateGCs( 
57                         Widget w) ;
58 static void Redisplay( 
59                         Widget w,
60                         XEvent *event,
61                         Region region) ;
62 static Boolean SetValues( 
63                         Widget current_w,
64                         Widget request_w,
65                         Widget new_w) ;
66 static void Arm( 
67                         Widget w,
68                         XEvent *event,
69                         String *params,
70                         Cardinal *num_params) ;
71 static void Disarm( 
72                         Widget w,
73                         XEvent *event,
74                         String *params,
75                         Cardinal *num_params) ;
76 static void Activate( 
77                         Widget w,
78                         XEvent *event,
79                         String *params,
80                         Cardinal *num_params) ;
81 static void ArmAndActivate( 
82                         Widget w,
83                         XEvent *event,
84                         String *params,
85                         Cardinal *num_params) ;
86 static void InputDispatch(
87                         Widget w,
88                         XButtonEvent *event,
89                         Mask event_mask) ;
90 static Boolean VisualChange(
91                         Widget w,
92                         Widget current_w,
93                         Widget new_w) ;
94 static void ArmTimeout( 
95                         Widget w,
96                         XtIntervalId *id) ;
97 static void Enter( 
98                         Widget wid,
99                         XEvent *event,
100                         String *params,
101                         Cardinal *num_params) ;
102 static void Leave( 
103                         Widget wid,
104                         XEvent *event,
105                         String *params,
106                         Cardinal *num_params) ;
107 static void CallCallback( 
108                         DtButtonGadget g,
109                         XtCallbackList cb,
110                         int reason,
111                         XEvent *event) ;
112 static void DefaultSelectColor(
113                         Widget widget,
114                         int offset,
115                         XrmValue *value) ;
116
117 /*  Resource list for button  */
118
119 #define R_Offset(field) \
120         XtOffset (DtButtonGadget, button.field)
121 static XtResource resources[] = 
122 {
123         {
124                 XmNcursorFont,
125                 XmCCursorFont, XmRInt, sizeof (int),
126                 R_Offset (cursor_font),
127                 XmRImmediate, (XtPointer) 1
128         },
129         {
130                 XmNarmColor,
131                 XmCArmColor, XmRPixel, sizeof (Pixel),
132                 R_Offset (arm_color),
133                 XmRCallProc, (XtPointer) DefaultSelectColor
134         },
135         {
136                 XmNsubpanel,
137                 XmCSubpanel, XmRWidget, sizeof (Widget),
138                 R_Offset (subpanel),
139                 XmRImmediate, (XtPointer) NULL
140         },
141         {
142                 XmNpushFunction,
143                 XmCPushFunction, XmRFunction, sizeof (XtPointer),
144                 R_Offset (push_function),
145                 XmRImmediate, (XtPointer) NULL
146         },
147         {
148                 XmNpushArgument,
149                 XmCPushArgument, XmRPointer, sizeof (XtPointer),
150                 R_Offset (push_argument),
151                 XmRImmediate, (XtPointer) NULL
152         },
153         {
154                 XmNimageName,
155                 XmCString, XmRString, sizeof (String),
156                 R_Offset (image_name),
157                 XmRImmediate, (XtPointer) ""
158         },
159
160         {
161                 XmNcallback,
162                 XmCCallback, XmRCallback, sizeof(XtCallbackList),
163                 R_Offset (callback),
164                 XmRImmediate, (caddr_t) NULL
165         },
166
167         {
168                 XmNmultiClick,
169                 XmCMultiClick, XmRMultiClick, sizeof (unsigned char),
170                 R_Offset (multiClick),
171                 XmRImmediate, (XtPointer) XmMULTICLICK_KEEP
172         }
173 };
174
175
176 /*  The button class record definition  */
177
178 externaldef (dtbuttongadgetclassrec)
179         DtButtonGadgetClassRec dtButtonGadgetClassRec=
180 {
181    {
182       (WidgetClass) &xmGadgetClassRec,  /* superclass            */     
183       "DtButton",                       /* class_name            */     
184       sizeof(DtButtonGadgetRec),        /* widget_size           */     
185       NULL,                             /* class_initialize      */    
186       NULL,                             /* class_part_initialize */
187       FALSE,                            /* class_inited          */     
188       (XtInitProc) Initialize,          /* initialize            */     
189       NULL,                             /* initialize_hook       */
190       NULL,                             /* realize               */     
191       NULL,                             /* actions               */     
192       0,                                /* num_actions           */     
193       resources,                        /* resources             */     
194       XtNumber(resources),              /* num_resources         */     
195       NULLQUARK,                        /* xrm_class             */     
196       TRUE,                             /* compress_motion       */     
197       XtExposeCompressMaximal,          /* compress_exposure     */     
198       TRUE,                             /* compress_enterleave   */
199       FALSE,                            /* visible_interest      */     
200       NULL,                             /* destroy               */     
201       NULL,                             /* resize                */
202       (XtExposeProc) Redisplay,         /* expose                */     
203       (XtSetValuesFunc) SetValues,      /* set_values            */     
204       NULL,                             /* set_values_hook       */
205       XtInheritSetValuesAlmost,         /* set_values_almost     */
206       NULL,                             /* get_values_hook       */
207       NULL,                             /* accept_focus          */     
208       XtVersion,                        /* version               */
209       NULL,                             /* callback private      */
210       NULL,                             /* tm_table              */
211       NULL,                             /* query_geometry        */
212       NULL,                             /* display_accelerator   */
213       NULL,                             /* extension             */
214    },
215
216    /*      XmGadget Part     */
217    {
218       (XtWidgetProc) _XtInherit,           /* Gadget border_highlight   */
219       (XtWidgetProc) _XtInherit,           /* Gadget border_unhighlight */
220       ArmAndActivate,                      /* arm_and_activate          */
221       (XmWidgetDispatchProc)InputDispatch, /* input_dispatch            */
222       VisualChange,                        /* visual_change             */
223       NULL,                                /* get resources             */
224       0,                                   /* num get_resources         */
225       NULL,                                /* class_cache_part          */
226       NULL,                                /* extension                 */
227    }
228
229 };
230
231 externaldef(dtbuttonwidgetclass) WidgetClass dtButtonGadgetClass =
232                           (WidgetClass) &dtButtonGadgetClassRec;
233
234
235 /************************************************************************
236  *
237  *  Initialize
238  *     The main widget instance initialization routine.
239  *
240  ************************************************************************/
241
242 static void 
243 Initialize(
244         Widget request_w,
245         Widget new_w )
246 {
247    DtButtonGadget request = (DtButtonGadget) request_w ;
248    DtButtonGadget new_g = (DtButtonGadget) new_w ;
249    XmManagerWidget mw = (XmManagerWidget) XtParent(new_w) ;
250
251    new_g->button.timer = 0;
252    new_g->button.click_count = 0;
253    new_g->button.armTimeStamp = 0;
254    new_g->button.activateTimeStamp = 0;
255
256    B_Armed (new_g) = False;
257
258 /* Set the input mask for events handled by Manager.
259 */
260    G_EventMask (new_g) = (XmARM_EVENT | XmACTIVATE_EVENT |
261                         XmMULTI_ARM_EVENT | XmMULTI_ACTIVATE_EVENT |
262                         XmHELP_EVENT | XmFOCUS_IN_EVENT |
263                         XmFOCUS_OUT_EVENT | XmENTER_EVENT | XmLEAVE_EVENT);
264
265 /*      Get pixmap and mask, get pixmap geometry, get gcs.
266  */
267    if (B_ImageName (new_g) != NULL)
268    {
269        String str = B_ImageName (new_g);
270        B_ImageName (new_g) = XtMalloc (strlen (str) + 1);
271        strcpy (B_ImageName (new_g), str);
272
273        B_Pixmap (new_g) =
274                    XmGetPixmap (XtScreen (new_g), B_ImageName (new_g),
275                                    M_BottomShadowColor (mw),
276                                    M_TopShadowColor (mw));
277        B_Mask (new_g) =
278                    _DtGetMask (XtScreen (new_g), B_ImageName (new_g));
279
280        if (B_Pixmap (new_g) != XmUNSPECIFIED_PIXMAP)
281        {
282            Window               root;
283            int          int_x = 0, int_y = 0;
284            unsigned int int_w = 0, int_h = 0,
285                            int_bw, depth;
286
287            XGetGeometry (XtDisplay (new_g), B_Pixmap (new_g),
288                            &root, &int_x, &int_y, &int_w, &int_h,
289                            &int_bw, &depth);
290
291            B_PixmapWidth (new_g) = (Dimension) int_w;
292            B_PixmapHeight (new_g) = (Dimension) int_h;
293        }
294        else
295        {
296            B_PixmapWidth (new_g) = 0;
297            B_PixmapHeight (new_g) = 0;
298        }
299    }
300    else
301    {
302        B_Pixmap (new_g) = XmUNSPECIFIED_PIXMAP;
303        B_Mask (new_g) = XmUNSPECIFIED_PIXMAP;
304        B_PixmapWidth (new_g) = 0;
305        B_PixmapHeight (new_g) = 0;
306    }
307
308    GetGCs (new_w);
309
310 /*      Set widget geometry.
311  */
312    new_g -> gadget.shadow_thickness = 1;
313    new_g -> gadget.highlight_thickness = 1;
314    if (G_Width(request) == 0)
315        {
316        if (B_PixmapWidth (new_g) > 0)
317            G_Width(new_g) = B_PixmapWidth (new_g) + 4;
318        else
319            G_Width(new_g) = 10;
320        }
321    if (G_Height(request) == 0)
322        {
323        if (B_PixmapHeight (new_g) > 0)
324            G_Height(new_g) = B_PixmapHeight (new_g) + 4;
325        else
326            G_Height(new_g) = 10;
327        }
328 }
329
330
331
332
333 /************************************************************************
334  *
335  *  GetGCs
336  *     Get the graphics context used for drawing the button.
337  *
338  ************************************************************************/
339
340 static void 
341 GetGCs(
342         Widget w )
343 {
344 DtButtonGadget bg = (DtButtonGadget) w ;
345 XmManagerWidget mw = (XmManagerWidget) XtParent(w) ;
346 XGCValues values;
347 XtGCMask  valueMask;
348
349 valueMask = GCForeground | GCBackground;
350
351 values.foreground = M_Foreground(mw);
352 values.background = M_Background(mw);
353 bg -> button.gc_normal = XtGetGC ((Widget) mw, valueMask, &values);
354
355 values.foreground = B_ArmColor (bg);
356 bg -> button.gc_armed_bg = XtGetGC ((Widget) mw, valueMask, &values);
357
358 values.foreground = M_Background(mw);
359 values.background = M_Foreground(mw);
360 bg -> button.gc_background = XtGetGC ((Widget) mw, valueMask, &values);
361
362 /*      Get Clip GC
363  */
364 if (B_Mask(bg) != XmUNSPECIFIED_PIXMAP) 
365     {
366     valueMask = GCForeground | GCBackground | GCClipMask;
367     values.clip_mask = B_Mask(bg);
368     values.foreground = M_Foreground (mw);
369     values.background = M_Background (mw);
370     bg->button.gc_clip = XtGetGC ((Widget) mw, valueMask, &values);
371     }
372 else
373     bg->button.gc_clip = NULL;
374 }
375
376
377 static void 
378 UpdateGCs(
379         Widget w )
380 {
381    DtButtonGadget bg = (DtButtonGadget) w ;
382    XmManagerWidget mw = (XmManagerWidget) XtParent(w) ;
383
384    XtReleaseGC ((Widget) mw, bg->button.gc_normal);
385    XtReleaseGC ((Widget) mw, bg->button.gc_background);
386    XtReleaseGC ((Widget) mw, bg->button.gc_armed_bg);
387
388    if (bg->button.gc_clip != NULL) 
389       XtReleaseGC ((Widget) mw, bg->button.gc_clip);
390
391    GetGCs (w);
392 }
393
394
395 /************************************************************************
396  *
397  *  Redisplay
398  *     General redisplay function called on exposure events.
399  *
400  ************************************************************************/
401 /* ARGSUSED */
402 static void 
403 Redisplay(
404         Widget w,
405         XEvent *event,
406         Region region )
407 {
408 DtButtonGadget bg = (DtButtonGadget) w;
409 Dimension       s_t = bg -> gadget.shadow_thickness;
410 Dimension       h_t = bg -> gadget.highlight_thickness;
411 Position        x;
412 Pixmap  pix;
413 GC      gc;
414
415 gc = (B_Armed (bg)) ? bg -> button.gc_armed_bg : bg -> button.gc_background;
416 XFillRectangle (XtDisplay (bg), XtWindow (bg),
417                 gc, G_X(bg) +s_t + h_t, G_Y(bg) + s_t + h_t,
418                 G_Width(bg) - 2 * (s_t + h_t),
419                 G_Height(bg) - 2 * (s_t + h_t));
420
421 if (s_t > 0)
422     {
423     GC  gc1, gc2;
424     if (B_Armed (bg))
425         {
426         gc1 = XmParentBottomShadowGC(w);
427         gc2 = XmParentTopShadowGC(w);
428         }
429     else
430         {
431         gc1 = bg -> button.gc_background;
432         gc2 = bg -> button.gc_background;
433         }
434     XmeDrawShadows (XtDisplay(bg), XtWindow (bg), gc1, gc2, 
435                           G_X(bg) + h_t, G_Y(bg) + h_t,
436                           G_Width(bg) - 2 * h_t, G_Height(bg) - 2 * h_t,
437                           s_t,XmSHADOW_OUT);
438     }
439
440 x = G_X(bg) + ((Position)(G_Width(bg) - B_PixmapWidth (bg))/2);
441 if (x % 2 == 1)
442     x++;
443
444 if (B_Mask (bg) != XmUNSPECIFIED_PIXMAP)
445     {
446     gc = bg->button.gc_clip;
447     XSetClipMask (XtDisplay(bg), gc, B_Mask (bg));
448     XSetClipOrigin (XtDisplay(bg), gc,
449                 x, G_Y(bg) + (Position)(G_Height(bg) - B_PixmapHeight (bg))/2);
450     }
451 else
452     gc = bg->button.gc_normal;
453
454 pix = B_Pixmap (bg);
455 if ((gc != NULL) && (pix != XmUNSPECIFIED_PIXMAP))
456     {   
457     XCopyArea (XtDisplay ((Widget) bg), pix, XtWindow ((Widget) bg), gc, 0, 0,
458                 B_PixmapWidth (bg), B_PixmapHeight (bg),
459                 x, G_Y(bg) + (Position)(G_Height(bg) - B_PixmapHeight (bg))/2);
460     }
461
462 if (bg -> gadget.highlighted)
463    (*(xmGadgetClassRec.gadget_class.border_highlight))((Widget) bg);
464
465 }
466
467
468 /************************************************************************
469  *
470  *  Destroy
471  *      Clean up allocated resources when the widget is destroyed.
472  *
473  ************************************************************************/
474 #if 0
475 static void 
476 Destroy(
477         Widget w )
478 {
479 DtButtonGadget bg = (DtButtonGadget) w ;
480
481 if (bg->button.timer)
482     XtRemoveTimeOut (bg->button.timer);
483
484 XtReleaseGC (w, bg -> button.gc_normal);
485 XtReleaseGC (w, bg -> button.gc_background);
486 XtReleaseGC (w, bg -> button.gc_armed_bg);
487 if (bg -> button.gc_clip != NULL) 
488     XtReleaseGC (w, bg -> button.gc_clip);
489
490 XtRemoveAllCallbacks (w, "callback");
491 }
492 #endif /* 0 */
493
494
495
496 /************************************************************************
497  *
498  *  SetValues
499  *      Note:  The only implementation within this function is to
500  *      support the resetting of the image, cursor, and functions
501  *      as needed by the front panel.
502  *
503  ************************************************************************/
504
505 /* ARGSUSED */
506 static Boolean 
507 SetValues(
508         Widget current_w,
509         Widget request_w,
510         Widget new_w )
511
512 {
513    DtButtonGadget  current = (DtButtonGadget) current_w;
514    DtButtonGadget  new_g = (DtButtonGadget) new_w;
515    XmManagerWidget mw = (XmManagerWidget) XtParent(new_w);
516    Boolean          returnFlag = FALSE;
517
518    G_EventMask (new_g) = (XmARM_EVENT | XmACTIVATE_EVENT |
519                         XmMULTI_ARM_EVENT | XmMULTI_ACTIVATE_EVENT |
520                         XmHELP_EVENT | XmFOCUS_IN_EVENT |
521                         XmFOCUS_OUT_EVENT | XmENTER_EVENT | XmLEAVE_EVENT);
522
523    /*  Change the image  */
524
525    if (strcmp (B_ImageName (current), B_ImageName (new_g)) != 0)
526    {
527       String str = B_ImageName (new_g);
528
529       XtFree (B_ImageName (current));
530       B_ImageName (new_g) = XtMalloc (strlen (str) + 1);
531       strcpy (B_ImageName (new_g), str);
532
533       B_Pixmap (new_g) =
534          XmGetPixmap (XtScreen (new_g), B_ImageName (new_g),
535                       M_BottomShadowColor (mw),
536                       M_TopShadowColor (mw));
537       B_Mask (new_g) =
538          _DtGetMask (XtScreen (new_g), B_ImageName (new_g));
539
540       if (B_Pixmap (new_g) != XmUNSPECIFIED_PIXMAP)
541       {
542          Window       root;
543          int          int_x = 0, int_y = 0;
544          unsigned int int_w = 0, int_h = 0,
545                       int_bw, depth;
546
547          XGetGeometry (XtDisplay (new_g), B_Pixmap (new_g),
548                        &root, &int_x, &int_y, &int_w, &int_h, &int_bw, &depth);
549
550          B_PixmapWidth (new_g) = (Dimension) int_w;
551          B_PixmapHeight (new_g) = (Dimension) int_h;
552       }
553       else
554       {
555          B_PixmapWidth (new_g) = 0;
556          B_PixmapHeight (new_g) = 0;
557       }
558
559       UpdateGCs(new_w);
560
561       returnFlag = TRUE;
562    }
563    else
564    {
565       if (B_ImageName (new_g) != B_ImageName (current))
566       {
567          String str = B_ImageName (new_g);
568
569          XtFree (B_ImageName (current));
570          B_ImageName (new_g) = XtMalloc (strlen (str) + 1);
571          strcpy (B_ImageName (new_g), str);
572       }
573    }
574
575    return (returnFlag);
576 }
577
578
579
580
581 /************************************************************************
582  *
583  *  arm
584  *     This function processes button 1 down occuring on the button.
585  *
586  ************************************************************************/
587
588 static void 
589 Arm(
590         Widget w,
591         XEvent *event,
592         String *params,
593         Cardinal *num_params )
594 {
595    DtButtonGadget bg = (DtButtonGadget) w ;
596
597    (void) XmProcessTraversal((Widget) bg, XmTRAVERSE_CURRENT);
598
599    B_Armed (bg) = True;
600
601    if ((event->xbutton.time - bg->button.armTimeStamp) >
602        XtGetMultiClickTime(XtDisplay(bg)))
603    {
604       bg -> button.armTimeStamp = event->xbutton.time;
605       B_Expose ( w, event, NULL);
606    }
607 }
608
609
610 /************************************************************************
611  *
612  *  disarm
613  *     This function processes button 1 up occuring on the button.
614  *
615  ************************************************************************/
616
617 static void 
618 Disarm(
619         Widget w,
620         XEvent *event,
621         String *params,
622         Cardinal *num_params )
623 {
624    DtButtonGadget bg = (DtButtonGadget) w ;
625
626    B_Armed (bg) = False;
627
628    B_Expose (w, event, NULL);
629 }
630
631
632 /************************************************************************
633  *
634  *  activate
635  *     This function processes button 1 up occuring on the button.
636  *     If the button 1 up occurred inside the button the activate
637  *     callbacks are called.
638  *
639  ************************************************************************/
640
641 static void 
642 Activate(
643         Widget w,
644         XEvent *event,
645         String *params,
646         Cardinal *num_params )
647 {
648    DtButtonGadget bg = (DtButtonGadget) w ;
649    DtButtonCallbackStruct call_value;
650
651    if (!B_Armed (bg))
652       return;
653
654    if ((event->xbutton.time - bg->button.activateTimeStamp) >
655        XtGetMultiClickTime(XtDisplay(bg)))
656    {
657       bg -> button.activateTimeStamp = event->xbutton.time;
658       bg->button.click_count = 1;
659    }
660    else
661       bg->button.click_count++;
662
663    B_Armed (bg) = False;
664
665    if (bg->button.callback)
666    {
667       call_value.reason = XmCR_ACTIVATE;
668       call_value.event = event;
669       call_value.click_count = bg->button.click_count;
670
671       if ((bg->button.multiClick == XmMULTICLICK_DISCARD) &&
672           (call_value.click_count > 1)) { 
673           return;
674       }
675
676       XFlush(XtDisplay(bg));
677
678       CallCallback (bg, B_Callback (bg), XmCR_ACTIVATE, event);
679    }
680 }
681
682
683 /************************************************************************
684  *
685  *     ArmAndActivate
686  *
687  ************************************************************************/
688
689 static void 
690 ArmAndActivate(
691         Widget w,
692         XEvent *event,
693         String *params,
694         Cardinal *num_params )
695 {
696    DtButtonCallbackStruct call_value;
697    DtButtonGadget bg = (DtButtonGadget) w ;
698
699    B_Armed (bg) = True;
700    Redisplay ( w, event, FALSE); 
701
702    XFlush (XtDisplay (bg));
703
704    call_value.reason = XmCR_ACTIVATE;
705    call_value.event = event;
706    call_value.click_count = 1;  /* always 1 in kselect */
707
708    if (bg->button.callback)
709    {
710       XFlush (XtDisplay (bg));
711       CallCallback (bg, B_Callback (bg), XmCR_ACTIVATE, event);
712    }
713    B_Armed (bg) = False;
714
715    /* If the button is still around, show it released, after a short delay */
716
717    if (bg->object.being_destroyed == False)
718    {
719       bg->button.timer = XtAppAddTimeOut(
720                         XtWidgetToApplicationContext((Widget)bg),
721                         (unsigned long) DELAY_DEFAULT,
722                         (XtTimerCallbackProc)ArmTimeout,
723                         (caddr_t)bg);
724    }
725 }
726
727 /* ARGSUSED */
728 static void 
729 ArmTimeout(
730         Widget w,
731         XtIntervalId *id )
732 {
733     DtButtonGadget bg = (DtButtonGadget) w ;
734
735     bg -> button.timer = 0;
736     if (XtIsRealized ((Widget)bg) && XtIsManaged ((Widget)bg)) {
737        Redisplay ( w, NULL, FALSE); 
738        XFlush (XtDisplay (bg));
739     }
740     return;
741 }
742
743
744 /*-------------------------------------------------------------
745 **      InputDispatch
746 **              Process event dispatched from parent or event handler.
747 */
748 static void
749 InputDispatch(
750         Widget w,
751         XButtonEvent *event,
752         Mask event_mask )
753 {
754         DtButtonGadget bg = (DtButtonGadget) w ;
755
756         if (event_mask & XmARM_EVENT ||
757             event_mask & XmMULTI_ARM_EVENT)
758         {
759            if (event->button == Button1)
760              Arm (w, (XEvent*) event, (String *)NULL, (Cardinal)0);
761         }
762         else if (event_mask & XmACTIVATE_EVENT ||
763                  event_mask & XmMULTI_ACTIVATE_EVENT)
764         {
765                 if (event->button == Button1)
766                 {
767                    if (event->x >= G_X (bg) &&
768                          event->x <= (Position)(G_X (bg) + G_Width (bg)) &&
769                          event->y >= G_Y (bg) &&
770                          event->y <= (Position)(G_Y (bg) + G_Height (bg)))
771                    {
772                         Activate (w, (XEvent*) event,
773                                   (String *)NULL, (Cardinal)0);
774                         Disarm (w, (XEvent*) event,
775                                   (String *)NULL, (Cardinal)0);
776                    }
777                    else
778                         Disarm (w, (XEvent*) event,
779                                   (String *)NULL, (Cardinal)0);
780                 }
781         }
782         else if (event_mask & XmHELP_EVENT)
783                 _XmSocorro (w, (XEvent *)event,
784                                      (String *)NULL,(Cardinal)0);
785         else if (event_mask & XmENTER_EVENT)
786                 Enter (w, (XEvent *)event, (String *)NULL,(Cardinal)0);
787         else if (event_mask & XmLEAVE_EVENT)
788                 Leave (w, (XEvent *)event, (String *)NULL,(Cardinal)0);
789         else if (event_mask & XmFOCUS_IN_EVENT)
790                 _XmFocusInGadget (w, (XEvent *)event,
791                                     (String *)NULL,(Cardinal)0);
792         else if (event_mask & XmFOCUS_OUT_EVENT)
793                 _XmFocusOutGadget (w, (XEvent *)event,
794                                     (String *)NULL,(Cardinal)0);
795 }
796
797
798 /*-------------------------------------------------------------
799 **      VisualChange
800 **              Update GCs when parent visuals change.
801 */
802 static Boolean
803 VisualChange(
804         Widget w,
805         Widget current_w,
806         Widget new_w )
807 {
808     XmManagerWidget  current = (XmManagerWidget) current_w;
809     XmManagerWidget  new_m = (XmManagerWidget) new_w;
810     DtButtonGadget   bg = (DtButtonGadget) w ;
811     Boolean          update = False;
812
813     /* If the parent foreground or background has changed,
814      * then update gcs and pixmap.
815      */
816     if (M_Foreground (current) != M_Foreground (new_m) ||
817         M_Background (current) != M_Background (new_m))
818     {
819        UpdateGCs(w);
820        update = True;
821     }
822
823     if (update)
824     {
825        if (B_ImageName (bg) != NULL)
826        {
827              if (B_Mask(bg) != XmUNSPECIFIED_PIXMAP)
828                 XmDestroyPixmap (XtScreen(bg), B_Mask(bg));
829
830              if (B_Pixmap(bg) != XmUNSPECIFIED_PIXMAP)
831                 XmDestroyPixmap (XtScreen(w), B_Pixmap (bg));
832
833              B_Pixmap (bg) = XmGetPixmap (XtScreen (bg), B_ImageName (bg),
834                                          M_TopShadowColor (new_m),
835                                          M_BottomShadowColor (new_m));
836
837              if (B_Pixmap (bg) != XmUNSPECIFIED_PIXMAP)
838                B_Mask(bg) = (Pixmap)_DtGetMask(XtScreen(bg), B_ImageName(bg));
839
840              return (True);
841        }
842        else
843          return (False);
844     }
845     return (False);
846 }
847
848 /************************************************************************
849  *
850  *  Enter
851  *
852  ************************************************************************/
853
854 static void 
855 Enter(
856         Widget wid,
857         XEvent *event,
858         String *params,
859         Cardinal *num_params )
860 {
861    DtButtonGadget bg = (DtButtonGadget) wid ;
862
863    _XmEnterGadget (wid, (XEvent *)event, (String *)NULL,(Cardinal *)0);
864
865    if (B_Armed (bg))
866       B_Expose (wid, event, NULL);
867 }
868
869
870
871
872 /************************************************************************
873  *
874  *  Leave
875  *
876  ************************************************************************/
877
878 static void 
879 Leave(
880         Widget wid,
881         XEvent *event,
882         String *params,
883         Cardinal *num_params )
884 {
885    DtButtonGadget bg = (DtButtonGadget) wid ;
886
887    _XmLeaveGadget (wid, (XEvent *)event, (String *)NULL,  (Cardinal *)0);
888
889    if (B_Armed (bg))
890    {
891       B_Armed (bg) = False;
892       B_Expose (wid, event, NULL);
893       B_Armed (bg) = True;
894    }
895 }
896
897
898 /*-------------------------------------------------------------
899 **      CallCallback
900 **              Call callback, if any, with reason and event.
901 */
902 static void 
903 CallCallback(
904         DtButtonGadget w,
905         XtCallbackList cb,
906         int reason,
907         XEvent *event )
908 {
909     DtControlCallbackStruct     cb_data;
910
911     if (cb != NULL)
912     {
913        cb_data.reason = reason;
914        cb_data.event = event;
915        cb_data.control_type = XmCONTROL_BUTTON;
916        cb_data.set = False;
917        cb_data.subpanel = B_Subpanel (w);
918        cb_data.push_function = B_PushFunction (w);
919        cb_data.push_argument = B_PushArgument (w);
920        cb_data.file_size = 0;
921        XtCallCallbackList ((Widget) w, cb, &cb_data);
922     }
923 }
924
925
926 /*-------------------------------------------------------------
927 **      DefaultSelectColor
928 **              Resource proc. to determine the default select color.
929 **              (Formerly _XmSelectColorDefault).
930 */
931 static void 
932 DefaultSelectColor(
933         Widget widget,
934         int offset,
935         XrmValue *value )
936 {
937    XmeGetDefaultPixel (widget, XmSELECT, offset, value);
938 }
939
940
941 /************************************************************************
942  *
943  *  DtCreateButtonGadget
944  *      Create an instance of an button and return the widget id.
945  *
946  ************************************************************************/
947
948 Widget 
949 DtCreateButtonGadget(
950         Widget parent,
951         char *name,
952         ArgList arglist,
953         Cardinal argcount )
954 {
955    return (XtCreateWidget (name, dtButtonGadgetClass, 
956                            parent, arglist, argcount));
957 }
958