Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/297.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 设置BindableProperty时未触发OnPropertyChanged_C#_Xamarin_Xamarin.forms - Fatal编程技术网

C# 设置BindableProperty时未触发OnPropertyChanged

C# 设置BindableProperty时未触发OnPropertyChanged,c#,xamarin,xamarin.forms,C#,Xamarin,Xamarin.forms,我在Xamarin.Forms中的自定义ContentView中设置BindablePropertyIconName时遇到问题。它永远不会被设置并且保持为空。除了IconName之外,对每个属性都执行OnPropertyChanged方法。当我将类型从enum更改为字符串时,它会按预期工作。我错过了什么 需要使用OnPropertyChanged方法,否则将设置非属性并保持其默认值 <?xml version="1.0" encoding="UTF-8&quo

我在Xamarin.Forms中的自定义
ContentView
中设置
BindableProperty
IconName
时遇到问题。它永远不会被设置并且保持为空。除了
IconName
之外,对每个属性都执行
OnPropertyChanged
方法。当我将类型从enum更改为字符串时,它会按预期工作。我错过了什么

需要使用
OnPropertyChanged
方法,否则将设置非属性并保持其默认值

<?xml version="1.0" encoding="UTF-8" ?>
<ContentView
    x:Class="Peripass.Mobile.Framework.UIControls.PeripassIcon"
    xmlns="http://xamarin.com/schemas/2014/forms"
    xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
    xmlns:d="http://xamarin.com/schemas/2014/forms/design"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d">
  <ContentView.Resources>
  </ContentView.Resources>
  <ContentView.Content>
    <StackLayout HorizontalOptions="FillAndExpand" VerticalOptions="FillAndExpand">
      <Image>
        <Image.Source>
          <FontImageSource x:Name="_icon" Glyph="" Color="Black" Size="20" FontFamily="{OnPlatform  Android=PeripassIcon.ttf#}" />
        </Image.Source>
      </Image>
    </StackLayout>
  </ContentView.Content>
</ContentView>

您遇到的问题与以下事实有关:
OnPropertyChanged
仅在属性值更改时触发(设置它是不够的!

在代码中,您将默认值
IconName
设置为
IconType.NuclearExplosion
。稍后,当您调用所设置的控件时


它将
IconName
设置为默认值,再次。。。因此它的值实际上不会改变,因此不会触发
OnPropertyChanged


警告
话虽如此,我必须提到,您将在BindableProperties和视图中的对应项之间使用绑定的“正常”。例如,您可以将ContentView中FontImageSource中的Color属性值绑定到BindableProperty IconColor。有关详细信息,请参阅。

@Tijl.Reynhout,我很高兴它对您有所帮助。我用警告扩展了答案。请看一看,让我知道它是否对您有帮助…您的意思是像我的FontImageSource Color=“{Binding IconColor}”上这样,因为出于某种原因,这不起作用…如果您对如何做有疑问,请发布另一个问题,我将很乐意看一看:)我创建了关于此主题的另一个问题:)
using Xamarin.Forms;
using Xamarin.Forms.Xaml;

namespace Peripass.Mobile.Framework.UIControls
{
  [XamlCompilation(XamlCompilationOptions.Compile)]
  public partial class PeripassIcon : ContentView
  {

    public static readonly BindableProperty IconSizeProperty = BindableProperty.Create(nameof(IconSize), typeof(double), typeof(PeripassIcon), 26.0);
    public static readonly BindableProperty IconColorProperty = BindableProperty.Create(nameof(IconColor), typeof(Color), typeof(PeripassIcon), Color.White);
    public static readonly BindableProperty IconNameProperty = BindableProperty.Create(nameof(IconName), typeof(IconType), typeof(PeripassIcon), IconType.NuclearExplosion);

    public PeripassIcon()
    {
      InitializeComponent();
    }

    public IconType IconName
    {
      get => (IconType)GetValue(IconNameProperty);
      set => SetValue(IconNameProperty, value);
    }

    public double IconSize
    {
      get => (double)GetValue(IconSizeProperty);
      set => SetValue(IconSizeProperty, value);
    }

    public Color IconColor
    {
      get => (Color)GetValue(IconColorProperty);
      set => SetValue(IconColorProperty, value);
    }

    protected override void OnPropertyChanged(string propertyName = null)
    {
      base.OnPropertyChanged(propertyName);
      if (propertyName == IconNameProperty.PropertyName) {
        _icon.Glyph = $"&#x{(int)IconName:X4};";
      }
      if (propertyName == IconColorProperty.PropertyName) {
        _icon.Color = IconColor;
      }
      if (propertyName == IconSizeProperty.PropertyName) {
        _icon.Size = IconSize;
      }
    }
  }
}
<StackLayout Grid.Row="1" Grid.Column="0">
    <uiControls:PeripassIcon IconName="NuclearExplosion" IconColor="#EE4022" IconSize="85.5"/>
</StackLayout>