Skip to content

Commit

Permalink
Implemented enhancement from issue 20. It is now possible to change a…
Browse files Browse the repository at this point in the history
…ccount order in preferences with drag and drop.
  • Loading branch information
eofster committed Feb 21, 2009
1 parent d0a3ec6 commit 6945bee
Show file tree
Hide file tree
Showing 3 changed files with 104 additions and 0 deletions.
4 changes: 4 additions & 0 deletions AKPreferenceController.h
Expand Up @@ -68,6 +68,9 @@ extern NSString * const AKUseProxy;
extern NSString * const AKProxyHost;
extern NSString * const AKProxyPort;

extern NSString * const AKSourceIndex;
extern NSString * const AKDestinationIndex;

@interface AKPreferenceController : NSWindowController {
@private
id delegate;
Expand Down Expand Up @@ -176,4 +179,5 @@ enum {
extern NSString * const AKPreferenceControllerDidAddAccountNotification;
extern NSString * const AKPreferenceControllerDidRemoveAccountNotification; // AKAccountIndex.
extern NSString * const AKPreferenceControllerDidChangeAccountEnabledNotification; // AKAccountIndex.
extern NSString * const AKPreferenceControllerDidSwapAccountsNotification; // AKSourceIndex, AKDestinationIndex.
extern NSString * const AKPreferenceControllerDidChangeNetworkSettingsNotification;
84 changes: 84 additions & 0 deletions AKPreferenceController.m
Expand Up @@ -35,6 +35,8 @@
#import "NSWindowAdditions.h"


NSString * const AKTelephoneAccountPboardType = @"AKTelephoneAccountPboardType";

@interface AKPreferenceController()

- (BOOL)checkForNetworkSettingsChanges:(id)sender;
Expand Down Expand Up @@ -78,9 +80,13 @@ - (void)networkSettingsChangeAlertDidEnd:(NSAlert *)alert returnCode:(int)return
NSString * const AKProxyHost = @"ProxyHost";
NSString * const AKProxyPort = @"ProxyPort";

NSString * const AKSourceIndex = @"AKSourceIndex";
NSString * const AKDestinationIndex = @"AKDestinationIndex";

NSString * const AKPreferenceControllerDidAddAccountNotification = @"AKPreferenceControllerDidAddAccount";
NSString * const AKPreferenceControllerDidRemoveAccountNotification = @"AKPreferenceControllerDidRemoveAccount";
NSString * const AKPreferenceControllerDidChangeAccountEnabledNotification = @"AKPreferenceControllerDidChangeAccountEnabled";
NSString * const AKPreferenceControllerDidSwapAccountsNotification = @"AKPreferenceControllerDidSwapAccounts";
NSString * const AKPreferenceControllerDidChangeNetworkSettingsNotification = @"AKPreferenceControllerDidChangeNetworkSettings";

@implementation AKPreferenceController
Expand Down Expand Up @@ -124,6 +130,12 @@ - (void)setDelegate:(id)aDelegate
name:AKPreferenceControllerDidChangeAccountEnabledNotification
object:self];

if ([aDelegate respondsToSelector:@selector(preferenceControllerDidSwapAccounts:)])
[notificationCenter addObserver:aDelegate
selector:@selector(preferenceControllerDidSwapAccounts:)
name:AKPreferenceControllerDidSwapAccountsNotification
object:self];

if ([aDelegate respondsToSelector:@selector(preferenceControllerDidChangeNetworkSettings:)])
[notificationCenter addObserver:aDelegate
selector:@selector(preferenceControllerDidChangeNetworkSettings:)
Expand Down Expand Up @@ -164,6 +176,12 @@ - (void)dealloc
[super dealloc];
}

- (void)awakeFromNib
{
// Register a pasteboard type to rearrange accounts with drag and drop.
[accountsTable registerForDraggedTypes:[NSArray arrayWithObject:AKTelephoneAccountPboardType]];
}

- (void)windowDidLoad
{
[self updateAvailableSounds];
Expand Down Expand Up @@ -884,6 +902,72 @@ - (id)tableView:(NSTableView *)aTableView
return [accountDict objectForKey:[aTableColumn identifier]];
}

- (BOOL)tableView:(NSTableView *)aTableView writeRowsWithIndexes:(NSIndexSet *)rowIndexes toPasteboard:(NSPasteboard *)pboard
{
NSData *data = [NSKeyedArchiver archivedDataWithRootObject:rowIndexes];
[pboard declareTypes:[NSArray arrayWithObject:AKTelephoneAccountPboardType] owner:self];
[pboard setData:data forType:AKTelephoneAccountPboardType];

return YES;
}

- (NSDragOperation)tableView:(NSTableView *)aTableView
validateDrop:(id <NSDraggingInfo>)info
proposedRow:(NSInteger)row
proposedDropOperation:(NSTableViewDropOperation)operation
{
NSData *data = [[info draggingPasteboard] dataForType:AKTelephoneAccountPboardType];
NSIndexSet *indexes = [NSKeyedUnarchiver unarchiveObjectWithData:data];
NSInteger draggingRow = [indexes firstIndex];

if (row == draggingRow || row == draggingRow + 1)
return NSDragOperationNone;

[accountsTable setDropRow:row dropOperation:NSTableViewDropAbove];

return NSDragOperationMove;
}

- (BOOL)tableView:(NSTableView *)aTableView
acceptDrop:(id <NSDraggingInfo>)info
row:(NSInteger)row
dropOperation:(NSTableViewDropOperation)operation
{
NSData *data = [[info draggingPasteboard] dataForType:AKTelephoneAccountPboardType];
NSIndexSet *indexes = [NSKeyedUnarchiver unarchiveObjectWithData:data];
NSInteger draggingRow = [indexes firstIndex];

NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
NSMutableArray *accounts = [[defaults arrayForKey:AKAccounts] mutableCopy];
id selectedAccount = [accounts objectAtIndex:[accountsTable selectedRow]];

// Swap accounts.
[accounts insertObject:[accounts objectAtIndex:draggingRow] atIndex:row];
if (draggingRow < row)
[accounts removeObjectAtIndex:draggingRow];
else if (draggingRow > row)
[accounts removeObjectAtIndex:(draggingRow + 1)];
else // This should never happen because we don't validate such drop.
return NO;

[defaults setObject:accounts forKey:AKAccounts];
[defaults synchronize];

[accountsTable reloadData];

// Preserve account selection.
[accountsTable selectRow:[accounts indexOfObject:selectedAccount] byExtendingSelection:NO];

[[NSNotificationCenter defaultCenter] postNotificationName:AKPreferenceControllerDidSwapAccountsNotification
object:self
userInfo:[NSDictionary dictionaryWithObjectsAndKeys:
[NSNumber numberWithInteger:draggingRow], AKSourceIndex,
[NSNumber numberWithInteger:row], AKDestinationIndex,
nil]];

return YES;
}


#pragma mark -
#pragma mark NSTableView delegate
Expand Down
16 changes: 16 additions & 0 deletions AppController.m
Expand Up @@ -944,6 +944,22 @@ - (void)preferenceControllerDidChangeAccountEnabled:(NSNotification *)notificati
}
}

- (void)preferenceControllerDidSwapAccounts:(NSNotification *)notification
{
NSDictionary *userInfo = [notification userInfo];
NSInteger sourceIndex = [[userInfo objectForKey:AKSourceIndex] integerValue];
NSInteger destinationIndex = [[userInfo objectForKey:AKDestinationIndex] integerValue];

if (sourceIndex == destinationIndex)
return;

[[self accountControllers] insertObject:[[self accountControllers] objectAtIndex:sourceIndex] atIndex:destinationIndex];
if (sourceIndex < destinationIndex)
[[self accountControllers] removeObjectAtIndex:sourceIndex];
else if (sourceIndex > destinationIndex)
[[self accountControllers] removeObjectAtIndex:(sourceIndex + 1)];
}

- (void)preferenceControllerDidChangeNetworkSettings:(NSNotification *)notification
{
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
Expand Down

0 comments on commit 6945bee

Please sign in to comment.