10

I am new to component creation and was experimenting with creating some of my own custom derived components using the standard issue VCL from Delphi.

I thought I could mix two components together, to create one singular one. Take below what I have so far, the idea is to put a TImage inside a TScrollBox:

unit MyComponent;

interface

uses
  Windows,
  Classes, 
  Controls,
  Forms,
  ExtCtrls;

type
  TMyPanel = class(TScrollBox)
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
  end;

procedure Register;

implementation

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

{ TMyPanel }

constructor TMyPanel.Create(AOwner: TComponent);
var
  AImage: TImage;
begin
  inherited Create(AOwner);

  AImage := TImage.Create(AOwner);
  AImage.Align := alClient;
  AImage.Parent := Self;
end;

destructor TMyPanel.Destroy;
begin
  inherited;
end;

end.

If I compile and install the above into a package, the result is as shown below:

enter image description here

enter image description here

Problem

I would like my component to be registered as one single component. But the component should be a combination of both TScrollBox and TImage. The main component will be the TScrollBox, but it should now have access to the properties and events etc of the TImage aswell.

For example, TMyPanel could share the properties of TImage and TScrollBox together:

  • AutoSize
  • BorderStyle
  • HorzScrollBar
  • ParentBackground
  • Picture
  • VertScrollBar

I think it would be overkill to completely write a new component to do the behavior described above, that and I really wouldn't know where to begin. If this can be accomplished you could create some interesting components that are combined into one, but keep there original properties, methods and events etc.

This is what I want to achieve here with a TImage inside a TScrollBox.

Solution

The answer shown by Uwe Raabe works as expected. The TImage is now registered inside the TScrollBox, but appears as one component. The properties of the TImage are shown in the Object Inspector as Image. > which will reveal the properties of TImage :)

1 Answers1

14

You should make the image a subcomponent of TMyPanel: SetSubComponent

Update: Here is an example

unit MyComponent;

interface

uses
  System.Classes,
  VCL.Controls,
  VCL.Forms,
  VCL.ExtCtrls;

type
  TMyPanel = class(TScrollBox)
  private
    FImage: TImage;
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
  published
    property Image: TImage read FImage;
  end;

procedure Register;

implementation

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

constructor TMyPanel.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);

  FImage := TImage.Create(Self);
  FImage.SetSubComponent(true);
  FImage.Align := alClient;
  FImage.Parent := Self;
end;

destructor TMyPanel.Destroy;
begin
  inherited;
end;

end.
Uwe Raabe
  • 45,288
  • 3
  • 82
  • 130
  • +1 Thanks for quick reply, I had a feeling there might be something else I need to do. Let me have a look at this article some more.. –  Feb 28 '12 at 10:06
  • With the approach shown above the published Image property should be visible and expandable in the Object Inspector. – Uwe Raabe Feb 28 '12 at 16:14
  • 2
    I advise to name the sub component. Right now the object inspector will show _MyPanel._ , but it could look like _MyPanel.SubImage_ . – NGLN Feb 28 '12 at 16:33
  • Thanks for the suggestion NGLN, I will use an appropriate name for the TImage. –  Feb 28 '12 at 16:45
  • Hi Uwe - You set FImage.Parent:= Self but some are against it. Can you comment on that? Thanks. – Gabriel Sep 27 '12 at 12:42
  • @Altar, what do you mean with "some are against it"? The image is supposed to be a control inside the outer scrollbox. How would you manage that in another way? – Uwe Raabe Sep 27 '12 at 12:53
  • People here are saying that the parent should not be set manually/ It is set automatically by the (DFM) streaming system. – Gabriel Sep 27 '12 at 13:10
  • 1
    @Altar, that would be true if you don't use the subcomponent approach. The parenting of the subcomponent is not handled by the DFM system but by the outer component. Actually, the subcomponent doesn't exist in the DFM, only its properties are written as part of th properties of the outer component. It would simply not work if you omit setting the parent. – Uwe Raabe Sep 27 '12 at 13:17