Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   GUI-Design mit VCL / FireMonkey / Common Controls (https://www.delphipraxis.net/18-gui-design-mit-vcl-firemonkey-common-controls/)
-   -   Delphi Komponente (TImage & TLabel) -> Image wird nicht angezeigt (https://www.delphipraxis.net/214936-komponente-timage-tlabel-image-wird-nicht-angezeigt.html)

NoGAD 8. Apr 2024 08:09

Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Hallo,

Folgende Unit soll eigentlich ein TImage und ein TLabel kombiniert anzeigen. Leider wird zur Laufzeit das TPicture wieder gelöscht. In der Designansicht ist das TPicture dagegen komplett sichtbar - egal, welcher Typ (Gif/png/jpg/bmp) als Bild ausgewählt wurde.

Habe ich eine Property falsch gesetzt?

Delphi-Quellcode:
unit TRM_ImageLabel;

interface

uses
  System.SysUtils, System.Classes, Vcl.Controls, Vcl.ExtCtrls, Vcl.StdCtrls,
  Vcl.Imaging.GIFConsts,
  Vcl.Imaging.GIFImg,
  Vcl.Imaging.JConsts,
  Vcl.Imaging.jpeg,
  Vcl.Imaging.pngimage,
  Vcl.Imaging.pnglang;

type
  TLabelPosition = (lpTop, lpBottom, lpLeft, lpRight);

  TTRM_ImageLabel = class(TCustomPanel)
  private
    FSubImageComponent: TImage;
    FSubLabelComponent: TLabel;
    FLabelPosition: TLabelPosition;
    procedure SetLabelPosition(const Value: TLabelPosition);
  protected
    procedure Resize; override;
  public
    constructor Create(AOwner: TComponent); override;
  published
    property SubImageComponent: TImage read FSubImageComponent;
    property SubLabelComponent: TLabel read FSubLabelComponent;
    property Align;
    property Anchors;
    property OnClick;
    property OnDblClick;
    property OnMouseEnter;
    property OnMouseLeave;
    property LabelPosition: TLabelPosition read FLabelPosition write SetLabelPosition;
  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('TRM', [TTRM_ImageLabel]);
end;

{ TTRM_ImageLabel }

constructor TTRM_ImageLabel.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  (* Für meine eigenen Bedürfnisse *)
  Self.Width := 64;
  Self.Height := 97;

  FSubImageComponent := TImage.Create(Self);
  FSubImageComponent.Parent := Self;
  FSubImageComponent.Align := alClient;

  FSubLabelComponent := TLabel.Create(Self);
  FSubLabelComponent.Parent := Self;
  FSubLabelComponent.Height := 25;
  FSubLabelComponent.AlignWithMargins := False;
  FSubLabelComponent.Margins.Left := 0;
  FSubLabelComponent.Margins.Right := 0;
  FSubLabelComponent.Margins.Top := 8;
  FSubLabelComponent.Margins.Bottom := 0;
  FSubLabelComponent.Caption := 'TEST';
  SubLabelComponent.Font.Size := 14;

  FLabelPosition := lpBottom;

  Resize;
end;

procedure TTRM_ImageLabel.Resize;
begin
  inherited;
  case FLabelPosition of
    lpTop:
      begin
        FSubLabelComponent.Align := alTop;
        FSubLabelComponent.Alignment := taCenter;
      end;
    lpBottom:
      begin
        FSubLabelComponent.Align := alBottom;
        FSubLabelComponent.Alignment := taCenter;
      end;
    lpLeft:
      begin
        FSubLabelComponent.Align := alLeft;
        FSubLabelComponent.Alignment := taCenter;
      end;
    lpRight:
      begin
        FSubLabelComponent.Align := alRight;
        FSubLabelComponent.Alignment := taCenter;
      end;
  end;
end;

procedure TTRM_ImageLabel.SetLabelPosition(const Value: TLabelPosition);
begin
  if FLabelPosition <> Value then
  begin
    FLabelPosition := Value;
    Resize;
  end;
end;

end.

Delphi.Narium 8. Apr 2024 08:31

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zu Beginn wird das Label alBottom gesetzt. Damit erhält es die volle Breite das Panels, auf das es gelegt wird.

Wenn Du nun hergehst und das Label z. B. alLeft setzt, so bleibt die Breite des Labels erhalten und es füllt damit das Panel vollständig aus, so dass für das Image kein Platz mehr übrig bleibt.

Du müsstest im Resize die Höhe bzw. die Breite das Labels jeweils mit anpassen, bei alTop und alBottom jeweils Height, wie im Create auf 25 setzen und bei alLeft bzw. alRight Width auf die von Dir gewünschte Breite.

himitsu 8. Apr 2024 08:44

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Tja, diese Komponenten wissen nunmal nicht, dass sie im Design-Modus sein sollen.
Wobei, sollen sie es wirklich, also z.B. auch per Hand im Designer umhergeschubst und mit dem Property-Editor geändert werden können?

* in TTRM_ImageLabel auf csDesigning reagieren und die untergeordneten Komponenten manuell anpassen, also z.B. garnicht oder anders darstellen
* * im constructor beim Owner nachsehn, da es bei sich selbst leider noch nicht gesetzt ist (obwohl das möglich wäre, wenn Emba die zugehörigen FeatureRequsts/Bugreports übernommen hätte)
* TComponent.SetDesignInstance
* TComponent.SetDesigning
* oder
* oder
* oder
* ...

Uwe Raabe 8. Apr 2024 08:48

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Lädst du das Bild in die TImage-Komponente während des Design? Dann musst du auch dafür sorgen, dass es mit in die DFM gestreamt wird. Nach dem Erzeugen der Controls sollte somit noch ein Aufruf von SetSubcomponent erfolgen.

itsChris 8. Apr 2024 09:29

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Moin,
so wie Uwe schon geschrieben hat, merkt sich die DFM zurzeit dein Picture nicht, wenn du es zur Designzeit lädst.

OT: Auch, wenn dass nicht deine Frage war, ist mir noch folgendes an deinem Code aufgefallen:

Margins werden nur beachtet, wenn AlignWithMargins = True ist. Deine gesetzten Margins werden also nicht beachtet.
Für dein Image würde ich noch Proportional und Center auf True setzen, damit das eingefügte Bild an die Komponentengröße angepasst wird und zentriert ist.

NoGAD 8. Apr 2024 10:12

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Hallo an euch alle.

Danke für die Bemerkungen. Ich möchte nicht unverschämt klingen, jedoch hat mir keine der Informationen bis auf die von Uwe geholfen. ;-)

Danke @Uwe, das hatte ich bisher noch nie benötigt.

@itsChris: (* Für meine eigenen Bedürfnisse *) ;-)
@Delphi.Narium: Die Anpassung (Breite bei lpLeft/lpRight) erfolgt noch, hier werde ich eine vertikalen Ausrichtung einbinden.
@himitsu: Tja, diese Komponenten wissen nunmal nicht, dass sie im Design-Modus sein sollen. Warum nicht? Die Ableitung ist doch von den Standardkomponenten. (Oder verstehe ich etwas falsch?)


LG Mathias :-)

itsChris 8. Apr 2024 10:30

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von NoGAD (Beitrag 1535490)
@itsChris: (* Für meine eigenen Bedürfnisse *) ;-)

Kann ja sein, ich wollte dich nur darauf hinweisen, dass der folgende Code keine Auswirkung/Funktionalität hat:
Delphi-Quellcode:
  FSubLabelComponent.AlignWithMargins := False;
  FSubLabelComponent.Margins.Left := 0;
  FSubLabelComponent.Margins.Right := 0;
  FSubLabelComponent.Margins.Top := 8;
  FSubLabelComponent.Margins.Bottom := 0;

