Solved

Array of Bitmaps

Posted on 2000-04-10
10
429 Views
Last Modified: 2010-04-04
I have a form with a listbox on the left and an image control on the right.
When you click something in the listbox, it needs to display the image to go with it. The only way I could think to do this was to declare an array of tbitmap and when you click the listbox, the array with the listbox's itemindex shows in the image control. When I try to clear the whole thing, the array, the image and the listbox, it appears to clear. When you reload every thing new, the listitems that contained images before, still do. I have been having alot of access errors trying to free the whole array eachtime.
The array needs to hold at least 75 images. Any Ideas?

Thanks in advance,
Cando
0
Comment
Question by:cando
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 2
  • 2
  • 2
  • +4
10 Comments
 
LVL 4

Expert Comment

by:StevenB
ID: 2702310
 I'm in a hurry here, but one word springs to mind: TImageList.

  (Sorry if I've misinterpreted things and stated the bleedin' obvious)

  Gotta dash,

  Steven
0
 
LVL 13

Expert Comment

by:Epsylon
ID: 2702326
Maintain a TObjectList next to the ListBox and store the bitmaps in this list. TObjectList frees the bitmaps automatically when necessary...
0
 
LVL 13

Expert Comment

by:Epsylon
ID: 2702345
TImageList can only hold images of equal size. Maybe this is case here... don't know.
0
Industry Leaders: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 

Author Comment

by:cando
ID: 2702654
Sorry,

All the images could be very different, loaded from files or pasted form the clipboard.
0
 
LVL 12

Expert Comment

by:rwilson032697
ID: 2702726
Can you post the relevant code?

Cheers,

Raymond.


0
 

Author Comment

by:cando
ID: 2702773
FImage: array[1..75] of TBitmap;

procedure TForm1.LoadFromFile1Click(Sender: TObject);
begin
 if OpenPictureDialog1.Execute then
 begin
   FImage[ListBox2.ItemIndex + 1] := TBitmap.Create;
   FImage[ListBox2.ItemIndex + 1].LoadFromFile(openPictureDialog1.FIleName);
   Image1.Picture.Bitmap := FImage[ListBox2.ItemIndex + 1];
 end;
end;

procedure TForm1.ListBox2Click(Sender: TObject);
begin
  try Image1.Picture.Bitmap := FImage[ListBox2.ItemIndex + 1] except end;
end;


This all seems to work alright When I try to clear it all so it can be refilled, it clears but when the listbox is filled again, it has pictures for the items that had them last time. I dont know how to clear the array.

Here is the code I use to clear everything.



procedure TForm1.ClearAll;
var
  i: integer;
begin
  Image1.Picture := nil;
  ListBox2.Clear;

  try
    for I := 1 to 75 do FImage[i].free;
  except end;
end;
0
 
LVL 2

Expert Comment

by:mullet_attack
ID: 2702781
When you add the items to the listbox, use addobject

a sample (form with button1, listbox1, image1 and openpicturedialog1)

procedure TForm1.Button1Click(Sender: TObject);
var
  mybitmap : tbitmap;
begin
  if openpicturedialog1.execute then
    begin
      mybitmap := tbitmap.create;
      mybitmap.loadfromfile(openpicturedialog1.filename);
      listbox1.items.addobject ('item', TObject(mybitmap));
    end;

When you delete an item from the list box, don't forget to call TBitmap(listbox1.items.object[x]).free first.

Mark


end;

procedure TForm1.ListBox1Click(Sender: TObject);
begin
  image1.picture.bitmap.assign(TBitmap(listbox1.items.objects[listbox1.itemindex]));
end;
0
 
LVL 6

Expert Comment

by:DrDelphi
ID: 2702794
Actually, if you are working in Delphi 4 or higher, you could use a dynamic array of Bitmaps, incrementing it as you poplulate it:

Var BMPArray:array of Tbitmap;

Begin
  BmpArray[length(bmpArray)-1]:=Tbitmap.create;
  BmpArray[length(bmpArray)-1].LoadFromfile('yada.bmp');
end;


and then scaling that array down to
nothing again by using Copy:


bmpArray:=Copy(BmpArray,0,0);


0
 
LVL 2

Expert Comment

by:mullet_attack
ID: 2702796
Oops, my last comment about delete is in the middle of my sample, sorry 'bout that...  below is a better example, button2 is a delete item button (no error checking..)


procedure TForm1.Button1Click(Sender: TObject);
var
  mybitmap : tbitmap;
begin
  if openpicturedialog1.execute then
    begin
      mybitmap := tbitmap.create;
      mybitmap.loadfromfile(openpicturedialog1.filename);
      listbox1.items.addobject ('item', TObject(mybitmap));
    end;

end;

procedure TForm1.ListBox1Click(Sender: TObject);
begin
if assigned(listbox1.items.objects[listbox1.itemindex]) then
  image1.picture.bitmap.assign(TBitmap(listbox1.items.objects[listbox1.itemindex]));
end;

procedure TForm1.Button2Click(Sender: TObject);
begin
 TBitmap(listbox1.items.objects[listbox1.itemindex]).free;
 TBitmap(listbox1.items.objects[listbox1.itemindex]).Assign(nil);
end;
0
 
LVL 10

Accepted Solution

by:
Lischke earned 150 total points
ID: 2703270
Hi all,

I'm currently writing on an image database browser which shows all images as thumbnails. For performance reasons I cache 300 (adjustable) TBitmaps in a normal TList. mulllet_attack has already mentioned to use the listbox's ability to store objects. This is also a good solution. Take care that you free the objects correctly.

If you still want to use your extra list then make sure you reset the references in it:

procedure TForm1.ClearAll;
var
  i: integer;
begin
  Image1.Picture := nil;
  ListBox2.Clear;

  try
    for I := 1 to 75 do
    begin
      FImage[i].free;
      FImage[i] := nil;
    end;
  except end;
end;

otherwise you will access invalid memory!

DrDelphi, just a hint for your dynamic array approach which is something I also like (and use quite often).

Allocation:

  SetLength(BMPArray, Length(BMPArray) + 1);
  BMPArray[High(BMPArray)] := TBitmap.Create;
  :

Do not rely on automatic memory allocation, this will not happen (as in Java)!

Deallocation:

for I := 0 to High(BMPArray) do
  BMPArray[I].Free;
BMPArray := nil;

Ciao, Mike
0

Featured Post

Technology Partners: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Have you ever had your Delphi form/application just hanging while waiting for data to load? This is the article to read if you want to learn some things about adding threads for data loading in the background. First, I'll setup a general applica…
In my programming career I have only very rarely run into situations where operator overloading would be of any use in my work.  Normally those situations involved math with either overly large numbers (hundreds of thousands of digits or accuracy re…
Finds all prime numbers in a range requested and places them in a public primes() array. I've demostrated a template size of 30 (2 * 3 * 5) but larger templates can be built such 210  (2 * 3 * 5 * 7) or 2310  (2 * 3 * 5 * 7 * 11). The larger templa…
Exchange organizations may use the Journaling Agent of the Transport Service to archive messages going through Exchange. However, if the Transport Service is integrated with some email content management application (such as an antispam), the admini…

730 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question