diff --git a/Xamarin.Forms.Core/Frame.cs b/Xamarin.Forms.Core/Frame.cs index a298c0f0a..bb35f147d 100644 --- a/Xamarin.Forms.Core/Frame.cs +++ b/Xamarin.Forms.Core/Frame.cs @@ -11,6 +11,8 @@ namespace Xamarin.Forms public static readonly BindableProperty HasShadowProperty = BindableProperty.Create("HasShadow", typeof(bool), typeof(Frame), true); + public static readonly BindableProperty CornerRadiusProperty = BindableProperty.Create(nameof(CornerRadius), typeof(float), typeof(Frame), -1.0f); + readonly Lazy> _platformConfigurationRegistry; public Frame() @@ -31,6 +33,12 @@ namespace Xamarin.Forms set { SetValue(OutlineColorProperty, value); } } + public float CornerRadius + { + get { return (float)GetValue(CornerRadiusProperty); } + set { SetValue(CornerRadiusProperty, value); } + } + public IPlatformElementConfiguration On() where T : IConfigPlatform { return _platformConfigurationRegistry.Value.On(); diff --git a/Xamarin.Forms.Platform.Android/AppCompat/FrameRenderer.cs b/Xamarin.Forms.Platform.Android/AppCompat/FrameRenderer.cs index 3ca14eaeb..1092f7671 100644 --- a/Xamarin.Forms.Platform.Android/AppCompat/FrameRenderer.cs +++ b/Xamarin.Forms.Platform.Android/AppCompat/FrameRenderer.cs @@ -20,6 +20,7 @@ namespace Xamarin.Forms.Platform.Android.AppCompat readonly TapGestureHandler _tapGestureHandler; float _defaultElevation = -1f; + float _defaultCornerRadius = -1f; bool _clickable; bool _disposed; @@ -184,6 +185,7 @@ namespace Xamarin.Forms.Platform.Android.AppCompat e.NewElement.PropertyChanged += OnElementPropertyChanged; UpdateShadow(); UpdateBackgroundColor(); + UpdateCornerRadius(); SubscribeGestureRecognizers(e.NewElement); } } @@ -215,6 +217,8 @@ namespace Xamarin.Forms.Platform.Android.AppCompat UpdateShadow(); else if (e.PropertyName == VisualElement.BackgroundColorProperty.PropertyName) UpdateBackgroundColor(); + else if (e.PropertyName == Frame.CornerRadiusProperty.PropertyName) + UpdateCornerRadius(); } void SubscribeGestureRecognizers(VisualElement element) @@ -286,5 +290,22 @@ namespace Xamarin.Forms.Platform.Android.AppCompat else CardElevation = 0f; } + + void UpdateCornerRadius() + { + if (_defaultCornerRadius == -1f) + { + _defaultCornerRadius = Radius; + } + + float cornerRadius = Element.CornerRadius; + + if (cornerRadius == -1f) + cornerRadius = _defaultCornerRadius; + else + cornerRadius = Context.ToPixels(cornerRadius); + + Radius = cornerRadius; + } } } \ No newline at end of file diff --git a/Xamarin.Forms.Platform.Android/Renderers/FrameRenderer.cs b/Xamarin.Forms.Platform.Android/Renderers/FrameRenderer.cs index f24c8d45c..ca020ad26 100644 --- a/Xamarin.Forms.Platform.Android/Renderers/FrameRenderer.cs +++ b/Xamarin.Forms.Platform.Android/Renderers/FrameRenderer.cs @@ -27,7 +27,10 @@ namespace Xamarin.Forms.Platform.Android base.OnElementChanged(e); if (e.NewElement != null && e.OldElement == null) + { UpdateBackground(); + UpdateCornerRadius(); + } } void UpdateBackground() @@ -35,6 +38,11 @@ namespace Xamarin.Forms.Platform.Android this.SetBackground(new FrameDrawable(Element)); } + void UpdateCornerRadius() + { + this.SetBackground(new FrameDrawable(Element)); + } + class FrameDrawable : Drawable { readonly Frame _frame; @@ -127,14 +135,13 @@ namespace Xamarin.Forms.Platform.Android using (var canvas = new ACanvas(bitmap)) { - DrawBackground(canvas, width, height, pressed); - DrawOutline(canvas, width, height); + DrawCanvas(canvas, width, height, pressed); } return bitmap; } - void DrawBackground(ACanvas canvas, int width, int height, bool pressed) + void DrawBackground(ACanvas canvas, int width, int height, float cornerRadius, bool pressed) { using (var paint = new Paint { AntiAlias = true }) using (var path = new Path()) @@ -142,8 +149,8 @@ namespace Xamarin.Forms.Platform.Android using (Paint.Style style = Paint.Style.Fill) using (var rect = new RectF(0, 0, width, height)) { - float rx = Forms.Context.ToPixels(5); - float ry = Forms.Context.ToPixels(5); + float rx = Forms.Context.ToPixels(cornerRadius); + float ry = Forms.Context.ToPixels(cornerRadius); path.AddRoundRect(rect, rx, ry, direction); global::Android.Graphics.Color color = _frame.BackgroundColor.ToAndroid(); @@ -155,7 +162,7 @@ namespace Xamarin.Forms.Platform.Android } } - void DrawOutline(ACanvas canvas, int width, int height) + void DrawOutline(ACanvas canvas, int width, int height, float cornerRadius) { using (var paint = new Paint { AntiAlias = true }) using (var path = new Path()) @@ -163,8 +170,8 @@ namespace Xamarin.Forms.Platform.Android using (Paint.Style style = Paint.Style.Stroke) using (var rect = new RectF(0, 0, width, height)) { - float rx = Forms.Context.ToPixels(5); - float ry = Forms.Context.ToPixels(5); + float rx = Forms.Context.ToPixels(cornerRadius); + float ry = Forms.Context.ToPixels(cornerRadius); path.AddRoundRect(rect, rx, ry, direction); paint.StrokeWidth = 1; @@ -177,19 +184,33 @@ namespace Xamarin.Forms.Platform.Android void FrameOnPropertyChanged(object sender, PropertyChangedEventArgs e) { - if (e.PropertyName == VisualElement.BackgroundColorProperty.PropertyName || e.PropertyName == Frame.OutlineColorProperty.PropertyName) + if (e.PropertyName == VisualElement.BackgroundColorProperty.PropertyName || + e.PropertyName == Frame.OutlineColorProperty.PropertyName || + e.PropertyName == Frame.CornerRadiusProperty.PropertyName) { using (var canvas = new ACanvas(_normalBitmap)) { int width = Bounds.Width(); int height = Bounds.Height(); canvas.DrawColor(global::Android.Graphics.Color.Black, PorterDuff.Mode.Clear); - DrawBackground(canvas, width, height, false); - DrawOutline(canvas, width, height); + DrawCanvas(canvas, width, height, false); } InvalidateSelf(); } } + + void DrawCanvas(ACanvas canvas, int width, int height, bool pressed) + { + float cornerRadius = _frame.CornerRadius; + + if (cornerRadius == -1f) + cornerRadius = 5f; // default corner radius + else + cornerRadius = Forms.Context.ToPixels(cornerRadius); + + DrawBackground(canvas, width, height, cornerRadius, pressed); + DrawOutline(canvas, width, height, cornerRadius); + } } } } \ No newline at end of file diff --git a/Xamarin.Forms.Platform.WP8/FrameRenderer.cs b/Xamarin.Forms.Platform.WP8/FrameRenderer.cs index 00472161d..2149033b1 100644 --- a/Xamarin.Forms.Platform.WP8/FrameRenderer.cs +++ b/Xamarin.Forms.Platform.WP8/FrameRenderer.cs @@ -19,6 +19,7 @@ namespace Xamarin.Forms.Platform.WinPhone PackChild(); UpdateBorder(); + UpdateCornerRadius(); } protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e) @@ -29,6 +30,8 @@ namespace Xamarin.Forms.Platform.WinPhone PackChild(); else if (e.PropertyName == Frame.OutlineColorProperty.PropertyName || e.PropertyName == Frame.HasShadowProperty.PropertyName) UpdateBorder(); + else if (e.PropertyName == Frame.CornerRadiusProperty.PropertyName) + UpdateCornerRadius(); } void PackChild() @@ -44,7 +47,6 @@ namespace Xamarin.Forms.Platform.WinPhone void UpdateBorder() { - Control.CornerRadius = new CornerRadius(5); if (Element.OutlineColor != Color.Default) { Control.BorderBrush = Element.OutlineColor.ToBrush(); @@ -53,5 +55,15 @@ namespace Xamarin.Forms.Platform.WinPhone else Control.BorderBrush = new Color(0, 0, 0, 0).ToBrush(); } + + void UpdateCornerRadius() + { + float cornerRadius = Element.CornerRadius; + + if (cornerRadius == -1f) + cornerRadius = 5f; // default corner radius + + Control.CornerRadius = new CornerRadius(cornerRadius); + } } } \ No newline at end of file diff --git a/Xamarin.Forms.Platform.WinRT/FrameRenderer.cs b/Xamarin.Forms.Platform.WinRT/FrameRenderer.cs index 7dcac4352..3eb48d03f 100644 --- a/Xamarin.Forms.Platform.WinRT/FrameRenderer.cs +++ b/Xamarin.Forms.Platform.WinRT/FrameRenderer.cs @@ -28,6 +28,7 @@ namespace Xamarin.Forms.Platform.WinRT PackChild(); UpdateBorder(); + UpdateCornerRadius(); } } @@ -43,6 +44,10 @@ namespace Xamarin.Forms.Platform.WinRT { UpdateBorder(); } + else if (e.PropertyName == Frame.CornerRadiusProperty.PropertyName) + { + UpdateCornerRadius(); + } } void PackChild() @@ -56,7 +61,6 @@ namespace Xamarin.Forms.Platform.WinRT void UpdateBorder() { - Control.CornerRadius = new CornerRadius(5); if (Element.OutlineColor != Color.Default) { Control.BorderBrush = Element.OutlineColor.ToBrush(); @@ -67,5 +71,15 @@ namespace Xamarin.Forms.Platform.WinRT Control.BorderBrush = new Color(0, 0, 0, 0).ToBrush(); } } + + void UpdateCornerRadius() + { + float cornerRadius = Element.CornerRadius; + + if (cornerRadius == -1f) + cornerRadius = 5f; // default corner radius + + Control.CornerRadius = new CornerRadius(cornerRadius); + } } } \ No newline at end of file diff --git a/Xamarin.Forms.Platform.iOS/Renderers/FrameRenderer.cs b/Xamarin.Forms.Platform.iOS/Renderers/FrameRenderer.cs index 3d2213f4c..3914cf304 100644 --- a/Xamarin.Forms.Platform.iOS/Renderers/FrameRenderer.cs +++ b/Xamarin.Forms.Platform.iOS/Renderers/FrameRenderer.cs @@ -25,7 +25,13 @@ namespace Xamarin.Forms.Platform.iOS void SetupLayer() { - Layer.CornerRadius = 5; + float cornerRadius = Element.CornerRadius; + + if (cornerRadius == -1f) + cornerRadius = 5f; // default corner radius + + Layer.CornerRadius = cornerRadius; + if (Element.BackgroundColor == Color.Default) Layer.BackgroundColor = UIColor.White.CGColor; else