WPF:禁用组合框中的所选项目

时间:2018-07-02 19:15:59

标签: wpf xaml

我已经3个小时都无法浏览帖子了。我是WPF的新手,并在下面创建了ComboBox:

enter image description here

很遗憾,我无法禁用所选项目的突出显示。有人有可行的解决方案吗?

代码

            <StackPanel Grid.Column="1" 
                        Margin="800,0,0,0"
                        Width="135"
                        HorizontalAlignment="Right"
                        VerticalAlignment="Center">
                <ComboBox Name="LangComboBox"
                          IsEditable="True"
                          IsReadOnly="True"
                          Text="Select Language">
                    <ComboBoxItem>English</ComboBoxItem>
                    <ComboBoxItem>Spanish</ComboBoxItem>
                    <ComboBoxItem>Both</ComboBoxItem>
                </ComboBox>
            </StackPanel>

1 个答案:

答案 0 :(得分:1)

首先,我想澄清一下我的想法是具有建设性 answer ,并希望传播良好的编程文化。 我们所有人也总是要学习编程! 如果您不知道某个主题,那么最好从一本好书或该平台的官方文档开始学习。

那就是让我们继续解决问题的一些可能方法。

首先,之所以选择组合框,是因为组合框的基本模板,我邀请您查看:https://msdn.microsoft.com/library/ms752094(v=vs.85).aspx

您正在寻找的是组合框的另一种行为:

  1. 允许显示默认值
  2. 一旦选择了元素,其内部的文本将不加下划线

第一种方法可以基于 ComboBox模板:组合框的构建方式是:如果可编辑,则其模板 包含一个名为 PART_EditableTextBox 的文本框 通过对文本框进行操作(例如将其禁用),可以获得所需的结果。

这可以通过不同的方式实现:

  1. 插入代码隐藏事件处理程序,该事件处理程序在加载组合框时禁用文本框
  2. 具有附加行为,可让您向控件(https://www.codeproject.com/Articles/28959/Introduction-to-Attached-Behaviors-in-WPF)添加自定义行为
  3. 编写一个自定义控件,该控件可能会在组合框中插入水印类型的部分

现在考虑实现最快的第一种方法,因此代码如下:

<ComboBox Name="LangComboBox" IsEditable="True" IsReadOnly="True" 
                          Loaded="LangComboBox_Loaded"
                          Text="Select language">
    <ComboBoxItem Content="English"/>
    <ComboBoxItem Content="Spanish"/>
    <ComboBoxItem Content="Both"/>
</ComboBox>

在后面的代码中:

private void LangComboBox_Loaded(object sender, RoutedEventArgs e)
{
    ComboBox ctrl = (ComboBox)sender;
    TextBox Editable_tb = (TextBox)ctrl.Template.FindName("PART_EditableTextBox", ctrl);
    if (Editable_tb != null)
    {
        // Disable the textbox
        Editable_tb.IsEnabled = false;
    }
}

但是,这种方法具有缺点,其中一个事实是,如果用户要取消选择/重置组合的值,则无法做到这一点。

因此,您可以使用 MVVM 模式遵循另一条路径。

来自Web编程世界,您应该了解 MVC 模式,在WPF中,最常见的模式是 MVVM或模型-视图-ViewModel 两种模式之间有共同点,我邀请您来看一下它们:Mvvm Pattern

您可以使用将在组合中托管的模型创建一个类,例如:

public class Language
    {
        public int Id { get; set; }
        public string Description { get; set; }

        public Language(int id, string desc)
        {
            this.Id = id;
            this.Description = desc;
        }
    }

    public class YourDataContext : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        private List<Language> _Languages;
        public List<Language> Languages
        {
            get
            {
                return _Languages;
            }
            set
            {
                _Languages = value;
                OnPropertyChanged("Languages");
            }
        }

        private Language _selectedLanguage;
        public Language SelectedLanguage
        {
            get
            {
                return _selectedLanguage;
            }
            set
            {
                _selectedLanguage = value;
                OnPropertyChanged("SelectedLanguage");

            }
        }

        public YourDataContext()
        {
            // Initialization of languages
            Languages = new List<Language>();

            Languages.Add(new Language(0, "None - Select a Language"));

            Languages.Add(new Language(1, "English"));

            Languages.Add(new Language(2, "Spanish"));

            Languages.Add(new Language(3, "Both"));

            SelectedLanguage = Languages.First();
        }

        protected virtual void OnPropertyChanged(string propertyName)
        {
            PropertyChangedEventHandler handler = PropertyChanged;
            if (handler != null) handler(this, new PropertyChangedEventArgs(propertyName));
        }
        // some other properties and commands
    }


    // Your Window class

    public MainWindow()
    {
        InitializeComponent();
        var dc = new YourDataContext();
        DataContext = dc;


    }


<ComboBox ItemsSource="{Binding Languages}"
                          DisplayMemberPath="Description"
                          SelectedItem="{Binding SelectedLanguage}"/>

请注意,现在组合框不再可编辑,并且可以重置选择。

您可以使用模型管理选择:

if(dc.SelectedLanguage.Id == 0)
    {
        //No language selected
    }

有很多方法可以实现您想要的,我希望这可以给您一些好的起点。

对每个人都很好的编程。