Stuck noobie: XRC/xrcise woes

Hi,

I’m teaching myself to use wxRuby and DialogBlocks to create a front end
for a Ruby program I wrote. And I’m hopelessly stuck!

In DialogBlocks (or indeed wxFormBuilder, which gives me the same
problem) I can create a widget, give that widget a new id and class name
(in the example I created below, text_box1 and CaseChangeTextCtrl1,
respectively), and then add a module which utilises that widget in my
program, no problem.

But the moment I try to add a second widget with a second id and a
second class, (in the example below, text_box2 and CaseChangeTextCtrl2 )
I get an “uninitialized constant” error for that widget when I run my
program. I don’t understand it at all. The two widgets are the same,
except they have different class names and different id names.

Is there some limit (a limit of 1) to the number of classes you can
create in an XRC file or xrcise-generated rb file? Do you have to get
DialogBlocks to create separate files for each new class apart from the
first class, or something?

I am sure I am missing something simple. But I have spent hours on this,
and can’t figure it out. Please! Help! Me!

warm regards

John

Below is everything in the chain: 1) the xrc file created by
dialogblocks; 2) the rb file generated from that xrc file by xrcise
(this is the file that produces the error); 3) the user-written code (in
this case, an exercise taken from the web) that calls that
xrcise-generated rb file; and 4) the error message.

the xrc file
<?xml version="1.0" encoding="UTF-8"?>

;

wxCAPTION|wxRESIZE_BORDER|wxSYSTEM_MENU|wxCLOSE_BOX
400,300
From Scratch
1

wxVERTICAL

wxGROW|wxALL
5
1

wxTE_MULTILINE



wxALIGN_CENTER_HORIZONTAL|wxALL
5

Upper



wxALIGN_CENTER_HORIZONTAL|wxALL
5

Lower



wxGROW|wxALL
5
1

wxTE_MULTILINE



######## the ruby file generated by xrcise ######

This class was automatically generated from XRC source. It is not

recommended that this file is edited directly; instead, inherit from

this class and extend its behaviour there.

Source file: exercise.xrc

Generated at: Tue Jun 22 16:49:12 +1000 2010

class TextFrameBase < Wx::Frame

 attr_reader :text_box1, :upper_bt, :lower_bt, :text_box2

 def initialize(parent = nil)
      super()
      xml = Wx::XmlResource.get
      xml.flags = 2 # Wx::XRC_NO_SUBCLASSING
      xml.init_all_handlers
      xml.load("exercise.xrc")
      xml.load_frame_subclass(self, parent, "ID_WXFRAME")

      finder = lambda do | x |
           int_id = Wx::xrcid(x)
           begin
                Wx::Window.find_window_by_id(int_id, self) || int_id
           # Temporary hack to work around regression in 1.9.2;

remove
# begin/rescue clause in later versions
rescue RuntimeError
int_id
end
end

      @text_box1 = finder.call("text_box1")
      @text_box1.extend(CaseChangeTextCtrl1)
      @upper_bt = finder.call("upper_bt")
      @lower_bt = finder.call("lower_bt")
      @text_box2 = finder.call("text_box2")
      @text_box2.extend(CaseChangeTextCtrl2) #<<<<< THIS IS THE BAD

LINE THAT CAUSES THE ERROR
if self.class.method_defined? “on_init”
self.on_init()
end
end
end

######## Exercise.rb ########
require ‘rubygems’
require ‘wx’

load in the generated code

require ‘my_frame’

Mix-in for a Wx::TextCtrl

module CaseChangeTextCtrl1

convert all the text in the control to upper case

def upcase!
self.value = self.value.upcase
end

convert all the text in the control to lower case

def downcase!
self.value = self.value.downcase
end
end

Inherit from the generated base class and set up event handlers

class CaseChangeFrame < TextFrameBase
def initialize
super
evt_button(upper_bt) { text_box1.upcase! }
evt_button(lower_bt) { text_box1.downcase! }
end
end

Run the class

Wx::App.run do
CaseChangeFrame.new.show
end

ERROR MESSAGE:

R:\GUI\Practice\Exercise>ruby Exercise.rb
./my_frame.rb:37:in initialize': uninitialized constant TextFrameBase::CaseChangeTextCtrl2(NameError) from Exercise.rb:21:ininitialize’
from Exercise.rb:29:in new' from Exercise.rb:29:inon_init’
from
C:/Ruby187/lib/ruby/gems/1.8/gems/wxruby-2.0.1-x86-mingw32/lib/wx/classes/app.rb:16:in
main_loop' from C:/Ruby187/lib/ruby/gems/1.8/gems/wxruby-2.0.1-x86-mingw32/lib/wx/classes/app.rb:16:inrun’
from Exercise.rb:28

Dont worry. Figured it out. I was writing empty modules for the new
classes, thinking that would suffice as I went along, but I need to put
some placeholder functions into them.

cheers

John