Bug 18567 - Xaw: relayout of Form widget when a child resizes is broken
Xaw: relayout of Form widget when a child resizes is broken
Product: Red Hat Linux
Classification: Retired
Component: XFree86 (Show other bugs)
i386 Linux
medium Severity medium
: ---
: ---
Assigned To: Mike A. Harris
David Lawrence
Depends On:
  Show dependency treegraph
Reported: 2000-10-06 16:18 EDT by Tim Mann
Modified: 2007-04-18 12:29 EDT (History)
0 users

See Also:
Fixed In Version:
Doc Type: Bug Fix
Doc Text:
Story Points: ---
Clone Of:
Last Closed: 2002-11-03 02:55:10 EST
Type: ---
Regression: ---
Mount Type: ---
Documentation: ---
Verified Versions:
Category: ---
oVirt Team: ---
RHEL 7.3 requirements from Atomic Host:
Cloudforms Team: ---

Attachments (Terms of Use)

  None (edit)
Description Tim Mann 2000-10-06 16:18:12 EDT
This bug is submitted for your information only.  I've also sent the bug
report directly to xbugs@opengroup.org and xfree86@xfree86.org, so
hopefully one of those groups will be fixing it.

To: xbugs@opengroup.org
cc: XFree86@XFree86.org
Subject: Xaw: relayout of Form widget when a child resizes is broken

R6.4, public-patch-3
XFree86 4.0.1


