在delphi中乱码图像和标签的动态数组

时间:2013-02-26 10:55:03

标签: delphi

我想添加附件,并且每次添加附件时表单都会变长,以便为包含标签和一些16X16图像的附件信息的行腾出空间。为此,我选择使用动态数组(不确定是否最好)。每次添加附件时,我都想创建这些对象的新实例。我的代码似乎不起作用。以下代码有什么问题?

procedure TVisionMail.AddAttachment(FileString: String);
var
I: Integer;
begin
     AttCount := AttCount + 1; // increment attachment count

     //set attachment file name
     if (AttCount <> 0) and (edAttachment.Text <> '') then
       edAttachment.text := edAttachment.text + ';';
     edAttachment.text := edAttachment.text + FileString;

     //move objects position down to allow space for attachment line
     VisionMail.Height := VisionMail.Height + 25;
     Panel1.Height     := Panel1.Height + 25;
     btnSend.Top       := btnSend.Top + 25;
     btnExit.Top       := btnExit.Top + 25;
     StatusMemo.Top    := StatusMemo.Top + 25;
     Memo1.Top         := Memo1.Top + 25;
     lblBody.Top       := lblBody.Top + 25;

       //Allocate memory for arrays
       SetLength(newImg, AttCount);
       SetLength(newlbl, AttCount);
       SetLength(newDel, AttCount);
       SetLength(newPin, AttCount);

        //create new instance and set parents, positions, color, events
        newImg[AttCount]:= TImage.Create(VisionMail);
        with newImg[AttCount] do
        begin
              Parent     := Panel1;
              Top        := Memo1.Top - 25;
              Left       := 408;
              Height     := 16;
              Width      := 16;
        end;
        newlbl[AttCount]:= TLabel.Create(VisionMail);
        with newlbl[AttCount] do
        begin
              Parent     := Panel1;
              Top        := newImg[I].Top + 2;
              Left       := 397;
              Height     := 3;
              Width      := 13;
              BiDiMode   := bdRightToLeft;
       end;
       newDel[AttCount] := TAdvToolButton.Create(VisionMail);
       with newDel[AttCount] do
        begin
              Parent       := Panel1;
              Top          := newImg[I].Top;
              Left         := 440;
              Height       := 16;
              Width        := 16;
              color        := clBtnFace;
              colorChecked := clBtnFace;
              colorDown    := clBtnFace;
              colorHot     := clBtnFace;
              OnClick      := btnDelAttClick;
              OnMouseEnter := btnDelAttMouseEnter;
              OnMouseLeave := btnDelAttMouseLeave;
       end;
       newPin[AttCount] := TImage.Create(VisionMail);
       with newDel[AttCount] do
        begin
              Parent     := Panel1;
              Top        := newImg[I].Top;
              Left       := 425;
              Height     := 16;
              Width      := 16;
       end;
       //get Icon for extension of file
       lstIcons.GetBitmap(GetIcon(ExtractFileExt
                          (OpenDialog1.FileName)),
                          newImg[AttCount].Picture.Bitmap);
       newlbl[AttCount].Caption    := ExtractFileName(FileString);

end; 

1 个答案:

答案 0 :(得分:1)

最明显的缺陷是你正在写下所有阵列的末尾。例如,你写

SetLength(newImg, AttCount);

这意味着newImg的有效索引为0AttCount-1。但是你写了

newImg[AttCount] := ...

这是一个超出范围的访问权限,因为最后一个索引是AttCount-1。您对所有阵列访问都这样做。

如果在启用范围检查的情况下进行编译,编译器将生成运行时错误,以解释您的错误。

我个人认为你最好使用一个记录来保存你的四个组件:

TAttachmentControls = record
  Img: TImage;
  Lbl: TLabel;
  .. etc.
end;

使用TList<TAttachmentControls>作为容器。