Uwe Raabe 8. Apr 2024 10:56

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von itsChris (Beitrag 1535491)
Kann ja sein, ich wollte dich nur darauf hinweisen, dass der folgende Code keine Auswirkung/Funktionalität hat:

Margins und Padding werden auch bei AlignWithMargins = False für die Abstands-Designer-Hilflinien verwendet.

itsChris 8. Apr 2024 11:03

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von Uwe Raabe (Beitrag 1535493)
Margins und Padding werden auch bei AlignWithMargins = False für die Abstands-Designer-Hilflinien verwendet.

Was hat das für eine Auswirkung, also wofür wird das benutzt? Visuell gesehen stimmt meine Aussage aber, jedenfalls kann ich keine Margins sehen, wenn AlignWithMargins = False ist.

Aber ok, dann nehme ich meine Aussage zurück.

Uwe Raabe 8. Apr 2024 11:14

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von itsChris (Beitrag 1535495)
Aber ok, dann nehme ich meine Aussage zurück.

Das war eher als eine Art Ergänzung gemeint. Es betrifft ja auch nur den Design-Vorgang.

NoGAD 8. Apr 2024 11:47

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Für mich macht es Sinn. Bei den Standardkomponenten hat sich ja bisher sicher auch keiner daran gestört, dass die Eigenschaften auf 3 gesetzt sind ;-)

himitsu 8. Apr 2024 13:44

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von NoGAD (Beitrag 1535490)
@himitsu: Tja, diese Komponenten wissen nunmal nicht, dass sie im Design-Modus sein sollen. Warum nicht? Die Ableitung ist doch von den Standardkomponenten. (Oder verstehe ich etwas falsch?)

Ausschließlich Komponenten, welche vom Designer erstellt werden (mit Owner=Form) werden von ihm auch in den DesignModus versetzt.
Aber UnterKomponenten standardmäßig nicht.

* SetSubcomponent
* oder, wenn es nur ums Speichern geht, diese Funktion in die Hauptkomponente und dann intern die Daten zur Subkomponente durchreichen.



Ach ja, wenn man die initialen Werte von "Standardeigenschaften" ändert, dann sollte man auch niemals vergessen das DEFAULT am Property zu aktualisieren.

NoGAD 8. Apr 2024 20:59

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Danke für die Ergänzung. 😃

LG Mathias

NoGAD 14. Mai 2024 09:43

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Ich habe eine Rückfrage zu SetSubComponent.

Die Komponente funktioniert sehr gut, jedoch besteht jetzt das Problem, dass das Label (SubComponente) einige Eigenschaften nicht speichert.

Z.B. Align. Ich setze die Eigenscahft der Subcomponente auf alClient, speichere das Project, schließe und lade es erneut. Dann ist die Eigenschaft wieder auf alRight.

Hier der Code der aktuellen Version

Delphi-Quellcode:
unit TRM_ImageLabel;

(*

  TRM_ImageLabel erstellt von Mathias Fiege 2024

  www.nogad.de

  Open Source License
  Permission is hereby granted, free of charge, to any person obtaining a copy
  of this software component and associated documentation files (the "Software"),
  to deal in the Software without restriction, including without limitation the
  rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  sell copies of the Software, and to permit persons to whom the Software is
  furnished to do so, subject to the following conditions:

  The above copyright notice and this permission notice shall be included in all
  copies or substantial portions of the Software.

  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  THE SOFTWARE.

  Thanks and greetings to www.delphipraxis.net

*)

interface

uses
  System.SysUtils, System.Classes, Vcl.Controls, Vcl.Forms, Vcl.ExtCtrls, Vcl.StdCtrls,
  Vcl.Imaging.GIFConsts,
  Vcl.Imaging.GIFImg,
  Vcl.Imaging.JConsts,
  Vcl.Imaging.jpeg,
  Vcl.Imaging.pngimage,
  Vcl.Imaging.pnglang;

type
  TLabelPosition = (lpTop, lpBottom, lpLeft, lpRight);

  TTRM_ImageLabel = class(TCustomPanel)
  private
    FSubImageComponent: TImage;
    FSubLabelComponent: TLabel;

    FLabelPosition: TLabelPosition;

    FVersion: String;

    procedure SetLabelPosition(const Value: TLabelPosition);

    procedure ImageClick(Sender: TObject);
    procedure ImageDblClick(Sender: TObject);
    procedure ImageMouseEnter(Sender: TObject);
    procedure ImageMouseLeave(Sender: TObject);

    procedure LabelClick(Sender: TObject);
    procedure LabelDblClick(Sender: TObject);
    procedure LabelMouseEnter(Sender: TObject);
    procedure LabelMouseLeave(Sender: TObject);
  protected
    procedure Resize; override;
  public
    constructor Create(AOwner: TComponent); override;
  published
    property SubImageComponent: TImage read FSubImageComponent;
    property SubLabelComponent: TLabel read FSubLabelComponent;
    property Align;
    property Anchors;

    property BevelInner;
    property BevelKind;
    property BevelOuter;
    property BevelWidth;
    property BorderStyle;
    property BorderWidth;
    property Caption;
    property Ctl3D;
    property Cursor;
    property ParentBackground;
    property PopupMenu;

    property OnClick;
    property OnDblClick;
    property OnMouseEnter;
    property OnMouseLeave;
    property LabelPosition: TLabelPosition read FLabelPosition write SetLabelPosition;

    property Version: String read FVersion;

  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('TRM', [TTRM_ImageLabel]);
end;

{ TTRM_ImageLabel }

constructor TTRM_ImageLabel.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  Self.Width := 64;
  Self.Height := 89;
  Self.AlignWithMargins := True;
  Self.Margins.Top := 0;
  Self.Margins.Left := 8;
  Self.Margins.Right := 8;
  Self.Margins.Bottom := 0;
  Self.BevelInner := bvNone;
  Self.BevelKind := bkNone;
  Self.BevelOuter := bvNone;
  Self.BevelWidth := 1;
  Self.BorderStyle := bsNone;
  Self.BorderWidth := 0;
  Self.Caption := '';
  Self.Ctl3D := False;
  Self.Cursor := crHandPoint;
  Self.ParentBackground := True;

  FSubImageComponent := TImage.Create(Self);
  SubImageComponent.SetSubComponent(True);
  FSubImageComponent.Parent := Self;
  FSubImageComponent.Align := alClient;
  FSubImageComponent.OnClick := ImageClick;
  FSubImageComponent.OnDblClick := ImageDblClick;
  FSubImageComponent.OnMouseEnter := ImageMouseEnter;
  FSubImageComponent.OnMouseLeave := ImageMouseLeave;

  FSubLabelComponent := TLabel.Create(Self);
  SubLabelComponent.SetSubComponent(True);
  FSubLabelComponent.Parent := Self;
  FSubLabelComponent.Height := 25;
  FSubLabelComponent.AlignWithMargins := False;
  FSubLabelComponent.Margins.Left := 0;
  FSubLabelComponent.Margins.Right := 0;
  FSubLabelComponent.Margins.Top := 8;
  FSubLabelComponent.Margins.Bottom := 0;
  FSubLabelComponent.Caption := '...';
  SubLabelComponent.Font.Size := 14;
  SubLabelComponent.OnClick := LabelClick;
  SubLabelComponent.OnDblClick := LabelDblClick;
  SubLabelComponent.OnMouseEnter := LabelMouseEnter;
  SubLabelComponent.OnMouseLeave := LabelMouseLeave;

  FLabelPosition := lpBottom;

  FVersion := '2024.05.14.1038';

  Resize;
end;

