Fel*_*oux 8 cocoa-touch core-graphics objective-c quartz-graphics uiview
假设我有一个点数组,形成一条线和一个文本.我怎样才能沿着这条线绘制文本
- (void)drawRect:(CGRect)rect
Run Code Online (Sandbox Code Playgroud)
一个UIView?
我能够毫无问题地绘制路径.是否存在我忽略的标准方法或允许我沿着该路径绘制文本的框架?理想情况下,我只想使用QuartzCore/CoreGraphics来做这件事.
我尝试计算每个角色的宽度并旋转每个角色.这种作品,但我想知道是否有更优雅的方法.
Dav*_*rek 11
我相信你可以在Mac OS X中做到这一点,但你最接近iPhone的是CGContextShowGlyphsWithAdvances,这甚至不会旋转.
使用循环并使用类似下面的内容绘制每个字符应该不会太难.这是根据Apple的文档改编而来的,未经过测试,因此请注意:
CGContextSelectFont(myContext, "Helvetica", 12, kCGEncodingMacRoman);
CGContextSetCharacterSpacing(myContext, 10);
CGContextSetTextDrawingMode(myContext, kCGTextFillStroke);
CGContextSetRGBFillColor(myContext, 0, 0, 0, 1);
CGContextSetRGBStrokeColor(myContext, 0, 0, 0, 1);
NSUInteger charIndex = 0;
for(NSString *myChar in arrayOfChars) {
char *cString = [myChar UTF8String];
CGPoint charOrigin = originForPositionAlongPath(charIndex, myPath);
CGFloat slope = slopeForPositionAlongPath(charIndex, myPath);
CGContextSetTextMatrix(myContext, CGAffineTransformMakeRotation(slope));
CGContextShowTextAtPoint(myContext, charOrigin.x, charOrigin.y, cString, 1);
}
Run Code Online (Sandbox Code Playgroud)
编辑:这是PositionAlongPath函数的概念.同样,他们没有经过测试,但应该接近.originAlong ...如果你的路径用完,则返回(-1,-1).
CGPoint originForPositionAlongPath(int index, NSArray *path) {
CGFloat charWidth = 12.0;
CGFloat widthToGo = charWidth * index;
NSInteger i = 0;
CGPoint position = [path objectAtIndex:i];
while(widthToGo >= 0) {
//out of path, return invalid point
if(i >= [path count]) {
return CGPointMake(-1, -1);
}
CGPoint next = [path objectAtIndex:i+1];
CGFloat xDiff = next.x - position.x;
CGFloat yDiff = next.y - position.y;
CGFloat distToNext = sqrt(xDiff*xDiff + yDiff*yDiff);
CGFloat fracToGo = widthToGo/distToNext
//point is before next point in path, interpolate the answer
if(fracToGo < 1) {
return CGPointMake(position.x+(xDiff*fracToGo), position.y+(yDiff*fracToGo));
}
//advance to next point on the path
widthToGo -= distToNext;
position = next;
++i;
}
}
CGFloat slopeForPositionAlongPath(int index, NSArray *path) {
CGPoint begin = originForPositionAlongPath(index, path);
CGPoint end = originForPositionAlongPath(index+1, path);
CGFloat xDiff = end.x - begin.x;
CGFloat yDiff = end.y - begin.y;
return atan(yDiff/xDiff);
}
Run Code Online (Sandbox Code Playgroud)