Sign in Join

Live chat for Free Pascal, Lazarus, Delphi and every Pascal programmer.

Mailing lists / lazarus / 2014-03

constructor Create How is it work?

11 messages · 3 people · –

Reply by email Subscribe to this list Your subscription

Read-only archive. Use j and k to move between messages.

FreeMan

Hello,
constructor Create how is work ? In IDE not problem, but In application, form created AOwner not nil, self created, FGrid created, but Self.Parent is NILL ??? Self.left is 0 (not because its 10) all Self.BoundsRect value is 0. Why? for test I added that code to in @EditChange procedure (FGrid.Parent := Self.Parent; this line and later) values is been correct, But in create not work properly. Has any one any idea?
Thank you

type
   TExLookUp = class(TCustomEditButton)
   private
     FGrid: TRxDBGrid;
   Public
     constructor Create(AOwner: TComponent); override;
.....
constructor TExLookUp.Create(AOwner: TComponent);
begin
   inherited Create(AOwner);
   Self.OnChange  := @EditChange;
   FGrid := TRxDBGrid.Create(Self);
   FGrid.Parent  := Self.Parent;
   FGrid.Left  := Self.Left;
   FGrid.Top   := Self.BoundsRect.Bottom-4;
   FGrid.Width := Self.BoundsRect.Right - Self.BoundsRect.Left;

Reply by email

Mattias Gaertner
to FreeMan
Show quoted text 8 lines
Hello, constructor Create how is work ? In IDE not problem, but In application, form created AOwner not nil, self created, FGrid created, but Self.Parent is NILL ??? Self.left is 0 (not because its 10) all Self.BoundsRect value is 0. Why? for test I added that code to in @EditChange procedure (FGrid.Parent := Self.Parent; this line and later) values is been correct, But in create not work properly. Has any one any idea?

A control is created like this:

ExLookUp1:=TExLookUp.Create(Form1);
with ExLookUp1 do begin
  Name:='ExLookUp1';
  Parent:=Form1;
  Left:=10;
  Top:=15;
  ...
end;

The order of setting properties is arbitrary. Your component should work with any order. Keep in mind that properties might be set multiple times.

Show quoted text 9 lines
constructor TExLookUp.Create(AOwner: TComponent); begin inherited Create(AOwner); Self.OnChange := @EditChange; FGrid := TRxDBGrid.Create(Self); FGrid.Parent := Self.Parent; FGrid.Left := Self.Left; FGrid.Top := Self.BoundsRect.Bottom-4; FGrid.Width := Self.BoundsRect.Right - Self.BoundsRect.Left;

Instead of fixed values you can define rules:

FGrid.AnchorParallel(akLeft,0,Self);
FGrid.AnchorParallel(akRight,0,Self);
FGrid.AnchorParallel(akTop,4,Self);

This way whenever the TExLookUp is resized the FGrid is resized as well.

See
http://wiki.lazarus.freepascal.org/Autosize_/_Layout

Mattias

Reply by email

FreeMan
to Mattias Gaertner

ExLookUp1:=TExLookUp.Create(Form1); This is for manual creating, I'm talk about, I'm designing in IDE, 1-2 TExLookUp on form, and run my application, TExLookUp is class(TCustomEditButton) so Edit and button is shown on where I put on form, in designtime IDE.

constructor TExLookUp.Create(AOwner: TComponent);
begin inherited Create(AOwner);
   Self.OnChange := @EditChange;
   FGrid := TRxDBGrid.Create(Self);
   FGrid.Parent := Self.Parent;
   FGrid.Left := Self.Left;
   FGrid.Top := Self.Heigh + 10;
   FGrid.Width := 150;
   FGrid.visible := False;
...
set FGrid.visible := False; FGrid not visible, same where in component,
example in TExLookUp.OnClick event writen this code
"FGrid.visible := True;" and while application running, user click button,
  FGrid not visible, Because in create "FGrid.Parent := Self.Parent;"
and FGrid=nil, has not parent and FGrid not showing.
FGrid.Left=0 and
FGrid.Top=10

similar problem, when I porting component, Main component has maybe more 10 class create in Main created procedure.Huge class not created and other class has need some property from huge class, but huge class not created and accesses volation error generated, I fixed that, I added "if assigned()then" this is runaway from problem just, not mean fixed

another problem same on porting:
(not clearly analysis) another create problem:
TxItem = class(TCollectionItem)
....
constructor Tx.Create(Collection: TCollection);
begin

   inherited Create(Collection);

.....
FName := 'XItem' + IntToStr(Index); --> FName is Item's name, TCollection.Index is always 0(zero). Collection has to added so it has a index number from TCollectionItem, but not known.

The order of setting properties is arbitrary. Your component should work with any order.

Sorry, but I'm scared this answer, because nothing my under control

04-03-2014 12:10 tarihinde, Mattias Gaertner yazd?:

