Recent

Author Topic: Issues with subclass creation  (Read 34012 times)

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #30 on: February 06, 2014, 01:38:01 pm »
Quote
Maybe you want to check that.

Thanks again, engkin


 

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #31 on: February 09, 2014, 11:11:36 am »
Testing different LCL components for my new controls, I think that I found a bug in TGroupBox . This control has a "Caption" (for the text) and  "Font" for the type of  font in the text of Caption. Well, you can changes the color of the font and the control doesn't change the font color

I've tested different controls, and only this one doesn't works properly.

Is this a bug ? Where should  I notify the problem for fixing?
 

It happen in 1.0.14 and 1.2RC2  version

Regards

howardpc

  • Hero Member
  • *****
  • Posts: 4144
Re: Issues with subclass creation
« Reply #32 on: February 09, 2014, 01:41:22 pm »

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #33 on: February 09, 2014, 02:13:57 pm »
Thanks, howardpc

Additional testing:  Linux version  works properly.  Only Windows versions are wrong

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #34 on: February 16, 2014, 04:24:25 pm »
New Issue!!

 I've put together three TLabeledEdit Controls plus a Tlabel, inside Tpanel control. I've called the new control, TPanelG3

That is the code:
Code: [Select]
unit PanelG3;

{$mode objfpc}{$H+}

interface

uses
  Classes, SysUtils, LResources, Forms, Controls, Graphics, Dialogs, ExtCtrls, StdCtrls;

type

  TPanelG3 = class(TPanel)
  private
    { Private declarations }
    FControlX                                 : TLabeledEdit;
    FControlY                                 : TLabeledEdit;
    FControlZ                                 : TLabeledEdit;
    FControlLabel                             : TLabel;
  protected
    { Protected declarations }
  public
    { Public declarations }
    constructor Create(AOwner : TComponent) ;   override;
    destructor  Destroy;                        override;
  //      property ControlX: TLabeledNumberEdit read FControl1;
  //      property ControlY: TLabeledNumberEdit read FControl2;
  //     property ControlZ: TLabeledNumberEdit read FControl3;
  published
    { Published declarations }
    property ControlX: TLabeledEdit read FControlX;
    property ControlY: TLabeledEdit read FControlY;
    property ControlZ: TLabeledEdit read FControlZ;
    property ControlLabel: TLabel read FControlLabel;
  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('Standard',[TPanelG3]);
end;

constructor TPanelG3.Create(AOwner : TComponent);
begin      (* Parametros iniciales de Provisional*)
   inherited Create (AOwner);
   Height := 136;
   Width := 176;
   ClientHeight := 132;
   ClientWidth := 172;
   Constraints.MaxHeight:=136;
   Constraints.MaxWidth :=176;
   Constraints.MinHeight:=136;
   Constraints.MinWidth :=176;
   Align := alCustom;
   BevelInner := bvLowered;
   BevelOuter := bvLowered;
   BorderStyle := bsSingle;
   (* FControlX - Parametros iniciales del PRIMER Subcontrol dentro de TGRoupBox*)
   FControlX:= TLabeledEdit.Create(Self);
   FControlX.Parent:= Self;
   FControlX.SetSubComponent(true);
   FControlX.ControlStyle := FControlX.ControlStyle - [csNoDesignSelectable];
   FControlX.Name := 'X';
   FControlX.Left := 36;
   FControlX.Height := 23;
   FControlX.Top := 20;
   FControlX.Width := 130;
   (* FControlY - Parametros iniciales del SEGUNDO Subcontrol dentro de TGRoupBox*)
   FControlY:= TLabeledEdit.Create(Self);
   FControlY.Parent:= Self;
   FControlY.SetSubComponent(true);
   FControlY.ControlStyle := FControlY.ControlStyle - [csNoDesignSelectable];
   FControlY.Name := 'Y';
   FControlY.Left := 36;
   FControlY.Height := 23;
   FControlY.Top := 59;
   FControlY.Width := 130;
   (* FControlZ - Parametros iniciales del TERCER Subcontrol dentro de TGRoupBox*)
   FControlZ:= TLabeledEdit.Create(Self);
   FControlZ.Parent:= Self;
   FControlZ.SetSubComponent(true);
   FControlZ.ControlStyle := FControlZ.ControlStyle - [csNoDesignSelectable];
   FControlZ.Name := 'Z';
   FControlZ.Left := 36;
   FControlZ.Height := 23;
   FControlZ.Top := 98;
   FControlZ.Width := 130;
   (* FControlLabel - Parametros iniciales del CUARTO Subcontrol dentro de TGRoupBox*)
   FControlLabel:= TLabel.Create(Self);
   FControlLabel.Parent:= Self;
   FControlLabel.SetSubComponent(true);
   FControlLabel.ControlStyle := FControlLabel.ControlStyle - [csNoDesignSelectable];
   FControlLabel.Name := 'Etiqueta';
   FControlLabel.Left := 129;
   FControlLabel.Height := 31;
   FControlLabel.Top := -2;
   FControlLabel.Width := 37;
   FControlLabel.Align := alCustom;
   FControlLabel.Alignment := taRightJustify;
   FControlLabel.AutoSize := False;
   FControlLabel.BidiMode := bdRightToLeftNoAlign;
   FControlLabel.Caption := 'XYZ';
   FControlLabel.ParentBidiMode := False;
   FControlLabel.ParentColor := False;
