ActiveDelphi - Índice do Fórum ActiveDelphi
.: O site do programador Delphi! :.
 
 FAQFAQ   PesquisarPesquisar   MembrosMembros   GruposGrupos   RegistrarRegistrar 
 PerfilPerfil   Entrar e ver Mensagens ParticularesEntrar e ver Mensagens Particulares   EntrarEntrar 

ListBox personalizado

 
Novo Tópico   Responder Mensagem    ActiveDelphi - Índice do Fórum -> Delphi
Exibir mensagem anterior :: Exibir próxima mensagem  
Autor Mensagem
jrman
Novato
Novato


Registrado: Sexta-Feira, 24 de Fevereiro de 2017
Mensagens: 80

MensagemEnviada: Qui Jun 08, 2017 9:48 am    Assunto: ListBox personalizado Responder com Citação

Bom dia pessoal, estou enrolado na construção de um listBox, preciso que ele fique assim:

Eu sei fazer um simples com header control...mas como ficaria dessa forma?
Tem como colocar dois textos (um em baixo do outro) na mesma linha com tamanhos diferentes? ou deve ser outra linha?
E a imagem? tem como pegar duas linhas?

Muito Obrigado!
Voltar ao Topo
Ver o perfil de Usuários Enviar Mensagem Particular
joemil
Moderador
Moderador


Registrado: Quinta-Feira, 25 de Março de 2004
Mensagens: 9100
Localização: Sinop-MT

MensagemEnviada: Qui Jun 08, 2017 3:23 pm    Assunto: Responder com Citação

vc esta usando FMX? ou a VCL mesmo?
_________________
<b>SEMPRE COLOQUE [RESOLVIDO] NO SEU POST</b>
Enviar imagens: http://tinypic.com/
Voltar ao Topo
Ver o perfil de Usuários Enviar Mensagem Particular
jrman
Novato
Novato


Registrado: Sexta-Feira, 24 de Fevereiro de 2017
Mensagens: 80

MensagemEnviada: Sex Jun 09, 2017 8:30 am    Assunto: Responder com Citação

É VCL....
Obrigado!
Voltar ao Topo
Ver o perfil de Usuários Enviar Mensagem Particular
joemil
Moderador
Moderador


Registrado: Quinta-Feira, 25 de Março de 2004
Mensagens: 9100
Localização: Sinop-MT

MensagemEnviada: Sex Jun 09, 2017 9:10 am    Assunto: Responder com Citação

complicado fazer isso no listbox. melhor usar o ListView. tem varios exemplos na net
_________________
<b>SEMPRE COLOQUE [RESOLVIDO] NO SEU POST</b>
Enviar imagens: http://tinypic.com/
Voltar ao Topo
Ver o perfil de Usuários Enviar Mensagem Particular
johnny-walker
Moderador
Moderador


Registrado: Sábado, 4 de Outubro de 2003
Mensagens: 10653
Localização: Contagem/MG - BRAZIL

MensagemEnviada: Sex Jun 09, 2017 7:39 pm    Assunto: Responder com Citação

Eis aí, mas claro que você terá de adaptar às suas necessidades, são dois códigos, um com o formato que você quer e outro com as imagens, basta você implementar com o outro as imagens:



Código:
unit UMain;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, ExtCtrls, StdCtrls, ImgList, Buttons;

type
  TForm1 = class(TForm)
    lsbRight: TListBox;
    ImageList1: TImageList;
    StaticText1: TStaticText;
    lsbLeft: TListBox;
    imgHouse: TImage;
    imgHouseGray: TImage;
    SpeedButton1: TSpeedButton;
    procedure FormCreate(Sender: TObject);
    procedure lsbRightDrawItem(Control: TWinControl; Index: Integer;
      Rect: TRect; State: TOwnerDrawState);
    procedure lsbRightClick(Sender: TObject);
    procedure lsbLeftDrawItem(Control: TWinControl; Index: Integer;
      Rect: TRect; State: TOwnerDrawState);
    procedure FormShow(Sender: TObject);
    procedure SpeedButton1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.FormCreate(Sender: TObject);
var
    i: integer;
