Eigene Komponenten mit beliebiger Anzahl von Sub-Komponenten

Rund um die LCL und andere Komponenten
Antworten
LazProgger
Beiträge: 63
Registriert: Di 11. Mär 2014, 00:33

Eigene Komponenten mit beliebiger Anzahl von Sub-Komponenten

Beitrag von LazProgger »

Ich würde gerne eine eigene Komponente erstellen, die eine variable Anzahl von Sub-Komponenten enthält, auf die man auch zur Design-Zeit andere Controls legen kann.
Ähnlich ist zum Beispiel TPageControl oder TNoteBook aufgebaut. Es gibt also zunächst eine Basis-Komponente (abgeleitet von TCustomControl), diese enthält einen dynamischen Array für die "Seiten" oder "Tabs", die dann eingeblendet oder ausgeblendet werden und als Parent entsprechend die Basis-Komponente haben.

So weit, so gut. Wie ich sowas dynamisch erzeugen würde, weiß ich und dafür gibt es ja auch genug Beispiele im Netz. Ich würde allerdings gerne haben, dass man auch zur Design-Zeit Komponenten auf die Tabs legen kann und auch das aktive Tab ändern kann.
Beim TNoteBook funktioniert das ganze und ich habe schon versucht, den Code irgendwie nachzubauen, aber es klappt nicht.
Wenn man im Object Inspector auf das TNoteBook klickt, kommt im Kontextmenü beispielsweise "Add Page" oder "Delete Page". Wie aber ist das im Code umgesetzt? Ich habe im TNoteBook-Code nichts dazu gefunden. Weiß das vielleicht jemand? Ich denke das wäre ein erster Ansatzpunkt, um zu sehen, wie man so etwas zur Design-Zeit umsetzen kann.

PS: Als ersten Ansatz habe ich versucht den Code vom TNoteBook als eigene neue Komponente compilierbar zu machen (siehe angehängte Datei). Allerdings funktioniert genau das mit dem "Add Page" und "Delete Page" nicht, obwohl ich den Original-Code kopiert habe.
Dateianhänge
testtabpanela.pas
(12.01 KiB) 47-mal heruntergeladen

Michl
Beiträge: 2505
Registriert: Di 19. Jun 2012, 12:54

Re: Eigene Komponenten mit beliebiger Anzahl von Sub-Kompone

Beitrag von Michl »

Ich habe mir dein Package nicht angeschaut, doch wenn du eine Komponente bauen willst, die ähnlich dem TPageControl oder TNotebook ist, so verwende doch auch den gleichen Vorfahr, den auch sie benutzen (TCustomTabControl) und nicht TCustomControl. Bei diesem Vorfahr wird auch gleich der entsprechende Editor für deine Komponente mit verfügbar gemacht:

Code: Alles auswählen

unit ComponentEditors;
...
initialization
...
  RegisterComponentEditor(TCustomTabControl, TTabControlComponentEditor);   

Willst du diese Möglichkeit nicht nutzen, so könnte dir der ausführliche Kommentar von Mattias in der Unit Lazarus\components\ideintf\componenteditors.pas weiterhelfen.

Code: Alles auswählen

type
  TLiveSelection = (lsMoney, lsChilds, lsTime);
  TLive = Array[0..1] of TLiveSelection; 

LazProgger
Beiträge: 63
Registriert: Di 11. Mär 2014, 00:33

Re: Eigene Komponenten mit beliebiger Anzahl von Sub-Kompone

Beitrag von LazProgger »

Ah, vielen Dank. Das bringt schon mal ein wenig Licht ins dunkle. Ohne dich wäre ich niemals darauf gekommen!

Das merkwürdige ist, das TPageControl zwar von besagtem TCustomTabControl abgeleitet ist, TNotebook allerdings nicht (hier ist es TCustomControl):

Code: Alles auswählen

 
 
TNotebook = class(TCustomControl)     
 
TPageControl = class(TCustomTabControl)   
 
 


Dennoch steht in der ComponentEditors-Unit auch folgende Zeile zum TNoteBook:

Code: Alles auswählen

 
 
initialization
  RegisterComponentEditor(TNotebook, TUntabbedNotebookComponentEditor);     
  RegisterComponentEditor(TPage, TUNBPageComponentEditor);     
 
 


Die zugrunde liegende Klasse ist wohl auch die Realisierung der "Add Page" Geschichte:

Code: Alles auswählen

 
  { TUntabbedNotebookComponentEditor
    The default component editor for TUntabbedNotebook. }

  TUntabbedNotebookComponentEditor = class(TDefaultComponentEditor)
  protected
    procedure AddNewPageToDesigner(Index: integer); virtual;
    procedure DoAddPage; virtual;
    procedure DoDeletePage; virtual;
    procedure AddMenuItemsForPages(ParentMenuItem: TMenuItem); virtual;
    procedure ShowPageMenuItemClick(Sender: TObject);
  public
    procedure ExecuteVerb(Index: Integer); override;
    function GetVerb(Index: Integer): string; override;
    function GetVerbCount: Integer; override;
    procedure PrepareItem(Index: Integer; const AnItem: TMenuItem); override;
    function Notebook: TNotebook; virtual;
  end;
 
  { TUNBPageComponentEditor
    The default component editor for TUNBPage. }

  TUNBPageComponentEditor = class(TUntabbedNotebookComponentEditor)
  public
    function Notebook: TNotebook; override;
    function Page: TPage; virtual;
  end;   
 
 


Meine Idee nun: Soetwas auch für meine Komponente bauen und im initialization Abschnitt RegisterComponentEditor aufrufen.

marcov
Beiträge: 1100
Registriert: Di 5. Aug 2008, 09:37
OS, Lazarus, FPC: Windows ,Linux,FreeBSD,Dos (L trunk FPC trunk)
CPU-Target: 32/64,PPC(+64), ARM
Wohnort: Eindhoven (Niederlande)

Re: Eigene Komponenten mit beliebiger Anzahl von Sub-Kompone

Beitrag von marcov »

(database tables, queries, grids usw haben typisch auch eine beliebiger Anzahl von Sub-Komponenten)

Antworten