diff --git a/AppKit/CPArrayController.j b/AppKit/CPArrayController.j index 764096a0b..3e22ad838 100644 --- a/AppKit/CPArrayController.j +++ b/AppKit/CPArrayController.j @@ -879,6 +879,9 @@ [_arrangedObjects removeObjectAtIndex:pos]; [_selectionIndexes shiftIndexesStartingAtIndex:pos by:-1]; + + // This will automatically handle the avoidsEmptySelection case. + [self __setSelectionIndexes:_selectionIndexes]; } [self didChangeValueForKey:@"content"]; diff --git a/Tests/Manual/ArrayControllerRemovingFirstTest/AppController.j b/Tests/Manual/ArrayControllerRemovingFirstTest/AppController.j new file mode 100644 index 000000000..1ddd8d6f6 --- /dev/null +++ b/Tests/Manual/ArrayControllerRemovingFirstTest/AppController.j @@ -0,0 +1,102 @@ +/* + * AppController.j + * ArrayControllerRemovingFirstTest + * + * Created by You on July 17, 2012. + * Copyright 2012, Your Company All rights reserved. + */ + +@import + + +@implementation AppController : CPObject +{ + CPArrayController arrayController; +} + +- (void)applicationDidFinishLaunching:(CPNotification)aNotification +{ + var theWindow = [[CPWindow alloc] initWithContentRect:CGRectMakeZero() styleMask:CPBorderlessBridgeWindowMask], + contentView = [theWindow contentView]; + + arrayController = [[CPArrayController alloc] init]; + [arrayController addObserver:self forKeyPath:@"selectionIndex" options: nil context: nil]; + var items = [CPMutableArray array]; + [items addObject:[[Item alloc] initWithTitle:@"1st Item"]]; + [items addObject:[[Item alloc] initWithTitle:@"2nd Item"]]; + [items addObject:[[Item alloc] initWithTitle:@"3rd Item"]]; + [items addObject:[[Item alloc] initWithTitle:@"4th Item"]]; + [arrayController setContent:items]; + + var label = [CPTextField labelWithTitle:@"Press buttons to see [Remove First By Object] fails while [Remove First By Index] succeeds"]; + [label setFrameOrigin:CGPointMake(20, 20)]; + [contentView addSubview:label]; + + var field = [CPTextField textFieldWithStringValue:@"" placeholder:@"" width:100]; + [field setFrameOrigin:CGPointMake(20, 50)]; + [field bind:@"value" toObject:self withKeyPath:@"arrayController.selection.title" options:nil]; + [contentView addSubview:field]; + + var button = [CPButton buttonWithTitle:@"Remove First By Object"]; + [button setFrameOrigin:CGPointMake(150, 50)]; + [button setTarget:self]; + [button setAction:@selector(removeFirst:)]; + [contentView addSubview:button]; + + var button2 = [CPButton buttonWithTitle:@"Remove First By Index"]; + [button2 setFrameOrigin:CGPointMake(350, 50)]; + [button2 setTarget:self]; + [button2 setAction:@selector(removeFirstByIndex:)]; + [contentView addSubview:button2]; + + [arrayController setSelectionIndex:0] + + [theWindow orderFront:self]; + + // Uncomment the following line to turn on the standard menu bar. + //[CPMenu setMenuBarVisible:YES]; +} + +- (void)removeFirst:(id)sender +{ + var selectedObjects = [arrayController selectedObjects]; + [arrayController removeObject:[selectedObjects objectAtIndex:0]]; +} + +- (void)removeFirstByIndex:(id)sender +{ + [arrayController removeObjectAtArrangedObjectIndex:0]; +} + +- (void)observeValueForKeyPath:(CPString)keyPath ofObject:(id)object change:(CPDictionary)change context:(id)context +{ + var oldIndex = [change valueForKey:CPKeyValueChangeOldKey]; + var newIndex = [change valueForKey:CPKeyValueChangeNewKey]; + + CPLog("TCDocument selectionIndexChanged from " + oldIndex + " to " + newIndex + ", contains " + [[arrayController arrangedObjects] count] + " objects"); +} + +@end + +@implementation Item : CPObject +{ + CPString title; +} + +- (id)initWithTitle:(CPString)aTitle +{ + self = [super init]; + if (self) + { + title = aTitle; + } + return self; +} + +- (CPString)title +{ + return title; +} + +@end + diff --git a/Tests/Manual/ArrayControllerRemovingFirstTest/Info.plist b/Tests/Manual/ArrayControllerRemovingFirstTest/Info.plist new file mode 100644 index 000000000..42f65de58 --- /dev/null +++ b/Tests/Manual/ArrayControllerRemovingFirstTest/Info.plist @@ -0,0 +1,12 @@ + + + + + CPApplicationDelegateClass + AppController + CPBundleName + ArrayControllerRemovingFirstTest + CPPrincipalClass + CPApplication + + diff --git a/Tests/Manual/ArrayControllerRemovingFirstTest/Jakefile b/Tests/Manual/ArrayControllerRemovingFirstTest/Jakefile new file mode 100644 index 000000000..6f4a90273 --- /dev/null +++ b/Tests/Manual/ArrayControllerRemovingFirstTest/Jakefile @@ -0,0 +1,93 @@ +/* + * Jakefile + * ArrayControllerRemovingFirstTest + * + * Created by You on July 17, 2012. + * Copyright 2012, Your Company All rights reserved. + */ + +var ENV = require("system").env, + FILE = require("file"), + JAKE = require("jake"), + task = JAKE.task, + FileList = JAKE.FileList, + app = require("cappuccino/jake").app, + configuration = ENV["CONFIG"] || ENV["CONFIGURATION"] || ENV["c"] || "Debug", + OS = require("os"); + +app ("ArrayControllerRemovingFirstTest", function(task) +{ + task.setBuildIntermediatesPath(FILE.join("Build", "ArrayControllerRemovingFirstTest.build", configuration)); + task.setBuildPath(FILE.join("Build", configuration)); + + task.setProductName("ArrayControllerRemovingFirstTest"); + task.setIdentifier("com.yourcompany.ArrayControllerRemovingFirstTest"); + task.setVersion("1.0"); + task.setAuthor("Your Company"); + task.setEmail("feedback @nospam@ yourcompany.com"); + task.setSummary("ArrayControllerRemovingFirstTest"); + task.setSources((new FileList("**/*.j")).exclude(FILE.join("Build", "**"))); + task.setResources(new FileList("Resources/**")); + task.setIndexFilePath("index.html"); + task.setInfoPlistPath("Info.plist"); + + if (configuration === "Debug") + task.setCompilerFlags("-DDEBUG -g"); + else + task.setCompilerFlags("-O"); +}); + +task ("default", ["ArrayControllerRemovingFirstTest"], function() +{ + printResults(configuration); +}); + +task ("build", ["default"]); + +task ("debug", function() +{ + ENV["CONFIGURATION"] = "Debug"; + JAKE.subjake(["."], "build", ENV); +}); + +task ("release", function() +{ + ENV["CONFIGURATION"] = "Release"; + JAKE.subjake(["."], "build", ENV); +}); + +task ("run", ["debug"], function() +{ + OS.system(["open", FILE.join("Build", "Debug", "ArrayControllerRemovingFirstTest", "index.html")]); +}); + +task ("run-release", ["release"], function() +{ + OS.system(["open", FILE.join("Build", "Release", "ArrayControllerRemovingFirstTest", "index.html")]); +}); + +task ("deploy", ["release"], function() +{ + FILE.mkdirs(FILE.join("Build", "Deployment", "ArrayControllerRemovingFirstTest")); + OS.system(["press", "-f", FILE.join("Build", "Release", "ArrayControllerRemovingFirstTest"), FILE.join("Build", "Deployment", "ArrayControllerRemovingFirstTest")]); + printResults("Deployment") +}); + +task ("desktop", ["release"], function() +{ + FILE.mkdirs(FILE.join("Build", "Desktop", "ArrayControllerRemovingFirstTest")); + require("cappuccino/nativehost").buildNativeHost(FILE.join("Build", "Release", "ArrayControllerRemovingFirstTest"), FILE.join("Build", "Desktop", "ArrayControllerRemovingFirstTest", "ArrayControllerRemovingFirstTest.app")); + printResults("Desktop") +}); + +task ("run-desktop", ["desktop"], function() +{ + OS.system([FILE.join("Build", "Desktop", "ArrayControllerRemovingFirstTest", "ArrayControllerRemovingFirstTest.app", "Contents", "MacOS", "NativeHost"), "-i"]); +}); + +function printResults(configuration) +{ + print("----------------------------"); + print(configuration+" app built at path: "+FILE.join("Build", configuration, "ArrayControllerRemovingFirstTest")); + print("----------------------------"); +} diff --git a/Tests/Manual/ArrayControllerRemovingFirstTest/Resources/spinner.gif b/Tests/Manual/ArrayControllerRemovingFirstTest/Resources/spinner.gif new file mode 100644 index 000000000..06dbc2bc2 Binary files /dev/null and b/Tests/Manual/ArrayControllerRemovingFirstTest/Resources/spinner.gif differ diff --git a/Tests/Manual/ArrayControllerRemovingFirstTest/index-debug.html b/Tests/Manual/ArrayControllerRemovingFirstTest/index-debug.html new file mode 100644 index 000000000..1c5f0943a --- /dev/null +++ b/Tests/Manual/ArrayControllerRemovingFirstTest/index-debug.html @@ -0,0 +1,107 @@ + + + + + + + + + + + + + + + ArrayControllerRemovingFirstTest + + + + + + + + + + + + + + +
+
+ + + +
+
+ + + diff --git a/Tests/Manual/ArrayControllerRemovingFirstTest/index.html b/Tests/Manual/ArrayControllerRemovingFirstTest/index.html new file mode 100644 index 000000000..707d86be9 --- /dev/null +++ b/Tests/Manual/ArrayControllerRemovingFirstTest/index.html @@ -0,0 +1,78 @@ + + + + + + + + + + + + + + + ArrayControllerRemovingFirstTest + + + + + + + + + + + + +
+
+ + + +
+
+ + + + diff --git a/Tests/Manual/ArrayControllerRemovingFirstTest/main.j b/Tests/Manual/ArrayControllerRemovingFirstTest/main.j new file mode 100644 index 000000000..60b8fb56d --- /dev/null +++ b/Tests/Manual/ArrayControllerRemovingFirstTest/main.j @@ -0,0 +1,18 @@ +/* + * AppController.j + * ArrayControllerRemovingFirstTest + * + * Created by You on July 17, 2012. + * Copyright 2012, Your Company All rights reserved. + */ + +@import +@import + +@import "AppController.j" + + +function main(args, namedArgs) +{ + CPApplicationMain(args, namedArgs); +}