Jump to content

Possible to tag a value onto a listbox item?

- - - - -

This topic has been archived. This means that you cannot reply to this topic.
12 replies to this topic

#1
2710

2710

    Programmer

  • Members
  • PipPipPipPip
  • 110 posts
Hi,

So I just want to know if I can tag a boolean value for each item I add into the listbox. The reason is, when I add items to the listbox, it is just plain data, therefore if I want to process it any further, I will have to re-evaluate the item. Whereas if I had just tagged on a simple value of say 'True', then I can just reference this value, and simply evaluate it from there.

Is there a function for this?

I don't think I have explained it properly, so here is a simple example:

I have a list box and I enter in the fruits Apple and Banana several times in mixed order on separate lines each.

I want it so that whenever I click on an 'Apple' it +1 to the variable of Count. And whenever I click banana it does nothing.

Now, it would be helpful if from the start each time I added Apple, the value 'True' is added to the item. So then I can just query this and see if I do +1 to count or not.

In this case, it is simple, since I can just say:

If listbox.items[listbox.itemindex] = 'Apple' then blahblahablha

But in my program its a bit more complicated, and I have to evaluate half the string and then extract words and then compare it with a database :P

So it would be gretaly helpful if there was a function.

/rant >__>

#2
alienkinetics

alienkinetics

    Programmer

  • Members
  • PipPipPipPip
  • 154 posts
You can store a TObject pointer with each item. This doesn't have to be a TObject. It can be any 32bit datatype.

ListBox.Items.AddObject('Apple', TObject(True));

You can access the values via the Objects list:

if Boolean(ListBox.Items.Objects[ListBox.ItemIndex]) then

TListBox doesn't own the objects, so it wont be free'ed, so if you have more data to store per item, and you create a class, you must free it when you remove the item.

Quote

The TStrings object does not own the objects you add this way. Objects added to the TStrings object still exist even if the TStrings instance is destroyed. They must be explicitly destroyed by the application.


#3
2710

2710

    Programmer

  • Members
  • PipPipPipPip
  • 110 posts
T__T this is hard...I remind you I am still a noob :P

1) With this:

ListBox.Items.AddObject('Apple', TObject(True));

Can I stick any value for 'True', like 'Waffles' or '32' , do I have to change the TObject to something else then?

2) if Boolean(ListBox.Items.Objects[ListBox.ItemIndex]) then

Why do I need 'Boolean' before it? What if my attached object is just a plain string? would I do 'if String(...)' ? And are you missing a =, ie:

if Boolean(ListBox.Items.Objects[ListBox.ItemIndex]) = True then...

3) I don't understand what you mean by destroy. I do actually have a button where I can remove items from my list, but are you saying that I need to manually remove these attached items? How do I do this and what happens if I don't?

Thanks

#4
alienkinetics

alienkinetics

    Programmer

  • Members
  • PipPipPipPip
  • 154 posts
1) The AddObject method expects a TObject parameter. Hence the need for a typecast. Yes, you can change the value to something like a Integer, Single since they are both 32bit.

2) The "Boolean" is there to typecast the TObject pointer back to a boolean value. Since they are both 32bit's, it works. Memory is just memory after all.

But, I wouldn't try to store a string. You will get weird bugs because a Delphi string is a special type of "managed variable" in Delphi. If you use a const string, then the value will be a pointer to static string data. if you use a string variable, then it will be a pointer to the string variable, but, since Delphi doesn't know about the copy in the TListBox, you will end up with dangling pointers = random crashes.

3) The "correct" usage of AddObject is to add a class object. eg: If you have a class:

  CApple = class

    S: String;

  end;

You add an item using:
ListBox.Items.AddObject('Apple', CApple.Create);
To delete an item use:

  ListBox.Items.Objects[0].Free;

  ListBox.Items.Delete(0);


If you dont free the objects before deleting the item, then you have a memory leak, and overtime your program will choo memory.

