2 * Adium is the legal property of its developers, whose names are listed in the copyright file included
3 * with this source distribution.
5 * This program is free software; you can redistribute it and/or modify it under the terms of the GNU
6 * General Public License as published by the Free Software Foundation; either version 2 of the License,
7 * or (at your option) any later version.
9 * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even
10 * the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
11 * Public License for more details.
13 * You should have received a copy of the GNU General Public License along with this program; if not,
14 * write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
17 #import <Adium/AIContactControllerProtocol.h>
18 #import "ESAccountEvents.h"
19 #import <Adium/AIContactAlertsControllerProtocol.h>
20 #import <AIUtilities/AIImageAdditions.h>
21 #import <Adium/AIAccount.h>
23 #define ACCOUNT_CONNECTION_STATUS_GROUPING 4.0
26 * @class ESAccountEvents
27 * @brief Component to handle account-related Contact Alerts events
29 @implementation ESAccountEvents
36 accountConnectionStatusGroupingOnlineTimer = nil;
37 accountConnectionStatusGroupingOfflineTimer = nil;
39 //Register the events we generate
40 [[adium contactAlertsController] registerEventID:ACCOUNT_CONNECTED withHandler:self inGroup:AIAccountsEventHandlerGroup globalOnly:YES];
41 [[adium contactAlertsController] registerEventID:ACCOUNT_DISCONNECTED withHandler:self inGroup:AIAccountsEventHandlerGroup globalOnly:YES];
42 [[adium contactAlertsController] registerEventID:ACCOUNT_RECEIVED_EMAIL withHandler:self inGroup:AIOtherEventHandlerGroup globalOnly:YES];
44 //Observe status changes
45 [[adium contactController] registerListObjectObserver:self];
48 - (void)uninstallPlugin
50 [[adium contactController] unregisterListObjectObserver:self];
54 * @brief Short description for an event
56 * We're global-only, so no short descriptions are needed.
58 - (NSString *)shortDescriptionForEventID:(NSString *)eventID { return @""; }
61 * @brief Global short description for an event
63 - (NSString *)globalShortDescriptionForEventID:(NSString *)eventID
65 NSString *description;
67 if ([eventID isEqualToString:ACCOUNT_CONNECTED]) {
68 description = AILocalizedString(@"You connect",nil);
69 } else if ([eventID isEqualToString:ACCOUNT_DISCONNECTED]) {
70 description = AILocalizedString(@"You disconnect",nil);
71 } else if ([eventID isEqualToString:ACCOUNT_RECEIVED_EMAIL]) {
72 description = AILocalizedString(@"New email notification",nil);
81 * @brief English, non-translated global short description for an event
83 * This exists because old X(tras) relied upon matching the description of event IDs, and I don't feel like making
84 * a converter for old packs. If anyone wants to fix this situation, please feel free :)
86 * @result English global short description which should only be used internally
88 - (NSString *)englishGlobalShortDescriptionForEventID:(NSString *)eventID
90 NSString *description;
92 if ([eventID isEqualToString:ACCOUNT_CONNECTED]) {
93 description = @"Connected";
94 } else if ([eventID isEqualToString:ACCOUNT_DISCONNECTED]) {
95 description = @"Disconnected";
96 } else if ([eventID isEqualToString:ACCOUNT_RECEIVED_EMAIL]) {
97 description = @"New Mail Received";
106 * @brief Long description for an event
108 - (NSString *)longDescriptionForEventID:(NSString *)eventID forListObject:(AIListObject *)listObject
110 NSString *description;
112 if ([eventID isEqualToString:ACCOUNT_CONNECTED]) {
113 description = AILocalizedString(@"When you connect",nil);
114 } else if ([eventID isEqualToString:ACCOUNT_DISCONNECTED]) {
115 description = AILocalizedString(@"When you disconnect",nil);
116 } else if ([eventID isEqualToString:ACCOUNT_RECEIVED_EMAIL]) {
117 description = AILocalizedString(@"When you receive a new email notification",nil);
126 * @brief Natural language description for an event
128 * @param eventID The event identifier
129 * @param listObject The listObject triggering the event
130 * @param userInfo Event-specific userInfo
131 * @param includeSubject If YES, return a full sentence. If not, return a fragment.
132 * @result The natural language description.
134 - (NSString *)naturalLanguageDescriptionForEventID:(NSString *)eventID
135 listObject:(AIListObject *)listObject
136 userInfo:(id)userInfo
137 includeSubject:(BOOL)includeSubject
139 NSString *description = nil;
141 if (includeSubject) {
142 NSString *format = nil;
143 if ([eventID isEqualToString:ACCOUNT_CONNECTED]) {
144 format = AILocalizedString(@"%@ connected",nil);
145 } else if ([eventID isEqualToString:ACCOUNT_DISCONNECTED]) {
146 format = AILocalizedString(@"%@ disconnected",nil);
147 } else if ([eventID isEqualToString:ACCOUNT_RECEIVED_EMAIL]) {
148 format = AILocalizedString(@"%@ received new email",nil);
152 description = [NSString stringWithFormat:format,[listObject formattedUID]];
155 if ([eventID isEqualToString:ACCOUNT_CONNECTED]) {
156 description = AILocalizedString(@"connected",nil);
157 } else if ([eventID isEqualToString:ACCOUNT_DISCONNECTED]) {
158 description = AILocalizedString(@"disconnected",nil);
159 } else if ([eventID isEqualToString:ACCOUNT_RECEIVED_EMAIL]) {
160 if (userInfo && [userInfo isKindOfClass:[NSString class]]) {
161 description = [[(NSString *)userInfo copy] autorelease];
164 description = AILocalizedString(@"received new email",nil);
172 - (NSImage *)imageForEventID:(NSString *)eventID
174 static NSImage *eventImage = nil;
175 if (!eventImage) eventImage = [[NSImage imageNamed:@"pref-accounts" forClass:[self class]] retain];
179 #pragma mark Aggregation and event generation
181 * @brief Update list object
183 * We aggregate account connection events to avoid a quick sign on/sign off from triggering the event
185 - (NSSet *)updateListObject:(AIListObject *)inObject keys:(NSSet *)inModifiedKeys silent:(BOOL)silent
187 if ([inObject isKindOfClass:[AIAccount class]]) { //We only care about accounts
188 if ([inModifiedKeys containsObject:@"Online"]) {
190 if ([[inObject numberStatusObjectForKey:@"Online"] boolValue]) {
191 if (accountConnectionStatusGroupingOnlineTimer) {
192 [accountConnectionStatusGroupingOnlineTimer invalidate]; [accountConnectionStatusGroupingOnlineTimer release];
195 accountConnectionStatusGroupingOnlineTimer = [[NSTimer scheduledTimerWithTimeInterval:ACCOUNT_CONNECTION_STATUS_GROUPING
197 selector:@selector(accountConnection:)
201 if (accountConnectionStatusGroupingOfflineTimer) {
202 [accountConnectionStatusGroupingOfflineTimer invalidate]; [accountConnectionStatusGroupingOfflineTimer release];
205 accountConnectionStatusGroupingOfflineTimer = [[NSTimer scheduledTimerWithTimeInterval:ACCOUNT_CONNECTION_STATUS_GROUPING
207 selector:@selector(accountDisconnection:)
218 * @brief Called an account connects and remains online for ACCOUNT_CONNECTION_STATUS_GROUPING
220 - (void)accountConnection:(NSTimer *)timer
222 [[adium contactAlertsController] generateEvent:ACCOUNT_CONNECTED
223 forListObject:[timer userInfo]
225 previouslyPerformedActionIDs:nil];
226 [accountConnectionStatusGroupingOnlineTimer release]; accountConnectionStatusGroupingOnlineTimer = nil;
230 * @brief Called an account disconnects and remains offline for ACCOUNT_CONNECTION_STATUS_GROUPING
232 - (void)accountDisconnection:(NSTimer *)timer
234 [[adium contactAlertsController] generateEvent:ACCOUNT_DISCONNECTED
235 forListObject:[timer userInfo]
237 previouslyPerformedActionIDs:nil];
238 [accountConnectionStatusGroupingOfflineTimer release]; accountConnectionStatusGroupingOfflineTimer = nil;