ios - 观察 UIView 变化崩溃

标签 ios objective-c uiview objective-c-blocks

我使用下面的代码来确定何时将 View 添加到父 View :

//Makes views announce their change of superviews
Method method = class_getInstanceMethod([UIView class], @selector(willMoveToSuperview:));
IMP originalImp = method_getImplementation(method);

void (^ block)(id, UIView *) = ^(id _self, UIView *superview) {
    [_self willChangeValueForKey:@"superview"];
    originalImp(_self, @selector(willMoveToSuperview:), superview);
    [_self didChangeValueForKey:@"superview"];
};

IMP newImp = imp_implementationWithBlock((__bridge id)((__bridge void*)block));
method_setImplementation(method, newImp);

我对此没有任何问题,但是当我尝试在 64 位 中运行它时,我得到了

EXC_BAD_ACCESS (code=EXC_I386_GPFLT) on originalImp(_self, @selector(willMoveToSuperview:), superview);

谁有什么见解?

谢谢

最佳答案

似乎在 arm64 上使用 imp_implementationWithBlock 会崩溃。

您可以尝试使用经典的 swizzling(将代码放在专用的 swizzledWillMoveToSuperview: 方法中,交换两种方法/选择器的实现,然后调用 [self swizzledWillModeToSuperview:superview] swizzledWillModeToSuperview: 中实际调用原始实现)。

避免使用 imp_implementationWithBlock 并使用现有方法的实现似乎适用于 32 位和 64 位架构。

请注意,无论如何这不会涵盖所有情况,尤其是如果有人子类化 UIView 并覆盖 willMoveToSuperview 而不调用 super,那么这些实现将不会正如您所期望的那样 swizzled 并且对这些的观察将不起作用。

关于ios - 观察 UIView 变化崩溃,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22567869/

相关文章:

iphone - 尝试使用 Twitter ACAccount 时的奇怪行为

objective-c - keyDown 有效,但我听到哔哔声

ios - SpriteKit - iOS 7 - iAd 集成错误

objective-c - 在 NSString 的 isa 指针上使用 "setValue: forKey:"然后调用 [string class] 时出错

iphone - CATransaction 动画淡入淡出 uiviews

cocoa-touch - UIVIew 动画 - 缩放 + 翻译

ios - 多个位置的 Firebase updateChildValue

Ruby 对于 OS X 应用程序/iOS 应用程序开发实用吗?

ios - 实时速率和音调调整 Swift

ios - 触摸时自定义 UIView 的奇怪行为