繁体   English   中英

如何实现“Xamarin.Forms DataTemplateView 中的两个可绑定属性”?

[英]How to implement 'Xamarin.Forms Two bindable properties inside a DataTemplateView'?

我正在研究这种代码

我的图片资源 class

[ContentProperty(nameof(Source))]
class ImageResourceExtension : IMarkupExtension
{
  public string Source { get; set; }
  public object ProvideValue(IServiceProvider serviceProvider)
  {
    var newImageSource = ImageSource.FromResource(Source, typeof(ImageResourceExtension).GetTypeInfo().Assembly);
    return newImageSource;
  }
}

我的清单型号 class

class ListModel
{
   public string IconSource { get; set; }
   public string IconPath { get; set; }
}

我的 MyViewModel class

class MyViewModel : INotifyPropertyChanged
{
   public List<Models.ListModel> MyListModel { get; }
   public Command MyListCommand { get; }
   public MyViewModel()
   {
      MyListModel = new List<Models.ListModel>()
      {
         new Models.ListModel(){ IconSource="https://example.com/image1",IconPath="MyImage1.jpg"},
         new Models.ListModel(){ IconSource="https://example.com/image2",IconPath="MyImage2.jpg"}
      };
      MyListCommand = new Command(OnListClicked);
   }

   private async void OnListClicked(object value)
   {
      string valueString = value as string;
      await Launcher.OpenAsync(valueString);
   }
 }

我的看法 class

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
    xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
    xmlns:images="clr-namespace:MyProject.Images"
    xmlns:models="clr-namespace:MyProject.Models"
    xmlns:viewModels="clr-namespace:MyProject.ViewModels"

...

   <ContentPage.BindingContext>
      <viewModels:MyViewModel/>
   </ContentPage.BindingContext>

   <ContentPage.Content>
     <StackLayout BindableLayout.ItemsSource="{Binding MyListModel}">
       <BindableLayout.ItemTemplate>
         <DataTemplate> <!-- line{setup path} -->
           <Image Source="{images:ImageResource Source={Binding Source={RelativeSource AncestorType={x:Type viewModels:MyListModel}}, Path=ImageSource}}">
             <Image.GestureRecognizers>
               <TapGestureRecognizer 
                 NumberOfTapsRequired="1" 
                 Command="{Binding Source={RelativeSource AncestorType={x:Type viewModels:MyListModel}}, Path=MyListCommand}" 
                 CommandParameter="{Binding ImagePath}"/>
             </Image.GestureRecognizers>
           </Image>
         </DataTemplate>
       </BindableLayout.ItemTemplate>
     </StackLayout>
   </ContentPage.Content>

我的问题是如何在以下line: {setup path}

如果你能解决这个问题,我真的很感激。 谢谢你。

编辑:我忘记在我的共享代码中添加我的图像是Embedded resource

您可以使用值转换器来实现此 function。

假设您的图像放置在 xamarin 表单项目(例如MyFormDemo )的文件夹Images中。

1.创建EmbeddedToImageSourceConverter.cs

public class EmbeddedToImageSourceConverter: IValueConverter
{


    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        string ResourceId = value.ToString();
        if (String.IsNullOrWhiteSpace(ResourceId))
            return null;
        return ImageSource.FromResource(ResourceId);
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

2.在MyViewModel.cs IconPath (添加MyFormDemo.Images. ):

       public MyViewModel()
    {
        MyListModel = new List<ListModel>()
  {
     new ListModel(){ IconSource="https://example.com/image1",IconPath="MyFormDemo.Images.cherry.png"},
     new ListModel(){ IconSource="https://example.com/image2",IconPath="MyFormDemo.Images.love.png"}
  };
        MyListCommand = new Command(OnListClicked);
    }

3.为 class ListModel接口INotifyPropertyChanged

  public class ListModel: INotifyPropertyChanged
{
    public string IconSource { get; set; }
    //public string IconPath { get; set; }

    string _iconPath;
    public string IconPath
    {
        set { SetProperty(ref _iconPath, value); }

        get { return _iconPath; }
    }


    bool SetProperty<T>(ref T storage, T value, [CallerMemberName] string propertyName = null)
    {
        if (Object.Equals(storage, value))
            return false;

        storage = value;
        OnPropertyChanged(propertyName);
        return true;
    }

    protected void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }

    public event PropertyChangedEventHandler PropertyChanged;
}

4.在您页面的xaml中:

<ContentPage.Resources>
    <MyFormDemo:EmbeddedToImageSourceConverter x:Key="converter">
    </MyFormDemo:EmbeddedToImageSourceConverter>
</ContentPage.Resources>

<ContentPage.BindingContext>
    <viewmodel:MyViewModel></viewmodel:MyViewModel>
</ContentPage.BindingContext>

<ContentPage.Content>
    <StackLayout BindableLayout.ItemsSource="{Binding MyListModel}">
        <BindableLayout.ItemTemplate>
            <DataTemplate>

                <!-- line{setup path} -->
                <Image Source="{Binding IconPath, Converter={StaticResource converter}}"  WidthRequest="60" HeightRequest=" 60" BackgroundColor="Gray">

                </Image>


            </DataTemplate>
        </BindableLayout.ItemTemplate>
    </StackLayout>
</ContentPage.Content>

暂无
暂无

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

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM