[gtkada] Signal handler
Dmitry A. Kazakov
mailbox at dmitry-kazakov.de
Wed Aug 3 20:34:43 CEST 2011
On Wed, 03 Aug 2011 14:06:25 +0200, you wrote:
>> Maybe the names Connect and Handle should rather include the event name.
>> E.g. Connect_To_Clicked and Handle_Clicked. That would ease adding handler
>> interfaces to the composite widgets.
>
> I'd rather use names like On_Clicked, or something.
Yes, I used "Handle" because it is how it is described in the
documentation. On_<event> is a better name.
> By the way, since we would be generating the code, we could indeed generate a
> "not null access" if the user passes a -gnat05 switch. Currently, we do not
> expect users to generate the sources on their machine, since that requires a
> python installation which might not always be available.
If you do, do not forget to add "constant" for the getters. E.g.
function Get_Label
( Button : not null access constant Gtk_Button_Record
) return UTF8_String;
>> Window : Gtk_Window;
>> On_Destroy : Destroy_Main;
>> On_Delete : Delete_Main;
>> begin
>> Gtk_New (Window);
>> Window.Connect_To_Destroy_Event (On_Destroy);
>> Window.Connect_To_Delete_Event (On_Delete);
>
> This code is very dangerous.
Yes, actually I didn't want to make the example more complex than
necessary. Practically it is always better to derive a new type:
type My_Main_Window is new Gtk_Window_Record with record
On_Destroy : Destroy_Main;
On_Delete : Delete_Main;
end record;
or with interfaces:
type My_Main_Window is
new Gtk_Window_Record
and Delete_Event_Handler
and Destroy_Event_Handler with null record;
> The approach taken (and now abandoned) by Java was to subclass:
>
> type My_Window is new Gtk_Window_Record with private;
> overriding procedure On_Delete_Event (Self : My_Window) return Boolean;
No wonder they have to abandon that because it is not very frequent for a
widget to handle its own signals. That incidentally is the case for main
window.
But a much more common case is like a window handling an event from one of
its buttons:
type My_Main_Window_Record;
type My_Main_Window is access all My_Main_Window_Record;
type My_Window_Clicked_Handler is new Clicked_Handler with
Window : My_Main_Window_Ptr;
end record;
overriding procedure On_Clicked ...;
type My_Main_Window_Record is new Gtk_Window_Record with record
Box : Gtk_VBox;
Button : Gtk_Button;
Button_Clicked : My_Window_Clicked_Handler;
end record;
[ Button_Clicked : Clicked_Handler (My_Main_Window'Access); would not work
because objects are not limited. ]
> At least that solves the lifetime issue (the callback exists as long as the
> window).
Actually not fully. Sometimes you want a handler connected to several
emitters. An automatically disconnecting handler object would need to
maintain a list of emitters and keep track of them disappearing. Though
technically possible, I had use that scheme once or twice, it might be to
complex to implement as the default.
>> BTW, did you consider possible impact of turning GObject_Record limited? It
>> would make life much easier when developing user and composite widgets.
>
> I don't think we have looked at this approach. Since we are mostly manipulating
> pointers in GtkAda, it might be a simple matter of adding "limited" in the
> declaration. Can you check whether it works ?
Glib.Type_Conversion_Hooks uses aggregates in Hook_Registrator.
--
Regards,
Dmitry A. Kazakov
http://www.dmitry-kazakov.de
More information about the gtkada
mailing list