Red Hat Linux 7.0, kernel 2.2.16
(but this doesn't matter to the bug)


(but this doesn't matter to the bug; also seen on other displays)


GNOME with Sawfish window manager
(but this doesn't matter to the bug)


gcc version 2.96 20000731 (Red Hat Linux 7.0)




Relayout of Form widget when a child resizes is broken


When a child of a Form widget is resized by the user program after the 
Form widget has been realized, relayout of the form is not done properly.
In the case I've seen, the children do not move.  This bug was not present
in earlier versions of Xaw; they repositioned the children correctly.

Looking at the code and comparing it with an older version, the Form widget 
is going through the motions of trying to do the relayout, but an extra 
layer of code has been added that does not work properly and keeps the 
relayout from actually changing the layout as it should.  It seems that 
layout now uses something called the "virtual" width and height of the 
child widgets to compute the layout instead of looking inside the child 
widgets for their actual width and height.  I don't understand what is 
supposed to be accomplished by doing that -- it can't be an optimization 
to avoid communicating with the server, since the actual width and height 
are already in local fields.  What it does do is break the relayout
because the virtual width and height are not updated to match the real 
width and height.

In particular, if a child resizes, the sequence of events is (1) the child 
resizes itself, (2) the Form's geometry manager is called, (3) the geometry 
manager redoes the form layout using the virtual sizes of the children, 
which DO NOT reflect the new size of the child that just changed, (4) 
the geometry manager MIGHT update the virtual size of the child.  In step 
(3), obviously the layout will be wrong because the outdated size is used. 
In step (4) there is an additional bug, because the virtual size is updated 
only if XawFormDoLayout(w, False) had been called earlier to put the form 
into deferred layout mode.

Perhaps the virtual stuff is some kind of optimization for the case where
the form itself is resized and it must then resize its children.  But it
completely breaks the case where a child is resized by the user program
and the form needs relayout.


Below is a program that demonstrates the problem.  If you run it with 
the argument "0", it draws a Form widget with three children and does 
not attempt to resize any of them.  If you run it with the argument "1", 
it will widen the child marked "Label 1".  Under older versions of Xaw, 
this causes Label 2 to move to the right to get out of the way.  Under 
the current version, Label 2 does not move, because the Layout procedure 
uses the old size of Label 1 (the incorrect "virtual" size) to compute 
the new layout.  Thus Label 1 ends up overlapping Label 2.  You can also 
run the program with the argument "3", which calls XawFormDoLayout(w, 
FALSE) before the resize and XawFormDoLayout(2, TRUE) after.  This does 
not change the result on the screen, but does cause the code to go down 
a somewhat different path.

Another way to reproduce the problem is to run any version of xboard from
3.0.0 to 4.1.0.  (See http://www.tim-mann.org for source code.)  The button
bar [<< < P > >>] ends up on top of the message widget instead of moving
to the far right of the window as it should.  xboard lays out its window
by first making the message widget small, then realizing all the widgets,
then looking to see how much extra space there is and enlarging the message
widget to fill it.  This has worked fine for years but is now broken with
the current Xaw.

=============cut here=================

#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include <X11/Shell.h>
#include <X11/Xaw/Form.h>
#include <X11/Xaw/Label.h>
#include <stdio.h>

XtAppContext appContext;
Widget shellWidget, formWidget, labelWidget[3];

main(int argc, char **argv)
  int i;
  Arg args[16];
  Dimension w, h, wr, hr;
  XtGeometryResult gres;
  int arg = 1;
  Position x, y;

  shellWidget = XtAppInitialize(&appContext, "XawBug", NULL, 0,
				&argc, argv, NULL, NULL, 0);

  if (argc > 1) arg = atoi(argv[1]);

  formWidget =
    XtCreateManagedWidget("form", formWidgetClass, shellWidget, NULL, 0);

  labelWidget[0] =
    XtCreateWidget("label0", labelWidgetClass, formWidget, NULL, 0);
  labelWidget[1] =
    XtCreateWidget("label1", labelWidgetClass, formWidget, NULL, 0);
  labelWidget[2] =
    XtCreateWidget("label2", labelWidgetClass, formWidget, NULL, 0);

  XtManageChildren(labelWidget, sizeof(labelWidget)/sizeof(Widget));

  i = 0;
  XtSetArg(args[i], XtNlabel,
	   "This is a long label to make the form wide"); i++;
  XtSetValues(labelWidget[0], args, i);

  i = 0;
  XtSetArg(args[i], XtNresizable, True); i++;
  XtSetArg(args[i], XtNlabel, "Label 1"); i++;
  XtSetArg(args[i], XtNfromVert, labelWidget[0]); i++;
  XtSetValues(labelWidget[1], args, i);

  i = 0;
  XtSetArg(args[i], XtNlabel, "Label 2"); i++;
  XtSetArg(args[i], XtNfromVert, labelWidget[0]); i++;
  XtSetArg(args[i], XtNfromHoriz, labelWidget[1]); i++;
  XtSetValues(labelWidget[2], args, i);

  if (arg & 2) {
    XawFormDoLayout(formWidget, False);

  if (arg & 1) {

    i = 0;
    XtSetArg(args[i], XtNwidth, &w);  i++;
    XtSetArg(args[i], XtNheight, &h);  i++;
    XtGetValues(labelWidget[1], args, i);

    w += 40;

    gres = XtMakeResizeRequest(labelWidget[1], w, h, &wr, &hr);
    if (gres != XtGeometryYes) {
      fprintf(stderr, "resize geometry error %d %d %d %d %d\n",
	      gres, w, h, wr, hr);


  if (arg & 2) {
    XawFormDoLayout(formWidget, True);

  return 0;

=============cut here=================


I'm sorry, but I don't understand what the virtual stuff is supposed to 
do, so I don't know the proper fix.  You can definitely fix this bug by 
going back to the old version of Xaw that was used in XFree86 3.3.6.  

The identifying lines from the OLD, WORKING version are:
/* $XConsortium: Form.c,v 1.52 94/04/17 20:12:06 kaleb Exp $ */
/* $XFree86: xc/lib/Xaw/Form.c,v 1998/05/16 09:05:19 dawes Exp
$ */

The identifying lines from the NEW, BROKEN version are:
/* $TOG: Form.c /main/54 1998/05/14 14:55:45 kaleb $ */
/* $XFree86: xc/lib/Xaw/Form.c,v 1.16 1999/11/19 13:53:26 hohndel Exp $ */


This is totally irrelevant, but the XFree86 FAQ says to include it in but
reports, so here it is.  Apparently I have an XFree86 3.3.6 server, but
nevertheless the bug I'm reporting is in the XFree86 4.0.1 libraries. 
It's independent of the server that's running.

XFree86 Version 3.3.6 / X Window System
(protocol Version 11, revision 0, vendor release 6300)
Release Date: January 8 2000
	If the server is older than 6-12 months, or if your card is newer
	than the above date, look for a newer version before reporting
	problems.  (see http://www.XFree86.Org/FAQ)
Operating System: Linux 2.2.5-22smp i686 [ELF] 
Configured drivers:
  Mach64: accelerated server for ATI Mach64 graphics adaptors (Patchlevel
(using VT number 8)

XF86Config: /usr/X11R6/lib/X11/XF86Config
(**) stands for supplied, (--) stands for probed/default values
(**) XKB: rules: "xfree86"
(**) XKB: model: "pc101"
(**) XKB: layout: "us"
(**) Mouse: type: PS/2, device: /dev/mouse, buttons: 3
(**) Mach64: Graphics device ID: "Primary Card"
(**) Mach64: Monitor ID: "Primary Monitor"
(**) FontPath set to "unix/:7100"
(--) Mach64: PCI: Mach64 RagePro rev 92, Aperture @ 0x41000000, Registers @
0x40000000, Block I/O @ 0x1000
(--) Mach64: PCI (92) and CONFIG_CHIP_ID (124) don't agree on ChipRev,
	using PCI value
(--) Mach64: Card type: AGP
(--) Mach64: Memory type: SGRAM (1:1) (5)
(--) Mach64: Clock type: Internal
(--) Mach64: Maximum allowed dot-clock: 230.000 MHz
(**) Mach64: Mode "1600x1200": mode clock = 162.000
(--) Mach64: Too little memory for mode "1600x1200"
(--) Mach64: Removing mode "1600x1200" from list of valid modes.
(**) Mach64: Mode "1280x1024": mode clock = 135.000
(**) Mach64: Mode "1152x864": mode clock = 135.000
(**) Mach64: Mode "1024x768": mode clock = 115.500
(**) Mach64: Mode "800x600": mode clock =  69.650
(**) Mach64: Mode "640x480": mode clock =  45.800
(--) Mach64: Virtual resolution: 1280x1024
(--) Mach64: Video RAM: 6144k
(--) Mach64: Using hardware cursor
(--) Mach64: Using 16 MB aperture @ 0x41000000
(--) Mach64: Using 4 KB register aperture @ 0x40000000
(--) Mach64: Ramdac is Internal
(--) Mach64: Ramdac speed: 230 MHz
Warning: Ron = 43, Rloop = 10, Roff = 46
(--) Mach64: Pixmap cache: 0 256x256 slots, 0 128x128 slots, 0 64x64 slots
(--) Mach64: Font cache: 0 fonts
Xlib:  extension "XINERAMA" missing on display ":1.0".
SetKbdSettings - type: 2 rate: 30 delay: 500 snumlk: 0
SetKbdSettings - Succeeded
subshell.c: couldn't get terminal settings: Inappropriate ioctl for device

Tim Mann  tim.mann@compaq.com  http://www.tim-mann.org
Compaq Computer Corporation, Systems Research Center, Palo Alto, CA
Comment 1 Mike A. Harris 2001-09-18 04:22:25 EDT
If it hasn't been picked up already, we will pick up the upstream
fix when available.  Thanks for the report.
Comment 2 Mike A. Harris 2002-11-03 02:55:53 EST
This should be fixed in XFree86 CVS which is going into rawhide soon,
if not in an earlier release.

Closing as RAWHIDE


Note You need to log in before you can comment on or make changes to this bug.