BorlandTalk.com Forum Index BorlandTalk.com
Borland discussion newsgroups
 
Archives   FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

TMemo parent problem

 
Post new topic   Reply to topic    BorlandTalk.com Forum Index -> C++ Builder (VCL Components Development)
View previous topic :: View next topic  
Author Message
David
Guest





PostPosted: Fri Jun 23, 2006 5:05 am    Post subject: TMemo parent problem Reply with quote



Hi,

I am having yet another problem with Borland Builder. Web searches on an
answer are not bringing much joy.
I have a normal Borland form that contains a TPanel (named Panel) and the
constuctor coded thus:

__fastcall TMyForm::TMyForm(TComponent* Owner)
: TForm(Owner)
{
mem =new TMemo(Panel);
mem->Parent=Panel;
mem->Lines->Strings[0]="testing";

// /*MyClass2* */ myClass2 = new MyClass2(this);

}


This works fine. The word "testing" shows as you would expect it to. Next I
have a class that inherits from TPanel and called from the constuctor of the
previous class previous with the following consturctor:


__fastcall MyClass2::MyClass2(TComponent* Owner) : TPanel(Owner)
{

TMemo* mem =new TMemo(this);
mem->Parent=this;
mem->Lines->Strings[0]="testing";
delete mem;
}


But here I get an error ...EInvalidOperation with message 'Control '' has no
parent window'... at the point of "mem->Lines->Strings[0]="testing";"
when the code is run. The code compiles without any problems.
I have tried various things such as use TForm* in place of TComponent* in
the constructor definition and used Owner in place of 'this' when creating
'mem'. I get the same error every time. I have come to the conclusion that
an instance of TMemo cannot be created in any class that itself is not
derived from TForm. Is this a correct assumption, or am I simply missing the
point somewhere.
Back to top
Remy Lebeau (TeamB)
Guest





PostPosted: Fri Jun 23, 2006 5:09 am    Post subject: Re: TMemo parent problem Reply with quote



"David" <dbai7864 (AT) bigpond (DOT) net.au> wrote in message
news:449b2c9e$1 (AT) newsgroups (DOT) borland.com...

Quote:
mem =new TMemo(Panel);
mem->Parent=Panel;
mem->Lines->Strings[0]="testing";

Your memo is Empty when you create it. You can't access strings that do not
exist. To add new strings to it, use the Add() method instead, ie:

mem->Lines->Add("testing");

Or use the Text property:

mem->Text = "testing";

Quote:
Next I have a class that inherits from TPanel and called from
the constuctor of the previous class previous with the following
consturctor:


Quote:
But here I get an error ...EInvalidOperation with message 'Control ''
has no parent window'.

The error is self-explanatory. You tried to do something that required a
Parent window be present, but there was no Parent available. In this case,
the TMyClass constructor is trying to access the Memo before the myClass2
instance's Parent property had been set. You need to set the Parent for a
child component before it can do anything that requires a valid Handle,
since the Parent is needed to initialize the Handle properly.

Quote:
I have come to the conclusion that an instance of TMemo cannot
be created in any class that itself is not derived from TForm.

Yes, it can. You are simply trying to access the contents of the Memo too
early. In order for the Memo's Handle to be created, the Memo has to have a
Parent, and the Parent has to already have a Parent, and so on until the
top-level TForm is reached, since a TForm does not (usually) have a Parent
of its own.


Gambit
Back to top
JD
Guest





PostPosted: Fri Jun 23, 2006 5:19 am    Post subject: Re: TMemo parent problem Reply with quote



"David" <dbai7864 (AT) bigpond (DOT) net.au> wrote:
Quote:

[...] I have come to the conclusion that an instance of
TMemo cannot be created in any class that itself is not
derived from TForm.

Just let MyClass finish construction before you assign the
Lines. This can be accomplished by posting a custom message
in it's ctor and by overriding it's WndProc method to
intercept the message. For example:

