在上一节中,通过drawrect会导致内存激增的情况,我是用image来代替的,但是同样所有的内容需要重新绘制,生成图片,我们画得越多,程序就会越慢,直接导致了帧数的下降。那就需要一个更好的方法了。
在 Core Animation 中,有一个专门处理多边形、曲线、直线的专有图层,由于使用了硬件加速,所以效果还是不错的。
@interface CAShapeLayer : CALayer
@property(nullable) CGPathRef path;
@property(nullable) CGColorRef fillColor;
@property(copy) NSString *fillRule;
@property(nullable) CGColorRef strokeColor;
@property CGFloat strokeStart;
@property CGFloat strokeEnd;
@property CGFloat lineWidth;
@property CGFloat miterLimit;
@property(copy) NSString *lineCap;
@property(copy) NSString *lineJoin;
@property CGFloat lineDashPhase;
@property(nullable, copy) NSArray<NSNumber *> *lineDashPattern;
@end
我们可以通过获取 用户移动的路径(UIBezierPath 添加移动的点) 设置 path
#import "DrawView.h"
@interface DrawView ()
@property (nonatomic, strong) UIBezierPath *path;
@end
@implementation DrawView
+ (Class)layerClass
{
return [CAShapeLayer class];
}
- (void)awakeFromNib
{
[self configView];
}
- (instancetype)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
[self configView];
}
return self;
}
- (void)configView
{
self.path = [[UIBezierPath alloc] init];
CAShapeLayer *shapeLayer = (CAShapeLayer *)self.layer;
shapeLayer.strokeColor = [UIColor redColor].CGColor;
shapeLayer.fillColor = [UIColor clearColor].CGColor;
shapeLayer.lineJoin = kCALineJoinRound;
shapeLayer.lineCap = kCALineCapRound;
shapeLayer.lineWidth = 5;
}
-(void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
{
//get the starting point
CGPoint point = [[touches anyObject] locationInView:self];
//move the path drawing cursor to the starting point
[self.path moveToPoint:point];
}
- (void)touchesMoved:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event
{
//get the current point
CGPoint point = [[touches anyObject] locationInView:self];
//add a new line segment to our path
[self.path addLineToPoint:point];
//update the layer with a copy of the path
((CAShapeLayer *)self.layer).path = self.path.CGPath;
}
@end
好了,这样就可以解决重复绘制的问题了~
具体Demo,在这里
// demo 一
// [self.view addSubview:self.imageView];
// demo 二, 此时的绘制是在 drawView 中进行的
[self.view addSubview:self.drawView];
网友评论