通过单击整个项目来检查WPF中的ckeckbox

时间:2019-04-17 09:18:42

标签: c# wpf checkbox

我的客户遇到CheckBoxListBox的大小的问题。我同意,它很小,有时很难检查。

我试图找到一种使CheckBox更大的方法,但是我发现它很复杂(并且需要使用Blend,我不想使用它)。

我想做的是单击整个项目时检查CheckBox

[]一些文字

在此示例中-在“某些文本”上或项目内部的任何位置。现在,我必须在CheckBox内单击以进行检查。

我动态生成了CheckBoxes

我对此控件的xamls如下:

     <ListBox Name="restoredDBsListBox" ItemsSource="{Binding ProperlyRestoredDatabases}"  Grid.ColumnSpan="2" HorizontalAlignment="Left" Height="170" Margin="34,160,0,0" VerticalAlignment="Top" Width="276" SelectionMode="Extended">
        <ListBox.ItemTemplate>
            <DataTemplate>
                <StackPanel Orientation="Horizontal" >
                    <CheckBox Name="check" IsChecked="{Binding IsChecked, Mode=TwoWay}" Margin="3" VerticalAlignment="Center"/>
                    <ContentPresenter Content="{Binding Value}" Margin="1"/>                       
                </StackPanel>
            </DataTemplate>
        </ListBox.ItemTemplate>
    </ListBox>

和我的ViewModel:

    /// <summary>
    /// Defines the _properlyRestoredDatabases
    /// </summary>
    private CheckableObservableCollection<string> _properlyRestoredDatabases;

    /// <summary>
    /// Gets or sets the ProperlyRestoredDatabases
    /// </summary>
    public CheckableObservableCollection<string> ProperlyRestoredDatabases
    {
        get { return _properlyRestoredDatabases; }
        set
        {
            _properlyRestoredDatabases = value;
            OnPropertyChanged("ProperlyRestoredDatabases");
        }
    }

CheckableObservableCollection类:

  public class CheckableObservableCollection<T> : ObservableCollection<CheckedWrapper<T>>
{
    private ListCollectionView _selected;

    public CheckableObservableCollection()
    {
        _selected = new ListCollectionView(this);
        _selected.Filter = delegate (object checkObject) {
            return ((CheckedWrapper<T>)checkObject).IsChecked;
        };
    }

    public void Add(T item)
    {
        this.Add(new CheckedWrapper<T>(this) { Value = item });
    }

    public ICollectionView CheckedItems
    {
        get { return _selected; }
    }

    internal void Refresh()
    {
        _selected.Refresh();
    }
}

和CheckedWrapper

 public class CheckedWrapper<T> : INotifyPropertyChanged
{
    private readonly CheckableObservableCollection<T> _parent;

    public CheckedWrapper(CheckableObservableCollection<T> parent)
    {
        _parent = parent;
    }

    private T _value;

    public T Value
    {
        get { return _value; }
        set
        {
            _value = value;
            OnPropertyChanged("Value");
        }
    }

    private bool _isChecked;

    public bool IsChecked
    {
        get { return _isChecked; }
        set
        {
            _isChecked = value;
            CheckChanged();
            OnPropertyChanged("IsChecked");
        }
    }

    private void CheckChanged()
    {
        _parent.Refresh();
    }

    public event PropertyChangedEventHandler PropertyChanged;

    protected virtual void OnPropertyChanged(string propertyName)
    {
        PropertyChangedEventHandler pceh = PropertyChanged;
        if (pceh != null)
        {
            pceh(this, new PropertyChangedEventArgs(propertyName));
        }
    }
}

1 个答案:

答案 0 :(得分:1)

CheckBox具有Content属性,因此没有理由使用单独的ContentPresenter。如果您还添加了ItemContainerStyle来水平拉伸ListBoxItem容器,则可以通过单击行上的任意位置来选中和取消选中CheckBox

<ListBox Name="restoredDBsListBox" ItemsSource="{Binding ProperlyRestoredDatabases}"  Grid.ColumnSpan="2" HorizontalAlignment="Left" Height="170" Margin="34,160,0,0" VerticalAlignment="Top" Width="276" SelectionMode="Extended">
    <ListBox.ItemContainerStyle>
        <Style TargetType="ListBoxItem">
            <Setter Property="HorizontalContentAlignment" Value="Stretch" />
        </Style>
    </ListBox.ItemContainerStyle>
    <ListBox.ItemTemplate>
        <DataTemplate>
            <CheckBox Name="check" IsChecked="{Binding IsChecked, Mode=TwoWay}"
                    Content="{Binding Value}"
                    Margin="3" 
                    VerticalAlignment="Center"/>
        </DataTemplate>
    </ListBox.ItemTemplate>
</ListBox>