在运行时更改列表框中显示的图像

时间:2011-09-08 10:04:13

标签: silverlight xaml windows-phone-7

我有一个Listbox绑定到一个Observable收集器,它根据其中的数据显示不同的图像,如下所示:

<phone:PhoneApplicationPage.Resources>
    <DataTemplate x:Key="PersonTemplate">
        <Grid>
            <Grid.ColumnDefinitions>
                <ColumnDefinition/>
                <ColumnDefinition/>
            </Grid.ColumnDefinitions>
            <Image Source="{Binding Path=ImagePath}"/>
            <TextBlock x:Name="id" Text="{Binding Id}" Grid.Column="1"/>
        </Grid>
    </DataTemplate>
</phone:PhoneApplicationPage.Resources>

我稍后再使用它:

<Grid x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0">
    <ListBox x:Name="personListBox" ItemTemplate="{StaticResource PersonTemplate}" 
             ItemsSource="{Binding PersonCollection}"/>
</Grid>

但是这意味着我已经将ImagePath属性创建为Person的一部分,这是不正确的,因为它是ViewModel的一部分而不是模型。是否有可能以某种方式将一个绑定添加到ViewModel中,我可以将Id传递给相应的图像更改?

编辑: 我实际上经过一些游戏后发现了一种方法,但我不确定这是否是一种明智的做法。我创建了一个ValueConverter并用它来改变值。

public class IdToImageConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        int id = (int)value;
        string img;

        switch (id)
        {
            case 1: img = @"Resources/Image/image1.png"; break;
            case 2: img = @"Resources/Image/image2.png"; break;
            default: img = @"Resources/Image/unknown.png"; break;
        }

        return img;
    }

然后这个有效:

<phone:PhoneApplicationPage.Resources>
    <local:IdToImageConverter x:Key="IdImageConverter"/>
    <DataTemplate x:Key="PersonTemplate">
        <Grid>
            <Grid.ColumnDefinitions>
                <ColumnDefinition/>
                <ColumnDefinition/>
            </Grid.ColumnDefinitions>
            <Image Source="{Binding Id,Converter={StaticResource IdImageConverter}}"/>
            <TextBlock x:Name="id" Text="{Binding Id}" Grid.Column="1"/>
        </Grid>
    </DataTemplate>
</phone:PhoneApplicationPage.Resources>

2 个答案:

答案 0 :(得分:1)

这是一项常见要求,也是编辑显示的特定IValueConverter编码的最常用解决方案。但是,由于它是一个常见的要求,最好创建一个可用于处理此问题的公共代码块。

请参阅此blog以获取常见转换器实现的示例(称为StringToObjectConverter,但不要让它让您失望)。

然后,您可以在视图中添加转换器: -

         <local:StringToObjectConverter x:Key="TypeToImageSource">
             <ResourceDictionary>
                 <BitmapImage UriSource="Resources/Image/image1.png" x:Key="1" />
                 <BitmapImage UriSource="Resources/Image/image2.png" x:Key="2" />
                 <BitmapImage UriSource="Resources/Image/unknown.png" x:Key="__default__" /> 
            </ResourceDictionary>
         </local:StringToObjectConverter>

答案 1 :(得分:0)

我不确定我是否理解你的问题。您是说ImagePath不是PersonCollection集合的属性,它属于其他一些集合吗?如果是这样,您可以通过指定DataContext来引用它,如下所示:

<phone:PhoneApplicationPage.Resources>
    <DataTemplate x:Key="PersonTemplate">
        <Grid>
            <Grid.ColumnDefinitions>
                <ColumnDefinition/>
                <ColumnDefinition/>
            </Grid.ColumnDefinitions>
            <Image DataContext="{Binding ImageCollection}" 
                   Source="{Binding Path=ImagePath}"/>
            <TextBlock x:Name="id" Text="{Binding Id}" Grid.Column="1"/>
        </Grid>
    </DataTemplate>
</phone:PhoneApplicationPage.Resources>

修改
重新阅读您的问题我认为您正在询问如何根据Id的{​​{1}}属性绑定所选的图像。为此,在ViewModel中创建一个名为PersonCollection的集合,其中包含属性ImageCollection,该集合包含与ImagePath列表中创建的Id列表对应的图像列表。 1}}并按上图所示绑定它。