procedure TTRM_ImageLabel.Resize;
begin
  inherited;
  case FLabelPosition of
    lpTop:
      begin
        FSubLabelComponent.Align := alTop;
        // FSubLabelComponent.Alignment := taCenter;
      end;
    lpBottom:
      begin
        FSubLabelComponent.Align := alBottom;
        // FSubLabelComponent.Alignment := taCenter;
      end;
    lpLeft:
      begin
        FSubLabelComponent.Align := alLeft;
        // FSubLabelComponent.Alignment := taCenter;
      end;
    lpRight:
      begin
        FSubLabelComponent.Align := alRight;
        // FSubLabelComponent.Alignment := taCenter;
      end;
  end;

  Update;
end;

procedure TTRM_ImageLabel.SetLabelPosition(const Value: TLabelPosition);
begin
  if FLabelPosition <> Value then
  begin
    FLabelPosition := Value;
    Resize;
  end;
end;

procedure TTRM_ImageLabel.ImageClick(Sender: TObject);
begin
  if Assigned(OnClick) then
    OnClick(Self);
end;

procedure TTRM_ImageLabel.ImageDblClick(Sender: TObject);
begin
  if Assigned(OnDblClick) then
    OnDblClick(Self);
end;

procedure TTRM_ImageLabel.ImageMouseEnter(Sender: TObject);
begin
  if Assigned(OnMouseEnter) then
    OnMouseEnter(Self);
end;

procedure TTRM_ImageLabel.ImageMouseLeave(Sender: TObject);
begin
  if Assigned(OnMouseLeave) then
    OnMouseLeave(Self);
end;

procedure TTRM_ImageLabel.LabelClick(Sender: TObject);
begin
  if Assigned(OnClick) then
    OnClick(Self);
end;

procedure TTRM_ImageLabel.LabelDblClick(Sender: TObject);
begin
  if Assigned(OnDblClick) then
    OnDblClick(Self);
end;

procedure TTRM_ImageLabel.LabelMouseEnter(Sender: TObject);
begin
  if Assigned(OnMouseEnter) then
    OnMouseEnter(Self);
end;

procedure TTRM_ImageLabel.LabelMouseLeave(Sender: TObject);
begin
  if Assigned(OnMouseLeave) then
    OnMouseLeave(Self);
end;

end.

KodeZwerg 14. Mai 2024 12:16

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Ich habs mal versucht nachzustellen wobei ich gleich auf TPanel umgestiegen bin.
Zur laufzeit benötige ich nicht mehr als:
Delphi-Quellcode:
unit EinUnitName;

interface

uses
  System.SysUtils,
  System.Classes,
  Vcl.Controls, Vcl.StdCtrls, Vcl.ExtCtrls;

type
  TLabeledImage = class(TCustomPanel)
    strict private
      FImage: TImage;
      FLabel: TLabel;
    public
      constructor Create(AOwner: TComponent);
      destructor Destroy; override;
    published
      property Img: TImage read FImage write FImage;
      property Lbl: TLabel read FLabel write FLabel;
  end;

implementation

{ TLabeledImage }

constructor TLabeledImage.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  Self.Parent := TWinControl(AOwner);
  FLabel := TLabel.Create(Self);
  try
    FLabel.Parent := Self;
    FLabel.Align := alBottom;
    FLabel.Alignment := taCenter;
    FLabel.Caption := '';
    FLabel.Visible := True;
  finally
  end;
  FImage := TImage.Create(Self);
  try
    FImage.Parent := Self;
    FImage.Align := alClient;
    FImage.Visible := True;
  finally
  end;
  Self.Width := 150;
  Self.Height := 150;
end;

destructor TLabeledImage.Destroy;
begin
  FImage.Free;
  FLabel.Free;
  inherited Destroy;
end;

end.

NoGAD 14. Mai 2024 13:17

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Huhu. Danke für Deine Hilfe.

Ich habe den Fehler gefunden:

Delphi-Quellcode:
FSubImageComponent := TImage.Create(Self);
  SubImageComponent.SetSubComponent(True); // <--- hier fehlt ein F; ebenso beim Label.
  FSubImageComponent.Parent := Self;

Tut mir leid, hatte ich übersehen.

LG Mathias :-)

NoGAD 15. Mai 2024 08:13

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Hier ist die aktuelle Variante der Komponente. Jetzt klappt es auch mit den Zuweisungen. Der Fehler war, dass ich TSubPosition nur als (lpTop, lpBottom, lpLeft, lpRight) deklariert hatte. Wenn ich dann die Subkomponente (Label) aber z.B. als Client eingestellt hatte, gab es diesen ominösen Fehler beim Laden. Jetzt, nachdem ich TSubPosition als (lpNone, lpTop, lpBottom, lpLeft, lpRight, lpClient, lpCustom) deklariert habe, klappt es.

Was ich jetzt noch gern machen würde, wäre eine Abkürzung, um ein Bild (png,bmp,gif,...) über den ObjectInspector als Property bereitstellen zu können.

Aber ich scheitere an der korrekten Zuweisung ;-)



Delphi-Quellcode:
unit TRM_ImageLabel;

(*

  TRM_ImageLabel erstellt von Mathias Fiege 2024

  www.nogad.de

  Open Source License
  Permission is hereby granted, free of charge, to any person obtaining a copy
  of this software component and associated documentation files (the "Software"),
  to deal in the Software without restriction, including without limitation the
  rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  sell copies of the Software, and to permit persons to whom the Software is
  furnished to do so, subject to the following conditions:

  The above copyright notice and this permission notice shall be included in all
  copies or substantial portions of the Software.

  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  THE SOFTWARE.

  Thanks and greetings to www.delphipraxis.net

*)

interface


uses
  System.SysUtils, System.Classes, Vcl.Controls, Vcl.Forms, Vcl.ExtCtrls, Vcl.StdCtrls,
  Vcl.Imaging.GIFConsts,
  Vcl.Imaging.GIFImg,
  Vcl.Imaging.JConsts,
  Vcl.Imaging.jpeg,
  Vcl.Imaging.pngimage,
  Vcl.Imaging.pnglang,
  Vcl.Graphics;

const
  _version = '2024.05.15.0901';

type
  TSubPosition = (lpNone, lpTop, lpBottom, lpLeft, lpRight, lpClient, lpCustom);

  TTRM_ImageLabel = class(TCustomPanel)
  private
    FSubImage: TImage;
    FImagePosition: TSubPosition;

    FSubLabel: TLabel;
    FLabelCaption: String;
    FLabelPosition: TSubPosition;

    FVersion: String;

    procedure SetImagePosition(const Value: TSubPosition);

    procedure SetLabelCaption(const Value: String);
    procedure SetLabelPosition(const Value: TSubPosition);

    procedure ImageClick(Sender: TObject);
    procedure ImageDblClick(Sender: TObject);
    procedure ImageMouseEnter(Sender: TObject);
    procedure ImageMouseLeave(Sender: TObject);

    procedure LabelClick(Sender: TObject);
    procedure LabelDblClick(Sender: TObject);
    procedure LabelMouseEnter(Sender: TObject);
    procedure LabelMouseLeave(Sender: TObject);
  protected
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
    procedure Resize; override;
  published
    property SubImage: TImage read FSubImage;
    property SubLabel: TLabel read FSubLabel;
    property Align;
    property Anchors;

    property BevelInner;
    property BevelKind;
    property BevelOuter;
    property BevelWidth;
    property BorderStyle;
    property BorderWidth;
    property Caption;
    property Ctl3D;
    property Cursor;
    property ParentBackground;
    property PopupMenu;

    property OnClick;
    property OnDblClick;
    property OnMouseEnter;
    property OnMouseLeave;

    property ImagePosition: TSubPosition read FImagePosition write SetImagePosition;

    property LabelCaption: String read FLabelCaption write SetLabelCaption;
    property LabelPosition: TSubPosition read FLabelPosition write SetLabelPosition;

    property Version: String read FVersion;

  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('TRM', [TTRM_ImageLabel]);

