• c# 自定义多选下拉列表2


    以下为工作中遇到的,备注一下

    先需要几个辅助类

      1 #region GripBounds
      2 
      3 using System.Drawing;
      4 internal struct GripBounds
      5 {
      6     private const int GripSize = 6;
      7     private const int CornerGripSize = GripSize << 1;
      8 
      9     public GripBounds(Rectangle clientRectangle)
     10     {
     11         this.clientRectangle = clientRectangle;
     12     }
     13 
     14     private Rectangle clientRectangle;
     15     public Rectangle ClientRectangle
     16     {
     17         get { return clientRectangle; }
     18         //set { clientRectangle = value; }
     19     }
     20 
     21     public Rectangle Bottom
     22     {
     23         get
     24         {
     25             Rectangle rect = ClientRectangle;
     26             rect.Y = rect.Bottom - GripSize + 1;
     27             rect.Height = GripSize;
     28             return rect;
     29         }
     30     }
     31 
     32     public Rectangle BottomRight
     33     {
     34         get
     35         {
     36             Rectangle rect = ClientRectangle;
     37             rect.Y = rect.Bottom - CornerGripSize + 1;
     38             rect.Height = CornerGripSize;
     39             rect.X = rect.Width - CornerGripSize + 1;
     40             rect.Width = CornerGripSize;
     41             return rect;
     42         }
     43     }
     44 
     45     public Rectangle Top
     46     {
     47         get
     48         {
     49             Rectangle rect = ClientRectangle;
     50             rect.Height = GripSize;
     51             return rect;
     52         }
     53     }
     54 
     55     public Rectangle TopRight
     56     {
     57         get
     58         {
     59             Rectangle rect = ClientRectangle;
     60             rect.Height = CornerGripSize;
     61             rect.X = rect.Width - CornerGripSize + 1;
     62             rect.Width = CornerGripSize;
     63             return rect;
     64         }
     65     }
     66 
     67     public Rectangle Left
     68     {
     69         get
     70         {
     71             Rectangle rect = ClientRectangle;
     72             rect.Width = GripSize;
     73             return rect;
     74         }
     75     }
     76 
     77     public Rectangle BottomLeft
     78     {
     79         get
     80         {
     81             Rectangle rect = ClientRectangle;
     82             rect.Width = CornerGripSize;
     83             rect.Y = rect.Height - CornerGripSize + 1;
     84             rect.Height = CornerGripSize;
     85             return rect;
     86         }
     87     }
     88 
     89     public Rectangle Right
     90     {
     91         get
     92         {
     93             Rectangle rect = ClientRectangle;
     94             rect.X = rect.Right - GripSize + 1;
     95             rect.Width = GripSize;
     96             return rect;
     97         }
     98     }
     99 
    100     public Rectangle TopLeft
    101     {
    102         get
    103         {
    104             Rectangle rect = ClientRectangle;
    105             rect.Width = CornerGripSize;
    106             rect.Height = CornerGripSize;
    107             return rect;
    108         }
    109     }
    110 }
    111 
    112 #endregion
    View Code
      1 #region UnsafeMethods
      2 
      3 using System;
      4 using System.Drawing;
      5 using System.Runtime.InteropServices;
      6 internal class UnsafeMethods
      7 {
      8     public static readonly IntPtr TRUE = new IntPtr(1);
      9     public static readonly IntPtr FALSE = new IntPtr(0);
     10 
     11     public const int WM_LBUTTONDOWN = 0x201;
     12     public const int WM_RBUTTONDOWN = 0x204;
     13     public const int WM_MBUTTONDOWN = 0x207;
     14     public const int WM_NCLBUTTONDOWN = 0x0A1;
     15     public const int WM_NCRBUTTONDOWN = 0x0A4;
     16     public const int WM_NCMBUTTONDOWN = 0x0A7;
     17     public const int WM_NCCALCSIZE = 0x0083;
     18     public const int WM_NCHITTEST = 0x0084;
     19     public const int WM_NCPAINT = 0x0085;
     20     public const int WM_NCACTIVATE = 0x0086;
     21     public const int WM_MOUSELEAVE = 0x02A3;
     22     public const int WS_EX_NOACTIVATE = 0x08000000;
     23     public const int HTTRANSPARENT = -1;
     24     public const int HTLEFT = 10;
     25     public const int HTRIGHT = 11;
     26     public const int HTTOP = 12;
     27     public const int HTTOPLEFT = 13;
     28     public const int HTTOPRIGHT = 14;
     29     public const int HTBOTTOM = 15;
     30     public const int HTBOTTOMLEFT = 16;
     31     public const int HTBOTTOMRIGHT = 17;
     32     public const int WM_USER = 0x0400;
     33     public const int WM_REFLECT = WM_USER + 0x1C00;
     34     public const int WM_COMMAND = 0x0111;
     35     public const int CBN_DROPDOWN = 7;
     36     public const int WM_GETMINMAXINFO = 0x0024;
     37 
     38     public enum TrackerEventFlags : uint
     39     {
     40         TME_HOVER = 0x00000001,
     41         TME_LEAVE = 0x00000002,
     42         TME_QUERY = 0x40000000,
     43         TME_CANCEL = 0x80000000
     44     }
     45 
     46     [DllImport("user32.dll")]
     47     public static extern IntPtr GetWindowDC(IntPtr hWnd);
     48 
     49     [DllImport("user32.dll")]
     50     public static extern int ReleaseDC(IntPtr hwnd, IntPtr hDC);
     51 
     52     [DllImport("user32")]
     53     public static extern bool TrackMouseEvent(ref TRACKMOUSEEVENT lpEventTrack);
     54 
     55     [DllImport("user32.dll")]
     56     public static extern bool SendMessage(IntPtr hWnd, int Msg, IntPtr wParam, IntPtr lParam);
     57 
     58     internal static int HIWORD(int n)
     59     {
     60         return (n >> 16) & 0xffff;
     61     }
     62 
     63     internal static int HIWORD(IntPtr n)
     64     {
     65         return HIWORD(unchecked((int)(long)n));
     66     }
     67 
     68     internal static int LOWORD(int n)
     69     {
     70         return n & 0xffff;
     71     }
     72 
     73     internal static int LOWORD(IntPtr n)
     74     {
     75         return LOWORD(unchecked((int)(long)n));
     76     }
     77 
     78     [StructLayout(LayoutKind.Sequential)]
     79     internal struct TRACKMOUSEEVENT
     80     {
     81         public uint cbSize;
     82         public uint dwFlags;
     83         public IntPtr hwndTrack;
     84         public uint dwHoverTime;
     85     }
     86 
     87     [StructLayout(LayoutKind.Sequential)]
     88     internal struct MINMAXINFO
     89     {
     90         public Point reserved;
     91         public Size maxSize;
     92         public Point maxPosition;
     93         public Size minTrackSize;
     94         public Size maxTrackSize;
     95     }
     96 
     97     #region RECT structure
     98 
     99     [StructLayout(LayoutKind.Sequential)]
    100     internal struct RECT
    101     {
    102         public int left;
    103         public int top;
    104         public int right;
    105         public int bottom;
    106 
    107         public RECT(int left, int top, int right, int bottom)
    108         {
    109             this.left = left;
    110             this.top = top;
    111             this.right = right;
    112             this.bottom = bottom;
    113         }
    114 
    115         public Rectangle Rect
    116         {
    117             get
    118             {
    119                 return new Rectangle(
    120                     this.left,
    121                     this.top,
    122                     this.right - this.left,
    123                     this.bottom - this.top);
    124             }
    125         }
    126 
    127         public static RECT FromXYWH(int x, int y, int width, int height)
    128         {
    129             return new RECT(x,
    130                             y,
    131                             x + width,
    132                             y + height);
    133         }
    134 
    135         public static RECT FromRectangle(Rectangle rect)
    136         {
    137             return new RECT(rect.Left,
    138                              rect.Top,
    139                              rect.Right,
    140                              rect.Bottom);
    141         }
    142     }
    143 
    144     #endregion RECT structure
    145 
    146     #region WINDOWPOS
    147 
    148     [StructLayout(LayoutKind.Sequential)]
    149     internal struct WINDOWPOS
    150     {
    151         internal IntPtr hwnd;
    152         internal IntPtr hWndInsertAfter;
    153         internal int x;
    154         internal int y;
    155         internal int cx;
    156         internal int cy;
    157         internal uint flags;
    158     }
    159     #endregion
    160 
    161     #region NCCALCSIZE_PARAMS
    162     //http://msdn.microsoft.com/library/default.asp?url=/library/en-us/winui/winui/windowsuserinterface/windowing/windows/windowreference/windowstructures/nccalcsize_params.asp
    163     [StructLayout(LayoutKind.Sequential)]
    164     public struct NCCALCSIZE_PARAMS
    165     {
    166         /// <summary>
    167         /// Contains the new coordinates of a window that has been moved or resized, that is, it is the proposed new window coordinates.
    168         /// </summary>
    169         public RECT rectProposed;
    170         /// <summary>
    171         /// Contains the coordinates of the window before it was moved or resized.
    172         /// </summary>
    173         public RECT rectBeforeMove;
    174         /// <summary>
    175         /// Contains the coordinates of the window's client area before the window was moved or resized.
    176         /// </summary>
    177         public RECT rectClientBeforeMove;
    178         /// <summary>
    179         /// Pointer to a WINDOWPOS structure that contains the size and position values specified in the operation that moved or resized the window.
    180         /// </summary>
    181         public WINDOWPOS lpPos;
    182     }
    183 
    184     #endregion
    185 }
    186 
    187 #endregion
    View Code
      1 using System;
      2 using System.Collections.Generic;
      3 using System.ComponentModel;
      4 using System.Data;
      5 using System.Drawing;
      6 using System.Drawing.Drawing2D;
      7 using System.Text;
      8 using System.Windows.Forms;
      9 using System.Security.Permissions;
     10 using System.Runtime.InteropServices;
     11 using VS = System.Windows.Forms.VisualStyles;
     12 
     13 /*
     14 <li>Base class for custom tooltips.</li>
     15 <li>Office-2007-like tooltip class.</li>
     16 */
     17 namespace ZhuoYueE.Bpc.Controls
     18 {
     19     /// <summary>
     20     /// Represents a pop-up window.
     21     /// </summary>
     22     [ToolboxItem(false)]
     23     public partial class PopupForm : ToolStripDropDown
     24     {
     25         #region " Fields & Properties "
     26 
     27         private Control content;
     28         /// <summary>
     29         /// Gets the content of the pop-up.
     30         /// </summary>
     31         public Control Content
     32         {
     33             get { return content; }
     34         }
     35 
     36         private bool fade;
     37         /// <summary>
     38         /// Gets a value indicating whether the <see cref="PopupControl.Popup"/> uses the fade effect.
     39         /// </summary>
     40         /// <value><c>true</c> if pop-up uses the fade effect; otherwise, <c>false</c>.</value>
     41         /// <remarks>To use the fade effect, the FocusOnOpen property also has to be set to <c>true</c>.</remarks>
     42         public bool UseFadeEffect
     43         {
     44             get { return fade; }
     45             set
     46             {
     47                 if (fade == value) return;
     48                 fade = value;
     49             }
     50         }
     51 
     52         private bool focusOnOpen = true;
     53         /// <summary>
     54         /// Gets or sets a value indicating whether the content should receive the focus after the pop-up has been opened.
     55         /// </summary>
     56         /// <value><c>true</c> if the content should be focused after the pop-up has been opened; otherwise, <c>false</c>.</value>
     57         /// <remarks>If the FocusOnOpen property is set to <c>false</c>, then pop-up cannot use the fade effect.</remarks>
     58         public bool FocusOnOpen
     59         {
     60             get { return focusOnOpen; }
     61             set { focusOnOpen = value; }
     62         }
     63 
     64         private bool acceptAlt = true;
     65         /// <summary>
     66         /// Gets or sets a value indicating whether presing the alt key should close the pop-up.
     67         /// </summary>
     68         /// <value><c>true</c> if presing the alt key does not close the pop-up; otherwise, <c>false</c>.</value>
     69         public bool AcceptAlt
     70         {
     71             get { return acceptAlt; }
     72             set { acceptAlt = value; }
     73         }
     74 
     75         private PopupForm ownerPopup;
     76         private PopupForm childPopup;
     77 
     78         private bool _resizable;
     79         private bool resizable;
     80         /// <summary>
     81         /// Gets or sets a value indicating whether the <see cref="PopupControl.Popup" /> is resizable.
     82         /// </summary>
     83         /// <value><c>true</c> if resizable; otherwise, <c>false</c>.</value>
     84         public bool Resizable
     85         {
     86             get { return resizable && _resizable; }
     87             set { resizable = value; }
     88         }
     89 
     90         private ToolStripControlHost host;
     91 
     92         private Size minSize;
     93         /// <summary>
     94         /// Gets or sets a minimum size of the pop-up.
     95         /// </summary>
     96         /// <returns>An ordered pair of type <see cref="T:System.Drawing.Size" /> representing the width and height of a rectangle.</returns>
     97         public new Size MinimumSize
     98         {
     99             get { return minSize; }
    100             set { minSize = value; }
    101         }
    102 
    103         private Size maxSize;
    104         /// <summary>
    105         /// Gets or sets a maximum size of the pop-up.
    106         /// </summary>
    107         /// <returns>An ordered pair of type <see cref="T:System.Drawing.Size" /> representing the width and height of a rectangle.</returns>
    108         public new Size MaximumSize
    109         {
    110             get { return maxSize; }
    111             set { maxSize = value; }
    112         }
    113 
    114         private bool _isOpen;
    115 
    116         public bool IsOpen
    117         {
    118             get { return _isOpen; }
    119         }
    120 
    121         /// <summary>
    122         /// Gets parameters of a new window.
    123         /// </summary>
    124         /// <returns>An object of type <see cref="T:System.Windows.Forms.CreateParams" /> used when creating a new window.</returns>
    125         protected override CreateParams CreateParams
    126         {
    127             [SecurityPermission(SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.UnmanagedCode)]
    128             get
    129             {
    130                 CreateParams cp = base.CreateParams;
    131                 cp.ExStyle |= UnsafeMethods.WS_EX_NOACTIVATE;
    132                 return cp;
    133             }
    134         }
    135 
    136         #endregion
    137 
    138         #region " Constructors "
    139 
    140         /// <summary>
    141         /// Initializes a new instance of the <see cref="PopupControl.Popup"/> class.
    142         /// </summary>
    143         /// <param name="content">The content of the pop-up.</param>
    144         /// <remarks>
    145         /// Pop-up will be disposed immediately after disposion of the content control.
    146         /// </remarks>
    147         /// <exception cref="T:System.ArgumentNullException"><paramref name="content" /> is <code>null</code>.</exception>
    148         public PopupForm(Control content)
    149         {
    150             if (content == null)
    151             {
    152                 throw new ArgumentNullException("content");
    153             }
    154             this.content = content;
    155             this.fade = SystemInformation.IsMenuAnimationEnabled && SystemInformation.IsMenuFadeEnabled;
    156             this._resizable = true;
    157             AutoSize = false;
    158             DoubleBuffered = true;
    159             ResizeRedraw = true;
    160             host = new ToolStripControlHost(content);
    161             Padding = Margin = host.Padding = host.Margin = Padding.Empty;
    162             MinimumSize = content.MinimumSize;
    163             content.MinimumSize = content.Size;
    164             MaximumSize = content.MaximumSize;
    165             content.MaximumSize = content.Size;
    166             Size = content.Size;
    167             content.Location = Point.Empty;
    168             Items.Add(host);
    169             content.Disposed += delegate(object sender, EventArgs e)
    170             {
    171                 content = null;
    172                 Dispose(true);
    173             };
    174             content.RegionChanged += delegate(object sender, EventArgs e)
    175             {
    176                 UpdateRegion();
    177             };
    178             content.Paint += delegate(object sender, PaintEventArgs e)
    179             {
    180                 PaintSizeGrip(e);
    181             };
    182             UpdateRegion();
    183         }
    184 
    185         #endregion
    186 
    187         #region " Methods "
    188 
    189         /// <summary>
    190         /// Processes a dialog box key.
    191         /// </summary>
    192         /// <param name="keyData">One of the <see cref="T:System.Windows.Forms.Keys" /> values that represents the key to process.</param>
    193         /// <returns>
    194         /// true if the key was processed by the control; otherwise, false.
    195         /// </returns>
    196         protected override bool ProcessDialogKey(Keys keyData)
    197         {
    198             if (acceptAlt && ((keyData & Keys.Alt) == Keys.Alt))
    199             {
    200                 if ((keyData & Keys.F4) != Keys.F4)
    201                 {
    202                     return false;
    203                 }
    204                 else
    205                 {
    206                     this.Close();
    207                 }
    208             }
    209             return base.ProcessDialogKey(keyData);
    210         }
    211 
    212         /// <summary>
    213         /// Updates the pop-up region.
    214         /// </summary>
    215         protected void UpdateRegion()
    216         {
    217             if (this.Region != null)
    218             {
    219                 this.Region.Dispose();
    220                 this.Region = null;
    221             }
    222             if (content.Region != null)
    223             {
    224                 this.Region = content.Region.Clone();
    225             }
    226         }
    227 
    228         /// <summary>
    229         /// Shows the pop-up window below the specified control.
    230         /// </summary>
    231         /// <param name="control">The control below which the pop-up will be shown.</param>
    232         /// <remarks>
    233         /// When there is no space below the specified control, the pop-up control is shown above it.
    234         /// </remarks>
    235         /// <exception cref="T:System.ArgumentNullException"><paramref name="control"/> is <code>null</code>.</exception>
    236         public void Show(Control control)
    237         {
    238             Show(control, control.ClientRectangle);
    239         }
    240 
    241         public void Show(Control control, bool center)
    242         {
    243             Show(control, control.ClientRectangle, center);
    244         }
    245 
    246         /// <summary>
    247         /// Shows the pop-up window below the specified area of the specified control.
    248         /// </summary>
    249         /// <param name="control">The control used to compute screen location of specified area.</param>
    250         /// <param name="area">The area of control below which the pop-up will be shown.</param>
    251         /// <remarks>
    252         /// When there is no space below specified area, the pop-up control is shown above it.
    253         /// </remarks>
    254         /// <exception cref="T:System.ArgumentNullException"><paramref name="control"/> is <code>null</code>.</exception>
    255         public void Show(Control control, Rectangle area)
    256         {
    257             Show(control, area, false);
    258         }
    259 
    260         public void Show(Control control, Rectangle area, bool center)
    261         {
    262             if (control == null)
    263             {
    264                 throw new ArgumentNullException("control");
    265             }
    266             SetOwnerItem(control);
    267             resizableTop = resizableLeft = false;
    268             Point location = control.PointToScreen(new Point(area.Left, area.Top + area.Height));
    269             Rectangle screen = Screen.FromControl(control).WorkingArea;
    270             if (center)
    271             {
    272                 if (location.X + (area.Width + Size.Width) / 2 > screen.Right)
    273                 {
    274                     resizableLeft = true;
    275                     location.X = screen.Right - Size.Width;
    276                 }
    277                 else
    278                 {
    279                     resizableLeft = true;
    280                     location.X = location.X - (Size.Width - area.Width) / 2;
    281                 }
    282             }
    283             else
    284             {
    285                 if (location.X + Size.Width > (screen.Left + screen.Width))
    286                 {
    287                     resizableLeft = true;
    288                     location.X = (screen.Left + screen.Width) - Size.Width;
    289                 }
    290             }
    291 
    292             if (location.Y + Size.Height > (screen.Top + screen.Height))
    293             {
    294                 resizableTop = true;
    295                 location.Y -= Size.Height + area.Height;
    296             }
    297             location = control.PointToClient(location);
    298             Show(control, location, ToolStripDropDownDirection.BelowRight);
    299         }
    300 
    301         private const int frames = 5;
    302         private const int totalduration = 100;
    303         private const int frameduration = totalduration / frames;
    304         /// <summary>
    305         /// Adjusts the size of the owner <see cref="T:System.Windows.Forms.ToolStrip" /> to accommodate the <see cref="T:System.Windows.Forms.ToolStripDropDown" /> if the owner <see cref="T:System.Windows.Forms.ToolStrip" /> is currently displayed, or clears and resets active <see cref="T:System.Windows.Forms.ToolStripDropDown" /> child controls of the <see cref="T:System.Windows.Forms.ToolStrip" /> if the <see cref="T:System.Windows.Forms.ToolStrip" /> is not currently displayed.
    306         /// </summary>
    307         /// <param name="visible">true if the owner <see cref="T:System.Windows.Forms.ToolStrip" /> is currently displayed; otherwise, false.</param>
    308         protected override void SetVisibleCore(bool visible)
    309         {
    310             double opacity = Opacity;
    311             if (visible && fade && focusOnOpen) Opacity = 0;
    312             base.SetVisibleCore(visible);
    313             if (!visible || !fade || !focusOnOpen) return;
    314             for (int i = 1; i <= frames; i++)
    315             {
    316                 if (i > 1)
    317                 {
    318                     System.Threading.Thread.Sleep(frameduration);
    319                 }
    320                 Opacity = opacity * (double)i / (double)frames;
    321             }
    322             Opacity = opacity;
    323         }
    324 
    325         private bool resizableTop;
    326         private bool resizableLeft;
    327 
    328         private void SetOwnerItem(Control control)
    329         {
    330             if (control == null)
    331             {
    332                 return;
    333             }
    334             if (control is PopupForm)
    335             {
    336                 PopupForm popupControl = control as PopupForm;
    337                 ownerPopup = popupControl;
    338                 ownerPopup.childPopup = this;
    339                 OwnerItem = popupControl.Items[0];
    340                 return;
    341             }
    342             if (control.Parent != null)
    343             {
    344                 SetOwnerItem(control.Parent);
    345             }
    346         }
    347 
    348         /// <summary>
    349         /// Raises the <see cref="E:System.Windows.Forms.Control.SizeChanged" /> event.
    350         /// </summary>
    351         /// <param name="e">An <see cref="T:System.EventArgs" /> that contains the event data.</param>
    352         protected override void OnSizeChanged(EventArgs e)
    353         {
    354             content.MinimumSize = Size;
    355             content.MaximumSize = Size;
    356             content.Size = Size;
    357             content.Location = Point.Empty;
    358             base.OnSizeChanged(e);
    359         }
    360 
    361         /// <summary>
    362         /// Raises the <see cref="E:System.Windows.Forms.ToolStripDropDown.Opening" /> event.
    363         /// </summary>
    364         /// <param name="e">A <see cref="T:System.ComponentModel.CancelEventArgs" /> that contains the event data.</param>
    365         protected override void OnOpening(CancelEventArgs e)
    366         {
    367             if (content.IsDisposed || content.Disposing)
    368             {
    369                 e.Cancel = true;
    370                 return;
    371             }
    372             UpdateRegion();
    373             base.OnOpening(e);
    374         }
    375 
    376         /// <summary>
    377         /// Raises the <see cref="E:System.Windows.Forms.ToolStripDropDown.Opened" /> event.
    378         /// </summary>
    379         /// <param name="e">An <see cref="T:System.EventArgs" /> that contains the event data.</param>
    380         protected override void OnOpened(EventArgs e)
    381         {
    382             if (ownerPopup != null)
    383             {
    384                 ownerPopup._resizable = false;
    385             }
    386             if (focusOnOpen)
    387             {
    388                 content.Focus();
    389             }
    390             _isOpen = true;
    391             base.OnOpened(e);
    392         }
    393 
    394         /// <summary>
    395         /// Raises the <see cref="E:System.Windows.Forms.ToolStripDropDown.Closed"/> event.
    396         /// </summary>
    397         /// <param name="e">A <see cref="T:System.Windows.Forms.ToolStripDropDownClosedEventArgs"/> that contains the event data.</param>
    398         protected override void OnClosed(ToolStripDropDownClosedEventArgs e)
    399         {
    400             if (ownerPopup != null)
    401             {
    402                 ownerPopup._resizable = true;
    403             }
    404             _isOpen = false;
    405             base.OnClosed(e);
    406         }
    407 
    408         #endregion
    409 
    410         #region " Resizing Support "
    411 
    412         /// <summary>
    413         /// Processes Windows messages.
    414         /// </summary>
    415         /// <param name="m">The Windows <see cref="T:System.Windows.Forms.Message" /> to process.</param>
    416         [SecurityPermission(SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.UnmanagedCode)]
    417         protected override void WndProc(ref Message m)
    418         {
    419             if (InternalProcessResizing(ref m, false))
    420             {
    421                 return;
    422             }
    423             base.WndProc(ref m);
    424         }
    425 
    426         /// <summary>
    427         /// Processes the resizing messages.
    428         /// </summary>
    429         /// <param name="m">The message.</param>
    430         /// <returns>true, if the WndProc method from the base class shouldn't be invoked.</returns>
    431         [SecurityPermission(SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.UnmanagedCode)]
    432         public bool ProcessResizing(ref Message m)
    433         {
    434             return InternalProcessResizing(ref m, true);
    435         }
    436 
    437         [SecurityPermission(SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.UnmanagedCode)]
    438         private bool InternalProcessResizing(ref Message m, bool contentControl)
    439         {
    440             if (m.Msg == UnsafeMethods.WM_NCACTIVATE && m.WParam != IntPtr.Zero && childPopup != null && childPopup.Visible)
    441             {
    442                 childPopup.Hide();
    443             }
    444             if (!Resizable)
    445             {
    446                 return false;
    447             }
    448             if (m.Msg == UnsafeMethods.WM_NCHITTEST)
    449             {
    450                 return OnNcHitTest(ref m, contentControl);
    451             }
    452             else if (m.Msg == UnsafeMethods.WM_GETMINMAXINFO)
    453             {
    454                 return OnGetMinMaxInfo(ref m);
    455             }
    456             return false;
    457         }
    458 
    459         [SecurityPermission(SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.UnmanagedCode)]
    460         private bool OnGetMinMaxInfo(ref Message m)
    461         {
    462             UnsafeMethods.MINMAXINFO minmax = (UnsafeMethods.MINMAXINFO)Marshal.PtrToStructure(m.LParam, typeof(UnsafeMethods.MINMAXINFO));
    463             minmax.maxTrackSize = this.MaximumSize;
    464             minmax.minTrackSize = this.MinimumSize;
    465             Marshal.StructureToPtr(minmax, m.LParam, false);
    466             return true;
    467         }
    468 
    469         private bool OnNcHitTest(ref Message m, bool contentControl)
    470         {
    471             int x = UnsafeMethods.LOWORD(m.LParam);
    472             int y = UnsafeMethods.HIWORD(m.LParam);
    473             Point clientLocation = PointToClient(new Point(x, y));
    474 
    475             GripBounds gripBouns = new GripBounds(contentControl ? content.ClientRectangle : ClientRectangle);
    476             IntPtr transparent = new IntPtr(UnsafeMethods.HTTRANSPARENT);
    477 
    478             if (resizableTop)
    479             {
    480                 if (resizableLeft && gripBouns.TopLeft.Contains(clientLocation))
    481                 {
    482                     m.Result = contentControl ? transparent : (IntPtr)UnsafeMethods.HTTOPLEFT;
    483                     return true;
    484                 }
    485                 if (!resizableLeft && gripBouns.TopRight.Contains(clientLocation))
    486                 {
    487                     m.Result = contentControl ? transparent : (IntPtr)UnsafeMethods.HTTOPRIGHT;
    488                     return true;
    489                 }
    490                 if (gripBouns.Top.Contains(clientLocation))
    491                 {
    492                     m.Result = contentControl ? transparent : (IntPtr)UnsafeMethods.HTTOP;
    493                     return true;
    494                 }
    495             }
    496             else
    497             {
    498                 if (resizableLeft && gripBouns.BottomLeft.Contains(clientLocation))
    499                 {
    500                     m.Result = contentControl ? transparent : (IntPtr)UnsafeMethods.HTBOTTOMLEFT;
    501                     return true;
    502                 }
    503                 if (!resizableLeft && gripBouns.BottomRight.Contains(clientLocation))
    504                 {
    505                     m.Result = contentControl ? transparent : (IntPtr)UnsafeMethods.HTBOTTOMRIGHT;
    506                     return true;
    507                 }
    508                 if (gripBouns.Bottom.Contains(clientLocation))
    509                 {
    510                     m.Result = contentControl ? transparent : (IntPtr)UnsafeMethods.HTBOTTOM;
    511                     return true;
    512                 }
    513             }
    514             if (resizableLeft && gripBouns.Left.Contains(clientLocation))
    515             {
    516                 m.Result = contentControl ? transparent : (IntPtr)UnsafeMethods.HTLEFT;
    517                 return true;
    518             }
    519             if (!resizableLeft && gripBouns.Right.Contains(clientLocation))
    520             {
    521                 m.Result = contentControl ? transparent : (IntPtr)UnsafeMethods.HTRIGHT;
    522                 return true;
    523             }
    524             return false;
    525         }
    526 
    527         private VS.VisualStyleRenderer sizeGripRenderer;
    528         /// <summary>
    529         /// Paints the sizing grip.
    530         /// </summary>
    531         /// <param name="e">The <see cref="System.Windows.Forms.PaintEventArgs" /> instance containing the event data.</param>
    532         public void PaintSizeGrip(PaintEventArgs e)
    533         {
    534             if (e == null || e.Graphics == null || !resizable)
    535             {
    536                 return;
    537             }
    538             Size clientSize = content.ClientSize;
    539             using (Bitmap gripImage = new Bitmap(0x10, 0x10))
    540             {
    541                 using (Graphics g = Graphics.FromImage(gripImage))
    542                 {
    543                     if (Application.RenderWithVisualStyles)
    544                     {
    545                         if (this.sizeGripRenderer == null)
    546                         {
    547                             this.sizeGripRenderer = new VS.VisualStyleRenderer(VS.VisualStyleElement.Status.Gripper.Normal);
    548                         }
    549                         this.sizeGripRenderer.DrawBackground(g, new Rectangle(0, 0, 0x10, 0x10));
    550                     }
    551                     else
    552                     {
    553                         ControlPaint.DrawSizeGrip(g, content.BackColor, 0, 0, 0x10, 0x10);
    554                     }
    555                 }
    556                 GraphicsState gs = e.Graphics.Save();
    557                 e.Graphics.ResetTransform();
    558                 if (resizableTop)
    559                 {
    560                     if (resizableLeft)
    561                     {
    562                         e.Graphics.RotateTransform(180);
    563                         e.Graphics.TranslateTransform(-clientSize.Width, -clientSize.Height);
    564                     }
    565                     else
    566                     {
    567                         e.Graphics.ScaleTransform(1, -1);
    568                         e.Graphics.TranslateTransform(0, -clientSize.Height);
    569                     }
    570                 }
    571                 else if (resizableLeft)
    572                 {
    573                     e.Graphics.ScaleTransform(-1, 1);
    574                     e.Graphics.TranslateTransform(-clientSize.Width, 0);
    575                 }
    576                 e.Graphics.DrawImage(gripImage, clientSize.Width - 0x10, clientSize.Height - 0x10 + 1, 0x10, 0x10);
    577                 e.Graphics.Restore(gs);
    578             }
    579         }
    580 
    581         #endregion
    582     }
    583 }
    View Code

    然后新建一个自定义控件,代码如下

      1   2 using System;
      3 using System.Collections.Generic;
      4 using System.ComponentModel;
      5 using System.Drawing;
      6 using System.Data;
      7 using System.Linq;
      8 using System.Text;
      9 using System.Windows.Forms;
     10 using System.Collections;
     11 using System.Reflection;
     12 using Newtonsoft.Json.Linq;
     13 
     14 namespace Controls
     15 {
     16 
     17     /// <summary>
     18     /// 功能描述:自定义多选下拉框
     19     /// 作  者:huangzh
     20     /// 创建日期:2016-01-04 11:57:13
     21     /// 任务编号:
     22     /// </summary>
     23     public class ComboBoxEx : ComboBox
     24     {
     25         PopupForm frmhost;
     26         TreeView lst = new TreeView();
     27         /// <summary>
     28         /// 功能描述:构造方法
     29         /// 作  者:huangzh
     30         /// 创建日期:2016-01-04 11:57:27
     31         /// 任务编号:
     32         /// </summary>
     33         public ComboBoxEx()
     34         {
     35             this.DrawMode = DrawMode.OwnerDrawFixed;//只有设置这个属性为OwnerDrawFixed才可能让重画起作用   
     36 
     37             lst.Width = ListWidth == 0 ? this.Width : ListWidth;
     38             lst.Height = ListHeight == 0 ? 300 : ListHeight;
     39             lst.CheckBoxes = true;
     40             lst.ShowLines = false;
     41             lst.ShowPlusMinus = false;
     42             lst.ShowRootLines = false;
     43             lst.KeyUp += new KeyEventHandler(lst_KeyUp);
     44             lst.AfterCheck += new TreeViewEventHandler(lst_AfterCheck);
     45             this.DropDownHeight = 1;
     46             frmhost = new PopupForm(lst);
     47             //frmhost.Closed += new ToolStripDropDownClosedEventHandler(frmhost_Closed);
     48             //frmhost.Opened += new EventHandler(frmhost_Opened);
     49         }
     50 
     51         void lst_KeyUp(object sender, KeyEventArgs e)
     52         {
     53             OnKeyUp(e);
     54         }
     55 
     56         void lst_AfterCheck(object sender, TreeViewEventArgs e)
     57         {
     58             if (e.Node.Checked)
     59             {
     60                 if (Text != "")
     61                 {
     62                     Text += ",";
     63                 }
     64                 Text += e.Node.Tag.ToString();
     65             }
     66             else
     67             {
     68                 string strValue = e.Node.Tag.ToString().Trim();
     69                 if (Text != "")
     70                 {
     71                     List<string> strs = Text.Split(',').ToList();
     72                     strs.Remove("");
     73                     if (strs.Contains(strValue))
     74                     {
     75                         strs.Remove(strValue);
     76                         Text = string.Join(",", strs);
     77                     }
     78                 }
     79             }
     80         }
     81 
     82         void frmhost_Opened(object sender, EventArgs e)
     83         {
     84 
     85         }
     86 
     87         void frmhost_Closed(object sender, ToolStripDropDownClosedEventArgs e)
     88         {
     89 
     90         }
     91 
     92         #region Property
     93         /// <summary>
     94         /// 选中项
     95         /// </summary>
     96         [Description("选定项的值"), Category("Data")]
     97         public List<TreeNode> SelectedItems
     98         {
     99             get
    100             {
    101                 List<TreeNode> lsttn = new List<TreeNode>();
    102                 foreach (TreeNode tn in lst.Nodes)
    103                 {
    104                     if (tn.Checked)
    105                     {
    106                         lsttn.Add(tn);
    107                     }
    108                 }
    109                 return lsttn;
    110             }
    111         }
    112 
    113         /// <summary>
    114         /// 数据源
    115         /// </summary>
    116         [Description("数据源"), Category("Data")]
    117         public new object DataSource
    118         {
    119             get;
    120             set;
    121         }
    122         /// <summary>
    123         /// 显示字段
    124         /// </summary>
    125         [Description("显示字段"), Category("Data")]
    126         public string DisplayFiled
    127         {
    128             get;
    129             set;
    130         }
    131         /// <summary>
    132         /// 值字段
    133         /// </summary>
    134         [Description("值字段"), Category("Data")]
    135         public string ValueFiled
    136         {
    137             get;
    138             set;
    139         }
    140         /// <summary>
    141         /// 列表高度
    142         /// </summary>
    143         [Description("列表高度"), Category("Data")]
    144         public int ListHeight
    145         {
    146             get;
    147             set;
    148         }
    149 
    150         /// <summary>
    151         /// 列表宽度
    152         /// </summary>
    153         [Description("列表宽度"), Category("Data")]
    154         public int ListWidth
    155         {
    156             get;
    157             set;
    158         }
    159         #endregion
    160 
    161         /// <summary>
    162         /// 功能描述:绑定数据
    163         /// 作  者:huangzh
    164         /// 创建日期:2016-01-04 10:38:51
    165         /// 任务编号:
    166         /// </summary>
    167         public void DataBind()
    168         {
    169             this.BeginUpdate();
    170             if (DataSource != null)
    171             {
    172                 if (DataSource is IDataReader)
    173                 {
    174                     DataTable dataTable = new DataTable();
    175                     dataTable.Load(DataSource as IDataReader);
    176 
    177                     DataBindToDataTable(dataTable);
    178                 }
    179                 else if (DataSource is DataView || DataSource is DataSet || DataSource is DataTable)
    180                 {
    181                     DataTable dataTable = null;
    182 
    183                     if (DataSource is DataView)
    184                     {
    185                         dataTable = ((DataView)DataSource).ToTable();
    186                     }
    187                     else if (DataSource is DataSet)
    188                     {
    189                         dataTable = ((DataSet)DataSource).Tables[0];
    190                     }
    191                     else
    192                     {
    193                         dataTable = ((DataTable)DataSource);
    194                     }
    195 
    196                     DataBindToDataTable(dataTable);
    197                 }
    198                 else if (DataSource is IEnumerable)
    199                 {
    200                     DataBindToEnumerable((IEnumerable)DataSource);
    201                 }
    202                 else
    203                 {
    204                     throw new Exception("DataSource doesn't support data type: " + DataSource.GetType().ToString());
    205                 }
    206             }
    207             else
    208             {
    209                 lst.Nodes.Clear();
    210             }
    211 
    212             this.EndUpdate();
    213         }
    214 
    215         /// <summary>
    216         /// 功能描述:绑定Table数据
    217         /// 作  者:huangzh
    218         /// 创建日期:2016-01-04 10:47:27
    219         /// 任务编号:
    220         /// </summary>
    221         /// <param name="dt">dt</param>
    222         private void DataBindToDataTable(DataTable dt)
    223         {
    224             foreach (DataRow dr in dt.Rows)
    225             {
    226                 TreeNode tn = new TreeNode();
    227                 if (!string.IsNullOrEmpty(DisplayFiled) && !string.IsNullOrEmpty(ValueFiled))
    228                 {
    229                     tn.Text = dr[DisplayFiled].ToString();
    230                     tn.Tag = dr[ValueFiled].ToString();
    231                 }
    232                 else if (string.IsNullOrEmpty(ValueFiled))
    233                 {
    234                     tn.Text = dr[DisplayFiled].ToString();
    235                     tn.Tag = dr[DisplayFiled].ToString();
    236                 }
    237                 else if (string.IsNullOrEmpty(DisplayFiled))
    238                 {
    239                     tn.Text = dr[ValueFiled].ToString();
    240                     tn.Tag = dr[ValueFiled].ToString();
    241                 }
    242                 else
    243                 {
    244                     throw new Exception("ValueFiled和DisplayFiled至少保证有一项有值");
    245                 }
    246                 tn.ToolTipText = tn.Text;
    247 
    248                 tn.Checked = false;
    249                 lst.Nodes.Add(tn);
    250             }
    251         }
    252 
    253         /// <summary>
    254         /// 绑定到可枚举类型
    255         /// </summary>
    256         /// <param name="enumerable">可枚举类型</param>
    257         private void DataBindToEnumerable(IEnumerable enumerable)
    258         {
    259             IEnumerator enumerator = enumerable.GetEnumerator();
    260             while (enumerator.MoveNext())
    261             {
    262                 object currentObject = enumerator.Current;
    263                 lst.Nodes.Add(CreateListItem(currentObject));
    264             }
    265         }
    266 
    267 
    268         /// <summary>
    269         /// 功能描述:获取一个CheckBox
    270         /// 作  者:huangzh
    271         /// 创建日期:2016-01-04 10:53:12
    272         /// 任务编号:
    273         /// </summary>
    274         /// <param name="obj">obj</param>
    275         /// <returns>返回值</returns>
    276         private TreeNode CreateListItem(Object obj)
    277         {
    278             TreeNode item = new TreeNode();
    279 
    280             if (obj is string)
    281             {
    282                 item.Text = obj.ToString();
    283                 item.Tag = obj.ToString();
    284             }
    285             else
    286             {
    287                 if (DisplayFiled != "")
    288                 {
    289                     item.Text = GetPropertyValue(obj, DisplayFiled);
    290                 }
    291                 else
    292                 {
    293                     item.Text = obj.ToString();
    294                 }
    295 
    296                 if (ValueFiled != "")
    297                 {
    298                     item.Tag = GetPropertyValue(obj, ValueFiled);
    299                 }
    300                 else
    301                 {
    302                     item.Tag = obj.ToString();
    303                 }
    304             }
    305             item.ToolTipText = item.Text;
    306             return item;
    307         }
    308 
    309         /// <summary>
    310         /// 取得属性值
    311         /// </summary>
    312         /// <param name="obj"></param>
    313         /// <param name="propertyName"></param>
    314         private string GetPropertyValue(object obj, string propertyName)
    315         {
    316             object result = null;
    317 
    318             result = ObjectUtil.GetPropertyValue(obj, propertyName);
    319             return result == null ? String.Empty : result.ToString();
    320         }
    321 
    322         #region override
    323 
    324         /// <summary>
    325         /// 功能描述:OnKeyUp
    326         /// 作  者:huangzh
    327         /// 创建日期:2016-01-04 11:58:33
    328         /// 任务编号:
    329         /// </summary>
    330         /// <param name="e">e</param>
    331         protected override void OnKeyUp(KeyEventArgs e)
    332         {
    333             base.OnKeyDown(e);
    334             bool Pressed = (e.Control && ((e.KeyData & Keys.A) == Keys.A));
    335             if (Pressed)
    336             {
    337                 this.Text = "";
    338                 for (int i = 0; i < lst.Nodes.Count; i++)
    339                 {
    340                     lst.Nodes[i].Checked = true;
    341                 }
    342             }
    343         }
    344 
    345         /// <summary>
    346         /// 功能描述:OnDropDown
    347         /// 作  者:huangzh
    348         /// 创建日期:2016-01-04 11:58:53
    349         /// 任务编号:
    350         /// </summary>
    351         /// <param name="e">e</param>
    352         protected override void OnDropDown(EventArgs e)
    353         {
    354             this.DroppedDown = false;
    355             string strValue = this.Text;
    356             if (!string.IsNullOrEmpty(strValue))
    357             {
    358                 List<string> lstvalues = strValue.Split(',').ToList<string>();
    359                 foreach (TreeNode tn in lst.Nodes)
    360                 {
    361                     if (tn.Checked && !lstvalues.Contains(tn.Tag.ToString()) && !string.IsNullOrEmpty(tn.Tag.ToString().Trim()))
    362                     {
    363                         tn.Checked = false;
    364                     }
    365                     else if (!tn.Checked && lstvalues.Contains(tn.Tag.ToString()) && !string.IsNullOrEmpty(tn.Tag.ToString().Trim()))
    366                     {
    367                         tn.Checked = true;
    368                     }
    369                 }
    370             }
    371             else
    372             {
    373                 foreach (TreeNode tn in lst.Nodes)
    374                 {
    375                     tn.Checked = false;
    376                 }
    377             }
    378             frmhost.Show(this);
    379         }
    380         #endregion
    381     }
    382 
    383 
    384     /// <summary>
    385     /// 对象帮助类
    386     /// </summary>
    387     public class ObjectUtil
    388     {
    389         /// <summary>
    390         /// 获取对象的属性值
    391         /// </summary>
    392         /// <param name="obj">可能是DataRowView或一个对象</param>
    393         /// <param name="propertyName">属性名</param>
    394         /// <returns>属性值</returns>
    395         public static object GetPropertyValue(object obj, string propertyName)
    396         {
    397             object result = null;
    398 
    399             try
    400             {
    401                 if (obj is DataRow)
    402                 {
    403                     result = (obj as DataRow)[propertyName];
    404                 }
    405                 else if (obj is DataRowView)
    406                 {
    407                     result = (obj as DataRowView)[propertyName];
    408                 }
    409                 else if (obj is JObject)
    410                 {
    411                     result = (obj as JObject).Value<JValue>(propertyName).Value; //.getValue(propertyName);
    412                 }
    413                 else
    414                 {
    415                     result = GetPropertyValueFormObject(obj, propertyName);
    416                 }
    417             }
    418             catch (Exception)
    419             {
    420                 // 找不到此属性
    421             }
    422 
    423             return result;
    424         }
    425 
    426         /// <summary>
    427         /// 获取对象的属性值
    428         /// </summary>
    429         /// <param name="obj">对象</param>
    430         /// <param name="propertyName">属性名("Color"、"BodyStyle"或者"Info.UserName")</param>
    431         /// <returns>属性值</returns>
    432         private static object GetPropertyValueFormObject(object obj, string propertyName)
    433         {
    434             object rowObj = obj;
    435             object result = null;
    436 
    437             if (propertyName.IndexOf(".") > 0)
    438             {
    439                 string[] properties = propertyName.Split('.');
    440                 object tmpObj = rowObj;
    441 
    442                 for (int i = 0; i < properties.Length; i++)
    443                 {
    444                     PropertyInfo property = tmpObj.GetType().GetProperty(properties[i], BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
    445                     if (property != null)
    446                     {
    447                         tmpObj = property.GetValue(tmpObj, null);
    448                     }
    449                 }
    450 
    451                 result = tmpObj;
    452             }
    453             else
    454             {
    455                 PropertyInfo property = rowObj.GetType().GetProperty(propertyName, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
    456                 if (property != null)
    457                 {
    458                     result = property.GetValue(rowObj, null);
    459                 }
    460             }
    461 
    462             return result;
    463         }
    464     }
    465 }
    View Code

    然后就是使用了,直接拖一个到界面上,然后设置值就可以了

    ListHeight,ListWidth 这两个属性一定要修改下的哦

    然后就是绑定数据源

      var varSourceFrom = from p in lstEnumEnitty
                                        where p.Type == "source"
                                        select p;
                    cboSourceFromType.DataSource = varSourceFrom;
                    cboSourceFromType.DisplayFiled = "Name";
                    cboSourceFromType.ValueFiled = "Code";
                    cboSourceFromType.DataBind();

    效果就是这样的了

    需要引用的一个DLL去我的上一个文章里面下载吧

  • 相关阅读:
    devstack screen 详解
    devstack with neutron 参考文献
    Linux 启动文件、设置环境变量的位置
    Android解析服务器Json数据实例
    JDBC连接MySQL数据库的方法和实例
    Github如何更新远程代码
    最简单的Android教程之自定义控件
    Markdown入门教程
    如何将代码托管到GitHub上
    Github如何删除repository(仓库)
  • 原文地址:https://www.cnblogs.com/bfyx/p/5099823.html
Copyright © 2020-2023  润新知