Dialog in Dialog
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 08:01, xxxxxxxx wrote:
Yeah. That sounds similar to Robert's Init() method recommendation.
But I just can't get it to work. It crashes on me.Here's an example:
class myDialog : public GeDialog { private: SubDialog1 *dlg; LONG rows; public: myDialog(void); Bool Init(); virtual Bool CreateLayout(void); virtual Bool InitValues(void); virtual Bool Command(LONG id,const BaseContainer &msg); virtual LONG Message(const BaseContainer &msg,BaseContainer &result); virtual Bool CoreMessage (LONG id,const BaseContainer &msg); }; myDialog::myDialog(void) { rows = 1; dlg = NULL; } Bool myDialog::Init() { dlg = gNew SubDialog1; if (!dlg) return FALSE; return TRUE; } /////////////// My Command method /////////// Bool myDialog::Command(LONG id,const BaseContainer &msg) { if(1002) //If the button is pressed..open the subdialog { dlg->Open(DLG_TYPE_MODAL_RESIZEABLE, SUB_PLUGIN_ID); } return TRUE; } }
I don't know what I'm doing wrong.
But boy.. it crashes very badly.-ScottA
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 12:31, xxxxxxxx wrote:
Hi Scott,
I think I found the culprit.
Please try one of the following:- Don't use a SubDialog1 pointer, but rather make a member an instance od SubDialog1, by changing:
SubDialog1 *dlg;
into
SubDialog1 dlg;
Then of course you need to use . instead of -> in Command().
This has the advantage, that you don't need to care to free the dialog, which you need to pay attention to in 2).
2) Don't create your SubDialog1 in Init() but rather in the constructor, like so:myDialog::myDialog(void) { rows = 1; dlg = gNew SubDialog1; if (!dlg) return; // Note not sure, what to do here, if it fails... }
At least this does the trick here (although I have to admit, I did use DLG_TYPE_ASYNC for testing). Not sure if it's a good idea to open a modal dialog from Command()...
And to be honest, I also don't understand, why your method does not work from Init(), but I remember having trouble with Init() as well in another context. Perhaps Matthias or Yannick can give us some inside view on Init()?
[edit] Just did another test, and I really don't get it, why Init() does not work. It seems to be called right after the constructor (as we expected). I fear, I'm missing something big in here as well...Hope it works for you as well,
Andreas -
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 13:20, xxxxxxxx wrote:
Thanks a ton! Works like a charm.
This stupid thing was driving me absolutely crazy.I read in another post a comment that using a modal dialog we don't have to use a second pluginID. But I'm not sure if that applies to what we're doing here or not. I can't seem to get it to work if I call the second dialog with same pluginID.
It would be nice to know more about this. And maybe Robert will pop in here at some point and offer more info about how to use an Init() function.
But even if he doesn't. I'm happy enough with the way I've got it set up and working now with your help.Cheers,
-ScottA -
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 13:58, xxxxxxxx wrote:
Doh!
Foiled again.After testing it some more. This isn't going to work.
The dialog pops up when a gizmo is used in the main dialog.
I'm pretty sure this is why Robert was talking about using an Init() function.Still looking for a solution.
-ScottA
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 14:24, xxxxxxxx wrote:
You mean it pops up, even if the open function is not called?
I'll try to reproduce it tomorrow. -
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 14:28, xxxxxxxx wrote:
Yeah.
Any gizmo activity in the Command() method of the main dialog makes it open. Which is very bad.-ScottA
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 14:51, xxxxxxxx wrote:
First, you should never allocate memory in a constructor as the behavior is unpredictable (there is no return path for failure). myDialog->Init() must be called after the creation of your dialog in order to ensure that the subdialog is created for later use.
Second, you should check that the SubDialog was created even in later calls (in Command(), for instance) :
/////////////// My Command method /////////// Bool myDialog::Command(LONG id,const BaseContainer &msg) { if(1002) //If the button is pressed..open the subdialog { if (dlg && !dlg->IsOpen()) dlg->Open(DLG_TYPE_MODAL_RESIZEABLE, SUB_PLUGIN_ID); } return TRUE; } }
Third, SubDialogs must be attached to the dialog (GeDialog) using AttachSubDialog() if you are adding it as a control element of the dialog (AddSubDialog()).
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 16:10, xxxxxxxx wrote:
Hi Robert,
Thanks for popping in. But I'm afraid you've lost me.I don't know where you're expecting me to call the Init() method. Or how.
I don't understand what you're talking about with AttachSubDialog(). This is not a subdialog. It's a dialog within a dialog.
Are you saying that I need to use the same kind of code for this as they use to create subdialogs?I don't think I'm going to be able follow all the things you're talking about without looking at a simple working example. And studying how everything works.
Just a very simple example of a dialog with a button in it that opens another dialog that has maybe just a textbox and a close button in it. That's it.What can I do to make this example happen?
Can I send you something? My plugin code?
These little hints you're dropping just aren't enough for me to figure it out. They just leave me confused with more questions.-ScottA
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 18:12, xxxxxxxx wrote:
If you create the GeDialog using gNew then call Init() after that:
myDialog* mydlg; // As a member of some class
mydlg = gNew myDialog;
if (!mydlg) return FALSE;
if (!mydlg->Init()) return FALSE; // subdialog failed to allocateIf you declare your myDialog as an instance of another class then you should call the Init() at some initialization of that other class. Hard to say without seeing code. If there is no other class then you will need to initialize it in your main.cpp.
A BIG note about dialogs: You really don't need to use SubDialog for opening new dialogs from a dialog (synchronous or not). SubDialogs are for attaching a bunch of GUI elements directly to the GUI of a GeDialog. You can open new dialogs from a GeDialog as GeDialogs (and, yes, that means you can open a dialog from a dialog opened from another dialog ad infinitum). Maybe that is where your problem lies : you are trying to treat a SubDialog which needs to show up inside your Dialog as a new separate Dialog. That is not the purpose of a SubDialog. Use GeDialog instead.
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 19:57, xxxxxxxx wrote:
Thanks Robert,
But I'm afraid I don't have enough knowledge to apply what you're saying.I understand most of it in theory.
But I have too many "what goes where" questions about creating the framework for the classes and methods.
Without a working example to learn from. I'm not going to be able to figure this one out just from hints & tips.Thanks for the help,
-ScottA -
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 14/03/2012 at 23:11, xxxxxxxx wrote:
Hi,
of course Robert is right about allocation in a constructor (and about testing for NULL pointer in Command()). So at first forget my 2) version and rather stick with the 1). Then I'm not sure, if Robert realized, that your SubDialog1 is no subdialog, but rather a normal GeDialog (which confused me in my first post as well). At least that's what his explanations about AttachSubdialog() suggest.
I get confused about the manual Init() call, Robert talks about. I thought this was implicitly done for classes derived from e.g. GeDialog. But if it's not, this might be one of our problems with Init(), but I doubt that this is a problem with your SubDialog1 opening on any "Command()" interaction.
I'll do some testing this evening and try to see, if I can get it to work.Another slightly off topic question:
I'm thinking about a GoogleCode (or SourceForge or what not) project, where we could share such examples and could actively work on such problems together. This would make it easier to understand some problems (as there would be the complete source for a problem) and several people could actively add in or optimize. A bit like the SDK examples... I have s slight feeling, that SVN (or CVS or GIT) usage () is not so common or popular in this community, but I'd happily stand aside to get everyone going. And don't fear, I'm not suggesting to open up your plugin development. Just these small code snippets we're discussing here, could be administered and collected in one common place in a somewhat enhanced manner.
I certainly don't want to counter spedler's great work of examples on Microbion's site, but perhaps he would like to contribute to such a project, too.
I'd also ask this question more prominently in a separate thread, but for now, I'd be interested in your opinions first.If there's some positive feedback, I'd set up such a project and would add this issue here as a starting point.
Regards,
Andreas -
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 15/03/2012 at 06:52, xxxxxxxx wrote:
Originally posted by xxxxxxxx
Without a working example to learn from. I'm not going to be able to figure this one out just from hints & tips.Thanks for the help,-ScottA
Here you go Scott. A bare-bones example of how to open one dialog from another. Should just compile and run.
Download the archive with source and resource files here.
Steve
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 15/03/2012 at 08:26, xxxxxxxx wrote:
You're a life saver Steve.
Thank you.Working examples are the very best way to communicate ideas with other people. Especially with C++ freshman like me. Who aren't quite as strong with the lingo sometimes.
So anything you guys do that ends up in more examples being available would be a wonderful thing.Instead of "Show me money". My catch phrase is "Show me the code".
-ScottA
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 15/03/2012 at 09:56, xxxxxxxx wrote:
One last question Steve,
I'm trying to figure out how to make these two dialogs communicate with each other.
I have a EditText() gizmo in the main dialog. And a EditText() gizmo in the secondary dialog.
What I'm trying to do is type something in the secondary dialog's texbox. Then when it closes it updates the textbox in the main dialog.I had thought I could do it like this: dlg_2nd.GetLong(IDC_EDIT1);
But that doesn't work. It only works to open the second dialog.How do I get two different dialogs. That each have their own resources. To communicate with eachother?
-ScottA
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 15/03/2012 at 16:31, xxxxxxxx wrote:
A quick and dirty way to do this would be to create a class-level public variable in the secondary dialog that would hold the string from the text box in the secondary dialog. Then when the secondary dialog closes, copy the text from the edit box into this variable.
Back in the main dialog, just read the value of that variable and copy it into the edit box you have there. Code goes something like this:
// in secondarydialog.h: class SecondaryDialog : public GeModalDialog { public: String textLine; // then the rest of the functions as before }; // in secondarydialog.cpp Bool SecondaryDialog::Command(LONG id, const BaseContainer &msg;) { switch (id) { case IDC_BUTTON_CLOSE_2ND: GetString(IDC_EDIT1, textLine); Close(TRUE); return TRUE; break; } } // in maindialog.cpp Bool MainDialog::Command(LONG id, const BaseContainer &msg;) { switch(id) { // open secondary dialog case IDC_BUTTON_OPEN_2ND: dlg_2nd.Open(); SetString(IDC_YOUREDITBOX, dlg_2nd.textLine); break; } return TRUE; }
Note that this works fine here because the secondary dialog is modal, so the call to dlg_2nd.Open() doesn't return until dlg_2nd closes. Handling this communication for two non-modal dialogs would be different (and harder). But it could be done.
Steve
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 15/03/2012 at 17:12, xxxxxxxx wrote:
Works good.
Thanks for taking the time to help me with this. I know you're busy with other things.
You've been a big help.-ScottA
-
THE POST BELOW IS MORE THAN 5 YEARS OLD. RELATED SUPPORT INFORMATION MIGHT BE OUTDATED OR DEPRECATED
On 16/03/2012 at 04:54, xxxxxxxx wrote:
No problem Scott. Glad to be of help.
Steve