-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathUIBezierPath+Smoothing.m
65 lines (49 loc) · 1.81 KB
/
UIBezierPath+Smoothing.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
//
// UIBezierPath+Smoothing.m
// Exercise
//
// Created by 汪迪岑 on 2017/10/19.
// Copyright © 2017年 汪迪岑. All rights reserved.
//
#import "UIBezierPath+Smoothing.h"
#import "UIBezierPath+Points.h"
#define POINT(_INDEX_) [(NSValue *)[points objectAtIndex:_INDEX_] CGPointValue]
@implementation UIBezierPath (Smoothing)
-(UIBezierPath *)smoothedPath:(int)granularity
{
NSMutableArray *points = [self.points mutableCopy];
if (points.count < 4) {
return [self copy];
}
[points insertObject:[points objectAtIndex:0] atIndex:0];
[points addObject:[points lastObject]];
UIBezierPath *smoothedPath = [UIBezierPath bezierPath];
smoothedPath.lineWidth = self.lineWidth;
[smoothedPath moveToPoint:POINT(0)];
for (int index = 1; index <3;index++) {
[smoothedPath addLineToPoint:POINT(index)];
}
for (int index = 4; index <points.count; index++) {
CGPoint p0 = POINT(index -3);
CGPoint p1 = POINT(index -2);
CGPoint p2 = POINT(index -1);
CGPoint p3 = POINT(index);
for (int i=1; i<granularity; i++) {
float t = (float) i*(1.0f/(float)granularity);
float tt = t*t;
float ttt = t*t*t;
CGPoint pi;
pi.x = 0.5*(2*p1.x + (p2.x - p0.x) *t +
(2*p0.x - 5*p1.x + 4*p2.x - p3.x)*tt +
(3*p1.x - p0.x - 3*p2.x + p3.x)*ttt);
pi.y = 0.5*(2*p1.y + (p2.y - p0.y) *t +
(2*p0.y - 5*p1.y + 4*p2.y - p3.y)*tt +
(3*p1.y - p0.y - 3*p2.y + p3.y)*ttt);
[smoothedPath addLineToPoint:pi];
}
[smoothedPath addLineToPoint:p2];
}
[smoothedPath addLineToPoint:POINT(points.count - 1)];
return smoothedPath;
}
@end