2005-12-18 Peter Dennis Bartok <pbartok@novell.com>
authorPeter Dennis Bartok <pbartok@mono-cvs.ximian.com>
Sun, 18 Dec 2005 23:59:45 +0000 (23:59 -0000)
committerPeter Dennis Bartok <pbartok@mono-cvs.ximian.com>
Sun, 18 Dec 2005 23:59:45 +0000 (23:59 -0000)
* Control.cs:
  - Reworked Controls.Add(), Controls.Remove() and set_Parent() to
    cause events to be sent in the same order as MS does.
  - Added ChangeParent() method to trigger various OnXXXChanged events
    that need to be fired when a parent changes (This is a reworking
    of the patch from r54254, with the X11 errors fixed)
  - Removed SuspendLayout()/ResumeLayout() calls from Controls.Clear()
    since on MS we get OnLayoutChanged events when calling Clear()
  - Changed Enabled property to consider parent state as well, if a
    parent is not enabled, the control will not be either
  - Changed Parent property to simply call Controls.Add() since that
    now does all the work required, this way we avoid code duplication
  - Threw in a few OnBindingsContextChanged calls to try and match
    when MS sends them. We seem to send a few too many, though.
  - Added call to CreateControl when adding the control to a parent.
    We were never calling CreateControl. Still needs some work, in
    some places we treat HandleCreated and ControlCreated as equal,
    which is wrong
  - Removed obsolete commented out code from UpdateZOrder()

svn path=/trunk/mcs/; revision=54584

mcs/class/Managed.Windows.Forms/System.Windows.Forms/ChangeLog
mcs/class/Managed.Windows.Forms/System.Windows.Forms/Control.cs

index 6f58c0a02b11e1ddbdc7be44f14120e846d45f35..42cdb4b6e7814e6dcf3afbe693aaa0ea6f2483cf 100644 (file)
@@ -1,3 +1,25 @@
+2005-12-18  Peter Dennis Bartok  <pbartok@novell.com> 
+
+       * Control.cs:
+         - Reworked Controls.Add(), Controls.Remove() and set_Parent() to
+           cause events to be sent in the same order as MS does.
+         - Added ChangeParent() method to trigger various OnXXXChanged events
+           that need to be fired when a parent changes (This is a reworking
+           of the patch from r54254, with the X11 errors fixed)
+         - Removed SuspendLayout()/ResumeLayout() calls from Controls.Clear()
+           since on MS we get OnLayoutChanged events when calling Clear()
+         - Changed Enabled property to consider parent state as well, if a
+           parent is not enabled, the control will not be either
+         - Changed Parent property to simply call Controls.Add() since that
+           now does all the work required, this way we avoid code duplication
+         - Threw in a few OnBindingsContextChanged calls to try and match
+           when MS sends them. We seem to send a few too many, though.
+         - Added call to CreateControl when adding the control to a parent.
+           We were never calling CreateControl. Still needs some work, in
+           some places we treat HandleCreated and ControlCreated as equal, 
+           which is wrong
+         - Removed obsolete commented out code from UpdateZOrder()
+
 2005-12-18  Alexander Olk  <alex.olk@googlemail.com>
 
        * ThemeClearlooks.cs: Updated TrackBar drawing.
index ebd1734e05aa7059729e657bd1f1e8b74bb180da..bef697d86e4b18e1b3adae177c151b7dd201a95e 100644 (file)
@@ -63,7 +63,7 @@ namespace System.Windows.Forms
                internal string                 name;                   // for object naming
 
                // State
-               private bool                    create_handled;         // true if OnCreateControl has been sent
+               internal bool                   is_created;             // true if OnCreateControl has been sent
                internal bool                   has_focus;              // true if control has focus
                internal bool                   is_visible;             // true if control is visible
                internal bool                   is_entered;             // is the mouse inside the control?
@@ -297,8 +297,10 @@ namespace System.Windows.Forms
                                if (value == null)
                                        return;
                                
-                                if (Contains (value))
+                                if (Contains (value)) {
+                                       owner.PerformLayout();
                                         return;
+                               }
 
                                if (value.tab_index == -1) {
                                        int     end;
@@ -316,10 +318,19 @@ namespace System.Windows.Forms
                                        value.tab_index = use;
                                }
 