begin
    lsbRight.Style := lbOwnerDrawFixed;
    lsbRight.Ctl3D := false;
    lsbRight.ItemHeight := 50;
    lsbRight.Items.Add('C++ Builder'#13'ccrun(XX)');
    lsbRight.Items.Add('My Developer Knowledge Base'#13'http://blog.csdn.net/nhconch'#13'????');
    for i:=3 to 10 do begin
        lsbRight.Items.Add('ListBox Items of ' + IntTostr(i) + #13'Second of '
            + IntToStr(i) + #13'Third of ' + IntToStr(i));
    end;

    lsbLeft.Style := lbOwnerDrawFixed;
    lsbLeft.Ctl3D := false;
    lsbLeft.ItemHeight := 90;
    lsbLeft.Items.Add('DSDSD');
    lsbLeft.Items.Add('My Developer Knowledge Base');
    lsbLeft.Items.Add('XX:XXX');
    lsbLeft.Items.Add('http://blog.csdn.net/nhconch');
end;

procedure TForm1.lsbRightDrawItem(Control: TWinControl; Index: Integer;
  Rect: TRect; State: TOwnerDrawState);
var
    strTemp: String;
begin
    //
    lsbRight.Canvas.Font.Color := clBlack;
    //
    lsbRight.Canvas.Brush.Color := clWhite;
    lsbRight.Canvas.FillRect (Rect);
    //
    lsbRight.Canvas.Brush.Color := TColor($00FFF7F7);
    lsbRight.Canvas.Pen.Color := TColor($00131315);
    lsbRight.Canvas.RoundRect(Rect.Left + 3, Rect.Top + 3,
            Rect.Right - 2, Rect.Bottom - 2, 8, 8);
    //?
    lsbRight.Canvas.RoundRect(Rect.Left + 3, Rect.Top + 3,
            Rect.Right - 3, Rect.Bottom - 3, 5, 5);
    //
    if(odSelected in State) then
    begin
        //
        lsbRight.Canvas.Brush.Color := TColor($00FFB2B5);
        lsbRight.Canvas.RoundRect(Rect.Left + 3, Rect.Top + 3,
                Rect.Right - 3, Rect.Bottom - 3, 5, 5);
        //
        lsbRight.Canvas.Font.Color := clBlue;
        //XOR
        if(odFocused in State) then DrawFocusRect(lsbRight.Canvas.Handle, Rect);
    end;
    //
    ImageList1.Draw(lsbRight.Canvas, Rect.Left + 7,
            Rect.top + (lsbRight.ItemHeight - ImageList1.Height) div 2, Index, true);
    //
    strTemp := lsbRight.Items.Strings[Index];
    lsbRight.Canvas.TextOut(Rect.Left + 32 + 10, Rect.Top + 4
                            , Copy(strTemp, 1, Pos(#13, strTemp)-1));
    strTemp := Copy(strTemp, Pos(#13, strTemp)+1, Length(strTemp));
    lsbRight.Canvas.TextOut(Rect.Left + 32 + 10, Rect.Top + 18,
                            Copy(strTemp, 1, Pos(#13, strTemp)-1));
    lsbRight.Canvas.TextOut(Rect.Left + 32 + 10, Rect.Top + 32,
                            Copy(strTemp, Pos(#13, strTemp)+1, Length(strTemp)));
end;

procedure TForm1.lsbRightClick(Sender: TObject);
begin
     StaticText1.Caption := ' ' + lsbRight.Items.Strings[lsbRight.ItemIndex];
end;

procedure TForm1.lsbLeftDrawItem(Control: TWinControl; Index: Integer;
  Rect: TRect; State: TOwnerDrawState);
var
    r: TRect;
begin
    with lsbLeft.Canvas do begin
        //
        Brush.Color := clWhite;
        FillRect (Rect);
        //
        if (odSelected in State) then
            Pen.Color := $FFB2B5
        else
            Pen.Color := clSilver;
        Brush.Style := bsClear;
        SetRect(r, Rect.Left+3, Rect.Top+3, Rect.Right-3, Rect.Bottom-3);
        RoundRect(r.Left, r.Top, r.Right, r.Bottom, 10, 10);
        //
        if (odSelected in State) then
            Draw(r.Left + (r.Right - r.Left - imgHouse.Width) shr 1,
                r.Top + 2, imgHouse.Picture.Graphic)
        else                            //
            Draw(r.Left + (r.Right - r.Left - imgHouseGray.Width) shr 1,
                r.Top + 2, imgHouseGray.Picture.Graphic);
        //
        r.Top := r.Bottom - Abs(Font.Height) - 4;
        Brush.Style := bsSolid;
        if (odSelected in State) then
            Brush.Color := $FFB2B5
        else
            Brush.Color := clSilver;
        FillRect(r);
        //
        Font.Color := clBlack;
        r.Top := r.Top + 2; //,(XXXX,DT_CENTER)
        DrawText(Handle, PChar(TListBox(Control).Items.Strings[Index]), -1, r
                , DT_CENTER or DT_END_ELLIPSIS{ or DT_WORDBREAK});
        //XOR
        if(odFocused in State) then DrawFocusRect(Rect);
    end;
end;

procedure TForm1.FormShow(Sender: TObject);
begin
    lsbRight.ItemIndex := 0;
    lsbRight.Repaint();

    lsbLeft.ItemIndex := 0;
    lsbLeft.Repaint();
end;

procedure TForm1.SpeedButton1Click(Sender: TObject);
begin
     Close;
end;

end.


Código:
unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, ImgList;

type
  TForm1 = class(TForm)
    ListBox1: TListBox;
    ImageList1: TImageList;
    Label1: TLabel;
    procedure FormShow(Sender: TObject);
    procedure ListBox1DrawItem(Control: TWinControl; Index: Integer;
      Rect: TRect; State: TOwnerDrawState);
    procedure FormCreate(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

// Inicializando a altura da lista de acordo com a altura da imagem
procedure TForm1.FormCreate(Sender: TObject);
begin
  ListBox1.ItemHeight := ImageList1.Height +2;
end;

// Populando minha lista
procedure TForm1.FormShow(Sender: TObject);
var
  Idx :Integer;
begin
  Randomize;
  for Idx := 0 to 6 do
    ListBox1.Items.AddObject(Format('Usuário %d', [Idx]), Pointer(Random(3)))
end;

// Devido ao conflito entre o nome da função e do parâmetro, temos que indicar
// a que rect nos referimos, logo apontamos a unit Classes aonde se encontra
procedure TForm1.ListBox1DrawItem(Control: TWinControl; Index: Integer;
  Rect: TRect; State: TOwnerDrawState);
const
  IconMargin  = 4;
  TextMargin  = 6;
var
  OffSetY :Integer;
  StatusIcon :TBitmap;
begin
 // Pinta o fundo do retângulo
  (Control as TListBox).Canvas.FillRect(Rect);
 // Para centralizar o texto na altura, iremos calcular aqui em que posição (Y)
 // deverá ser desenhado o texto
  OffSetY := ((Rect.Bottom -Rect.Top) -(Control as TListBox).Canvas.TextHeight('A')) div 2;
 // Para as próximas etapas, desenharemos apenas dentro do retângulo,
 // não interferindo nas suas bordas
  Inc(Rect.Left, 1 +IconMargin);  // também ajustamos o início do icone
  Inc(Rect.Top, 1);
  Dec(Rect.Bottom, 1);
  Dec(Rect.Right, 1);
 // Alocamos um bitmap para obter uma figura referente ao status da lista de imagens
  StatusIcon := TBitmap.Create;
  try
   // obtemos o bitmap da lista, referente ao status armazenado no item de Objects
   // a conversão ser faz necessária porque Objects armazena ponteiros
    if ImageList1.GetBitmap((LongInt((Control as TListBox).Items.Objects[Index])), StatusIcon) then
     // Utilizando a função BrushCopy, pintamos o bitmap na definida por Rect.
     // A função fará um stretch da imagem se utilizar outro tamanho que não o da imagem
      (Control as TListBox).Canvas.BrushCopy(Classes.Rect(Rect.Left, Rect.Top, Rect.Left +ImageList1.Width, Rect.Top +ImageList1.Height),
                                             StatusIcon,  // imagem
                                             Classes.Rect(0, 0, ImageList1.Width -1, ImageList1.Height -1),   // área da imagem a copiar
                                             StatusIcon.Canvas.Pixels[0, 0]);  // cor de fundo (usamos o pixel superior-esquerdo
  finally
 // liberamos o bitmap alocado
    StatusIcon.Free;
  end;
 // Para desenhar o texto após o icone, devemos avançar o início do retângulo para
 // além da largura da imagem + a margem desejada
  Inc(Rect.Left, ImageList1.Width +TextMargin);
  (Control as TListBox).Canvas.TextRect(Rect,  // área onde será desenhado o texto
                                        Rect.Left,  // início na posição X
                                        Rect.Top +OffSetY,  // início na posição Y
                                        (Control as TListBox).Items[Index]);
end;

end.



PS.: Com isto aí você monta o seu componente se quiser, tem tudo que você precisa.



bye
_________________
P.O.W.E.R B.Y D.E.L.P.H.I
Voltar ao Topo
Ver o perfil de Usuários Enviar Mensagem Particular MSN Messenger
jrman
Novato
Novato


Registrado: Sexta-Feira, 24 de Fevereiro de 2017
Mensagens: 80

MensagemEnviada: Ter Jun 13, 2017 3:14 pm    Assunto: Responder com Citação

Obrigado Johnny, eu implementei só a lbsRight:
Código:


procedure TfrmDash.lsbRightDrawItem(Control: TWinControl; Index: Integer;
  Rect: TRect; State: TOwnerDrawState);
var
    strTemp: String;
begin
    //
    lsbRight.Canvas.Font.Color := clBlack;
    //
    lsbRight.Canvas.Brush.Color := clWhite;
    lsbRight.Canvas.FillRect (Rect);
    //
    lsbRight.Canvas.Brush.Color := TColor($00FFF7F7);
    lsbRight.Canvas.Pen.Color := TColor($00131315);
    lsbRight.Canvas.RoundRect(Rect.Left + 3, Rect.Top + 3,
            Rect.Right - 2, Rect.Bottom - 2, 8, 8);
    //?
    lsbRight.Canvas.RoundRect(Rect.Left + 3, Rect.Top + 3,
            Rect.Right - 3, Rect.Bottom - 3, 5, 5);
    //
    if(odSelected in State) then
    begin
        //
        lsbRight.Canvas.Brush.Color := TColor($00FFB2B5);
        lsbRight.Canvas.RoundRect(Rect.Left + 3, Rect.Top + 3,
                Rect.Right - 3, Rect.Bottom - 3, 5, 5);
        //
        lsbRight.Canvas.Font.Color := clBlue;
        //XOR
        if(odFocused in State) then DrawFocusRect(lsbRight.Canvas.Handle, Rect);
    end;
    //
    ImageList1.Draw(lsbRight.Canvas, Rect.Left + 7,
            Rect.top + (lsbRight.ItemHeight - ImageList1.Height) div 2, Index, true);
    //
    strTemp := lsbRight.Items.Strings[Index];
    lsbRight.Canvas.TextOut(Rect.Left + 32 + 10, Rect.Top + 4
                            , Copy(strTemp, 1, Pos(#13, strTemp)-1));
    strTemp := Copy(strTemp, Pos(#13, strTemp)+1, Length(strTemp));
    lsbRight.Canvas.TextOut(Rect.Left + 32 + 10, Rect.Top + 18,
                            Copy(strTemp, 1, Pos(#13, strTemp)-1));
    lsbRight.Canvas.TextOut(Rect.Left + 32 + 10, Rect.Top + 32,
                            Copy(strTemp, Pos(#13, strTemp)+1, Length(strTemp)));

end;



estou perto do que preciso, você pode me ajudar nessas duas mudanças usando essa listBox?




Muito Obrigado[/img]
Voltar ao Topo
Ver o perfil de Usuários Enviar Mensagem Particular
johnny-walker
Moderador
Moderador


Registrado: Sábado, 4 de Outubro de 2003
Mensagens: 10653
Localização: Contagem/MG - BRAZIL

MensagemEnviada: Qui Jun 15, 2017 8:56 pm    Assunto: Responder com Citação

Neste caso amigo, acredito que imagelist esteja com o formato em 32x32, sendo assim você terá de configurar a imagelist para um ícone maior, 64x64 por exemplo.

Outro fator é que você terá de recuar o texto da direita para a esquerda para acomodar a imagem, caso contrário você terá problemas.
Desta forma eu não fiz com duas imagens.
E no momento não estou podendo debruçar-me sobre tal, devido a tempo escasso.
Boa sorte com o projeto.



bye
_________________
P.O.W.E.R B.Y D.E.L.P.H.I
Voltar ao Topo
Ver o perfil de Usuários Enviar Mensagem Particular MSN Messenger
Mostrar os tópicos anteriores:   
Novo Tópico   Responder Mensagem    ActiveDelphi - Índice do Fórum -> Delphi Todos os horários são GMT - 3 Horas
Página 1 de 1

 
Ir para:  
Enviar Mensagens Novas: Proibido.
Responder Tópicos Proibido
Editar Mensagens: Proibido.
Excluir Mensagens: Proibido.
Votar em Enquetes: Proibido.


Powered by phpBB © 2001, 2005 phpBB Group
Traduzido por: Suporte phpBB