[Mono-winforms-list] patch (implementation of StatusBar and StatusBarPanel)

Aleksey Ryabchuk ryabchuk@yahoo.com
Fri, 14 Mar 2003 08:44:52 -0800 (PST)


--0-1811095656-1047660292=:11174
Content-Type: text/plain; charset=us-ascii
Content-Id: 
Content-Disposition: inline

regards
Aleksey

__________________________________________________
Do you Yahoo!?
Yahoo! Web Hosting - establish your business online
http://webhosting.yahoo.com
--0-1811095656-1047660292=:11174
Content-Type: text/plain; name=patch
Content-Description: patch
Content-Disposition: inline; filename=patch

Index: Control.cs
===================================================================
RCS file: /mono/mcs/class/System.Windows.Forms/System.Windows.Forms/Control.cs,v
retrieving revision 1.28
diff -u -r1.28 Control.cs
--- Control.cs	1 Mar 2003 21:20:31 -0000	1.28
+++ Control.cs	14 Mar 2003 16:35:25 -0000
@@ -2445,9 +2445,9 @@
 					break;
     			case Msg.WM_KEYUP:
     				// FIXME:
-    				// OnKeyUp (eventArgs);
-					CallControlWndProc(ref m);
-					break;
+    				OnKeyUp ( new KeyEventArgs ( (Keys)m.WParam.ToInt32() ) );
+				CallControlWndProc(ref m);
+				break;
     			case Msg.WM_KILLFOCUS:
     				OnLeave (eventArgs);
     				OnLostFocus (eventArgs);