end;


destructor TPanelG3.Destroy;
begin
   FControlLabel.Free;
   FControlZ.Free;
   FControlY.Free;
   FControlX.Free;
   inherited Destroy;
end;


end.

I can compile the code without any problems. I can take one/two/..  of  these new controls, and I can put them in a new form, without any problems, but when I compile the new form, the IDE hangs up completely, without any error messages.

What's wrong in my code? (If I change TLabeledEdit to TEdit, all works properly. Is  my code wrong, or is  the TLabeledEdit code, wrong?

Regards

howardpc

  • Hero Member
  • *****
  • Posts: 4144
Re: Issues with subclass creation
« Reply #35 on: February 16, 2014, 05:22:45 pm »
You're publishing three TLabeledEdits as properties, and the Object Inspector has no default property editor for a TLabeledEdit property.
Probably you don't need to publish the entire class as a property (it will bulk up the RTTI of your composite component greatly to little purpose). Better to publish properties of simple types, and only those that are really needed. For this reason you would be better advised to base your internal private controls on TCustomXXX ancestors, and avoid a whole slew of published stuff you don't really need.
Something along these lines:

Code: [Select]
  TPanelG3Ex = class(TCustomPanel)
  private
    FControlX           : TCustomLabeledEdit;
    FControlY           : TCustomLabeledEdit;
    FControlZ           : TCustomLabeledEdit;
    FControlLabel       : TCustomLabel;
    function GetLabelCaption: string;
    function GetXText: string;
    function GetYText: string;
    function GetZText: string;
    procedure SetLabelCaption(AValue: string);
    procedure SetXText(AValue: string);
    procedure SetYText(AValue: string);
    procedure SetZText(AValue: string);
  public
    constructor Create(AOwner : TComponent) ;   override;
    destructor  Destroy;                        override;
  published
    property XText: string read GetXText write SetXText;
    property YText: string read GetYText write SetYText;
    property ZText: string read GetZText write SetZText;
    property LabelCaption: string read GetLabelCaption write SetLabelCaption;
  end;             

Your property setters and getters would then be something like this

Code: [Select]
...
function TPanelG3Ex.GetXText: string;
begin
  Result:=FControlX.Text;
end;

procedure TPanelG3Ex.SetXText(AValue: string);
begin
  if not SameText(AValue, FControlX.Text) then
    FControlX.Text:=AValue;
end;
« Last Edit: February 16, 2014, 07:54:22 pm by howardpc »

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #36 on: February 17, 2014, 02:57:26 pm »
Hi!! HowardPC