end;

{ TTRM_ImageLabel }

constructor TTRM_ImageLabel.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  Self.Parent := TWinControl(AOwner);

  FSubImage := TImage.Create(Self);
  try
    FSubImage.SetSubComponent(True);
    FSubImage.Parent := Self;
    FSubImage.Align := alClient;
    FSubImage.OnClick := ImageClick;
    FSubImage.OnDblClick := ImageDblClick;
    FSubImage.OnMouseEnter := ImageMouseEnter;
    FSubImage.OnMouseLeave := ImageMouseLeave;
  finally
  end;

  FSubLabel := TLabel.Create(Self);
  try
    FSubLabel.SetSubComponent(True);
    FSubLabel.Parent := Self;
    FSubLabel.Align := alBottom;
    FSubLabel.AutoSize := True;
    FSubLabel.Height := 25;
    FSubLabel.AlignWithMargins := False;
    FSubLabel.Margins.Left := 0;
    FSubLabel.Margins.Right := 0;
    FSubLabel.Margins.Top := 8;
    FSubLabel.Margins.Bottom := 0;
    FSubLabel.Caption := '...';
    FSubLabel.Font.Size := 14;
    FSubLabel.OnClick := LabelClick;
    FSubLabel.OnDblClick := LabelDblClick;
    FSubLabel.OnMouseEnter := LabelMouseEnter;
    FSubLabel.OnMouseLeave := LabelMouseLeave;
  finally
  end;

  Self.Width := 64;
  Self.Height := 89;
  Self.AlignWithMargins := True;
  Self.Margins.Top := 0;
  Self.Margins.Left := 8;
  Self.Margins.Right := 8;
  Self.Margins.Bottom := 0;
  Self.BevelInner := bvNone;
  Self.BevelKind := bkNone;
  Self.BevelOuter := bvNone;
  Self.BevelWidth := 1;
  Self.BorderStyle := bsNone;
  Self.BorderWidth := 0;
  Self.Caption := '';
  Self.Ctl3D := False;
  Self.Cursor := crHandPoint;
  Self.ParentBackground := True;

  FVersion := _version;

  FImagePosition := lpClient;
  FLabelPosition := lpBottom;

  Update;
  Resize;

end;

procedure TTRM_ImageLabel.Resize;
begin
  (* lpNone, lpTop, lpBottom, lpLeft, lpRight, lpClient, lpCustom *)
  inherited;
  case FLabelPosition of
    lpNone:
      begin
        FSubLabel.Align := alNone;
      end;
    lpTop:
      begin
        FSubLabel.Align := alTop;
      end;
    lpBottom:
      begin
        FSubLabel.Align := alBottom;
      end;
    lpLeft:
      begin
        FSubLabel.Align := alLeft;
      end;
    lpRight:
      begin
        FSubLabel.Align := alRight;
      end;
    lpClient:
      begin
        FSubLabel.Align := alClient;
      end;
    lpCustom:
      begin
        FSubLabel.Align := alCustom;
      end;
  end;

  case FImagePosition of
    lpNone:
      begin
        FSubImage.Align := alNone;
      end;
    lpTop:
      begin
        FSubImage.Align := alTop;
      end;
    lpBottom:
      begin
        FSubImage.Align := alBottom;
      end;
    lpLeft:
      begin
        FSubImage.Align := alLeft;
      end;
    lpRight:
      begin
        FSubImage.Align := alRight;
      end;
    lpClient:
      begin
        FSubImage.Align := alClient;
      end;
    lpCustom:
      begin
        FSubImage.Align := alCustom;
      end;
  end;

  FSubLabel.Caption := FLabelCaption;

  Update;

end;

procedure TTRM_ImageLabel.SetImagePosition(const Value: TSubPosition);
begin
  if FImagePosition <> Value then
  begin
    FImagePosition := Value;
    Resize;
  end;

end;

procedure TTRM_ImageLabel.SetLabelCaption(const Value: string);
begin
  if FLabelCaption <> Value then
  begin
    FLabelCaption := Value;
    Resize;
  end;

end;

procedure TTRM_ImageLabel.SetLabelPosition(const Value: TSubPosition);
begin
  if FLabelPosition <> Value then
  begin
    FLabelPosition := Value;
    Resize;
  end;

end;

procedure TTRM_ImageLabel.ImageClick(Sender: TObject);
begin
  if Assigned(OnClick) then
    OnClick(Self);

end;

procedure TTRM_ImageLabel.ImageDblClick(Sender: TObject);
begin
  if Assigned(OnDblClick) then
    OnDblClick(Self);

end;

procedure TTRM_ImageLabel.ImageMouseEnter(Sender: TObject);
begin
  if Assigned(OnMouseEnter) then
    OnMouseEnter(Self);

end;

procedure TTRM_ImageLabel.ImageMouseLeave(Sender: TObject);
begin
  if Assigned(OnMouseLeave) then
    OnMouseLeave(Self);
end;

procedure TTRM_ImageLabel.LabelClick(Sender: TObject);
begin
  if Assigned(OnClick) then
    OnClick(Self);

end;

procedure TTRM_ImageLabel.LabelDblClick(Sender: TObject);
begin
  if Assigned(OnDblClick) then
    OnDblClick(Self);

end;

procedure TTRM_ImageLabel.LabelMouseEnter(Sender: TObject);
begin
  if Assigned(OnMouseEnter) then
    OnMouseEnter(Self);

end;

procedure TTRM_ImageLabel.LabelMouseLeave(Sender: TObject);
begin
  if Assigned(OnMouseLeave) then
    OnMouseLeave(Self);

end;

destructor TTRM_ImageLabel.Destroy;
begin
  FSubImage.Free;
  FSubLabel.Free;

  inherited Destroy;

end;

end.


LG Mathias

Sinspin 15. Mai 2024 13:43

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Hey,

Wie das genau geht lässt sich am besten herausfinden wenn Du dir die Quelltexte von TImage ansiehst.
Das ist eigentlich ganz einfach, wenn man weis wie es geht.

Grüße in die Stadt im Park.

himitsu 15. Mai 2024 14:15

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Hat das Image überhaupt ein Bild, welches es anzeigen könnte?



Die Free im Destroy sind nicht nötig, da du Self als Owner nutzt und somit dein ImageLabel das automatisch freigibt.

Wozu die leeren Try-Finally?

Im Create würde ich nicht strändig zwischen FSub... und Sub... wechseln, alleine schon von der Lesbarkeit her.
Ja, da es (aktuell) keinen Getter gibt, ist es am Ende technisch vollkommen irrelevant.

Sinspin 15. Mai 2024 16:34

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von himitsu (Beitrag 1536715)
Hat das Image überhaupt ein Bild, welches es anzeigen könnte?

Ja. TImage hat
Delphi-Quellcode:
property Picture
.

himitsu 15. Mai 2024 16:38

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Ja klar, aber auch dort auch jemand was reingeladen?

KodeZwerg 15. Mai 2024 22:46

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von himitsu (Beitrag 1536715)
Wozu die leeren Try-Finally?

Bei mir war es nur ein schneller runtime test, schubs einfach "Visible := True" ins finally :D
Zitat:

Zitat von himitsu (Beitrag 1536715)
Die Free im Destroy sind nicht nötig, da du Self als Owner nutzt und somit dein ImageLabel das automatisch freigibt.

Ich räum gerne auf :lol:

NoGAD 16. Mai 2024 08:14

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Hallo nochmal.

Ich habe die Komponente erweitert. Jetzt klappt es mit der Zuweisung "von außen" :-)

Eine weitere Frage habe ich aber: Kann man die Property Picture der Subkomponente entfernen, dass diese nicht mehr sichtbar ist?