Index: Panel.cs
===================================================================
RCS file: /mono/mcs/class/System.Windows.Forms/System.Windows.Forms/Panel.cs,v
retrieving revision 1.9
diff -u -r1.9 Panel.cs
--- Panel.cs	6 Feb 2003 03:45:10 -0000	1.9
+++ Panel.cs	14 Mar 2003 16:35:25 -0000
@@ -18,6 +18,7 @@
 
 	public class Panel : ScrollableControl {
 
+		BorderStyle borderStyle = BorderStyle.None;
 		//
 		//  --- Constructor
 		//
@@ -32,10 +33,10 @@
 		[MonoTODO]
 		public BorderStyle BorderStyle {
 			get {
-				throw new NotImplementedException ();
+				return borderStyle;
 			}
 			set {
-				//FIXME:
+				borderStyle = value;
 			}
 		}
 
@@ -69,9 +70,6 @@
 			get {
 				if( Parent != null) {
 					CreateParams createParams = base.CreateParams;
-					if( window == null) {
-						window = new ControlNativeWindow (this);
-					}
 
 					createParams.Caption = Text;
 					createParams.X = Left;
@@ -85,6 +83,16 @@
 					createParams.Style = (int) (
 						WindowStyles.WS_CHILD | 
 						WindowStyles.WS_VISIBLE);
+
+					switch (BorderStyle) {
+					case BorderStyle.Fixed3D:
+						createParams.ExStyle |= (int)WindowExStyles.WS_EX_CLIENTEDGE;
+					break;
+					case BorderStyle.FixedSingle:
+						createParams.Style   |= (int)WindowStyles.WS_BORDER;
+					break;
+					}
+
 					return createParams;
 				}
 				return null;
Index: StatusBar.cs
===================================================================
RCS file: /mono/mcs/class/System.Windows.Forms/System.Windows.Forms/StatusBar.cs,v
retrieving revision 1.11
diff -u -r1.11 StatusBar.cs
--- StatusBar.cs	10 Dec 2002 03:02:48 -0000	1.11
+++ StatusBar.cs	14 Mar 2003 16:35:25 -0000
@@ -5,6 +5,7 @@
 //   stubbed out by Daniel Carrera (dcarrera@math.toronto.edu)
 //   stubbed out by Richard Baumann (biochem333@nyc.rr.com)
 //   Dennis Hayes (dennish@Raytek.com)
+//   Aleksey Ryabchuk (ryabchuk@yahoo.com)
 //
 // (C) 2002 Ximian, Inc
 //
@@ -13,6 +14,7 @@
 using System.Collections;
 using System.Drawing;
 using System.ComponentModel;
+using System.Runtime.InteropServices;
 
 namespace System.Windows.Forms {
 
@@ -21,53 +23,50 @@
 	// </summary>
 	public class StatusBar : Control {
 
-		//
-		//  --- Private Fields
-		//
-		private bool showPanels;
 		private bool sizingGrip;
+		private bool showPanels;
+		private StatusBarPanelCollection panels;
+		private string  stext;
+		private const int GripSize = 16;   // FIXME: get size from SystemMetrics
+		private const int PanelGap = 2;    // FIXME: get size from StatusBar
+		private const int TextOffset = 3;
+		internal DockStyle dockstyle;
 
-		//
-		//  --- Constructors/Destructors
-		//
-		[MonoTODO]
 		public StatusBar() : base()
 		{
 			Dock = DockStyle.Bottom;
 			showPanels = false;
 			sizingGrip = true;
+			Size = DefaultSize;
 		}
 
-		//
-		//  --- Public Methods
-		//
-		[MonoTODO]
 		public override string ToString()
 		{
-			//FIXME:
-			return base.ToString();
+			string str = "System.Windows.Forms.StatusBar, Panels.Count: ";
+			str += Panels.Count;
+			for ( int i = 0; i < Panels.Count ; i++ ) {
+				
+				str += ", Panels[" + i + "]: " + Panels[i].ToString ( );
+			}
+			return str;
 		}
 
-		//
-		//  --- Protected Methods
-		//
 		[MonoTODO]
 		protected override void CreateHandle()
 		{
 			base.CreateHandle();
 		}
 
-		[MonoTODO]
 		protected virtual void OnDrawItem(StatusBarDrawItemEventArgs e)
 		{
-			//FIXME:
+			if( DrawItem != null)
+				DrawItem ( this, e );
 		}
 
-		[MonoTODO]
 		protected override void OnHandleCreated(EventArgs e)
 		{
-			//FIXME:
 			base.OnHandleCreated(e);
+			SetPanelsImpl ( );
 		}
 
 		[MonoTODO]
@@ -91,60 +90,65 @@
 			base.OnMouseDown(e);
 		}
 
-		[MonoTODO]
 		protected virtual void OnPanelClick(StatusBarPanelClickEventArgs e)
 		{
-			//FIXME:
+			if ( PanelClick != null )
+				PanelClick ( this , e );
 		}
 
 		[MonoTODO]
 		protected override void OnResize(EventArgs e)
 		{
-			//FIXME:
+			UpdatePanels( true, false, null );
 			base.OnResize(e);
 		}
 
 		[MonoTODO]
 		protected override void WndProc(ref Message m)
 		{
-			//FIXME:
-			base.WndProc(ref m);
+			switch ( m.Msg ) {
+			case Msg.WM_DRAWITEM:
+				DRAWITEMSTRUCT dis = new DRAWITEMSTRUCT();
+				dis = (DRAWITEMSTRUCT)Marshal.PtrToStructure( m.LParam, dis.GetType() );
+				
+				if ( dis.itemID < Panels.Count ) {
+					OnDrawItem (
+						new StatusBarDrawItemEventArgs (
+						Graphics.FromHdc ( dis.hDC ),
+						Font,
+						new Rectangle(  dis.rcItem.left,
+						dis.rcItem.top,
+						dis.rcItem.right - dis.rcItem.left,
+						dis.rcItem.bottom - dis.rcItem.top),
+						dis.itemID,
+						(DrawItemState)dis.itemState,
+						Panels[dis.itemID] ) );
+				}
+				m.Result = (IntPtr)1;
+			break;
+			case Msg.WM_NOTIFY:
+				// FIXME
+			break;
+			default:
+				base.WndProc(ref m);
+			break;
+			}
 		}
 
-		//
-		//  --- Public Events
-		//
 		public event StatusBarDrawItemEventHandler DrawItem;
 		public event StatusBarPanelClickEventHandler PanelClick;
 
-		//
-		//  --- Public Properties
-		//
-		[MonoTODO]
 		public override Color BackColor {
-
-			get {
-				throw new NotImplementedException ();
-			}
-			set {
-				throw new NotImplementedException ();
-			}
+			get {	return base.BackColor;	}
+			set {	base.BackColor = value;	}
 		}
 
-		[MonoTODO]
 		public override Image BackgroundImage {
-
-			get {
-				throw new NotImplementedException ();
-			}
-			set {
-				throw new NotImplementedException ();
-			}
+			get {	return base.BackgroundImage;	}
+			set {	base.BackgroundImage = value;	}
 		}
 
-		//just to get it to run
 		//FIXME:
-		internal DockStyle dockstyle;
 		[MonoTODO]
 		public override DockStyle Dock {
 			get {
@@ -155,62 +159,69 @@
 			}
 		}
 
-		[MonoTODO]
 		public override Font Font {
 
-			get { throw new NotImplementedException (); }
-			set { throw new NotImplementedException (); }
+			get { return base.Font; }
+			set { base.Font = value; }
 		}
 
-		[MonoTODO]
 		public override Color ForeColor {
 
-			get { throw new NotImplementedException (); }
-			set { throw new NotImplementedException (); }
+			get { return base.ForeColor; }
+			set { base.ForeColor = value; }
 		}
 
-		[MonoTODO]
 		public new ImeMode ImeMode {
 
-			get { throw new NotImplementedException (); }
-			set { throw new NotImplementedException (); }
+			get { return DefaultImeMode; }
+			set {  }
 		}
 
-		[MonoTODO]
 		public StatusBar.StatusBarPanelCollection Panels {
-
-			get { throw new NotImplementedException (); }
+			get { 
+				if( panels == null )
+					panels = new StatusBar.StatusBarPanelCollection( this );
+				return panels;
+			}
 		}
 
-		[MonoTODO]
-		public bool ShowPanels {// default false {
-
-			get { throw new NotImplementedException (); }
-			set { throw new NotImplementedException (); }
+		public bool ShowPanels {
+			get { return showPanels; }
+			set {
+				showPanels = value; 
+				SetPanelsImpl ( );
+			}
 		}
 
 		[MonoTODO]
-		public bool SizingGrip // default true {
+		public bool SizingGrip
 		{
-			get { throw new NotImplementedException (); }
-			set { throw new NotImplementedException (); }
+			get { return sizingGrip; }
+			set { 
+				// the only way to get rid of the grip dynamically
+				// is to recreate window
+				bool recreate = sizingGrip != value;
+				sizingGrip = value;
+				if ( IsHandleCreated && recreate )
+					RecreateHandle();
+			}
 		}
 
 		[MonoTODO]
 		public new bool TabStop {
-
-			get { throw new NotImplementedException (); }
-			set { throw new NotImplementedException (); }
+			get { return false; }
+			set {  } 
 		}
 
 		[MonoTODO]
 		public override string Text {
-
-			get { 
-				return base.Text;
+			get {   // should reuse base.Text ?
+				return stext;
 			}
 			set {
-				base.Text = value;
+				stext = value;
+				if ( IsHandleCreated )
+					UpdateStatusText ( );
 			}
 		}
 
@@ -219,13 +230,11 @@
 		//
 		[MonoTODO]
 		protected override CreateParams CreateParams {
-
 			get {
 				CreateParams createParams = new CreateParams ();
-				window = new ControlNativeWindow (this);
 
 				createParams.Caption = Text;
-				createParams.ClassName = "STATUSBAR";
+				createParams.ClassName = "msctls_statusbar32";
 				createParams.X = Left;
 				createParams.Y = Top;
 				createParams.Width = Width;
@@ -233,25 +242,169 @@
 				createParams.ClassStyle = 0;
 				createParams.ExStyle = 0;
 				createParams.Param = 0;
-				//			createParams.Parent = Parent.Handle;
+				createParams.Parent = Parent.Handle;
 				createParams.Style = (int) (
 					WindowStyles.WS_CHILD | 
-					WindowStyles.WS_VISIBLE);
-				window.CreateHandle (createParams);
+					WindowStyles.WS_VISIBLE |
+					WindowStyles.WS_OVERLAPPED |
+					WindowStyles.WS_CLIPCHILDREN |
+					WindowStyles.WS_CLIPCHILDREN );
+
+				if( SizingGrip )
+					createParams.Style |= (int)StatusbarControlStyles.SBARS_SIZEGRIP;
+
+				createParams.Style |= (int)StatusbarControlStyles.SBT_TOOLTIPS;
+
 				return createParams;
 			}		
 		}
 
-		[MonoTODO]
 		protected override ImeMode DefaultImeMode {
-
-			get { throw new NotImplementedException (); }
+			get { return ImeMode.Disable; }
 		}
 
-		[MonoTODO]
 		protected override Size DefaultSize {
-
-			get { throw new NotImplementedException (); }
+			get { return new Size ( 100, 22 ); }
+		}
+		
+		internal  void UpdateParts ( ) 	{
+			if ( Panels.Count > 0) {
+				int[] array = new int[ panels.Count ];
+
+				CalculatePanelWidths ( array );
+				int size = array.Length;
+
+				IntPtr buffer = Marshal.AllocCoTaskMem( Marshal.SizeOf( size ) * size );
+				Marshal.Copy( array, 0, buffer, size );
+				Win32.SendMessage( Handle, (int)StatusbarMessages.SB_SETPARTS, size, buffer.ToInt32() );
+				Win32.SendMessage( Handle, (int)StatusbarMessages.SB_SIMPLE, 0, 0 );
+				Marshal.FreeCoTaskMem( buffer );
+			}
+			else {
+				Win32.SendMessage( Handle, (int)StatusbarMessages.SB_SIMPLE, 1, 0 );
+				UpdateStatusText ( );
+			}
+		}
+
+		internal  void UpdateText ( StatusBarPanel p ) {
+			// if p is not null then this call is request to 
+			// update text in some specific panel
+			for (int i = 0; i < panels.Count; i++ ) {
+				if ( p != null && p != panels[i] )
+					continue;
+
+				int DrawStyle = i;
+						
+				if ( panels[i].Style == StatusBarPanelStyle.OwnerDraw )
+					DrawStyle |= (int)StatusbarDrawType.SBT_OWNERDRAW;
+
+				switch ( panels[i].BorderStyle ) 
+				{
+					case StatusBarPanelBorderStyle.None:
+						DrawStyle |= (int)StatusbarDrawType.SBT_NOBORDERS;
+						break;
+					case StatusBarPanelBorderStyle.Raised:
+						DrawStyle |= (int)StatusbarDrawType.SBT_POPOUT;
+						break;
+				}
+
+				string TextToSet;
+				
+				switch ( panels[i].Alignment ) {
+				case HorizontalAlignment.Center:
+					TextToSet = panels[i].Text.Insert( 0, "\t" );
+				break;
+				case HorizontalAlignment.Right:
+					TextToSet = panels[i].Text.Insert( 0, "\t\t" );
+				break;
+				default:
+					TextToSet = panels[i].Text;
+				break;
+				}
+
+				Win32.SendMessage( Handle, (int)StatusbarMessages.SB_SETTEXT, DrawStyle,
+							TextToSet );
+			}
+		}
+
+		internal  void UpdateToolTips ( StatusBarPanel p ) {
+			// if p == null set tooltips for each panel
+			for (int i = 0; i < panels.Count; i++ ) {
+				if ( p != null && p != panels[i] )
+					continue;
+
+				Win32.SendMessage ( Handle, (int)StatusbarMessages.SB_SETTIPTEXT, i ,
+							panels[i].ToolTipText );
+			}
+		}
+
+		internal  void UpdatePanels ( bool updateParts, bool updateText, StatusBarPanel p ) {
+			if ( IsHandleCreated ) {
+				if ( updateParts )
+					UpdateParts ( );
+
+				if ( updateText )
+					UpdateText( p );
+
+				Invalidate( );
+			}
+		}
+
+		protected void CalculatePanelWidths ( int[] array ) {
+			int[] WidthArray = new int[panels.Count];
+
+			int FixedWidth = ClientSize.Width - (SizingGrip == true ? GripSize : 0);
+			int NumSpringPanels = 0;
+
+			for (int i = 0; i < panels.Count; i++ )	{
+				switch ( panels[i].AutoSize ) {
+				case StatusBarPanelAutoSize.None: 
+					WidthArray[i] = panels[i].Width + (PanelGap + TextOffset)*2;
+				break;
+				case StatusBarPanelAutoSize.Contents:
+					WidthArray[i] = panels[i].GetContentWidth( ) + (PanelGap + TextOffset)*2;
+				break;
+				default:
+					WidthArray[i] = 0;
+					NumSpringPanels++;
+				break;
+				}
+				FixedWidth   -= WidthArray[i];
+			}
+
+			int SpringPanelLength = 0;
+			if ( NumSpringPanels > 0 && FixedWidth > 0)
+				SpringPanelLength = FixedWidth / NumSpringPanels;
+
+			for (int i = 0; i < panels.Count; i++ )	{
+				if ( panels[i].AutoSize == StatusBarPanelAutoSize.Spring) 
+					WidthArray[i] = SpringPanelLength > panels[i].MinWidth ? 
+							SpringPanelLength : panels[i].MinWidth;
+			}
+
+			for (int i = 0; i < panels.Count; i++ )
+				array[i] = WidthArray[i] + (i == 0 ? 0 : array[i - 1]);
+		}
+
+		internal  void UpdateStatusText ( ){
+			Win32.SendMessage( Handle, (int)StatusbarMessages.SB_SETTEXT,
+						255 | (int)StatusbarDrawType.SBT_NOBORDERS, Text );
+		}
+
+		internal  void SetPanelsImpl ( ) {
+			if( IsHandleCreated ) {
+				if ( base.Font.ToHfont ( ) != IntPtr.Zero )
+					Win32.SendMessage ( Handle, Msg.WM_SETFONT, base.Font.ToHfont().ToInt32(), 0 );
+
+				if( panels == null || panels.Count == 0 || showPanels == false) {
+					Win32.SendMessage( Handle, (int)StatusbarMessages.SB_SIMPLE, 1, 0 );
+					UpdateStatusText ( );
+				}
+				else {
+					UpdatePanels ( true, true, null );
+					UpdateToolTips ( null );
+				}
+			}
 		}
 
 		//
@@ -267,229 +420,179 @@
 		//	Represents the collection of panels in a StatusBar control.
 		// </summary>
 		public class StatusBarPanelCollection : IList, ICollection, IEnumerable {
-
-			//
-			//  --- Private Fields
-			//
 			private ArrayList list;
 			private StatusBar owner;
-			private static string class_string = "System.Windows.Forms.StatusBar.StatusBarPanelCollection::";
 
-			//
-			//  --- Constructors/Destructors
-			//
-			StatusBarPanelCollection(StatusBar owner) : base()
-			{
+			public StatusBarPanelCollection( StatusBar owner ) : base() {
 				list = new ArrayList();
 				this.owner = owner;
 			}
 
-			//
-			//  --- Public Methods
-			//
-			[MonoTODO]
-			public virtual int Add(StatusBarPanel panel)
-			{
-				string method_string = "Add(StatusBarPanel) ";
-				if (panel == null) {
+			public virtual int Add( StatusBarPanel value ) {
+				if (value == null)
+					throw new ArgumentNullException("value");
 
-					throw new ArgumentNullException(class_string + method_string + "panel == null");
-				}
-				if (panel.Parent == null) {
+				if (value.Parent != null)
+					throw new ArgumentException("Object already has a parent.", "value");
 
-					throw new ArgumentException(class_string + method_string + "panel.Parent != null");
-				}
-				// FIXME: StatusBarPanel.Parent is readonly!
-				//panel.Parent = owner;
-				return list.Add(panel);
+				value.SetParent( owner );
+				int Index = list.Add( value );
+
+				owner.UpdatePanels ( true, true, null );
+				return Index;
 			}
 
-			[MonoTODO]
-			public virtual StatusBarPanel Add(string s)
-			{
-				throw new NotImplementedException ();
-			//	StatusBarPanel tmp = new StatusBarPanel();
-			//	tmp.Text = s;
-			//	// FIXME: StatusBarPanel.Parent is readonly!
-			//	//tmp.Parent = owner;
-			//	list.Add(tmp);
-			//	return tmp;
+			public virtual StatusBarPanel Add( string text ) {
+				StatusBarPanel panel = new StatusBarPanel();
+				panel.Text = text;
+				this.Add ( panel );
+				return panel;
 			}
 
-			[MonoTODO]
-			public virtual void AddRange(StatusBarPanel[] panels)
-			{
-				string method_string = "AddRange(StatusBarPanel[]) ";
-				if (panels == null) {
+			public virtual void AddRange(StatusBarPanel[] panels) {
+				if (panels == null)
+					throw new ArgumentNullException("panels");
+
+				// do we need to check for panel.Parent
+				// like it is done in Add(StatusBarPanel) ?
+
+				for (int i = 0; i < panels.Length; i++)
+					panels[i].SetParent( owner );
 
-					throw new ArgumentNullException(class_string + method_string + "panels == null");
-				}
-				for (int i = 0; i < panels.Length; i++) {
-					// FIXME: StatusBarPanel.Parent is readonly!
-					//panels[i].Parent = owner;
-				}
 				list.AddRange(panels);
+				owner.UpdatePanels ( true, true, null );
 			}
 
-			public virtual void Clear()
-			{
+			public virtual void Clear() {
+				for (int i = 0; i < list.Count; i++ )
+					((StatusBarPanel)list[i]).SetParent ( null );
+
 				list.Clear();
+				owner.UpdatePanels ( true, true, null );
 			}
 
-			public bool Contains(StatusBarPanel panel)
-			{
+			public bool Contains(StatusBarPanel panel) {
 				return list.Contains(panel);
 			}
 
-			public IEnumerator GetEnumerator()
-			{
+			public IEnumerator GetEnumerator() {
 				return list.GetEnumerator();
 			}
 
-			public int IndexOf(StatusBarPanel panel)
-			{
+			public int IndexOf(StatusBarPanel panel) {
 				return list.IndexOf(panel);
 			}
 
-			[MonoTODO]
-			public virtual void Insert(int index, StatusBarPanel panel)
-			{
-				string method_string = "Insert(int,StatusBarPanel) ";
-				if (panel == null) {
+			public virtual void Insert(int index, StatusBarPanel value) {
+				if (value == null)
+					throw new ArgumentNullException ( "value" );
 
-					throw new ArgumentNullException(class_string + method_string + "panel == null");
-				}
-				if (panel.Parent == null) {
+				if (value.Parent != null)
+					throw new ArgumentException ( "Object already has a parent.", "value" );
 
-					throw new ArgumentException(class_string + method_string + "panel.Parent != null");
-				}
-				if  (panel.AutoSize != StatusBarPanelAutoSize.None &&
-				     panel.AutoSize != StatusBarPanelAutoSize.Contents &&
-				     panel.AutoSize != StatusBarPanelAutoSize.Spring)
-				{
-					throw new InvalidEnumArgumentException(class_string + method_string + "panel.AutoSize is not a valid StatusBarPanelAutoSize value");
-				}
-				list.Insert(index,panel);
-				
-				                      // do this after insert because insert does the range checking and might throw an exception
-				// FIXME: StatusBarPanel.Parent is readonly!
-				// panel.Parent = owner; // a rethrow for a better exception message, or an extra range check, would incur an unnecessary performance cost
-			}
+				if (index < 0 || index > Count )
+					throw new ArgumentOutOfRangeException( "index" );
 
-			public virtual void Remove(StatusBarPanel panel)
-			{
-				string method_string = "Remove(StatusBarPanel) ";
-				if (panel == null) {
+				// very strange place to check autosize property :-))
+				if ( !Enum.IsDefined ( typeof(StatusBarPanelAutoSize), value.AutoSize ) )
+					throw new InvalidEnumArgumentException( "AutoSize",
+						(int)value.AutoSize,
+						typeof(StatusBarPanelAutoSize));
 
-					throw new ArgumentNullException(class_string + method_string + "panel == null");
-				}
-				list.Remove(panel);
+				list.Insert(index, value);
+				value.SetParent ( owner ); 
+				owner.UpdatePanels ( true, true , null );
 			}
 
-			public virtual void RemoveAt(int index)
-			{
-				list.RemoveAt(index);
+			public virtual void Remove(StatusBarPanel value) {
+				if (value == null)
+					throw new ArgumentNullException( "value" );
+
+				list.Remove( value );
+				value.SetParent ( null );
 			}
 
-			void ICollection.CopyTo(Array dest, int index)
-			{
-				string method_string = "ICollection.CopyTo(Array,int) ";
-				if (dest == null) {
+			public virtual void RemoveAt(int index)	{
+				if (index < 0 || index > Count )
+					throw new ArgumentOutOfRangeException( "index" );
 
-					throw new ArgumentNullException(class_string + method_string + "array == null");
-				}
-				if (index < 0) {
+				StatusBarPanel p = (StatusBarPanel)list[index];
+				list.RemoveAt(index);
+				p.SetParent ( null );
+				owner.UpdatePanels( true, true, null );
+			}
 
-					throw new ArgumentOutOfRangeException(class_string + method_string + "index < 0");
-				}
-				if (dest.Rank != 1) {
+			[MonoTODO]
+			// This member supports the .NET Framework 
+			void ICollection.CopyTo(Array array, int index)	{
+				if (array == null)
+					throw new ArgumentNullException ( "array" );
 
-					throw new ArgumentException(class_string + method_string + "array is multidimensional");
-				}
-				if (index >= dest.Length) {
+				if (index < 0)
+					throw new ArgumentOutOfRangeException ( "index" );
 
-					throw new ArgumentException(class_string + method_string + "index >= array.Length");
-				}
-				if (Count+index >= dest.Length) {
+				if (array.Rank != 1 || index >= array.Length || Count+index >= array.Length)
+					throw new ArgumentException ( ); // FIXME: messages
 
-					throw new ArgumentException(class_string + method_string + "insufficient array capacity");
-				}
 				// easier/quicker to let the runtime throw the invalid cast exception if necessary
-				for (int i = 0; index < dest.Length; i++, index++) {
-
-					dest.SetValue(list[i], index);
-				}
+				for (int i = 0; index < array.Length; i++, index++)
+					array.SetValue(list[i], index);
 			}
-
+			
+			[MonoTODO]
 			int IList.Add(object panel)
 			{
-				string method_string = "IList.Add(object) ";
-				if (!(panel is StatusBarPanel)) {
-
-					throw new ArgumentException(class_string + method_string + "panel is not a StatusBarPanel");
-				}
+				if (!(panel is StatusBarPanel))
+					throw new ArgumentException();//FIXME: message
 				return Add((StatusBarPanel) panel);
 			}
 
 			bool IList.Contains(object panel)
 			{
-				if (!(panel is StatusBarPanel)) {
-
+				if (!(panel is StatusBarPanel))
 					return false;
-				}
 				return Contains((StatusBarPanel) panel);
 			}
 
-			int IList.IndexOf(object panel)
-			{
-				if (!(panel is StatusBarPanel)) {
-
+			int IList.IndexOf(object panel)	{
+				if (!(panel is StatusBarPanel))
 					return -1;
-				}
 				return IndexOf((StatusBarPanel) panel);
 			}
 
+			[MonoTODO]
 			void IList.Insert(int index, object panel)
 			{
-				string method_string = "IList.Insert(int,object) ";
-				if (!(panel is StatusBarPanel)) {
+				if (!(panel is StatusBarPanel))
+					throw new ArgumentException();//FIXME: message
 
-					throw new ArgumentException(class_string + method_string + "panel is not a StatusBarPanel");
-				}
 				Insert(index, (StatusBarPanel) panel);
 			}
 
+			[MonoTODO]
 			void IList.Remove(object panel)
 			{
-				string method_string = "IList.Remove(object) ";
-				if (!(panel is StatusBarPanel)) {
+				if (!(panel is StatusBarPanel))
+					throw new ArgumentException(); //FIXME: message
 
-					throw new ArgumentException(class_string + method_string + "panel is not a StatusBarPanel");
-				}
 				Remove((StatusBarPanel) panel);
 			}
 
 			
-			//  --- Public Properties
-			[MonoTODO]
 			public int Count {
-				get { throw new NotImplementedException (); }
-				//get { return list.Count; }
+				get { return list.Count; }
 			}
 
 			public bool IsReadOnly {
-
 				get { return false; }
 			}
 
 			object IList.this[int index] {
-
 				get { return this[index]; }
-				set { this[index]=(StatusBarPanel)value; }
+				set { this[index]= (StatusBarPanel)value; }
 			}
 
 			public virtual StatusBarPanel this[int index] {
-
 				get
 				{
 					// The same checks are done by the list, so this is redundant
@@ -540,24 +643,7 @@
 				[MonoTODO] get { throw new NotImplementedException (); }
 			}
 			
-			
-			//  --- Private Properties
-			
 			private bool IsFixedSize { get { return false; } }
-
-//			private object ILList.this[int index]
-//			{
-//				get { return (StatusBarPanel) this[index]; }
-//				set
-//				{
-//					string method_string = "IList.set_Item(int,object) ";
-//					if (!(value is StatusBarPanel))
-//					{
-//						throw new ArgumentException(class_string + method_string + "panel is not a StatusBarPanel");
-//					}
-//					this[index] = (StatusBarPanel) value;
-//				}
-//			}
 		}
 	}
 }
Index: StatusBarPanel.cs
===================================================================
RCS file: /mono/mcs/class/System.Windows.Forms/System.Windows.Forms/StatusBarPanel.cs,v
retrieving revision 1.10
diff -u -r1.10 StatusBarPanel.cs
--- StatusBarPanel.cs	4 Dec 2002 01:35:41 -0000	1.10
+++ StatusBarPanel.cs	14 Mar 2003 16:35:25 -0000
@@ -4,6 +4,7 @@
 // Author:
 //   stubbed out by Richard Baumann (biochem333@nyc.rr.com)
 //   Dennis Hayes (dennish@Raytek.com)
+//   Aleksey Ryabchuk (ryabchuk@yahoo.com)
 //
 // (C) Ximian, Inc., 2002
 //
@@ -31,101 +32,170 @@
 		private string text;
 		private string toolTipText;
 		private int width;
+		private bool suppressUpdates;
 
 		//
 		//  --- Constructors/Destructors
 		//
-		StatusBarPanel() : base()
+		public StatusBarPanel() : base()
 		{
 			alignment = HorizontalAlignment.Left;
 			autoSize = StatusBarPanelAutoSize.None;
 			borderStyle = StatusBarPanelBorderStyle.Sunken;
-			icon = null;
 			minWidth = 10;
 			style = StatusBarPanelStyle.Text;
-			text = "";
-			toolTipText = "";
 			width = 100;
+			suppressUpdates = false;
 		}
 
 		//
 		//  --- Public Methods
 		//
-		[MonoTODO]
 		public void BeginInit()
 		{
-			//FIXME:
+			suppressUpdates = true;
 		}
-		[MonoTODO]
+
 		public void EndInit()
 		{
-			//FIXME:
+			suppressUpdates = false;
+			UpdateParent( true, true, null );
 		}
+
 		public override string ToString()
 		{
-			return text;
+			return "StatusBarPanel: {" + Text + "}";
 		}
 		//
 		//  --- Public Properties
 		//
 		public HorizontalAlignment Alignment {
-
 			get { return alignment; }
-			set { alignment = value; }
+			set {
+				if ( !Enum.IsDefined ( typeof(HorizontalAlignment), value ) )
+					throw new InvalidEnumArgumentException( "Alignment",
+						(int)value,
+						typeof(HorizontalAlignment));
+
+				alignment = value; 
+				UpdateParent ( false, true, this );
+			}
 		}
-		public StatusBarPanelAutoSize AutoSize {
 
+		public StatusBarPanelAutoSize AutoSize {
 			get { return autoSize; }
 			set
 			{
-				if  (value != StatusBarPanelAutoSize.None && value != StatusBarPanelAutoSize.Contents && value != StatusBarPanelAutoSize.Spring) {
-
-					throw new InvalidEnumArgumentException(
-						"System.Windows.Forms.StatusBarPanel::set_AutoSize(StatusBarPanelAutoSize) " +
-						"value is not a valid StatusBarPanelAutoSize value");
-				}
+				if ( !Enum.IsDefined ( typeof(StatusBarPanelAutoSize), value ) )
+					throw new InvalidEnumArgumentException( "AutoSize",
+										(int)value,
+										typeof(StatusBarPanelAutoSize));
 				autoSize = value;
+				UpdateParent ( true, false, null );
 			}
 		}
-		public StatusBarPanelBorderStyle BorderStyle {
 
+		public StatusBarPanelBorderStyle BorderStyle {
 			get { return borderStyle; }
-			set { borderStyle = value; }
+			set { 
+				if ( !Enum.IsDefined ( typeof(StatusBarPanelBorderStyle), value ) )
+					throw new InvalidEnumArgumentException( "BorderStyle",
+						(int)value,
+						typeof(StatusBarPanelBorderStyle));
+
+				borderStyle = value;
+				UpdateParent ( false, true, this );
+			}
 		}
-		public Icon Icon {
 
+		public Icon Icon {
 			get { return icon; }
-			set { icon = value; }
+			set { 
+				icon = value; 
+				UpdateParent (  true, false, null );
+			}
 		}
-		public int MinWidth {
 
+		public int MinWidth 
+		{
 			get { return minWidth; }
-			set { minWidth = value; }
+			set { 
+				if ( value < 0 )
+					throw new ArgumentException(
+					string.Format("'{0}' is not a valid value for 'value'. 'value' must be greater than or equal to 0.",
+							value ) ) ;
+				minWidth = value;
+				UpdateParent ( true, false, null );
+			}
 		}
-		public StatusBar Parent {
 
+		public StatusBar Parent {
 			get { return parent; }
-			set { parent = value; }
 		}
-		public StatusBarPanelStyle Style {
 
+		public StatusBarPanelStyle Style {
 			get { return style; }
-			set { style = value; }
+			set { 
+				if ( !Enum.IsDefined ( typeof(StatusBarPanelStyle), value ) )
+					throw new InvalidEnumArgumentException( "Style",
+						(int)value,
+						typeof(StatusBarPanelStyle));
+				style = value; 
+				UpdateParent ( false, true, this );
+			}
 		}
-		public string Text {
 
+		public string Text {
 			get { return text; }
-			set { text = value; }
+			set { 
+				text = value;
+				UpdateParent ( AutoSize == StatusBarPanelAutoSize.Contents, true, this );
+			}
 		}
-		public string ToolTipText {
 
+		public string ToolTipText 
+		{
 			get { return toolTipText; }
-			set { toolTipText = value; }
+			set { 
+				toolTipText = value;
+				UpdateTooltips ( this );
+			}
 		}
-		public int Width {
 
+		public int Width {
 			get { return width; }
-			set { width = value; }
+			set { 
+				// According to MS documentation this method
+				// should throw ArgumentException if value < MinWidth,
+				// but it does not actually happens.
+				if ( value < MinWidth )
+					width = MinWidth; 
+				else
+					width = value;
+				UpdateParent ( true, false, null );
+			}
+		}
+
+		public int GetContentWidth ( ) {
+			if( Parent != null) {
+				int cxsize = Win32.GetTextExtent( Parent.Handle, Text ).cx;
+				return cxsize < MinWidth ? MinWidth : cxsize;
+			}
+			return Width;
+		}
+
+		private void UpdateParent (  bool UpdateParts, bool UpdateText, StatusBarPanel p ) {
+			if ( Parent != null && suppressUpdates != true)
+				Parent.UpdatePanels ( UpdateParts, UpdateText, p );
+		}
+
+		private void UpdateTooltips ( StatusBarPanel p ) {
+			if ( Parent != null && suppressUpdates != true)
+				Parent.UpdateToolTips ( p );
+		}
+
+		internal void SetParent ( StatusBar prnt ) {
+			parent = prnt;
 		}
 	}
 }
Index: win32Enums.cs
===================================================================
RCS file: /mono/mcs/class/System.Windows.Forms/System.Windows.Forms/win32Enums.cs,v
retrieving revision 1.8
diff -u -r1.8 win32Enums.cs
--- win32Enums.cs	9 Mar 2003 17:38:41 -0000	1.8
+++ win32Enums.cs	14 Mar 2003 16:35:26 -0000
@@ -2381,6 +2381,49 @@
 		TB_ENDTRACK         =    8
 	}
 
+	#region StatusBar Control Styles
+	public enum StatusbarControlStyles {
+		SBARS_SIZEGRIP      =    0x0100,
+		SBT_TOOLTIPS	    =	 0x0800
+	}
+	#endregion
+
+	#region StatusBar notifications
+	internal enum StatusbarNotifications : int {
+		SBN_FIRST	= (0 - 880),
+		SBN_LAST	= (0 - 899),
+		SBN_SIMPLEMODECHANGE = (SBN_FIRST - 0)
+	}
+	#endregion
+
+	#region Statusbar Control Messages
+	internal enum StatusbarMessages {
+		SB_SETTEXT	= ( Msg.WM_USER+1 ),
+		SB_GETTEXT	= ( Msg.WM_USER+2 ),
+		SB_GETTEXTLENGTH= ( Msg.WM_USER+3 ),
+		SB_SETPARTS	= ( Msg.WM_USER+4 ),
+		SB_GETPARTS	= ( Msg.WM_USER+6 ),
+		SB_GETBORDERS	= ( Msg.WM_USER+7 ),
+		SB_SETMINHEIGHT	= ( Msg.WM_USER+8 ),
+		SB_SIMPLE	= ( Msg.WM_USER+9 ),
+		SB_GETRECT	= ( Msg.WM_USER+10),
+		SB_ISSIMPLE	= ( Msg.WM_USER+14),
+		SB_SETICON	= ( Msg.WM_USER+15),
+		SB_SETTIPTEXT	= ( Msg.WM_USER+16),
+		SB_GETTIPTEXT	= ( Msg.WM_USER+18),
+		SB_GETICON	= ( Msg.WM_USER+20),
+		SB_SETBKCOLOR	= CommonControlMessages.CCM_SETBKCOLOR
+	}
+	#endregion
+
+	#region Statusbar Drawing Operations Types
+	internal enum StatusbarDrawType {
+		SBT_OWNERDRAW   = 0x1000,
+		SBT_NOBORDERS   = 0x0100,
+		SBT_POPOUT      = 0x0200,
+		SBT_RTLREADING  = 0x0400
+	}
+	#endregion
 
 	internal enum OwnerDrawTypes : int {
 		ODT_COMBOBOX = 3,
Index: win32functions.cs
===================================================================
RCS file: /mono/mcs/class/System.Windows.Forms/System.Windows.Forms/win32functions.cs,v
retrieving revision 1.13
diff -u -r1.13 win32functions.cs
--- win32functions.cs	1 Mar 2003 21:20:31 -0000	1.13
+++ win32functions.cs	14 Mar 2003 16:35:26 -0000
@@ -168,6 +168,8 @@
 		[DllImport("gdi32.dll")]
 		internal static extern int ExtTextOut(IntPtr hdc, int x, int y,
 			ExtTextOutFlags options, ref RECT rc, string str, int strLen, IntPtr distances);
+		[DllImport("gdi32.dll")]
+		internal static extern bool GetTextExtentPoint32(IntPtr hDC, string lpString, int cbString, ref SIZE lpSize);
 
 
 		[DllImport ("gdi32.dll", 
@@ -472,6 +474,9 @@
 		[DllImport ("user32.dll", CallingConvention = CallingConvention.StdCall, CharSet = CharSet.Auto)]
 		internal extern static int AdjustWindowRect( ref RECT rc, int dwStyle, int bMenu);
 
+		[DllImport ("user32.dll", CallingConvention = CallingConvention.StdCall, CharSet = CharSet.Auto)]
+		internal extern static int AdjustWindowRectEx( ref RECT rc, int dwStyle, int bMenu, int dwStyleEx);
+
 		[DllImport("user32.dll", CallingConvention = CallingConvention.StdCall, CharSet = CharSet.Auto)]
 		internal static extern int DrawEdge(IntPtr hdc, ref RECT rc, Border3DStyle edge, Border3DSide flags);
 
@@ -1037,6 +1042,19 @@
 			Win32.SetTextColor(hdc, prevColor);
 			paintOn.ReleaseHdc(hdc);
 		}
-		
+
+		internal static SIZE GetTextExtent ( IntPtr hWnd, string text ) {
+			IntPtr hOldFont = new IntPtr ( 0 );
+			IntPtr hFont = new IntPtr ( Win32.SendMessage ( hWnd, (int)Msg.WM_GETFONT, 0, 0 ) );
+			IntPtr hDC   = Win32.GetWindowDC ( hWnd );
+			if ( hFont != IntPtr.Zero )
+				hOldFont = Win32.SelectObject ( hDC, hFont );
+			SIZE size = new SIZE();
+			Win32.GetTextExtentPoint32 ( hDC, text, text.Length, ref size);
+			if ( hOldFont != IntPtr.Zero )
+				Win32.SelectObject ( hDC, hOldFont );
+			Win32.ReleaseDC ( hWnd, hDC );
+			return size;
+		}
 	}
 }

--0-1811095656-1047660292=:11174--