ComboBox with empty item?

后端 未结 4 714
悲&欢浪女
悲&欢浪女 2020-11-29 23:00

Suppose we have a DataSource bind to a collection from Database. There is no null item of course. How to add a void item into a ComboBox, so that at first l

相关标签:
4条回答
  • 2020-11-29 23:28
    <UserControl.Resources>
        <CollectionViewSource x:Key="Modules" Source="{Binding Path=Modules}" />
    </UserControl.Resources>
    
    <abv:ComboBox SelectedIndex="0" IsNullable="True"
        SelectedItem="{Binding Path=SelectedModule, Mode=TwoWay}">
        <abv:ComboBox.ItemsSource>
            <CompositeCollection>
                <ComboBoxItem Content="{DynamicResource EmptyModuleComboBox}"/>
                <CollectionContainer Collection="{Binding Source={StaticResource Modules}}" />
            </CompositeCollection>
        </abv:ComboBox.ItemsSource>
    </abv:ComboBox>
    
    public class ComboBox : System.Windows.Controls.ComboBox
    {
        public static readonly DependencyProperty IsNullableProperty =
            DependencyProperty.Register("IsNullable", typeof(bool), typeof(ComboBox));
    
        public bool IsNullable
        {
            get { return (bool)GetValue(IsNullableProperty); }
            set { SetValue(IsNullableProperty, value); }
        }
    
        public ComboBox()
        {
            Loaded += ComboBox_Loaded;
        }
    
        void ComboBox_Loaded(object sender, RoutedEventArgs e)
        {
    
            if (IsNullable)
            {
                this.ItemContainerStyle = new Style();
    
                this.ItemContainerStyle.Setters.Add(new EventSetter()
                {
                    Event = ComboBoxItem.PreviewMouseUpEvent,
                    Handler = new MouseButtonEventHandler(cmbItem_PreviewMouseUp)
                });
            }
        }
    
        public void cmbItem_PreviewMouseUp(object sender, MouseButtonEventArgs e)
        {
            if (Items.IndexOf(sender as ComboBoxItem) == 0)
            {
                SelectedItem = null;
            }
        }
    }
    
    0 讨论(0)
  • 2020-11-29 23:29
    <ComboBox Name="myComboBox" Width="200" Background="White">    
        <ComboBox.ItemsSource>    
            <CompositeCollection>
               <ComboBoxItem IsEnabled="False" Foreground="Black">Select Item</ComboBoxItem>
               <CollectionContainer Collection="{Binding Source={StaticResource DataKey}}" />    
            </CompositeCollection>
        </ComboBox.ItemsSource>
    </ComboBox>
    

    EDIT

    As @surfen mentioned in comment, BindingProxy is workaround for the binding issue

    0 讨论(0)
  • 2020-11-29 23:33

    For binding on MVVM object:

                            <ComboBox Name="cbbFiltres" SelectedItem="{Binding ElmtInfo, Mode=TwoWay}" Height="26" MinWidth="90" SelectedIndex="0" SelectedValuePath="Id">
                            <ComboBox.Resources>
                                <CollectionViewSource x:Key="cvsFiltres" Source="{Binding Elmts.items}"/>
                            </ComboBox.Resources>
                            <ComboBox.ItemsSource>
                                <CompositeCollection>
                                    <model:tblFiltreChamps Desc="{x:Static resx:resMain.enumAucun}" Id="0"/>
                                    <CollectionContainer Collection="{Binding Source={StaticResource cvsFiltres}}" />
                                </CompositeCollection>
                            </ComboBox.ItemsSource>
                        </ComboBox>
    

    And for binding on :

    <Label Visibility="{Binding Path=SelectedValue, ElementName=cbbFiltres, Converter={StaticResource NullToVisibility}}" />
    

    And the generic converter :

        public class ConvNullToVisibility : IValueConverter {
        /// <summary>Convertisseur pour le Get.</summary>
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) {
            if (DesignerProperties.GetIsInDesignMode(new DependencyObject())) return Visibility.Visible; // Pour annuler l'effet dans le designer: http://stackoverflow.com/questions/33401900/wpf-detect-design-mode-in-a-converter
            return ((value == null) || (string.IsNullOrEmpty(value.ToString())) || (value.ToString() == "0")) ? Visibility.Collapsed : Visibility.Visible;
        }
    
        /// <summary>Convertisseur inverse, pour le Set (Binding).</summary>
        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) {
            if (value is Visibility) {
                return (((Visibility)value) == Visibility.Visible) ? true : false;
            } else return false;
        }
    }
    

    Just important to declare the SelectedValuePath in combobox. :-)

    0 讨论(0)
  • 2020-11-29 23:54

    Try the Mahapps combobox.

    xmlns:controls="http://metro.mahapps.com/winfx/xaml/controls"

      <ComboBox x:Name="bars"  **controls:TextBoxHelper.ClearTextButton="True"**
                  DisplayMemberPath="Name" 
                  Height="21" 
                  SelectedItem="{Binding Bar}"/>
    

    0 讨论(0)
提交回复
热议问题