#define UWM_INITIALIZE (WM_USER + 100)
//-------------------------------------------------------------
class MyClass2 : public TPanel
{
typedef inherited TPanel;
....
private:
TMemo* mem;
protected:
virtual void __fastcall WndProc( TMessage &Message );
....
}
//-------------------------------------------------------------
__fastcall MyClass2::MyClass2(TComponent* Owner) : TPanel(Owner)
{
mem =new TMemo(this);
mem->Parent=this;
::PostMessage( Handle, UWM_INITIALIZE, 0, 0 );
}
//-------------------------------------------------------------
void __fastcall MyClass2::WndProc( TMessage &Message )
{
if( Message.Msg == UWM_INITIALIZE )
{
mem->Lines->Strings[0]="testing";
}
inherited::WndProc( Message );
}
//-------------------------------------------------------------

Note that I did not delete the TMemo. That's because it was
assigned an Owner and the rules are that when an object is
destroyed, all of the objects that it ownes are also destroyed.

~ JD
Back to top
JD
Guest





PostPosted: Fri Jun 23, 2006 5:21 am    Post subject: Re: TMemo parent problem Reply with quote

"Remy Lebeau \(TeamB\)" <no.spam (AT) no (DOT) spam.com> wrote:
Quote:

mem->Lines->Strings[0]="testing";

Your memo is Empty when you create it. You can't access strings that do not
exist.

Good catch ... missed that one.

~ JD
Back to top
Remy Lebeau (TeamB)
Guest





PostPosted: Fri Jun 23, 2006 5:26 am    Post subject: Re: TMemo parent problem Reply with quote

"JD" <nospam (AT) nospam (DOT) com> wrote in message
news:449b33ac$1 (AT) newsgroups (DOT) borland.com...

Quote:
Just let MyClass finish construction before you assign the
Lines. This can be accomplished by posting a custom
message in it's ctor and by overriding it's WndProc method
to intercept the message.

That won't work. Posting a message requires a valid Handle to post to. A
Parent is needed in order to create that Handle. Which is exactly why
David's code is failing in the first place - accessing the Lines requires a
valid Handle, which cannot be created in the constructor because no Parent
has been assigned yet. Which is why your code will also fail - your
MyClass2 instance does not have a Parent assigned yet when you try to access
its Handle in the constructor.


Gambit
Back to top
David Bailey
Guest





PostPosted: Fri Jun 23, 2006 7:10 am    Post subject: Thankyou Reply with quote

Thankyou, thankyou, thankyou, thankyou, thankyou, thankyou, thankyou...

Thankyou to you both. I needed to set the Parent's Parent. Just need to go
though the code and do some clean up, but initial tests showed that it'll
work

Regards,
David
Back to top
JD
Guest





PostPosted: Fri Jun 23, 2006 1:12 pm    Post subject: Re: TMemo parent problem Reply with quote

"Remy Lebeau \(TeamB\)" <no.spam (AT) no (DOT) spam.com> wrote:
Quote:

That won't work. [...]

It does.

~ JD
Back to top
Remy Lebeau (TeamB)
Guest





PostPosted: Fri Jun 23, 2006 3:25 pm    Post subject: Re: TMemo parent problem Reply with quote

"JD" <nospam (AT) nospam (DOT) com> wrote in message
news:449ba25b$1 (AT) newsgroups (DOT) borland.com...

Quote:
It does.

As I explained earlier, the Handle property is not valid inside the
constructor without a Parent being assigned first. TWinControl::CreateWnd()
throws an exception if a Parent is not assigned yet - which is exactly what
was happening in David's code. The *only* possibility of the Handle being
valid in the constructor is if the class is instantiated by the DFM
streaming, in which case the Owner is used as the Parent window in
CreateWnd(). If the class is not created during DFM streaming, then the
Parent is required.


Gambit
Back to top
Display posts from previous:   
Post new topic   Reply to topic    BorlandTalk.com Forum Index -> C++ Builder (VCL Components Development) All times are GMT
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2006 phpBB Group
SEO toolkit © 2004-2006 webmedic.