WPF ComboBox 动态创建并动态显示数据库内容

实现动态创建的方法很多,我尝试了两种方法:

方法一,做一个模板选择器

根据class中的Type字段判断当前模板,动态添加到datagrid的column中。模板选择器代码如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Media;
//using System.Windows.Forms;

namespace x
{
    public class ValueSelector : DataTemplateSelector //模板选择器
    {
        public override DataTemplate SelectTemplate(object item, DependencyObject container)
        {
            DataTemplate dt = new DataTemplate();
            if (item != null && item is DataRec)
            {
                DataRec dataRec = item as DataRec;
                Window window = Application.Current.MainWindow;
                if (dataRec.Type.Equals("1"))
                {
                    FrameworkElementFactory comboBox = new FrameworkElementFactory(typeof(ComboBox)); //实例化下拉框控件
                    if (dataRec.Val.Equals("")) //如果当前数据为空,绑定list
                    {
                        comboBox.SetBinding(ComboBox.ItemsSourceProperty, new Binding()
                        {
                            Path = new PropertyPath("ValueList"),
                            Mode = BindingMode.TwoWay,
                            UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged
                        });
                        comboBox.SetValue(ComboBox.SelectedIndexProperty, 0); //默认显示请选择
                        comboBox.SetValue(ComboBox.NameProperty, "comboBox_val");
                        //comboBox.SetValue(ComboBox.SelectionChangedEvent, new EventHandler(ComboBox_val_SelectedIndexChanged))
                    }
                    else //绑定当前值,用户不可再选择
                    {
                        comboBox.SetBinding(ComboBox.TextProperty, new Binding()
                        {
                            Path = new PropertyPath("Val"),
                            Mode = BindingMode.TwoWay,
                            UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged
                        });
                        //comboBox.SetValue(ComboBox.NameProperty, "comboBox_val"); 
                    }
                    //HyperlinkStyle
                    comboBox.SetValue(ComboBox.StyleProperty, Application.Current.Resources["AduComboBox"]); //style
                    //comboBox.SetValue(ComboBox.MarginProperty, new Thickness(5));
                    //comboBox.SetValue(ComboBox.BackgroundProperty, new SolidColorBrush(Colors.Red));
                    //comboBox.SetValue(ComboBox.ForegroundProperty, Brushes.DarkBlue);
                    //comboBox.SetValue(ComboBox.BorderThicknessProperty, new Thickness(1));
                    //comboBox.SetValue(ComboBox.SelectionChangedEvent)
                    //System.Windows.Forms.ComboBox.hand
                    dt.VisualTree = comboBox;
                }
                else
                {
                    FrameworkElementFactory txtBox = new FrameworkElementFactory(typeof(TextBox)); //实例化文本控件
                    txtBox.SetBinding(TextBox.TextProperty, new Binding()
                    {
                        Path = new PropertyPath("Val"),
                        Mode = BindingMode.TwoWay,
                        UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged
                    });
                    //HyperlinkStyle
                    //textBlock.SetValue(TextBlock.StyleProperty, ); //style
                    txtBox.SetValue(TextBox.ForegroundProperty, new SolidColorBrush((Color)ColorConverter.ConvertFromString("#FF134584")));
                    txtBox.SetValue(TextBox.BackgroundProperty, new SolidColorBrush(Colors.Transparent));
                    txtBox.SetValue(TextBox.NameProperty, "textBox_val");
                    dt.VisualTree = txtBox;
                }
            }
            return dt;
        }

        //private void ComboBox_val_SelectedIndexChanged(object sender, System.EventArgs e)
        //{
        //    ComboBox comboBox = (ComboBox)sender;
        //    string selectedEmployee = (string)ComboBox_val.SelectedItem;
        //}
    }
}

前端是这样:

<DataGridTemplateColumn Width="150" Header="x" CellTemplateSelector="{StaticResource selector}" IsReadOnly="False"/>

这个方法在添加事件、更新样式方面我个人觉得不是很灵活,在需要添加事件时没找到合适办法弃用。

方法二,利用Visibility属性实现动态下拉框显示,实现起来更复杂一些。

<Page.Resources>
<!--#region 动态可视-->
        <local:TextConverter x:Key="TextCvn"/>
        <local:ComboBoxConverter x:Key="ComboBoxCvn"/>
        <DataTemplate x:Key="GridType">
            <Grid  x:Name="TypeGrid">
                <ComboBox SelectionChanged="ComboBox_val_SelectionChanged" ItemsSource="{Binding ValueList}" SelectedItem="{Binding Val}" x:Name="comboBox_val" Visibility="{Binding Type,Converter={StaticResource ComboBoxCvn}}" Width="130" Style="{StaticResource AduComboBox}" HorizontalAlignment="Left">

                </ComboBox>
                <TextBox x:Name="textBox_val" Background="Transparent" Foreground="{StaticResource BlueColor2}" Text="{Binding Val}" Width="130" Visibility="{Binding Type,Converter={StaticResource TextCvn}}" HorizontalAlignment="Left" ></TextBox>
            </Grid>
        </DataTemplate>
 </Page.Resources>

<DataGridTemplateColumn Width="150" Header="x" CellTemplate="{StaticResource GridType}" IsReadOnly="False"/>

封装进celltemplate中,后端需要实现接口:

public class ComboBoxConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            if (value.ToString() != "1")
            {
                return Visibility.Hidden;
            }
            else
            {
                return Visibility.Visible;
            }

        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            return value;
        }
    }

如果下拉框显示的内容需要记忆在数据库,注意绑定selectedsource,绑定不好使的原因可能是itemsource和它不属于同一个对象。

在这个方法中,下拉框绑定事件和正常方法是一样的。

这个技术路线交MVVC。。。貌似

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值