Delphi-Quellcode:
unit TRM_ImageLabel;

(*

  TRM_ImageLabel erstellt von Mathias Fiege 2024

  www.nogad.de

  Open Source License
  Permission is hereby granted, free of charge, to any person obtaining a copy
  of this software component and associated documentation files (the "Software"),
  to deal in the Software without restriction, including without limitation the
  rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  sell copies of the Software, and to permit persons to whom the Software is
  furnished to do so, subject to the following conditions:

  The above copyright notice and this permission notice shall be included in all
  copies or substantial portions of the Software.

  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  THE SOFTWARE.

  Thanks and greetings to www.delphipraxis.net

*)

interface


uses
  System.SysUtils, System.Classes, System.Types, Vcl.Controls, Vcl.ExtCtrls, Vcl.Forms, Vcl.StdCtrls,
  Vcl.Imaging.GIFConsts,
  Vcl.Imaging.GIFImg,
  Vcl.Imaging.JConsts,
  Vcl.Imaging.jpeg,
  Vcl.Imaging.pngimage,
  Vcl.Imaging.pnglang,
  Vcl.Graphics;

const
  _version = '2024.05.16.0913';

type
  TSubPosition = (lpNone, lpTop, lpBottom, lpLeft, lpRight, lpClient, lpCustom);

  TTRM_ImageLabel = class(TCustomPanel)
  private
    FSubImage: TImage;
    FImagePosition: TSubPosition;
    FImagePicture: TPicture;

    FSubLabel: TLabel;
    FLabelCaption: String;
    FLabelPosition: TSubPosition;

    FVersion: String;

    procedure SetImagePosition(const Value: TSubPosition);
    procedure PictureChanged(Sender: TObject);
    procedure SetPicture(Value: TPicture);

    procedure SetLabelCaption(const Value: String);
    procedure SetLabelPosition(const Value: TSubPosition);

    procedure ImageClick(Sender: TObject);
    procedure ImageDblClick(Sender: TObject);
    procedure ImageMouseEnter(Sender: TObject);
    procedure ImageMouseLeave(Sender: TObject);

    procedure LabelClick(Sender: TObject);
    procedure LabelDblClick(Sender: TObject);
    procedure LabelMouseEnter(Sender: TObject);
    procedure LabelMouseLeave(Sender: TObject);
  protected
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
    procedure Resize; override;
  published
    property SubImage: TImage read FSubImage;
    property SubLabel: TLabel read FSubLabel;
    property Align;
    property Anchors;

    property BevelInner;
    property BevelKind;
    property BevelOuter;
    property BevelWidth;
    property BorderStyle;
    property BorderWidth;
    property Caption;
    property Ctl3D;
    property Cursor;
    property ParentBackground;
    property PopupMenu;

    property OnClick;
    property OnDblClick;
    property OnMouseEnter;
    property OnMouseLeave;

    property ImagePosition: TSubPosition read FImagePosition write SetImagePosition;
    property ImagePicture: TPicture read FImagePicture write SetPicture;

    property LabelCaption: String read FLabelCaption write SetLabelCaption;
    property LabelPosition: TSubPosition read FLabelPosition write SetLabelPosition;

    property Version: String read FVersion;

  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('TRM', [TTRM_ImageLabel]);

end;

{ TTRM_ImageLabel }

constructor TTRM_ImageLabel.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  Self.Parent := TWinControl(AOwner);

  FSubImage := TImage.Create(Self);
  FSubImage.SetSubComponent(True);
  FSubImage.Parent := Self;
  FSubImage.Align := alClient;
  FSubImage.Center := True;
  FSubImage.OnClick := ImageClick;
  FSubImage.OnDblClick := ImageDblClick;
  FSubImage.OnMouseEnter := ImageMouseEnter;
  FSubImage.OnMouseLeave := ImageMouseLeave;

  FSubLabel := TLabel.Create(Self);
  FSubLabel.SetSubComponent(True);
  FSubLabel.Parent := Self;
  FSubLabel.Align := alBottom;
  FSubLabel.AutoSize := True;
  FSubLabel.Height := 25;
  FSubLabel.AlignWithMargins := False;
  FSubLabel.Margins.Left := 0;
  FSubLabel.Margins.Right := 0;
  FSubLabel.Margins.Top := 8;
  FSubLabel.Margins.Bottom := 0;
  FSubLabel.Caption := '...';
  FSubLabel.Font.Size := 14;
  FSubLabel.OnClick := LabelClick;
  FSubLabel.OnDblClick := LabelDblClick;
  FSubLabel.OnMouseEnter := LabelMouseEnter;
  FSubLabel.OnMouseLeave := LabelMouseLeave;

  FImagePicture := TPicture.Create;
  FImagePicture.OnChange := PictureChanged;

  Self.Width := 64;
  Self.Height := 89;
  Self.AlignWithMargins := True;
  Self.Margins.Top := 0;
  Self.Margins.Left := 8;
  Self.Margins.Right := 8;
  Self.Margins.Bottom := 0;
  Self.BevelInner := bvNone;
  Self.BevelKind := bkNone;
  Self.BevelOuter := bvNone;
  Self.BevelWidth := 1;
  Self.BorderStyle := bsNone;
  Self.BorderWidth := 0;
  Self.Caption := '';
  Self.Ctl3D := False;
  Self.Cursor := crHandPoint;
  Self.ParentBackground := True;

  FVersion := _version;

  FImagePosition := lpClient;
  FLabelPosition := lpBottom;

  Update;
  Resize;

end;

procedure TTRM_ImageLabel.Resize;
begin
  (* lpNone, lpTop, lpBottom, lpLeft, lpRight, lpClient, lpCustom *)
  inherited;
  case FLabelPosition of
    lpNone:
      begin
        FSubLabel.Align := alNone;
      end;
    lpTop:
      begin
        FSubLabel.Align := alTop;
      end;
    lpBottom:
      begin
        FSubLabel.Align := alBottom;
      end;
    lpLeft:
      begin
        FSubLabel.Align := alLeft;
      end;
    lpRight:
      begin
        FSubLabel.Align := alRight;
      end;
    lpClient:
      begin
        FSubLabel.Align := alClient;
      end;
    lpCustom:
      begin
        FSubLabel.Align := alCustom;
      end;
  end;

  case FImagePosition of
    lpNone:
      begin
        FSubImage.Align := alNone;
      end;
    lpTop:
      begin
        FSubImage.Align := alTop;
      end;
    lpBottom:
      begin
        FSubImage.Align := alBottom;
      end;
    lpLeft:
      begin
        FSubImage.Align := alLeft;
      end;
    lpRight:
      begin
        FSubImage.Align := alRight;
      end;
    lpClient:
      begin
        FSubImage.Align := alClient;
      end;
    lpCustom:
      begin
        FSubImage.Align := alCustom;
      end;
  end;

  FSubLabel.Caption := FLabelCaption;

  Update;

end;

procedure TTRM_ImageLabel.SetImagePosition(const Value: TSubPosition);
begin
  if FImagePosition <> Value then
  begin
    FImagePosition := Value;
    Resize;
  end;

end;

procedure TTRM_ImageLabel.SetPicture(Value: TPicture);
begin
  FImagePicture.Assign(Value);
  FSubImage.Picture.Assign(FImagePicture);

end;

procedure TTRM_ImageLabel.PictureChanged(Sender: TObject);
begin
  Repaint;

end;

procedure TTRM_ImageLabel.SetLabelCaption(const Value: string);
begin
  if FLabelCaption <> Value then
  begin
    FLabelCaption := Value;
    Resize;
  end;

end;

procedure TTRM_ImageLabel.SetLabelPosition(const Value: TSubPosition);
begin
  if FLabelPosition <> Value then
  begin
    FLabelPosition := Value;
    Resize;
  end;

