very wierd behaviour of multi-column ListCtrl on Windows

hi,

i'm seeing very strange behaviour on WindowsXP wx-2.8.9.1
(and wx-2.8.8.1) with a multi-column ListCtrl. the attached
program works fine on MacOSX and Linux but is completely
broken on Windows.

On MacOSX and Linux, the ListCtrl contains:

11111 John Smith
22222 Julie Jones
33333 Peter Wallace
44444 Jane Brown
55555 Philip Jenkins
66666 Mary Smith
77777 Sarah Donaldson
88888 Jacob Silk
99999 Sally Moss

But on Windows, it contains:

99999
88888
77777
66666
55555
44444
33333
22222
11111 Sally Moss

i.e. first column is reversed and other columns are mostly
empty. sometimes the 11111 is another 99999.

initially, i was using InsertStringItem for the first column
and then SetStringItem to overwrite the first column and to
add the remaining columns. i stopped overwriting the first
column but it made little difference (slight difference to
what went in the first column but still very wrong).

Also ListCtrl.GetFirstSelected() on Windows always returns 0
no matter what item is actually the first/only selected item
(so it always says that John Smith was selected) but on MacOSX
and Linux, it returns the index i expect it to return.

these behaviours are too wierd to be unnoticed wx bugs.
it must be a bug in my code. can anyone see what i'm doing wrong?
as you can imagine, i really need this to work :slight_smile:

thanks,
raf

wx-listctrl-windows-bug.py (8.34 KB)

Hi,

hi,

i'm seeing very strange behaviour on WindowsXP wx-2.8.9.1
(and wx-2.8.8.1) with a multi-column ListCtrl. the attached
program works fine on MacOSX and Linux but is completely
broken on Windows.

<snip>
<snap>

these behaviours are too wierd to be unnoticed wx bugs.
it must be a bug in my code. can anyone see what i'm doing wrong?
as you can imagine, i really need this to work :slight_smile:

You should remove the listctrl style LC_SORT_DESCENDING, in this way
it works. Also, it's pretty much useless as you are using the
ColumnSorter mixin, which does the job for you. I supsect anyway that
this may be a bug in the Windows implementation, as this style
shouldn't affect the results so much. Ah, by the way, you shouldn't
use global imports like:

from wx import *
from wx.aui import *
from wx.lib.mixins.listctrl import *
from wx.lib.scrolledpanel import *

This unnecessarily clutter your namespace and may lead to obscure bugs
when two names conflict... good luck then in debugging it.

Andrea.

"Imagination Is The Only Weapon In The War Against Reality."
http://xoomer.alice.it/infinity77/

···

On Tue, Oct 7, 2008 at 3:21 AM, raf wrote:

Andrea Gavana wrote:

Hi,

> hi,
>
> i'm seeing very strange behaviour on WindowsXP wx-2.8.9.1
> (and wx-2.8.8.1) with a multi-column ListCtrl. the attached
> program works fine on MacOSX and Linux but is completely
> broken on Windows.

<snip>
<snap>

> these behaviours are too wierd to be unnoticed wx bugs.
> it must be a bug in my code. can anyone see what i'm doing wrong?
> as you can imagine, i really need this to work :slight_smile:

You should remove the listctrl style LC_SORT_DESCENDING, in this way
it works.

that's wonderful. many thanks.

Also, it's pretty much useless as you are using the
ColumnSorter mixin, which does the job for you.

i was expecting the style to set the initial sort order
and the mixin to allow the user to change it afterwards.
ah, but i do tell the mixin to sort items initially as well.

but i see now that the initial sort order was actually
ascending, not descending, the whole time. the mixin
is probably doing that. hmm, no, the descending style
seems to have no effect even when the mixin isn't used.
ah, the documentation says that the ascending/descending
styles require "a comparison callback in SortItems" without
actually giving any details like what the callback needs
to be called. that's probably why the style is being ignored.
that's ok. i'll just always use the mixin.

I supsect anyway that this may be a bug in the Windows implementation,
as this style shouldn't affect the results so much.

ok. that's another bug to report.

Andrea.

cheers,
raf

···

On Tue, Oct 7, 2008 at 3:21 AM, raf wrote:

raf wrote:

    for i in range(len(self.data)):
      r = self.data[i]
      self.list.InsertStringItem(i, r[0])
      for j in range(1, len(self.columns)):
        self.list.SetStringItem(i, j, r[j] if r[j] != None else '')
      self.list.SetItemData(i, i) # Needed by ColumnSorterMixin
      self.itemDataMap[i] = r # Needed by ColumnSorterMixin

When you use a LC_SORT_ style then the items are inserted in order when you add them. This means that after the InsertStringItem then the actual position of the item may not be the same as i. So when adding the data for the other columns in the same item you should use the value returned from InsertStringItem instead of using i, otherwise you are always setting the values for whatever happens to be the last item in the list at the moment instead of the one you just inserted.

···

--
Robin Dunn
Software Craftsman
http://wxPython.org Java give you jitters? Relax with wxPython!

Robin Dunn wrote:

raf wrote:

> for i in range(len(self.data)):
> r = self.data[i]
> self.list.InsertStringItem(i, r[0])
> for j in range(1, len(self.columns)):
> self.list.SetStringItem(i, j, r[j] if r[j]
> != None else '')
> self.list.SetItemData(i, i) # Needed by
> ColumnSorterMixin
> self.itemDataMap[i] = r # Needed by ColumnSorterMixin
>

When you use a LC_SORT_ style then the items are inserted in order when
you add them. This means that after the InsertStringItem then the
actual position of the item may not be the same as i. So when adding
the data for the other columns in the same item you should use the value
returned from InsertStringItem instead of using i, otherwise you are
always setting the values for whatever happens to be the last item in
the list at the moment instead of the one you just inserted.

--
Robin Dunn
Software Craftsman
http://wxPython.org Java give you jitters? Relax with wxPython!

many thanks for yet another brilliant explanation.

cheers,
raf