如何将组合框数据源绑定到Windows窗体中的窗体/列表框?

时间:2016-02-13 10:17:17

标签: winforms combobox

Combo box datasource as form/listbox

我想在单击组合框时将表单作为数据源。我怎么能实现这一点。请提出建议。

1 个答案:

答案 0 :(得分:0)

我创建了一个继承自标准Windows Forms ComboBox的PopupComboBox类。它有一个Title属性,您可以设置在单击组合时将在弹出窗口中使用的属性。

public class PopupComboBox : ComboBox
    {
        private string title;
        public string Title
        {
            get { return this.title; }
            set { this.title = value; }
        }
        public PopupComboBox() : base()
        {

        }

        public PopupComboBox (string title)
            : base()
        {
            this.title = title;
        }

        protected override void OnMouseClick(MouseEventArgs e)
        {
            base.OnMouseClick(e);

            // Show the popup form
            var popup = new SelectItemForm(this.title, this);
            var result = popup.ShowDialog(this);

            if (result == DialogResult.OK)
            {
                // Select this item in the ComboBox
                SelectedIndex = this.FindStringExact(popup.SelectedDisplay);
            }
        }
    }

当您单击组合时,将出现一个弹出窗体(SelectItemForm下面的源代码)。它使用父PopupComboBox的DataSource,ValueMember和DisplayMember来填充ListView以及组合中的项目列表。当您单击“确定”时,它会将所选项目保存在SelectedValue和SelectedDisplay属性中,以便我们可以在表单关闭时在ComboBox中选择该项目。

The popup form

public partial class SelectItemForm : Form
    {
        public object SelectedValue { get; private set; }
        public string SelectedDisplay { get; private set; }

        public SelectItemForm(string title, PopupComboBox parent)
            :base()
        {
            InitializeComponent();

            this.Text = title;

            // Add items to the list
            foreach (var item in parent.Items)
            {
                // Get the display and value member properties for this combo box
                // and use them for the Code/Name columns in the popup form
                var props = item.GetType().GetProperties();
                var code = props.Where(p => p.Name == parent.ValueMember).Single().GetValue(item);
                var name = props.Where(p => p.Name == parent.DisplayMember).Single().GetValue(item);

                listView.Items.Add(new ListViewItem(
                    new string[] { code.ToString(), name.ToString() }));
            }
        }

        private void btnOk_Click(object sender, EventArgs e)
        {
            if (listView.SelectedItems != null && listView.SelectedItems.Count > 0)
            {
                SelectedValue = listView.SelectedItems[0].Text;
                SelectedDisplay = listView.SelectedItems[0].SubItems[1].Text;

                DialogResult = DialogResult.OK;
            }
            else
            {
                MessageBox.Show(this, "Select an item first", "Error", MessageBoxButtons.OK, MessageBoxIcon.Exclamation);
            }
        }

        private void btnCancel_Click(object sender, EventArgs e)
        {
            DialogResult = DialogResult.Cancel;
        }
    }

以下是表单的设计器部分,您可以在其中查看我为ListView看到的更改的属性:

partial class SelectItemForm
    {
        /// <summary>
        /// Required designer variable.
        /// </summary>
        private System.ComponentModel.IContainer components = null;

        /// <summary>
        /// Clean up any resources being used.
        /// </summary>
        /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
        protected override void Dispose(bool disposing)
        {
            if (disposing && (components != null))
            {
                components.Dispose();
            }
            base.Dispose(disposing);
        }

        #region Windows Form Designer generated code

        /// <summary>
        /// Required method for Designer support - do not modify
        /// the contents of this method with the code editor.
        /// </summary>
        private void InitializeComponent()
        {
            this.listView = new System.Windows.Forms.ListView();
            this.btnOk = new System.Windows.Forms.Button();
            this.btnCancel = new System.Windows.Forms.Button();
            this.Code = ((System.Windows.Forms.ColumnHeader)(new System.Windows.Forms.ColumnHeader()));
            this.Value = ((System.Windows.Forms.ColumnHeader)(new System.Windows.Forms.ColumnHeader()));
            this.SuspendLayout();
            // 
            // listView
            // 
            this.listView.Anchor = ((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom) 
            | System.Windows.Forms.AnchorStyles.Left) 
            | System.Windows.Forms.AnchorStyles.Right)));
            this.listView.Columns.AddRange(new System.Windows.Forms.ColumnHeader[] {
            this.Code,
            this.Value});
            this.listView.FullRowSelect = true;
            this.listView.GridLines = true;
            this.listView.Location = new System.Drawing.Point(3, 3);
            this.listView.MultiSelect = false;
            this.listView.Name = "listView";
            this.listView.Size = new System.Drawing.Size(432, 170);
            this.listView.TabIndex = 0;
            this.listView.UseCompatibleStateImageBehavior = false;
            this.listView.View = System.Windows.Forms.View.Details;
            // 
            // btnOk
            // 
            this.btnOk.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
            this.btnOk.Location = new System.Drawing.Point(272, 179);
            this.btnOk.Name = "btnOk";
            this.btnOk.Size = new System.Drawing.Size(75, 23);
            this.btnOk.TabIndex = 1;
            this.btnOk.Text = "OK";
            this.btnOk.UseVisualStyleBackColor = true;
            this.btnOk.Click += new System.EventHandler(this.btnOk_Click);
            // 
            // btnCancel
            // 
            this.btnCancel.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
            this.btnCancel.Location = new System.Drawing.Point(353, 179);
            this.btnCancel.Name = "btnCancel";
            this.btnCancel.Size = new System.Drawing.Size(75, 23);
            this.btnCancel.TabIndex = 2;
            this.btnCancel.Text = "Cancel";
            this.btnCancel.UseVisualStyleBackColor = true;
            this.btnCancel.Click += new System.EventHandler(this.btnCancel_Click);
            // 
            // Code
            // 
            this.Code.Text = "Code";
            this.Code.Width = 108;
            // 
            // Value
            // 
            this.Value.Text = "Name";
            this.Value.Width = 296;
            // 
            // SelectItemForm
            // 
            this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
            this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
            this.ClientSize = new System.Drawing.Size(440, 214);
            this.Controls.Add(this.btnCancel);
            this.Controls.Add(this.btnOk);
            this.Controls.Add(this.listView);
            this.MaximizeBox = false;
            this.MinimizeBox = false;
            this.Name = "SelectItemForm";
            this.StartPosition = System.Windows.Forms.FormStartPosition.CenterParent;
            this.Text = "Title";
            this.ResumeLayout(false);

        }

        #endregion

        private System.Windows.Forms.ListView listView;
        private System.Windows.Forms.Button btnOk;
        private System.Windows.Forms.Button btnCancel;
        private System.Windows.Forms.ColumnHeader Code;
        private System.Windows.Forms.ColumnHeader Value;
    }

我还创建了一个小型测试表单,您可以使用一小部分产品测试PopupComboBox的功能。您需要将PopupComboBox添加到设计器中的表单中,并将其命名为comboPopup。

public partial class TestForm : Form
    {
        public class Product
        {
            public string Code { get; set; }
            public string Name { get; set; }
        }

        public TestForm()
        {
            InitializeComponent();
        }

        private void TestForm_Load(object sender, EventArgs e)
        {
            var products = new List<Product>();
            products.Add(new Product { Code = "0001", Name = "Coca Cola" });
            products.Add(new Product { Code = "0002", Name = "Mountain Dew" });
            products.Add(new Product { Code = "0003", Name = "Sprite Zero" });

            comboPopup.DataSource = products;
            comboPopup.DisplayMember = "Name";
            comboPopup.ValueMember = "Code";

        }
    }