Re: GType::register RFE



Brett Kosinski said:
muppet said:
thus, there is no need for a class_init at the perl level.  you can consider
the loading of your module to be class_init (your module gets parsed and
executed once, which is when the registration happens).

[...]
As a result, in order to implement subclassing, I need to be able to
define a class_init function which can do the nitty gritty work of
overriding these virtual methods (with a perlish interface to make it nice
and pretty)

i don't dispute your need to be able to run stuff at class_init time --- what
i'm saying is that there's no need to put that stuff into a function, because
any code placed immediately after Glib::Type::register will run after the
class has been initialized.  (and if not, you can force it to exist when you
get into an xsub called there.)

This is how the CellRenderer subclassing stuff works.  it requires that you
override some vtable functions which are not signals, and we do that with an
unfortunately ugly trick that looks like this:

  # register a new object type
  use Glib::Object::Subclass
          Gtk2::CellRenderer::,
          ...
          ;
  # do class init stuff here, e.g.
  __PACKAGE__->_install_overrides;


an extra wrinkle for the cellrenderer stuff is that i'd love to have that not
be necessary, e.g. override the base_init for Gtk2::CellRenderer to call
install the overrides itself, but this simply isn't safe, as it would require
pretending that it's a perl-derived type, which isn't true --- its *children*
are perl-derived types.  this discrepancy has the potential to lead to core
dumps down the road.


but anyway, i think it would be silly to put those sort of things into
functions which will be executed only once when we already have code that will
be executed only once.

(i'm assuming here that multiple 'use' statements only evaluate the code once.)


[snip a sneaky and evil plan]
And voila.  Assuming, of course, I'm not totally off my rocker. ;)

an implementation of that algorithm, and a sample program, and a t-directory
test version of the sample are attached.

the patch is against HEAD as of five minutes ago, and adds a boolean value to
the type's qdata when we register it (to say that we created this type), and
adds the base_init override which looks for INIT_BASE in the proper package. 
the package of the type being created is passed to INIT_BASE, not the package
whose base_init is being called; this ensures that you have the proper class
pointer when you look it up by name.

the init stuff will happen *after* registration with the bindings, but before
any signals or properties are installed and before any instances are created. 
basically, the initialization stuff happens the first time anybody says
g_type_class_ref(gtype).


let me know if this works.

-- 
muppet <scott at asofyet dot org>

Attachment: double-derived.pl
Description: Binary data

Attachment: base_init.patch
Description: Binary data



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]