2011-08-31 36 views
5

Tôi có một câu hỏi hóc búa đang thúc đẩy tôi lên tường. Tôi đang sử dụng đoàn đại biểu khá nhiều như là một mô hình trong một ứng dụng tôi đang viết. Tôi đang cố gắng để được như "cẩn thận" trong mã gọi các đại biểu như tôi có thể bằng cách kiểm tra các đại biểu với "[delegate respondsToSelector]" trên mỗi cuộc gọi được ủy quyền. Tất cả mọi thứ hoạt động tốt trừ khi tôi đang ở trong một lớp con UIView. Trong trường hợp đó, responsesToSelector trả về NO nhưng tôi có thể gọi một cách an toàn mã đại biểu để rõ ràng nó tồn tại và hoạt động chính xác.Tại sao respondsToSelector không hoạt động đối với tôi trong trường hợp này?

Tôi đã đun sôi nó xuống ví dụ đơn giản nhất tôi có thể bên dưới. Bất kỳ giúp bạn có thể cung cấp sẽ được đánh giá:

Bên trong tập tin .h phân lớp UIView của tôi:

#import <UIKit/UIKit.h> 

@protocol TestDelegate <NSObject> 
@optional 
-(double)GetLineWidth; 
@end 

@interface ViewSubclass : UIView { 
    id<TestDelegate> delegate; 
} 

@property (nonatomic, retain) id<TestDelegate> delegate; 

@end 

Bên trong tập tin .h lớp đại biểu của tôi:

#import <Foundation/Foundation.h> 
#import "ViewSubclass.h" 

@interface ViewDelegate : NSObject <TestDelegate> { 

} 

@end 

Bên .m lớp đại biểu của tôi file:

#import "ViewDelegate.h" 

@implementation ViewDelegate 

-(double)GetLineWidth { 
    return 25.0; 
} 

@end 

Bên trong tập tin .m của lớp con UIView:

- (void)drawRect:(CGRect)rect 
{ 
    CGContextRef context = UIGraphicsGetCurrentContext(); 

    double lineWidth = 2.0; 

    if (delegate == nil) { 
     ViewDelegate *vd = [[ViewDelegate alloc]init]; 
     delegate = vd; 
    } 

    // If I comment out the "if" statement and just call the delegate 
    // delegate directly, the call works! 
    if ([delegate respondsToSelector:@selector(GetLineWidth:)]) { 
     lineWidth = [delegate GetLineWidth]; 
    } 

    CGContextSetLineWidth(context, lineWidth); 
+0

Thông thường bạn sẽ không muốn giữ lại các đại biểu '@property (nonatomic, chuyển nhượng) id đại biểu; ' – slf

+1

gì Rob Said ; phương thức đó nên được gọi là 'lineWidth'. Các phương thức không bao giờ nên bắt đầu bằng chữ in hoa và chỉ nên bắt đầu bằng 'get' trong những trường hợp rất hiếm. Đây không phải là một lựa chọn phong cách, đây là một mẫu mà bạn phải tuân theo để tất cả các tính năng của khung làm việc chính xác. – bbum

Trả lời

14

bộ chọn cho -(double)GetLineWidth@selector(GetLineWidth).

bạn có dấu hai chấm phụ trong bộ chọn của mình.

if ([delegate respondsToSelector:@selector(GetLineWidth:)]) { 
                ^
+0

Ok, trước tiên bạn là =) – Nekto

+5

Và đổi tên 'GetLineWidth' thành' lineWidth'. Không truy cập tùy chọn có "Nhận" và không bắt đầu với giới hạn hàng đầu. Nó quan trọng trong Cocoa, nó không chỉ là một sự lựa chọn phong cách. –

+0

Doh! Cảm ơn mọi người! – user704315

3

Thay if-tuyên bố với một này:

if ([delegate respondsToSelector:@selector(GetLineWidth)]) { 
    lineWidth = [delegate GetLineWidth]; 
} 
Các vấn đề liên quan