简体   繁体   English

使用自定义渲染器强制重绘Xamarin.Forms视图

[英]Force redraw of Xamarin.Forms View with custom renderer

I have a visual element MyButton with a custom renderer implemented for iOS. 我有一个可视元素MyButton有一个为iOS实现的自定义渲染器。

Shared: 共享:

namespace RendererTest
{
    public class MyButton: Button
    {
        public Color BoundaryColor { get; set; }
    }

    public static class App
    {
        public static Page GetMainPage()
        {    
            var button = new MyButton { Text = "Click me!", BoundaryColor = Color.Red };
            button.Clicked += (sender, e) => (sender as MyButton).BoundaryColor = Color.Blue;
            return new ContentPage { Content = button };
        }
    }
}

iOS: iOS版:

[assembly:ExportRenderer(typeof(MyButton), typeof(MyButtonRenderer))]

namespace RendererTest.iOS
{
    public class MyButtonRenderer: ButtonRenderer
    {
        public override void Draw(RectangleF rect)
        {
            using (var context = UIGraphics.GetCurrentContext()) {
                context.SetFillColor(Element.BackgroundColor.ToCGColor());
                context.SetStrokeColor((Element as MyButton).BoundaryColor.ToCGColor());
                context.SetLineWidth(10);
                context.AddPath(CGPath.FromRect(Bounds));
                context.DrawPath(CGPathDrawingMode.FillStroke);
            }
        }
    }
}

When pressing the button, the red boundary should become blue. 按下按钮时,红色边界应变为蓝色。 Apparently the renderer does not notice the changed property. 显然渲染器没有注意到已更改的属性。 How can I trigger a redraw? 如何触发重绘?

(This example is for iOS. But my question applies to Android as well.) (此示例适用于iOS。但我的问题也适用于Android。)

First, turn you BoundaryColor into a bindable property. 首先,将BoundaryColor转换为可绑定属性。 That's not required, firing INPC event is enough, but then you can bind to it: 这不是必需的,触发INPC事件就足够了,但是你可以绑定它:

public static readonly BindableProperty BoundaryColorProperty =
    BindableProperty.Create ("BoundaryColor", typeof(Color), typeof(MyButton), Color.Default);

public Color BoundaryColor {
    get { return (Color)GetValue (BoudaryColorProperty); }
    set { SetValue (BoundaryColorProperty, value); }
}

then, in your renderer: 然后,在你的渲染器中:

protected override void OnElementPropertyChanged (object sender, PropertyChangedEventArgs e)
{
    base.OnElementPropertyChanged (sender, e);

    if (e.PropertyName == MyButton.BoundaryColorProperty.PropertyName)
        SetNeedsDisplay ();
}

Two modifications were required: 需要进行两项修改:

  1. Call OnPropertyChanged within the setter of the BoundaryColor property: BoundaryColor属性的setter中调用OnPropertyChanged

     public class MyButton: Button { Color boundaryColor = Color.Red; public Color BoundaryColor { get { return boundaryColor; } set { boundaryColor = value; OnPropertyChanged(); // <-- here } } } 
  2. Subscribe to the event within the OnElementChanged method of MyButtonRenderer : MyButtonRendererOnElementChanged方法中订阅事件:

     public class MyButtonRenderer: ButtonRenderer { protected override void OnElementChanged(ElementChangedEventArgs<Button> e) { base.OnElementChanged(e); Element.PropertyChanged += (s_, e_) => SetNeedsDisplay(); // <-- here } public override void Draw(RectangleF rect) { // ... } } 

Note: It seems to be important to subscribe within OnElementChanged and not the constructor. 注意:OnElementChanged订阅似乎很重要,而不是构造函数。 Otherwise a System.Reflection.TargetInvocationException is raised. 否则会引发System.Reflection.TargetInvocationException

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Xamarin.Forms中的条目自定义渲染器(为Android添加所有边框) - Entry Custom Renderer(add all borders for Android) in Xamarin.Forms xamarin.forms从自定义渲染器访问viewmodel属性 - xamarin.forms access viewmodel property from custom renderer Xamarin.Forms Timepicker IsVisible 属性与自定义呈现器 - Xamarin.Forms Timepicker IsVisible property vs. Custom Renderer 我想使用资源! (Xamarin.Forms的自定义渲染器) - I want to use Resource !! (Xamarin.Forms 's custom renderer) 在Xamarin Forms Custom Renderer中将Mapbox添加到Android视图 - Add Mapbox to Android View in Xamarin Forms Custom Renderer 为什么在Xamarin.forms的自定义渲染器中将ImeOptions设置为Next不能将我带到Android中的next字段 - Why is Setting ImeOptions to Next in custom renderer of Xamarin.forms not taking me to next field in Android 指定文字重力时,Android中的Xamarin.Forms自定义渲染器将停止工作 - Xamarin.Forms Custom Renderer in Android stops working when text gravity is specified 如何获得对从Xamarin.Forms中的自定义渲染器渲染的控件的引用? - How to get a reference to the control being rendered from a custom renderer in Xamarin.Forms? 如何使用自定义渲染器更改TableSection文本颜色 - Xamarin.Forms C# - How to change the TableSection text color with a custom renderer - Xamarin.Forms C# android [Xamarin.Forms] 中用于唯一角半径值的自定义帧渲染器 - Custom Frame renderer for unique corner radius values in android [Xamarin.Forms]
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM