将变量添加到块
Adding a variable to a block
我正在使用 UIAlertView
+ 块类别 found here。
我无法理解他是如何创建块的:
typedef void (^DismissBlock)(int buttonIndex);
我明白这一点,用它来创建我自己的块。所以我创建了我的:
typedef void (^DismissBlockWithView)(UIAlertView *alertview, int buttonIndex);
我想我明白 setter 方法发生了什么:
- (void)setDismissBlock:(DismissBlock)dismissBlock
{
objc_setAssociatedObject(self, &DISMISS_IDENTIFER, dismissBlock, OBJC_ASSOCIATION_COPY_NONATOMIC);
}
据我了解,这是设置变量的较低级别的方法。我不确定应该在何处、何时或为何使用它。如果我弄错了,请纠正我。它正在将 DIMISS_IDENTIFER
的引用值设置为 dismissBlock
对象。
所以对于我的街区:
-(void)setDismissBlockWithView:(DismissBlockWithView)dismissBlockWithView {
objc_setAssociatedObject(self, &ALERT_VIEW, dismissBlockWithView, OBJC_ASSOCIATION_COPY_NONATOMIC);
objc_setAssociatedObject(self, &DISMISS_IDENTIFER, dismissBlockWithView, OBJC_ASSOCIATION_COPY_NONATOMIC);
}
我设置了每个变量。
现在我难以理解的部分是 getter 方法:
- (DismissBlock)dismissBlock
{
return objc_getAssociatedObject(self, &DISMISS_IDENTIFER);
}
所以 objc_getAssociatedObject()
接受 id object
和 const void *key
变量。以这种方式创建块时,您只能有一个变量吗?我知道我不知道这一切背后的基本逻辑,只是有点想用常识逻辑把它们放在一起。
我需要做些什么来更改它以便我可以返回 UIAlertView
和 buttonIndex?
我想要返回 UIAlertView
,因为我正在通过它接收用户输入(使用 UIAlertViewStylePlainTextInput
样式选项)并且文本存储在警报视图中。
objective-c 关联引用方法是运行时 API 的一部分,它允许您在运行时 "attach" 对象到其他对象。在您的情况下,您将块与警报视图相关联,允许您在必要时访问这些块(例如,当警报被解除时)。
代码中的 DIMISS_IDENTIFER
只是关联键,稍后您可以使用它来检索关联的对象 - 块。将其视为存储关联对象并用于标识它的字典的键。
您可以为每个键关联一个对象。在方法 setDismissBlockWithView
中,您将同一块与警报视图相关联但使用不同的键,我认为这没有多大用处。您创建的新区块签名就可以了,您可以在执行区块时通过警报视图。例如,我修改了 UIAlertView+MKBlockAdditions 中的一种方法,以使用您的签名调用 dismissBlock
,同时将警报视图和索引传递给块:
+ (void)alertView:(UIAlertView*) alertView didDismissWithButtonIndex:(NSInteger) buttonIndex {
if(buttonIndex != [alertView cancelButtonIndex]){
if (alertView.dismissBlock) {
alertView.dismissBlock(alertView, buttonIndex - 1);
}
}
}
您可以将关联对象视为在对象上设置 属性 的低级方法。确切地说,不是这样,但它已经足够接近讨论的目的了。查看 this NSHipster piece 以获取有关关联对象的信息。
I'm not sure where, when, or why it should be used.
答案是,几乎从来没有。严重地。如果您发现自己在输入 "objc_",您应该就此停下来,问问自己您要做什么,因为可能有更好的方法。 Objective-C Runtime 很棒,很强大,但也很糟糕,不容小觑。再看上面的NSHipsterlink
关联对象的一个用例是通过 class 类别或扩展将实例变量或属性添加到 class,这在几年前是 not possible, and that's exactly what UIAlertView+MKBlockAdditions.m
is using them for. It's not how I'd have done it; I'd have subclassed UIAlertView
, and added regular @property
s to achieve that functionality. In fact, I did that。 :)
但是,我认为我们可能会在这里杂草丛生。关于块和关联对象的所有这些讨论,您真的只是想从具有文本字段的 UIAlertView 中获取一些文本吗?
如果是这样,您将使用 alertViewWithTitle:message:cancelButtonTitle:otherButtonTitles:onDismiss:onCancel:
创建警报。您将块作为 onDismiss:
参数传递,您可以使用 textFieldAtIndex:
获取文本字段。它应该看起来像这样:
__block UIAlertView* alert = [UIAlertView alertViewWithTitle:@"Hi!"
message:@"What's your name?"
cancelButtonTitle:@"Cancel"
otherButtonTitles:@[@"OK"]
onDismiss:^(int buttonIndex)
{
UITextField* nameField = [alert textFieldAtIndex:0];
NSLog( @"Hello, %@", nameField.text );
}
onCancel:nil];
alert.alertViewStyle = UIAlertViewStylePlainTextInput;
[alert show];
我正在使用 UIAlertView
+ 块类别 found here。
我无法理解他是如何创建块的:
typedef void (^DismissBlock)(int buttonIndex);
我明白这一点,用它来创建我自己的块。所以我创建了我的:
typedef void (^DismissBlockWithView)(UIAlertView *alertview, int buttonIndex);
我想我明白 setter 方法发生了什么:
- (void)setDismissBlock:(DismissBlock)dismissBlock
{
objc_setAssociatedObject(self, &DISMISS_IDENTIFER, dismissBlock, OBJC_ASSOCIATION_COPY_NONATOMIC);
}
据我了解,这是设置变量的较低级别的方法。我不确定应该在何处、何时或为何使用它。如果我弄错了,请纠正我。它正在将 DIMISS_IDENTIFER
的引用值设置为 dismissBlock
对象。
所以对于我的街区:
-(void)setDismissBlockWithView:(DismissBlockWithView)dismissBlockWithView {
objc_setAssociatedObject(self, &ALERT_VIEW, dismissBlockWithView, OBJC_ASSOCIATION_COPY_NONATOMIC);
objc_setAssociatedObject(self, &DISMISS_IDENTIFER, dismissBlockWithView, OBJC_ASSOCIATION_COPY_NONATOMIC);
}
我设置了每个变量。
现在我难以理解的部分是 getter 方法:
- (DismissBlock)dismissBlock
{
return objc_getAssociatedObject(self, &DISMISS_IDENTIFER);
}
所以 objc_getAssociatedObject()
接受 id object
和 const void *key
变量。以这种方式创建块时,您只能有一个变量吗?我知道我不知道这一切背后的基本逻辑,只是有点想用常识逻辑把它们放在一起。
我需要做些什么来更改它以便我可以返回 UIAlertView
和 buttonIndex?
我想要返回 UIAlertView
,因为我正在通过它接收用户输入(使用 UIAlertViewStylePlainTextInput
样式选项)并且文本存储在警报视图中。
objective-c 关联引用方法是运行时 API 的一部分,它允许您在运行时 "attach" 对象到其他对象。在您的情况下,您将块与警报视图相关联,允许您在必要时访问这些块(例如,当警报被解除时)。
代码中的 DIMISS_IDENTIFER
只是关联键,稍后您可以使用它来检索关联的对象 - 块。将其视为存储关联对象并用于标识它的字典的键。
您可以为每个键关联一个对象。在方法 setDismissBlockWithView
中,您将同一块与警报视图相关联但使用不同的键,我认为这没有多大用处。您创建的新区块签名就可以了,您可以在执行区块时通过警报视图。例如,我修改了 UIAlertView+MKBlockAdditions 中的一种方法,以使用您的签名调用 dismissBlock
,同时将警报视图和索引传递给块:
+ (void)alertView:(UIAlertView*) alertView didDismissWithButtonIndex:(NSInteger) buttonIndex {
if(buttonIndex != [alertView cancelButtonIndex]){
if (alertView.dismissBlock) {
alertView.dismissBlock(alertView, buttonIndex - 1);
}
}
}
您可以将关联对象视为在对象上设置 属性 的低级方法。确切地说,不是这样,但它已经足够接近讨论的目的了。查看 this NSHipster piece 以获取有关关联对象的信息。
I'm not sure where, when, or why it should be used.
答案是,几乎从来没有。严重地。如果您发现自己在输入 "objc_",您应该就此停下来,问问自己您要做什么,因为可能有更好的方法。 Objective-C Runtime 很棒,很强大,但也很糟糕,不容小觑。再看上面的NSHipsterlink
关联对象的一个用例是通过 class 类别或扩展将实例变量或属性添加到 class,这在几年前是 not possible, and that's exactly what UIAlertView+MKBlockAdditions.m
is using them for. It's not how I'd have done it; I'd have subclassed UIAlertView
, and added regular @property
s to achieve that functionality. In fact, I did that。 :)
但是,我认为我们可能会在这里杂草丛生。关于块和关联对象的所有这些讨论,您真的只是想从具有文本字段的 UIAlertView 中获取一些文本吗?
如果是这样,您将使用 alertViewWithTitle:message:cancelButtonTitle:otherButtonTitles:onDismiss:onCancel:
创建警报。您将块作为 onDismiss:
参数传递,您可以使用 textFieldAtIndex:
获取文本字段。它应该看起来像这样:
__block UIAlertView* alert = [UIAlertView alertViewWithTitle:@"Hi!"
message:@"What's your name?"
cancelButtonTitle:@"Cancel"
otherButtonTitles:@[@"OK"]
onDismiss:^(int buttonIndex)
{
UITextField* nameField = [alert textFieldAtIndex:0];
NSLog( @"Hello, %@", nameField.text );
}
onCancel:nil];
alert.alertViewStyle = UIAlertViewStylePlainTextInput;
[alert show];