Geometry.c revision 444c061a
1/* $Xorg: Geometry.c,v 1.5 2001/02/09 02:03:54 xorgcvs Exp $ */ 2 3/*********************************************************** 4Copyright 1987, 1988 by Digital Equipment Corporation, Maynard, Massachusetts 5Copyright 1993 by Sun Microsystems, Inc. Mountain View, CA. 6 7 All Rights Reserved 8 9Permission to use, copy, modify, and distribute this software and its 10documentation for any purpose and without fee is hereby granted, 11provided that the above copyright notice appear in all copies and that 12both that copyright notice and this permission notice appear in 13supporting documentation, and that the names of Digital or Sun not be 14used in advertising or publicity pertaining to distribution of the 15software without specific, written prior permission. 16 17DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING 18ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL 19DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR 20ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, 21WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, 22ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS 23SOFTWARE. 24 25SUN DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, 26INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FIT- 27NESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SUN BE LI- 28ABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR 29ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR 30PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR 31OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH 32THE USE OR PERFORMANCE OF THIS SOFTWARE. 33 34******************************************************************/ 35 36/* 37 38Copyright 1987, 1988, 1994, 1998 The Open Group 39 40Permission to use, copy, modify, distribute, and sell this software and its 41documentation for any purpose is hereby granted without fee, provided that 42the above copyright notice appear in all copies and that both that 43copyright notice and this permission notice appear in supporting 44documentation. 45 46The above copyright notice and this permission notice shall be included in 47all copies or substantial portions of the Software. 48 49THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 50IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 51FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 52OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 53AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 54CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 55 56Except as contained in this notice, the name of The Open Group shall not be 57used in advertising or otherwise to promote the sale, use or other dealings 58in this Software without prior written authorization from The Open Group. 59 60*/ 61/* $XFree86: xc/lib/Xt/Geometry.c,v 1.12 2001/12/14 19:56:15 dawes Exp $ */ 62 63#ifdef HAVE_CONFIG_H 64#include <config.h> 65#endif 66#include "IntrinsicI.h" 67#include "ShellP.h" 68#include "ShellI.h" 69 70static void ClearRectObjAreas( 71 RectObj r, 72 XWindowChanges* old) 73{ 74 Widget pw = _XtWindowedAncestor((Widget)r); 75 int bw2; 76 77 bw2 = old->border_width << 1; 78 XClearArea( XtDisplay(pw), XtWindow(pw), 79 old->x, old->y, 80 old->width + bw2, old->height + bw2, 81 TRUE ); 82 83 bw2 = r->rectangle.border_width << 1; 84 XClearArea( XtDisplay(pw), XtWindow(pw), 85 (int)r->rectangle.x, (int)r->rectangle.y, 86 (unsigned int)(r->rectangle.width + bw2), 87 (unsigned int)(r->rectangle.height + bw2), 88 TRUE ); 89} 90 91/* 92 * Internal function used by XtMakeGeometryRequest and XtSetValues. 93 * Returns more data than the public interface. Does not convert 94 * XtGeometryDone to XtGeometryYes. 95 * 96 * clear_rect_obj - *** RETURNED *** 97 * TRUE if the rect obj has been cleared, false otherwise. 98 */ 99 100XtGeometryResult 101_XtMakeGeometryRequest ( 102 Widget widget, 103 XtWidgetGeometry *request, 104 XtWidgetGeometry *reply, 105 Boolean * clear_rect_obj) 106{ 107 XtWidgetGeometry junk; 108 XtGeometryHandler manager = (XtGeometryHandler) NULL; 109 XtGeometryResult returnCode; 110 Widget parent = widget->core.parent; 111 Boolean managed, parentRealized, rgm = False; 112 XtConfigureHookDataRec req; 113 Widget hookobj; 114 115 *clear_rect_obj = FALSE; 116 117 CALLGEOTAT(_XtGeoTrace(widget, 118 "\"%s\" is making a %sgeometry request to its parent \"%s\".\n", 119 XtName(widget), 120 ((request->request_mode & XtCWQueryOnly))? "query only ":"", 121 (XtParent(widget))?XtName(XtParent(widget)):"Root")); 122 CALLGEOTAT(_XtGeoTab(1)); 123 124 if (XtIsShell(widget)) { 125 ShellClassExtension ext; 126 LOCK_PROCESS; 127 for (ext = (ShellClassExtension)((ShellWidgetClass)XtClass(widget)) 128 ->shell_class.extension; 129 ext != NULL && ext->record_type != NULLQUARK; 130 ext = (ShellClassExtension)ext->next_extension); 131 132 if (ext != NULL) { 133 if ( ext->version == XtShellExtensionVersion 134 && ext->record_size == sizeof(ShellClassExtensionRec)) { 135 manager = ext->root_geometry_manager; 136 rgm = True; 137 } else { 138 String params[1]; 139 Cardinal num_params = 1; 140 params[0] = XtClass(widget)->core_class.class_name; 141 XtAppErrorMsg(XtWidgetToApplicationContext(widget), 142 "invalidExtension", "xtMakeGeometryRequest", 143 XtCXtToolkitError, 144 "widget class %s has invalid ShellClassExtension record", 145 params, &num_params); 146 } 147 } else { 148 XtAppErrorMsg(XtWidgetToApplicationContext(widget), 149 "internalError", "xtMakeGeometryRequest", 150 XtCXtToolkitError, 151 "internal error; ShellClassExtension is NULL", 152 NULL, NULL); 153 } 154 managed = True; 155 parentRealized = TRUE; 156 UNLOCK_PROCESS; 157 } else /* not shell */ { 158 if (parent == NULL) 159 XtAppErrorMsg(XtWidgetToApplicationContext(widget), 160 "invalidParent","xtMakeGeometryRequest", 161 XtCXtToolkitError, 162 "non-shell has no parent in XtMakeGeometryRequest", 163 (String *)NULL, (Cardinal *)NULL); 164 165 managed = XtIsManaged(widget); 166 parentRealized = XtIsRealized(parent); 167 if (XtIsComposite(parent)) 168 { 169 LOCK_PROCESS; 170 manager = ((CompositeWidgetClass) (parent->core.widget_class)) 171 ->composite_class.geometry_manager; 172 UNLOCK_PROCESS; 173 } 174 } 175 176#if 0 177 /* 178 * The Xt spec says that these conditions must generate 179 * error messages (not warnings), but many Xt applications 180 * and toolkits (including parts of Xaw, Motif and Netscape) 181 * depend on the previous Xt behaviour. Thus, these tests 182 * should probably remain disabled. 183 */ 184 if (parentRealized && managed) { 185 if (parent && !XtIsComposite(parent)) 186 { 187 /* 188 * This shouldn't ever happen, we only test for this to pass 189 * VSW5. Normally managing the widget will catch this, but VSW5 190 * does some really screwy stuff to get here. 191 */ 192 XtAppErrorMsg(XtWidgetToApplicationContext(widget), 193 "invalidParent", "xtMakeGeometryRequest", 194 XtCXtToolkitError, 195 "XtMakeGeometryRequest - parent not composite", 196 (String *)NULL, (Cardinal *)NULL); 197 } 198 else if (manager == (XtGeometryHandler) NULL) 199 { 200 XtAppErrorMsg(XtWidgetToApplicationContext(widget), 201 "invalidGeometryManager","xtMakeGeometryRequest", 202 XtCXtToolkitError, 203 "XtMakeGeometryRequest - parent has no geometry manager", 204 (String *)NULL, (Cardinal *)NULL); 205 } 206 } 207#else 208 if (!manager) 209 managed = False; 210#endif 211 212 if (widget->core.being_destroyed) { 213 CALLGEOTAT(_XtGeoTab(-1)); 214 CALLGEOTAT(_XtGeoTrace(widget, 215 "It is being destroyed, just return XtGeometryNo.\n")); 216 return XtGeometryNo; 217 } 218 219 /* see if requesting anything to change */ 220 req.changeMask = 0; 221 if (request->request_mode & CWStackMode 222 && request->stack_mode != XtSMDontChange) { 223 req.changeMask |= CWStackMode; 224 CALLGEOTAT(_XtGeoTrace(widget, 225 "Asking for a change in StackMode!\n")); 226 if (request->request_mode & CWSibling) { 227 XtCheckSubclass(request->sibling, rectObjClass, 228 "XtMakeGeometryRequest"); 229 req.changeMask |= CWSibling; 230 } 231 } 232 if (request->request_mode & CWX 233 && widget->core.x != request->x) { 234 CALLGEOTAT(_XtGeoTrace(widget, 235 "Asking for a change in x: from %d to %d.\n", 236 widget->core.x, request->x)); 237 req.changeMask |= CWX; 238 } 239 if (request->request_mode & CWY 240 && widget->core.y != request->y) { 241 CALLGEOTAT(_XtGeoTrace(widget, 242 "Asking for a change in y: from %d to %d.\n", 243 widget->core.y, request->y)); 244 req.changeMask |= CWY; 245 } 246 if (request->request_mode & CWWidth 247 && widget->core.width != request->width) { 248 CALLGEOTAT(_XtGeoTrace(widget,"Asking for a change in width: from %d to %d.\n", 249 widget->core.width, request->width)); 250 req.changeMask |= CWWidth; 251 } 252 if (request->request_mode & CWHeight 253 && widget->core.height != request->height) { 254 CALLGEOTAT(_XtGeoTrace(widget, 255 "Asking for a change in height: from %d to %d.\n", 256 widget->core.height, request->height)); 257 req.changeMask |= CWHeight; 258 } 259 if (request->request_mode & CWBorderWidth 260 && widget->core.border_width != request->border_width){ 261 CALLGEOTAT(_XtGeoTrace(widget, 262 "Asking for a change in border_width: from %d to %d.\n", 263 widget->core.border_width, request->border_width)); 264 req.changeMask |= CWBorderWidth; 265 } 266 if (! req.changeMask) { 267 CALLGEOTAT(_XtGeoTrace(widget, 268 "Asking for nothing new,\n")); 269 CALLGEOTAT(_XtGeoTab(-1)); 270 CALLGEOTAT(_XtGeoTrace(widget, 271 "just return XtGeometryYes.\n")); 272 return XtGeometryYes; 273 } 274 req.changeMask |= (request->request_mode & XtCWQueryOnly); 275 276 if ( !(req.changeMask & XtCWQueryOnly) && XtIsRealized(widget) ) { 277 /* keep record of the current geometry so we know what's changed */ 278 req.changes.x = widget->core.x ; 279 req.changes.y = widget->core.y ; 280 req.changes.width = widget->core.width ; 281 req.changes.height = widget->core.height ; 282 req.changes.border_width = widget->core.border_width ; 283 } 284 285 if (!managed || !parentRealized) { 286 CALLGEOTAT(_XtGeoTrace(widget, 287 "Not Managed or Parent not realized.\n")); 288 /* Don't get parent's manager involved--assume the answer is yes */ 289 if (req.changeMask & XtCWQueryOnly) { 290 /* He was just asking, don't change anything, just tell him yes */ 291 CALLGEOTAT(_XtGeoTrace(widget,"QueryOnly request\n")); 292 CALLGEOTAT(_XtGeoTab(-1)); 293 CALLGEOTAT(_XtGeoTrace(widget,"just return XtGeometryYes.\n")); 294 return XtGeometryYes; 295 } else { 296 CALLGEOTAT(_XtGeoTrace(widget, 297 "Copy values from request to widget.\n")); 298 /* copy values from request to widget */ 299 if (request->request_mode & CWX) 300 widget->core.x = request->x; 301 if (request->request_mode & CWY) 302 widget->core.y = request->y; 303 if (request->request_mode & CWWidth) 304 widget->core.width = request->width; 305 if (request->request_mode & CWHeight) 306 widget->core.height = request->height; 307 if (request->request_mode & CWBorderWidth) 308 widget->core.border_width = request->border_width; 309 if (!parentRealized) { 310 CALLGEOTAT(_XtGeoTab(-1)); 311 CALLGEOTAT(_XtGeoTrace(widget,"and return XtGeometryYes.\n")); 312 return XtGeometryYes; 313 } 314 else returnCode = XtGeometryYes; 315 } 316 } else { 317 /* go ask the widget's geometry manager */ 318 CALLGEOTAT(_XtGeoTrace(widget, 319 "Go ask the parent geometry manager.\n")); 320 if (reply == (XtWidgetGeometry *) NULL) { 321 returnCode = (*manager)(widget, request, &junk); 322 } else { 323 returnCode = (*manager)(widget, request, reply); 324 } 325 } 326 327 /* 328 * If Unrealized, not a XtGeometryYes, or a query-only then we are done. 329 */ 330 331 if ((returnCode != XtGeometryYes) || 332 (req.changeMask & XtCWQueryOnly) || !XtIsRealized(widget)) { 333 334#ifdef XT_GEO_TATTLER 335 switch(returnCode){ 336 case XtGeometryNo: 337 CALLGEOTAT(_XtGeoTab(-1)); 338 CALLGEOTAT(_XtGeoTrace(widget,"\"%s\" returns XtGeometryNo.\n", 339 (XtParent(widget))?XtName(XtParent(widget)):"Root")); 340 /* check for no change */ 341 break ; 342 case XtGeometryDone: 343 CALLGEOTAT(_XtGeoTab(-1)); 344 CALLGEOTAT(_XtGeoTrace(widget,"\"%s\" returns XtGeometryDone.\n", 345 (XtParent(widget))?XtName(XtParent(widget)):"Root")); 346 /* check for no change in queryonly */ 347 break ; 348 case XtGeometryAlmost: 349 CALLGEOTAT(_XtGeoTab(-1)); 350 CALLGEOTAT(_XtGeoTrace(widget,"\"%s\" returns XtGeometryAlmost.\n", 351 (XtParent(widget))?XtName(XtParent(widget)):"Root")); 352 CALLGEOTAT(_XtGeoTab(1)); 353 CALLGEOTAT(_XtGeoTrace(widget,"Proposal: width %d height %d.\n", 354 (reply)?reply->width:junk.width, 355 (reply)?reply->height:junk.height)); 356 CALLGEOTAT(_XtGeoTab(-1)); 357 358 /* check for no change */ 359 break ; 360 case XtGeometryYes: 361 if (req.changeMask & XtCWQueryOnly) { 362 CALLGEOTAT(_XtGeoTrace(widget, 363 "QueryOnly specified, no configuration.\n")); 364 } 365 if (!XtIsRealized(widget)) { 366 CALLGEOTAT(_XtGeoTrace(widget, 367 "\"%s\" not realized, no configuration.\n", 368 XtName(widget))); 369 } 370 CALLGEOTAT(_XtGeoTab(-1)); 371 CALLGEOTAT(_XtGeoTrace(widget,"\"%s\" returns XtGeometryYes.\n", 372 (XtParent(widget))?XtName(XtParent(widget)):"Root")); 373 break ; 374 } 375#endif 376 return returnCode; 377 } 378 379 CALLGEOTAT(_XtGeoTab(-1)); 380 CALLGEOTAT(_XtGeoTrace(widget,"\"%s\" returns XtGeometryYes.\n", 381 (XtParent(widget))?XtName(XtParent(widget)):"Root")); 382 383 if (XtIsWidget(widget)) { /* reconfigure the window (if needed) */ 384 385 if (rgm) return returnCode; 386 387 if (req.changes.x != widget->core.x) { 388 req.changeMask |= CWX; 389 req.changes.x = widget->core.x; 390 CALLGEOTAT(_XtGeoTrace(widget, 391 "x changing to %d\n",widget->core.x)); 392 } 393 if (req.changes.y != widget->core.y) { 394 req.changeMask |= CWY; 395 req.changes.y = widget->core.y; 396 CALLGEOTAT(_XtGeoTrace(widget, 397 "y changing to %d\n",widget->core.y)); 398 } 399 if (req.changes.width != widget->core.width) { 400 req.changeMask |= CWWidth; 401 req.changes.width = widget->core.width; 402 CALLGEOTAT(_XtGeoTrace(widget, 403 "width changing to %d\n",widget->core.width)); 404 } 405 if (req.changes.height != widget->core.height) { 406 req.changeMask |= CWHeight; 407 req.changes.height = widget->core.height; 408 CALLGEOTAT(_XtGeoTrace(widget, 409 "height changing to %d\n",widget->core.height)); 410 } 411 if (req.changes.border_width != widget->core.border_width) { 412 req.changeMask |= CWBorderWidth; 413 req.changes.border_width = widget->core.border_width; 414 CALLGEOTAT(_XtGeoTrace(widget, 415 "border_width changing to %d\n", 416 widget->core.border_width)); 417 } 418 if (req.changeMask & CWStackMode) { 419 req.changes.stack_mode = request->stack_mode; 420 CALLGEOTAT(_XtGeoTrace(widget,"stack_mode changing\n")); 421 if (req.changeMask & CWSibling) { 422 if (XtIsWidget(request->sibling)) 423 req.changes.sibling = XtWindow(request->sibling); 424 else 425 req.changeMask &= ~(CWStackMode | CWSibling); 426 } 427 } 428 429#ifdef XT_GEO_TATTLER 430 if (req.changeMask) { 431 CALLGEOTAT(_XtGeoTrace(widget, 432 "XConfigure \"%s\"'s window.\n", 433 XtName(widget))); 434 } else { 435 CALLGEOTAT(_XtGeoTrace(widget, 436 "No window configuration needed for \"%s\".\n", 437 XtName(widget))); 438 } 439#endif 440 441 XConfigureWindow(XtDisplay(widget), XtWindow(widget), 442 req.changeMask, &req.changes); 443 } 444 else { /* RectObj child of realized Widget */ 445 *clear_rect_obj = TRUE; 446 CALLGEOTAT(_XtGeoTrace(widget, 447 "ClearRectObj on \"%s\".\n",XtName(widget))); 448 449 ClearRectObjAreas((RectObj)widget, &req.changes); 450 } 451 hookobj = XtHooksOfDisplay(XtDisplayOfObject(widget));; 452 if (XtHasCallbacks(hookobj, XtNconfigureHook) == XtCallbackHasSome) { 453 req.type = XtHconfigure; 454 req.widget = widget; 455 XtCallCallbackList(hookobj, 456 ((HookObject)hookobj)->hooks.confighook_callbacks, 457 (XtPointer)&req); 458 } 459 460 return returnCode; 461} /* _XtMakeGeometryRequest */ 462 463 464/* Public routines */ 465 466XtGeometryResult XtMakeGeometryRequest ( 467 Widget widget, 468 XtWidgetGeometry *request, 469 XtWidgetGeometry *reply) 470{ 471 Boolean junk; 472 XtGeometryResult r; 473 XtGeometryHookDataRec call_data; 474 Widget hookobj = XtHooksOfDisplay(XtDisplayOfObject(widget)); 475 WIDGET_TO_APPCON(widget); 476 477 LOCK_APP(app); 478 if (XtHasCallbacks(hookobj, XtNgeometryHook) == XtCallbackHasSome) { 479 call_data.type = XtHpreGeometry; 480 call_data.widget = widget; 481 call_data.request = request; 482 XtCallCallbackList(hookobj, 483 ((HookObject)hookobj)->hooks.geometryhook_callbacks, 484 (XtPointer)&call_data); 485 call_data.result = r = 486 _XtMakeGeometryRequest(widget, request, reply, &junk); 487 call_data.type = XtHpostGeometry; 488 call_data.reply = reply; 489 XtCallCallbackList(hookobj, 490 ((HookObject)hookobj)->hooks.geometryhook_callbacks, 491 (XtPointer)&call_data); 492 } else { 493 r = _XtMakeGeometryRequest(widget, request, reply, &junk); 494 } 495 UNLOCK_APP(app); 496 497 return ((r == XtGeometryDone) ? XtGeometryYes : r); 498} 499 500XtGeometryResult 501XtMakeResizeRequest( 502 Widget widget, 503 _XtDimension width, 504 _XtDimension height, 505 Dimension *replyWidth, 506 Dimension *replyHeight) 507{ 508 XtWidgetGeometry request, reply; 509 XtGeometryResult r; 510 XtGeometryHookDataRec call_data; 511 Boolean junk; 512 Widget hookobj = XtHooksOfDisplay(XtDisplayOfObject(widget)); 513 WIDGET_TO_APPCON(widget); 514 515 LOCK_APP(app); 516 request.request_mode = CWWidth | CWHeight; 517 request.width = width; 518 request.height = height; 519 520 if (XtHasCallbacks(hookobj, XtNgeometryHook) == XtCallbackHasSome) { 521 call_data.type = XtHpreGeometry; 522 call_data.widget = widget; 523 call_data.request = &request; 524 XtCallCallbackList(hookobj, 525 ((HookObject)hookobj)->hooks.geometryhook_callbacks, 526 (XtPointer)&call_data); 527 call_data.result = r = 528 _XtMakeGeometryRequest(widget, &request, &reply, &junk); 529 call_data.type = XtHpostGeometry; 530 call_data.reply = &reply; 531 XtCallCallbackList(hookobj, 532 ((HookObject)hookobj)->hooks.geometryhook_callbacks, 533 (XtPointer)&call_data); 534 } else { 535 r = _XtMakeGeometryRequest(widget, &request, &reply, &junk); 536 } 537 if (replyWidth != NULL) { 538 if (r == XtGeometryAlmost && reply.request_mode & CWWidth) 539 *replyWidth = reply.width; 540 else 541 *replyWidth = width; 542 } 543 if (replyHeight != NULL) { 544 if (r == XtGeometryAlmost && reply.request_mode & CWHeight) 545 *replyHeight = reply.height; 546 else 547 *replyHeight = height; 548 } 549 UNLOCK_APP(app); 550 return ((r == XtGeometryDone) ? XtGeometryYes : r); 551} /* XtMakeResizeRequest */ 552 553void XtResizeWindow( 554 Widget w) 555{ 556 XtConfigureHookDataRec req; 557 Widget hookobj; 558 WIDGET_TO_APPCON(w); 559 560 LOCK_APP(app); 561 if (XtIsRealized(w)) { 562 req.changes.width = w->core.width; 563 req.changes.height = w->core.height; 564 req.changes.border_width = w->core.border_width; 565 req.changeMask = CWWidth | CWHeight | CWBorderWidth; 566 XConfigureWindow(XtDisplay(w), XtWindow(w), 567 (unsigned) req.changeMask, &req.changes); 568 hookobj = XtHooksOfDisplay(XtDisplayOfObject(w));; 569 if (XtHasCallbacks(hookobj, XtNconfigureHook) == XtCallbackHasSome) { 570 req.type = XtHconfigure; 571 req.widget = w; 572 XtCallCallbackList(hookobj, 573 ((HookObject)hookobj)->hooks.confighook_callbacks, 574 (XtPointer)&req); 575 } 576 } 577 UNLOCK_APP(app); 578} /* XtResizeWindow */ 579 580void XtResizeWidget( 581 Widget w, 582 _XtDimension width, 583 _XtDimension height, 584 _XtDimension borderWidth) 585{ 586 XtConfigureWidget(w, w->core.x, w->core.y, width, height, borderWidth); 587} /* XtResizeWidget */ 588 589void XtConfigureWidget( 590 Widget w, 591 _XtPosition x, 592 _XtPosition y, 593 _XtDimension width, 594 _XtDimension height, 595 _XtDimension borderWidth) 596{ 597 XtConfigureHookDataRec req; 598 Widget hookobj; 599 XWindowChanges old; 600 WIDGET_TO_APPCON(w); 601 602 CALLGEOTAT(_XtGeoTrace(w, 603 "\"%s\" is being configured by its parent \"%s\"\n", 604 XtName(w), 605 (XtParent(w))?XtName(XtParent(w)):"Root")); 606 CALLGEOTAT(_XtGeoTab(1)); 607 608 LOCK_APP(app); 609 req.changeMask = 0; 610 if ((old.x = w->core.x) != x) { 611 CALLGEOTAT(_XtGeoTrace(w,"x move from %d to %d\n",w->core.x, x)); 612 req.changes.x = w->core.x = x; 613 req.changeMask |= CWX; 614 } 615 616 if ((old.y = w->core.y) != y) { 617 CALLGEOTAT(_XtGeoTrace(w,"y move from %d to %d\n",w->core.y, y)); 618 req.changes.y = w->core.y = y; 619 req.changeMask |= CWY; 620 } 621 622 if ((old.width = w->core.width) != width) { 623 CALLGEOTAT(_XtGeoTrace(w, 624 "width move from %d to %d\n",w->core.width, width)); 625 req.changes.width = w->core.width = width; 626 req.changeMask |= CWWidth; 627 } 628 629 if ((old.height = w->core.height) != height) { 630 CALLGEOTAT(_XtGeoTrace(w, 631 "height move from %d to %d\n",w->core.height, height)); 632 req.changes.height = w->core.height = height; 633 req.changeMask |= CWHeight; 634 } 635 636 if ((old.border_width = w->core.border_width) != borderWidth) { 637 CALLGEOTAT(_XtGeoTrace(w,"border_width move from %d to %d\n", 638 w->core.border_width,borderWidth )); 639 req.changes.border_width = w->core.border_width = borderWidth; 640 req.changeMask |= CWBorderWidth; 641 } 642 643 if (req.changeMask != 0) { 644 if (XtIsRealized(w)) { 645 if (XtIsWidget(w)) { 646 CALLGEOTAT(_XtGeoTrace(w, 647 "XConfigure \"%s\"'s window\n",XtName(w))); 648 XConfigureWindow(XtDisplay(w), XtWindow(w), 649 req.changeMask, &req.changes); 650 } else { 651 CALLGEOTAT(_XtGeoTrace(w, 652 "ClearRectObj called on \"%s\"\n",XtName(w))); 653 ClearRectObjAreas((RectObj)w, &old); 654 } 655 } 656 hookobj = XtHooksOfDisplay(XtDisplayOfObject(w));; 657 if (XtHasCallbacks(hookobj, XtNconfigureHook) == XtCallbackHasSome) { 658 req.type = XtHconfigure; 659 req.widget = w; 660 XtCallCallbackList(hookobj, 661 ((HookObject)hookobj)->hooks.confighook_callbacks, 662 (XtPointer)&req); 663 } 664 { 665 XtWidgetProc resize; 666 667 LOCK_PROCESS; 668 resize = XtClass(w)->core_class.resize; 669 UNLOCK_PROCESS; 670 if ((req.changeMask & (CWWidth | CWHeight)) && 671 resize != (XtWidgetProc) NULL) { 672 CALLGEOTAT(_XtGeoTrace(w,"Resize proc is called.\n")); 673 (*resize)(w); 674 } 675 } 676 } else { 677 CALLGEOTAT(_XtGeoTrace(w,"No change in configuration\n")); 678 } 679 680 CALLGEOTAT(_XtGeoTab(-1)); 681 UNLOCK_APP(app); 682} /* XtConfigureWidget */ 683 684void XtMoveWidget( 685 Widget w, 686 _XtPosition x, 687 _XtPosition y) 688{ 689 XtConfigureWidget(w, x, y, w->core.width, w->core.height, 690 w->core.border_width); 691} /* XtMoveWidget */ 692 693void XtTranslateCoords( 694 register Widget w, 695 _XtPosition x, 696 _XtPosition y, 697 register Position *rootx, /* return */ 698 register Position *rooty) /* return */ 699{ 700 Position garbagex, garbagey; 701 XtAppContext app = XtWidgetToApplicationContext(w); 702 703 LOCK_APP(app); 704 if (rootx == NULL) rootx = &garbagex; 705 if (rooty == NULL) rooty = &garbagey; 706 707 *rootx = x; 708 *rooty = y; 709 710 for (; w != NULL && ! XtIsShell(w); w = w->core.parent) { 711 *rootx += w->core.x + w->core.border_width; 712 *rooty += w->core.y + w->core.border_width; 713 } 714 715 if (w == NULL) 716 XtAppWarningMsg(app, 717 "invalidShell","xtTranslateCoords",XtCXtToolkitError, 718 "Widget has no shell ancestor", 719 (String *)NULL, (Cardinal *)NULL); 720 else { 721 Position x, y; 722 _XtShellGetCoordinates( w, &x, &y ); 723 *rootx += x + w->core.border_width; 724 *rooty += y + w->core.border_width; 725 } 726 UNLOCK_APP(app); 727} 728 729XtGeometryResult XtQueryGeometry( 730 Widget widget, 731 register XtWidgetGeometry *intended, /* parent's changes; may be NULL */ 732 XtWidgetGeometry *reply) /* child's preferred geometry; never NULL */ 733{ 734 XtWidgetGeometry null_intended; 735 XtGeometryHandler query; 736 XtGeometryResult result; 737 WIDGET_TO_APPCON(widget); 738 739 CALLGEOTAT(_XtGeoTrace(widget, 740 "\"%s\" is asking its preferred geometry to \"%s\".\n", 741 (XtParent(widget))?XtName(XtParent(widget)):"Root", 742 XtName(widget))); 743 CALLGEOTAT(_XtGeoTab(1)); 744 745 LOCK_APP(app); 746 LOCK_PROCESS; 747 query = XtClass(widget)->core_class.query_geometry; 748 UNLOCK_PROCESS; 749 reply->request_mode = 0; 750 if (query != NULL) { 751 if (intended == NULL) { 752 null_intended.request_mode = 0; 753 intended = &null_intended; 754#ifdef XT_GEO_TATTLER 755 CALLGEOTAT(_XtGeoTrace(widget,"without any constraint.\n")); 756 } else { 757 CALLGEOTAT(_XtGeoTrace(widget, 758 "with the following constraints:\n")); 759 760 if (intended->request_mode & CWX) { 761 CALLGEOTAT(_XtGeoTrace(widget," x = %d\n",intended->x)); 762 } 763 if (intended->request_mode & CWY) { 764 CALLGEOTAT(_XtGeoTrace(widget," y = %d\n",intended->y)); 765 } 766 if (intended->request_mode & CWWidth) { 767 CALLGEOTAT(_XtGeoTrace(widget, 768 " width = %d\n",intended->width)); 769 } 770 if (intended->request_mode & CWHeight) { 771 CALLGEOTAT(_XtGeoTrace(widget, 772 " height = %d\n",intended->height)); 773 } 774 if (intended->request_mode & CWBorderWidth) { 775 CALLGEOTAT(_XtGeoTrace(widget, 776 " border_width = %d\n",intended->border_width)); 777 } 778#endif 779 } 780 781 result = (*query) (widget, intended, reply); 782 } 783 else { 784 CALLGEOTAT(_XtGeoTrace(widget,"\"%s\" has no QueryGeometry proc, return the current state\n",XtName(widget))); 785 786 result = XtGeometryYes; 787 } 788 789#ifdef XT_GEO_TATTLER 790#define FillIn(mask, field) \ 791 if (!(reply->request_mode & mask)) {\ 792 reply->field = widget->core.field;\ 793 _XtGeoTrace(widget," using core %s = %d.\n","field",\ 794 widget->core.field);\ 795 } else {\ 796 _XtGeoTrace(widget," replied %s = %d\n","field",\ 797 reply->field);\ 798 } 799#else 800#define FillIn(mask, field) \ 801 if (!(reply->request_mode & mask)) reply->field = widget->core.field; 802#endif 803 804 FillIn(CWX, x); 805 FillIn(CWY, y); 806 FillIn(CWWidth, width); 807 FillIn(CWHeight, height); 808 FillIn(CWBorderWidth, border_width); 809 810 CALLGEOTAT(_XtGeoTab(-1)); 811#undef FillIn 812 813 if (!(reply->request_mode & CWStackMode)) 814 reply->stack_mode = XtSMDontChange; 815 UNLOCK_APP(app); 816 return result; 817} 818