You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WPF自定义CheckedListBox如何从外部动态设置内部CheckBox的Content

方案1:通过公开内容模板实现(最灵活,支持复杂内容展示)

步骤1:给CheckedListBox添加依赖属性

打开CheckedListBox.xaml.cs,添加以下代码:

using System.Windows;
using System.Windows.Data;

namespace AC.CodA.WPF.UserControls
{
    public partial class CheckedListBox : UserControl
    {
        // 注册CheckBox内容模板依赖属性
        public static readonly DependencyProperty CheckBoxContentTemplateProperty = DependencyProperty.Register(
            nameof(CheckBoxContentTemplate),
            typeof(DataTemplate),
            typeof(CheckedListBox),
            new PropertyMetadata(null));

        public DataTemplate CheckBoxContentTemplate
        {
            get => (DataTemplate)GetValue(CheckBoxContentTemplateProperty);
            set => SetValue(CheckBoxContentTemplateProperty, value);
        }

        public CheckedListBox()
        {
            InitializeComponent();
        }

        // 原有全选/反选逻辑保留即可
        private void DeSelectAll_Checked(object sender, RoutedEventArgs e)
        {
            // 原有逻辑
        }

        private void DeSelectAll_Unchecked(object sender, RoutedEventArgs e)
        {
            // 原有逻辑
        }
    }
}

步骤2:修改内部XAML的CheckBox绑定

修改CheckedListBox.xaml中ListBox的ItemTemplate部分:

<ListBox.ItemTemplate>
    <DataTemplate>
        <CheckBox IsChecked="{Binding IsChecked}" 
                  Content="{Binding}"
                  ContentTemplate="{Binding RelativeSource={RelativeSource AncestorType=user:CheckedListBox}, Path=CheckBoxContentTemplate}">
        </CheckBox>
    </DataTemplate>
</ListBox.ItemTemplate>

步骤3:外部使用方式

<user:CheckedListBox ItemsSource="{Binding ElementName=Root, Path=Companies}">
    <user:CheckedListBox.CheckBoxContentTemplate>
        <DataTemplate>
            <!-- 这里可以任意绑定CheckedListBoxItem<T>的属性,比如Item.Name、Item.Code都可以 -->
            <TextBlock Text="{Binding Item.Name}" />
        </DataTemplate>
    </user:CheckedListBox.CheckBoxContentTemplate>
</user:CheckedListBox>

如果要兼容旧逻辑,你可以给CheckBoxContentTemplate设置默认值,默认显示Item的ToString()结果,这样原有使用代码不需要修改。


方案2:实现简洁的绑定路径写法(符合你给出的示例用法)

如果想要直接用CheckBoxContent="{Binding Item.Name}"这种写法,可以通过注册Binding类型的依赖属性实现:

步骤1:注册依赖属性

public static readonly DependencyProperty CheckBoxContentProperty = DependencyProperty.Register(
    nameof(CheckBoxContent),
    typeof(BindingBase),
    typeof(CheckedListBox),
    new PropertyMetadata(default(BindingBase)));

public BindingBase CheckBoxContent
{
    get => (BindingBase)GetValue(CheckBoxContentProperty);
    set => SetValue(CheckBoxContentProperty, value);
}

步骤2:修改内部CheckBox的Content绑定

<CheckBox IsChecked="{Binding IsChecked}">
    <CheckBox.Content>
        <Binding RelativeSource="{RelativeSource AncestorType=user:CheckedListBox}" Path="CheckBoxContent.Path" />
    </CheckBox.Content>
</CheckBox>

步骤3:外部使用和你示例完全一致

<user:CheckedListBox ItemsSource="{Binding ElementName=Root, Path=Companies}" CheckBoxContent="{Binding Item.Name}" />

简化替代方案(无需修改控件)

如果暂时不想改用户控件代码,你可以直接给你的Company类重写ToString()方法:

public override string ToString()
{
    return Name;
}

这个方案的缺点是只能固定显示Name属性,无法灵活切换展示字段。

内容的提问来源于stack exchange,提问作者Krowi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.25 05:15:03