end;

procedure TTRM_ImageLabel.ImageClick(Sender: TObject);
begin
  if Assigned(OnClick) then
    OnClick(Self);

end;

procedure TTRM_ImageLabel.ImageDblClick(Sender: TObject);
begin
  if Assigned(OnDblClick) then
    OnDblClick(Self);

end;

procedure TTRM_ImageLabel.ImageMouseEnter(Sender: TObject);
begin
  if Assigned(OnMouseEnter) then
    OnMouseEnter(Self);

end;

procedure TTRM_ImageLabel.ImageMouseLeave(Sender: TObject);
begin
  if Assigned(OnMouseLeave) then
    OnMouseLeave(Self);
end;

procedure TTRM_ImageLabel.LabelClick(Sender: TObject);
begin
  if Assigned(OnClick) then
    OnClick(Self);

end;

procedure TTRM_ImageLabel.LabelDblClick(Sender: TObject);
begin
  if Assigned(OnDblClick) then
    OnDblClick(Self);

end;

procedure TTRM_ImageLabel.LabelMouseEnter(Sender: TObject);
begin
  if Assigned(OnMouseEnter) then
    OnMouseEnter(Self);

end;

procedure TTRM_ImageLabel.LabelMouseLeave(Sender: TObject);
begin
  if Assigned(OnMouseLeave) then
    OnMouseLeave(Self);

end;

destructor TTRM_ImageLabel.Destroy;
begin
  FSubImage.Free;
  FSubLabel.Free;
  FImagePicture.Free;

  inherited Destroy;

end;

end.

Sinspin 16. Mai 2024 09:52

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Warum hast Du die Subkomponenten eigentlich sichtbar? Was willst Du in denen einstellen was dir nicht woanders Ärger macht?

Bei guten komponenten gäbe es unterhalb von TImage ein TCommonImage. TImage würde keine andere Function haben außer alle Properties auf published zu setzen. Eine Ableitung von TCommonImage würde dir dann erlauben wegzulassen was du nicht brauchst.

Aber hier geht das genauso TImage -> TMyImage. Alle Properties die Du nicht brauchst deklarierst Du unter public und nicht published.

NoGAD 16. Mai 2024 11:25

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von Sinspin (Beitrag 1536737)
Warum hast Du die Subkomponenten eigentlich sichtbar?

Hallo Stefan,

weil ich nicht weiß, wie es anders gemacht wird und angenommen hatte, dass properties immer in published gehören. Ich mache die Programmiererei als Hobby, bin kein gelernter Programmierer.

Ich versuche nachher nochmals die Subkomponenten nicht ins published zu stecken. :-)

Danke für die Hilfe.

NoGAD 16. Mai 2024 13:13

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Huhu.

Scheinbar habe ich einige Prizipien nicht gelernt/verstanden.

Nachdem ich die beiden Subkomponenten verschoben abe, ist es mir nicht mehr möglich, Standard-Eigenschaften von den Komponenten anzusprechen.

Delphi-Quellcode:
  public
    property SubImage: TImage read FSubImage;
    property SubLabel: TLabel read FSubLabel;
Jetzt müsste ich der Hauptkomponente also alle Eigenschaften, die ich später im Code setzten möchte, noch hinzufügen.

Wo liegt jetzt der Vorteil in dieser Vorgensweise?

LG nach Dubai :-)

Sinspin 16. Mai 2024 14:37

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von NoGAD (Beitrag 1536761)
Jetzt müsste ich der Hauptkomponente also alle Eigenschaften, die ich später im Code setzten möchte, noch hinzufügen.

Wo liegt jetzt der Vorteil in dieser Vorgensweise?

Das hängt davon ab was Du vorhast, ob das ein Vorteil ist oder nicht.
Ich habe Komponenten die fassen 5 oder 6 andere in einer zusammen. Die möchte ich nicht alle im Property Editor haben.
Ich lege für die dann aber garkein Property an. Ich habe ja die lokale Variable im Object.

Aber, für alles was Du nur im Code setzen willst brauchst Du ja nicht wirklich Properties. Nur was über den Editor zur Designzeit einstellbar sein soll muss zwingend ein Property bekommen.
Durch Getter und Setter hat man bestimmte Vorteile. Ich liebe Properties dafür. Aber die sind bei mir trotzdem nur public oder protected deklariert. Nicht published. Denn ich brauche sie nicht sichtbar zur Designzeit.

Zitat:

Zitat von NoGAD (Beitrag 1536747)
weil ich nicht weiß, wie es anders gemacht wird und angenommen hatte, dass properties immer in published gehören. Ich mache die Programmiererei als Hobby, bin kein gelernter Programmierer.

Keine Sorge, es ist absolut egal warum du programmierst. Wer nett fragt bekommt Hilfe.

NoGAD 17. Mai 2024 08:16

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Guten Morgen.

Hier ist ein Test, damit ich das Prinzip verstehen kann.

Was mir jetzt fehlt, sind folgende Properties:
Falls möglich, hätte ich die gerne gebündelt dargestellt, will heißen, im ObjectExplorer sollte z.B.:

Code:
aImage + (aufklappbar)
  - Caption
  - Visible
aImage + (aufklappbar)
  - Picture
  - Visible
[..] (weitere property)
erreichbar sein.

Code:
TMyLabel ->
    property Caption;
    property Visible; // als Test

TMyImage ->
    property Picture;
    property Visible; // auch ein Test
Delphi-Quellcode:
unit ImageLabelTEST;

interface

uses
  System.SysUtils, System.Classes, Vcl.Controls, Vcl.StdCtrls, Vcl.ExtCtrls, Vcl.Graphics, Vcl.Forms;

type
  TMyImage = class(TImage)
  private
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
  published
    property Picture;
    property Visible;
  end;

  TMyLabel = class(TLabel)
  private
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
  published
    property Caption;
    property Visible;
  end;

  TImageLabelTEST = class(TCustomControl)
  private
    FImage: TMyImage;
    FLabel: TMyLabel;

    function GetImage: TPicture;
    procedure SetImage(const Value: TPicture);

    function GetLabelCaption: TCaption;
    procedure SetLabelCaption(const Value: TCaption);
    function GetLabelFont: TFont;
    procedure SetLabelFont(const Value: TFont);
  protected
    procedure Resize; override;
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
    property aImage: TMyImage read FImage;
    property aLabel: TMyLabel read FLabel;
  published
// folgende properties würde ich gerne mit den properties aus den eigenen Subkomponenten ersetzen
    property I_Picture: TPicture read GetImage write SetImage;

    property L_Caption: TCaption read GetLabelCaption write SetLabelCaption;
    property L_Font: TFont read GetLabelFont write SetLabelFont;

    property Align;
    property Anchors;
    property Visible;
  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('TRM', [TImageLabelTEST]);
end;

{ TMyImage }
constructor TMyImage.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);

end;

destructor TMyImage.Destroy;
begin
  Self.Free;
  inherited Destroy;

end;

{ TMyLabel }
constructor TMyLabel.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);

end;

destructor TMyLabel.Destroy;
begin
  Self.Free;
  inherited Destroy;

end;

{ TImageLabel }
constructor TImageLabelTEST.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);

  FImage := TMyImage.Create(Self);
  FImage.Parent := Self;
  FImage.Align := alTop;
  FImage.Height := 100;

  FLabel := TMyLabel.Create(Self);
  FLabel.Parent := Self;
  FLabel.Align := alClient;
  FLabel.Alignment := taCenter;
end;

procedure TImageLabelTEST.Resize;
begin
  inherited;

end;

function TImageLabelTEST.GetImage: TPicture;
begin
  Result := FImage.Picture;

end;

procedure TImageLabelTEST.SetImage(const Value: TPicture);
begin
  FImage.Picture.Assign(Value);

