我正试图找到一种在视图上绘制线条的方法,而无需重新绘制所有上下文。
这是我的绘图方法:
-(void)drawInContext:(CGContextRef)context {
for (int i = 0; i < self.drawings.count; ++i) {
Drawing* drawing = [self.drawings objectAtIndex:i];
CGContextSetStrokeColorWithColor(context, drawing.colorTrait.CGColor);
CGContextSetLineWidth(context, 1.0);
CGContextMoveToPoint(context, [[drawing.points objectAtIndex:0] CGPointValue].x * self.zoomScale, [[drawing.points objectAtIndex:] CGPointValue].y * self.zoomScale);
for (int i = 1; i < drawing.points.count; i++) {
CGContextAddLineToPoint(context, [[drawing.points objectAtIndex:i] CGPointValue].x * self.zoomScale, [[drawing.points objectAtIndex:i] CGPointValue].y * self.zoomScale);
}
CGContextStrokePath(context);
}
}
-(void)drawRect:(CGRect)rect {
if (isRedrawing) {
[self drawInContext:UIGraphicsGetCurrentContext()];
isRedrawing = NO;
}
[[UIColor redColor] set];
[currentPath stroke];
}
但是当我在触摸方法中调用setNeedsDisplay时,视图完全被清除。 有没有办法让我的方法有效?
答案 0 :(得分:3)
无论好坏,我都使用图层:
- (void)drawRect:(CGRect)rect {
CGContextRef context = UIGraphicsGetCurrentContext();
if (first) {
// Wait for the first call to get a valid context
first = NO;
// Then create a CGContextRef (offlineContext_1) and matching CGLayer (layer_1)
layer_1 = CGLayerCreateWithContext (context,self.bounds.size, NULL);
offlineContext_1 = CGLayerGetContext (layer_1);
// If you have any pending graphics to draw, draw them now on offlineContext_1
}
// Normally graphics calls are made here, but the use of an "offline" context means the graphics calls can be made any time.
CGContextSaveGState(context);
// Write whatever is in offlineContext_1 to the UIView's context
CGContextDrawLayerAtPoint (context, CGPointZero, layer_1);
CGContextRestoreGState(context);
}
这个想法是虽然UIView的上下文总是被清除,但是与Layer相关联的离线上下文却不是。您可以继续累积图形操作,而不是通过drawRect清除它们。
编辑:所以你已经指出了你的问题和我解决的问题之间的区别。直到第一次显示之后我才需要绘制任何东西,而你想在第一次显示之前绘制一些东西。根据我的记忆,您可以随时以任何大小和分辨率创建图层。我发现最简单的方法是等待有效的上下文(当前设备的正确设置)传递给我,然后根据该上下文创建一个新的上下文/图层。请参阅“if(first)”块的内部。您可以执行相同的操作,但是您还必须缓存从服务器获取的行等,直到调用第一个drawRect:。然后,您可以使用给定的上下文创建脱机上下文,将从服务器获得的行等绘制到脱机上下文,然后如下所示绘制图层。因此,您唯一要添加到该方法的是在“if(first)”循环内调用以在继续之前绘制待处理的服务器源图形(请参阅源代码中添加的注释)。