OLD | NEW |
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #import "chrome/browser/cocoa/cookies_window_controller.h" | 5 #import "chrome/browser/cocoa/cookies_window_controller.h" |
6 | 6 |
7 #include <queue> | 7 #include <queue> |
8 #include <vector> | 8 #include <vector> |
9 | 9 |
10 #include "app/l10n_util_mac.h" | 10 #include "app/l10n_util_mac.h" |
(...skipping 256 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
267 DCHECK([sender isKindOfClass:[NSSearchField class]]); | 267 DCHECK([sender isKindOfClass:[NSSearchField class]]); |
268 NSString* string = [sender stringValue]; | 268 NSString* string = [sender stringValue]; |
269 // Invalidate the model here because all the nodes are going to be removed | 269 // Invalidate the model here because all the nodes are going to be removed |
270 // in UpdateSearchResults(). This could lead to there temporarily being | 270 // in UpdateSearchResults(). This could lead to there temporarily being |
271 // invalid pointers in the Cocoa model. | 271 // invalid pointers in the Cocoa model. |
272 modelObserver_->InvalidateCocoaModel(); | 272 modelObserver_->InvalidateCocoaModel(); |
273 treeModel_->UpdateSearchResults(base::SysNSStringToWide(string)); | 273 treeModel_->UpdateSearchResults(base::SysNSStringToWide(string)); |
274 } | 274 } |
275 | 275 |
276 - (IBAction)deleteCookie:(id)sender { | 276 - (IBAction)deleteCookie:(id)sender { |
277 NSIndexPath* selectionPath = [treeController_ selectionIndexPath]; | 277 DCHECK_EQ(1U, [[treeController_ selectedObjects] count]); |
278 // N.B.: I suspect that |-selectedObjects| does not retain/autorelease the | 278 [self deleteNodeAtIndexPath:[treeController_ selectionIndexPath]]; |
279 // return value, which may result in the pointer going to garbage before it | 279 } |
280 // even goes out of scope. Retaining it immediately will fix this. | 280 |
281 NSArray* selection = [treeController_ selectedObjects]; | 281 // This will delete the Cocoa model node as well as the backing model object at |
282 if (selectionPath) { | 282 // the specified index path in the Cocoa model. If the node that was deleted |
283 DCHECK_EQ([selection count], 1U); | 283 // was the sole child of the parent node, this will be called recursively to |
284 CocoaCookieTreeNode* node = [selection lastObject]; | 284 // delete empty parents. |
285 CookieTreeNode* cookie = static_cast<CookieTreeNode*>([node treeNode]); | 285 - (void)deleteNodeAtIndexPath:(NSIndexPath*)path { |
286 treeModel_->DeleteCookieNode(cookie); | 286 NSTreeNode* treeNode = |
287 // If there is a next cookie, this will select it because items will slide | 287 [[treeController_ arrangedObjects] descendantNodeAtIndexPath:path]; |
288 // up. If there is no next cookie, this is a no-op. | 288 if (!treeNode) |
289 [treeController_ setSelectionIndexPath:selectionPath]; | 289 return; |
| 290 |
| 291 CocoaCookieTreeNode* node = [treeNode representedObject]; |
| 292 CookieTreeNode* cookie = static_cast<CookieTreeNode*>([node treeNode]); |
| 293 treeModel_->DeleteCookieNode(cookie); |
| 294 // If there is a next cookie, this will select it because items will slide |
| 295 // up. If there is no next cookie, this is a no-op. |
| 296 [treeController_ setSelectionIndexPath:path]; |
| 297 // If the above setting of the selection was in fact a no-op, find the next |
| 298 // node to select. |
| 299 if (![[treeController_ selectedObjects] count]) { |
| 300 NSUInteger lastIndex = [path indexAtPosition:[path length] - 1]; |
| 301 if (lastIndex == 0) { |
| 302 // If this was the only child node, then perform a delete again to |
| 303 // remove the parent. When the path becomes empty, we're done. |
| 304 path = [path indexPathByRemovingLastIndex]; |
| 305 if ([path length]) |
| 306 [self deleteNodeAtIndexPath:path]; |
| 307 } else { |
| 308 // Otherwise, select the node that is in the list before this one. |
| 309 path = [path indexPathByRemovingLastIndex]; |
| 310 path = [path indexPathByAddingIndex:lastIndex - 1]; |
| 311 [treeController_ setSelectionIndexPath:path]; |
| 312 } |
290 } | 313 } |
291 } | 314 } |
292 | 315 |
293 - (IBAction)deleteAllCookies:(id)sender { | 316 - (IBAction)deleteAllCookies:(id)sender { |
294 // Preemptively delete all cookies in the Cocoa model. | 317 // Preemptively delete all cookies in the Cocoa model. |
295 modelObserver_->InvalidateCocoaModel(); | 318 modelObserver_->InvalidateCocoaModel(); |
296 treeModel_->DeleteAllStoredObjects(); | 319 treeModel_->DeleteAllStoredObjects(); |
297 } | 320 } |
298 | 321 |
299 - (IBAction)closeSheet:(id)sender { | 322 - (IBAction)closeSheet:(id)sender { |
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
427 [icons_ addObject:rb.GetNSImageNamed(IDR_BOOKMARK_BAR_FOLDER)]; | 450 [icons_ addObject:rb.GetNSImageNamed(IDR_BOOKMARK_BAR_FOLDER)]; |
428 | 451 |
429 // Create the Cocoa model. | 452 // Create the Cocoa model. |
430 CookieTreeNode* root = static_cast<CookieTreeNode*>(treeModel_->GetRoot()); | 453 CookieTreeNode* root = static_cast<CookieTreeNode*>(treeModel_->GetRoot()); |
431 scoped_nsobject<CocoaCookieTreeNode> model( | 454 scoped_nsobject<CocoaCookieTreeNode> model( |
432 [[CocoaCookieTreeNode alloc] initWithNode:root]); | 455 [[CocoaCookieTreeNode alloc] initWithNode:root]); |
433 [self setCocoaTreeModel:model.get()]; // Takes ownership. | 456 [self setCocoaTreeModel:model.get()]; // Takes ownership. |
434 } | 457 } |
435 | 458 |
436 @end | 459 @end |
OLD | NEW |