views:

321

answers:

3

As docs say it's impossible to add two menu items to NSPopUpButton if they both have the same title. I was trying to add menu items to [popupButton menu], but with no luck. I was also trying to create a new menu, add items to it and then use [popupButton setMenu:newMenu], but no. Menu always display only one item per name.

But I know it should be possible, if you try to create a smart playlist in iTunes, you could select "Playlist" from the left popup button, "=" from the middle, and the right one will hold menu items for every playlist in iTunes EVEN if they have the same title. So how do they do it?

A: 

While NSPopUpButton methods like addItemWithTitle: and addMenu: won't allow duplicate names, it is definitely possible to have items with the same title. You simply have to set the name on the NSMenuItem itself.

For example, if you have an array of strings (like playlist names perhaps) you want to add them to a popup button, and want to make sure duplicates will be in there, do it like this:

NSArray* items = [NSArray arrayWithObjects:@"Foo", @"Bar", @"Baz", @"Foo", nil];

for (NSString* item in items)
{
   [popupButton addItemWithTitle:@"blah"];
   [[popupButton lastItem] setTitle:item];
   [[popupButton lastItem] setTarget:self];
   [[popupButton lastItem] setAction:@selector(something:)];
}
Ken Aspeslagh
Ken I tried this approach also. But the result is the same. Maybe because my popup button is in NSPredicateEditorRowTemplate and it is post processed by its predicate editor.I'd like to see some source code where this method works.
William S. Pear
I'm doing this in one of my apps and it does work. That's where I got the code that I simplified above. I had to do it this way because the menu lists user-named preset settings and duplicates had to be allowed. I've never used the predicate editor so I can't help there. Sorry!
Ken Aspeslagh
PS: If you want to see it work, just make a new test project with a popup button and paste in that code.
Ken Aspeslagh
A: 

Instead of using addItemWithTitle:, you can create an NSMenuItem manually and add it directly to the menu. This allows you to specify any title you want, as well as being able to insert it at any location in the menu.

NSMenuItem* newItem = [[NSMenuItem alloc] initWithTitle:@"foo" action:@selector(something:) keyEquivalent:@""];

[newItem setTarget:self];
[[popupButton menu] addItem:newItem];
[newItem release];
Brian Webster
A: 

I had the exact problem and it was solved easily. Instead of using NSPopUpButton methods such as –addItemWithTitle: to manipulate the button items, I added an NSArrayController and added the items into the array controller instead. Then I used the bindings to bind the controller and the popup button and now it shows items with same titles.

To do the bindings:

  1. Add an NSArrayController in IB.
  2. Set the NSPopUpButton bindings for "Content" to Array Controller with the "Controller Key" being "arrangedObjects"
  3. Set the NSPopUpButton bindings for "Selected Index" to Array Controller with the "Controller Key" being "selectionIndex"
  4. [Optional] Select the array controller and set the Class Name in attributes to whatever class your items are e.g. NSString or you can use the default NSMutableDictionary and add keys in the box below which consequently lets you wrap your items in a dictionary and add different keys for what you want to show in popup button and what you want to have in background. To set which key of the dictionary you want to be reflected in the popup button, go to popup button's bindings for "Content" again and set the "Modal key Path" to the key you added in the array controller attribute.
Mili Alem