Re: Two *other* problems with xscanimage

Matto Marjanovic (maddog@mir.com)
Thu, 7 May 1998 14:59:58 -0400 (EDT)

Matto> b) ___Gamma Curve data is corrupted.___

It looks like Owen Taylor fixed this bug in gtk+-1.0.1. At least, I
don't see any problems anymore since upgrading.

--david

I haven't checked how it works yet myself (the latest GTK hasn't percolated
through to Debian), but from the Changelog, it looks like he made the change
he suggested in his reply to my bug report (attached below).
It kind of strikes me as a hack to avoid some more insidious problem, but,
you know, I've got other things to think about right now, etc....

-matt m.

From: Owen Taylor <owen@gtk.org>
Cc: gtkdev@gimp.org
Date: Sat, 02 May 1998 23:05:07 -0400
Sender: owt1@cornell.edu

Matto Marjanovic <maddog@mir.com> writes:

> There seems to be a bug in the GtkCurve widget, which is manifested in
> the "xscanimage" program from SANE (0.72) [http://www.mostang.com/sane/].
>
> This would be GTK 1.0.0 (from the Debian package, although the same bug
> has been reported in other sources). My particular system is Linux 2.0.32,
> Debian 2.0/Frozen w/glibc, XFree86 3.3.2.
>
> What follows is the assessment I had sent to the sane-devel mailing list.
> I'll include the relevant snippets of xscanimage code at the end.
>
> If you need more information, please ask.
>
> Thanks!
> matt marjanovic
> maddog@mir.com

[...]

> From: Oliver.Rauch@Wolfsburg.DE
>
> > b) ___Gamma Curve data is corrupted.___
> > When turning on table-based gamma correction (and thus instantiating the
> > gamma curve widget), the following happen:
> > o correct values are read from the (microtek) backend, so far so good.
> > o immediately after the call to gtk_curve_set_gamma in curve_new(),
> > a call to gtk_curve_get_gamma reveals the correct values were
> > written to the widget.
> > o sometime later (when the event loop updates/displays the widget, I
> > imagine), xscanimage declares

Not knowing exactly what the symptoms are (and not wanting
to compile SANE right now, and not having a scanner) it's
a bit hard to figure out what needs to be fixed, but...

> For no good reason, I went poking at this with gdb (well, at least I'm
> learning how to use gdb), and made some discoveries. The problem is in
> the widgets, not xscanimage. Someone who knows more about GTK widget
> programming will need to take over from here....
>
> When xscanimage runs, the corruption to the gamma curve widget happens
> during the call to gtk_widget_show(notebook) at the end of vector_new()
> ["gtkglue.c"]. Here are before and after snapshots of the Curve:
>
> BEFORE:

[...]

> Note how "height" and "num_points" are now the unlikely values of -5, and
> the "point" vector has moved.
>
> The basic problem is that "allocation.width" and "allocation.height" are 1,1
> and not 262,262. The chain of events (I believe) is: [in "gtk/gtkcurve.c"]

Here's some background on the situation. In versions of GTK+ before
0.99.8 or so, a widget would always have its window created
with an initial size of 1x1, then afterwords be size_allocated()
to the proper size. However, under certain circumstances this
initial invalid size could cause problems, and the procedure
was inefficient as well.

So that was changed so that whenever possible a widget would be
allocated to the correct size, then be realized. This caused
problems with the way GtkDrawingArea generated its configure
events - because they were generated in size_allocate() - but
only after it was realized. So the code to generate the
configure events was also added to the realize() handler.

But note "whenever possible". Under some circumstances a widget _must_
be "realized" (have its window created) before it is size allocated -
for instance, when the user calls realize() explicitely. In those
cases, a DrawingArea widget will generate two configure events -
the first one with a size of 1x1, and the second one with the
real size. This is what is apparently confusing GtkGammaCureve.

I am less sure why this applies to xscanimage. I can't see anything
that would cause it to be realized before the toplevel window is
gtk_widget_show()'d and it is size_allocated, at least without
running the code.

> gtk_curve_graph_events() is called for either a CONFIGURE or EXPOSE event,
> and subsequently calls gtk_curve_draw() with the width and height taken
> from the "allocation", as:
> width = w->allocation.width - RADIUS * 2;
> height = w->allocation.height - RADIUS * 2;
> i.e. -5 and -5
>
> gtk_curve_draw() sees the requested width,height (-5,-5) doesn't match what
> was loaded into it (256,256), and calls gtk_curve_interpolate(), which then
> generates screwy numbers.

> SO: Perhaps gtk_curve_graph_events() should use the curve's "requisition"
> instead of its "allocation" to calculate those width and height.
> Perhaps in an earlier incarnation of GTK, the curve widget got 'allocated'
> earlier or something.
> I don't really know what design issues are involved here.

Using the requisition is not a good idea, because perhaps the curve
widget got more or less size than it requested.

What I think is the right think to do is:

Index: gtkcurve.c
===================================================================
RCS file: /debian/home/gnomecvs/gtk+/gtk/gtkcurve.c,v
retrieving revision 1.9
diff -u -r1.9 gtkcurve.c
--- gtkcurve.c 1998/04/13 01:59:47 1.9
+++ gtkcurve.c 1998/05/03 02:40:12
@@ -294,6 +294,9 @@
width = w->allocation.width - RADIUS * 2;
height = w->allocation.height - RADIUS * 2;

+ if ((width < 0) || (height < 0))
+ return FALSE;
+
/* get the pointer position */
gdk_window_get_pointer (w->window, &tx, &ty, NULL);
x = CLAMP ((tx - RADIUS), 0, width-1);

That is, simply ignore the event that occurs with the initial bogus
size, since a real one will come along later. I don't really
understand why the initial bogus size confuses the GammaCurve widget
_after_ the second real size is determined - that would require more
investigation into the internals of GammaCurve than I want to do at
the moment.

If you want to check this out and see if it fixes the problem,
it would be appreciated.

(BTW, are there plans to release a version of SANE that uses
'gtk-config' to determine the proper include directories and
libraries for GTK+? (see the file docs/gtk-config.txt in
the GTK+ distribution) I believe that the Debian maintainer
might have a suitable patch. SANE-0.72 will not work with
any version of GTK+ released in the last 1.5 months.)

Regards,
Owen

--
Source code, list archive, and docs: http://www.mostang.com/sane/
To unsubscribe: echo unsubscribe sane-devel | mail majordomo@mostang.com