Core.c revision 249c3046
1/***********************************************************
2Copyright (c) 1993, Oracle and/or its affiliates. All rights reserved.
3
4Permission is hereby granted, free of charge, to any person obtaining a
5copy of this software and associated documentation files (the "Software"),
6to deal in the Software without restriction, including without limitation
7the rights to use, copy, modify, merge, publish, distribute, sublicense,
8and/or sell copies of the Software, and to permit persons to whom the
9Software is furnished to do so, subject to the following conditions:
10
11The above copyright notice and this permission notice (including the next
12paragraph) shall be included in all copies or substantial portions of the
13Software.
14
15THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21DEALINGS IN THE SOFTWARE.
22
23Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts.
24
25                        All Rights Reserved
26
27Permission to use, copy, modify, and distribute this software and its
28documentation for any purpose and without fee is hereby granted,
29provided that the above copyright notice appear in all copies and that
30both that copyright notice and this permission notice appear in
31supporting documentation, and that the name of Digital not be
32used in advertising or publicity pertaining to distribution of the
33software without specific, written prior permission.
34
35DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
36ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
37DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
38ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
39WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
40ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
41SOFTWARE.
42
43******************************************************************/
44
45/*
46
47Copyright 1987, 1988, 1998  The Open Group
48
49Permission to use, copy, modify, distribute, and sell this software and its
50documentation for any purpose is hereby granted without fee, provided that
51the above copyright notice appear in all copies and that both that
52copyright notice and this permission notice appear in supporting
53documentation.
54
55The above copyright notice and this permission notice shall be included in
56all copies or substantial portions of the Software.
57
58THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
59IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
60FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
61OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
62AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
63CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
64
65Except as contained in this notice, the name of The Open Group shall not be
66used in advertising or otherwise to promote the sale, use or other dealings
67in this Software without prior written authorization from The Open Group.
68
69*/
70
71#ifdef HAVE_CONFIG_H
72#include <config.h>
73#endif
74#include "IntrinsicP.h"
75#include "EventI.h"
76#include "ConvertI.h"
77#include "TranslateI.h"
78#include "ResourceI.h"
79#include "RectObj.h"
80#include "RectObjP.h"
81#include "ThreadsI.h"
82#include "StringDefs.h"
83
84/******************************************************************
85 *
86 * CoreWidget Resources
87 *
88 ******************************************************************/
89
90externaldef(xtinherittranslations) int _XtInheritTranslations = 0;
91extern String XtCXtToolkitError; /* from IntrinsicI.h */
92static void XtCopyScreen(Widget, int, XrmValue *);
93
94static XtResource resources[] = {
95    {XtNscreen, XtCScreen, XtRScreen, sizeof(Screen*),
96      XtOffsetOf(CoreRec,core.screen), XtRCallProc, (XtPointer)XtCopyScreen},
97/*_XtCopyFromParent does not work for screen because the Display
98parameter is not passed through to the XtRCallProc routines */
99    {XtNdepth, XtCDepth, XtRInt,sizeof(int),
100         XtOffsetOf(CoreRec,core.depth),
101	 XtRCallProc, (XtPointer)_XtCopyFromParent},
102    {XtNcolormap, XtCColormap, XtRColormap, sizeof(Colormap),
103	 XtOffsetOf(CoreRec,core.colormap),
104	 XtRCallProc,(XtPointer)_XtCopyFromParent},
105    {XtNbackground, XtCBackground, XtRPixel,sizeof(Pixel),
106         XtOffsetOf(CoreRec,core.background_pixel),
107	 XtRString, (XtPointer)"XtDefaultBackground"},
108    {XtNbackgroundPixmap, XtCPixmap, XtRPixmap, sizeof(Pixmap),
109         XtOffsetOf(CoreRec,core.background_pixmap),
110	 XtRImmediate, (XtPointer)XtUnspecifiedPixmap},
111    {XtNborderColor, XtCBorderColor, XtRPixel,sizeof(Pixel),
112         XtOffsetOf(CoreRec,core.border_pixel),
113         XtRString,(XtPointer)"XtDefaultForeground"},
114    {XtNborderPixmap, XtCPixmap, XtRPixmap, sizeof(Pixmap),
115         XtOffsetOf(CoreRec,core.border_pixmap),
116	 XtRImmediate, (XtPointer)XtUnspecifiedPixmap},
117    {XtNmappedWhenManaged, XtCMappedWhenManaged, XtRBoolean, sizeof(Boolean),
118         XtOffsetOf(CoreRec,core.mapped_when_managed),
119	 XtRImmediate, (XtPointer)True},
120    {XtNtranslations, XtCTranslations, XtRTranslationTable,
121        sizeof(XtTranslations), XtOffsetOf(CoreRec,core.tm.translations),
122        XtRTranslationTable, (XtPointer)NULL},
123    {XtNaccelerators, XtCAccelerators, XtRAcceleratorTable,
124        sizeof(XtTranslations), XtOffsetOf(CoreRec,core.accelerators),
125        XtRTranslationTable, (XtPointer)NULL}
126    };
127
128static void CoreInitialize(Widget, Widget, ArgList, Cardinal *);
129static void CoreClassPartInitialize(WidgetClass);
130static void CoreDestroy(Widget);
131static void CoreRealize(Widget, XtValueMask *, XSetWindowAttributes *);
132static Boolean CoreSetValues(Widget, Widget, Widget, ArgList, Cardinal *);
133static void CoreSetValuesAlmost(Widget, Widget, XtWidgetGeometry *, XtWidgetGeometry *);
134
135static RectObjClassRec unNamedObjClassRec = {
136  {
137    /* superclass	  */	(WidgetClass)&rectObjClassRec,
138    /* class_name	  */	"UnNamedObj",
139    /* widget_size	  */	0,
140    /* class_initialize   */    NULL,
141    /* class_part_initialize*/	NULL,
142    /* class_inited       */	FALSE,
143    /* initialize	  */	NULL,
144    /* initialize_hook    */	NULL,
145    /* realize		  */	(XtProc)XtInheritRealize,
146    /* actions		  */	NULL,
147    /* num_actions	  */	0,
148    /* resources	  */	NULL,
149    /* num_resources	  */	0,
150    /* xrm_class	  */	NULLQUARK,
151    /* compress_motion	  */	FALSE,
152    /* compress_exposure  */	FALSE,
153    /* compress_enterleave*/ 	FALSE,
154    /* visible_interest	  */	FALSE,
155    /* destroy		  */	NULL,
156    /* resize		  */	NULL,
157    /* expose		  */	NULL,
158    /* set_values	  */	NULL,
159    /* set_values_hook    */	NULL,
160    /* set_values_almost  */	XtInheritSetValuesAlmost,
161    /* get_values_hook    */	NULL,
162    /* accept_focus	  */	NULL,
163    /* version		  */	XtVersion,
164    /* callback_offsets   */    NULL,
165    /* tm_table           */    NULL,
166    /* query_geometry	    */  NULL,
167    /* display_accelerator  */	NULL,
168    /* extension	    */  NULL
169  }
170};
171
172
173externaldef(widgetclassrec) WidgetClassRec widgetClassRec = {
174{
175    /* superclass         */    (WidgetClass)&unNamedObjClassRec,
176    /* class_name         */    "Core",
177    /* widget_size        */    sizeof(WidgetRec),
178    /* class_initialize   */    NULL,
179    /* class_part_initialize*/  CoreClassPartInitialize,
180    /* class_inited       */    FALSE,
181    /* initialize         */    CoreInitialize,
182    /* initialize_hook    */    NULL,
183    /* realize            */    CoreRealize,
184    /* actions            */    NULL,
185    /* num_actions        */    0,
186    /* resources          */    resources,
187    /* num_resources      */    XtNumber(resources),
188    /* xrm_class          */    NULLQUARK,
189    /* compress_motion    */    FALSE,
190    /* compress_exposure  */    TRUE,
191    /* compress_enterleave*/    FALSE,
192    /* visible_interest   */    FALSE,
193    /* destroy            */    CoreDestroy,
194    /* resize             */    NULL,
195    /* expose             */    NULL,
196    /* set_values         */    CoreSetValues,
197    /* set_values_hook    */    NULL,
198    /* set_values_almost  */    CoreSetValuesAlmost,
199    /* get_values_hook    */    NULL,
200    /* accept_focus       */    NULL,
201    /* version            */    XtVersion,
202    /* callback_offsets   */    NULL,
203    /* tm_table           */    NULL,
204    /* query_geometry       */  NULL,
205    /* display_accelerator  */  NULL,
206    /* extension            */  NULL
207  }
208};
209externaldef (WidgetClass) WidgetClass widgetClass = &widgetClassRec;
210
211externaldef (WidgetClass) WidgetClass coreWidgetClass = &widgetClassRec;
212
213
214/*ARGSUSED*/
215static void XtCopyScreen(
216    Widget      widget,
217    int		offset,
218    XrmValue    *value)
219{
220    value->addr = (XPointer)(&widget->core.screen);
221}
222
223/*
224 * Start of Core methods
225 */
226
227static void CoreClassPartInitialize(
228    register WidgetClass wc)
229{
230    /* We don't need to check for null super since we'll get to object
231       eventually, and it had better define them!  */
232
233    register WidgetClass super = wc->core_class.superclass;
234
235    LOCK_PROCESS;
236    if (wc->core_class.realize == XtInheritRealize) {
237	wc->core_class.realize = super->core_class.realize;
238    }
239
240    if (wc->core_class.accept_focus == XtInheritAcceptFocus) {
241	wc->core_class.accept_focus = super->core_class.accept_focus;
242    }
243
244    if (wc->core_class.display_accelerator == XtInheritDisplayAccelerator) {
245	wc->core_class.display_accelerator =
246		super->core_class.display_accelerator;
247    }
248
249    if (wc->core_class.tm_table == (char *) XtInheritTranslations) {
250	wc->core_class.tm_table =
251		wc->core_class.superclass->core_class.tm_table;
252    } else if (wc->core_class.tm_table != NULL) {
253	wc->core_class.tm_table =
254	      (String)XtParseTranslationTable(wc->core_class.tm_table);
255    }
256
257    if (wc->core_class.actions != NULL) {
258	Boolean inPlace;
259
260	if (wc->core_class.version == XtVersionDontCheck)
261	    inPlace = True;
262	else
263	    inPlace = (wc->core_class.version < XtVersion) ? False : True;
264
265	/* Compile the action table into a more efficient form */
266        wc->core_class.actions = (XtActionList) _XtInitializeActionData(
267	    wc->core_class.actions, wc->core_class.num_actions, inPlace);
268    }
269    UNLOCK_PROCESS;
270}
271/* ARGSUSED */
272static void CoreInitialize(
273    Widget   requested_widget,
274    register Widget new_widget,
275    ArgList args,
276    Cardinal *num_args)
277{
278    XtTranslations save1, save2;
279    new_widget->core.event_table = NULL;
280    new_widget->core.tm.proc_table = NULL;
281    new_widget->core.tm.lastEventTime = 0;
282    /* magic semi-resource fetched by GetResources */
283    save1 = (XtTranslations)new_widget->core.tm.current_state;
284    new_widget->core.tm.current_state = NULL;
285    save2 = new_widget->core.tm.translations;
286    LOCK_PROCESS;
287    new_widget->core.tm.translations =
288	(XtTranslations)new_widget->core.widget_class->core_class.tm_table;
289    UNLOCK_PROCESS;
290    if (save1)
291	_XtMergeTranslations(new_widget, save1, save1->operation);
292    if (save2)
293	_XtMergeTranslations(new_widget, save2, save2->operation);
294}
295
296static void CoreRealize(
297    Widget		 widget,
298    XtValueMask		 *value_mask,
299    XSetWindowAttributes *attributes)
300{
301    XtCreateWindow(widget, (unsigned int) InputOutput,
302	(Visual *) CopyFromParent, *value_mask, attributes);
303} /* CoreRealize */
304
305static void CoreDestroy (
306     Widget    widget)
307{
308    _XtFreeEventTable(&widget->core.event_table);
309    _XtDestroyTMData(widget);
310    XtUnregisterDrawable(XtDisplay(widget), widget->core.window);
311
312    if (widget->core.popup_list != NULL)
313        XtFree((char *)widget->core.popup_list);
314
315} /* CoreDestroy */
316
317/* ARGSUSED */
318static Boolean CoreSetValues(
319    Widget old, Widget reference, Widget new,
320    ArgList args,
321    Cardinal *num_args)
322{
323    Boolean redisplay;
324    Mask    window_mask;
325    XSetWindowAttributes attributes;
326    XtTranslations save;
327
328    redisplay = FALSE;
329    if  (old->core.tm.translations != new->core.tm.translations) {
330	save = new->core.tm.translations;
331	new->core.tm.translations = old->core.tm.translations;
332	_XtMergeTranslations(new, save, XtTableReplace);
333    }
334
335    /* Check everything that depends upon window being realized */
336    if (XtIsRealized(old)) {
337	window_mask = 0;
338	/* Check window attributes */
339	if (old->core.background_pixel != new->core.background_pixel
340	    && new->core.background_pixmap == XtUnspecifiedPixmap) {
341	   attributes.background_pixel  = new->core.background_pixel;
342	   window_mask |= CWBackPixel;
343	   redisplay = TRUE;
344	}
345	if (old->core.background_pixmap != new->core.background_pixmap) {
346	   if (new->core.background_pixmap == XtUnspecifiedPixmap) {
347	       window_mask |= CWBackPixel;
348	       attributes.background_pixel  = new->core.background_pixel;
349	   }
350	   else {
351	       attributes.background_pixmap = new->core.background_pixmap;
352	       window_mask &= ~CWBackPixel;
353	       window_mask |= CWBackPixmap;
354	   }
355	   redisplay = TRUE;
356	}
357	if (old->core.border_pixel != new->core.border_pixel
358	    && new->core.border_pixmap == XtUnspecifiedPixmap) {
359	   attributes.border_pixel  = new->core.border_pixel;
360	   window_mask |= CWBorderPixel;
361       }
362	if (old->core.border_pixmap != new->core.border_pixmap) {
363	   if (new->core.border_pixmap == XtUnspecifiedPixmap) {
364	       window_mask |= CWBorderPixel;
365	       attributes.border_pixel  = new->core.border_pixel;
366	   }
367	   else {
368	       attributes.border_pixmap = new->core.border_pixmap;
369	       window_mask &= ~CWBorderPixel;
370	       window_mask |= CWBorderPixmap;
371	   }
372       }
373	if (old->core.depth != new->core.depth) {
374	   XtAppWarningMsg(XtWidgetToApplicationContext(old),
375		    "invalidDepth","setValues",XtCXtToolkitError,
376               "Can't change widget depth", (String *)NULL, (Cardinal *)NULL);
377	   new->core.depth = old->core.depth;
378	}
379	if (old->core.colormap != new->core.colormap) {
380	    window_mask |= CWColormap;
381	    attributes.colormap = new->core.colormap;
382	}
383	if (window_mask != 0) {
384	    /* Actually change X window attributes */
385	    XChangeWindowAttributes(
386		XtDisplay(new), XtWindow(new), window_mask, &attributes);
387	}
388
389	if (old->core.mapped_when_managed != new->core.mapped_when_managed) {
390	    Boolean mapped_when_managed = new->core.mapped_when_managed;
391	    new->core.mapped_when_managed = !mapped_when_managed;
392	    XtSetMappedWhenManaged(new, mapped_when_managed);
393	}
394    } /* if realized */
395
396    return redisplay;
397} /* CoreSetValues */
398
399/*ARGSUSED*/
400static void CoreSetValuesAlmost(
401    Widget		old,
402    Widget		new,
403    XtWidgetGeometry    *request,
404    XtWidgetGeometry    *reply)
405{
406    *request = *reply;
407}
408