自学内容网 自学内容网

winform tagBox(标签框)

想做一个有下拉框的标签框类似于easyui tagbox这个插件:

一个combox,可以多选显示在输入框内。

便于查看、编辑。

找了下winform的自带控件,没有。查了查资料,琢磨着自己做一个,刚好放在和B/S端的easyui TagBox对应起来。

拆解一下这个tagbox :

多选combox。。。。但是combox 没办法放标签控件!!

所以索性把combox一起做了吧:

一个带边框的 panel = (内部一个后期放标签的panel+一个按钮Button)

还有一个陈列标签选项的listbox.

组合起来就是:tagBox = (大)panel+listbox。

好了,新建一个用户控件:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Data;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace ProjectTest
{
    public partial class TagBoxControl : UserControl
    {
        public CheckedListBox CheckedListBox { get; set; } //为选项赋值的接口
        public List<string> SelectedItems1 { get; set; }    //传递已选择项目的接口
        public Panel panel1 = new Panel();
        private Panel panel2 = new Panel();
        private int p1Height = 30;
        public int panel1Height
        {
            get{return p1Height;}
            set{
                p1Height = value;
                panel1.Height = value;
            }
        }
      
        public TagBoxControl()
        {
            SelectedItems1 = new List<string>();
            this.VerticalScroll.Enabled = true;
            this.AutoSize = true;
            Button btn = new Button();
            btn.Text = "v";
            btn.Width = 18;
            btn.FlatStyle = FlatStyle.Flat;
            btn.FlatAppearance.BorderSize = 0;
            btn.BackColor = Color.White;
            btn.Click += new EventHandler(btn_Click);
            btn.Dock = DockStyle.Right;
            btn.Margin = new Padding(0);

            panel2.BackColor = System.Drawing.SystemColors.Window;
            panel2.Dock = DockStyle.Fill;
            panel2.Margin = new Padding(0);
            panel2.AutoScroll = true;
            panel2.AutoScrollMinSize = new System.Drawing.Size(this.Width, this.panel2.Height-2);
            panel2.VerticalScroll.Visible = true;//竖的
            panel2.HorizontalScroll.Visible = false;//横的
           

            panel1.BorderStyle = BorderStyle.FixedSingle;
            panel1.Margin = new Padding(0);
            panel1.Dock = DockStyle.Top;
            panel1.Height = p1Height;
            panel1.BackColor = System.Drawing.SystemColors.Window;
            panel1.Controls.Add(panel2);
            panel1.Controls.Add(btn);

            CheckedListBox = new CheckedListBox();
            CheckedListBox.CheckOnClick = true;
            CheckedListBox.MultiColumn = true;
            CheckedListBox.Visible = false;
            CheckedListBox.HorizontalScrollbar = false;
            CheckedListBox.MouseUp += MouseUp1;
            CheckedListBox.MouseLeave += MouseLeave1;
            this.Controls.Add(panel1);
            InitializeComponent();
        }
        #region 订阅方法模块
        private void MouseLeave1(object sender, EventArgs e)  //鼠标离开CheckedListBox,隐藏CheckedListBox
        {
            CheckedListBox.Hide();
        }
        private void MouseUp1(object sender, EventArgs e)  //在CheckedListBox中选择后,在Panel2中显示相应项目
        {
            SetPanelData();
        }
        private void btn_Click(object sender, EventArgs e)
        {
            if (CheckedListBox.Visible)
            {
                return;
            }
            else
            {
                CheckedListBox.Width = panel1.Width;
                CheckedListBox.Size = new Size(panel1.Width, 100);
                CheckedListBox.Location = new Point(panel1.Left, panel1.Height);
                Controls.Add(CheckedListBox);
                CheckedListBox.Visible = true;
            }
        }

        #endregion
        private void SetPanelData() //设置panel数据
        {
            this.panel2.Controls.Clear();
            var list = new List<string>();
            foreach (var v in CheckedListBox.CheckedItems)  //将选择的项目加入list
            {
                list.Add(v.ToString());
            }

            Double tmp = (double)this.panel2.Width / (double)(100);//panel/btn.width  一行显示几个
            int colNum = (int)Math.Floor(tmp);  //向下取整
            tmp = (double)list.Count / (double)colNum; //选中个数/一行几个
            int rowNum = (int)Math.Ceiling(tmp);//几行
            for (int i = 0; i < list.Count; i++)
            {
                Button btn = new Button();
                if (i % 2 == 0)
                {
                    btn.BackColor = Color.LightGoldenrodYellow;
                }
                else
                {
                    btn.BackColor = Color.LightGreen;
                }

                btn.Click += new EventHandler(btnRemo_Click);
                btn.Width = 100;
                btn.Height = 25;
                btn.Text = list[i];
                btn.Location = new Point((i % colNum) * btn.Width, (i / colNum) * btn.Height);
                this.panel2.Controls.Add(btn);

            }
            SelectedItems1 = list;  //对外数据赋值
        }
        void btnRemo_Click(object sender, EventArgs e)//移除
        {
            Button btn = sender as Button;

            for (int i = 0; i < CheckedListBox.Items.Count; i++)
            {
                var tmp = CheckedListBox.Items[i].ToString();
                if (tmp == btn.Text)
                {
                    CheckedListBox.SetItemChecked(i, false);
                }
            }
            SetPanelData();
        }
        public void InitView() //初始页面
        {
            this.panel2.Controls.Clear();
            for (int i = 0; i < CheckedListBox.Items.Count; i++)
            {
                var tmp = this.SelectedItems1.Contains(CheckedListBox.Items[i].ToString());
                CheckedListBox.SetItemChecked(i, tmp);
            }
            SetPanelData();
        }
    }
}

直接上代码,怼上去就能用:

Form搞个测试:

 for (int i=0;i<100;i++)
            {
                this.tagBoxControl1.CheckedListBox.Items.Add("标签"+i);
            }

其中panel内的标签是按钮,设置了个点击事件,双击移除,可以获取所有选中的标签。基本功能没毛病,有需要的按照自己需求拿回去再改改,优化下直接用。

留个痕迹,指不定啥时候就能用得到了。


原文地址:https://blog.csdn.net/weixin_40899924/article/details/135694163

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!