+                               if (value.parent != null) {
+                                       value.parent.Controls.Remove(value);
+                               }
+
                                all_controls = null;
                                list.Add (value);
-                               value.Parent = owner;
+
+                               value.ChangeParent(owner);
+
+                               value.InitLayout();
+
                                owner.UpdateZOrder();
+                               owner.PerformLayout(value, "Parent");
                                owner.OnControlAdded(new ControlEventArgs(value));
                        }
                        
@@ -335,8 +346,10 @@ namespace System.Windows.Forms
                                        impl_list = new ArrayList ();
                                all_controls = null;
                                impl_list.Add (control);
-                               control.Parent = owner;
+                               control.ChangeParent (owner);
                                owner.UpdateZOrder ();
+                               owner.PerformLayout (control, "Parent");
+                               owner.OnControlAdded (new ControlEventArgs (control));
                        }
 
                        public virtual void AddRange (Control[] controls)
@@ -371,13 +384,12 @@ namespace System.Windows.Forms
 
                        public virtual void Clear ()
                        {
-                               owner.SuspendLayout();
                                all_controls = null;
-                               for (int i = 0; i < list.Count; i++) {
-                                       owner.OnControlRemoved(new ControlEventArgs((Control)list[i]));
+
+                               // MS sends remove events in reverse order
+                               while (list.Count > 0) {
+                                       RemoveAt(list.Count - 1);
                                }
-                               list.Clear();
-                               owner.ResumeLayout();
                        }
 
                        internal virtual void ClearImplicit ()
@@ -484,9 +496,12 @@ namespace System.Windows.Forms
                        public virtual void Remove(Control value) {
                                all_controls = null;
 
+                               owner.PerformLayout(value, "Parent");
                                owner.OnControlRemoved(new ControlEventArgs(value));
                                list.Remove(value);
-                               value.parent = null;
+
+                               value.ChangeParent(null);
+
                                owner.UpdateZOrder();
                        }
 
@@ -494,9 +509,11 @@ namespace System.Windows.Forms
                        {
                                if (impl_list != null) {
                                        all_controls = null;
+                                       owner.PerformLayout (control, "Parent");
+                                       owner.OnControlRemoved (new ControlEventArgs (control));
                                        impl_list.Remove (control);
                                }
-                               control.Parent = null;
+                               control.ChangeParent (null);
                                owner.UpdateZOrder ();
                        }
 
@@ -640,7 +657,7 @@ namespace System.Windows.Forms
 
                        anchor_style = AnchorStyles.Top | AnchorStyles.Left;
 
-                       create_handled = false;
+                       is_created = false;
                        is_visible = true;
                        is_captured = false;
                        is_disposed = false;
@@ -1135,6 +1152,70 @@ namespace System.Windows.Forms
                                binding.Check (binding_context);
                        }
                }
+
+
+               private void ChangeParent(Control new_parent) {
+                       bool            pre_enabled;
+                       bool            pre_visible;
+                       Font            pre_font;
+                       Color           pre_fore_color;
+                       Color           pre_back_color;
+                       RightToLeft     pre_rtl;
+
+                       // These properties are inherited from our parent
+                       // Get them pre parent-change and then send events
+                       // if they are changed after we have our new parent
+                       pre_enabled = Enabled;
+                       pre_visible = Visible;
+                       pre_font = Font;
+                       pre_fore_color = ForeColor;
+                       pre_back_color = BackColor;
+                       pre_rtl = RightToLeft;
+                       // MS doesn't seem to send a CursorChangedEvent
+
+                       parent = new_parent;
+
+                       if (IsHandleCreated && (new_parent != null) && new_parent.IsHandleCreated) {
+                               XplatUI.SetParent(Handle, new_parent.Handle);
+                       }
+
+                       OnParentChanged(EventArgs.Empty);
+
+                       if (pre_enabled != Enabled) {
+                               OnEnabledChanged(EventArgs.Empty);
+                       }
+
+                       if (pre_visible != Visible) {
+                               OnVisibleChanged(EventArgs.Empty);
+                       }
+
+                       if (pre_font != Font) {
+                               OnFontChanged(EventArgs.Empty);
+                       }
+
+                       if (pre_fore_color != ForeColor) {
+                               OnForeColorChanged(EventArgs.Empty);
+                       }
+
+                       if (pre_back_color != BackColor) {
+                               OnBackColorChanged(EventArgs.Empty);
+                       }
+
+                       if (pre_rtl != RightToLeft) {
+                               // MS sneaks a OnCreateControl and OnHandleCreated in here, I guess
+                               // because when RTL changes they have to recreate the win32 control
+                               // We don't really need that (until someone runs into compatibility issues)
+                               OnRightToLeftChanged(EventArgs.Empty);
+                       }
+
+                       if ((new_parent != null) && new_parent.Created && !Created) {
+                               CreateControl();
+                       }
+
+                       if (binding_context == null) {  // seem to be sent whenever it's null?
+                               OnBindingContextChanged(EventArgs.Empty);
+                       }
+               }
                #endregion      // Private & Internal Methods
 
                #region Public Static Properties
