www.pudn.com > lphant-v1.00-src.zip > eLePhantListView.cs


#region Copyright (c)2003 Juanjo < http://lphant.sourceforge.net > 
/* 
* This file is part of eLePhant 
* Copyright (C)2003 Juanjo < j_u_a_n_j_o@users.sourceforge.net / http://lphant.sourceforge.net > 
*  
* This program is free software; you can redistribute it and/or 
* modify it under the terms of the GNU General Public License 
* as published by the Free Software Foundation; either 
* version 2 of the License, or (at your option) any later version. 
*  
* This program is distributed in the hope that it will be useful, 
* but WITHOUT ANY WARRANTY; without even the implied warranty of 
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
* GNU General Public License for more details. 
*  
* You should have received a copy of the GNU General Public License 
* along with this program; if not, write to the Free Software 
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 
*/ 
#endregion 
 
using System; 
using System.ComponentModel; 
using System.Collections; 
using System.Diagnostics; 
using System.Windows.Forms; 
using System.Drawing; 
using System.Runtime.InteropServices; 
using System.Text; 
 
namespace eLePhant.Client 
{ 
	//The delegate for the HeaderEventArgs class 
	public delegate void HeaderEventHandler(object sender, HeaderEventArgs e); 
	//The delegate for drawing the entire header 
	public delegate void DrawHeaderEventHandler(DrawHeaderEventArgs e); 
	//The delegate for click the header 
	public delegate void ClickHeaderEventHandler(ColumnClickEventHandler e); 
 
	public class eLePhantListView : ListView 
	{ 
		public int SortColumnIndex; 
		//The event for drawing columns 
		public event DrawItemEventHandler DrawColumn; 
		//The event for handling the entire border drawing of the header 
		public event DrawHeaderEventHandler DrawHeader; 
 
		//Event handlers associated with the header control 
		public event HeaderEventHandler BeginDragHeaderDivider; 
		public event HeaderEventHandler DragHeaderDivider; 
		public event HeaderEventHandler EndDragHeaderDivider; 
		public event HeaderEventHandler ClickHeader; 
 
		private System.ComponentModel.Container components = null; 
		//private StringBuilder strB; 
		private Pen borderPen; 
		public int ScrollBarBKColor; 
		ListColumnArray myColumns;		 
		public ImageList headerImages; 
		HeaderControl header; 
		bool ownerDrawHeader; 
		int increaseHeaderHeight; 
		public Color headerBackColor; 
		public Color headerForeColor; 
		int headerHeight; 
		bool defaultCustomDraw; 
		bool m_Loaded; 
		private int m_sortColumn; 
 
		protected int[] m_DefaultWidths; 
		public int sortOrder; 
		 
		private int[] m_headerleft=new int[20]; 
		private int[] m_headerright=new int[20]; 
		private Pen m_ArrowPen; 
		public Color HeaderBorderColor 
		{ 
			set  
			{ 
				borderPen=new Pen(value); 
			} 
		} 
 
		public int sortColumn 
		{ 
			get 
			{ 
				return m_sortColumn; 
			} 
			set 
			{ 
				m_sortColumn=value; 
				this.Refresh(); 
			} 
		} 
 
		public eLePhantListView() 
		{ 
			InitializeComponent(); 
			 
			//strB=new StringBuilder(); 
			myColumns = new ListColumnArray();  
			ownerDrawHeader = false;			 
			headerBackColor = Color.FromArgb(222,231,247);//SystemColors.Control; 
			headerForeColor= Color.Black; 
			ScrollBarBKColor = 0x00F7E7DE; 
			//m_ArrowPen=new Pen(headerForeColor); 
			m_ArrowPen=new Pen(Color.FromArgb(0x80,0,0,0)); 
			borderPen=new Pen(Color.FromArgb(68,69,151)); 
			increaseHeaderHeight = 0; 
			defaultCustomDraw = false; 
			this.CheckBoxes = false; 
			this.FullRowSelect=true; 
			this.AllowColumnReorder=true; 
			this.AutoArrange=false; 
			this.HideSelection=false; 
			ownerDrawHeader = true; 
			this.defaultCustomDraw=false; 
			headerImages=new ImageList(); 
			sortColumn=-1; 
			sortOrder=1; 
			m_Loaded=false; 
			InsertColumns(); 
		} 
 
