NSCollectionViewのビューサブクラスでプログラムでバインドするにはどうすればよいですか?

StackOverflow https://stackoverflow.com/questions/1210352

質問

NSCollectionViewを正常に作成し、IBのビュープロトタイプにラベルを追加しました。これは、表示されるオブジェクトのプロパティにバインドされています。 NSTextFieldを、表現されたオブジェクトのプロパティにバインドして、プログラムでNSButtonとNSTextFieldを作成します。ボタンがクリックされたとき、NSTextFieldを表示および非表示にします。

私が遭遇した問題は、コントロールの初期化コードをビューのinitWithCoderメソッドに入れ、ビューのawakeFromNibのバインディングを入れた場合、バインディングがフックされないことです。コントロールの初期化をawakeFromNibに配置すると、ボタンがクリックされたときに、ビュー内のコントロールにアクセスできません(NSLogを使用して印刷すると、nullになります)。

私が知ることができるのは、NSCollectionViewの動作方法がビューのインスタンスを作成し、それからコレクションビューにあるすべてのオブジェクトの数に応じてコピーすることである可能性があります。初期化するボタンとプロトタイプのコピーで動作するバインディングを取得するにはどうすればよいですか?

サブクラス化されたビューの初期化コードとawakeFromNibのバインディングは次のとおりです。

SubView.h

@interface SubView : NSView {
    NSButton *button;
    NSTextField *textField;
    IBOutlet NSCollectionViewItem *item; // Connected in IB to my NSCollectionViewItem
}

- (IBAction)buttonClicked:(id)sender;

@end

SubView.m

@implementation SubView

- (id)initWithCoder:(NSCoder *)decoder
{
    id view = [super initWithCoder:decoder];

    button = [[NSButton alloc] initWithFrame:NSMakeRect(50, 95, 100, 20)];
    [button setTitle:@"Begin Editing"];
    [button setTarget:self];
    [button setAction:@selector(buttonClicked:)];
    [self addSubview:button];

    textField = [[NSTextField alloc] initWithFrame:NSMakeRect(10, 10, 100, 75)];
    [self addSubview:textField];

    return(view);
}

- (void)awakeFromNib
{   
        // Bind the textField to the representedObject's name property
        [textField bind:@"value" 
       toObject:item 
        withKeyPath:@"representedObject.name" 
        options:nil];
}

- (IBAction)buttonClicked:(id)sender
{
    [button setTitle:@"End Editing"];
    [textField setHidden:YES];
}

@end
役に立ちましたか?

解決

これは私がやったことと似ているように聞こえるので、おそらくあなたが必要としているものです。

サブクラス NSCollectionView およびオーバーライド:

- (NSCollectionViewItem *)newItemForRepresentedObject:(id)object

newItemForRepresentedObject:で、ビューアイテムを取得し、コントロールとプログラムバインディングを追加します。

@implementation NSCollectionViewSubclass

- (NSCollectionViewItem *)newItemForRepresentedObject:(id)object {

    // Allow the superclass to create or copy the collection view item
    NSSCollectionViewItem *newItem = [super newItemForRepresentedObject:object];

    // Get the new item's view so you can mess with it
    NSView *itemView = [newItem view];

    //
    // add your controls to the view here, bind, etc
    //

    return newItem;
}

@end

うまくいけば、これはあなたがいる必要がある場所に近いところです...

他のヒント

NSCollectionViewと同じnibにある場合、NSCollectionViewItemのビューでは

-awakeFromNib は呼び出されませんが、ビューを別のnibに入れると呼び出されます。

  • 空のnibファイル(BlahBlahCollectionViewItem.nib)を作成します。
  • 持っているペン先からコレクションアイテムビューを切り取ります
  • 新しいnibファイルに貼り付けます
  • 所有者のクラスをNSCollectionViewItemに変更します。
  • 所有者のビューアウトレットを新しく貼り付けられたビューに接続します
  • NSViewControllerを含むnibファイルを開きます
  • 関連するNSViewControllerItemを選択
  • 「ペン先名」プロパティを新しいペン先の名前に変更します
  • コードを -awakeFromNib
  • に保存します

-awakeFromNib は、プロトタイプNSCollectionViewItemからコピーされたビューでは呼び出されません。バインディングコードを initWithCoder:に入れると、問題ありません。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top