[Kde-bindings] playground/bindings/kimono

Richard Dale richard.j.dale at gmail.com
Tue Mar 6 15:19:39 UTC 2007


On Tuesday 06 March 2007, Arno Rehn wrote:
> Am Dienstag, 6. März 2007 schrieb Richard Dale:
> > On Tuesday 06 March 2007, Arno Rehn wrote:
> > > Am Montag, 5. März 2007 schrieb Richard Dale:
> > > > So the 'internalPointer' has a different value even when the
> > > > underlying instance is the same. That's because
> > > > QAbstractItemModel.CreateIndex() allocates a new GCHandle every time,
> > > > which will have different values. The reason it works in QtRuby is
> > > > because the internalPointer is a Ruby VALUE that is  the same for
> > > > every createIndex call.
> > >
> > > Ah tanks. I added a Dictionary where all the GCHandles for
> > > QModelIndex'es are stored. This GCHandle is looked up for the specific
> > > QModelIndex and then passed to the C++ helper function. Selecting child
> > > items is no problem anymore. Up to now I thought GCHandle.Alloc()
> > > returns always the same value, but apparently it doesn't.
> >
> > I thought about have a WeakReference as a key, but I don't think that
> > works because wrapping an instance in a GCHandle will probably create a
> > strong reference (you wouldn't want an instance to be GC'd while you were
> > referencing it in C code).
>
> Yes, that's right, but than we just need to change the WeakReference to a
> normal, 'strong' reference.
>
> > So I think you need to have the actual object as a key, and a struct as a
> > value with two fields; a reference count and a GCHandle. When you add a
> > new GCHandle, set the ref count to 1 and increment every time the handle
> > is reused in another QModelIndex. Then in the QModelIndex destructor,
> > retrieve the entry for the wrapped object and decrement the ref count. If
> > the ref count is then zero, delete the entry.
>
> That won't work, I think, because the destructor is only called
> automatically, when the object is GC'd. And as long as there is a strong
> reference, the object won't be GC'd, so the destrcutor is never called.
> Hence, the only case in which a destructor is called is when you have
> something like
> using (QModelIndex index = CreateIndex(...)) {
>       // code
> }
No, there won't be a reference to the QModelIndex in the dictionary to prevent
it being GC'd, only to the thing inside the 'internalPointer' (ie TreeItem or
similar).

> After that the instance is gone, and then it wouldn't make sense anymore to
> decrement some counter, because the instance was deleted anyway.
>
> I think the current way is OK, because we can easily check if the instance
> is still alive (e.g. in the above example with using(...) {...} it may have
> been deleted) and if not, we can just delete the entry in the Dictionary.
> The WeakReference is just as good as a strong reference for this kind of
> doings and provides us with IsAlive a useful property.
The key WeakReference will always be alive because the value has a GCHandle
wrapping the key.

-- Richard



More information about the Kde-bindings mailing list