Objective c setNeedsLayout是如何工作的?

Objective c setNeedsLayout是如何工作的?,objective-c,delay,setter,nsrunloop,delayed-execution,Objective C,Delay,Setter,Nsrunloop,Delayed Execution,我想知道苹果的-setNeedsLayout是如何工作的 我已经知道它比直接调用-layoutSubviews更有效,因为我可能需要在一个方法中执行两次。 这正是我需要它的目的:为视图控制器进行一些自定义-setneedsvalization。 但是如何实现这样一个功能呢?只要大声想一想。。。文档说明,-setNeedsLayout计划在下一个“更新周期”(或“图形更新”,如-layoutSubviews文档中所述)中进行布局更新 因此-setNeedsLayout很可能设置了BOOL标志。稍后

我想知道苹果的
-setNeedsLayout
是如何工作的

我已经知道它比直接调用
-layoutSubviews
更有效,因为我可能需要在一个方法中执行两次。
这正是我需要它的目的:为视图控制器进行一些自定义
-setneedsvalization


但是如何实现这样一个功能呢?

只要大声想一想。。。文档说明,
-setNeedsLayout
计划在下一个“更新周期”(或“图形更新”,如
-layoutSubviews
文档中所述)中进行布局更新


因此
-setNeedsLayout
很可能设置了
BOOL
标志。稍后将检查该标志(在
-drawRect:
?)中),如果将其设置为
YES
,则调用
-layoutSubviews
。然后清除标志并等待下一次调用
-setNeedsLayout

我无法确认苹果是否确实是这样做的,但这里有一种方法可以实现您想要的,并且可能类似于
setNeedsLayout
的实现方式。我还没有对此进行测试(甚至没有对其进行编译),但它应该能够提供如何在
UIViewController
中将问题作为一个类别进行攻击的想法。与UIKit一样,这是完全不安全的线程

static NSMutableSet sViewControllersNeedingValidation = nil;
static BOOL sWillValidate = NO;

@implementation UIViewController (Validation)
+ (void)load {
  sViewControllersNeedingValidation = [[NSMutableSet alloc] init];
}

- (void)setNeedsValidation {
  [sViewControllersNeedingValidation addObject:self];

  if (! sWillValidate) {
    sWillValidate = YES;
    // Schedule for the next event loop
    [[self class] performSelector:@selector(dispatchValidation) withObject:nil afterDelay:0];
  }
}

+ (void)dispatchValidation {
  sWillValidate = NO;
  // The copy here is in case any of the validations call setNeedsValidation.
  NSSet *controllers = [sViewControllersNeedingValidation copy];
  [sViewControllersNeedingValidation removeAllObjects];
  [controllers makeObjectsPerformSelector:@selector(validate)];
  [controllers release];
}

- (void)validate {
  // Empty default implementation
}

我就是这么想的。那么,如何创建一个在主运行循环的下一次迭代中执行的方法呢?
-performSelector:withObject:afterDelay:
使用零延迟将选择器执行调度到运行循环。好的,这是显而易见的。很抱歉