Discussion:
XRC-related question
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
Hi,

I have an XRC file (attached) created with wxGlade. There are two
issues with this I cannot seem to solve... Here's what I do with the
XRC:

DGVMessageDialogMetVinkjePresenter >>view
| res |
view ifNil: [
res := WxXmlResource new.
res initAllHandlers.
res loadFromString: self class resourceText.
view := res loadObject: nil name: 'dialog_1' className: 'wxDialog'.
res destroy].
^view

DGVMessageDialogMetVinkjePresenter >>connectView
| messageField |
messageField _ self view findWindowByName: 'message'.
messageField setLabel: 'this is a test. It is a bit longer than a
single line, so we can check whether this is really a good idea,
you know the painting and stuff...'.

okButton _ self view findWindowByName: 'okButton'.
okButton on: #wxEvtCommandButtonClicked send: #okButtonClicked: to: self.

self view getSizer setSizeHints: self view

Test code:
dlg _ DGVMessageDialogMetVinkjePresenter new.
dlg connectView.
dlg view showModal

Two things don't really work out right. In wxGlade, on the sizer
there's a button "fit parent". It will resize the dialog according to
whatever label you've set on the message field. If tried different
things here (the #setSizeHints: being the last attempt), but I cannot
seem to get the dialog to resize around the text. Further, my
#okButtonClicked: never triggers....

Is there anything I'm missing? Generally or XRC related? This is my
first attempt at using XRC, being fed up with creating handcoded
#createView methods :)

TIA,

Cees
-------------- next part --------------
A non-text attachment was scrubbed...
Name: DGVMessageDialogMetVinkjePresenter.xrc
Type: application/octet-stream
Size: 1795 bytes
Desc: not available
Url : http://lists.squeakfoundation.org/pipermail/wxsqueak/attachments/20050726/6dd62069/DGVMessageDialogMetVinkjePresenter.obj
Rob Gayvert
2006-07-19 15:18:02 UTC
Permalink
Hi Cees,

The main problem here is that I haven't added all of the hooks you need
to make this easy.
If you look at WxTopLevelPresenter>>restoreView, you'll see that after
#loadFromXRC:,
the view and its children need to be "registered". If they're not, then
when a callback comes
in, it can't find an object to notify, so the events are just ignored.

For now, give the following a try. When loading the resource, use

view := res loadDialog: nil name: 'dialog_1'.
view registerHandle.
view getAllChildren
do: [:child | child registerHandle].

Also, it doesn't look like #setSizeHints: is sufficient here. Instead, try

self view getSizer layout.

.. Rob
Post by Cees De Groot
Hi,
I have an XRC file (attached) created with wxGlade. There are two
issues with this I cannot seem to solve... Here's what I do with the
DGVMessageDialogMetVinkjePresenter >>view
| res |
view ifNil: [
res := WxXmlResource new.
res initAllHandlers.
res loadFromString: self class resourceText.
view := res loadObject: nil name: 'dialog_1' className: 'wxDialog'.
res destroy].
^view
DGVMessageDialogMetVinkjePresenter >>connectView
| messageField |
messageField _ self view findWindowByName: 'message'.
messageField setLabel: 'this is a test. It is a bit longer than a
single line, so we can check whether this is really a good idea,
you know the painting and stuff...'.
okButton _ self view findWindowByName: 'okButton'.
okButton on: #wxEvtCommandButtonClicked send: #okButtonClicked: to: self.
self view getSizer setSizeHints: self view
dlg _ DGVMessageDialogMetVinkjePresenter new.
dlg connectView.
dlg view showModal
Two things don't really work out right. In wxGlade, on the sizer
there's a button "fit parent". It will resize the dialog according to
whatever label you've set on the message field. If tried different
things here (the #setSizeHints: being the last attempt), but I cannot
seem to get the dialog to resize around the text. Further, my
#okButtonClicked: never triggers....
Is there anything I'm missing? Generally or XRC related? This is my
first attempt at using XRC, being fed up with creating handcoded
#createView methods :)
TIA,
Cees
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
The layout thing indeed fixes it. I've studied the wx docs, but
they're not really clear...

With the #registerHandle stuff, I get better results indeed. Which is
good, because I really like doing layouts with XRC tools a whole lot
better :). Hadn't noticed the XRC support in WxTopLevelPresenter yet,
thanks for bringing my attention to it.
Post by Rob Gayvert
Hi Cees,
The main problem here is that I haven't added all of the hooks you need
to make this easy.
If you look at WxTopLevelPresenter>>restoreView, you'll see that after
#loadFromXRC:,
the view and its children need to be "registered". If they're not, then
when a callback comes
in, it can't find an object to notify, so the events are just ignored.
For now, give the following a try. When loading the resource, use
view := res loadDialog: nil name: 'dialog_1'.
view registerHandle.
view getAllChildren
do: [:child | child registerHandle].
Also, it doesn't look like #setSizeHints: is sufficient here. Instead, try
self view getSizer layout.
.. Rob
Post by Cees De Groot
Hi,
I have an XRC file (attached) created with wxGlade. There are two
issues with this I cannot seem to solve... Here's what I do with the
DGVMessageDialogMetVinkjePresenter >>view
| res |
view ifNil: [
res := WxXmlResource new.
res initAllHandlers.
res loadFromString: self class resourceText.
view := res loadObject: nil name: 'dialog_1' className: 'wxDialog'.
res destroy].
^view
DGVMessageDialogMetVinkjePresenter >>connectView
| messageField |
messageField _ self view findWindowByName: 'message'.
messageField setLabel: 'this is a test. It is a bit longer than a
single line, so we can check whether this is really a good idea,
you know the painting and stuff...'.
okButton _ self view findWindowByName: 'okButton'.
okButton on: #wxEvtCommandButtonClicked send: #okButtonClicked: to: self.
self view getSizer setSizeHints: self view
dlg _ DGVMessageDialogMetVinkjePresenter new.
dlg connectView.
dlg view showModal
Two things don't really work out right. In wxGlade, on the sizer
there's a button "fit parent". It will resize the dialog according to
whatever label you've set on the message field. If tried different
things here (the #setSizeHints: being the last attempt), but I cannot
seem to get the dialog to resize around the text. Further, my
#okButtonClicked: never triggers....
Is there anything I'm missing? Generally or XRC related? This is my
first attempt at using XRC, being fed up with creating handcoded
#createView methods :)
TIA,
Cees
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
Post by Cees De Groot
The layout thing indeed fixes it. I've studied the wx docs, but
they're not really clear...
Post by Rob Gayvert
self view getSizer layout.
Hmm... tried some more, and it's not doing what the 'Fit to parent'
button in wxGlade does. I wonder what code is behind it (probably need
to grab the wxGlade source code for that...)
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
Post by Cees De Groot
Hmm... tried some more, and it's not doing what the 'Fit to parent'
button in wxGlade does. I wonder what code is behind it (probably need
to grab the wxGlade source code for that...)
Ok, two steps gave the solution:
- A multi-line static text needs to be run through 'replaceAll:
Character cr with: Character lf'. Apparently Wx, even though it
displays the CR's correctly, doesn't handle them when calculating
sizes;
- "self view getSizer fit: self view" seems to be necessary before the
call to #layout. Haven't got a clue what it does, I nicked it from the
wxGlade sources.

Got my 'message dialog with check box' component now. And my first XRC UI!
Rob Gayvert
2006-07-19 15:18:02 UTC
Permalink
Post by Cees De Groot
Post by Cees De Groot
Hmm... tried some more, and it's not doing what the 'Fit to parent'
button in wxGlade does. I wonder what code is behind it (probably need
to grab the wxGlade source code for that...)
Character cr with: Character lf'. Apparently Wx, even though it
displays the CR's correctly, doesn't handle them when calculating
sizes;
Yes, I forgot about that. In the demo code you'll see a lot of
references to #crToLf.
Post by Cees De Groot
- "self view getSizer fit: self view" seems to be necessary before the
call to #layout. Haven't got a clue what it does, I nicked it from the
wxGlade sources.
Sizers seem more complicated than necessary, especially with this
fit/layout business. I'm hoping we
can find a way to simplify this.
Post by Cees De Groot
Got my 'message dialog with check box' component now. And my first XRC UI!
Very cool, and definitely a Good Thing.
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
Post by Rob Gayvert
Post by Cees De Groot
Got my 'message dialog with check box' component now. And my first XRC UI!
Very cool, and definitely a Good Thing.
Well, never content to let software just work, I upped the complexity a bit :)

I have painted a XRC with a custom object on it - my particular flavor
of a pluggable list.

WxXmlResourceHandler subclass: #DGVPluggableListXmlResourceHandler ....
canHandle: xmlNode
^self isOfClass: xmlNode classname: DGVPluggableList
doCreateResource

| list |
list := DGVPluggableList ....

and #initializeStyles, and class #new just the same as the sample. The
top-level object I need to get from the XRC is a frame, so:

res := WxXmlResource new.
res initAllHandlers.
res addHandler: DGVPluggableListXmlResourceHandler new.
res loadFromString: self class resourceText.
view _ WxFrame new.
res loadFrame: view parent: nil name: 'frame'.

but this results in a Wx error dialog 'Subclass 'DGVPluggableList' not
found for 'listCtrl', not subclassing!'. So it seems that a step is
missing to register my pluggable list class with Wx or something like
that?

(I like XRC so far. UI's look much better with a bit trial and error
in wxGlade than when you have to manually specify them...)
Rob Gayvert
2006-07-19 15:18:02 UTC
Permalink
Post by Cees De Groot
I have painted a XRC with a custom object on it - my particular flavor
of a pluggable list.
WxXmlResourceHandler subclass: #DGVPluggableListXmlResourceHandler ....
canHandle: xmlNode
^self isOfClass: xmlNode classname: DGVPluggableList
The last argument should be a string ('DGVPluggableList'), but the
wrapper converts it anyway, so it's not really a problem.
Post by Cees De Groot
doCreateResource
| list |
list := DGVPluggableList ....
and #initializeStyles, and class #new just the same as the sample. The
res := WxXmlResource new.
res initAllHandlers.
res addHandler: DGVPluggableListXmlResourceHandler new.
res loadFromString: self class resourceText.
view _ WxFrame new.
res loadFrame: view parent: nil name: 'frame'.
This looks reasonable. The only difference I see between this and my
demo is that the demo uses

res loadObject: self name: 'MyPanel' className: 'WxXmlCustomPanel'.

instead of #loadFrame:parent:name:. But this would be a real pain if
you had to load custom instances that way.
Post by Cees De Groot
but this results in a Wx error dialog 'Subclass 'DGVPluggableList' not
found for 'listCtrl', not subclassing!'. So it seems that a step is
missing to register my pluggable list class with Wx or something like
that?
What does your XRC look like? Does it have a "subclass" attribute? If
so, try removing it -- I think a subclass
attribute requires a subclass factory.
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
Post by Rob Gayvert
The last argument should be a string ('DGVPluggableList'), but the
wrapper converts it anyway, so it's not really a problem.
I know. I like a classname better because of the compiler check.
Post by Rob Gayvert
What does your XRC look like? Does it have a "subclass" attribute? If
so, try removing it -- I think a subclass attribute requires a subclass factory.
Removing it gets rid of the error, but the element is loaded as a
WxListCtrl while I want a DGVPluggableList (ergo, a subclass...)
Rob Gayvert
2006-07-19 15:18:02 UTC
Permalink
Post by Cees De Groot
Post by Rob Gayvert
The last argument should be a string ('DGVPluggableList'), but the
wrapper converts it anyway, so it's not really a problem.
I know. I like a classname better because of the compiler check.
Good point. But I may remove the #asString coercions in the wrappers at
some point (they
may cause more problems than they fix), so you might want to use
something like
"DGVPluggableList asString" instead.
Post by Cees De Groot
Post by Rob Gayvert
What does your XRC look like? Does it have a "subclass" attribute? If
so, try removing it -- I think a subclass attribute requires a subclass factory.
Removing it gets rid of the error, but the element is loaded as a
WxListCtrl while I want a DGVPluggableList (ergo, a subclass...)
So does your XRC look like
<object class="WxListCtrl " name="dialog_1">
or
<object class="DGVPluggableList " name="dialog_1">

I would think the latter would result in your custom handler being called.
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
Post by Rob Gayvert
So does your XRC look like
<object class="WxListCtrl " name="dialog_1">
or
<object class="DGVPluggableList " name="dialog_1">
At the moment it uses the subclass attribute:
<object class="wxListCtrl" name="listCtrl" subclass="DGVPluggableList">
I tried to work according to your xrc subclass demo, but that one
gives the same problem, so... :)

