iOS 7.0下无效的上下文0x0和系统退化

219

我已经阅读了尽可能多关于这个可怕问题的搜索结果,不幸的是,每一个都似乎专注于特定的函数调用。

我的问题是,我从多个函数中获得相同的错误,我猜想这些函数是从我使用的函数中回调的。

更糟糕的是,实际代码位于自定义私有框架内,该框架正在导入另一个项目中,并且因此,调试并不简单?

有人能指出我正确的方向吗?我感觉我在错误地调用某些方法或上下文错误,但是xcode的输出目前并不是很有帮助。

: CGContextSetFillColorWithColor:无效的上下文0x0。这是一个严重的错误。此应用程序或其使用的库正在使用无效的上下文,从而对系统稳定性和可靠性造成了总体退化。这是一种礼貌:请解决此问题。它将在即将推出的更新中变成致命错误。

:CGContextSetStrokeColorWithColor:无效的上下文0x0。这是一个严重的错误。此应用程序或其使用的库正在使用无效的上下文,从而对系统稳定性和可靠性造成了总体退化。这是一种礼貌:请解决此问题。它将在即将推出的更新中变成致命错误。

CGContextSaveGState:无效的上下文0x0。这是一个严重的错误。此应用程序或其使用的库正在使用无效的上下文,从而对系统稳定性和可靠性造成了总体退化。这是一种礼貌:请解决此问题。它将在即将推出的更新中变成致命错误。

: CGContextSetFlatness:无效的上下文0x0。这是一个严重的错误。此应用程序或其使用的库正在使用无效的上下文,从而对系统稳定性和可靠性造成了总体退化。这是一种礼貌:请解决此问题。它将在即将推出的更新中变成致命错误。

: CGContextAddPath: 无效上下文0x0。这是一个严重的错误。该应用程序或其使用的库正在使用无效上下文,从而导致系统稳定性和可靠性的总体降级。这是一种礼貌:请解决此问题。在即将发布的更新中,它将成为致命错误。

: CGContextDrawPath: 无效上下文0x0。这是一个严重的错误。该应用程序或其使用的库正在使用无效上下文,从而导致系统稳定性和可靠性的总体降级。这是一种礼貌:请解决此问题。在即将发布的更新中,它将成为致命错误。

: CGContextRestoreGState: 无效上下文0x0。这是一个严重的错误。该应用程序或其使用的库正在使用无效上下文,从而导致系统稳定性和可靠性的总体降级。这是一种礼貌:请解决此问题。在即将发布的更新中,它将成为致命错误。

: CGContextGetBlendMode: 无效上下文0x0。这是一个严重的错误。该应用程序或其使用的库正在使用无效上下文,从而导致系统稳定性和可靠性的总体降级。这是一种礼貌:请解决此问题。在即将发布的更新中,它将成为致命错误。

当呈现自定义视图或其继承类之一时,可能会出现这些错误。在此时,它们会多次生成,直到键盘不再提供任何输入。触摸事件仍然被注册,但系统会变慢,并最终可能导致未分配对象错误。

编辑#1:我可以访问被导入的框架,但是我在引起问题的类中没有看到任何奇怪的东西。

编辑#2:我刚刚收到一封电子邮件,称iOS 7.1已经发布给开发人员。我很想知道这个问题是否会消失,变得更糟还是可以解决。


8
我们的应用程序也出现了相同的错误 - 来自表单中的标准文本框。 如果您在键盘显示时多次轻击文本框,则会出现此错误。 - user3083658
同样的问题。有时候会出现数百个这样的日志,有时则没有。我以为是因为我重写了drawRect:方法,但似乎不是这个原因。暂时先忽略它。 - Krumelur
2
我刚刚完成了developer.apple.com上的第一个教程(复制了Apple建议的代码),但我遇到了同样的错误。也许如果更有经验的程序员看一下这个教程,他们就能找出这个问题的原因。 - Antonio Sesto
1
在使用自定义UI元素的视图中,请关闭自动布局。 - JuJoDi
1
仍然会发生在2016年(XCode 7,iOS 9.2),但似乎没有造成明显的损害。 - Hatchmaster J
26个回答

200

2
谢谢你提供关于CGPostError的提示。我在它上面设置了断点,看起来似乎没有任何问题导致这个错误。在我的情况下,它发生在主线程上,但不是由我的代码引起的。 - Paul Heller
10
投票支持这个观点,因为虽然它不是在这种特定情况下的解决方案,但它通常会凸显出故障所在,尤其是当问题出现在程序员自己的代码范围内时。 - Ash
28
这是一个很好的建议。对于那些不熟悉符号断点或如何在Xcode中添加它们的人来说,这里是苹果公司的文档。https://developer.apple.com/library/ios/recipes/xcode_help-breakpoint_navigator/articles/adding_a_symbolic_breakpoint.html - Tony Adams
这对我很有帮助。在我的情况下,它突出显示了我在我的 OS X 应用程序中向视图添加 NSGradient。 - Aaron Vegh
1
看起来我在为某个视图设置框架之前进行了绘制,谢谢! :) - Rick van der Linde
显示剩余3条评论

162

其他人可能会要求你发布访问核心图形上下文的代码,但我怀疑那不是问题所在。这些无效的上下文0x0错误消息在iOS 7中很常见且易于复现。实际上,我可以使用零代码在storyboard中重现此错误。我将UITextField拖到IB中的画布上,运行应用程序,然后双击文本字段内部。

在许多情况下,我很难认真对待无效上下文0x0错误消息。我不知道你的情况是否需要更多关注(我同意Rob Napier的看法,值得调查,特别是如果你明确使用图形上下文)。

