From: Hidetoshi NAGAI Date: 2004-04-30T13:52:22+09:00 Subject: Re: Ruby/Tk - TkComposite Hi, From: mhm26@drexel.edu (matt) Subject: Ruby/Tk - TkComposite Date: Fri, 30 Apr 2004 10:19:02 +0900 Message-ID: <13383d7a.0404291715.4208c80c@posting.google.com> > Are there any good pointers on where to learn how to make new Tk > Widgets? I'm not a Tk guy, and I've been using Ruby/Tk for only about > a week and a half (so I'm making okay stuff, but not even near > guru...) There are some samples in 'ext/tk/sample' directory of Ruby source archive. 'tkmulticolumnlist.rb', 'tkmultilistbox.rb', tkmultilistframe.rb', and 'tktextframe.rb' use TkComposite module. 'tkalignbox.rb' and 'tkballoonhelp.rb' don't use the module. When create a new widget class, you shold make it as a daughter class of TkWindow. If you want to use TkComposite module, note @path, @epath, and 'delegate' method. Each of @path and @epath keeps a Tk's widget path string. General widgets keep same string on both of @path and @epath. @path decides the receiver widget of method calls, and @epath (returned by 'epath' method) is used by geometry managers. A composite widget is a widget set layouted on a frame widget. So, @epath of the composite widget has to denote the frame widget. The composite widget's initializer overrided by TkComposite module create a frame widget (kept on @frame) as a container, and set @path and @epath to the path name of the frame widget. After that, the initializer calls 'initialize_composite' method. In the 'initialize_composite' method, you will create widgets as parts of the composite widget and set @path to the pathname of one of the widgets. 'delegate' method is used to make easier for controlling options of contained widgets. 1st argument of the method is a name of the widget option, and others are widgets to change the option simultaneously. For example, on 'tktextframe.rb', -------------------------------------------------------------- delegate('DEFAULT', @text) delegate('background', @frame, @h_scroll, @v_scroll) delegate('activebackground', @h_scroll, @v_scroll) delegate('troughcolor', @h_scroll, @v_scroll) delegate('repeatdelay', @h_scroll, @v_scroll) delegate('repeatinterval', @h_scroll, @v_scroll) delegate('borderwidth', @frame) delegate('relief', @frame) -------------------------------------------------------------- When the configure method of the composite widget is called (e.g. widget['troughcolor'] = 'yellow'), the option name is searched on the delegate table of the widget. If find it, configure all widgets of the list defined by 'delegate' method (e.g. configure 'troughcolor', both of @h_scroll and @v_scroll are changed about the option). If cannot find the definition, 'DEFAULT' entry is used. When not include TkComposite module, note @path and 'epath' method. Although sample 'tkalignbox.rb' and 'tkballoonhelp.rb' override 'initialize' method, you can define an initializer by overriding 'create_self' method. The following is one of the simple examples. -------------------------------------------------------------- require 'tk' class Button_with_Frame < TkButton def create_self(keys) @frame = TkFrame.new('widgetname'=>@path, 'background'=>'yellow') install_win(@path) # create new @path which is a daughter of old @path super(keys) TkPack(@path, :padx=>7, :pady=>7) @epath = @frame.path end def epath @epath end end Button_with_Frame.new(:text=>'QUIT', :command=>proc{exit}) { pack(:padx=>15, :pady=>5) } Tk.mainloop -------------------------------------------------------------- -- Hidetoshi NAGAI (nagai@ai.kyutech.ac.jp)