The first version of the control that I made, had very little properties. If you look at the source code in previous post, you can see in the Published  section some lines with //, where  previously I defined the new controls (TLabeledEdtit), inside the  TPanel control, without any compiled problems.

At the begining, I  only  declared those  properties that I really needed,  but still, I have a lot:

That is the code, for some of them:
Code: [Select]
      function  x1GetValueIntegerX ()          : int64;
      function  x1GetValueIntegerY ()          : int64;
      function  x1GetValueIntegerZ ()          : int64;
      function  x1GetValueRealX    ()          : extended;
      function  x1GetValueRealY    ()          : extended;
      function  x1GetValueRealZ    ()          : extended;
      procedure x1SetEditLabelCaptionX (FLabel : string);
      function  x1GetEditLabelCaptionX ()      : string;
      procedure x1SetEditLabelCaptionY (FLabel : string);
      function  x1GetEditLabelCaptionY ()      : string;
      procedure x1SetEditLabelCaptionZ (FLabel : string);
      function  x1GetEditLabelCaptionZ ()      : string;
      procedure x3SetParentColor (FParentColor : BOOLEAN);
      function  x3GetParentColor   ()          : BOOLEAN;
      procedure x3SetParentFont (FParentFont : BOOLEAN);
      function  x3GetParentFont    ()          : BOOLEAN;
      procedure x3SetParentBidiMode (FParentBidiMode: BOOLEAN);
      function  x3GetParentBidiMode()          : BOOLEAN;
      procedure x3SetBidiMode (FBidiMode: TBiDiMode);
      function  x3GetBidiMode      ()          : TBiDiMode;
      procedure x3SetLabelPosition (FLabelPosition: TLabelPosition);
      function  x3GetLabelPosition ()          : TLabelPosition;
      procedure x3SetMaxLength (FMaxLength: integer);
      function  x3GetMaxLength     ()          : integer;
      procedure x3SetMode (FMode : tNumero);
      function  x3GetMode          ()          : tNumero;
      procedure x3SetColor (FColor : TColor);
      function  x3GetColor         ()          : TColor;
      procedure x3SetColorError (FColor: TColor);
      function  x3GetColorError    ()          : TColor;
      procedure x3SetColorErrorTime (FColorTime : cardinal);
      function  x3GetColorErrorTime()          : cardinal;
      procedure x3SetSoundError (FSoundError : BOOLEAN);
      function  x3GetSoundError ()             : BOOLEAN;
      procedure x3SetFont (AValue: TFont);
      function  x3GetFont       ()             : TFont;
      procedure x3SetFocusFont (AValue: TFont);
      function  x3GetFocusFont  ()             : TFont;
      procedure x3SetEditLabelBidiMode (FBidiMode: TBiDiMode);
      function  x3GetEditLabelBidiMode ()      : TBiDiMode;
      procedure x3SetEditLabelColor (FColor : TColor);
      function  x3GetEditLabelColor ()         : TColor;
      procedure x3SetEditLabelColorError (FColor: TColor);
      function  x3GetEditLabelColorError ()    : TColor;
      procedure x3SetEditLabelColorErrorTime (FColorTime : cardinal);
      function  x3GetEditLabelColorErrorTime (): cardinal;
      procedure x3SetEditLabelFont (AValue: TFont);
      function  x3GetEditLabelFont ()          : TFont;
      procedure x3SetEditLabelFocusFont (AValue: TFont);
      function  x3GetEditLabelFocusFont ()     : TFont;
      procedure x3SetEditLabelParentColor (FParentColor : BOOLEAN);
      function  x3GetEditLabelParentColor ()   : BOOLEAN;
      procedure x3SetEditLabelParentFont (FParentFont : BOOLEAN);
      function  x3GetEditLabelParentFont  ()   : BOOLEAN;
      procedure x3SetEditLabelParentBidiMode (FParentBidiMode: BOOLEAN);
      function  x3GetEditLabelParentBidiMode (): BOOLEAN;