end;

function TImageLabelTEST.GetLabelCaption: TCaption;
begin
  Result := FLabel.Caption;

end;

procedure TImageLabelTEST.SetLabelCaption(const Value: TCaption);
begin
  FLabel.Caption := Value;

end;

function TImageLabelTEST.GetLabelFont: TFont;
begin
  Result := FLabel.Font;

end;

procedure TImageLabelTEST.SetLabelFont(const Value: TFont);
begin
  FLabel.Font.Assign(Value);

end;

destructor TImageLabelTEST.Destroy;
begin
  FImage.Free;
  FLabel.Free;
  inherited Destroy;

end;

end.

Sinspin 17. Mai 2024 12:31

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Zitat:

Zitat von NoGAD (Beitrag 1536785)
Delphi-Quellcode:
// folgende properties würde ich gerne mit den properties aus den eigenen Subkomponenten ersetzen
    property I_Picture: TPicture read GetImage write SetImage;

    property L_Caption: TCaption read GetLabelCaption write SetLabelCaption;
    property L_Font: TFont read GetLabelFont write SetLabelFont;
Delphi-Quellcode:
type
  TMyImage = class(TImage)
  private
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
  published
    property Picture;
    property Visible;
  end;

  TMyLabel = class(TLabel)
  private
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
  published
    property Caption;
    property Visible;
  end;

Wenn die Komponenten in Delphi schöner implementiert wären, wäre das so einfach wie in deinem Beispiel. Leider ist es nicht so einfach.
Alles was Du nicht unter published haben willst must Du in deiner Ableitung als public deklarieren. Weglassen bedeutet das es in der gleichen Sichtbarkeit bleibt wie es ist.

Dann könntest du das so machen:
Delphi-Quellcode:
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
  published
    property ImageProps: TMyImage read FImage;
    property LabelProps: TMyLabel read FLabel;

    property Align;
    property Anchors;
    property Visible;
  end;

NoGAD 17. Mai 2024 20:04

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Ich verzweifle bald ;-)

Testweise habe ich in den SubComponenten Anchors beim TImage und Caption beim TLabel in public verschoben.

Dennoch sind die weiterhin im Objectexplorer sichtbar und auch änderbar.

Wo ist denn mein Fehler im Code, damit die beiden Properties nicht mehr angezeigt werden?


Delphi-Quellcode:
unit ImageLabelTEST;

interface

uses
  System.SysUtils, System.Classes, Vcl.Controls, Vcl.StdCtrls, Vcl.ExtCtrls, Vcl.Graphics, Vcl.Forms;

type
  { TMyImage }
  TMyImage = class(TImage)
  private
  protected
  public
    property Anchors;
  published
  end;

  { TMyLabel }
  TMyLabel = class(TLabel)
  private
  protected
  public
    property Caption;
  published
  end;

  { TIMageLabelTest }
  TImageLabelTEST = class(TCustomControl)
  private
    MyImage: TMyImage;
    MyLabel: TMyLabel;
  protected
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
    procedure Resize; override;
  published
    property MySubImage: TMyImage read MyImage;
    property MySubLabel: TMyLabel read MyLabel;
  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('TRM', [TImageLabelTEST]);
end;

{ TMyImage }

{ TMyLabel }

{ TImageLabel }
constructor TImageLabelTEST.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  Self.Parent := TWinControl(AOwner);

  MyImage := TMyImage.Create(Self);
  MyImage.SetSubComponent(True);
  MyImage.Parent := Self;

  MyLabel := TMyLabel.Create(Self);
  MyLabel.SetSubComponent(True);
  MyLabel.Parent := Self;

end;

procedure TImageLabelTEST.Resize;
begin
  inherited;

end;

destructor TImageLabelTEST.Destroy;
begin
  MyImage.Free;
  MyLabel.Free;
  inherited Destroy;

end;

end.
LG Mathias

NoGAD 18. Mai 2024 23:17

AW: Komponente (TImage & TLabel) -> Image wird nicht angezeigt
 
Hallo an alle.

Danke für eure Hilfen.

Inzwischen habe ich meine Komponente erweitert und bin zufrieden damit :-)

Delphi-Quellcode:
unit TRM_ImageLabel;

(*

  TRM_ImageLabel erstellt von Mathias Fiege 2024

  www.nogad.de

  Open Source License
  Permission is hereby granted, free of charge, to any person obtaining a copy
  of this software component and associated documentation files (the "Software"),
  to deal in the Software without restriction, including without limitation the
  rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
  sell copies of the Software, and to permit persons to whom the Software is
  furnished to do so, subject to the following conditions:

  The above copyright notice and this permission notice shall be included in all
  copies or substantial portions of the Software.

  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  THE SOFTWARE.

  Thanks and greetings to www.delphipraxis.net

*)

interface


uses
  System.Classes,
  Vcl.Controls,
  Vcl.ExtCtrls,
  Vcl.Forms,
  Vcl.Imaging.GIFConsts,
  Vcl.Imaging.GIFImg,
  Vcl.Imaging.JConsts,
  Vcl.Imaging.jpeg,
  Vcl.Imaging.pngimage,
  Vcl.Imaging.pnglang,
  Vcl.StdCtrls,
  Vcl.Graphics;

const
  _version = '2024.05.19.0015';

type

  TTRM_ImageLabel = class(TCustomPanel)
  private
    FSubImage: TImage;
    FSubImageAlign: TAlign;

    FSubLabel: TLabel;
    FSubLabelCaption: String;
    FSubLabelAlign: TAlign;

    FPictureDefault: TPicture;
    FPictureHover: TPicture;
    FPictureLeave: TPicture;

    FHoverLeaveLabel: Boolean;
    FHoverLeaveImage: Boolean;

    FVersion: String;

    function GetSubImageAlign: TAlign;
    procedure SetSubImageAlign(Value: TAlign);

    function GetPictureDefault: TPicture;
    procedure SetPictureDefault(Value: TPicture);
    procedure ChangePictureDefault(Sender: TObject);
    function GetPictureHover: TPicture;
    procedure SetPictureHover(Value: TPicture);
    function GetPictureLeave: TPicture;
    procedure SetPictureLeave(Value: TPicture);

    function GetLabelCaption: String;
    procedure SetLabelCaption(const Value: String);
    function GetSubLabelAlign: TAlign;
    procedure SetSubLabelAlign(Value: TAlign);

    procedure ImageClick(Sender: TObject);
    procedure ImageDblClick(Sender: TObject);
    procedure ImageMouseEnter(Sender: TObject);
    procedure ImageMouseLeave(Sender: TObject);

    procedure LabelClick(Sender: TObject);
    procedure LabelDblClick(Sender: TObject);
    procedure LabelMouseEnter(Sender: TObject);
    procedure LabelMouseLeave(Sender: TObject);

  protected
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;

  published
    property SubImage: TImage read FSubImage;
    property SubLabel: TLabel read FSubLabel;

    property Align;
    property Anchors;
    property BevelInner;
    property BevelKind;
    property BevelOuter;
    property BevelWidth;
    property BorderWidth;
    property BorderStyle;
    property Caption;
    property Ctl3D;
    property Cursor;
    property ParentBackground;
    property PopupMenu;

    property OnClick;
    property OnDblClick;
    property OnMouseEnter;
    property OnMouseLeave;

    property PictureDefault: TPicture read GetPictureDefault write SetPictureDefault;
    property PictureHover: TPicture read GetPictureHover write SetPictureHover;
    property PictureLeave: TPicture read GetPictureLeave write SetPictureLeave;

    property HoverLeaveLabel: Boolean read FHoverLeaveLabel write FHoverLeaveLabel default True;
    property HoverLeaveImage: Boolean read FHoverLeaveImage write FHoverLeaveImage default True;

    property ImageAlign: TAlign read GetSubImageAlign write SetSubImageAlign default alClient;

    property LabelCaption: String read GetLabelCaption write SetLabelCaption;
    property LabelAlign: TAlign read GetSubLabelAlign write SetSubLabelAlign default alBottom;

    property Version: String read FVersion;

  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('TRM', [TTRM_ImageLabel]);
