2009-03-14 7 views
7

Tôi đang sử dụng NSArrayController, NSMutableArrayNSTableView để hiển thị danh sách các đối tượng tùy chỉnh của riêng tôi (mặc dù câu hỏi này có thể áp dụng nếu bạn chỉ hiển thị danh sách vanilla NSString đối tượng).Làm cách nào để xóa tất cả các mục khỏi NSTableView do NSArrayController kiểm soát?

Tại các thời điểm khác nhau, tôi cần phải xóa mảng của mình và làm mới dữ liệu từ nguồn dữ liệu của tôi. Tuy nhiên, chỉ cần gọi removeAllObjects trên đối tượng NSMutableArray của tôi không kích hoạt bản cập nhật KVO, vì vậy danh sách trên màn hình vẫn không thay đổi.

NSArrayControllerkhôngremoveAllObjects phương pháp có sẵn, mà dường như thực sự kỳ lạ. (Nó có addObject, mà tôi sử dụng để thêm các đối tượng, đảm bảo KVO được kích hoạt và giao diện người dùng được cập nhật.)

Cách sạch tôi đã quản lý để gây ra điều này xảy ra một cách chính xác là:

[self willChangeValueForKey:@"myArray"]; 
[myArray removeAllObjects]; 
[self didChangeValueForKey:@"myArray"]; 

... vì vậy tôi là loại phải làm các thông báo KVO bằng tay bản thân mình (đây là trong lớp ứng dụng thử nghiệm của tôi, có chứa các tài sản myArray, đó là NSMutableArray, như đã đề cập.)

Điều này có vẻ sai - có cách nào tốt hơn không? Từ googling của tôi có vẻ như một vài người đang bối rối bởi thiếu removeAllObjects trong NSArrayController, nhưng chưa thấy bất kỳ giải pháp tốt hơn.

Tôi đã thấy giải pháp này:

[self removeObjectsAtArrangedObjectIndexes: 
    [NSIndexSet indexSetWithIndexesInRange: 
    NSMakeRange(0, [[self arrangedObjects] count])]]; 

nhưng điều này có vẻ thậm chí khó chịu với tôi. Ít nhất giải pháp của tôi ít nhất là tự tài liệu.

Apple có không nhận thấy rằng đôi khi mọi người có thể muốn trống kiểm soát danh sách được quản lý thông qua đối tượng NSArrayController? Điều này có vẻ hiển nhiên, vì vậy tôi nghĩ tôi phải thiếu một cái gì đó ...

Ngoài ra, nếu tôi thêm mục mới vào mảng (qua NSArrayController), thì điều này sẽ kích hoạt bản cập nhật KVO với NSArrayController/NSTableView, nhưng :

  1. Đôi khi tôi không đặt bất kỳ mục nào trong danh sách, vì không có mục nào. Vì vậy, bạn chỉ cần xem các mục cũ.
  2. Tuy nhiên, điều này hơi khó khăn.

Trả lời

16

Bạn không xóa các mục khỏi chế độ xem bảng. Nó không có bất kỳ mục nào - nó chỉ hiển thị các mục của đối tượng khác.

Nếu bạn đã ràng buộc mảng nội dung của bộ điều khiển mảng liên kết với thuộc tính mảng của một đối tượng khác, thì bạn nên làm việc với thuộc tính đó của đối tượng đó. Sử dụng [[object mutableArrayValueForKey:@"property"] removeAllObjects].

Nếu, mặt khác, bạn không bị ràng buộc ràng buộc mảng nội dung của bộ điều khiển mảng, thì bạn cần tương tác trực tiếp với số content của nó. Sử dụng [[arrayController mutableArrayValueForKey:@"content"] removeAllObjects]. (Bạn cũng có thể làm việc với arrangedObjects thay vì content. Nếu không hoạt động, hãy thử cái kia — Tôi chỉ làm mọi thứ theo cách thứ nhất, gắn bộ điều khiển mảng vào cái gì khác.)

+0

Cảm ơn - điều đó hoạt động. Tôi đã thay đổi mã ban đầu trong câu hỏi của mình thành: [[self mutableArrayValueForKey: @ "myArray"] removeAllObjects]; và hoạt động tốt. Sạch hơn nhiều. Bạn đánh vần mutableArrayValueForKey sai btw - sửa lỗi đó và tôi sẽ đánh dấu nó là câu trả lời được chấp nhận. :-) – Slacker

+3

Phương thức của bạn hoạt động hoàn hảo khi ArrayController được gắn vào một mảng. Nhưng nó không hoạt động khi ArrayController không bị ràng buộc vào một mảng. Mảng 'content' bạn nhận được từ ArrayController là một' NSArray' không phải 'NSMutableArray'. Chỉ cần sử dụng phương thức từ ArrayController để xóa nội dung: 'NSRange range = NSMakeRange (0, [[anArrayController arrangementObjects] count]); [anArrayController removeObjectsAtArrangedObjectIndexes: [NSIndexSet indexSetWithIndexesInRange: range]];' – Quincy

+2

@Quincy '' 'NSRange'' 'giải pháp nhanh hơn đáng kể so với câu trả lời gốc hoặc' '' [anArrayController removeObjects: [anArrayController arrangementObjects]] '' '. Cảm ơn! – bdunagan

3

có vấn đề này như là tốt và giải quyết nó theo cách này:

NSArrayController* persons = /* your array controller */; 
[[persons content] removeAllObjects]; 
+1

Thật không may, điều này không hoạt động. Nếu một người gọi [who arrangementObjects], nội dung mảng vẫn có thể ở đó. Sau khi xóa tất cả các mục khỏi mảng nội dung bằng removeAllObjects, tôi thấy rằng bạn cũng cần phải gọi [persons rearrangeObjects]. – ericg

+0

chương trình của tôi bị lỗi với ... – TCB13

0

Giải pháp trong Swift:

if let ac = arrayController 
{ 
    let range:NSRange = NSMakeRange(0, ac.arrangedObjects.count); 
    let indexSet:NSIndexSet = NSIndexSet(indexesInRange: range); 
    ac.removeObjectsAtArrangedObjectIndexes(indexSet); 
} 
1

Swift

@IBOutlet var acLogs: NSArrayController! 

acLogs.removeObjects(acLogs.content as! [AnyObject]) 

làm việc cho tôi.