4 // Permission is hereby granted, free of charge, to any person obtaining
5 // a copy of this software and associated documentation files (the
6 // "Software"), to deal in the Software without restriction, including
7 // without limitation the rights to use, copy, modify, merge, publish,
8 // distribute, sublicense, and/or sell copies of the Software, and to
9 // permit persons to whom the Software is furnished to do so, subject to
10 // the following conditions:
12 // The above copyright notice and this permission notice shall be
13 // included in all copies or substantial portions of the Software.
15 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
19 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
20 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
21 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23 // Copyright (c) 2006 Jonathan Pobst
26 // Jonathan Pobst (monkey@jpobst.com)
32 using System.ComponentModel;
34 namespace System.Windows.Forms
36 [DefaultEvent ("Click")]
37 [DefaultProperty ("Text")]
38 [DesignTimeVisible (false)]
40 public abstract class ToolStripItem : Component, IDropTarget, IComponent, IDisposable
42 #region Private Variables
43 private AccessibleObject accessibility_object;
44 private string accessible_default_action_description;
45 private bool allow_drop;
46 private ToolStripItemAlignment alignment;
47 private AnchorStyles anchor;
48 private bool auto_size;
49 private bool auto_tool_tip;
50 private Color back_color;
51 private Image background_image;
52 private ImageLayout background_image_layout;
53 private Rectangle bounds;
54 private bool can_select;
55 private ToolStripItemDisplayStyle display_style;
56 private DockStyle dock;
57 private bool double_click_enabled;
59 private Size explicit_size;
61 private Color fore_color;
63 private ContentAlignment image_align;
64 private int image_index;
65 private string image_key;
66 private ToolStripItemImageScaling image_scaling;
67 private Color image_transparent_color;
68 private bool is_disposed;
69 internal bool is_pressed;
70 private bool is_selected;
71 private Padding margin;
73 private ToolStripItemOverflow overflow;
74 private ToolStrip owner;
75 internal ToolStripItem owner_item;
76 private Padding padding;
77 private ToolStripItemPlacement placement;
78 private RightToLeft right_to_left;
81 private ContentAlignment text_align;
82 private TextImageRelation text_image_relation;
83 private string tool_tip_text;
86 private ToolStrip parent;
87 private Size text_size;
90 #region Public Constructors
91 protected ToolStripItem ()
92 : this (String.Empty, null, null, String.Empty)
96 protected ToolStripItem (string text, Image image, EventHandler onClick)
97 : this (text, image, onClick, String.Empty)
101 protected ToolStripItem (string text, Image image, EventHandler onClick, string name)
103 this.alignment = ToolStripItemAlignment.Left;
104 this.anchor = AnchorStyles.Left | AnchorStyles.Top;
105 this.auto_size = true;
106 this.auto_tool_tip = this.DefaultAutoToolTip;
107 this.back_color = Control.DefaultBackColor;
108 this.background_image_layout = ImageLayout.Tile;
109 this.can_select = true;
110 this.display_style = this.DefaultDisplayStyle;
111 this.dock = DockStyle.None;
113 this.font = new Font ("Tahoma", 8.25f);
114 this.fore_color = Control.DefaultForeColor;
116 this.image_align = ContentAlignment.MiddleCenter;
117 this.image_index = -1;
118 this.image_key = string.Empty;
119 this.image_scaling = ToolStripItemImageScaling.SizeToFit;
120 this.image_transparent_color = Color.Empty;
121 this.margin = this.DefaultMargin;
123 this.overflow = ToolStripItemOverflow.AsNeeded;
124 this.padding = this.DefaultPadding;
125 this.placement = ToolStripItemPlacement.None;
126 this.right_to_left = RightToLeft.Inherit;
127 this.bounds.Size = this.DefaultSize;
129 this.text_align = ContentAlignment.MiddleCenter;
130 this.text_image_relation = TextImageRelation.ImageBeforeText;
133 this.Click += onClick;
134 OnLayout (new LayoutEventArgs (null, string.Empty));
138 #region Public Properties
140 [EditorBrowsable (EditorBrowsableState.Advanced)]
141 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
142 public AccessibleObject AccessibilityObject {
144 if (this.accessibility_object == null)
145 this.accessibility_object = CreateAccessibilityInstance ();
147 return this.accessibility_object;
152 [EditorBrowsable (EditorBrowsableState.Advanced)]
153 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
154 public string AccessibleDefaultActionDescription {
156 if (this.accessibility_object == null)
159 return this.accessible_default_action_description;
161 set { this.accessible_default_action_description = value; }
165 [DefaultValue (null)]
166 public string AccessibleDescription {
168 if (this.accessibility_object == null)
171 return this.AccessibilityObject.Description;
173 set { this.AccessibilityObject.description = value; }
177 [DefaultValue (null)]
178 public string AccessibleName {
180 if (this.accessibility_object == null)
183 return this.AccessibilityObject.Name;
185 set { this.AccessibilityObject.Name = value; }
188 [DefaultValue (AccessibleRole.Default)]
189 public AccessibleRole AccessibleRole {
192 if (this.accessibility_object == null)
193 return AccessibleRole.Default;
195 return this.AccessibilityObject.Role;
197 set { this.AccessibilityObject.role = value; }
201 [DefaultValue (ToolStripItemAlignment.Left)]
202 public ToolStripItemAlignment Alignment {
203 get { return this.alignment; }
205 if (!Enum.IsDefined (typeof (ToolStripItemAlignment), value))
206 throw new InvalidEnumArgumentException (string.Format ("Enum argument value '{0}' is not valid for ToolStripItemAlignment", value));
208 this.alignment = value;
213 public virtual bool AllowDrop {
215 return this.allow_drop;
219 this.allow_drop = value;
224 [DefaultValue (AnchorStyles.Top | AnchorStyles.Left)]
225 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
226 public AnchorStyles Anchor {
227 get { return this.anchor; }
228 set { this.anchor = value; }
232 [DefaultValue (true)]
233 [DesignerSerializationVisibility (DesignerSerializationVisibility.Visible)]
234 [RefreshProperties (RefreshProperties.All)]
235 public bool AutoSize {
236 get { return this.auto_size; }
238 this.auto_size = value;
239 this.CalculateAutoSize ();
243 [DefaultValue (false)]
244 public bool AutoToolTip {
245 get { return this.auto_tool_tip; }
246 set { this.auto_tool_tip = value; }
250 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
251 public bool Available {
252 get { return this.visible; }
254 if (this.visible != value) {
257 if (this.parent != null)
258 parent.PerformLayout ();
260 OnAvailableChanged (EventArgs.Empty);
261 OnVisibleChanged (EventArgs.Empty);
266 public virtual Color BackColor {
267 get { return this.back_color; }
269 if (this.back_color != value) {
271 OnBackColorChanged (EventArgs.Empty);
278 [DefaultValue (null)]
279 public virtual Image BackgroundImage {
280 get { return this.background_image; }
282 if (this.background_image != value) {
283 this.background_image = value;
290 [DefaultValue (ImageLayout.Tile)]
291 public virtual ImageLayout BackgroundImageLayout {
292 get { return this.background_image_layout; }
294 if (this.background_image_layout != value) {
295 this.background_image_layout = value;
302 public virtual Rectangle Bounds {
303 get { return this.bounds; }
307 public virtual bool CanSelect {
308 get { return this.can_select; }
312 public Rectangle ContentRectangle {
314 // ToolStripLabels don't have a border
315 if (this is ToolStripLabel || this is ToolStripStatusLabel)
316 return new Rectangle (0, 0, this.bounds.Width, this.bounds.Height);
318 if (this is ToolStripDropDownButton && (this as ToolStripDropDownButton).ShowDropDownArrow)
319 return new Rectangle (2, 2, this.bounds.Width - 13, this.bounds.Height - 4);
321 return new Rectangle (2, 2, this.bounds.Width - 4, this.bounds.Height - 4);
325 public virtual ToolStripItemDisplayStyle DisplayStyle {
326 get { return this.display_style; }
328 if (this.display_style != value) {
329 this.display_style = value;
330 this.CalculateAutoSize ();
331 OnDisplayStyleChanged (EventArgs.Empty);
332 if (this.Parent != null)
333 this.Parent.PerformLayout ();
338 public bool IsDisposed {
339 get { return this.is_disposed; }
343 [DefaultValue (DockStyle.None)]
344 public DockStyle Dock {
345 get { return this.dock; }
347 if (this.dock != value) {
348 if (!Enum.IsDefined (typeof (DockStyle), value))
349 throw new InvalidEnumArgumentException (string.Format ("Enum argument value '{0}' is not valid for DockStyle", value));
352 this.CalculateAutoSize ();
357 [DefaultValue (false)]
358 public bool DoubleClickEnabled {
359 get { return this.double_click_enabled; }
360 set { this.double_click_enabled = value; }
364 [DefaultValue (true)]
365 public virtual bool Enabled {
366 get { return enabled; }
368 if (this.enabled != value) {
369 this.enabled = value;
370 OnEnabledChanged (EventArgs.Empty);
377 public virtual Font Font
379 get { return this.font; }
381 if (this.font != value) {
383 this.CalculateAutoSize ();
384 this.OnFontChanged (EventArgs.Empty);
390 public virtual Color ForeColor {
391 get { return this.fore_color; }
393 if (this.fore_color != value) {
394 this.fore_color = value;
395 this.OnForeColorChanged (EventArgs.Empty);
402 [EditorBrowsable (EditorBrowsableState.Always)]
403 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
405 get { return this.Size.Height; }
407 this.bounds.Height = value;
408 this.explicit_size.Height = value;
411 this.CalculateAutoSize ();
412 this.OnBoundsChanged ();
419 public virtual Image Image {
421 if (this.image != null)
424 if (this.image_index >= 0)
425 if (this.owner != null && this.owner.ImageList != null)
426 return this.owner.ImageList.Images[this.image_index];
429 if (!string.IsNullOrEmpty (this.image_key))
430 if (this.owner != null && this.owner.ImageList != null)
431 return this.owner.ImageList.Images[this.image_key];
436 if (this.image != value) {
438 this.image_index = -1;
439 this.image_key = string.Empty;
440 this.CalculateAutoSize ();
447 [DefaultValue (ContentAlignment.MiddleCenter)]
448 public ContentAlignment ImageAlign {
449 get { return this.image_align; }
451 if (!Enum.IsDefined (typeof (ContentAlignment), value))
452 throw new InvalidEnumArgumentException (string.Format ("Enum argument value '{0}' is not valid for ContentAlignment", value));
454 this.image_align = value;
461 [RelatedImageList ("Owner.ImageList")]
462 [RefreshProperties (RefreshProperties.Repaint)]
463 public int ImageIndex {
464 get { return this.image_index; }
466 if (this.image_index != value) {
467 // Lamespec: MSDN says ArgumentException, tests say otherwise
469 throw new ArgumentOutOfRangeException ("ImageIndex cannot be less than -1");
471 this.image_index = value;
473 this.image_key = string.Empty;
474 this.CalculateAutoSize ();
482 [RelatedImageList ("Owner.ImageList")]
483 [RefreshProperties (RefreshProperties.Repaint)]
484 public string ImageKey
486 get { return this.image_key; }
488 if (this.image_key != value) {
490 this.image_index = -1;
491 this.image_key = value;
492 this.CalculateAutoSize ();
499 [DefaultValue (ToolStripItemImageScaling.SizeToFit)]
500 public ToolStripItemImageScaling ImageScaling {
501 get { return this.image_scaling; }
503 this.image_scaling = value;
504 this.CalculateAutoSize ();
510 [MonoTODO ("Stub, doesn't actually do anything yet.")]
511 public Color ImageTransparentColor {
512 get { return this.image_transparent_color; }
513 set { this.image_transparent_color = value; }
517 public bool IsOnDropDown {
519 if (this.parent != null && this.parent is ToolStripDropDown)
527 public bool IsOnOverflow {
528 get { return this.placement == ToolStripItemPlacement.Overflow; }
531 public Padding Margin {
532 get { return this.margin; }
535 this.CalculateAutoSize ();
539 [DefaultValue (null)]
542 get { return this.name; }
543 set { this.name = value; }
546 [DefaultValue (ToolStripItemOverflow.AsNeeded)]
547 public ToolStripItemOverflow Overflow {
548 get { return this.overflow; }
550 if (this.overflow != value) {
551 if (!Enum.IsDefined (typeof (ToolStripItemOverflow), value))
552 throw new InvalidEnumArgumentException (string.Format ("Enum argument value '{0}' is not valid for ToolStripItemOverflow", value));
554 this.overflow = value;
557 owner.PerformLayout ();
563 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
564 public ToolStrip Owner {
565 get { return this.owner; }
567 if (this.owner != value) {
569 this.CalculateAutoSize ();
570 OnOwnerChanged (EventArgs.Empty);
576 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
577 public ToolStripItem OwnerItem {
578 get { return this.owner_item; }
581 public virtual Padding Padding {
582 get { return this.padding; }
584 this.padding = value;
585 this.CalculateAutoSize ();
591 public ToolStripItemPlacement Placement {
592 get { return this.placement; }
596 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
597 public virtual bool Pressed { get { return this.is_pressed; } }
599 [MonoTODO ("Stub, not implemented")]
601 public virtual RightToLeft RightToLeft {
602 get { return this.right_to_left; }
603 set { this.right_to_left = value; }
607 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
608 public virtual bool Selected { get { return this.is_selected; } }
611 public virtual Size Size {
613 if (!this.AutoSize && this.explicit_size != Size.Empty)
614 return this.explicit_size;
616 return this.bounds.Size;
619 this.bounds.Size = value;
620 this.explicit_size = value;
623 this.CalculateAutoSize ();
624 this.OnBoundsChanged ();
629 [Localizable (false)]
631 [DefaultValue (null)]
632 [TypeConverter (typeof (StringConverter))]
634 get { return this.tag; }
635 set { this.tag = value; }
640 public virtual string Text
642 get { return this.text; }
644 if (this.text != value) {
646 this.CalculateAutoSize ();
647 this.OnTextChanged (EventArgs.Empty);
654 [DefaultValue (ContentAlignment.MiddleCenter)]
655 public virtual ContentAlignment TextAlign {
656 get { return this.text_align; }
658 if (!Enum.IsDefined (typeof (ContentAlignment), value))
659 throw new InvalidEnumArgumentException (string.Format ("Enum argument value '{0}' is not valid for ContentAlignment", value));
660 this.text_align = value;
666 [DefaultValue (TextImageRelation.ImageBeforeText)]
667 public TextImageRelation TextImageRelation {
668 get { return this.text_image_relation; }
670 this.text_image_relation = value;
671 this.CalculateAutoSize ();
677 public string ToolTipText {
678 get { return this.tool_tip_text; }
679 set { this.tool_tip_text = value; }
683 public bool Visible {
685 if (this.parent == null)
688 return this.visible && this.parent.Visible;
691 if (this.visible != value) {
692 this.SetVisibleCore (value);
698 [EditorBrowsable (EditorBrowsableState.Always)]
699 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
701 get { return this.Size.Width; }
703 this.bounds.Width = value;
704 this.explicit_size.Width = value;
707 this.CalculateAutoSize ();
708 this.OnBoundsChanged ();
715 #region Protected Properties
716 protected virtual bool DefaultAutoToolTip { get { return false; } }
717 protected virtual ToolStripItemDisplayStyle DefaultDisplayStyle { get { return ToolStripItemDisplayStyle.ImageAndText; } }
718 protected internal virtual Padding DefaultMargin { get { return new Padding (0, 1, 0, 2); } }
719 protected virtual Padding DefaultPadding { get { return new Padding (); } }
720 protected virtual Size DefaultSize { get { return new Size (23, 23); } }
721 protected internal virtual bool DismissWhenClicked { get { return true; } }
723 [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
724 protected internal ToolStrip Parent {
725 get { return this.parent; }
727 ToolStrip old_parent = this.parent;
729 OnParentChanged(old_parent, this.parent);
732 protected internal virtual bool ShowKeyboardCues { get { return false; } }
735 #region Public Methods
736 public ToolStrip GetCurrentParent ()
741 public virtual Size GetPreferredSize (Size constrainingSize)
743 return this.CalculatePreferredSize (constrainingSize);
746 public void Invalidate ()
749 parent.Invalidate (this.bounds);
752 public void Invalidate (Rectangle r)
755 parent.Invalidate (r);
758 public void PerformClick ()
760 this.OnClick (EventArgs.Empty);
763 [EditorBrowsable (EditorBrowsableState.Never)]
764 public virtual void ResetBackColor () { this.BackColor = Control.DefaultBackColor; }
766 [EditorBrowsable (EditorBrowsableState.Never)]
767 public virtual void ResetDisplayStyle () { this.display_style = this.DefaultDisplayStyle; }
769 [EditorBrowsable (EditorBrowsableState.Never)]
770 public virtual void ResetFont () { this.font = new Font ("Tahoma", 8.25f); }
772 [EditorBrowsable (EditorBrowsableState.Never)]
773 public virtual void ResetForeColor () { this.ForeColor = Control.DefaultForeColor; }
775 [EditorBrowsable (EditorBrowsableState.Never)]
776 public virtual void ResetImage () { this.image = null; }
778 [EditorBrowsable (EditorBrowsableState.Never)]
779 public void ResetMargin () { this.margin = this.DefaultMargin; }
781 [EditorBrowsable (EditorBrowsableState.Never)]
782 public void ResetPadding () { this.padding = this.DefaultPadding; }
784 public void Select ()
786 if (!this.is_selected && this.CanSelect) {
787 this.is_selected = true;
789 this.Parent.NotifySelectedChanged (this);
793 public override string ToString ()
799 #region Protected Methods
800 [EditorBrowsable (EditorBrowsableState.Advanced)]
801 protected virtual AccessibleObject CreateAccessibilityInstance ()
803 return new ToolStripItemAccessibleObject (this);
806 protected override void Dispose (bool disposing)
808 if (!is_disposed && disposing)
811 base.Dispose (disposing);
814 protected virtual void OnAvailableChanged (EventArgs e)
816 EventHandler eh = (EventHandler)(Events [AvailableChangedEvent]);
821 [EditorBrowsable (EditorBrowsableState.Advanced)]
822 protected virtual void OnBackColorChanged (EventArgs e)
824 EventHandler eh = (EventHandler)(Events [BackColorChangedEvent]);
829 protected virtual void OnBoundsChanged ()
831 OnLayout (new LayoutEventArgs(null, ""));
834 protected virtual void OnClick (EventArgs e)
836 EventHandler eh = (EventHandler)(Events [ClickEvent]);
841 [EditorBrowsable (EditorBrowsableState.Advanced)]
842 protected virtual void OnDisplayStyleChanged (EventArgs e)
844 EventHandler eh = (EventHandler)(Events [DisplayStyleChangedEvent]);
849 protected virtual void OnDoubleClick (EventArgs e)
851 EventHandler eh = (EventHandler)(Events [DoubleClickEvent]);
855 if (!double_click_enabled)
859 void IDropTarget.OnDragDrop (DragEventArgs e)
864 void IDropTarget.OnDragEnter (DragEventArgs e)
869 void IDropTarget.OnDragLeave (EventArgs e)
874 void IDropTarget.OnDragOver (DragEventArgs e)
879 protected virtual void OnEnabledChanged (EventArgs e)
881 EventHandler eh = (EventHandler)(Events [EnabledChangedEvent]);
886 [EditorBrowsable (EditorBrowsableState.Advanced)]
887 protected virtual void OnFontChanged (EventArgs e)
891 [EditorBrowsable (EditorBrowsableState.Advanced)]
892 protected virtual void OnForeColorChanged (EventArgs e)
894 EventHandler eh = (EventHandler)(Events [ForeColorChangedEvent]);
899 protected virtual void OnLayout (LayoutEventArgs e)
903 protected virtual void OnLocationChanged (EventArgs e)
905 EventHandler eh = (EventHandler)(Events [LocationChangedEvent]);
910 protected virtual void OnMouseDown (MouseEventArgs e)
913 this.is_pressed = true;
916 MouseEventHandler eh = (MouseEventHandler)(Events [MouseDownEvent]);
922 protected virtual void OnMouseEnter (EventArgs e)
926 EventHandler eh = (EventHandler)(Events [MouseEnterEvent]);
931 protected virtual void OnMouseHover (EventArgs e)
934 EventHandler eh = (EventHandler)(Events [MouseHoverEvent]);
940 protected virtual void OnMouseLeave (EventArgs e)
942 if (this.CanSelect) {
943 this.is_selected = false;
944 this.is_pressed = false;
948 EventHandler eh = (EventHandler)(Events [MouseLeaveEvent]);
953 protected virtual void OnMouseMove (MouseEventArgs e)
956 MouseEventHandler eh = (MouseEventHandler)(Events [MouseMoveEvent]);
962 protected virtual void OnMouseUp (MouseEventArgs e)
965 this.is_pressed = false;
968 if (this.IsOnDropDown)
969 if (!(this is ToolStripDropDownItem) || (this as ToolStripDropDownItem).DropDown.Visible == false) {
970 if ((this.Parent as ToolStripDropDown).OwnerItem != null)
971 ((this.Parent as ToolStripDropDown).OwnerItem as ToolStripDropDownItem).HideDropDown ();
973 (this.Parent as ToolStripDropDown).Hide ();
977 MouseEventHandler eh = (MouseEventHandler)(Events [MouseUpEvent]);
983 protected virtual void OnOwnerChanged (EventArgs e)
985 EventHandler eh = (EventHandler)(Events [OwnerChangedEvent]);
990 protected internal virtual void OnOwnerFontChanged (EventArgs e)
994 protected virtual void OnPaint (PaintEventArgs e)
996 if (this.parent != null)
997 this.parent.Renderer.DrawItemBackground (new ToolStripItemRenderEventArgs (e.Graphics, this));
999 PaintEventHandler eh = (PaintEventHandler)(Events [PaintEvent]);
1004 // This is never called.
1005 protected virtual void OnParentBackColorChanged (EventArgs e)
1009 protected virtual void OnParentChanged (ToolStrip oldParent, ToolStrip newParent)
1011 if (oldParent != null)
1012 oldParent.PerformLayout ();
1014 if (newParent != null)
1015 newParent.PerformLayout ();
1018 protected internal virtual void OnParentEnabledChanged (EventArgs e)
1020 this.OnEnabledChanged (e);
1023 // This is never called.
1024 protected virtual void OnParentForeColorChanged (EventArgs e)
1028 [EditorBrowsable (EditorBrowsableState.Advanced)]
1029 protected virtual void OnTextChanged (EventArgs e)
1031 EventHandler eh = (EventHandler)(Events [TextChangedEvent]);
1036 protected virtual void OnVisibleChanged (EventArgs e)
1038 EventHandler eh = (EventHandler)(Events [VisibleChangedEvent]);
1043 protected internal virtual bool ProcessCmdKey (ref Message m, Keys keyData)
1048 protected internal virtual void SetBounds (Rectangle bounds)
1050 if (this.bounds != bounds) {
1051 this.bounds = bounds;
1056 protected virtual void SetVisibleCore (bool visible)
1058 this.visible = visible;
1059 this.OnVisibleChanged (EventArgs.Empty);
1064 #region Public Events
1065 static object AvailableChangedEvent = new object ();
1066 static object BackColorChangedEvent = new object ();
1067 static object ClickEvent = new object ();
1068 static object DisplayStyleChangedEvent = new object ();
1069 static object DoubleClickEvent = new object ();
1070 static object EnabledChangedEvent = new object ();
1071 static object ForeColorChangedEvent = new object ();
1072 static object LocationChangedEvent = new object ();
1073 static object MouseDownEvent = new object ();
1074 static object MouseEnterEvent = new object ();
1075 static object MouseHoverEvent = new object ();
1076 static object MouseLeaveEvent = new object ();
1077 static object MouseMoveEvent = new object ();
1078 static object MouseUpEvent = new object ();
1079 static object OwnerChangedEvent = new object ();
1080 static object PaintEvent = new object ();
1081 static object TextChangedEvent = new object ();
1082 static object VisibleChangedEvent = new object ();
1085 public event EventHandler AvailableChanged {
1086 add { Events.AddHandler (AvailableChangedEvent, value); }
1087 remove {Events.RemoveHandler (AvailableChangedEvent, value); }
1090 public event EventHandler BackColorChanged {
1091 add { Events.AddHandler (BackColorChangedEvent, value); }
1092 remove {Events.RemoveHandler (BackColorChangedEvent, value); }
1095 public event EventHandler Click {
1096 add { Events.AddHandler (ClickEvent, value); }
1097 remove {Events.RemoveHandler (ClickEvent, value); }
1100 public event EventHandler DisplayStyleChanged {
1101 add { Events.AddHandler (DisplayStyleChangedEvent, value); }
1102 remove {Events.RemoveHandler (DisplayStyleChangedEvent, value); }
1105 public event EventHandler DoubleClick {
1106 add { Events.AddHandler (DoubleClickEvent, value); }
1107 remove {Events.RemoveHandler (DoubleClickEvent, value); }
1110 public event EventHandler EnabledChanged {
1111 add { Events.AddHandler (EnabledChangedEvent, value); }
1112 remove {Events.RemoveHandler (EnabledChangedEvent, value); }
1115 public event EventHandler ForeColorChanged {
1116 add { Events.AddHandler (ForeColorChangedEvent, value); }
1117 remove {Events.RemoveHandler (ForeColorChangedEvent, value); }
1120 public event EventHandler LocationChanged {
1121 add { Events.AddHandler (LocationChangedEvent, value); }
1122 remove {Events.RemoveHandler (LocationChangedEvent, value); }
1125 public event MouseEventHandler MouseDown {
1126 add { Events.AddHandler (MouseDownEvent, value); }
1127 remove {Events.RemoveHandler (MouseDownEvent, value); }
1130 public event EventHandler MouseEnter {
1131 add { Events.AddHandler (MouseEnterEvent, value); }
1132 remove {Events.RemoveHandler (MouseEnterEvent, value); }
1135 public event EventHandler MouseHover {
1136 add { Events.AddHandler (MouseHoverEvent, value); }
1137 remove {Events.RemoveHandler (MouseHoverEvent, value); }
1140 public event EventHandler MouseLeave {
1141 add { Events.AddHandler (MouseLeaveEvent, value); }
1142 remove {Events.RemoveHandler (MouseLeaveEvent, value); }
1145 public event MouseEventHandler MouseMove {
1146 add { Events.AddHandler (MouseMoveEvent, value); }
1147 remove {Events.RemoveHandler (MouseMoveEvent, value); }
1150 public event MouseEventHandler MouseUp {
1151 add { Events.AddHandler (MouseUpEvent, value); }
1152 remove {Events.RemoveHandler (MouseUpEvent, value); }
1155 public event EventHandler OwnerChanged {
1156 add { Events.AddHandler (OwnerChangedEvent, value); }
1157 remove {Events.RemoveHandler (OwnerChangedEvent, value); }
1160 public event PaintEventHandler Paint {
1161 add { Events.AddHandler (PaintEvent, value); }
1162 remove {Events.RemoveHandler (PaintEvent, value); }
1165 public event EventHandler TextChanged {
1166 add { Events.AddHandler (TextChangedEvent, value); }
1167 remove {Events.RemoveHandler (TextChangedEvent, value); }
1170 public event EventHandler VisibleChanged {
1171 add { Events.AddHandler (VisibleChangedEvent, value); }
1172 remove {Events.RemoveHandler (VisibleChangedEvent, value); }
1176 #region Internal Methods
1177 internal Rectangle AlignInRectangle (Rectangle outer, Size inner, ContentAlignment align)
1182 if (align == ContentAlignment.BottomLeft || align == ContentAlignment.MiddleLeft || align == ContentAlignment.TopLeft)
1184 else if (align == ContentAlignment.BottomCenter || align == ContentAlignment.MiddleCenter || align == ContentAlignment.TopCenter)
1185 x = Math.Max (outer.X + ((outer.Width - inner.Width) / 2), outer.Left);
1186 else if (align == ContentAlignment.BottomRight || align == ContentAlignment.MiddleRight || align == ContentAlignment.TopRight)
1187 x = outer.Right - inner.Width;
1188 if (align == ContentAlignment.TopCenter || align == ContentAlignment.TopLeft || align == ContentAlignment.TopRight)
1190 else if (align == ContentAlignment.MiddleCenter || align == ContentAlignment.MiddleLeft || align == ContentAlignment.MiddleRight)
1191 y = outer.Y + (outer.Height - inner.Height) / 2;
1192 else if (align == ContentAlignment.BottomCenter || align == ContentAlignment.BottomRight || align == ContentAlignment.BottomLeft)
1193 y = outer.Bottom - inner.Height;
1195 return new Rectangle (x, y, Math.Min (inner.Width, outer.Width), Math.Min (inner.Height, outer.Height));
1198 internal void CalculateAutoSize ()
1200 this.text_size = TextRenderer.MeasureText (this.Text == null ? string.Empty: this.text, this.Font, Size.Empty, TextFormatFlags.HidePrefix);
1202 if (!this.auto_size || this is ToolStripControlHost)
1204 //this.text_size.Width += 6;
1206 Size final_size = this.CalculatePreferredSize (Size.Empty);
1208 if (final_size != this.Size) {
1209 this.bounds.Width = final_size.Width;
1210 if (this.parent != null)
1211 this.parent.PerformLayout ();
1215 internal virtual Size CalculatePreferredSize (Size constrainingSize)
1217 if (!this.auto_size)
1218 return this.explicit_size;
1220 Size preferred_size = this.DefaultSize;
1222 switch (this.display_style) {
1223 case ToolStripItemDisplayStyle.Text:
1224 int width = text_size.Width + this.padding.Horizontal;
1225 int height = text_size.Height + this.padding.Vertical;
1226 preferred_size = new Size (width, height);
1228 case ToolStripItemDisplayStyle.Image:
1229 if (this.Image == null)
1230 preferred_size = this.DefaultSize;
1232 switch (this.image_scaling) {
1233 case ToolStripItemImageScaling.None:
1234 preferred_size = this.Image.Size;
1236 case ToolStripItemImageScaling.SizeToFit:
1237 if (this.parent == null)
1238 preferred_size = this.Image.Size;
1240 preferred_size = this.parent.ImageScalingSize;
1245 case ToolStripItemDisplayStyle.ImageAndText:
1246 int width2 = text_size.Width + this.padding.Horizontal;
1247 int height2 = text_size.Height + this.padding.Vertical;
1249 if (this.Image != null) {
1250 switch (this.text_image_relation) {
1251 case TextImageRelation.Overlay:
1252 width2 = Math.Max (width2, this.Image.Width);
1253 height2 = Math.Max (height2, this.Image.Height);
1255 case TextImageRelation.ImageAboveText:
1256 case TextImageRelation.TextAboveImage:
1257 width2 = Math.Max (width2, this.Image.Width);
1258 height2 += this.Image.Height;
1260 case TextImageRelation.ImageBeforeText:
1261 case TextImageRelation.TextBeforeImage:
1262 height2 = Math.Max (height2, this.Image.Height);
1263 width2 += this.Image.Width;
1268 preferred_size = new Size (width2, height2);
1272 if (!(this is ToolStripLabel)) { // Everything but labels have a border
1273 preferred_size.Height += 4;
1274 preferred_size.Width += 4;
1277 // Account for ToolStripDropDownButton's drop down arrow
1278 if (this is ToolStripDropDownButton && (this as ToolStripDropDownButton).ShowDropDownArrow)
1279 preferred_size.Width += 9;
1281 return preferred_size;
1284 internal void CalculateTextAndImageRectangles (out Rectangle text_rect, out Rectangle image_rect)
1286 this.CalculateTextAndImageRectangles (this.ContentRectangle, out text_rect, out image_rect);
1289 internal void CalculateTextAndImageRectangles (Rectangle contentRectangle, out Rectangle text_rect, out Rectangle image_rect)
1291 text_rect = Rectangle.Empty;
1292 image_rect = Rectangle.Empty;
1294 switch (this.display_style) {
1295 case ToolStripItemDisplayStyle.None:
1297 case ToolStripItemDisplayStyle.Text:
1298 if (this.text != string.Empty)
1299 text_rect = AlignInRectangle (contentRectangle, this.text_size, this.text_align);
1301 case ToolStripItemDisplayStyle.Image:
1302 if (this.Image != null)
1303 image_rect = AlignInRectangle (contentRectangle, GetImageSize (), this.image_align);
1305 case ToolStripItemDisplayStyle.ImageAndText:
1306 if (this.text != string.Empty && this.Image == null)
1307 text_rect = AlignInRectangle (contentRectangle, this.text_size, this.text_align);
1308 else if (this.text == string.Empty && this.Image != null)
1309 image_rect = AlignInRectangle (contentRectangle, GetImageSize (), this.image_align);
1310 else if (this.text == string.Empty && this.Image == null)
1313 Rectangle text_area;
1314 Rectangle image_area;
1316 switch (this.text_image_relation) {
1317 case TextImageRelation.Overlay:
1318 text_rect = AlignInRectangle (contentRectangle, this.text_size, this.text_align);
1319 image_rect = AlignInRectangle (contentRectangle, GetImageSize (), this.image_align);
1321 case TextImageRelation.ImageAboveText:
1322 text_area = new Rectangle (contentRectangle.Left, contentRectangle.Bottom - (text_size.Height - 4), contentRectangle.Width, text_size.Height - 4);
1323 image_area = new Rectangle (contentRectangle.Left, contentRectangle.Top, contentRectangle.Width, contentRectangle.Height - text_area.Height);
1325 text_rect = AlignInRectangle (text_area, this.text_size, this.text_align);
1326 image_rect = AlignInRectangle (image_area, GetImageSize (), this.image_align);
1328 case TextImageRelation.TextAboveImage:
1329 text_area = new Rectangle (contentRectangle.Left, contentRectangle.Top, contentRectangle.Width, text_size.Height - 4);
1330 image_area = new Rectangle (contentRectangle.Left, text_area.Bottom, contentRectangle.Width, contentRectangle.Height - text_area.Height);
1332 text_rect = AlignInRectangle (text_area, this.text_size, this.text_align);
1333 image_rect = AlignInRectangle (image_area, GetImageSize (), this.image_align);
1335 case TextImageRelation.ImageBeforeText:
1336 LayoutTextBeforeOrAfterImage (contentRectangle, false, text_size, GetImageSize (), text_align, image_align, out text_rect, out image_rect);
1338 case TextImageRelation.TextBeforeImage:
1339 LayoutTextBeforeOrAfterImage (contentRectangle, true, text_size, GetImageSize (), text_align, image_align, out text_rect, out image_rect);
1347 private void LayoutTextBeforeOrAfterImage (Rectangle totalArea, bool textFirst, Size textSize, Size imageSize, ContentAlignment textAlign, ContentAlignment imageAlign, out Rectangle textRect, out Rectangle imageRect)
1349 int element_spacing = 0; // Spacing between the Text and the Image
1350 int total_width = textSize.Width + element_spacing + imageSize.Width;
1351 int excess_width = totalArea.Width - total_width;
1354 Rectangle final_text_rect;
1355 Rectangle final_image_rect;
1357 HorizontalAlignment h_text = GetHorizontalAlignment (textAlign);
1358 HorizontalAlignment h_image = GetHorizontalAlignment (imageAlign);
1360 if (h_image == HorizontalAlignment.Left)
1362 else if (h_image == HorizontalAlignment.Right && h_text == HorizontalAlignment.Right)
1363 offset = excess_width;
1364 else if (h_image == HorizontalAlignment.Center && (h_text == HorizontalAlignment.Left || h_text == HorizontalAlignment.Center))
1365 offset += (int)(excess_width / 3);
1367 offset += (int)(2 * (excess_width / 3));
1370 final_text_rect = new Rectangle (totalArea.Left + offset, AlignInRectangle (totalArea, textSize, textAlign).Top, textSize.Width, textSize.Height);
1371 final_image_rect = new Rectangle (final_text_rect.Right + element_spacing, AlignInRectangle (totalArea, imageSize, imageAlign).Top, imageSize.Width, imageSize.Height);
1373 final_image_rect = new Rectangle (totalArea.Left + offset, AlignInRectangle (totalArea, imageSize, imageAlign).Top, imageSize.Width, imageSize.Height);
1374 final_text_rect = new Rectangle (final_image_rect.Right + element_spacing, AlignInRectangle (totalArea, textSize, textAlign).Top, textSize.Width, textSize.Height);
1377 textRect = final_text_rect;
1378 imageRect = final_image_rect;
1381 private HorizontalAlignment GetHorizontalAlignment (ContentAlignment align)
1384 case ContentAlignment.BottomLeft:
1385 case ContentAlignment.MiddleLeft:
1386 case ContentAlignment.TopLeft:
1387 return HorizontalAlignment.Left;
1388 case ContentAlignment.BottomCenter:
1389 case ContentAlignment.MiddleCenter:
1390 case ContentAlignment.TopCenter:
1391 return HorizontalAlignment.Center;
1392 case ContentAlignment.BottomRight:
1393 case ContentAlignment.MiddleRight:
1394 case ContentAlignment.TopRight:
1395 return HorizontalAlignment.Right;
1398 return HorizontalAlignment.Left;
1401 private Size GetImageSize ()
1403 if (this.Image == null)
1406 if (this.image_scaling == ToolStripItemImageScaling.None)
1407 return this.Image.Size;
1409 if (this.Parent == null)
1412 return this.Parent.ImageScalingSize;
1415 internal string GetToolTip ()
1417 if (this.auto_tool_tip && string.IsNullOrEmpty (this.tool_tip_text))
1420 return this.tool_tip_text;
1423 internal void FireEvent (EventArgs e, ToolStripItemEventType met)
1426 case ToolStripItemEventType.MouseUp:
1427 this.OnMouseUp ((MouseEventArgs)e);
1428 this.OnClick ((MouseEventArgs)e);
1430 case ToolStripItemEventType.MouseDown:
1431 this.OnMouseDown ((MouseEventArgs)e);
1433 case ToolStripItemEventType.MouseEnter:
1434 this.OnMouseEnter (e);
1436 case ToolStripItemEventType.MouseHover:
1437 this.OnMouseHover (e);
1439 case ToolStripItemEventType.MouseLeave:
1440 this.OnMouseLeave (e);
1442 case ToolStripItemEventType.MouseMove:
1443 this.OnMouseMove ((MouseEventArgs)e);
1445 case ToolStripItemEventType.Paint:
1446 this.OnPaint ((PaintEventArgs)e);
1448 case ToolStripItemEventType.Click:
1454 internal virtual void SetPlacement (ToolStripItemPlacement placement)
1456 this.placement = placement;
1459 internal Point Location {
1460 get { return this.bounds.Location; }
1462 if (this.bounds.Location != value) {
1463 this.bounds.Location = value;
1464 this.OnLocationChanged (EventArgs.Empty);
1470 get { return this.bounds.Y; }
1472 if (this.bounds.Y != value) {
1473 this.bounds.Y = value;
1474 this.OnLocationChanged (EventArgs.Empty);
1480 get { return this.bounds.X; }
1482 if (this.bounds.X != value) {
1483 this.bounds.X = value;
1484 this.OnLocationChanged (EventArgs.Empty);
1489 internal int Right { get { return this.bounds.Right; } }
1490 internal int Bottom { get { return this.bounds.Bottom; } }
1493 public class ToolStripItemAccessibleObject : AccessibleObject
1495 private ToolStripItem owner_item;
1497 public ToolStripItemAccessibleObject (ToolStripItem ownerItem)
1499 if (ownerItem == null)
1500 throw new ArgumentNullException ("ownerItem");
1502 this.owner_item = ownerItem;
1503 base.default_action = string.Empty;
1504 base.keyboard_shortcut = string.Empty;
1505 base.name = string.Empty;
1506 base.value = string.Empty;
1509 #region Public Properties
1510 public override Rectangle Bounds {
1512 return owner_item.Visible ? owner_item.Bounds : Rectangle.Empty;
1516 public override string DefaultAction {
1517 get { return base.DefaultAction; }
1520 public override string Description {
1521 get { return base.Description; }
1524 public override string Help {
1525 get { return base.Help; }
1528 public override string KeyboardShortcut {
1529 get { return base.KeyboardShortcut; }
1532 public override string Name {
1534 if (base.name == string.Empty)
1535 return owner_item.Text;
1539 set { base.Name = value; }
1542 public override AccessibleObject Parent {
1543 get { return base.Parent; }
1546 public override AccessibleRole Role {
1547 get { return base.Role; }
1550 public override AccessibleStates State {
1551 get { return base.State; }
1555 #region Public Methods
1556 public void AddState (AccessibleStates state)
1561 public override void DoDefaultAction ()
1563 base.DoDefaultAction ();
1566 public override int GetHelpTopic (out string FileName)
1568 return base.GetHelpTopic (out FileName);
1571 public override AccessibleObject Navigate (AccessibleNavigation navdir)
1573 return base.Navigate (navdir);
1576 public override string ToString ()
1578 return string.Format ("ToolStripItemAccessibleObject: Owner = {0}", owner_item.ToString());