Request to fix wx.ListCtrl.SetItemData()

Hi All,

As follow up to my previous message, about passing client data to
wx.ListCtrl, I would suggest a change in the wxPython binding, as the
int reference in wx.ListCtrl.SetItemData() should be a long. This is
taken from the wxWidgets C++ Help:

wxListCtrl::SetItemData
bool SetItemData(long item, long data)

Could this be safely changed to a long? Or maybe if the existing API
will break too much, reimplement this as wx.ListCtrl.SetItemDataLong()
/ wx.ListCtrl.SetClientData() ?

It is a bit annoying to have to keep a dictionary reference to my
objects, and come up with unique numbers to identify which object I
clicked, while changing the int to a long in wx.ListCtrl.SetItemData
() would allow us to pass object references to the GUI, and be more
consistent with wx.Choice / wx.ComboBox and the likes, which do allow
that.

With regards,
- Jorgen

Hi Robin,

Thanks for the reply. I see what you mean. The
wxControlWithItems::SetClientData is a void* .. well AFAIK I long can
be safely casted to a void * .. I've done it many times, So maybe the
indirect pyobject -> void * -> long construction might be a solution

- Jorgen

···

On 5/7/07, Robin Dunn <robin@alldunn.com> wrote:

Andrea Gavana wrote:
> Hi Jorgen,
>
> On 5/7/07, Jorgen Bodde wrote:
>> Could this be safely changed to a long? Or maybe if the existing API
>> will break too much, reimplement this as wx.ListCtrl.SetItemDataLong()
>> / wx.ListCtrl.SetClientData() ?
>>
>> It is a bit annoying to have to keep a dictionary reference to my
>> objects, and come up with unique numbers to identify which object I
>> clicked, while changing the int to a long in wx.ListCtrl.SetItemData
>> () would allow us to pass object references to the GUI, and be more
>> consistent with wx.Choice / wx.ComboBox and the likes, which do allow
>> that.
>
> I agree with you, it is a bit annoying to notice that the powerful
> wx.ListCtrl can not handle Python object data as, for example,
> wx.TreeCtrl does (using SetPyData). From the point of view of
> implementation, I don't think it will be that much problematic as it
> is a Python specific modification that would require a couple of
> methods (what about having SetPyData and GetPyData as wx.TreeCtrl
> has?).

It may be possible, but it is problematic. See my reply in the "Passing
python object as client data" thread. It really needs some surgery in
the wxListCtrl C++ classes to be done safely.

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

---------------------------------------------------------------------
To unsubscribe, e-mail: wxPython-users-unsubscribe@lists.wxwidgets.org
For additional commands, e-mail: wxPython-users-help@lists.wxwidgets.org

Jorgen Bodde wrote:

Hi Robin,

Thanks for the reply. I see what you mean. The
wxControlWithItems::SetClientData is a void* .. well AFAIK I long can
be safely casted to a void * .. I've done it many times, So maybe the
indirect pyobject -> void * -> long construction might be a solution

There would still be the problem with knowing when to delete the object. The wxListCtrl won't do it since it just thinks that it as long integers. And if we try to do it in the wrapper code we'll surely either miss some cases, or possibly disrupt some user apps as we'll have to catch all the delete events ourselves.

···

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

Hi Robin,

I think the wxWidgets c++ guys will not change the API easliy, but I
can start a discussion there to see what can be done, and why on earth
it was made an int to begin with.

Thanks for the explanation!

- Jorgen

···

On 5/8/07, Robin Dunn <robin@alldunn.com> wrote:

Jorgen Bodde wrote:

> Just a small question, is the SetClientData of wx.ControlWithItems
> also unsafe? I keep my objects in a list anyway, so there is no danger
> of being prematurely destroyed.. I come from a C++ background, so I am
> used to cleaning up my own crap, and I know the SetClientData does not
> keep a reference :wink:

It does in wxPython. Since the C++ class uses a class type to hold the
data instead of just a long int I am able to derive a Python-aware
subclass that does proper refcounting of the PyObject. Then I replace
the SetClientData method with one that looks like this:

         void SetClientData(int n, PyObject* clientData) {
             wxPyClientData* data = new wxPyClientData(clientData);
             self->SetClientObject(n, data);
         }

The wxPyClientData increments the refcount in the constructor and
decrements it in the destructor. Since wxControlWithItems takes
ownership of the data object then I know that it will eventually be
destroyed properly, either when the item is removed from the control or
when the control is destroyed, so I don't have to worry about it. If
wxListCtrl was changed to also use wxClientData then it would take about
five minutes to allow wxPython to do the same thing there too.

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

---------------------------------------------------------------------
To unsubscribe, e-mail: wxPython-users-unsubscribe@lists.wxwidgets.org
For additional commands, e-mail: wxPython-users-help@lists.wxwidgets.org