I prefer the TListView control which has OnInsert and OnDeletion events which can be used for creating/free-ing related data.

#5
2710

2710

    Programmer

  • Members
  • PipPipPipPip
  • 110 posts
OK thank you, but you didn't answer the second part of qu 2)

Ie, usually in if statements, you get and = :

If X = Y then

So are you missing it? I can't see how it would evaluate it otherwise

Thanks

#6
alienkinetics

alienkinetics

    Programmer

  • Members
  • PipPipPipPip
  • 154 posts
In Pascal, the equal '=' operator returns a boolean value.

We stored the value 'True' as a TObject pointer. When we extracted the value, we need to convert it back to a Boolean.

It is just typecasting. No data is changing.

In C/C++ you dont need to typecast to a boolean since any non-zero value is treated as True.

But, in Pascal, Boolean is a datatype and you must have a boolean for a IF/THEN block.

Trust me. It works :)

#7
2710

2710

    Programmer

  • Members
  • PipPipPipPip
  • 110 posts
Ok, but the thing is, I am going to be storing integers instead of 'True', I was only using True as an example. And I want it to recognise different numbers thus doing different procedures:

Case ListBox.Items.Object(ListBox.Itemindex) of

20: Procedure1;
21: Procedure2;
33: Procedure3;

end;

Something along the lines of this. I don't want a Boolean, since with Boolean you can only have True or False.

if Boolean(ListBox.Items.Objects[ListBox.ItemIndex]) then

With your code it can only detect whether I have tagged 'True' onto the item, but I want it to detect integers, not 'True'. Like, imagine me using your code, and I want it so that every product with tagged numbers >5 to do a procedure, how am I supposed to do that with your code?

Sorry, hope I'm making sense and forgive my noobishness :P

Edited by 2710, 11 February 2010 - 12:23 AM.


#8
alienkinetics

alienkinetics

    Programmer

  • Members
  • PipPipPipPip
  • 154 posts
Thats ok. Just typecast to a Integer:

Case Integer(ListBox.Items.Object(ListBox.Itemindex)) of


#9
2710

2710

    Programmer

  • Members
  • PipPipPipPip
  • 110 posts
I tried doing:

if Integer(listbox1.Items.objects[count])

To check whether the attached is an integer or not, but it goes:

"Type of expression must be BOOLEAN"

I also can't use Boolean, because I have attached a different number to each item in the listbox which I need to evaluate later on.

Any solutions?


Thanks

#10
2710

2710

    Programmer

  • Members
  • PipPipPipPip
  • 110 posts
Well I had to twist my program round to cope with it. Now I just used a case. Although I would still appreciate if you could solve it, so I can further my understanding lol

Another problem:

PLU:=listbox1.Items.objects[listbox1.itemindex];

Where PLU is an Integer variable. I get an error message saying:

"Incompatible types: 'Integer' and 'TObject' "

How do I convert a TObject to an integer?

Thanks

#11
alienkinetics

alienkinetics

    Programmer

  • Members
  • PipPipPipPip
  • 154 posts
Arrrrrrrrr :confused:

Quote

How do I convert a TObject to an integer?

typecasting!!!

Quote

Type of expression must be BOOLEAN

typecasting!!!

Its simple. Boolean, Integer and TObject are all 32bit values. but, Delphi checks for bugs by enforcing proper type usage (unlike C) So, you simply typecast your 32bit values to what ever is needed.

if Integer(listbox1.Items.objects[count]) then

As I said, IF/THEN requires a Boolean, and the '=' operator returns a Boolean, so you need:

if Integer(listbox1.Items.objects[count]) = 1234 then

I love helping people, but I think you need to hit the books again and learn the basic language concepts.

Or, just use brute force. After all, the compilier is telling you everything you need to know. Just read your code and ask yourself, does this make sence?
Buzz PHP Class Library - Web Components Made Easy!
http://www.buzzphp.com/

#12
2710

2710

    Programmer

  • Members
  • PipPipPipPip
  • 110 posts
Thank you :D