【问题标题】:How to bind an event to the property IsVisible of a ContentView?如何将事件绑定到 ContentView 的 IsVisible 属性?
【发布时间】:2021-02-21 14:37:49
【问题描述】:

我在 Xamarin.Forms 中创建了一个控件,允许我显示一个可重复使用的错误视图,带有ContentView 和@ 987654324@动画。

我的视图包含:Lottie 动画、2 个Labels(标题和描述)和一个“重试”Button

Lotie 动画是这样设置的,因为我希望动画只显示一次:

<lottie:AnimationView
    x:Name="networkErrorAnimationView"
    Animation="resource://lottie_error_no_network.json?assembly=ShellAppSample"
    AnimationSource="EmbeddedResource"
    BackgroundColor="Transparent"
    AutoPlay="True"
    HeightRequest="200" WidthRequest="200"
    VerticalOptions="Center" HorizontalOptions="Center"
    Clicked="NetworkErrorAnimationView_Clicked"/>

问题是当我从父视图显示错误控件时动画已经播放了:

<ctrl:ErrorView IsVisible="{Binding ShowErrorView, Converter={StaticResource BoolToVisibilityConverter}}"
                Title="{Binding ErrorTitle}"
                Description="{Binding ErrorDescription}"
                ErrorKind="{Binding ErrorKind}"
                RetryButtonCommand="{Binding RetryCommand}" />

我想知道是否有办法将事件绑定到控件的 IsVisible 属性,以在此时重新启动相应的动画? p>

【问题讨论】:

标签: events xamarin.forms controls lottie propertychanged


【解决方案1】:

您可以为您的ctrl:ErrorView 添加一个属性,然后在开始时将AutoPlay 设置为false。

这是ctrl:ErrorView的布局。

<ContentView xmlns="http://xamarin.com/schemas/2014/forms" 
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:forms="clr-namespace:Lottie.Forms;assembly=Lottie.Forms" 
              x:Name="MyErrorView"
             x:Class="App13.ErrorView">
    <ContentView.Content>
      <StackLayout>
          

            <forms:AnimationView
                x:Name="animationView"
                Animation="1.json"
                AnimationSource="AssetOrBundle"
                RepeatCount="1"
                AutoPlay="False"
                WidthRequest="100"
                HeightRequest="100"/>
            <Label x:Name="title" Text="test" />
            <Label Text="Hello Xamarin.Forms!" />
        </StackLayout>
  </ContentView.Content>
</ContentView>

这是ctrl:ErrorView 的后台代码。然后我添加IsStartAnimationView 属性。如果IsStartAnimationView 的绑定值为真。然后播放动画。

   public partial class ErrorView : ContentView
    {

     

        public string TitleText
        {
            get { return (string)GetValue(TitleTextProperty); }
            set { SetValue(TitleTextProperty, value); }
        }
        public static readonly BindableProperty TitleTextProperty = BindableProperty.Create(
                                                          propertyName: "TitleText",
                                                          returnType: typeof(string),
                                                          declaringType: typeof(ErrorView),
                                                          defaultValue: "",
                                                          defaultBindingMode: BindingMode.TwoWay,
                                                          propertyChanged: TitleTextPropertyChanged);

        private static void TitleTextPropertyChanged(BindableObject bindable, object oldValue, object newValue)
        {
           // var control = (ErrorView)bindable;
          //  control.title.Text = newValue.ToString();
        }


        public bool IsStartAnimationView
        {
            get { return (bool)GetValue(IsStartAnimationViewProperty); }
            set { SetValue(IsStartAnimationViewProperty, value); }
        }
        public static readonly BindableProperty IsStartAnimationViewProperty = BindableProperty.Create(
                                                          propertyName: "IsStartAnimationView",
                                                          returnType: typeof(bool),
                                                          declaringType: typeof(ErrorView),
                                                          defaultValue: false,
                                                          defaultBindingMode: BindingMode.TwoWay,
                                                          propertyChanged: IsStartAnimationViewChanged);

        private static void IsStartAnimationViewChanged(BindableObject bindable, object oldValue, object newValue)
        {
            // throw new NotImplementedException();
            var MyValue =(bool) newValue;
            if (MyValue == true) {
                 var control = (ErrorView)bindable;
                  control.animationView.PlayAnimation();
            }

        }

        public ErrorView()
        {
            InitializeComponent();

            this.Content.BindingContext = this;
        }
    }
}

在 Contentpage 中使用此控件。

 <ctrl:ErrorView IsVisible="{Binding Isfavourite}" TitleText="{Binding Name}" IsStartAnimationView="{Binding IsStart}" ></ctrl:ErrorView>

我使用按钮点击事件进行测试。

 private async void Button_Clicked(object sender, System.EventArgs e)
        {
           
                 myViewModel.IsStart = !myViewModel.IsStart;
        }

这是正在运行的 gif。

【讨论】:

  • 如果回复有帮助,请采纳为答案(点击该答案左上角的“✔”),对有类似问题的其他人有帮助
  • 嗨@Leon Lu,我已经实现了一个给我的更轻的解决方案。感谢您的宝贵时间。
【解决方案2】:

解决方案是在另一个forum 上给我的。我只需要在控件的代码后面添加这段代码:

protected override void OnPropertyChanged([CallerMemberName] string propertyName = null)
{
    base.OnPropertyChanged(propertyName);
    if (propertyName == nameof(IsVisible))
    {
        if (this.IsVisible)
        {
            networkErrorAnimationView.PlayAnimation();
        }
        else
        {
                networkErrorAnimationView.StopAnimation();
        }
    }
}

【讨论】:

  • 这和我的回答一样!请仔细看答案
猜你喜欢
  • 2018-08-08
  • 1970-01-01
  • 2012-06-10
  • 1970-01-01
  • 2020-12-01
  • 2021-04-27
  • 2020-11-28
  • 1970-01-01
  • 2022-06-20
相关资源
最近更新 更多