Xcode6,iOS8和(void)layoutSubviews

Mar*_*ria 7 uilabel layoutsubviews autolayout xcode6 ios8

我有自定义的UILabel,可以在iOS6和iOS7上正常使用.但是在iOS8上,这个标签的(void)layoutSubviews方法永远不会被调用.我用initWithFrame创建了这个标签,所以应该调用这个方法 - 并在另一个iOS版本上调用它.iOS8中的autoLayout系统会发生什么?

Nik*_*kyD 5

我只想添加这个答案,因为问题标题可能会导致很多人在这里遇到类似问题(比如我).

iOS 8到8.0.2的LayoutSubviews调用是不可靠的.它们可能永远不会被调用,或者(在我的情况下)被循环调用.

虽然你不应该这样做,但是在LayoutSubviews中分配东西是相当安全的,但是有了这个错误(?!)行为,它可能导致难以追踪的错误.

我不知道8.1是否修复了所有问题,但是一段时间后客户设备将运行8.1并且它们现在运行8.0.2


Igo*_*uta 4

我有同样的问题。实际上,iOS8 上的 UILabel 不再调用layoutSubviews,因为 Apple 不希望任何人使用它作为超级视图。

我正在使用ReactiveCocoaLayout,因此可以通过订阅 rcl_frameSignal 或 rcl_boundsSignal 来完成。

-(void)awakeFromNib { [ self.rcl_boundsSignal subscribeNext: ^( NSValue* boundsValue ) { //layout changed } ]; }

或者您可以使用简单的 KVO 来了解框架何时更改:

-(void)dealloc
{
   [ self removeObserver: self forKeyPath: @"layer.bounds" ];
}

-(void)observeValueForKeyPath:( NSString* )keyPath
                     ofObject:( id )object
                       change:( NSDictionary* )change
                      context:( void* )context
{
   if ( [ keyPath isEqualToString: @"layer.bounds" ] )
   {
      //layoutSubviews
   }
   else
   {
      [ super observeValueForKeyPath: keyPath
                      ofObject: object
                        change: change
                       context: context ];
   }
}

-(void)awakeFromNib
{
   [ self addObserver: self
           forKeyPath: @"layer.bounds"
              options: NSKeyValueObservingOptionNew
              context: 0 ];
}
Run Code Online (Sandbox Code Playgroud)