【问题标题】:How does snapshotting interfere with parent/child relationships?快照如何干扰父/子关系?
【发布时间】:2015-08-12 09:48:15
【问题描述】:

总结

  1. childVC 添加到parentVC
  2. 快照childVC.view
  3. 它出错了。

为什么?

情况

我刚刚遇到了一个奇怪的行为,我想知道它是正常的还是错误的。

我有一个视图控制器childVC,它是parentVC 的子级。创建父/子关系时,我的代码是

    [parentVC addChildViewController:childVC] ;
    [parentVC.view addSubview:childVC.view] ;
    [childVC didMoveToParentViewController: parentVC] ;

几行进一步,我想创建childVC.view 的快照。我的代码是

UIView * view = childVC.view ;

UIGraphicsBeginImageContextWithOptions(view.contentSize, NO, 0);
{
    [...]

    [view drawViewHierarchyInRect:view.bounds
               afterScreenUpdates:YES];

    image = UIGraphicsGetImageFromCurrentImageContext();

    [...]
}
UIGraphicsEndImageContext();

错误

然后我有错误:

* 由于未捕获的异常“UIViewControllerHierarchyInconsistency”而终止应用程序,原因:“子视图” 控制器:应该有父级 视图控制器:(null)但实际父级是:' * 第一次抛出调用堆栈:( 0 CoreFoundation 0x0260b466 __exceptionPreprocess + 182 1 libobjc.A.dylib
0x02290a97 objc_exception_throw + 44 2 核心基础
0x0260b38d +[NSException raise:format:] + 141 3 UIKit
0x01136710 -[UIView(层次结构) _associatedViewControllerForwardsAppearanceCallbacks:performHierarchyCheck:isRoot:] + 352 4 UIKit 0x01136b13 -[UIView(Hierarchy) _willMoveToWindow:withAncestorView:] + 285 5 UIKit 0x0114330a -[UIView(内部) _addSubview:positioned:relativeTo:] + 511 6 UIKit 0x01136252 -[UIView(Hierarchy) addSubview:] + 56 7 UIKit
0x0114ab0e +[_UIReplicantView _pendingSnapshotOfTarget:snapshotBlock:] + 584 8 UIKit 0x011312fe -[UIView drawViewHierarchyInRect:afterScreenUpdates:] + 287

问题

为什么会这样?我可以解决这个问题吗?

更多详情

其实childVC.viewUIScrollView,截图的代码是

UIScrollView * scrollView = (UIScrollView *)childVC.view;

UIGraphicsBeginImageContextWithOptions(scrollView.contentSize, NO, 0);
{
    CGPoint savedContentOffset = scrollView.contentOffset;
    CGRect savedFrame = scrollView.frame;

    scrollView.contentOffset = CGPointZero;
    scrollView.frame = CGRectMake(0,
                            0,
                            scrollView.contentSize.width,
                            scrollView.contentSize.height);

    [scrollView drawViewHierarchyInRect:scrollView.bounds
               afterScreenUpdates:YES];

    image = UIGraphicsGetImageFromCurrentImageContext();

    scrollView.contentOffset = savedContentOffset;
    scrollView.frame = savedFrame;
}
UIGraphicsEndImageContext();

也许这会带来很大的不同。

【问题讨论】:

  • 已经 3 岁了,但今天在 Swift 4 中发生在我身上。从那以后你的问题解决了吗?
  • 不,抱歉。祝你好运。
  • 这是最奇怪的错误!它对我来说只工作一次,并在随后的快照中崩溃
  • 我遇到了完全相同的崩溃,但情况不同。当您对没有窗口的视图进行快照时会发生这种情况(例如view.window == nil
  • 我也遇到过这个问题。我的解决方案是从父级快照中删除子级,然后将其添加回父级。我猜孩子 viewController 就像我的孩子 - 请不要快照!

标签: ios objective-c uiviewcontroller parent-child snapshot


【解决方案1】:

我今天在使用 UIViewControllerAnimatedTransitioning 实现自定义转换时遇到了同样的问题。问题是,当我尝试对子视图控制器进行快照时,它的父视图还不是视图层次结构的一部分。

解决方案是确保在您尝试对子视图进行快照之前,已将父视图添加到视图层次结构中。就我而言,我只需要先将“to”视图控制器添加到transitionContext.containerView

根据您的代码 sn-p,我无法判断您何时尝试拍摄快照。但是如果在viewDidAppear()之前,可能就不行了。

【讨论】:

  • 你救了我的命!在自定义转换中也有问题,我只是没有收到任何错误消息或崩溃,只是布局混乱。添加到容器首先解决了它。非常感谢!
【解决方案2】:

我在使用view.snapshotView(afterScreenUpdates: true) 捕获子视图控制器的视图然后从父视图中删除它时遇到了这个崩溃。

对我来说,将false 传递给afterScreenUpdates 解决了这个问题。

【讨论】:

    【解决方案3】:

    也许您的父视图控制器正在被释放,因此异常消息中的(null)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-10-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-12-15
      相关资源
      最近更新 更多