{{{
[adiumx.git] / Source / AIAbstractListObjectMenu.m
blobdce893cbe1282402ac165d774beed73fb15c16f6
1 //
2 //  AIAbstractListObjectMenu.m
3 //  Adium
4 //
5 //  Created by Adam Iser on 5/31/05.
6 //  Copyright 2006 The Adium Team. All rights reserved.
7 //
9 #import <Adium/AIAbstractListObjectMenu.h>
10 #import <AIUtilities/AIImageAdditions.h>
11 #import <Adium/AIListObject.h>
12 #import <Adium/AIServiceIcons.h>
13 #import <Adium/AIStatusIcons.h>
15 @interface AIAbstractListObjectMenu (PRIVATE)
16 - (void)_destroyMenuItems;
17 @end
19 @implementation AIAbstractListObjectMenu
21 /*!
22  * @brief Init
23  */
24 - (id)init
26         if((self = [super init])){
27                 //Rebuild our menu when Adium's status or service icon set changes
28                 [[adium notificationCenter] addObserver:self
29                                                                            selector:@selector(rebuildMenu)
30                                                                                    name:AIStatusIconSetDidChangeNotification
31                                                                                  object:nil];
32                 
33                 [[adium notificationCenter] addObserver:self
34                                                                            selector:@selector(rebuildMenu)
35                                                                                    name:AIServiceIconSetDidChangeNotification
36                                                                                  object:nil];
37         }
38         
39         return self;
42 - (void)dealloc
44         [[adium notificationCenter] removeObserver:self name:AIStatusIconSetDidChangeNotification object:nil];
45         [[adium notificationCenter] removeObserver:self name:AIServiceIconSetDidChangeNotification object:nil];
46         [self _destroyMenuItems];
48         [super dealloc];
51 /*!
52  * @brief Returns an array of menu items
53  */
54 - (NSArray *)menuItems
56         if(!menuItems){
57                 menuItems = [[self buildMenuItems] retain];
58         }
59         
60         return menuItems;
63 /*!
64  * @brief Returns a menu containing our menu items
65  *
66  * Remember that menu items can only be in one menu at a time, so if you use this functions you cannot do anything
67  * manually the menu items
68  */
69 - (NSMenu *)menu
71         if(!menu){
72                 NSEnumerator    *enumerator = [[self menuItems] objectEnumerator];
73                 NSMenuItem              *menuItem;
74                 
75                 menu = [[NSMenu allocWithZone:[NSMenu zone]] init];
76                 
77                 [menu setMenuChangedMessagesEnabled:NO];
78                 while((menuItem = [enumerator nextObject])) [menu addItem:menuItem];
79                 [menu setMenuChangedMessagesEnabled:YES];
80         }
81         
82         return menu;
85 /*!
86  * @brief Returns the existing menu item
87  *
88  * @param object 
89  * @return NSMenuItem 
90  */
91 - (NSMenuItem *)menuItemWithRepresentedObject:(id)object
93         NSEnumerator    *enumerator = [[self menuItems] objectEnumerator];
94         NSMenuItem              *menuItem;
96         while ((menuItem = [enumerator nextObject])) {
97                 if ([menuItem representedObject] == object) {
98                         return menuItem;
99                 } else if ([menuItem submenu]) {
100                         NSEnumerator    *submenuEnumerator = [[[menuItem submenu] itemArray] objectEnumerator];
101                         NSMenuItem              *submenuItem;
102                         
103                         while ((submenuItem = [submenuEnumerator nextObject])) {
104                                 if ([submenuItem representedObject] == object) {
105                                         return submenuItem;
106                                 }
107                         }
108                 }
109         }
111         return nil;
115  * @brief Rebuild the menu
116  */
117 - (void)rebuildMenu
119         [self _destroyMenuItems];
123  * @brief Destroy menu items
124  */
125 - (void)_destroyMenuItems
127         [menu release]; menu = nil;
128         [menuItems release]; menuItems = nil;   
132 //For Subclasses -------------------------------------------------------------------------------------------------------
133 #pragma mark For Subclasses
135  * @brief Builds and returns an array of menu items which should be in the listObjectMenu
137  * Subclass this method to build and return the menu items you want.
138  */
139 - (NSArray *)buildMenuItems
141         return [NSArray array];
145  * @brief Returns a menu image for the account
146  */
147 - (NSImage *)imageForListObject:(AIListObject *)listObject
149         NSImage *statusIcon, *serviceIcon;
150         NSSize  statusSize, serviceSize, compositeSize;
151         NSRect  compositeRect;
152         
153         //Get the service and status icons
154         statusIcon = [AIStatusIcons statusIconForListObject:listObject type:AIStatusIconList direction:AIIconNormal];
155         statusSize = [statusIcon size];
156         serviceIcon = [AIServiceIcons serviceIconForObject:listObject type:AIServiceIconSmall direction:AIIconNormal];  
157         serviceSize = [serviceIcon size];
158         
159         //Composite them side by side (since we're only allowed one image in a menu and we want to see both)
160         compositeSize = NSMakeSize(statusSize.width + serviceSize.width + 1,
161                                                            statusSize.height > serviceSize.height ? statusSize.height : serviceSize.height);
162         compositeRect = NSMakeRect(0, 0, compositeSize.width, compositeSize.height);
163         
164         //Render the image
165         NSImage *composite = [[NSImage alloc] initWithSize:compositeSize];
166         [composite lockFocus];
167         [statusIcon drawInRect:compositeRect atSize:[statusIcon size] position:IMAGE_POSITION_LEFT fraction:1.0];
168         [serviceIcon drawInRect:compositeRect atSize:[serviceIcon size] position:IMAGE_POSITION_RIGHT fraction:1.0];
169         [composite unlockFocus];
170         
171         return [composite autorelease];
174 @end