在我的项目中,我希望许多这些错误有一天会神奇地消失(但那一天没有在7.0.3到来)。

更新:安装Xcode 5.1并针对iOS 7.1,我再也不能通过双击空文本字段内部来重现该错误。


10
关于iOS 7的UITextField bug,你说得完全正确。一定要提交一个radar(bugreport.apple.com)。但不要过快地认为这就是问题所在。由于这是一个自定义视图,值得先研究@Rob提出的观点。 - Rob Napier
2
这种情况也发生在我身上了。我在IB上放置了一个UITextfield,出现了这个错误,但键盘并没有弹出来。有什么解决办法吗?谢谢。 - Frade
@Frade 对我来说,尽管有严厉的错误消息,键盘仍然可以正常显示,并且应用程序也可以正常运行。所以你可能还有其他问题。 - bilobatum
3
我也遇到了同样的问题,这个问题只在模拟器中出现。当我遇到这个 bug 时,我发现无法使用 Mac 键盘在模拟器中输入,必须使用屏幕键盘,这非常令人沮丧。在我的应用中,我没有使用任何自定义视图,因此我从未手动创建或使用 CG 上下文。 - user522860
1
谢天谢地,我还以为是我的应用程序出了问题! 你完全正确;对我来说,双击文本字段也导致了这个错误。 - Ash
显示剩余2条评论

42

这些错误通常是因为在未建立上下文的情况下调用核心图形函数,比如在不在 drawRect 中或在类似于 UIGraphicsBeginImageContextUIGraphicsEndImageContext (或其他开始和结束上下文的 UIKit 函数) 的调用之间。

话虽如此,bilobatum 正确指出,在他的答案中提到的那个 iOS 7 bug 可能导致这些特定的错误序列。如果您的 iOS6 目标没有看到这些错误,或者在快速扫描这个私有框架后没有发现任何可疑的核心图形调用,那么可能只是这个 iOS 7 bug。好发现,bilobatum!


我在私有框架中有一个视图调用了drawRect方法。虽然我没有直接调用任何提到的方法,但我的唯一假设是该类中的代码与此相关。然而,正如我所提到的,在之前的iOS版本下一切都运行顺利。 - Ælex
为了完整起见(这是谷歌的首要搜索结果),我想指出,在OSX 10.11.3上,晦涩的错误信息没有改变 - 正如Rob所说,这是由于将绘图函数放在drawRect或另一个上下文相关函数之外所造成的。 - green_knight

26
UIGraphicsBeginImageContext( size );
CGContextRef context = UIGraphicsGetCurrentContext();

确保size.width或size.height不为0,

你可以添加符号断点到CGPostError进行检查。


那么,在CGPostError处添加一个符号断点,如何查看该点的大小? - Cris
您可以通过按下 command+6 打开“显示调试导航”来查看函数调用堆栈。然后,您可以点击树形结构,回到您的函数并查看变量。 - lbsweek
是的,我在传递ImageView以使其成为圆形,但是发现它的大小为零。最终在两天后解决了:D。 - JiteshW

19

我曾经遇到一个简单的UITextField问题(无法弹出键盘,并且控制台上出现了许多不同的无效上下文错误消息)。

我通过查看SO上的另一个问题找到了一种解决方法:无法找到CFBundle CertUIFramework.axbundle的可执行文件

只需要:

点击iOS模拟器 > 重置内容和设置...,然后再次运行。

问题就不应该再存在了。


16

在我的情况下,我在这段代码中遇到了以下错误:

CAShapeLayer *shapeLayer = [CAShapeLayer layer];
UIBezierPath *path;

path = [UIBezierPath bezierPath];
[path moveToPoint:CGPointMake(0, 0)];
[path addLineToPoint:CGPointMake(size*2, 0)];
[path addLineToPoint:CGPointMake(size, size*2)];
[path closePath];
[path fill];

shapeLayer.path = path.CGPath;
shapeLayer.strokeColor = [[UIColor blackColor] CGColor];
shapeLayer.fillColor = color;
shapeLayer.lineWidth = width;

[self addSublayer:shapeLayer];

经过一些思考和测试,我发现问题所在 - 是这个调用:

[path fill];

我在代码中发现这个调用是不必要的,因为填充会通过其他方式完成,所以我只需将其删除。


5

我遇到了同样的问题,我忘记导入QuartzCore/QuartzCore.h。这个方法解决了我的错误。

    #import <QuartzCore/QuartzCore.h>

5

简明回答: 问题是因为您在非- (void)drawRect:(CGRect)rect方法中使用了核心绘图元素,如CGContext等。

现在请把您的代码移动到这个方法中。这样它就不会再给您警告/错误了。


4

我之前遇到这个错误是因为在一个NSAttributedString字典中,我使用了一个UIColor对象作为属性,并将其用于CATextLayer对象中。我将字典更改为保存一个CGColorRef对象,问题就解决了。

[wordAttributes setObject:(id)[UIColor whiteColor].CGColor forKey:(NSString*)kCTForegroundColorAttributeName];

2
在我的案例中,当使用cap insets创建可缩放图像时,出现了警告。问题在于我没有在“无法缩放”的区域留下至少1个像素。
    UIImage *image = [UIImage imageNamed:@"name"];
    UIEdgeInsets edgeInsets = UIEdgeInsetsMake(20, 10, 20, 10);  //Problem here if the width is 20 or the height is 40
    image = [image resizableImageWithCapInsets:edgeInsets];

1
遇到了完全相同的问题。显然,您必须留下至少1个区域点,以便图像可以拉伸。 - ribeto

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接