Mat*_*ijs 5 gradient objective-c cgcontext polyline
我正在寻找一种使用 CGContextRef 沿其路径绘制具有线性渐变的线的方法。我尝试了几种方法,但大多数都专注于用渐变填充区域(矩形),这不是我需要的。
我使用以下代码使用 CGPathRef 绘制实线。我实际上需要的是一个平滑的线性渐变,从线条的第一个点的 color1 开始,到线条的最后一个点的 color2 结束。
有谁知道如何实现这一目标?
- (CGMutablePathRef)generatedPath
{
CGMutablePathRef path = CGPathCreateMutable();
CGPathMoveToPoint(path, nil, 20, 10);
CGPathAddLineToPoint(path, nil, 100, 100);
CGPathAddLineToPoint(path, nil, 140, 120);
CGPathAddLineToPoint(path, nil, 160, 100);
CGPathAddLineToPoint(path, nil, 210, 70);
CGPathAddLineToPoint(path, nil, 250, 10);
return path;
}
- (void)drawRect:(CGRect)rect {
[super drawRect:rect];
CGContextRef ctx = UIGraphicsGetCurrentContext();
CGMutablePathRef path = [self generatedPath];
CGContextAddPath(ctx, path);
CGColorRef color = [UIColor redColor].CGColor;
CGContextSetLineWidth(ctx, 8.0);
CGContextSetStrokeColorWithColor(ctx, color);
CGContextStrokePath(ctx);
}
Run Code Online (Sandbox Code Playgroud)
=========更新========================================== ========
我实际上发现这个问题也与我需要的非常相似:Gradient Polyline with MapKit ios
我使用以下代码来实现沿着线条路径的渐变。作为评论,不要介意获取和传递路径点的低效方式。稍后我会优化一下:
- (NSArray*)generatePathPoints {
NSMutableArray *points = [[NSMutableArray alloc] init];
[points addObject:[NSValue valueWithCGPoint:CGPointMake(20, 50)]];
[points addObject:[NSValue valueWithCGPoint:CGPointMake(100, 100)]];
[points addObject:[NSValue valueWithCGPoint:CGPointMake(140, 120)]];
[points addObject:[NSValue valueWithCGPoint:CGPointMake(160, 100)]];
[points addObject:[NSValue valueWithCGPoint:CGPointMake(210, 70)]];
[points addObject:[NSValue valueWithCGPoint:CGPointMake(250, 10)]];
return points;
}
- (CGMutablePathRef)pathFromPoints: (NSArray*)points;
{
CGMutablePathRef path = CGPathCreateMutable();
for (int i = 0; i < points.count; i++) {
NSValue *pointValue = points[i];
CGPoint point = [pointValue CGPointValue];
if(i == 0){
CGPathMoveToPoint(path, nil, point.x, point.y);
}
else{
CGPathAddLineToPoint(path, nil, point.x, point.y);
}
}
return path;
}
- (void)drawRect:(CGRect)rect {
CGContextRef context = UIGraphicsGetCurrentContext();
NSArray *points = [self generatePathPoints];
CGFloat widthOfLine = 8.0;
CGLineCap lineCap = kCGLineCapRound;
CGLineJoin lineJoin = kCGLineJoinRound;
int miterLimit = 10;
UIColor *ccolor, *pcolor;
for (int i=0;i< points.count;i++){
CGMutablePathRef path = CGPathCreateMutable();
CGPoint point = ((NSValue*)points[i]).CGPointValue;
ccolor = [self colorForPointAtIndex:i points:points];
if (i==0){
CGPathMoveToPoint(path, nil, point.x, point.y);
} else {
CGPoint prevPoint = ((NSValue*)points[i-1]).CGPointValue;
CGPathMoveToPoint(path, nil, prevPoint.x, prevPoint.y);
CGPathAddLineToPoint(path, nil, point.x, point.y);
CGFloat pc_r,pc_g,pc_b,pc_a,
cc_r,cc_g,cc_b,cc_a;
[pcolor getRed:&pc_r green:&pc_g blue:&pc_b alpha:&pc_a];
[ccolor getRed:&cc_r green:&cc_g blue:&cc_b alpha:&cc_a];
CGFloat gradientColors[8] = {pc_r,pc_g,pc_b,pc_a,
cc_r,cc_g,cc_b,cc_a};
CGFloat gradientLocation[2] = {0,1};
CGContextSaveGState(context);
CGFloat lineWidth = CGContextConvertSizeToUserSpace(context, (CGSize){widthOfLine,widthOfLine}).width;
CGPathRef pathToFill = CGPathCreateCopyByStrokingPath(path, NULL, lineWidth, lineCap, lineJoin, miterLimit);
CGContextAddPath(context, pathToFill);
CGContextClip(context);//<--clip your context after you SAVE it, important!
CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
CGGradientRef gradient = CGGradientCreateWithColorComponents(colorSpace, gradientColors, gradientLocation, 2);
CGColorSpaceRelease(colorSpace);
CGPoint gradientStart = prevPoint;
CGPoint gradientEnd = point;
CGContextDrawLinearGradient(context, gradient, gradientStart, gradientEnd, kCGGradientDrawsAfterEndLocation | kCGGradientDrawsBeforeStartLocation);
CGGradientRelease(gradient);
CGContextRestoreGState(context);//<--Don't forget to restore your context.
}
pcolor = [UIColor colorWithCGColor:ccolor.CGColor];
}
}
-(UIColor*) colorForPointAtIndex: (NSUInteger)index points:(NSArray*)points {
return [UIColor colorWithRed:1.0 green:0 blue:0 alpha:(1.0 / points.count) * index];
}
Run Code Online (Sandbox Code Playgroud)
这几乎产生了我所需要的。不过只有一点小故障: https://i.stack.imgur.com/F9Efx.jpg
正如您所看到的,行结尾是重叠的,这通常不是问题。但因为线条是透明的,所以我得到了这种不需要的副作用。
有人知道如何从这里出发吗?
| 归档时间: |
|
| 查看次数: |
2865 次 |
| 最近记录: |