private UIBezierPath NormalPath(LiquittableCircle circle, LiquittableCircle other) { var tuple1 = CircleConnectedPoint(circle, other); var tuple2 = CircleConnectedPoint(other, circle); var cgPoint1 = tuple1.Item1; var cgPoint2 = tuple1.Item2; var cgPoint3 = tuple2.Item1; var cgPoint4 = tuple2.Item2; var nullable = CoreGraphicsExtensions.Intersection(cgPoint1, cgPoint3, cgPoint2, cgPoint4); if (!nullable.HasValue) { return(null); } var uiBezierPath = new UIBezierPath(); var nfloat = CircleRatio(circle, other); // ISSUE: reference to a compiler-generated method uiBezierPath.MoveTo(cgPoint1); var cgPoint5 = cgPoint2.Mid(cgPoint3); var cgPoint6 = cgPoint1.Mid(cgPoint4); var ratio = (1 - nfloat) / (1 - AngleThreshold) * Viscosity; var controlPoint1 = cgPoint5.Mid(nullable.Value).Split(cgPoint6, ratio); var controlPoint2 = cgPoint6.Mid(nullable.Value).Split(cgPoint5, ratio); // ISSUE: reference to a compiler-generated method uiBezierPath.AddQuadCurveToPoint(cgPoint4, controlPoint1); // ISSUE: reference to a compiler-generated method uiBezierPath.AddLineTo(cgPoint3); // ISSUE: reference to a compiler-generated method uiBezierPath.AddQuadCurveToPoint(cgPoint2, controlPoint2); // ISSUE: reference to a compiler-generated method uiBezierPath.ClosePath(); return(uiBezierPath); }
private UIBezierPath NormalPath(LiquittableCircle circle, LiquittableCircle other) { var p1p2 = CircleConnectedPoint(circle, other); var p3p4 = CircleConnectedPoint(other, circle); var p1 = p1p2.Item1; var p2 = p1p2.Item2; var p3 = p3p4.Item1; var p4 = p3p4.Item2; var crossed = CoreGraphicsExtensions.Intersection(p1, p3, p2, p4); if (crossed != null) { var path = new UIBezierPath(); var r = CircleRatio(circle, other); path.MoveTo(p1); var r1 = p2.Mid(p3); var r2 = p1.Mid(p4); var rate = (1 - r) / (1 - AngleThreshold) * Viscosity; var mul = r1.Mid(crossed.Value).Split(r2, rate); var mul2 = r2.Mid(crossed.Value).Split(r1, rate); path.AddQuadCurveToPoint(p4, mul); path.AddLineTo(p3); path.AddQuadCurveToPoint(p2, mul2); path.ClosePath(); return(path); } return(null); }
private UIBezierPath ShapePath(CGSize size) { var intensity = 0.44f; var controlRatio = 0.25f; var padding = 0; CGPoint leftTop = new CGPoint(x: padding, y: padding); CGPoint rightTop = new CGPoint(x: size.Width - padding, y: padding); CGPoint leftBottom = new CGPoint(x: padding, y: size.Height - padding); CGPoint rightBottom = new CGPoint(x: size.Width - padding, y: size.Height - padding); var path = new UIBezierPath(); path.MoveTo(leftTop); path.AddQuadCurveToPoint(new CGPoint(x: size.Width / 2, y: size.Height / 2 * intensity), controlPoint: new CGPoint(x: size.Width / 2 * controlRatio, y: size.Height / 2 * intensity)); path.AddQuadCurveToPoint(rightTop, controlPoint: new CGPoint(x: size.Width - (size.Width / 2 * controlRatio), y: size.Height / 2 * intensity)); path.AddLineTo(rightBottom); path.AddQuadCurveToPoint(new CGPoint(x: size.Width / 2, y: size.Height - (size.Height / 2 * intensity)), controlPoint: new CGPoint(x: size.Width - (size.Width / 2 * controlRatio), y: size.Height - (size.Height / 2 * intensity))); path.AddQuadCurveToPoint(leftBottom, controlPoint: new CGPoint(x: size.Width / 2 * controlRatio, y: size.Height - (size.Height / 2 * intensity))); path.AddLineTo(leftTop); path.ClosePath(); return(path); }
public static UIBezierPath CreatePolygonPath(CGRect rect, int sides, double cornerRadius = 0.0, double rotationOffset = 0.0) { var offsetRadians = rotationOffset * Math.PI / 180; var path = new UIBezierPath(); var theta = 2 * Math.PI / sides; var width = (-cornerRadius + Math.Min(rect.Size.Width, rect.Size.Height)) / 2; var center = new CGPoint(rect.Width / 2, rect.Height / 2); var radius = width + cornerRadius - (Math.Cos(theta) * cornerRadius) / 2; var angle = offsetRadians; var corner = new CGPoint(center.X + (radius - cornerRadius) * Math.Cos(angle), center.Y + (radius - cornerRadius) * Math.Sin(angle)); path.MoveTo(new CGPoint(corner.X + cornerRadius * Math.Cos(angle + theta), corner.Y + cornerRadius * Math.Sin(angle + theta))); for (var i = 0; i < sides; i++) { angle += theta; corner = new CGPoint(center.X + (radius - cornerRadius) * Math.Cos(angle), center.Y + (radius - cornerRadius) * Math.Sin(angle)); var tip = new CGPoint(center.X + radius * Math.Cos(angle), center.Y + radius * Math.Sin(angle)); var start = new CGPoint(corner.X + cornerRadius * Math.Cos(angle - theta), corner.Y + cornerRadius * Math.Sin(angle - theta)); var end = new CGPoint(corner.X + cornerRadius * Math.Cos(angle + theta), corner.Y + cornerRadius * Math.Sin(angle + theta)); path.AddLineTo(start); path.AddQuadCurveToPoint(end, tip); } path.ClosePath(); return(path); }
private UIBezierPath[] SplitPath(LiquittableCircle circle, LiquittableCircle other, nfloat ratio) { var p1p2 = CircleConnectedPoint(circle, other, CoreGraphicsExtensions.DegToRad(60)); var p3p4 = CircleConnectedPoint(other, circle, CoreGraphicsExtensions.DegToRad(60)); var p1 = p1p2.Item1; var p2 = p1p2.Item2; var p3 = p3p4.Item1; var p4 = p3p4.Item2; var crossed = CoreGraphicsExtensions.Intersection(p1, p3, p2, p4); if (crossed != null) { var d1 = CircleConnectedPoint(circle, other, 0).Item1; var d2 = CircleConnectedPoint(other, circle, 0).Item1; var r = (ratio - connectThresh) / (AngleThreshold - connectThresh); var a1 = d2.Split(crossed.Value, r * r); var part = new UIBezierPath(); part.MoveTo(p1); part.AddQuadCurveToPoint(p2, a1); part.ClosePath(); var a2 = d1.Split(crossed.Value, r * r); var part2 = new UIBezierPath(); part2.MoveTo(p3); part2.AddQuadCurveToPoint(p4, a2); part2.ClosePath(); return(new[] { part, part2 }); } return(new UIBezierPath[0]); }
async Task animateView(UIView view) { var size = view.Frame.Size; var grow = new SizeF(size.Width * 1.7f, size.Height * 1.7f); var shrink = new SizeF(size.Width * .4f, size.Height * .4f); TaskCompletionSource <bool> tcs = new TaskCompletionSource <bool> (); //Set the animation path var pathAnimation = CAKeyFrameAnimation.GetFromKeyPath("position"); pathAnimation.CalculationMode = CAAnimation.AnimationPaced; pathAnimation.FillMode = CAFillMode.Forwards; pathAnimation.RemovedOnCompletion = false; pathAnimation.Duration = .5; UIBezierPath path = new UIBezierPath(); path.MoveTo(view.Center); path.AddQuadCurveToPoint(new PointF(290, 34), new PointF(view.Center.X, View.Center.Y)); pathAnimation.Path = path.CGPath; //Set size change var growAnimation = CABasicAnimation.FromKeyPath("bounds.size"); growAnimation.To = NSValue.FromSizeF(grow); growAnimation.FillMode = CAFillMode.Forwards; growAnimation.Duration = .1; growAnimation.RemovedOnCompletion = false; var shrinkAnimation = CABasicAnimation.FromKeyPath("bounds.size"); shrinkAnimation.To = NSValue.FromSizeF(shrink); shrinkAnimation.FillMode = CAFillMode.Forwards; shrinkAnimation.Duration = .4; shrinkAnimation.RemovedOnCompletion = false; shrinkAnimation.BeginTime = .1; CAAnimationGroup animations = new CAAnimationGroup(); animations.FillMode = CAFillMode.Forwards; animations.RemovedOnCompletion = false; animations.Animations = new CAAnimation[] { pathAnimation, growAnimation, shrinkAnimation, }; animations.Duration = .5; animations.AnimationStopped += (sender, e) => { tcs.TrySetResult(true); }; view.Layer.AddAnimation(animations, "movetocart"); NSTimer.CreateScheduledTimer(.5, () => view.RemoveFromSuperview()); await tcs.Task; }
async Task animateView(UIView view) { var size = view.Frame.Size; var grow = new SizeF(size.Width * 1.7f, size.Height * 1.7f); var shrink = new SizeF(size.Width * .4f, size.Height * .4f); TaskCompletionSource<bool> tcs = new TaskCompletionSource<bool> (); //Set the animation path var pathAnimation = CAKeyFrameAnimation.GetFromKeyPath("position"); pathAnimation.CalculationMode = CAAnimation.AnimationPaced; pathAnimation.FillMode = CAFillMode.Forwards; pathAnimation.RemovedOnCompletion = false; pathAnimation.Duration = .5; UIBezierPath path = new UIBezierPath (); path.MoveTo (view.Center); path.AddQuadCurveToPoint (new PointF (290, 34), new PointF(view.Center.X,View.Center.Y)); pathAnimation.Path = path.CGPath; //Set size change var growAnimation = CABasicAnimation.FromKeyPath("bounds.size"); growAnimation.To = NSValue.FromSizeF (grow); growAnimation.FillMode = CAFillMode.Forwards; growAnimation.Duration = .1; growAnimation.RemovedOnCompletion = false; var shrinkAnimation = CABasicAnimation.FromKeyPath("bounds.size"); shrinkAnimation.To = NSValue.FromSizeF (shrink); shrinkAnimation.FillMode = CAFillMode.Forwards; shrinkAnimation.Duration = .4; shrinkAnimation.RemovedOnCompletion = false; shrinkAnimation.BeginTime = .1; CAAnimationGroup animations = new CAAnimationGroup (); animations.FillMode = CAFillMode.Forwards; animations.RemovedOnCompletion = false; animations.Animations = new CAAnimation[] { pathAnimation, growAnimation, shrinkAnimation, }; animations.Duration = .5; animations.AnimationStopped += (sender, e) => { tcs.TrySetResult(true); }; view.Layer.AddAnimation (animations,"movetocart"); NSTimer.CreateScheduledTimer (.5, () => view.RemoveFromSuperview ()); await tcs.Task; }
public override void TouchesMoved(NSSet touches, UIEvent evt) { base.TouchesMoved(touches, evt); UITouch touch = touches.AnyObject as UITouch; var currentPoint = touch.LocationInView(this); currentPoint = touch.LocationInView(this); if (Math.Abs(currentPoint.X - previousPoint.X) >= 4 || Math.Abs(currentPoint.Y - previousPoint.Y) >= 4) { var newPoint = new CGPoint((currentPoint.X + previousPoint.X) / 2, (currentPoint.Y + previousPoint.Y) / 2); currentPath.AddQuadCurveToPoint(newPoint, previousPoint); previousPoint = currentPoint; } InvokeOnMainThread(SetNeedsDisplay); }
public override void TouchesMoved(MonoTouch.Foundation.NSSet touches, UIEvent evt) { base.TouchesMoved(touches, evt); UITouch touch = (UITouch)touches.AnyObject; var location = touch.LocationInView(this); float dx = Math.Abs(location.X - mX); float dy = Math.Abs(location.Y - mY); if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE) { mPath.AddQuadCurveToPoint(new PointF((location.X + mX) / 2f, (location.Y + mY) / 2f), new PointF(mX, mY)); mMoved = true; mX = location.X; mY = location.Y; AddPixelsXY(mX, mY, false); } this.SetNeedsDisplay(); }
/// <summary> /// Sent when one or more fingers move on the screen. /// </summary> /// <param name="touches">Set containing the touches as objects of type <see cref="T:UIKit.UITouch" />.</param> /// <param name="evt"><para>The UIEvent that encapsulates all of the touches and the event information.</para> /// <para tool="nullallowed">This parameter can be <see langword="null" />.</para></param> /// <remarks><para>Since iOS 9.0, <see cref="M:UIKit.UIResponder.TouchesMoved(Foundation.NSSet,UIKit.UIEvent)" /> events are raised on supported hardware and configurations for changes in user-applied pressure. The <see cref="P:UIKit.UITouch.Force" /> property of the <see cref="T:UIKit.UITouch" /> object in the <paramref name="touches" /> set argument contains the magnitude of the touch that raised the event. The following example shows a basic use:</para> /// <para> /// <code lang="c#"><![CDATA[ /// if (TraitCollection.ForceTouchCapability == UIForceTouchCapability.Available) { /// UITouch t = touches.AnyObject as UITouch; /// ForceLabel.Text = "Force: " + t.Force.ToString (); /// } /// else { /// ForceLabel.Text = "Force Not Active"; /// }]]></code> /// </para></remarks> public override void TouchesMoved(NSSet touches, UIEvent evt) { var touch = (UITouch)touches.AnyObject; var currentPoint = touch.LocationInView(this); if (Math.Abs(currentPoint.X - _previousPoint.X) >= 4 || Math.Abs(currentPoint.Y - _previousPoint.Y) >= 4) { var newPoint = new CGPoint((currentPoint.X + _previousPoint.X) / 2, (currentPoint.Y + _previousPoint.Y) / 2); _currentPath.AddQuadCurveToPoint(newPoint, _previousPoint); _previousPoint = currentPoint; } else { _currentPath.AddLineTo(currentPoint); } InvokeOnMainThread(SetNeedsDisplay); }
private UIBezierPath[] SplitPath(LiquittableCircle circle, LiquittableCircle other, nfloat ratio) { var tuple1 = CircleConnectedPoint(circle, other, CoreGraphicsExtensions.DegToRad(60)); var tuple2 = CircleConnectedPoint(other, circle, CoreGraphicsExtensions.DegToRad(60)); var cgPoint1 = tuple1.Item1; var cgPoint2 = tuple1.Item2; var cgPoint3 = tuple2.Item1; var cgPoint4 = tuple2.Item2; var nullable = CoreGraphicsExtensions.Intersection(cgPoint1, cgPoint3, cgPoint2, cgPoint4); if (!nullable.HasValue) { return(new UIBezierPath[0]); } var self1 = CircleConnectedPoint(circle, other, 0).Item1; var self2 = CircleConnectedPoint(other, circle, 0).Item1; var nfloat = (ratio - _connectThresh) / (AngleThreshold - _connectThresh); var controlPoint1 = self2.Split(nullable.Value, nfloat * nfloat); var uiBezierPath1 = new UIBezierPath(); // ISSUE: reference to a compiler-generated method uiBezierPath1.MoveTo(cgPoint1); // ISSUE: reference to a compiler-generated method uiBezierPath1.AddQuadCurveToPoint(cgPoint2, controlPoint1); // ISSUE: reference to a compiler-generated method uiBezierPath1.ClosePath(); var controlPoint2 = self1.Split(nullable.Value, nfloat * nfloat); var uiBezierPath2 = new UIBezierPath(); // ISSUE: reference to a compiler-generated method uiBezierPath2.MoveTo(cgPoint3); // ISSUE: reference to a compiler-generated method uiBezierPath2.AddQuadCurveToPoint(cgPoint4, controlPoint2); // ISSUE: reference to a compiler-generated method uiBezierPath2.ClosePath(); return(new[] { uiBezierPath1, uiBezierPath2 }); }
public override void TouchesMoved(NSSet touches, UIEvent evt) { var touch = (UITouch)touches.AnyObject; var currentPoint = touch.LocationInView(this); if (Math.Abs(currentPoint.X - PreviousPoint.X) >= 4 || Math.Abs(currentPoint.Y - PreviousPoint.Y) >= 4) { var newPoint = new PointF((currentPoint.X + PreviousPoint.X) / 2, (currentPoint.Y + PreviousPoint.Y) / 2); CurrentPath.AddQuadCurveToPoint(newPoint, PreviousPoint); PreviousPoint = currentPoint; InvokeOnMainThread(SetNeedsDisplay); PointerEvent?.Invoke(this, new PointerEventArgs(PointerEventArgs. PointerEventType.Move, PreviousPoint.ToPoint(), newPoint.ToPoint(), PointerDown)); } else { CurrentPath.AddLineTo(currentPoint); InvokeOnMainThread(SetNeedsDisplay); } }
public CGPath WavePath(nfloat amountX, nfloat amountY) { var w = Frame.Width; var h = Frame.Height; var centerY = (nfloat)0f; var bottomY = h; var topLeftPoint = new CGPoint(0, centerY); var topMidPoint = new CGPoint(w / 2 + amountX, centerY + amountY); var topRightPoint = new CGPoint(w, centerY); var bottomLeftPoint = new CGPoint(0, bottomY); var bottomRightPoint = new CGPoint(w, bottomY); var bezierPath = new UIBezierPath(); bezierPath.MoveTo(bottomLeftPoint); bezierPath.AddLineTo(topLeftPoint); bezierPath.AddQuadCurveToPoint(topRightPoint, topMidPoint); bezierPath.AddLineTo(bottomRightPoint); return(bezierPath.CGPath); }
public override void Draw(CGRect rect) { var boxView = (RoundedStackLayout)Element; double sourceWidth = rect.Size.Width; double sourceHeight = rect.Size.Height; double desiredWidth = sourceWidth; double desiredHeight = sourceHeight; var topLeftCornerSize = boxView.CornerRadius; var topRightCornerSize = boxView.CornerRadius; var bottomLeftCornerSize = boxView.CornerRadius; var bottomRightCornerSize = boxView.CornerRadius; using (CGContext context = UIGraphics.GetCurrentContext()) { context.BeginPath(); using (var path = new UIBezierPath()) { // TopLeft if (boxView.CornersAttributes.HasFlag(CornerAttributes.TopLeftRounded)) { path.MoveTo(new CGPoint(0, topLeftCornerSize)); path.AddQuadCurveToPoint(new CGPoint(topLeftCornerSize, 0), new CGPoint(0, 0)); } else { path.MoveTo(new CGPoint(0, 0)); } // TopRight if (boxView.CornersAttributes.HasFlag(CornerAttributes.TopRightRounded)) { path.AddLineTo(new CGPoint(desiredWidth - topRightCornerSize, 0)); path.AddQuadCurveToPoint(new CGPoint(desiredWidth, topRightCornerSize), new CGPoint(desiredWidth, 0)); } else { path.AddLineTo(new CGPoint(desiredWidth, 0)); } // BottomRight if (boxView.CornersAttributes.HasFlag(CornerAttributes.BottomRightRounded)) { path.AddLineTo(new CGPoint(desiredWidth, desiredHeight - bottomRightCornerSize)); path.AddQuadCurveToPoint(new CGPoint(desiredWidth - bottomRightCornerSize, desiredHeight), new CGPoint(desiredWidth, desiredHeight)); } else { path.AddLineTo(new CGPoint(desiredWidth, desiredHeight)); } // BottomLeft if (boxView.CornersAttributes.HasFlag(CornerAttributes.BottomLeftRounded)) { path.AddLineTo(new CGPoint(bottomLeftCornerSize, desiredHeight)); path.AddQuadCurveToPoint(new CGPoint(0, desiredHeight - bottomLeftCornerSize), new CGPoint(0, desiredHeight)); } else { path.AddLineTo(new CGPoint(0, desiredHeight)); } boxView.BackgroundColor.ToUIColor().SetFill(); path.Fill(); path.ClosePath(); context.AddPath(path.CGPath); context.Clip(); } } }
public static UIImage ToTransformedCorners(UIImage source, double topLeftCornerSize, double topRightCornerSize, double bottomLeftCornerSize, double bottomRightCornerSize, CornerTransformType cornersTransformType, double cropWidthRatio, double cropHeightRatio) { double sourceWidth = source.Size.Width; double sourceHeight = source.Size.Height; double desiredWidth = sourceWidth; double desiredHeight = sourceHeight; double desiredRatio = cropWidthRatio / cropHeightRatio; double currentRatio = sourceWidth / sourceHeight; if (currentRatio > desiredRatio) { desiredWidth = (cropWidthRatio * sourceHeight / cropHeightRatio); } else if (currentRatio < desiredRatio) { desiredHeight = (cropHeightRatio * sourceWidth / cropWidthRatio); } topLeftCornerSize = topLeftCornerSize * (desiredWidth + desiredHeight) / 2 / 100; topRightCornerSize = topRightCornerSize * (desiredWidth + desiredHeight) / 2 / 100; bottomLeftCornerSize = bottomLeftCornerSize * (desiredWidth + desiredHeight) / 2 / 100; bottomRightCornerSize = bottomRightCornerSize * (desiredWidth + desiredHeight) / 2 / 100; float cropX = (float)((sourceWidth - desiredWidth) / 2); float cropY = (float)((sourceHeight - desiredHeight) / 2); UIGraphics.BeginImageContextWithOptions(new CGSize(desiredWidth, desiredHeight), false, (nfloat)0.0); try { using (var context = UIGraphics.GetCurrentContext()) { context.BeginPath(); using (var path = new UIBezierPath()) { // TopLeft if (cornersTransformType.HasFlag(CornerTransformType.TopLeftCut)) { path.MoveTo(new CGPoint(0, topLeftCornerSize)); path.AddLineTo(new CGPoint(topLeftCornerSize, 0)); } else if (cornersTransformType.HasFlag(CornerTransformType.TopLeftRounded)) { path.MoveTo(new CGPoint(0, topLeftCornerSize)); path.AddQuadCurveToPoint(new CGPoint(topLeftCornerSize, 0), new CGPoint(0, 0)); } else { path.MoveTo(new CGPoint(0, 0)); } // TopRight if (cornersTransformType.HasFlag(CornerTransformType.TopRightCut)) { path.AddLineTo(new CGPoint(desiredWidth - topRightCornerSize, 0)); path.AddLineTo(new CGPoint(desiredWidth, topRightCornerSize)); } else if (cornersTransformType.HasFlag(CornerTransformType.TopRightRounded)) { path.AddLineTo(new CGPoint(desiredWidth - topRightCornerSize, 0)); path.AddQuadCurveToPoint(new CGPoint(desiredWidth, topRightCornerSize), new CGPoint(desiredWidth, 0)); } else { path.AddLineTo(new CGPoint(desiredWidth, 0)); } // BottomRight if (cornersTransformType.HasFlag(CornerTransformType.BottomRightCut)) { path.AddLineTo(new CGPoint(desiredWidth, desiredHeight - bottomRightCornerSize)); path.AddLineTo(new CGPoint(desiredWidth - bottomRightCornerSize, desiredHeight)); } else if (cornersTransformType.HasFlag(CornerTransformType.BottomRightRounded)) { path.AddLineTo(new CGPoint(desiredWidth, desiredHeight - bottomRightCornerSize)); path.AddQuadCurveToPoint(new CGPoint(desiredWidth - bottomRightCornerSize, desiredHeight), new CGPoint(desiredWidth, desiredHeight)); } else { path.AddLineTo(new CGPoint(desiredWidth, desiredHeight)); } // BottomLeft if (cornersTransformType.HasFlag(CornerTransformType.BottomLeftCut)) { path.AddLineTo(new CGPoint(bottomLeftCornerSize, desiredHeight)); path.AddLineTo(new CGPoint(0, desiredHeight - bottomLeftCornerSize)); } else if (cornersTransformType.HasFlag(CornerTransformType.BottomLeftRounded)) { path.AddLineTo(new CGPoint(bottomLeftCornerSize, desiredHeight)); path.AddQuadCurveToPoint(new CGPoint(0, desiredHeight - bottomLeftCornerSize), new CGPoint(0, desiredHeight)); } else { path.AddLineTo(new CGPoint(0, desiredHeight)); } path.ClosePath(); context.AddPath(path.CGPath); context.Clip(); } var drawRect = new CGRect(-cropX, -cropY, sourceWidth, sourceHeight); source.Draw(drawRect); var modifiedImage = UIGraphics.GetImageFromCurrentImageContext(); return(modifiedImage); } } finally { UIGraphics.EndImageContext(); } }
public override void CreatePath(Arc shape, CGRect bounds) { using (var path = new UIBezierPath()) { var arcHeightAbs = Math.Abs(shape.ArcHeight); switch (shape.Position) { case ShapePosition.Left: if (shape.IsCropInside) { path.MoveTo(new CGPoint(bounds.Width, 0)); path.AddLineTo(new CGPoint(0, 0)); path.AddQuadCurveToPoint(new CGPoint(0, bounds.Height), new CGPoint(arcHeightAbs * 2, bounds.Height / 2)); path.AddLineTo(new CGPoint(bounds.Width, bounds.Height)); path.ClosePath(); } else { path.MoveTo(new CGPoint(bounds.Width, 0)); path.AddLineTo(new CGPoint(arcHeightAbs, 0)); path.AddQuadCurveToPoint(new CGPoint(arcHeightAbs, bounds.Height), new CGPoint(-arcHeightAbs, bounds.Height / 2)); path.AddLineTo(new CGPoint(bounds.Width, bounds.Height)); path.ClosePath(); } break; case ShapePosition.Top: if (shape.IsCropInside) { path.MoveTo(new CGPoint(0, bounds.Height)); path.AddLineTo(new CGPoint(0, 0)); path.AddQuadCurveToPoint(new CGPoint(bounds.Width, 0), new CGPoint(bounds.Width / 2, 2 * arcHeightAbs)); path.AddLineTo(new CGPoint(bounds.Width, bounds.Height)); path.ClosePath(); } else { path.MoveTo(new CGPoint(0, arcHeightAbs)); path.AddQuadCurveToPoint(new CGPoint(bounds.Width, arcHeightAbs), new CGPoint(bounds.Width / 2, -arcHeightAbs)); path.AddLineTo(new CGPoint(bounds.Width, bounds.Height)); path.AddLineTo(new CGPoint(0, bounds.Height)); path.ClosePath(); } break; case ShapePosition.Right: if (shape.IsCropInside) { path.MoveTo(new CGPoint(0, 0)); path.AddLineTo(new CGPoint(bounds.Width, 0)); path.AddQuadCurveToPoint(new CGPoint(bounds.Width, bounds.Height), new CGPoint(bounds.Width - arcHeightAbs * 2, bounds.Height / 2)); path.AddLineTo(new CGPoint(0, bounds.Height)); path.ClosePath(); } else { path.MoveTo(new CGPoint(0, 0)); path.AddLineTo(new CGPoint(bounds.Width - arcHeightAbs, 0)); path.AddQuadCurveToPoint(new CGPoint(bounds.Width - arcHeightAbs, bounds.Height), new CGPoint(bounds.Width + arcHeightAbs, bounds.Height / 2)); path.AddLineTo(new CGPoint(0, bounds.Height)); path.ClosePath(); } break; case ShapePosition.Bottom: if (shape.IsCropInside) { path.MoveTo(new CGPoint(0, 0)); path.AddLineTo(new CGPoint(0, bounds.Height)); path.AddQuadCurveToPoint(new CGPoint(bounds.Width, bounds.Height), new CGPoint(bounds.Width / 2, bounds.Height - 2 * arcHeightAbs)); path.AddLineTo(new CGPoint(bounds.Width, 0)); path.ClosePath(); } else { path.MoveTo(new CGPoint(0, 0)); path.AddLineTo(new CGPoint(0, bounds.Height - arcHeightAbs)); path.AddQuadCurveToPoint(new CGPoint(bounds.Width, bounds.Height - arcHeightAbs), new CGPoint(bounds.Width / 2, bounds.Height + arcHeightAbs)); path.AddLineTo(new CGPoint(bounds.Width, 0)); path.ClosePath(); } break; } Path = path.CGPath; } }