		public int GetColumnPosition(int column) 
		{ 
			Win32.LV_COLUMN pcol = new Win32.LV_COLUMN(); 
			pcol.mask = Win32.LVCF_ORDER; 
			Win32.SendMessage(Handle, Win32.LVM_GETCOLUMN, column, ref pcol); 
			return (int)pcol.iOrder; 
		} 
		public void SetColumnPosition(int column, int position) 
		{ 
			Win32.LV_COLUMN pcol = new Win32.LV_COLUMN(); 
			pcol.mask = Win32.LVCF_ORDER; 
			pcol.iOrder = position; 
			Win32.SendMessage(Handle, Win32.LVM_SETCOLUMN, column, ref pcol); 
		} 
		public int GetColumnsWidth(int column) 
		{ 
			return Win32.SendMessage(Handle,Win32.LVM_GETCOLUMNWIDTH,column,0); 
		} 
		public void SetColumnWidth(int column, int width) 
		{ 
			IntPtr lPram=Win32.MakeLParam(width,0); 
			Win32.SendMessage(Handle,Win32.LVM_SETCOLUMNWIDTH,column,lPram); 
		} 
		public void SetFlatScrollBar() 
		{ 
			IntPtr stylePtr; 
			int style; 
			stylePtr=Win32.SendMessage(this.Handle, 4151, IntPtr.Zero , IntPtr.Zero); 
			style=stylePtr.ToInt32(); 
			style+=256; 
			stylePtr=(IntPtr)style; 
			Win32.SendMessage(this.Handle, 4150, IntPtr.Zero , stylePtr);	 
			Win32.FlatSB_SetScrollProp(this.Handle,0x80,(IntPtr)ScrollBarBKColor,true); 
			Win32.FlatSB_SetScrollProp(this.Handle,0x40,(IntPtr)ScrollBarBKColor,true); 
		} 
		public void SavePreferences() 
		{ 
			for (int i=0;im_DefaultWidths.Length)) 
					def=60; 
				else  
					def=m_DefaultWidths[i]; 
				Columns[i].Width=eLePhantForm.preferences.GetInt(Name+"ColumnWidth-"+i.ToString(),def); 
			} 
		} 
		private void m_LoadPreferences() 
		{ 
			if (m_Loaded) return; 
			m_Loaded=true; 
			int newPosition; 
			for (int i=0;i 
		/// Clean up any resources being used. 
		///  
		protected override void Dispose( bool disposing ) 
		{ 
			if( disposing ) 
			{ 
				if(components != null) 
				{ 
					components.Dispose(); 
				} 
			} 
			base.Dispose( disposing ); 
		} 
	    protected virtual void OnDrawItem(int item,int column,Graphics g,Rectangle rec) 
		{ 
 
		} 
		#region Overriden methods 
		 
		protected override void OnResize(EventArgs e) 
		{ 
			this.Invalidate(); 
			base.OnResize (e); 
		} 
 
		protected override void OnHandleCreated(EventArgs e) 
		{ 
			//Create a new HeaderControl object 
			header = new HeaderControl(this); 
			if(header.Handle != IntPtr.Zero) 
			{ 
				if(headerImages != null)//If we have a valid header handle and a valid ImageList for it 
					//send a message HDM_SETIMAGELIST 
					Win32.SendMessage(header.Handle,0x1200+8,IntPtr.Zero,headerImages.Handle); 
				//Insert all the columns in Columns collection 
				if(this.Columns.Count > 0) 
					InsertColumns();				 
			} 
			base.OnHandleCreated(e); 
			SetFlatScrollBar(); 
		} 
 
		protected override void WndProc(ref Message m) 
		{ 
			Win32.NMHEADER nm; 
 
			switch(m.Msg) 
			{ 
				 
				case 0x004E://WM_NOTIFY 
					base.WndProc(ref m); 
					Win32.NMHDR nmhdr = (Win32.NMHDR)m.GetLParam(typeof(Win32.NMHDR)); 
					switch(nmhdr.code) 
					{ 
						case (int)Win32.NM.NM_CLICK-320: 
							nm=(Win32.NMHEADER)m.GetLParam(typeof(Win32.NMHEADER)); 
							if (ClickHeader!=null) 
							{ 
								sortColumn=nm.iItem; 
								if (sortOrder==1) sortOrder=-1; 
											else sortOrder=1; 
								ClickHeader(this.Columns[nm.iItem],  
									new HeaderEventArgs(nm.iItem, nm.iButton)); 
								 
							} 
							break; 
						case (0-300-26)://HDN_BEGINTRACK 
							nm=(Win32.NMHEADER)m.GetLParam(typeof(Win32.NMHEADER)); 
							if(BeginDragHeaderDivider != null) 
								BeginDragHeaderDivider(this.Columns[nm.iItem],  
									new HeaderEventArgs(nm.iItem, nm.iButton)); 
							break; 
						case (0-300-20)://HDN_ITEMCHANGING 
							nm=(Win32.NMHEADER)m.GetLParam(typeof(Win32.NMHEADER)); 
							//Adjust the column width 
							Win32.RECT rect = new Win32.RECT(); 
							//HDM_GETITEMRECT 
							Win32.SendMessage(header.Handle, 0x1200+7, nm.iItem, ref rect); 
							//Get the item height which is actually header's height 
							this.headerHeight = rect.bottom-rect.top; 
							//para pintar correctamente el progreso 
							//Debug.Write("Parte 1: id:" + nm.iItem + " left=" + rect.left + "\n"); 
							this.m_headerleft[nm.iItem]=rect.left; 
							this.m_headerright[nm.iItem]=rect.right; 
							this.Columns[nm.iItem].Width = rect.right - rect.left; 
							if(DragHeaderDivider != null) 
								DragHeaderDivider(this.Columns[nm.iItem], 
									new HeaderEventArgs(nm.iItem, nm.iButton)); 
							break; 
						case (0-300-27)://HDN_ENDTRACK 
							nm=(Win32.NMHEADER)m.GetLParam(typeof(Win32.NMHEADER)); 
							if(EndDragHeaderDivider != null) 
								EndDragHeaderDivider(this.Columns[nm.iItem], 
									new HeaderEventArgs(nm.iItem, nm.iButton)); 
							break; 
//						case (0-300-11): //HDN_ENDDRAG 
//							break; 
					} 
					break; 
				case (int)Win32.OCM.OCM_NOTIFY://Reflected WM_NOTIFY message 
					Win32.NMHDR nmh = (Win32.NMHDR)m.GetLParam(typeof(Win32.NMHDR)); 
					switch(nmh.code) 
					{ 
						case (int)Win32.NM.NM_CUSTOMDRAW: 
							Win32.NMCUSTOMDRAW nmcd =  
									(Win32.NMCUSTOMDRAW)m.GetLParam(typeof(Win32.NMCUSTOMDRAW)); 
							if(nmcd.hdr.hwndFrom != this.Handle) 
								break; 
							switch(nmcd.dwDrawStage) 
							{ 
								case (int)Win32.CDDS.CDDS_PREPAINT: 
									m.Result = (IntPtr)Win32.CDRF.CDRF_NOTIFYITEMDRAW; 
									break; 
								case (int)Win32.CDDS.CDDS_ITEMPREPAINT: 
									m.Result = (IntPtr)Win32.CDRF.CDRF_NOTIFYITEMDRAW; 
									break; 
								case (int)(Win32.CDDS.CDDS_SUBITEM|Win32.CDDS.CDDS_ITEMPREPAINT): 
									try 
									{ 
									Win32.NMLVCUSTOMDRAW nmlv = (Win32.NMLVCUSTOMDRAW) 
										m.GetLParam(typeof(Win32.NMLVCUSTOMDRAW)); 
									 
									if ((Columns[nmlv.iSubItem].subItemOwnerDraw)&&(nmlv.nmcd.dwItemSpec0) 
										{ 
											rc.top=nmlv.iSubItem; 
											rc.left=0; 
											Win32.SendMessage(this.Handle,0x1000 + 56,nmlv.nmcd.dwItemSpec,ref rc); 
										} 
										else 
										{ 
											rc.top=0; 
											rc.left=2; 
											Win32.SendMessage(this.Handle,0x1000 + 14,nmlv.nmcd.dwItemSpec,ref rc); 
										} 
										 
										//Rectangle rec=new Rectangle(rc.left+1,rc.top,rc.right-rc.left-2, rc.bottom-rc.top-2); 
										Rectangle rec=new Rectangle(rc.left,rc.top,rc.right-rc.left, rc.bottom-rc.top); 
										//Point p=this.PointToClient(new Point(rc.left,rc.top)); 
										//Point p2=this.PointToClient(new Point(rc.right,rc.bottom)); 
										//Rectangle rec=new Rectangle(p.X,rc.top,p2.X-p.X,rc.bottom-rc.top-2); 
										Graphics g = Graphics.FromHdc(nmlv.nmcd.hdc);									 
										OnDrawItem(nmlv.nmcd.dwItemSpec,nmlv.iSubItem,g,rec); 
										g.Dispose(); 
										//Win32.ReleaseDC(nmcd.hdr.hwndFrom,nmlv.nmcd.hdc); 
										m.Result = (IntPtr)Win32.CDRF.CDRF_SKIPDEFAULT; 
									} 
									else 
										base.WndProc(ref m);//m.Result = (IntPtr)Win32.CDRF.CDRF_DODEFAULT; 
									Marshal.StructureToPtr(nmlv,m.LParam,true); 
									} 
									catch 
									{ 
										base.WndProc(ref m); 
									} 
									break; 
								} 
								break; 
						default: 
							base.WndProc(ref m); 
							break; 
						} 
						break; 
				case 0x002B://WM_DRAWITEM 
					try 
					{ 
						//Get the DRAWITEMSTRUCT from the LParam of the message 
						Win32.DRAWITEMSTRUCT dis = (Win32.DRAWITEMSTRUCT)Marshal.PtrToStructure( 
							m.LParam,typeof(Win32.DRAWITEMSTRUCT)); 
						//agregar aqui la posicion x para pintar bien el progreso. 
						//Debug.Write("parte3: id: " + dis.itemID + "\n"); 
						this.m_headerleft[dis.itemID] = dis.rcItem.left; 
						this.m_headerright[dis.itemID] = dis.rcItem.right; 
						//Check if this message comes from the header 
						if(dis.ctrlType == 100)//ODT_HEADER - it do comes from the header 
						{ 
							//Get the graphics from the hdc field of the DRAWITEMSTRUCT 
							Graphics g = Graphics.FromHdc(dis.hdc); 
							//Create a rectangle from the RECT struct 
							Rectangle r = new Rectangle(dis.rcItem.left, dis.rcItem.top, dis.rcItem.right - 
								dis.rcItem.left, dis.rcItem.bottom - dis.rcItem.top);						 
							//Create new DrawItemState in its default state					 
							DrawItemState d = DrawItemState.Default; 
							//Set the correct state for drawing 
							if(dis.itemState == 0x0001) 
								d = DrawItemState.Selected; 
							//Create the DrawItemEventArgs object 
							DrawItemEventArgs e = new DrawItemEventArgs(g,this.Font,r,dis.itemID,d); 
							//If we have a handler attached call it and we don't want the default drawing 
							if(DrawColumn != null && !defaultCustomDraw) 
								DrawColumn(this.Columns[dis.itemID], e); 
							else if(defaultCustomDraw) 
								DoMyCustomHeaderDraw(this.Columns[dis.itemID],e); 
							//Release the graphics object					 
							g.Dispose();					 
						} 
					} 
					catch 
					{ 
						try 
						{ 
							base.WndProc(ref m); 
						} 
						catch{} 
					} 
					break; 
 
				case 0x0002://WM_DESTROY 
					//Release the handle associated with the header control window 
					header.ReleaseHandle(); 
					base.WndProc(ref m); 
					break; 
				case 0x0014://WM_ERASEBKGND 
					if (this.Items.Count==0) 
						base.WndProc(ref m); 
					else 
					{ 
						try 
						{ 
						Brush backBrush=new SolidBrush(BackColor); 
						//up 
						Rectangle clientRect=this.ClientRectangle;//this.GetItemAt(0,0).Index 
						Rectangle rec=clientRect; 
						Graphics g = Graphics.FromHdc(m.WParam); 
						rec.X=clientRect.X; 
						rec.Y=clientRect.Y; 
						rec.Width=clientRect.Width; 
						rec.Height=this.HeaderHeight+2; 
						g.FillRectangle(backBrush,rec); 
						//left 
						Rectangle itemRect=this.GetItemRect(0,ItemBoundsPortion.Entire); 
						rec.Width=itemRect.Left-clientRect.Left+2; 
						rec.Height=clientRect.Height+itemRect.Height+2; 
						if (rec.Width>0) 
						{ 
							g.FillRectangle(backBrush,rec); 
						} 
						//right 
						rec.X=itemRect.Right; 
						rec.Y=clientRect.Top; 
						rec.Width=clientRect.Width-itemRect.Width; 
						rec.Height=clientRect.Height; 
						g.FillRectangle(backBrush,rec); 
						//Debug.WriteLine(rec.ToString()); 
						//bottom 
						itemRect=this.GetItemRect(this.Items.Count-1,ItemBoundsPortion.Entire); 
						rec.X=clientRect.Left; 
						rec.Y=itemRect.Bottom; 
						rec.Width=clientRect.Width; 
						rec.Height=clientRect.Height-rec.Y+clientRect.Width; 
						if (rec.Height>0) 
						{ 
							g.FillRectangle(backBrush,rec); 
						} 
						} 
						catch 
						{ 
							base.WndProc(ref m); 
						} 
					} 
					break; 
				default: 
					try //Message 0x7b WM_CONTEXTMENU can cause exceptions if control is invisible 
					{ 
						base.WndProc(ref m); 
					} 
					catch//(Exception e) 
					{ 
						//Debug.WriteLine(e.ToString()); 
						Visible=true; 
					}  
					break; 
			} 
			 
		} 
 
		#endregion 
 
		#region Drawing methods 
 
		void DrawHeaderBorder(DrawHeaderEventArgs e) 
		{ 
			Graphics g = e.Graphics; 
			Rectangle r = new Rectangle(e.Bounds.Left,e.Bounds.Top,e.Bounds.Width,e.Bounds.Height); 
			if(r.Left == 0) 
				g.DrawLine(/*SystemPens.ControlLightLight*/borderPen,r.Left,r.Bottom,r.Left,r.Top); 
			if(r.Top == 0) 
				g.DrawLine(/*SystemPens.ControlLightLight*/borderPen,r.Left,r.Top,r.Right,r.Top); 
			if(r.Bottom == e.HeaderHeight) 
				g.DrawLine(/*SystemPens.ControlDark*/borderPen,r.Left,r.Bottom-1,r.Right,r.Bottom-1); 
		} 
 
		void DoMyCustomHeaderDraw(object sender, DrawItemEventArgs e) 
		{ 
			ListColumn m = sender as ListColumn;			 
			Graphics g = e.Graphics; 
			//Get the text width 
			SizeF szf = g.MeasureString(m.Text, this.Font); 
			int textWidth = (int)szf.Width+10; 
			Image image = null; 
			 
			Rectangle r = e.Bounds; 
			int leftOffset = 4; 
			int rightOffset = 4; 
			 
			StringFormat s = new StringFormat(); 
			s.FormatFlags = StringFormatFlags.NoWrap; 
			s.Trimming = StringTrimming.EllipsisCharacter; 
			switch(m.TextAlign) 
			{ 
				case HorizontalAlignment.Left: 
					s.Alignment = StringAlignment.Near; 
					break; 
				case HorizontalAlignment.Center: 
					s.Alignment = StringAlignment.Center; 
					break; 
				case HorizontalAlignment.Right: 
					s.Alignment = StringAlignment.Far; 
					break; 
			} 
			s.LineAlignment = StringAlignment.Center; 
			//Adjust the proper text bounds and get the correct image(if any) 
//			if(m.ImageIndex != -1 && headerImages != null) 
//			{ 
//				if(m.ImageIndex + 1 > headerImages.Images.Count) 
//					image = null; 
//				else 
//				{ 
//					if(m.ImageOnRight) 
//						rightOffset += 20; 
//					else 
//						leftOffset += 20; 
//					image = new Bitmap(headerImages.Images[m.ImageIndex],16,16); 
//				} 
//			} 
			if (this.Columns.IndexOf(m)==sortColumn) 
				rightOffset=13; 
			else 
				rightOffset=4; 
			leftOffset=2; 
			if(textWidth+leftOffset+rightOffset > r.Width) 
				textWidth = r.Width - leftOffset - rightOffset; 
			 
			Rectangle text = new Rectangle(r.Left+leftOffset, r.Top,  
				textWidth, r.Height); 
			Rectangle img = Rectangle.Empty; 
			image=null; 
			 
			if(!this.FullyCustomHeader) 
				g.FillRectangle(new SolidBrush(this.headerBackColor),r); 
 
//			if (HeaderImageList.Images.Count>1) 
//			{ 
//				if ((this.Columns.IndexOf(m)==sortColumn)&&(sortOrder==1)) 
//					image=this.HeaderImageList.Images[1]; 
//				if ((this.Columns.IndexOf(m)==sortColumn)&&(sortOrder==-1)) 
//					image=this.HeaderImageList.Images[0]; 
//			}	 
//			if(image != null) 
//			{ 
//				if(m.ImageOnRight) 
//					img = new Rectangle(text.Right+4,(r.Height-16)/2,16,16); 
//				else 
//					img = new Rectangle(r.Left+2,(r.Height-16)/2,16,16); 
//			} 
			if ((this.Columns.IndexOf(m)==sortColumn)&&((e.State & DrawItemState.Selected)==0)) 
			{ 
				img = new Rectangle(text.Right+1,(r.Height-12)/2+5,8,7); 
				if (sortOrder<0) 
					g.DrawLines(m_ArrowPen,new Point[] {new Point(img.Left,img.Top), 
														new Point(img.Right,img.Top), 
														new Point(img.Left+(img.Width/2),img.Bottom-img.Height/2), 
														new Point(img.Left,img.Top)});  
//For Filled arrows uncomment this 
//					g.FillPolygon(Brushes.Black,new Point[] {new Point(img.Left,img.Top), 
//														new Point(img.Right,img.Top), 
//														new Point(img.Left+(img.Width/2),img.Bottom-img.Height/2), 
//														new Point(img.Left,img.Top)});  
				else 
					g.DrawLines(m_ArrowPen,new Point[] {new Point(img.Left,img.Bottom-img.Height/2), 
														new Point(img.Right,img.Bottom-img.Height/2), 
														new Point(img.Left+(img.Width/2),img.Top), 
														new Point(img.Left,img.Bottom-img.Height/2)});  
            } 
 
			//This occurs when column is pressed 
			if ((e.State & DrawItemState.Selected)!=0) 
			{ 
				g.DrawLine(SystemPens.ControlDark,r.Right-1, r.Bottom-1, r.Right-1, r.Top); 
				g.DrawLine(SystemPens.ControlLightLight,r.Right, r.Bottom-1, r.Right, r.Top); 
 
				g.DrawLine(SystemPens.ControlDark,r.Left+2, r.Bottom-3, r.Left+2, r.Top+2); 
				g.DrawLine(SystemPens.ControlDark,r.Left+2, r.Top+2, r.Right-3, r.Top+2); 
				g.DrawLine(SystemPens.ControlLightLight,r.Right-3, r.Top+2, r.Right-3, r.Bottom-3); 
				g.DrawLine(SystemPens.ControlLightLight,r.Right-3, r.Bottom-3, r.Left+2, r.Bottom-3); 
 
				if(image != null) 
				{ 
					img.Offset(1,1); 
					g.DrawImage(image,img); 
					img.Offset(-1,-1); 
				} 
 
				text.Offset(1,1); 
				g.DrawString(m.Text,e.Font,new SolidBrush(headerForeColor),text,s); 
				text.Offset(-1,-1); 
			} 
			//Default state 
			else 
			{ 
				g.DrawLine(new Pen(this.headerBackColor),r.Right-2, r.Bottom, r.Right-2, r.Top); 
				g.DrawLine(new Pen(this.headerBackColor),r.Right-1, r.Bottom, r.Right-1, r.Top); 
 
				g.DrawLine(SystemPens.ControlDark,r.Right-1, r.Bottom-1, r.Right-1, r.Top); 
				g.DrawLine(SystemPens.ControlLightLight,r.Right, r.Bottom-1, r.Right, r.Top); 
				 
				g.DrawString(m.Text,e.Font,new SolidBrush(headerForeColor),text,s); 
				if(image != null) 
					g.DrawImage(image,img); 
				 
			} 
 
		} 
 
		#endregion 
 
		#region InsertColumns Method 
 
		void InsertColumns() 
		{ 
			int counter = 0; 
			foreach(ListColumn m in myColumns) 
			{ 
				Win32.LVCOLUMN lvc = new Win32.LVCOLUMN(); 
				lvc.mask = 0x0001|0x0008|0x0002|0x0004;//LVCF_FMT|LVCF_SUBITEM|LVCF_WIDTH|LVCF_TEXT 
				lvc.cx = m.Width; 
				lvc.subItem = counter; 
				lvc.text = m.Text; 
				switch(m.TextAlign) 
				{ 
					case HorizontalAlignment.Left: 
						lvc.fmt = 0x0000; 
						break; 
					case HorizontalAlignment.Center: 
						lvc.fmt = 0x0002; 
						break; 
					case HorizontalAlignment.Right: 
						lvc.fmt = 0x0001; 
						break; 
				} 
				if(headerImages != null && m.ImageIndex != -1) 
				{ 
					lvc.mask |= 0x0010;//LVCF_IMAGE 
					lvc.iImage = m.ImageIndex; 
					lvc.fmt |= 0x0800;//LVCFMT_IMAGE 
					if(m.ImageOnRight) 
						lvc.fmt |= 0x1000; 
				} 
				//Send message LVN_INSERTCOLUMN 
				Win32.SendMessage(this.Handle,0x1000+97,counter,ref lvc); 
				//Check if column is set to owner-draw 
				//If so - send message HDM_SETITEM with HDF_OWNERDRAW flag set 
				if(m.OwnerDraw) 
				{ 
					Win32.HDITEM hdi = new Win32.HDITEM(); 
					hdi.mask = (int)Win32.HDI.HDI_FORMAT; 
					hdi.fmt = (int)Win32.HDF.HDF_OWNERDRAW; 
					Win32.SendMessage(header.Handle,0x1200+12,counter,ref hdi); 
				} 
				counter++; 
			} 
		} 
 
		#endregion 
 
		#region Public properties 
 
        [DesignerSerializationVisibility(DesignerSerializationVisibility.Content)] 
		public new ListColumnArray Columns 
		{ 
			get{return myColumns;} 
		} 
 
		public int[] HeaderLeft  
		{ 
			get {return m_headerleft;} 
		} 
		public int[] HeaderRight  
		{ 
			get {return m_headerright;} 
		} 
		public ImageList HeaderImageList 
		{ 
			get{return headerImages;} 
			set{headerImages = value;} 
		} 
 
		public bool FullyCustomHeader 
		{ 
			get{return ownerDrawHeader;} 
			set{ownerDrawHeader = value;} 
		} 
 
		public IntPtr HeaderHandle 
		{ 
			get{return header.Handle;} 
		} 
 
		public int IncreaseHeaderHeight 
		{ 
			get{return increaseHeaderHeight;} 
			set 
			{ 
				increaseHeaderHeight = value; 
			} 
		} 
 
		public int HeaderHeight 
		{ 
			get{return headerHeight;} 
		} 
 
		public bool DefaultCustomDraw 
		{ 
			get{return defaultCustomDraw;} 
			set{defaultCustomDraw = value;} 
		} 
 
		#endregion 
 
		#region HeaderControl class 
 
		internal class HeaderControl : NativeWindow 
		{ 
			eLePhantListView parent; 
			bool mouseDown; 
			public HeaderControl(eLePhantListView m) 
			{ 
				parent = m; 
				//Get the header control handle 
				IntPtr header = Win32.SendMessage(parent.Handle, (0x1000+31), IntPtr.Zero, IntPtr.Zero); 
				this.AssignHandle(header);				 
			} 
 
			#region Overriden WndProc 
 
			protected override void WndProc(ref Message m) 
			{ 
				switch(m.Msg) 
				{ 
					case 0x000F://WM_PAINT 
						if(parent.FullyCustomHeader) 
						{ 
							Win32.RECT update = new Win32.RECT(); 
							if(Win32.GetUpdateRect(m.HWnd,ref update, false)==0) 
								break; 
							//Fill the paintstruct 
							Win32.PAINTSTRUCT ps = new Win32.PAINTSTRUCT(); 
							IntPtr hdc = Win32.BeginPaint(m.HWnd, ref ps); 
							//Create graphics object from the hdc 
							Graphics g = Graphics.FromHdc(hdc); 
							//Get the non-item rectangle 
							int left = 0; 
							Win32.RECT itemRect = new Win32.RECT(); 
							for(int i=0; i= ps.rcPaint.left) 
								left = ps.rcPaint.left; 
 
                            Rectangle r = new Rectangle(left, ps.rcPaint.top,  
								ps.rcPaint.right-left, ps.rcPaint.bottom-ps.rcPaint.top); 
							Rectangle r1 = new Rectangle(ps.rcPaint.left, ps.rcPaint.top,  
								ps.rcPaint.right-left, ps.rcPaint.bottom-ps.rcPaint.top); 
 
							g.FillRectangle(new SolidBrush(parent.headerBackColor),r); 
 
							//If we have a valid event handler - call it 
							if(parent.DrawHeader != null && !parent.DefaultCustomDraw) 
								parent.DrawHeader(new DrawHeaderEventArgs(g,r, 
									itemRect.bottom-itemRect.top)); 
							else 
								parent.DrawHeaderBorder(new DrawHeaderEventArgs(g,r, 
									itemRect.bottom-itemRect.top)); 
							//Now we have to check if we have owner-draw columns and fill 
							//the DRAWITEMSTRUCT appropriately 
							int counter = 0; 
							foreach(ListColumn mm in parent.Columns) 
							{ 
								if(mm.OwnerDraw) 
								{ 
									Win32.DRAWITEMSTRUCT dis = new Win32.DRAWITEMSTRUCT(); 
									dis.ctrlType = 100;//ODT_HEADER 
									dis.hwnd = m.HWnd; 
									dis.hdc = hdc; 
									dis.itemAction = 0x0001;//ODA_DRAWENTIRE 
									dis.itemID = counter; 
									//Must find if some item is pressed 
									Win32.HDHITTESTINFO hi = new Win32.HDHITTESTINFO(); 
									hi.pt.X = parent.PointToClient(MousePosition).X;									 
									hi.pt.Y = parent.PointToClient(MousePosition).Y; 
									int hotItem = Win32.SendMessage(m.HWnd, 0x1200+6, 0, ref hi); 
									//If clicked on a divider - we don't have hot item 
									if(hi.flags == 0x0004 || hotItem != counter) 
										hotItem = -1; 
									if(hotItem != -1 && mouseDown) 
										dis.itemState = 0x0001;//ODS_SELECTED 
									else 
										dis.itemState = 0x0020; 
									//HDM_GETITEMRECT 
									Win32.SendMessage(m.HWnd, 0x1200+7, counter, ref itemRect); 
									dis.rcItem = itemRect; 
									//Send message WM_DRAWITEM 
									Win32.SendMessage(parent.Handle,0x002B,0,ref dis); 
								} 
								counter++; 
							} 
							Win32.EndPaint(m.HWnd, ref ps); 
							 
						} 
						else 
							base.WndProc(ref m);						 
						break; 
					case 0x0014://WM_ERASEBKGND 
						//We don't need to do anything here in order to reduce flicker 
						if(parent.FullyCustomHeader) 
							break;						 
						else 
							base.WndProc(ref m); 
						break; 
				case 0x0201://WM_LBUTTONDOWN 
						mouseDown = true; 
						base.WndProc(ref m); 
						break; 
				case 0x0202://WM_LBUTTONUP 
						mouseDown = false; 
						base.WndProc(ref m); 
						break; 
				case 0x1200+5://HDM_LAYOUT 
						base.WndProc(ref m); 
						break; 
				case 0x0030://WM_SETFONT						 
						if(parent.IncreaseHeaderHeight > 0) 
						{ 
							System.Drawing.Font f = new System.Drawing.Font(parent.Font.Name, 
								parent.Font.SizeInPoints + parent.IncreaseHeaderHeight); 
							m.WParam = f.ToHfont(); 
						}						 
                        base.WndProc(ref m);						 
						break; 
					default: 
						base.WndProc(ref m); 
						break; 
				} 
			} 
 
			#endregion 
		} 
 
		#endregion		 
 
		#region Component Designer generated code 
		///  
		/// Required method for Designer support - do not modify 
		/// the contents of this method with the code editor. 
		///  
		private void InitializeComponent() 
		{ 
			components = new System.ComponentModel.Container(); 
		} 
		#endregion 
	#region transformationRoutines 
		public static string SizeToString(uint size) 
		{ 
			return SizeToString((ulong)size); 
		} 
		public static string SizeToString(ulong size) 
		{ 
			if(size==0) return "0"; 
			 
			StringBuilder strB=new StringBuilder(); 
			//strB.Remove(0,strB.Length); 
			 
			if (size<1024)  
			{  
				strB.Append(size); 
				strB.Append(" "+eLePhantForm.Globalization["LBL_BYTE"]); 
			} 
			else if ((size>=1024)&&(size<1048576))  
			{ 
				strB.Append(size/1024); 
				strB.Append(" "+eLePhantForm.Globalization["LBL_KBYTE"]); 
			} 
			else if ((size>=1048576)&&(size<1073741824)) 
			{ 
				strB.Append(((float)size/1048576F).ToString("###0.##")); 
				strB.Append(" "+eLePhantForm.Globalization["LBL_MBYTE"]); 
			} 
			else if (size>=1073741824)  
			{ 
				strB.Append(((float)size/1073741824F).ToString("###0.##")); 
				strB.Append(" "+eLePhantForm.Globalization["LBL_GBYTE"]); 
			} 
			return strB.ToString(); 
		} 
		public static string SpeedToString(float speed) 
		{ 
//			if (speed<1024) return Convert.ToString(speed)+" B/s"; 
//			if (speed<10240) return speed.ToString()+" KB/s"; 
//			if (speed>=102400) return Convert.ToString(speed/1000)+" MB/s"; 
//			return""; 
			StringBuilder strB=new StringBuilder(); 
			strB.Remove(0,strB.Length); 
			if (speed<10240)  
			{ 
				strB.Append(speed); 
				strB.Append(" "+eLePhantForm.Globalization["LBL_KBYTE"]+"/s"); 
			} 
			else  
			{ 
				strB.Append(speed/1024); 
				strB.Append(" "+eLePhantForm.Globalization["LBL_MBYTE"]+"/s"); 
			} 
			return strB.ToString(); 
		} 
		protected string PriorityToString(Types.Constants.Priority priority) 
		{ 
			switch (priority) 
			{ 
				case Types.Constants.Priority.VeryHigh: return eLePhantForm.Globalization["LBL_VERYHIGH"]; 
				case Types.Constants.Priority.High: return eLePhantForm.Globalization["LBL_HIGH"]; 
				case Types.Constants.Priority.Normal: return eLePhantForm.Globalization["LBL_NORMAL"]; 
				case Types.Constants.Priority.Low: return eLePhantForm.Globalization["LBL_LOW"]; 
				case Types.Constants.Priority.VeryLow: return eLePhantForm.Globalization["LBL_VERYLOW"]; 
			} 
			return ""; 
		} 
		protected string ServerPriorityToString(Types.Constants.ServerPriority priority) 
		{ 
			switch (priority) 
			{ 
				case Types.Constants.ServerPriority.High: return eLePhantForm.Globalization["LBL_HIGH"];  
				case Types.Constants.ServerPriority.Normal: return eLePhantForm.Globalization["LBL_NORMAL"]; 
				case Types.Constants.ServerPriority.Low: return eLePhantForm.Globalization["LBL_LOW"]; 
			} 
			return ""; 
		} 
	#endregion 
	} 
 
	#region HeaderEventArgs class 
 
	public class HeaderEventArgs : EventArgs 
	{ 
		int columnIndex; 
		int mouseButton; 
		public HeaderEventArgs(int index, int button) 
		{ 
			columnIndex = index; 
			mouseButton = button; 
		} 
		public int ColumnIndex 
		{ 
			get{return columnIndex;} 
		} 
		public int MouseButton 
		{ 
			get{return mouseButton;} 
		} 
	} 
 
		#endregion 
 
 
	#region DrawHeaderEventArgs class 
 
	public class DrawHeaderEventArgs : EventArgs 
	{ 
		Graphics graphics; 
		Rectangle bounds; 
		int height; 
		public DrawHeaderEventArgs(Graphics dc, Rectangle rect, int h) 
		{ 
			graphics = dc; 
			bounds = rect; 
			height = h; 
		} 
		public Graphics Graphics 
		{ 
			get{return graphics;} 
		}		 
		public Rectangle Bounds 
		{ 
			get{return bounds;} 
		} 
		public int HeaderHeight 
		{ 
			get{return height;} 
		} 
	#endregion 
 
	 
 
	}	 
}