1

特別なことが起こったときに、(もしあれば)デリゲートと呼ぶべきクラスのデリゲートを実装しようとしています。

ウィキペディアから私はこのコード例を持っています:

 @implementation TCScrollView
 -(void)scrollToPoint:(NSPoint)to;
 {
   BOOL shouldScroll = YES;
   // If we have a delegate, and that delegate indeed does implement our delegate method,
   if(delegate && [delegate respondsToSelector:@selector(scrollView:shouldScrollToPoint:)])
     shouldScroll = [delegate scrollView:self shouldScrollToPoint:to]; // ask it if it's okay to scroll to this point.

   if(!shouldScroll) return;  // If not, ignore the scroll request.

   /// Scrolling code omitted.
 }
 @end

これを自分で試してみると、デリゲートで呼び出しているメソッドが見つからないという警告が表示されます。もちろんそうではありませんでした。なぜなら、デリゲートはidによって参照されているだけだからです。それは何でもかまいません。セレクターに応答するかどうかを確認するので、実行時に問題なく動作します。しかし、Xcodeでの警告は必要ありません。より良いパターンはありますか?

4

3 に答える 3

7

デリゲートを SomeClassDelegate プロトコルを実装する id タイプにすることができます。このために、SomeClass (あなたの場合は TCScrollView) のヘッダーで、次のようにすることができます。

@protocol TCScrollViewDelegate; // forward declaration of the protocol

@interface TCScrollView {
    // ...
    id <TCScrollViewDelegate> delegate;
}
@property (assign) id<TCScrollViewDelegate> delegate;
@end

@protocol TCScrollViewDelegate
- (BOOL) scrollView:(TCScrollView *)tcScrollView shouldScrollToPoint:(CGPoint)to;
@end

次に、実装から、デリゲートでメソッドを呼び出すだけです。

@implementation TCScrollView

-(void)scrollToPoint:(NSPoint)to;
{
  BOOL shouldScroll = YES;
  shouldScroll = [delegate scrollView:self shouldScrollToPoint:to]; // ask it if it's okay to scroll to this point.
  if(!shouldScroll) return;  // If not, ignore the scroll request.
  /// Scrolling code omitted.
}
@end
于 2009-08-03T16:33:02.870 に答える
0

使用する[NSObject performSelector:]

[delegate performSelector:@selector(scrollView:shouldScrollToPoint:) withObject:self withObject:to];

コンパイラの警告は表示されなくなります。

MyProtocol *delegateまたは、プロトコルを作成し、ヘッダー ファイルで宣言します。

于 2009-10-27T17:31:19.353 に答える
0

drvdijk's answerのサンプル コードをフォローアップすると、デリゲート メソッドを呼び出すときに発生するdelegate可能性がある場合、問題が発生する可能性があります。nil

に送信されたメッセージの戻り値nilnil(aka 0.0aka 0aka NO) なので、delegateisの場合nil

[delegate scrollView:self shouldScrollToPoint:to]

が返さNOれますが、これはあなたのケースでは望ましい動作ではない可能性があります。最初に確認する方が安全です。

if (delegate != nil) {
    shouldScroll = [delegate scrollView:self shouldScrollToPoint:to]
}

NSObjectまた、によって宣言されたメッセージをデリゲート ( などrespondsToSelector:)に送信するときにコンパイラの警告を表示したくない場合はNSObject、プロトコル宣言にプロトコルを含めます。

@protocol TScrollViewDelegate <NSObject>
- (BOOL) scrollView:(TCScrollView *)tcScrollView shouldScrollToPoint:(CGPoint)to;
@end
于 2009-10-27T17:23:58.513 に答える