Checkbox on the ColumnHeader [modified]
-
i would like to achieve a checkbox on a ColumnHeader in a listview. i have been trying for days. i have achieved a checkbox on the right spot in the listview by virtual placing it on top.
[DllImport("user32")] private static extern IntPtr SetParent(IntPtr hWndChild, IntPtr hWndNewParent); protected override void OnHandleCreated(EventArgs e) { SetParent(_cCehckBox.Handle, Handle); base.OnHandleCreated(e); }
but the visual style/effect of the header causes the checkbox to fall in the background if you hover the mouse of the header. the Header class doesn't provide anu usefull stuff, atleast i don't see any usefull stuff. i have bene reading alot about it and viewed many things regarding headers. i have also been using ...protected override void WndProc(ref Message message) { .... }
filtering on WM_NOTIFY for 'HDN_ITEMCHANGINGA', 'HDN_ITEMCHANGEDA', 'HDN_BEGINTRACKA', 'HDN_BEGINTRACKW'. i used a piece of code from a project here on codeproject, virtually unchanged. but i only get the windows handle, the other things are empty.\[StructLayout(LayoutKind.Sequential)\] private struct NMHDR { public IntPtr hwndFrom; public int idFrom; public int code; } //NMHDR //OnMessageNeedsSending(message.ToString(), Color.Black); // pass messages on to the base control for processing base.WndProc(ref message); \*/ const int WM\_NOTIFY = 0x004E; const int HDN\_FIRST = (0 - 300); const int HDN\_BEGINTRACKA = (HDN\_FIRST - 6); const int HDN\_BEGINTRACKW = (HDN\_FIRST - 26); bool callBase = true; switch (message.Msg) { case WM\_NOTIFY: NMHDR nmhdr = (NMHDR)message.GetLParam(typeof(NMHDR)); OnMessageNeedsSending("WM\_NOTIFY " + message, Color.Black); OnMessageNeedsSending("code: " + nmhdr.code + ", hwndFrom: " + nmhdr.hwndFrom + ", idFrom: " + nmhdr.idFrom, Color.Black); switch (nmhdr.code) { case HDN\_BEGINTRACKA: //Process both ANSI and OnMessageNeedsSending("HDN\_BEGINTRACKA " + message, Color.Black); break; case HDN\_BEGINTRACKW:
-
i would like to achieve a checkbox on a ColumnHeader in a listview. i have been trying for days. i have achieved a checkbox on the right spot in the listview by virtual placing it on top.
[DllImport("user32")] private static extern IntPtr SetParent(IntPtr hWndChild, IntPtr hWndNewParent); protected override void OnHandleCreated(EventArgs e) { SetParent(_cCehckBox.Handle, Handle); base.OnHandleCreated(e); }
but the visual style/effect of the header causes the checkbox to fall in the background if you hover the mouse of the header. the Header class doesn't provide anu usefull stuff, atleast i don't see any usefull stuff. i have bene reading alot about it and viewed many things regarding headers. i have also been using ...protected override void WndProc(ref Message message) { .... }
filtering on WM_NOTIFY for 'HDN_ITEMCHANGINGA', 'HDN_ITEMCHANGEDA', 'HDN_BEGINTRACKA', 'HDN_BEGINTRACKW'. i used a piece of code from a project here on codeproject, virtually unchanged. but i only get the windows handle, the other things are empty.\[StructLayout(LayoutKind.Sequential)\] private struct NMHDR { public IntPtr hwndFrom; public int idFrom; public int code; } //NMHDR //OnMessageNeedsSending(message.ToString(), Color.Black); // pass messages on to the base control for processing base.WndProc(ref message); \*/ const int WM\_NOTIFY = 0x004E; const int HDN\_FIRST = (0 - 300); const int HDN\_BEGINTRACKA = (HDN\_FIRST - 6); const int HDN\_BEGINTRACKW = (HDN\_FIRST - 26); bool callBase = true; switch (message.Msg) { case WM\_NOTIFY: NMHDR nmhdr = (NMHDR)message.GetLParam(typeof(NMHDR)); OnMessageNeedsSending("WM\_NOTIFY " + message, Color.Black); OnMessageNeedsSending("code: " + nmhdr.code + ", hwndFrom: " + nmhdr.hwndFrom + ", idFrom: " + nmhdr.idFrom, Color.Black); switch (nmhdr.code) { case HDN\_BEGINTRACKA: //Process both ANSI and OnMessageNeedsSending("HDN\_BEGINTRACKA " + message, Color.Black); break; case HDN\_BEGINTRACKW:
i extented ...
\[StructLayout(LayoutKind.Sequential)\] private struct NMHDR { public IntPtr hwndFrom; public int idFrom; public int code; } //NMHDR
to ...
\[StructLayout(LayoutKind.Sequential)\] private struct NMHDR2 { public IntPtr hwndFrom; public int idFrom; public int code; public int coder; } //NMHDR
this new variable 'coder' contains numbers, like: -12, -16, -23 -320, -321, -326 -327, -530 -12 and -530 seam to be mouseover and mouseleave. -16 and -326 seam to be mouseclick / down and mouse release. i posted a logoutput. http://pastebin.com/HuCk5cac[^] anyone experienced with this?
Bad = knowing 2 much
modified on Tuesday, April 27, 2010 2:47 PM
-
i would like to achieve a checkbox on a ColumnHeader in a listview. i have been trying for days. i have achieved a checkbox on the right spot in the listview by virtual placing it on top.
[DllImport("user32")] private static extern IntPtr SetParent(IntPtr hWndChild, IntPtr hWndNewParent); protected override void OnHandleCreated(EventArgs e) { SetParent(_cCehckBox.Handle, Handle); base.OnHandleCreated(e); }
but the visual style/effect of the header causes the checkbox to fall in the background if you hover the mouse of the header. the Header class doesn't provide anu usefull stuff, atleast i don't see any usefull stuff. i have bene reading alot about it and viewed many things regarding headers. i have also been using ...protected override void WndProc(ref Message message) { .... }
filtering on WM_NOTIFY for 'HDN_ITEMCHANGINGA', 'HDN_ITEMCHANGEDA', 'HDN_BEGINTRACKA', 'HDN_BEGINTRACKW'. i used a piece of code from a project here on codeproject, virtually unchanged. but i only get the windows handle, the other things are empty.\[StructLayout(LayoutKind.Sequential)\] private struct NMHDR { public IntPtr hwndFrom; public int idFrom; public int code; } //NMHDR //OnMessageNeedsSending(message.ToString(), Color.Black); // pass messages on to the base control for processing base.WndProc(ref message); \*/ const int WM\_NOTIFY = 0x004E; const int HDN\_FIRST = (0 - 300); const int HDN\_BEGINTRACKA = (HDN\_FIRST - 6); const int HDN\_BEGINTRACKW = (HDN\_FIRST - 26); bool callBase = true; switch (message.Msg) { case WM\_NOTIFY: NMHDR nmhdr = (NMHDR)message.GetLParam(typeof(NMHDR)); OnMessageNeedsSending("WM\_NOTIFY " + message, Color.Black); OnMessageNeedsSending("code: " + nmhdr.code + ", hwndFrom: " + nmhdr.hwndFrom + ", idFrom: " + nmhdr.idFrom, Color.Black); switch (nmhdr.code) { case HDN\_BEGINTRACKA: //Process both ANSI and OnMessageNeedsSending("HDN\_BEGINTRACKA " + message, Color.Black); break; case HDN\_BEGINTRACKW:
this is the entire code to create a listview with a checkbox in the left upper corner of the ListView.
NM_CUSTOMDRAW
seams to be the message when the mouse hover over the headers. but i fail to keep the checkBox visible / ontop @ all time. if you slightly hoover of the first header, the headers mousehover effect draws over the check. anyone an idea how to prevent this?using System;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Windows.Forms;namespace Listview_Colum_header_checkbox
{
class CCehckBox2 : CheckBox
{
public CCehckBox2()
{
Width = 14;
Height = 14;
}
}class CustomChechBox2 : Control { readonly CCehckBox2 \_chb = new CCehckBox2(); public CustomChechBox2() { Size = new Size(16, 16); \_chb.Location = new Point(0, 0); Controls.Add(\_chb); } } class CListview2 : ListView { public delegate void MessageNeedsSendingCallback(string message, Color color); public event MessageNeedsSendingCallback OnMessageNeedsSending; //private readonly CCehckBox \_cCehckBox = new CCehckBox(); private readonly CustomChechBox2 \_cCehckBox = new CustomChechBox2(); private readonly ColumnHeader \_header1, \_header2, \_header3 = new ColumnHeader(); #region PInvoke Declarations \[DllImport("User32", CallingConvention = CallingConvention.Cdecl)\] private static extern uint RealGetWindowClass(IntPtr hwnd, System.Text.StringBuilder pszType, int cchType); \[DllImport("user32")\] private static extern IntPtr SetParent(IntPtr hWndChild, IntPtr hWndNewParent); \[DllImport("user32.dll")\] private static extern IntPtr SendMessage(IntPtr hWnd, int Msg, IntPtr wParam, IntPtr lParam); #endregion public CListview2() { View = View.Details; //this.HeaderStyle = ColumnHeaderStyle.Nonclickable; //\_header1. \_header1 = Columns.Add(""); \_header1.Width = (Location.X + 5) + 12; //\_header1.AutoResize(ColumnHeaderAutoResizeStyle.ColumnContent); \_header1.Name = "CheckBox"; \_header1.DisplayIndex = 0; \_header2 = Columns.Add("bah"); \_header2.Width = 50; \_header3 = Columns.Add("boh"); \_header3.Width = 50; var wijd = \_cCehck