Hi,
ich habe eine Komponente von TScrollBox abgeleitet und die Refresh Routine wie folgt überschrieben:
Delphi-Quellcode:
procedure TBeeperList.Refresh;
var
i, x: Integer;
NewPanel: TPanel;
NewLabel1, NewLabel2: TLabel;
NewImage1, NewImage2: TImage;
NewBevel: TBevel;
CurrFontColor, CurrColor: TColor;
begin
inherited Refresh;
if not (csDesigning in ComponentState) then
begin
if ControlCount > FItems.Count then
begin
//überflüssige Einträge entfernen falls schon welche vorhanden sind
for i := ControlCount -1 downto (ControlCount - FItems.Count) do
begin
if Controls[i] is TPanel then
(Controls[i] as TPanel).Free;
end;
end
else if ControlCount < FItems.Count then
begin
//evtl. neue Einträge hinzufügen
for i := 0 to (FItems.Count - ControlCount) -1 do
begin
NewPanel := TPanel.Create(Self);
with NewPanel do
begin
Parent := Self;
Caption := '';
BevelInner := bvNone;
BevelOuter := bvNone;
OnClick := ItemClick;
ParentBackground := False;
Align := alTop;
Height := 50;
NewLabel1 := TLabel.Create(NewPanel);
with NewLabel1 do
begin
Parent := NewPanel;
Font.Style := [fsBold];
Caption := (Items.Items[i] as TBeeperListItem).Title;
Left := 8;
Top := 8;
Transparent := True;
Hint := '2';
OnClick := ItemClick;
end;
NewImage2 := TImage.Create(NewPanel);
with NewImage2 do
begin
Parent := NewPanel;
Visible := (Items.Items[i] as TBeeperListItem).ShowRightIcon;
Left := NewPanel.Width - 24; //47
Top := 8;
Height := 16;
Width := 16;
Transparent := True;
Picture.Assign(FRightIcon);
Anchors := [akRight, akTop];
Hint := '2';
OnClick := ItemClick;
end;
NewImage1 := TImage.Create(NewPanel);
with NewImage1 do
begin
Parent := NewPanel;
Visible := (Items.Items[i] as TBeeperListItem).ShowDescriptionIcon;
Left := 8;
Top := 27;
Height := 16;
Width := 16;
Picture.Assign(FDescriptionIcon);
Transparent := True;
Hint := '1';
OnClick := ItemClick;
end;
NewLabel2 := TLabel.Create(NewPanel);
with NewLabel2 do
begin
Parent := NewPanel;
Caption := (Items.Items[i] as TBeeperListItem).Description;
Left := 30;
Top := 27;
Transparent := True;
Hint := '1';
OnClick := ItemClick;
end;
NewBevel := TBevel.Create(NewPanel);
with NewBevel do
begin
Align := alBottom;
Parent := NewPanel;
Height := 2;
Shape := bsTopLine;
OnClick := ItemClick;
Visible := False;
end;
end;
end;
end;
//und jetzt Attribute setzen
for i := 0 to ControlCount -1 do
begin
if Controls[i] is TPanel then
begin
with Controls[i] as TPanel do
begin
CurrFontColor := clBlack;
CurrColor := clWhite;
if FItemIndex = i then //wenn Eintrag = selektiert, dann anders darstellen
begin
CurrFontColor := clHighlightText;
CurrColor := clHighlight;
end;
Color := CurrColor;
Font.Color := CurrFontColor;
Tag := i;
Top := i * 50;
for x := 0 to ControlCount -1 do //Unterelemente anpassen
begin
if Controls[i] is TLabel then
begin
(Controls[i] as TLabel).Font.Color := CurrFontColor;
(Controls[i] as TLabel).Tag := i;
if StrToTimeDef((Controls[i] as TLabel).Hint, 1) = 1 then
(Controls[i] as TLabel).Caption := (FItems.Items[i] as TBeeperListItem).Title
else
(Controls[i] as TLabel).Caption := (FItems.Items[i] as TBeeperListItem).Description;
(Controls[i] as TLabel).Refresh;
end
else if Controls[i] is TBevel then
begin
(Controls[i] as TBevel).Visible := CurrColor = clHighlight;
(Controls[i] as TBevel).Tag := i;
end
else if Controls[i] is TImage then
begin
(Controls[i] as TImage).Tag := i;
if StrToTimeDef((Controls[i] as TImage).Hint, 1) = 1 then
(Controls[i] as TImage).Visible := (FItems.Items[i] as TBeeperListItem).ShowDescriptionIcon
else
(Controls[i] as TImage).Visible := (FItems.Items[i] as TBeeperListItem).ShowRightIcon;
end;
end;
end;
end;
end;
end;
end;
FItems ist eine Collection. TBeeperListItem ist wie folgt aufgebaut:
Delphi-Quellcode:
TBeeperListItem = class(TCollectionItem)
private
FTitle: String;
FDescription: String;
FShowDescriptionIcon: Boolean;
FShowRightIcon: Boolean;
published
property Title: String read FTitle write FTitle;
property Description: String read FDescription write FDescription;
property ShowRightIcon: Boolean read FShowRightIcon write FShowRightIcon;
property ShowDescriptionIcon: Boolean read FShowDescriptionIcon write FShowDescriptionIcon;
end;
Beim ersten Aufruf von Refresh sieht alles auch ganz toll aus (siehe Anhang1). Beim Klick auf einen Eintrag wird dann der ItemIndex gesetzt. Folgende Setter-Routine habe ich definiert:
Delphi-Quellcode:
procedure TBeeperList.SetItemIndex(Value: Integer);
begin
if (FItemIndex <> Value) and (Value <= FItems.Count -1) then
begin
FItemIndex := Value;
Refresh;
end;
end;
Es wird also Refresh aufgerufen um den neuen Eintrag zu markieren. Es wird aber die Farbe des ersten Labels nicht gesetzt (siehe Anhang2). Ich komm' nicht drauf warum das so ist. Jemand eine Idee?