the properties that start x3, modify the same  property  simultaneously for three components. x1,  idem but only one.

However,  I needed any more. The code  was ugly and big. I decided to use the full set of them . My code, in previous post, is very clean and short, but it hangs up the IDE.

Is necessary a default property editor for TLabeledEdit? Why not for TEdit? TEdit works properly, and -  I think - it has not  a default property editor. That one is what I do not understand


Best Regards

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #37 on: February 22, 2014, 11:56:18 am »
Hi again!! I've got a problem with my new control: I don't understand the anchor commands. I'm trying to  put in the right-top corner inside a TPanel a Tlabel, and TLabel appears in the left-top corner inside of TPanel

This is the code What's wrong?

Code: [Select]
unit Panel1;

{$mode objfpc}{$H+}

interface

uses
  Classes, SysUtils, LResources, Forms, Controls, Graphics, Dialogs, StdCtrls, ExtCtrls;

type
  TPanel1 = class(TPanel)
  private
    { Private declarations }
    FLabel1                            : TLabel;
  protected
    { Protected declarations }
  public
    { Public declarations }
    constructor Create(TheOwner: TComponent);    override;
    destructor Destroy;                          override;
  published
    { Published declarations }
    property Label1   : TLabel       read FLabel1;
  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('Standard',[TPanel1]);
end;

constructor TPanel1.Create(TheOwner: TComponent);
begin
   inherited Create(TheOwner);
   FLabel1 := TLabel.Create(Self);
   FLabel1.Parent:= Self;
   FLabel1.SetSubComponent(true);
   FLabel1.ControlStyle := FLabel1.ControlStyle - [csNoDesignSelectable];
   FLabel1.Name := 'Label1';
   FLabel1.Caption := 'Label1';
   FLabel1.AnchorParallel(akTop,0,Self);
   FLabel1.AnchorSideRight.Control := Self;
   FLabel1.AnchorSideRight.Side := asrLeft;



end;

destructor TPanel1.Destroy;
begin
   FLabel1.Free;
   inherited Destroy;
end;

end.         

Regards

engkin

  • Hero Member
  • *****
  • Posts: 3112
Re: Issues with subclass creation
« Reply #38 on: February 22, 2014, 03:09:16 pm »
I'm trying to  put in the right-top corner inside a TPanel a Tlabel
I used the Anchor Editor to see what it does in the lfm file. The result:
Code: [Select]
  FLabel1.AnchorSideTop.Control := Panel1;
  FLabel1.AnchorSideRight.Control := Panel1;
  FLabel1.AnchorSideRight.Side := asrRight;
  FLabel1.Anchors := [akTop, akRight];

Quote
This is the code What's wrong?
By default FLabel1.Anchors has akTop and akLeft. With your code FLabel1.Width extends along the Panel but since the FLabel1.Alignment is taLeftJustify the text is going to show on the left side which gives the impression that it moved to the left instead of the intended direction. I guess.

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #39 on: February 22, 2014, 04:51:55 pm »
Hi, engkin!!

I've tested your code and it works properly (only I had to change 'Panel1' to 'Self')

Another question: do you know if  there is a way to disable one/two parent's properties, in a child control ?

Thanks again

engkin

  • Hero Member
  • *****
  • Posts: 3112
Re: Issues with subclass creation
« Reply #40 on: February 22, 2014, 05:43:17 pm »
Another question: do you know if  there is a way to disable one/two parent's properties, in a child control ?
Are you trying to remove properties inherited from a parent class?
Are you trying to remove it from the Object Inspector?
You can re-declare a property in another section.
Which properties are you trying to disable and why?

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #41 on: February 23, 2014, 02:44:17 pm »
Are you trying to remove properties inherited from a parent class?
Yes
Quote from: engkin
Are you trying to remove it from the Object Inspector?
Yes
Quote from: engkin
You can re-declare a property in another section.
I didn't know it.
Quote from: engkin
Which properties are you trying to disable and why?