If I make the class a DGVPluggableList, WX doesn't create the instance
- asking for the control by name returns nil.

I was wondering (and that'll be my next try) - what if I just create
the component as a plain list control, and then simply change the
class of the instance after loading... The C++ code couldn't care
less, probably
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
Post by Cees De Groot
I was wondering (and that'll be my next try) - what if I just create
the component as a plain list control, and then simply change the
class of the instance after loading...
Well, that's off as well - Primitive Failed.
Cees De Groot
2006-07-19 15:18:02 UTC
Permalink
http://rubyforge.org/pipermail/wxruby-users/2004-October/000965.html

same for wxSqueak?
Rob Gayvert
2006-07-19 15:18:02 UTC
Permalink
Post by Cees De Groot
http://rubyforge.org/pipermail/wxruby-users/2004-October/000965.html
same for wxSqueak?
Nah -- the demos show this isn't the case. I just tried changing the
StaticText in your XRC sample
to a WxXmlCustomPanel, and added a WxXmlResourceCustomHandler to the
WxXrcViewerDemo
resource, and it creates a dialog with a WxXmlCustomPanel, and goes
through all of the expected
methods.

There may be something different about subclassing WxListCtrl instead of
WxPanel. I'll try a test
with a WxXmlCustomListCtrl instead and see if that works as well.
Rob Gayvert
2006-07-19 15:18:02 UTC
Permalink
An HTML attachment was scrubbed...
URL: http://lists.squeakfoundation.org/pipermail/wxsqueak/attachments/20050727/ae55cff7/attachment.htm
Loading...