Show quoted text 24 lines
ExLookUp1:=TExLookUp.Create(Form1); with ExLookUp1 do begin Name:='ExLookUp1'; Parent:=Form1; Left:=10; Top:=15; ... end; The order of setting properties is arbitrary. Your component should work with any order. Keep in mind that properties might be set multiple times. > constructor TExLookUp.Create(AOwner: TComponent); > begin > inherited Create(AOwner); > Self.OnChange := @EditChange; > FGrid := TRxDBGrid.Create(Self); > FGrid.Parent := Self.Parent; > FGrid.Left := Self.Left; > FGrid.Top := Self.BoundsRect.Bottom-4; > FGrid.Width := Self.BoundsRect.Right - Self.BoundsRect.Left; Mattias

Reply by email

Mattias Gaertner
to FreeMan
ExLookUp1:=TExLookUp.Create(Form1); This is for manual creating,

I showed you the corresponding code on how a designed component is created, so you can see the order.

Show quoted text 14 lines
I'm talk about, I'm designing in IDE, 1-2 TExLookUp on form, and run my application, TExLookUp is class(TCustomEditButton) so Edit and button is shown on where I put on form, in designtime IDE. constructor TExLookUp.Create(AOwner: TComponent); begin inherited Create(AOwner); Self.OnChange := @EditChange; FGrid := TRxDBGrid.Create(Self); FGrid.Parent := Self.Parent; FGrid.Left := Self.Left; FGrid.Top := Self.Heigh + 10; FGrid.Width := 150; FGrid.visible := False;

I now see, that you are creating the Grid as neighbor of TExLookUp. Then my prior mail was wrong and you can use the following rules to position the FGrid below TExLookUp:

FGrid.AnchorParallel(akLeft,0,Self);
FGrid.AnchorParallel(akRight,0,Self);
FGrid.AnchorToNeighbour(akTop,0,Self);

Keep in mind that Parent is not yet set in the constructor. You should override the method SetParent, so that each time ExLookUp.Parent is changed the FGrid.Parent is changed as well.

Show quoted text 5 lines
[...] > The order of setting properties is arbitrary. Your component should work > with any order. Sorry, but I'm scared this answer, because nothing my under control

It means for example

Left:=3;
Width:=10;

or

Width:=10;
Left:=3;

or

Left:=30;
Width:=10;
Left:=3;

Writing a control that works in others people programs is more complicated. You need to override more methods.

Mattias

Reply by email

FreeMan
to Mattias Gaertner

I useto other pascal, Its like a treeview
root --> TForm or Tdatamodule
Node -> parent always there
I mean before node create, owner(parent) created, everything finished, loaded properties from Tform etc, its ready to work alone, then jump to child, and if there is child jump bla bla
I understood please don't tell me, this is lazarus not "antique Hellenic city name" :)

Thank you for explain Mattias

04-03-2014 17:37 tarihinde, Mattias Gaertner yazd?:

Show quoted text 18 lines
I now see, that you are creating the Grid as neighbor of TExLookUp. Then my prior mail was wrong and you can use the following rules to position the FGrid below TExLookUp: FGrid.AnchorParallel(akLeft,0,Self); FGrid.AnchorParallel(akRight,0,Self); FGrid.AnchorToNeighbour(akTop,0,Self); Keep in mind that Parent is not yet set in the constructor. You should override the method SetParent, so that each time ExLookUp.Parent is changed the FGrid.Parent is changed as well. Writing a control that works in others people programs is more complicated. You need to override more methods. Mattias

Reply by email

Mattias Gaertner
to FreeMan
Show quoted text 6 lines
I useto other pascal, Its like a treeview root --> TForm or Tdatamodule Node -> parent always there I mean before node create, owner(parent) created, everything finished, loaded properties from Tform etc, its ready to work alone, then jump to child, and if there is child jump bla bla

I'm not sure what you mean.

You have to distinguish "Parent" property and the parent instance. The parent instance exists before the children are created. But the child is created before its properties are set.

And yes, this is Delphi compatible.

Mattias

Reply by email

Hans-Peter Diettrich
to FreeMan: ExLookUp1:=TExLookUp.Create(Form1); This is for manual creating, I'm talk about, I'm…
Show quoted text 8 lines
ExLookUp1:=TExLookUp.Create(Form1); This is for manual creating, I'm talk about, I'm designing in IDE, 1-2 TExLookUp on form, and run my application, TExLookUp is class(TCustomEditButton) so Edit and button is shown on where I put on form, in designtime IDE. constructor TExLookUp.Create(AOwner: TComponent); begin inherited Create(AOwner); Self.OnChange := @EditChange;

set more Self properties here!

Show quoted text 7 lines
FGrid := TRxDBGrid.Create(Self); FGrid.Parent := Self.Parent; FGrid.Left := Self.Left; FGrid.Top := Self.Heigh + 10; FGrid.Width := 150; FGrid.visible := False; ...

Please remember that you are in the TExLooUp constructor. Finish initialization of this component, before assigning Self.whatever to the FGrid.