@@ -1541,7 +1622,7 @@ namespace System.Windows.Forms
                                        cursor = value;
                                        
                                        pt = Cursor.Position;
-                                       Console.WriteLine ("{0}  {1}  {2}", bounds, pt, bounds.Contains (pt));
+                                       //Console.WriteLine ("{0}  {1}  {2}", bounds, pt, bounds.Contains (pt));
                                        if (bounds.Contains(pt)) {
                                                if (GetChildAtPoint(pt) == null) {
                                                        if (cursor != null) {
@@ -1618,7 +1699,15 @@ namespace System.Windows.Forms
                [Localizable(true)]
                public bool Enabled {
                        get {
-                               return is_enabled;
+                               if (!is_enabled) {
+                                       return false;
+                               }
+
+                               if (parent != null) {
+                                       return parent.Enabled;
+                               }
+
+                               return true;
                        }
 
                        set {
@@ -1848,19 +1937,7 @@ namespace System.Windows.Forms
                                                return;
                                        }
 
-                                       parent=value;
-
-                                       if (!parent.Controls.AllContains (this)) {
-                                                Console.WriteLine ("Adding child:  " + this);
-                                               parent.Controls.Add(this);
-                                       }
-
-                                       if (IsHandleCreated) {
-                                               XplatUI.SetParent(Handle, value.Handle);
-                                       }
-
-                                       OnParentChanged(EventArgs.Empty);
-                                       InitLayout();
+                                       value.Controls.Add(this);
                                }
                        }
                }
@@ -2354,15 +2431,20 @@ namespace System.Windows.Forms
                                CreateHandle();
                        }
 
-                       if (!create_handled) {
-                               create_handled = true;
-                               OnCreateControl();
+                       if (!is_created) {
+                               is_created = true;
                        }
 
                        Control [] controls = child_controls.GetAllControls ();
                        for (int i=0; i<controls.Length; i++) {
                                controls [i].CreateControl ();
                        }
+
+                       if (binding_context == null) {  // seem to be sent whenever it's null?
+                               OnBindingContextChanged(EventArgs.Empty);
+                       }
+
+                       OnCreateControl();
                }
 
                public Graphics CreateGraphics() {
@@ -3465,20 +3547,6 @@ namespace System.Windows.Forms
                [EditorBrowsable(EditorBrowsableState.Advanced)]
                protected void UpdateZOrder() {
                        Control [] controls;
-#if not
-                       Control ctl;
-
-                       if (parent == null) {
-                               return;
-                       }
-
-                       ctl = parent;
-
-                       controls = ctl.child_controls.GetAllControls ();
-                       for (int i = 1; i < controls.Length; i++ ) {
-                               XplatUI.SetZOrder(controls[i].window.Handle, controls[i-1].window.Handle, false, false); 
-                       }
-#else
                        if (!IsHandleCreated) {
                                return;
                        }
@@ -3487,7 +3555,6 @@ namespace System.Windows.Forms
                        for (int i = 1; i < controls.Length; i++ ) {
                                XplatUI.SetZOrder(controls[i].Handle, controls[i-1].Handle, false, false); 
                        }
-#endif
                }
 
                protected virtual void WndProc(ref Message m) {