If you look at the source code (the code  works ok) and you create a control with Panel1 new control,
Code: [Select]
unit Panel1;

{$mode objfpc}{$H+}

interface

uses
  Classes, SysUtils, LResources, Forms, Controls, Graphics, Dialogs, StdCtrls, ExtCtrls;

type
  TPanel1 = class(TPanel)
  private
    { Private declarations }
    FLabel1                            : TLabel;
    ColorTMP                           : TColor;
    procedure ColorRojo (Sender : TObject);
    procedure ColorOriginal (Sender : TObject);
  protected
    { Protected declarations }
  public
    { Public declarations }
    constructor Create(TheOwner: TComponent);    override;
    destructor Destroy;                          override;
  published
    { Published declarations }
    property Label1   : TLabel       read FLabel1;
  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('Standard',[TPanel1]);
end;

constructor TPanel1.Create(TheOwner: TComponent);
begin
   inherited Create(TheOwner);
   FLabel1 := TLabel.Create(Self);
   FLabel1.Parent:= Self;
   FLabel1.SetSubComponent(true);
   FLabel1.ControlStyle := FLabel1.ControlStyle - [csNoDesignSelectable];
   FLabel1.Name := 'Label1';
   FLabel1.Caption := 'Label1';
   FLabel1.AnchorSideTop.Control := Self;
   FLabel1.AnchorSideRight.Control := Self;
   FLabel1.AnchorSideRight.Side := asrRight;
   FLabel1.Anchors := [akTop, akRight];
   OnMouseEnter := @ColorRojo;
   OnMouseLeave  := @ColorOriginal;
end;

destructor TPanel1.Destroy;
begin
   FLabel1.Free;
   inherited Destroy;
end;


procedure TPanel1.ColorRojo (Sender : TObject);
begin
   inherited; // OnMouseEnter;
   ColorTMP := Color;
   Color := clRed;
   repaint;
end;


procedure TPanel1.ColorOriginal (Sender : TObject);
begin
   inherited; // OnMouseLeave;
   Color := ColorTMP;
   repaint;
end;

end.
The OnMouseEnter and OnMouseLeave events in the object inspector appear "unpublished" . I think they should not appear , because I've added code for these events .

I think the best will be disable in the parent class

Regards

taazz

  • Hero Member
  • *****
  • Posts: 5368
Re: Issues with subclass creation
« Reply #42 on: February 23, 2014, 03:05:20 pm »
1) never ever use the events from your inherited components there are methods you can override usually they have a name like DoMouseEnter, DoMouseLeave etc and the only thing they do is to call the event if assigned.
2) try to find a parent that does not have those events or properties published in your case that would be TCustomPanel. Take a look on TPanel to see which properties are published and copy from there which ever you want or all of them
Good judgement is the result of experience … Experience is the result of bad judgement.

OS : Windows 7 64 bit
Laz: Lazarus 1.4.4 FPC 2.6.4 i386-win32-win32/win64

howardpc

  • Hero Member
  • *****
  • Posts: 4144
Re: Issues with subclass creation
« Reply #43 on: February 23, 2014, 03:09:09 pm »
You can't reduce the visibility of a method or property by redeclaring it. You can only increase its visibility by redeclaration. This is why many VCL/LCL components are part of a hierarchy which includes a TCustomxxxx class which publishes very little (or nothing).
Then component designers can inherit from a TCustomxxx to build their descendant and publish only the properties they want.
Since you decend from TPanel, your OnMousexxx methods are already published in the ancestor, and cannot be unpublished. Even putting them in a private section has no effect at all on their publication, since RTTI is already generated for them in their ancestor's declaration.
You can avoid this by descending from TCustomPanel as taazz says, and not publishing those properties, which will prevent them from showing up in the Object Inspector (they will still be public, of course, and so accessible in code).

pusuni

  • Jr. Member
  • **
  • Posts: 72
Re: Issues with subclass creation
« Reply #44 on: February 23, 2014, 04:14:29 pm »
Thank very much for all advices

 

TinyPortal © 2005-2018