end;

{ TTRM_ImageLabel }

constructor TTRM_ImageLabel.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  Self.Parent := TWinControl(AOwner);

  FSubImage := TImage.Create(Self);
  FSubImage.SetSubComponent(True);
  FSubImage.Parent := Self;
  // FSubImage.Align := alClient;
  FSubImage.Center := True;
  FSubImage.OnClick := ImageClick;
  FSubImage.OnDblClick := ImageDblClick;
  FSubImage.OnMouseEnter := ImageMouseEnter;
  FSubImage.OnMouseLeave := ImageMouseLeave;

  FSubLabel := TLabel.Create(Self);
  FSubLabel.SetSubComponent(True);
  FSubLabel.Parent := Self;
  // FSubLabel.Align := alBottom;
  FSubLabel.AutoSize := True;
  FSubLabel.Height := 25;
  FSubLabel.AlignWithMargins := False;
  FSubLabel.Margins.Left := 0;
  FSubLabel.Margins.Right := 0;
  FSubLabel.Margins.Top := 8;
  FSubLabel.Margins.Bottom := 0;
  FSubLabel.Caption := '...';
  FSubLabel.Font.Size := 14;
  FSubLabel.OnClick := LabelClick;
  FSubLabel.OnDblClick := LabelDblClick;
  FSubLabel.OnMouseEnter := LabelMouseEnter;
  FSubLabel.OnMouseLeave := LabelMouseLeave;

  FPictureDefault := TPicture.Create;
  FPictureDefault.OnChange := ChangePictureDefault;
  FPictureHover := TPicture.Create;
  FPictureLeave := TPicture.Create;

  Self.Width := 64;
  Self.Height := 89;
  Self.AlignWithMargins := True;
  Self.Margins.Top := 0;
  Self.Margins.Left := 8;
  Self.Margins.Right := 8;
  Self.Margins.Bottom := 0;
  Self.BevelInner := bvNone;
  Self.BevelKind := bkNone;
  Self.BevelOuter := bvNone;
  Self.BevelWidth := 1;
  Self.BorderStyle := bsNone;
  Self.BorderWidth := 0;
  Self.Caption := '';
  Self.Ctl3D := False;
  Self.Cursor := crHandPoint;
  Self.ParentBackground := True;

  HoverLeaveLabel := True;
  HoverLeaveImage := True;

  ImageAlign := alClient;

  LabelAlign := alBottom;

  FVersion := _version;

end;

function TTRM_ImageLabel.GetSubImageAlign: TAlign;
begin
  Result := FSubImageAlign;
  FSubImage.Align := FSubImageAlign;
  Repaint;

end;

procedure TTRM_ImageLabel.SetSubImageAlign(Value: TAlign);
begin
  if FSubImageAlign <> Value then
  begin
    FSubImageAlign := Value;
    FSubImage.Align := FSubImageAlign;
    Repaint;
  end;

end;

function TTRM_ImageLabel.GetPictureDefault: TPicture;
begin
  Result := FPictureDefault;
  FSubImage.Picture.Assign(FPictureDefault);
  Repaint;

end;

procedure TTRM_ImageLabel.SetPictureDefault(Value: TPicture);
begin
  if FPictureDefault <> Value then
  begin
    FPictureDefault.Assign(Value);
    FSubImage.Picture.Assign(FPictureDefault);
    Repaint;
  end;

end;

procedure TTRM_ImageLabel.ChangePictureDefault(Sender: TObject);
begin
  FSubImage.Picture.Assign(FPictureDefault);
  Repaint;

end;

function TTRM_ImageLabel.GetPictureHover: TPicture;
begin
  Result := FPictureHover;

end;

procedure TTRM_ImageLabel.SetPictureHover(Value: TPicture);
begin
  if FPictureHover <> Value then
    FPictureHover.Assign(Value);

end;

function TTRM_ImageLabel.GetPictureLeave: TPicture;
begin
  Result := FPictureLeave;

end;

procedure TTRM_ImageLabel.SetPictureLeave(Value: TPicture);
begin
  if FPictureLeave <> Value then
    FPictureLeave.Assign(Value);

end;

function TTRM_ImageLabel.GetLabelCaption: String;
begin
  if FSubLabelCaption = '' then
    Result := SubLabel.Caption
  else
    Result := FSubLabelCaption;

  Repaint;

end;

procedure TTRM_ImageLabel.SetLabelCaption(const Value: string);
begin
  if FSubLabelCaption <> Value then
  begin
    FSubLabelCaption := Value;
    Self.SubLabel.Caption := FSubLabelCaption;
    Repaint;
  end;

end;

function TTRM_ImageLabel.GetSubLabelAlign: TAlign;
begin
  Result := FSubLabelAlign;
  FSubLabel.Align := FSubLabelAlign;
  Repaint;

end;

procedure TTRM_ImageLabel.SetSubLabelAlign(Value: TAlign);
begin
  if FSubLabelAlign <> Value then
  begin
    FSubLabelAlign := Value;
    FSubLabel.Align := FSubLabelAlign;
    Repaint;
  end;

end;

procedure TTRM_ImageLabel.ImageClick(Sender: TObject);
begin
  if assigned(OnClick) then
    inherited OnClick(Self);

end;

procedure TTRM_ImageLabel.ImageDblClick(Sender: TObject);
begin
  if assigned(OnDblClick) then
    inherited OnDblClick(Self);

end;

procedure TTRM_ImageLabel.ImageMouseEnter(Sender: TObject);
begin
  if HoverLeaveImage then
  begin
    Self.SubImage.Picture.Assign(FPictureHover);
    Repaint;
  end;
  if assigned(OnMouseEnter) then
    inherited OnMouseEnter(Self);

end;

procedure TTRM_ImageLabel.ImageMouseLeave(Sender: TObject);
begin
  if HoverLeaveImage then
  begin
    Self.SubImage.Picture.Assign(FPictureLeave);
    Repaint;
  end;
  if assigned(OnMouseLeave) then
    inherited OnMouseLeave(Self);
end;

procedure TTRM_ImageLabel.LabelClick(Sender: TObject);
begin
  if assigned(OnClick) then
    inherited OnClick(Self);

end;

procedure TTRM_ImageLabel.LabelDblClick(Sender: TObject);
begin
  if assigned(OnDblClick) then
    inherited OnDblClick(Self);

end;

procedure TTRM_ImageLabel.LabelMouseEnter(Sender: TObject);
begin
  if FHoverLeaveLabel then
  begin
    Self.SubImage.Picture.Assign(FPictureHover);
    Repaint;
  end;
  if assigned(OnMouseEnter) then
    inherited OnMouseEnter(Self);

end;

procedure TTRM_ImageLabel.LabelMouseLeave(Sender: TObject);
begin
  if FHoverLeaveLabel then
  begin
    Self.SubImage.Picture.Assign(FPictureLeave);
    Repaint;
  end;
  if assigned(OnMouseLeave) then
    inherited OnMouseLeave(Self);

end;

destructor TTRM_ImageLabel.Destroy;
begin
  FSubImage.Free;
  FSubLabel.Free;

  FPictureDefault.Free;
  FPictureHover.Free;
  FPictureLeave.Free;

  inherited Destroy;

end;

end.
LG und ein schönes langes Wochenende
~Mathias


Alle Zeitangaben in WEZ +1. Es ist jetzt 05:18 Uhr.

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz