我UIView
在运行时添加了代码.
我想画一个UIBezierPath
,但这是否意味着我必须覆盖drawRect
UIView?
或者是否有其他方式在定制上绘制它UIView
?
以下是生成以下内容的代码UIView
:
UIView* shapeView = [[UIView alloc]initWithFrame:CGRectMake(xOrigin,yOrigin+(i*MENU_BLOCK_FRAME_HEIGHT), self.shapeScroll.frame.size.width, MENU_BLOCK_FRAME_HEIGHT)];
shapeView.clipsToBounds = YES;
Run Code Online (Sandbox Code Playgroud)
以下是创建和返回的函数UIBezierPath
:
- (UIBezierPath*)createPath
{
UIBezierPath* path = [[UIBezierPath alloc]init];
[path moveToPoint:CGPointMake(100.0, 50.0)];
[path addLineToPoint:CGPointMake(200.0,50.0)];
[path addLineToPoint:CGPointMake(200.0, 200.0)];
[path addLineToPoint:CGPointMake(100.0, 200.0)];
[path closePath];
return path;
}
Run Code Online (Sandbox Code Playgroud) 通过使用[UIBezierPath bezierPathWithRoundedRect:byRoundingCorners:cornerRadii:]
,我可以创建一个圆形视图,如下所示:
我怎样才能从这一个(或其他方式)中减去另一条路径,以创建这样的路径:
我有什么方法可以做这样的事情吗?伪代码:
UIBezierPath *bigMaskPath = [UIBezierPath bezierPathWithRoundedRect:bigView.bounds
byRoundingCorners:(UIRectCornerTopLeft|UIRectCornerTopRight)
cornerRadii:CGSizeMake(18, 18)];
UIBezierPath *smallMaskPath = [UIBezierPath bezierPathWithRoundedRect:smalLView.bounds
byRoundingCorners:(UIRectCornerTopLeft|UIRectCornerTopRight)
cornerRadii:CGSizeMake(18, 18)];
UIBezierPath *finalPath = [UIBezierPath pathBySubtractingPath:smallMaskPath fromPath:bigMaskPath];
Run Code Online (Sandbox Code Playgroud) 当你右键点击底座上的某些东西时,我正试图获得类似于Mac OS X中的"语音气泡"效果.这就是我现在拥有的:
我需要得到下半部分的"三角形"部分.有什么方法可以画出类似的东西并围绕它画一个边框吗?这将是一个iPhone应用程序.
提前致谢!
编辑:非常感谢Brad Larson,这就是现在的样子:
目的
我试图使用从字形生成的UIBezierPath创建人类书写的动画近似.我理解并且我已经阅读了许多与我的相似的UIBezierPath问题(但不一样).我的目标是创建一个近似于执行字符和字母书写的人的外观的动画.
背景
我创建了一个游乐场,用于更好地理解用于动画字形的路径,就好像它们是手工绘制的一样.
Apple CAShapeLayer中的一些概念(strokeStart和strokeEnd)在动画时似乎并没有按预期运行.我认为通常人们倾向于将中风想象成使用书写工具(基本上是直线或曲线).我们认为笔划和填充是一条线,因为我们的书写工具不区分笔画和填充.
但是当动画时,路径的轮廓由线段构成(填充是单独处理的,不清楚如何设置填充位置的动画?).我想要实现的是一个自然的人类书写线/曲线,它显示了一个笔划的开始和结束,以及当动画从头到尾移动时添加的部分.最初看起来很简单,但我认为它可能需要设置填充位置的动画(不确定如何执行此操作),笔划开始/结束(不确定是否需要根据上面提到的动画执行方式的意外警告),以及使用子路径(如何从已知路径重建).
方法1
所以,我考虑过Path(CGPath/UIBezierPath)的想法.每个路径实际上包含构造字形所需的所有子路径,因此可能递归这些子路径并使用CAKeyframeAnimation/CABasicAnimations和显示部分构造的子路径的动画组将是一个很好的方法(尽管每个子路径的填充位置和笔划仍然是需要从头到尾动画?).
这种方法导致了一个精炼的问题:
如果有一个完整的UIBezierPath/CGPath,如何访问和创建UIBezierPath/CGPath(子路径)?
如何使用路径/子路径信息用书写工具绘制填充和描边的动画?(似乎这意味着需要同时为CALayer的strokeStart/strokeEnd,position和path属性设置动画)
注意:
正如人们可以在代码中观察到的那样,我确实拥有从字形获得的完成路径.我可以看到路径描述给了我类似路径的信息.如何获取该信息并将其重新编排为一组数据子路径 人类可写的笔画?
(这里的想法是将点信息转换为人类笔画的新数据类型.这意味着要求算法识别每个填充的起点,斜率,端点和边界)
提示
我在Pleco(一个成功实现类似算法的iOS应用程序)中注意到,每个笔划都由描述人类可写笔画的闭合路径组成.UIBezierPath具有基于连续填充填充的封闭路径.需要一种算法来细化重叠填充以为每个笔画类型创建不同的闭合路径.
Erica Sadun 在github上提供了一组路径实用程序.我没有完全探索这些文件,但它们可能在确定离散笔划时非常有用.
UIBezierPath结构似乎基于连续线段/曲线的概念.在填充的交叉点处出现汇合点,其表示有向路径变化.可以计算曲线/线段的行程/填充角度,并搜索相应汇流点的其他曲线/线吗?(即将一条线段连接在相交填充的间隙上,以产生两条独立的路径 - 假设一条线路拾取了点,并使用新的线段/曲线重新创建了路径)
内省:是否有更简单的方法?我错过了一个关键的API,一本书或更好的方法来解决这个问题吗?
一些替代方法(无用 - 需要加载GIF或闪存)以产生所需的结果:
良好的示例(使用Flash),其中一个表示层显示书写笔划的进展.(如果可能的话,这就是我想要在Swift/iOS中近似的东西) - (alt链接 - 请参阅左边的动画图像)
一个不太好的例子,显示使用渐进路径和填充来近似书写笔划特征(动画不流畅且需要外部资源):
一个Flash版本 - 我熟悉创建Flash动画,但我不愿意在1000版本中实现这些功能(不要太提及它在iOS上不受支持,尽管我可能还可以转换算法以利用带有css动画的HTML5画布).但是这个思路似乎有点远,毕竟,我想要的路径信息存储在我从提供的字体/字符串中提取的字形中.
方法2
我正在考虑使用基于笔划的字体而不是基于轮廓的字体来获取正确的路径信息(即填充表示为路径的信息).如果成功,这种方法比近似笔画,笔画类型,交叉点和笔画顺序更清晰.我已经向Apple提交了雷达,建议将基于笔划的字体添加到iOS(#20426819).尽管有这些努力,我仍然没有放弃形成一种算法,该算法解决了贝塞尔曲线上的线段和曲线的部分笔划,全笔画,交叉点和汇合点.
基于讨论/答案的最新想法
根据以下任何正在进行的对话和答案,提供以下附加信息.
笔划顺序很重要,大多数语言(本例中为中文)都有明确定义的笔划类型和笔划顺序规则,它们似乎提供了一种机制,可根据每个CGPathElement提供的点信息确定类型和顺序.
CGPathApply和CGPathApplierFunction看起来很有希望作为枚举子路径的方法(保存到数组并应用填充动画)
可以将一个蒙版应用于图层以显示子图层的一部分(我之前没有使用过此属性,但看起来如果我可以在子路径上移动可能有助于填充动画的蒙版图层?)
为每个路径定义了大量的点.好像仅使用字形轮廓定义BezierPath.这一事实使得理解交叉填充的开始,结束和结合是消除特定填充的歧义的重要因素.
可以使用其他外部库,以便更好地解决笔划行为.其他技术如Saffron Type System或其衍生产品之一可能适用于此问题域.
仅仅为动画设置动画的最简单解决方案的基本问题是可用的iOS字体是轮廓字体而不是基于笔划的字体.一些商业制造商确实生产基于笔划的字体.如果你有其中一个用于测试,请随意使用操场文件的链接.
我认为这是一个常见问题,随着我向解决方案迈进,我将继续更新帖子.如果需要进一步的信息或者我可能遗漏了一些必要的概念,请在评论中告诉我.
可能解决方案
我一直在寻找最简单的解决方案.问题源于字体的结构是轮廓字体而不是基于笔画的字体.我发现了一个基于笔划的字体样本进行测试,并使用它来评估概念证明(见视频).我现在正在寻找扩展的单笔划字体(包括中文字符)以进一步评估.一个不太简单的解决方案可能是找到一种方法来创建一个跟随填充的笔划,然后使用简单的二维几何来评估首先设置动画的笔划(例如中文规则在笔划顺序上非常清晰). …
第一次使用BezierPaths,想知道这个函数实际上应该如何实现.目前,贝塞尔曲线路径在图像的帧内移动,而不是在屏幕上绘制.
有没有更好的方法呢?
func drawLineFromPoint(start : CGPoint, toPoint end:CGPoint, ofColor lineColor: UIColor, inView view:UIView) {
var maxWidth = abs(start.x - end.x)
var maxHeight = abs(start.y - end.y)
var contextSize : CGSize!
if maxWidth == 0 {
contextSize = CGSize(width: 1, height: maxHeight)
}else {
contextSize = CGSize(width: maxWidth, height: 1)
}
//design the path
UIGraphicsBeginImageContextWithOptions(contextSize, false, 0)
var path = UIBezierPath()
path.lineWidth = 1.0
lineColor.set()
//draw the path and make visible
path.moveToPoint(start)
path.addLineToPoint(end)
path.stroke()
//create image from path and add to …
Run Code Online (Sandbox Code Playgroud) 在诸如如何绘制一个平滑的圆圈......,...绘制圆...和...绘制填充圆圈的问题和答案是非常广泛的,包含许多不必要的步骤,并使用的方法并不总是最容易重新创建或管理.
什么是绘制圆圈并将其添加到我的简单方法UIView
?
I want to get the image from the UIBezierpath
closed path(See the image). I draw the image on the UIView
using drawRect
method and also draw the lines are using the drawRect
method.
How can I get the particular closed path image? Please help me. Thanks in advance.
This code used for draw the bezierpath.
UIBezierPath *aPath = [UIBezierPath bezierPath];
for (NSString *pointString in pointArray) {
if ([pointArray indexOfObject:pointString] == 0)
[aPath moveToPoint:CGPointFromString(pointString)];
else
[aPath addLineToPoint:CGPointFromString(pointString)];
}
[aPath closePath];
Run Code Online (Sandbox Code Playgroud)
我想创建一个具有弧形的进度条.进度条的颜色必须根据值进行更改.
我使用创建了一个弧UIBezierPath bezierPathWithArcCenter
.我使用了以下代码:
- (void)viewDidLoad
{
[super viewDidLoad];
int radius = 100;
CAShapeLayer *arc = [CAShapeLayer layer];
arc.path = [UIBezierPath bezierPathWithArcCenter:CGPointMake(100, 50) radius:radius startAngle:60.0 endAngle:0.0 clockwise:YES].CGPath;
arc.position = CGPointMake(CGRectGetMidX(self.view.frame)-radius,
CGRectGetMidY(self.view.frame)-radius);
arc.fillColor = [UIColor clearColor].CGColor;
arc.strokeColor = [UIColor purpleColor].CGColor;
arc.lineWidth = 15;
[self.view.layer addSublayer:arc];
CABasicAnimation *drawAnimation = [CABasicAnimation animationWithKeyPath:@"strokeEnd"];
drawAnimation.duration = 5.0; // "animate over 10 seconds or so.."
drawAnimation.repeatCount = 1.0; // Animate only once..
drawAnimation.removedOnCompletion = NO; // Remain stroked after the animation..
drawAnimation.fromValue = [NSNumber numberWithFloat:0.0f]; …
Run Code Online (Sandbox Code Playgroud) 这是一张简单的图纸
- (void)drawRect:(CGRect)rect
{
//vertical line with 1 px stroking
UIBezierPath *vertLine = [[UIBezierPath alloc] init];
[vertLine moveToPoint:CGPointMake(20.0, 10.0)];
[vertLine addLineToPoint:CGPointMake(20.0, 400.0)];
vertLine.lineWidth = 1.0;
[[UIColor blackColor] setStroke];
[vertLine stroke];
//vertical rectangle 1px width
UIBezierPath *vertRect= [UIBezierPath bezierPathWithRect:CGRectMake(40.0, 10.0, 1.0, 390.0)];
[[UIColor blackColor] setFill];
[vertRect fill];
}
Run Code Online (Sandbox Code Playgroud)
在非视网膜3GS和模拟器上,第一行是模糊的,看起来比1 px宽,但第二行是清晰的.
不幸的是我没有iPhone4和新iPad进行测试,但在视网膜模拟器上两条线看起来都一样.
问题:矩形而非中风是获得非视网膜和视网膜设备相同结果的唯一方法吗?
uibezierpath ×10
ios ×9
objective-c ×6
iphone ×5
swift ×3
uiview ×2
cashapelayer ×1
cgpath ×1
drawing ×1
uicolor ×1
xcode ×1