When the TExtLookUp is initialized from the form resource, you have to wait until this has been done. In this case I'd move the FGrid related part into the TExLookUp.OnCreate handler, which AFAIK is called *after* the TExtLookUp has been created and fully initialized.

Or put the code into ExtLookUp.SetParent, as Mattias suggests. But this solution depends on the order, how the TExtLookUp properties are initialized from the form resource. When Parent is set before Left, Height etc., this solution doesn't work either.

DoDi

Reply by email

FreeMan
to Hans-Peter Diettrich

DoDi Thank you very much, You explain much better then me :) Main problem constructor not finished construction, I mean how to handle Self(TExLookUp) construction is finished? I have to wait, when self(TExLookUp) has created, and load self's properties loaded from, form resources (from .lfm) , then I can to use TExLookUp's properties, for child control, or some one else
I need similar a "TExLookUp.creatED" event, so I can now, class created and ready for use. This is not importend just my this component, other example,
was write previous message:

   TxItem = class(TCollectionItem)
   FName : string;
   property Name : string read Fname write Fname;
....
constructor Tx.Create(Collection: TCollection);
begin
   inherited Create(Collection);
.....
FName := 'XItem' + IntToStr(Index); --> FName is Item's name,
TCollection.Index is always 0(zero). Collection added, so it has a index
number from TCollectionItem, but TCollection not known this. I need
unique FName, and "Index" property. I can get index if TCollection.CreatED;

@DoDi: "TExLookUp.OnCreate handler" how to add this? if add it my self, where to triggered or its just example
"AFAIK" what mean this word? english is not mine language, I'm using dictionary while writeing message.
Thank you

I hope I can translate my problem about create method

05-03-2014 08:29 tarihinde, Hans-Peter Diettrich yazd?:

Show quoted text 28 lines
> constructor TExLookUp.Create(AOwner: TComponent); > begin inherited Create(AOwner); > Self.OnChange := @EditChange; set more Self properties here! > FGrid := TRxDBGrid.Create(Self); > FGrid.Parent := Self.Parent; > FGrid.Left := Self.Left; > FGrid.Top := Self.Heigh + 10; > FGrid.Width := 150; > FGrid.visible := False; > ... Please remember that you are in the TExLooUp constructor. Finish initialization of this component, before assigning Self.whatever to the FGrid. When the TExtLookUp is initialized from the form resource, you have to wait until this has been done. In this case I'd move the FGrid related part into the TExLookUp.OnCreate handler, which AFAIK is called *after* the TExtLookUp has been created and fully initialized. Or put the code into ExtLookUp.SetParent, as Mattias suggests. But this solution depends on the order, how the TExtLookUp properties are initialized from the form resource. When Parent is set before Left, Height etc., this solution doesn't work either. DoDi

Reply by email

FreeMan
to Mattias Gaertner

Yes, One moretime, all woit goes to Mattias, :)
I'm still not useto lazarus style code structure. Ancestor component, trigger when finish initialization self, this mean (for me) I have to sparate my code.
in

  constructor TExLookUp.Create;
  FGrid := TRxDBGrid.Create(Self);
   FGrid.Visible    := False;
   FGrid.DataSource := FListField.DataSource;

.....
set FGrid.xxx properies, not get parent's (TExLookUp) properties. TExLookUp.Left, TExLookUp.Top etc

procedure TExLookUp.Loaded;
begin
   inherited Loaded;
// Now TExLookUp.xx is ready for getting properties
   FGrid.Left  := Self.Left;
   FGrid.Top   := Self.BoundsRect.Bottom-2;
   FGrid.Width := Self.BoundsRect.Right - Self.BoundsRect.Left +
Self.ButtonWidth;
   FGrid.Parent := Self.Parent;
end;

I did, I tested, and thats okey now.

Thank you,

05-03-2014 14:12 tarihinde, Mattias Gaertner yazd?:

Show quoted text 7 lines
[...] I have to wait, when self(TExLookUp) has created, and load self's properties loaded from, Override method Loaded. Mattias

Reply by email

Hans-Peter Diettrich
to FreeMan: DoDi Thank you very much, You explain much better then me :) Main problem constructor not…
Show quoted text 8 lines
DoDi Thank you very much, You explain much better then me :) Main problem constructor not finished construction, I mean how to handle Self(TExLookUp) construction is finished? I have to wait, when self(TExLookUp) has created, and load self's properties loaded from, form resources (from .lfm) , then I can to use TExLookUp's properties, for child control, or some one else I need similar a "TExLookUp.creatED" event, so I can now, class created and ready for use.

Right. Perhaps Loaded() is what we are looking for. Override it in your component and add the creation of the other control to it.

@DoDi: "TExLookUp.OnCreate handler" how to add this? if add it my self, where to triggered or its just example
Add you handler to the component, and in the constructor install it:
   OnCreate := @MyOnCreateHandler;
"AFAIK" what mean this word? english is not mine language, I'm using dictionary while writeing message.

As Far As I Know

DoDi

Reply by email