自定义 ListView 条目的背景/前景能力

3
我有以下的功能代码,可以将GridViewColumns绑定到自定义类的数据:
<ListView Name="lv">
    <ListView.View>
        <GridView>
            <GridViewColumn Header="First" DisplayMemberBinding="{Binding lvi.firstName}"/>
            <GridViewColumn Header="Last" DisplayMemberBinding="{Binding lvi.lastName}"/>
        </GridView>
    </ListView.View>
</ListView>

public class LVItemBox {
    public LVItem lvi { get; set; }
}
public class LVItem : INotifyPropertyChanged {
    private string _firstName;
    private string _lastName;
    public string firstName {
        get { return _firstName; }
        set { SetField(ref _firstName, value); }
    }
    public string lastName {
        get { return _lastName; }
        set { SetField(ref _lastName, value); }
    }
    public event PropertyChangedEventHandler PropertyChanged;
    public virtual void OnPropertyChanged(string propertyName) {PropertyChangedEventHandler handler = PropertyChanged;
        if (handler != null) handler(this, new PropertyChangedEventArgs(propertyName));
    }
    public bool SetField<T>(ref T field, T value, [CallerMemberName] string propertyName = null) { if (EqualityComparer<T>.Default.Equals(field, value)) return false;
        field = value;
        OnPropertyChanged(propertyName);
        return true;
    }
}
public partial class MainWindow : Window {
    public MainWindow() {
        InitializeComponent();
        LVItem lvi1 = new LVItem {firstName = "John", lastName = "Doe"};
        LVItem lvi2 = new LVItem {firstName = "Jane", lastName = "Smith"};
        lv.Items.Add(new LVItemBox {lvi = lvi1});
        lv.Items.Add(new LVItemBox {lvi = lvi2});
    }
}

我的困境是我想在LVItemBox中实现背景/前景Brush的能力,然而如果我让LVItemBox扩展Control,改变Background/Foreground就没有效果:

public class LVItemBox : Control {
    public LVItem lvi { get; set; }            // data displays
}
...
...
private void changeBackground(object sender, EventArgs e) {
    LVItemBox lvib = (LVItemBox)lv.Items[0];
    lvib.Background = Brushes.Black;           // doesn't work
}

此外,如果我扩展ListViewItem而不是Control,则可以使背景更改工作,但数据绑定将不再起作用。
public class LVItemBox : ListViewItem {
    public LVItem lvi { get; set; }            // data doesn't display
}
...
...
private void changeBackground(object sender, EventArgs e) {
    LVItemBox lvib = (LVItemBox)lv.Items[0];
    lvib.Background = Brushes.Black;           // works
}

你知道如何在 LVItemBox 中实现前景/背景能力吗?


你可以将GridViewColumns的CellTemplate设置为一个包含合适UI元素的DataTemplate,它会绑定到项目类的前景和背景属性,而不是使用DisplayMemberBinding。 - Clemens
当您扩展Control时,我无法看到任何INPC在setter中被触发。此外,使用Control会破坏MvvM,而且您还没有向我们展示如何在XAML中绑定前景或背景。@Clemens 在这里是正确的,您应该使用DataTemplate。并且,可以考虑在WPF中使用Style,这样结构会更加清晰可读。 - XAMlMAX
1个回答

2
Control继承可以运行,如果你在你的XAML中添加以下ItemContainerStyle
<ListView Name="lv">
    <ListView.View>
        <GridView>
            <GridViewColumn Header="First" DisplayMemberBinding="{Binding lvi.firstName}"/>
            <GridViewColumn Header="Last" DisplayMemberBinding="{Binding lvi.lastName}"/>
        </GridView>
    </ListView.View>
    <ListView.ItemContainerStyle>
        <Style TargetType="ListViewItem">
            <Setter Property="Background" Value="{Binding Background}" />
        </Style>
    </ListView.ItemContainerStyle>
</ListView>

@archer:这个方案解决了你的问题吗?请记得接受答案。 - mm8

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接