|
From: <mi...@ph...> - 2004-08-16 08:50:38
|
There is a bug in the color palette treatment in the X11 terminal: when using multiple X11 terminals, window redraw (requested e.g. by a window manager) will change its palette. Try this script: set pm3d map set term x11 10 set title '10 gray levels' set palette gray set palette maxcolors 10 splot x*x set term x11 2 set title '2 colors' set palette color set palette maxcolors 2 splot x Now, maximize or resize window #10 by mouse => it will change from gray map with 10 gray levels to color map with 2 colors. Is it possible to fix it? --- PM |
|
From: Ethan M. <merritt@u.washington.edu> - 2004-08-16 19:31:49
|
On Monday 16 August 2004 01:50 am, Petr Mikulik <mi...@ph...> wrote: > There is a bug in the color palette treatment in the X11 terminal: when > using multiple X11 terminals, window redraw (requested e.g. by a window > manager) will change its palette. > > Is it possible to fix it? I am not very familiar with this, and I may have it wrong. But It looks to me that the PM3D code would have to be re-written. As it is, gnuplot_x11 only maintains two GC (= "Graphics Context") structures. One of these is used for PM3D operations, and the other is used for everything else. There is not currently any notion of keeping a separate GC for each plot window. So if you redefine the PM3D GC to use a different palette, it affects all PM3D operations in all windows. I imagine it would be possible to create a new GC for each window, but I am not sure what pitfalls that would expose. I believe that Johannes Zellner wrote this code, so maybe he has some insight into the issue. Otherwise, maintaining per-window information is related to code that Daniel Sebald added recently, so he might be interested in experimenting with this. -- Ethan A Merritt merritt@u.washington.edu Biomolecular Structure Center Mailstop 357742 University of Washington, Seattle, WA 98195 |
|
From: Dave D. <dde...@es...> - 2004-08-16 19:56:18
|
Ethan Merritt <merritt@u.washington.edu> writes:
> On Monday 16 August 2004 01:50 am, Petr Mikulik <mi...@ph...> wrote:
>> There is a bug in the color palette treatment in the X11 terminal: when
>> using multiple X11 terminals, window redraw (requested e.g. by a window
>> manager) will change its palette.
>>
>> Is it possible to fix it?
>
> I am not very familiar with this, and I may have it wrong.
> But It looks to me that the PM3D code would have to be re-written.
>
> As it is, gnuplot_x11 only maintains two GC (= "Graphics Context")
> structures. One of these is used for PM3D operations, and the other
> is used for everything else. There is not currently any notion of
> keeping a separate GC for each plot window. So if you redefine
> the PM3D GC to use a different palette, it affects all PM3D operations
> in all windows.
>
> I imagine it would be possible to create a new GC for each window,
> but I am not sure what pitfalls that would expose.
>
I had a quick look, and decided that the problem was that colors[] is
global, so that any change will affect all subsequent
repaints. Including the colors[] in the (gnuplot_x11) plot structure
may help.
I don't think the single GC is an issue - the values in the GC are
reset as required.
Eg in
/*-----------------------------------------------------------------------------
* display - display a stored plot
*---------------------------------------------------------------------------*/
void
display(plot)
plot_struct *plot;
{
we have
...
/* loop over accumulated commands from inboard driver */
for (n = 0; n < plot->ncommands; n++) {
...
/* X11_linetype(type) - set line type */
else if (*buffer == 'L') {
sscanf(buffer, "L%4d", <);
lt = (lt % 8) + 2;
/* default width is 0 {which X treats as 1} */
width = widths[lt] ? user_width * widths[lt] : user_width;
if (dashes[lt][0]) {
type = LineOnOffDash;
XSetDashes(dpy, gc, 0, dashes[lt], strlen(dashes[lt]));
} else {
type = LineSolid;
}
XSetForeground(dpy, gc, colors[lt + 3]);
XSetLineAttributes(dpy, gc, width, type, CapButt, JoinBevel);
}
which is updating the Gc foreground colour, but from the global
colors[] array, which may have changed since the plot was created.
(I also decided that line widths and dashes could suffer from the same
problem, but couldn't immediately reproduce any problem
)
dd
--
Dave Denholm <dde...@es...> http://www.esmertec.com
|
|
From: <mi...@ph...> - 2004-08-25 06:55:06
|
I have found yet another bug of X11 terminal which may (or may not?) have a common base with the bug in $Subj. Please try this: set palette maxcolors 4 set pm3d set term x11 1 splot x set term x11 2 splot x => only the 1st x11 window shows the palette correctly, the following ignore 'set palette' options. It seems like x11 window structure is either not copying the palette information, or ignores it. --- Petr Mikulik |
|
From: Daniel J S. <dan...@ie...> - 2004-08-25 09:37:59
|
I believe that may be tied into the same problem area. I think I described something in that recursive code where removing one conditional statement would allow the palette to be stored and then reinstalled upon refreshing the graph. But the problem was that with that alteration the palette wasn't orignally coming out with the proper number of colors. The behavior seemed similar to this example. Dan mi...@ph... wrote: >I have found yet another bug of X11 terminal which may (or may not?) have >a common base with the bug in $Subj. Please try this: >set palette maxcolors 4 >set pm3d >set term x11 1 >splot x >set term x11 2 >splot x > >=> only the 1st x11 window shows the palette correctly, the following >ignore 'set palette' options. It seems like x11 window structure is either >not copying the palette information, or ignores it. >--- >Petr Mikulik > > > > > >------------------------------------------------------- >SF.Net email is sponsored by Shop4tech.com-Lowest price on Blank Media >100pk Sonic DVD-R 4x for only $29 -100pk Sonic DVD+R for only $33 >Save 50% off Retail on Ink & Toner - Free Shipping and Free Gift. >http://www.shop4tech.com/z/Inkjet_Cartridges/9_108_r285 >_______________________________________________ >gnuplot-beta mailing list >gnu...@li... >https://lists.sourceforge.net/lists/listinfo/gnuplot-beta > > > > -- Dan Sebald email: daniel DOT sebald AT ieee DOT org URL: http://acer-access DOT com/~dsebald AT acer-access DOT com/ |
|
From: Daniel J S. <dan...@ie...> - 2004-08-16 20:00:16
|
Ethan Merritt wrote: >On Monday 16 August 2004 01:50 am, Petr Mikulik <mi...@ph...> wrote: > > >>There is a bug in the color palette treatment in the X11 terminal: when >>using multiple X11 terminals, window redraw (requested e.g. by a window >>manager) will change its palette. >> >>Is it possible to fix it? >> >> > >I am not very familiar with this, and I may have it wrong. >But It looks to me that the PM3D code would have to be re-written. > >As it is, gnuplot_x11 only maintains two GC (= "Graphics Context") >structures. One of these is used for PM3D operations, and the other >is used for everything else. There is not currently any notion of >keeping a separate GC for each plot window. So if you redefine >the PM3D GC to use a different palette, it affects all PM3D operations >in all windows. > >I imagine it would be possible to create a new GC for each window, >but I am not sure what pitfalls that would expose. > >I believe that Johannes Zellner wrote this code, so maybe he has >some insight into the issue. > >Otherwise, maintaining per-window information is related to code >that Daniel Sebald added recently, so he might be interested in >experimenting with this. > I didn't look at the code, but as soon as I tried Petr's example it struck me that what Ethan's describing is the case. I'll have a look this evening to assess how much it would involve. But it seems logical that since an X11 plot keeps all information about the plotting primitives so that it can be redrawn, it should also keep track of the palette. If things are organized as I suspect, that palette should be a separate entity in the plot structure, not go into the list of graphics primitives. That's easy enough to add. Then, when reactivated, just install the palette. What this means, I think, is that when you issue a palette command to a certain X11 plot, the graphics primitives can still be used to draw under that new palette. The X11 code could certainly be redrawn upon getting that palette command. Do you want that? I.e., for X11 do you want to have to have to do "set palette; replot"? Or should the "set palette" change the X11 plot right away? Note, that for non-GUI terminals you would always have to do a "set palette; replot" to affect a change. Dan |
|
From: Daniel J S. <dan...@ie...> - 2004-08-16 20:07:34
|
Daniel J Sebald wrote: > What this means, I think, is that when you issue a palette command to > a certain X11 plot, the graphics primitives can still be used to draw > under that new palette. The X11 code could certainly be redrawn upon > getting that palette command. Do you want that? I.e., for X11 do you > want to have to have to do "set palette; replot"? Or should the "set > palette" change the X11 plot right away? Note, that for non-GUI > terminals you would always have to do a "set palette; replot" to > affect a change. Hold on. There may be a problem with that scheme. We're not sure the primitives in the plot memory match the same size of the new palette installed. "set palette; replot" must be done to affect a change in the plot appearance. Yes? No? Dan |
|
From: <mi...@ph...> - 2004-08-17 06:50:48
|
> "set palette; replot" must be done to affect a change in > the plot appearance. Yes, it should work this way. -- PM |
|
From: Ethan M. <merritt@u.washington.edu> - 2004-08-17 22:46:18
|
On Monday 16 August 2004 11:47 pm, mi...@ph... wrote: > > "set palette; replot" must be done to affect a change in > > the plot appearance. > > Yes, it should work this way. I don't understand what you guys are saying. You cannot do a "replot" on a previous plot, only on the current plot. -- Ethan A Merritt merritt@u.washington.edu Biomolecular Structure Center Mailstop 357742 University of Washington, Seattle, WA 98195 |
|
From: Daniel J S. <dan...@ie...> - 2004-08-17 18:39:04
|
Ethan Merritt wrote: >On Monday 16 August 2004 11:47 pm, mi...@ph... wrote: > > >>>"set palette; replot" must be done to affect a change in >>>the plot appearance. >>> >>> >>Yes, it should work this way. >> >> > >I don't understand what you guys are saying. >You cannot do a "replot" on a previous plot, only on the current plot. > Right, I think it is already set up that way. Dan |
|
From: Daniel J S. <dan...@ie...> - 2004-08-16 20:24:30
|
Dave,
If you want to look into this one, let me know. (Otherwise I can do it
one of these evenings.) I can picture in my mind how to do it. A
palette pointer needs to be placed in the plot array. There is going to
be some alloc() and realloc() for that pointer and the palette when it
is changed, or in things like prepare_plot(). The one careful detail is
immediately upon creating the memory for the plot structure itself as
part of the linked-list of plots, be sure to set the pointer for the
palette to 0 (!!! much emphasis). That could also be done in
prepare_plot() but I advise putting it at the spot where memory is
created, because doing it in prepare_plot() leaves open the door for
someone to inadvertently call prepare_plot() and mash a valid palette
pointer, creating a memory leak.
Dan
Dave Denholm wrote:
>Ethan Merritt <merritt@u.washington.edu> writes:
>
>
>
>>On Monday 16 August 2004 01:50 am, Petr Mikulik <mi...@ph...> wrote:
>>
>>
>>>There is a bug in the color palette treatment in the X11 terminal: when
>>>using multiple X11 terminals, window redraw (requested e.g. by a window
>>>manager) will change its palette.
>>>
>>>Is it possible to fix it?
>>>
>>>
>>I am not very familiar with this, and I may have it wrong.
>>But It looks to me that the PM3D code would have to be re-written.
>>
>>As it is, gnuplot_x11 only maintains two GC (= "Graphics Context")
>>structures. One of these is used for PM3D operations, and the other
>>is used for everything else. There is not currently any notion of
>>keeping a separate GC for each plot window. So if you redefine
>>the PM3D GC to use a different palette, it affects all PM3D operations
>>in all windows.
>>
>>I imagine it would be possible to create a new GC for each window,
>>but I am not sure what pitfalls that would expose.
>>
>>
>>
>
>
>I had a quick look, and decided that the problem was that colors[] is
>global, so that any change will affect all subsequent
>repaints. Including the colors[] in the (gnuplot_x11) plot structure
>may help.
>
>I don't think the single GC is an issue - the values in the GC are
>reset as required.
>
>
>Eg in
>
>/*-----------------------------------------------------------------------------
> * display - display a stored plot
> *---------------------------------------------------------------------------*/
>
>void
>display(plot)
>plot_struct *plot;
>{
>
>we have
>
>...
>
> /* loop over accumulated commands from inboard driver */
> for (n = 0; n < plot->ncommands; n++) {
>
> ...
>
> /* X11_linetype(type) - set line type */
> else if (*buffer == 'L') {
> sscanf(buffer, "L%4d", <);
> lt = (lt % 8) + 2;
> /* default width is 0 {which X treats as 1} */
> width = widths[lt] ? user_width * widths[lt] : user_width;
> if (dashes[lt][0]) {
> type = LineOnOffDash;
> XSetDashes(dpy, gc, 0, dashes[lt], strlen(dashes[lt]));
> } else {
> type = LineSolid;
> }
> XSetForeground(dpy, gc, colors[lt + 3]);
> XSetLineAttributes(dpy, gc, width, type, CapButt, JoinBevel);
> }
>
>
>which is updating the Gc foreground colour, but from the global
>colors[] array, which may have changed since the plot was created.
>
>(I also decided that line widths and dashes could suffer from the same
> problem, but couldn't immediately reproduce any problem
>)
>
>
>
>dd
>
>
--
Dan Sebald
email: daniel DOT sebald AT ieee DOT org
URL: http://acer-access DOT com/~dsebald AT acer-access DOT com/
|
|
From: Daniel J S. <dan...@ie...> - 2004-08-16 20:28:50
|
And when the plot structure memory is freed, must first test whether the palette pointer is valid and if so free that as well. Dan Daniel J Sebald wrote: > Dave, > > If you want to look into this one, let me know. (Otherwise I can do > it one of these evenings.) I can picture in my mind how to do it. A > palette pointer needs to be placed in the plot array. There is going > to be some alloc() and realloc() for that pointer and the palette when > it is changed, or in things like prepare_plot(). The one careful > detail is immediately upon creating the memory for the plot structure > itself as part of the linked-list of plots, be sure to set the pointer > for the palette to 0 (!!! much emphasis). That could also be done in > prepare_plot() but I advise putting it at the spot where memory is > created, because doing it in prepare_plot() leaves open the door for > someone to inadvertently call prepare_plot() and mash a valid palette > pointer, creating a memory leak. > > Dan |
|
From: Dave D. <dde...@es...> - 2004-08-16 20:42:35
|
Daniel J Sebald <dan...@ie...> writes: > Dave, > > If you want to look into this one, let me know. (Otherwise I can do > it one of these evenings.) I can picture in my mind how to do it. A Sorry, I'm really out of touch with what it's *supposed* to do :-( (Come to think of it - I may not even have the latest sources, in which case what I just wrote may have been rubbish) dd -- Dave Denholm <dde...@es...> http://www.esmertec.com |
|
From: Ethan M. <merritt@u.washington.edu> - 2004-08-16 21:08:39
|
On Monday 16 August 2004 01:42 pm, Dave Denholm wrote:
>
> (Come to think of it - I may not even have the latest sources, in
> which case what I just wrote may have been rubbish)
The particular code bit you posted applies to line colors, not
to pm3d rectangles. But there is a similar bit of code in
PaletteSetColor(plot_struct * plot, double gray) that applies
to pm3d:
index = gray * (plot->cmap->allocated - 1);
if (index >= plot->cmap->allocated)
index = plot->cmap->allocated -1;
XSetForeground(dpy, gc_pm3d, plot->cmap->pixels[index]);
I don't really have a grasp of the big picture.
I *think* the problem is that plot->cmap itself is still only
a list of color indices, and since the time it was first set up the
true colormap stored in the gc has changed. So the above
code updates the index, but it is an index into an obsolete table.
That's why I thought we might have to store a copy of the gc
in use at the time the original color mapping was set up.
Maybe.
--
Ethan A Merritt merritt@u.washington.edu
Biomolecular Structure Center
Mailstop 357742
University of Washington, Seattle, WA 98195
|
|
From: Daniel J S. <dan...@ie...> - 2004-08-16 21:49:18
|
Ethan Merritt wrote: >On Monday 16 August 2004 01:42 pm, Dave Denholm wrote: > > >>(Come to think of it - I may not even have the latest sources, in >> which case what I just wrote may have been rubbish) >> <snip> >That's why I thought we might have to store a copy of the gc >in use at the time the original color mapping was set up. > > I'll give that a try this evening. I know exactly where the memory pointer initialization and alloc's should go. Dan |
|
From: Daniel J S. <dan...@ie...> - 2004-08-16 22:07:48
|
Looking through some code, I see the following line
df_column = (df_column_struct *) gp_realloc(df_column,
(df_max_cols += (df_max_cols < 20 ? 20 :
df_max_cols)) * sizeof(df_column_struct),
"datafile column");
Does anyone else find this suspicious? Particularly the part where
df_max_cols is changed *before* the actual allocation takes place.
Here is a far fetched scenario that might cause a problem. Say someone
runs gnuplot and has a bunch of other programs running. The person
tries a plot and it fails to allocate memory because there is no room.
Gnuplot gives an error in the gp_realloc() function. However,
df_max_cols has already been updated. The person then thinks to exit
some program to free memory, runs his or her plot command and it
crashes. The reason being, as I'm thinking, df_max_cols was adjusted
previously and the limit test thinks there is enough room for
df_max_cols when in fact that memory couldn't be allocated last time the
plot command was attempted.
There may be other similar instances of this and I'd say hold off
addressing it for a while.
Dan
|
|
From: Daniel J S. <dan...@ie...> - 2004-08-17 23:10:08
Attachments:
junk
|
Ethan Merritt wrote:
>On Monday 16 August 2004 01:42 pm, Dave Denholm wrote:
>
>
>>(Come to think of it - I may not even have the latest sources, in
>> which case what I just wrote may have been rubbish)
>>
>>
>
>The particular code bit you posted applies to line colors, not
>to pm3d rectangles. But there is a similar bit of code in
>PaletteSetColor(plot_struct * plot, double gray) that applies
>to pm3d:
>
> index = gray * (plot->cmap->allocated - 1);
> if (index >= plot->cmap->allocated)
> index = plot->cmap->allocated -1;
> XSetForeground(dpy, gc_pm3d, plot->cmap->pixels[index]);
>
>I don't really have a grasp of the big picture.
>I *think* the problem is that plot->cmap itself is still only
>a list of color indices, and since the time it was first set up the
>true colormap stored in the gc has changed. So the above
>code updates the index, but it is an index into an obsolete table.
>That's why I thought we might have to store a copy of the gc
>in use at the time the original color mapping was set up.
>
I believe this is correct. I looked at the array of GC values, it
doesn't look to have anything to do with the color map.
In
process_configure_notify_event(XEvent *event)
is where the mouse event comes for resizing the window. Now, I'm pretty
sure that a problem here is that in this routine is
plot = Find_Plot_In_Linked_List_By_Window(event->xconfigure.window);
near the top and if there is a change in the window size and a few other
things, eventually there is a
display(plot);
So, nothing in that code looks as though a window color scheme was
activated or reinstalled between those two commands. My thinking is
that the fix should be as simple as that attached diff file. But there
is that "small" detail that Ethan describes.
The complete color map needs to be stored as part of the structure.
That is, plot->cmap needs to point at something that is dynamically
allocated independent of the current color map. I'll work on that fix,
but if this doesn't sound correct, let me know. Also, maybe think if
what I've added in this patch is adequate to fix the problem when I have
the plot->cmap problem fixed. That is, are there any other details
about the GC that also must be updated?
Dan
|
|
From: Daniel J S. <dan...@ie...> - 2004-08-17 22:58:05
Attachments:
partialfix
|
Is joze out there?
> The complete color map needs to be stored as part of the structure.
> That is, plot->cmap needs to point at something that is dynamically
> allocated independent of the current color map. I'll work on that
> fix, but if this doesn't sound correct, let me know. Also, maybe
> think if what I've added in this patch is adequate to fix the problem
> when I have the plot->cmap problem fixed. That is, are there any
> other details about the GC that also must be updated?
I started on this one and soon realized that this code is already
present. (The default "cmap" is used similar to zero when doing dynamic
memory allocation.) So, I tracked down this problem to a line of code.
The small change in the attached diff will solve the problem Petr
found, but it also creates another.
Here is the situation. That update of plot->cmap to point to the proper
colormap is done inside PaletteMake. Here is the block of code:
if (plot->cmap->allocated < min_colors && !recursion) {
ReleaseColormap(plot);
/* create a private colormap. */
fprintf(stderr, "switching to private colormap\n");
plot->cmap = (cmap_t *) malloc(sizeof(cmap_t));
assert(plot->cmap);
CmapClear(plot->cmap);
plot->cmap->colormap = XCreateColormap(dpy, root, vis, AllocNone);
assert(plot->cmap->colormap);
pr_color(plot->cmap); /* set default colors for lines */
RecolorWindow(plot);
recursion = 1;
PaletteMake(plot, (t_sm_palette *) 0);
} else {
This allocates memory for the map and then sets plot->cmap to point to
it. If all things are hunky dory then, whenever plot->cmap is refered
to in the future plot->cmap will point to the proper colormap.
However, that test at the start:
plot->cmap->allocated < min_colors
I think that is the problem. The first time in, the min_colors will be
2 or 10 in one of the examples Petr gives. However, the default cmap,
what plot->cmap points to by default has more than 10 allocated values.
Hence, that test never passes and the code which dynamically allocates
the cmap never gets called.
So, remove that test as I did in the diff file. That fixes the problem
of the palette being restored to the proper palette. Unfortunately,
it's not creating the proper palette in the first place. (I has far
more than the 2 or 10 colors requested.)
I could look at it further, but the recursive nature of this routine
causes me to initially punt to joze.
Dan
|
|
From: Daniel J S. <dan...@ie...> - 2004-08-18 07:35:19
|
Some observations about demos:
borders.dem isn't very useful. Too fast to see what is on the page.
Plus requires CNTRL-C to exit.
The following demos are not in all.dem:
borders.dem
candlesticks.dem
charset.dem
enhancedtext.dem
multiplt.dem (such a nice demo)
starmap.dem (another nice demo)
vector.dem (another nice demo)
mousevariables.dem, fontfile.dem and fontfile_latex.dem aren't in
all.dem, but on purpose I think. Not finding the font files will cause
gnuplot to error out. Maybe they could be put at the very end of
all.dem so that if they do crash, nothing will be missed. (Include them
might be good because "all.dem" is a way of testing that nothing is
broke in gnuplot.)
|
|
From: <mi...@ph...> - 2004-08-19 06:12:09
|
> The following demos are not in all.dem: > borders.dem > candlesticks.dem > charset.dem > enhancedtext.dem > multiplt.dem (such a nice demo) > starmap.dem (another nice demo) > vector.dem (another nice demo) > > mousevariables.dem, fontfile.dem and fontfile_latex.dem aren't in > all.dem, but on purpose I think. Not finding the font files will cause > gnuplot to error out. Maybe they could be put at the very end of > all.dem so that if they do crash, nothing will be missed. (Include > them might be good because "all.dem" is a way of testing that nothing > is broke in gnuplot.) There could be files like all_tex.dem all_enhanced.dem which would load those demos which are not accessible from all.dem. --- PM |
|
From: Hans-Bernhard B. <br...@ph...> - 2004-08-19 08:35:54
|
mi...@ph... wrote:
> There could be files like
> all_tex.dem
> all_enhanced.dem
>
> which would load those demos which are not accessible from all.dem.
Nah, that'd be a placebo solution at best. What we really need is some
kind of feature availability test function exported to the user, so
all.dem could do
if (supported("enhanced")) load 'enhancedtext.dem'
(Syntax details to be discussed)
|
|
From: Petr M. <mi...@ph...> - 2004-09-17 13:20:40
|
> The complete color map needs to be stored as part of the structure. > That is, plot->cmap needs to point at something that is dynamically > allocated independent of the current color map. I'll work on that fix, > but if this doesn't sound correct, let me know. Also, maybe think if > what I've added in this patch is adequate to fix the problem when I have > the plot->cmap problem fixed. That is, are there any other details > about the GC that also must be updated? I have just tried the patch, but it was rejected. Don't you have an up-to-date version? Petr |
|
From: Daniel J S. <dan...@ie...> - 2004-09-17 15:05:28
|
Petr Mikulik wrote:
>>The complete color map needs to be stored as part of the structure.
>> That is, plot->cmap needs to point at something that is dynamically
>>allocated independent of the current color map. I'll work on that fix,
>>but if this doesn't sound correct, let me know. Also, maybe think if
>>what I've added in this patch is adequate to fix the problem when I have
>>the plot->cmap problem fixed. That is, are there any other details
>>about the GC that also must be updated?
>>
>>
>
>I have just tried the patch, but it was rejected. Don't you have an
>up-to-date version?
>
Why would that patch be rejected? I don't think anyone has altered that
bit of code in CVS... Anyway, that patch was just a lame alteration to
illustrate where the problem lies. Basically, search for this line of
code in gplt_x11.c
if (plot->cmap->allocated < min_colors && !recursion) {
and replace it with the following
if (!recursion) {
That fixes the problem of keeping track of the color map, but it also
results in an incorrect color map. It looks like a tricky bit of code
because it is recursive. I'm not exactly sure why it is recursive, as
opposed to calling a subroutine twice. In fact, I'm looking at some code
there and wondering what in fact it does. Here is the code in question:
if (plot->cmap->allocated < min_colors && !recursion) {
ReleaseColormap(plot);
/* create a private colormap. */
fprintf(stderr, "switching to private colormap\n");
plot->cmap = (cmap_t *) malloc(sizeof(cmap_t));
assert(plot->cmap);
CmapClear(plot->cmap);
plot->cmap->colormap = XCreateColormap(dpy, root, vis, AllocNone);
assert(plot->cmap->colormap);
pr_color(plot->cmap); /* set default colors for lines */
RecolorWindow(plot);
recursion = 1;
PaletteMake(plot, (t_sm_palette *) 0);
} else {
/* this is just for calculating the number of unique colors */
int i;
unsigned long previous = plot->cmap->allocated ? plot->cmap->pixels[0] : 0;
int unique_colors = 1;
for (i = 0; i < plot->cmap->allocated; i++) {
if (plot->cmap->pixels[i] != previous) {
previous = plot->cmap->pixels[i];
unique_colors++;
}
}
}
Notice that the second portion of the if/else statement alters two local
variables, previous and unique_colors, and that is all. That's a useless
bit of code, as I see it. I wish there were a short note explaining why
this is recursive, i.e., on the second time through, what portion of the
code is important?
Dan
|
|
From: Petr M. <mi...@ph...> - 2004-09-20 09:31:23
|
> >I have just tried the patch, but it was rejected. Don't you have an
> >up-to-date version?
>
> Why would that patch be rejected? I don't think anyone has altered that
> bit of code in CVS...
In the cvs current version, there is no that piece of code to be patched.
Haven't you use some old gplt_x11.c?
> if (plot->cmap->allocated < min_colors && !recursion) {
> and replace it with the following
> if (!recursion) {
But that's completely different from the patch you have sent:
XFreePixmap(dpy, plot->pixmap);
plot->pixmap = None;
}
+ if (plot != current_plot)
+ RecolorWindow(plot);
display(plot);
+ if (plot != current_plot)
+ RecolorWindow(current_plot);
}
}
Thus, what's the patch?
> That fixes the problem of keeping track of the color map, but it also
> results in an incorrect color map. It looks like a tricky bit of code
> because it is recursive. I'm not exactly sure why it is recursive, as
> opposed to calling a subroutine twice. In fact, I'm looking at some code
> there and wondering what in fact it does. Here is the code in question:
>
> Notice that the second portion of the if/else statement alters two local
> variables, previous and unique_colors, and that is all. That's a useless
> bit of code, as I see it. I wish there were a short note explaining why
> this is recursive, i.e., on the second time through, what portion of the
> code is important?
I remember from the old times when Johannes was coding "Make Palette"
function for X11 (term->makepalette(NULL)), that number of available colors
is not known under some visual modes. Then, you have to try to allocate
color palette several times until you find the limit. Can this explain the
recursion?
However, I wonder why this happens -- once the palette is constructed
(according to t_sm_palette) and copied into plot->cmap, it should be used in
every replot of that window.
Petr
|
|
From: Daniel J S. <dan...@ie...> - 2004-09-20 22:34:08
|
Petr Mikulik wrote:
>But that's completely different from the patch you have sent:
> XFreePixmap(dpy, plot->pixmap);
> plot->pixmap = None;
> }
>+ if (plot != current_plot)
>+ RecolorWindow(plot);
> display(plot);
>+ if (plot != current_plot)
>+ RecolorWindow(current_plot);
> }
> }
>
>Thus, what's the patch?
>
Oh, that one at first escaped me. But looking back in the emails, I
think that was the first attempt to make the link list contain
information about palettes. But soon after that I realized that such
code already exists. So the above patch you are referring to was
jettisoned.
>>That fixes the problem of keeping track of the color map, but it also
>>results in an incorrect color map. It looks like a tricky bit of code
>>because it is recursive. I'm not exactly sure why it is recursive, as
>>opposed to calling a subroutine twice. In fact, I'm looking at some code
>>there and wondering what in fact it does. Here is the code in question:
>>
>>Notice that the second portion of the if/else statement alters two local
>>variables, previous and unique_colors, and that is all. That's a useless
>>bit of code, as I see it. I wish there were a short note explaining why
>>this is recursive, i.e., on the second time through, what portion of the
>>code is important?
>>
>>
>
>I remember from the old times when Johannes was coding "Make Palette"
>function for X11 (term->makepalette(NULL)), that number of available colors
>is not known under some visual modes. Then, you have to try to allocate
>color palette several times until you find the limit. Can this explain the
>recursion?
>
>However, I wonder why this happens -- once the palette is constructed
>(according to t_sm_palette) and copied into plot->cmap, it should be used in
>every replot of that window.
>
If I recall, I think I tracked down the flaw in program flow. Let me
look for that... here's a portion of what I wrote before:
=====
I think that is the problem. The first time in, the min_colors will be
2 or 10 in one of the examples Petr gives. However, the default cmap,
what plot->cmap points to by default has more than 10 allocated values.
Hence, that test never passes and the code which dynamically allocates
the cmap never gets called.
=====
Regardless of whether that is correct or not, I think I'm getting a
better view of the big picture here. The real flaw may not necessarily
be in PaletteMake(), although I think PaletteMake() needs a good going
over to weed out cruft. Well, I shouldn't say that, because I think
this problem could be fixed in multiple ways.
The problem may be the following. When a plot window is first created,
its "plot->cmap" is set equal to the default "cmap". I propose that
rather than just pointing to the default colormap, the colomap should be
*duplicated* in memory. The reason is that PaletteMake() doesn't
necessarily create a new version of color map unless those strange
conditions (which I don't fully understand) are met, i.e.,
if (plot->cmap->allocated < min_colors && !recursion) {
ReleaseColormap(plot);
/* create a private colormap. */
fprintf(stderr, "switching to private colormap\n");
plot->cmap = (cmap_t *) malloc(sizeof(cmap_t));
assert(plot->cmap);
CmapClear(plot->cmap);
plot->cmap->colormap = XCreateColormap(dpy, root, vis, AllocNone);
assert(plot->cmap->colormap);
pr_color(plot->cmap); /* set default colors for lines */
RecolorWindow(plot);
recursion = 1;
PaletteMake(plot, (t_sm_palette *) tpal);
} else {
The above is the only place in PaletteMake() that plot->cmap is
malloced. That means that if that condition above is not met, which is
almost certain to be the case, then the rest of PaletteMake() must act
upon the "plot->cmap".
So, say two plots are created and by default they are both set to
"plot->cmap = cmap". Then whenever PaletteMake() is run on the colormap
for one of the plots, it is effectively changing the color map for the
other. So, that is why I'm saying that somewhere along the way upon the
creation of a plots color map, it must *duplicate* the default palette,
i.e., malloc an equal amount of memory as "cmap" and then use memcpy().
That is, if one wants color maps to be preserved in plots. I assume
that when the palette is changed at gnuplot's command line, that change
is supposed to apply to the default palette as well as the current
plot's palette.
Dan
|