Adium

Changeset 23671

Show
Ignore:
Timestamp:
05/26/2008 02:50:51 PM (6 months ago)
Author:
zacw
Message:

Display the group counting information on the right side of the group's cell. If a group is collapsed, always show the visible count. Fixes #9763. This also changes the behavior of the counting: it will count visible objects now, not just online. Something about "(3)" and seeing 1 below it because mobile was hidden was driving me crazy. This will also hide the "(3 of 3)" (for example) when visible == total.

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • trunk/Frameworks/Adium Framework/Source/AIListGroupCell.h

    r21357 r23671  
    3434- (void)setShadowColor:(NSColor *)inColor; 
    3535- (NSColor *)shadowColor; 
     36- (NSRect)drawGroupCountWithFrame:(NSRect)inRect; 
    3637- (void)setBackgroundColor:(NSColor *)inBackgroundColor gradientColor:(NSColor *)inGradientColor; 
    3738- (void)setDrawsBackground:(BOOL)inValue; 
  • trunk/Frameworks/Adium Framework/Source/AIListGroupCell.m

    r22764 r23671  
    189189                rect.size.width -= rect.size.height*.4 + rect.size.height*.2 + FLIPPY_TEXT_PADDING; 
    190190//      } 
    191  
    192         [self drawDisplayNameWithFrame:rect]; 
     191         
     192        if ([[listObject displayArrayObjectForKey:@"Show Count"] boolValue] || ![controlView isItemExpanded:listObject]) { 
     193                rect = [self drawGroupCountWithFrame:rect]; 
     194        } 
     195        rect = [self drawDisplayNameWithFrame:rect]; 
     196
     197 
     198- (NSRect)drawGroupCountWithFrame:(NSRect)inRect 
     199
     200        if ([listObject displayArrayObjectForKey:@"Count Text"]) { 
     201                NSAttributedString      *groupCount = [[NSAttributedString alloc] initWithString:[listObject displayArrayObjectForKey:@"Count Text"] 
     202                                                                                                                                                  attributes:[self labelAttributes]]; 
     203                 
     204                NSSize                          countSize = [groupCount size]; 
     205                NSRect                          rect = inRect; 
     206                 
     207                if (countSize.width > rect.size.width) countSize.width = rect.size.width; 
     208                if (countSize.height > rect.size.height) countSize.height = rect.size.height; 
     209                 
     210                rect.origin.x += (rect.size.width - countSize.width); 
     211                 
     212                //Draw (centered vertical) 
     213                int half = ceil((rect.size.height - labelFontHeight) / 2.0); 
     214                [groupCount drawInRect:NSMakeRect(rect.origin.x, 
     215                                                                                  rect.origin.y + half, 
     216                                                                                  rect.size.width, 
     217                                                                                  countSize.height)]; 
     218                [groupCount release]; 
     219                 
     220                inRect.size.width -= countSize.width; 
     221        } 
     222         
     223        return inRect; 
    193224} 
    194225 
  • trunk/Source/AIContactController.m

    r23607 r23671  
    378378                         
    379379                        //NSLog(@"listObjectRemoteGroupingChanged: %@: remoteGroupName %@ --> %@",inContact,remoteGroupName,localGroup); 
    380                          
     380                                
    381381                        [self _moveContactLocally:inContact 
    382382                                                          toGroup:localGroup]; 
  • trunk/Source/CBContactCountingDisplayPlugin.h

    r20017 r23671  
    2121{ 
    2222    BOOL                countAllObjects; 
    23     BOOL                countOnlineObjects; 
     23    BOOL                countVisibleObjects; 
    2424 
    2525        BOOL            showingGroups; 
    2626 
    27     NSMenuItem  *menuItem_countOnlineObjects; 
     27    NSMenuItem  *menuItem_countVisibleObjects; 
    2828    NSMenuItem  *menuItem_countAllObjects; 
    2929} 
  • trunk/Source/CBContactCountingDisplayPlugin.m

    r23556 r23671  
    2929#define CONTACT_COUNTING_DISPLAY_DEFAULT_PREFS  @"ContactCountingDisplayDefaults" 
    3030 
    31 #define SHOW_COUNT_ONLINE_CONTACTS_TITLE                               AILocalizedString(@"Show Group Online Count", nil) 
    32 #define HIDE_COUNT_ONLINE_CONTACTS_TITLE                               AILocalizedString(@"Hide Group Online Count", nil) 
     31#define SHOW_COUNT_VISIBLE_CONTACTS_TITLE                              AILocalizedString(@"Show Group Visible Count", nil) 
     32#define HIDE_COUNT_VISIBLE_CONTACTS_TITLE                              AILocalizedString(@"Hide Group Visible Count", nil) 
    3333#define SHOW_COUNT_ALL_CONTACTS_TITLE                           AILocalizedString(@"Show Group Total Count", nil) 
    3434#define HIDE_COUNT_ALL_CONTACTS_TITLE                           AILocalizedString(@"Hide Group Total Count", nil) 
     
    3636#define PREF_GROUP_CONTACT_LIST                                 @"Contact List" 
    3737#define KEY_COUNT_ALL_CONTACTS                                  @"Count All Contacts" 
    38 #define KEY_COUNT_ONLINE_CONTACTS                              @"Count Online Contacts" 
     38#define KEY_COUNT_VISIBLE_CONTACTS                             @"Count Online Contacts" //Kept as "Online" to preserve preferences 
    3939 
    4040#define KEY_HIDE_CONTACT_LIST_GROUPS                    @"Hide Contact List Groups" 
     
    4444 * @class CBContactCountingDisplayPlugin 
    4545 * 
    46  * @brief Component to handle displaying counts of contacts, both online and total, next to group names 
     46 * @brief Component to handle displaying counts of contacts, both visible and total, next to group names 
    4747 * 
    48  * This componenet adds two menu items, "Count All Contacts" and "Count Online Contacts." Both default to being off. 
     48 * This componenet adds two menu items, "Count All Contacts" and "Count Visible Contacts." Both default to being off. 
    4949 * When on, these options display the appropriate count for an AIListGroup's contained objects. 
    5050 */ 
     
    6262         
    6363    //init our menu items 
    64     menuItem_countOnlineObjects = [[NSMenuItem alloc] initWithTitle:SHOW_COUNT_ONLINE_CONTACTS_TITLE  
     64    menuItem_countVisibleObjects = [[NSMenuItem alloc] initWithTitle:SHOW_COUNT_VISIBLE_CONTACTS_TITLE  
    6565                                                                                                                 target:self  
    6666                                                                                                                 action:@selector(toggleMenuItem:) 
    6767                                                                                                  keyEquivalent:@""]; 
    68     [[adium menuController] addMenuItem:menuItem_countOnlineObjects toLocation:LOC_View_Counting_Toggles];             
     68    [[adium menuController] addMenuItem:menuItem_countVisibleObjects toLocation:LOC_View_Counting_Toggles];            
    6969 
    7070    menuItem_countAllObjects = [[NSMenuItem alloc] initWithTitle:SHOW_COUNT_ALL_CONTACTS_TITLE 
     
    7676        //set up the prefs 
    7777        countAllObjects = NO; 
    78         countOnlineObjects = NO; 
     78        countVisibleObjects = NO; 
    7979         
    8080        [[adium preferenceController] registerPreferenceObserver:self forGroup:PREF_GROUP_CONTACT_LIST]; 
    8181        [[adium preferenceController] registerPreferenceObserver:self forGroup:PREF_GROUP_CONTACT_LIST_DISPLAY]; 
     82         
     83        [[adium contactController] registerListObjectObserver:self]; 
    8284} 
    8385 
     
    9496                return; 
    9597         
    96         if ([group isEqualToString:PREF_GROUP_CONTACT_LIST]) { 
    97                 BOOL oldCountAllObjects = countAllObjects; 
    98                 BOOL oldCountOnlineObjects = countOnlineObjects; 
    99                  
     98        if ([group isEqualToString:PREF_GROUP_CONTACT_LIST] && 
     99                ([key isEqualToString:KEY_COUNT_VISIBLE_CONTACTS] || [key isEqualToString:KEY_COUNT_ALL_CONTACTS])) { 
    100100                countAllObjects = [[prefDict objectForKey:KEY_COUNT_ALL_CONTACTS] boolValue]; 
    101                 countOnlineObjects = [[prefDict objectForKey:KEY_COUNT_ONLINE_CONTACTS] boolValue]; 
    102                  
    103                 if ((countAllObjects && !oldCountAllObjects) || (countOnlineObjects && !oldCountOnlineObjects)) { 
    104                         //One of the displays is on, but it was off before 
    105                          
    106                         if (!oldCountAllObjects && !oldCountOnlineObjects) { 
    107                                 //Install our observer if we are now counting contacts in some form but weren't before 
    108                                 //This will update all list objects. 
    109                                 [[adium contactController] registerListObjectObserver:self];                             
    110                         } else { 
    111                                 //Refresh all 
    112                                 [[adium contactController] updateAllListObjectsForObserver:self]; 
    113                         } 
    114                          
    115                 } else if ((!countAllObjects && oldCountAllObjects) || (!countOnlineObjects && oldCountOnlineObjects)) { 
    116                         //One of the displays is off, but it was on before 
    117                          
    118                         //Refresh all 
    119                         [[adium contactController] updateAllListObjectsForObserver:self]; 
    120                          
    121                         if (!countAllObjects && !countOnlineObjects) { 
    122                                 //Remove our observer since we are now doing no counting 
    123                                 [[adium contactController] unregisterListObjectObserver:self]; 
    124                         } 
    125                 } 
    126                  
    127                 [menuItem_countOnlineObjects setTitle:(countOnlineObjects ? HIDE_COUNT_ONLINE_CONTACTS_TITLE : SHOW_COUNT_ONLINE_CONTACTS_TITLE)]; 
     101                countVisibleObjects = [[prefDict objectForKey:KEY_COUNT_VISIBLE_CONTACTS] boolValue]; 
     102                 
     103                [[adium contactController] updateAllListObjectsForObserver:self]; 
     104         
     105                [menuItem_countVisibleObjects setTitle:(countVisibleObjects ? HIDE_COUNT_VISIBLE_CONTACTS_TITLE : SHOW_COUNT_VISIBLE_CONTACTS_TITLE)]; 
    128106                [menuItem_countAllObjects setTitle:(countAllObjects ? HIDE_COUNT_ALL_CONTACTS_TITLE : SHOW_COUNT_ALL_CONTACTS_TITLE)]; 
    129107 
     
    142120 
    143121        //We never update for an AIAccount object 
    144         if ([inObject isKindOfClass:[AIAccount class]]) return nil; 
     122        if ([inObject isKindOfClass:[AIAccount class]] || ![inObject isKindOfClass:[AIListGroup class]]) return nil; 
    145123 
    146124        /* We check against a nil inModifiedKeys so we can remove our Counting information from the display when the user 
     
    148126         * 
    149127         * We update for any group which isn't the root group when its contained objects count changes. 
    150          * We update a contact's containing group when its online state changes. 
     128         * We update a contact's containing group when its visible state changes. 
    151129         */      
    152130        if ((inModifiedKeys == nil) || 
    153            ((countOnlineObjects || countAllObjects) && 
    154                 (([inObject isKindOfClass:[AIListGroup class]] && [inModifiedKeys containsObject:@"ObjectCount"] && ![[inObject UID] isEqualToString:ADIUM_ROOT_GROUP_NAME]) || 
    155                  ([inObject isKindOfClass:[AIListContact class]] && [inModifiedKeys containsObject:@"Online"])))) { 
    156                  
    157                 /* Obtain the group we want to work with -- for a contact, use its parent group. 
    158                  * 
    159                  * Casting note: We already checked that it isn't an AIAccount. If it's an AIListContact, we get the parentGroup. Otherwise, 
    160                  * it's an AIListGroup and we use the object itself. There is probably a way to set this method up without this convoluted casting interplay. 
    161                  */ 
    162                 AIListGroup             *targetGroup = ([inObject isKindOfClass:[AIListContact class]] ?  
    163                                                                                 [(AIListContact *)inObject parentGroup] : 
    164                                                                                 (AIListGroup *)inObject); 
    165  
     131                (([inModifiedKeys containsObject:@"ObjectCount"] || [inModifiedKeys containsObject:@"VisibleObjectCount"]) && 
     132                 (![[inObject UID] isEqualToString:ADIUM_ROOT_GROUP_NAME]))) { 
     133                 
    166134                NSString                *countString = nil; 
    167                 int onlineObjects = 0, totalObjects = 0; 
    168  
    169                 //Obtain a count of online objects in this group 
    170                 if (countOnlineObjects) { 
    171                         AIListObject    *containedObject; 
    172                         NSEnumerator    *enumerator; 
    173                          
    174                         onlineObjects = 0; 
    175                         enumerator = [[targetGroup containedObjects] objectEnumerator]; 
    176                         while ((containedObject = [enumerator nextObject])) { 
    177                                 if ([containedObject online]) onlineObjects++; 
    178                         } 
     135                 
     136                int visibleObjects = [[inObject valueForProperty:@"VisibleObjectCount"] intValue]; 
     137                int totalObjects = [[inObject valueForProperty:@"ObjectCount"] intValue]; 
     138         
     139                // Create our count string for displaying in the list group's cell 
     140                // If the number of visible objects is the same as the number of total objects, just display one number. 
     141                if (countVisibleObjects && countAllObjects && (visibleObjects != totalObjects)) { 
     142                        countString = [NSString stringWithFormat:AILocalizedString(@"(%i of %i)", "Used in the display for the contact list for the number of visible contacts out of the number of total contacts"), 
     143                                                                                                        visibleObjects, totalObjects]; 
     144                } else if (countAllObjects) { 
     145                        countString = [NSString stringWithFormat:@"(%i)", totalObjects]; 
     146                } else { 
     147                        countString = [NSString stringWithFormat:@"(%i)", visibleObjects]; 
    179148                } 
    180149                 
    181                 //Obtain a count of all objects in this group 
    182                 if (countAllObjects) { 
    183                         totalObjects = [[targetGroup valueForProperty:@"ObjectCount"] intValue]; 
    184                 } 
    185          
    186                 //Build a string to add to the right of the name which shows any information we just extracted 
    187                 if (countOnlineObjects && countAllObjects) { 
    188                         countString = [NSString stringWithFormat:AILocalizedString(@" (%i of %i)", /*comment*/ nil), onlineObjects, totalObjects]; 
    189                 } else if (countAllObjects) { 
    190                         countString = [NSString stringWithFormat:@" (%i)", totalObjects]; 
    191                 } else if (countOnlineObjects) { 
    192                         countString = [NSString stringWithFormat:@" (%i)", onlineObjects]; 
    193                 } 
    194  
    195                 if (countString) { 
    196                         AIMutableOwnerArray *rightTextArray = [targetGroup displayArrayForKey:@"Right Text"]; 
    197                          
    198                         [rightTextArray setObject:countString withOwner:self priorityLevel:High_Priority]; 
    199                         modifiedAttributes = [NSSet setWithObject:@"Right Text"]; 
    200                 } else { 
    201                         AIMutableOwnerArray *rightTextArray = [targetGroup displayArrayForKey:@"Right Text" create:NO]; 
    202                          
    203                         //If there is a right text object now but there shouldn't be anymore, remove it 
    204                         if ([rightTextArray objectWithOwner:self]) { 
    205                                 [rightTextArray setObject:nil withOwner:self priorityLevel:High_Priority]; 
    206                                 modifiedAttributes = [NSSet setWithObject:@"Right Text"]; 
    207                         } 
    208                 } 
     150                NSLog(@"Set to %@ for %@", countString, inObject); 
     151 
     152                [[inObject displayArrayForKey:@"Count Text"] setObject:countString withOwner:self]; 
     153                [[inObject displayArrayForKey:@"Show Count"] setObject:[NSNumber numberWithBool:(countVisibleObjects || countAllObjects)] withOwner:self]; 
     154         
     155                modifiedAttributes = [NSSet setWithObject:@"Count Text"]; 
    209156        } 
    210157         
     
    217164- (void)toggleMenuItem:(id)sender 
    218165{ 
    219         if (sender == menuItem_countOnlineObjects) { 
    220                 BOOL    newPref = !countOnlineObjects; 
     166        if (sender == menuItem_countVisibleObjects) { 
     167                BOOL    newPref = !countVisibleObjects; 
    221168 
    222169                //Toggle and set, which will call back on preferencesChanged: above 
    223                 [menuItem_countOnlineObjects setTitle:(newPref ? HIDE_COUNT_ONLINE_CONTACTS_TITLE : SHOW_COUNT_ONLINE_CONTACTS_TITLE)]; 
     170                [menuItem_countVisibleObjects setTitle:(newPref ? HIDE_COUNT_VISIBLE_CONTACTS_TITLE : SHOW_COUNT_VISIBLE_CONTACTS_TITLE)]; 
    224171                [[adium preferenceController] setPreference:[NSNumber numberWithBool:newPref] 
    225                                                                                          forKey:KEY_COUNT_ONLINE_CONTACTS 
     172                                                                                         forKey:KEY_COUNT_VISIBLE_CONTACTS 
    226173                                                                                          group:PREF_GROUP_CONTACT_LIST]; 
    227174 
     
    239186- (BOOL)validateMenuItem:(NSMenuItem *)menuItem 
    240187{ 
    241     if ((menuItem == menuItem_countOnlineObjects) || (menuItem == menuItem_countAllObjects)) { 
     188    if ((menuItem == menuItem_countVisibleObjects) || (menuItem == menuItem_countAllObjects)) { 
    242189                return showingGroups; 
    243190        }