using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms.Design;
using System.ComponentModel.Design;
namespace Dah.Framework.Windows.Design
{
internal class StackPanelDesigner : ParentControlDesigner // 这个类在System.Design.dll里, 一般的控件Designer可以继承ControlDesigner..
{
DesignerActionListCollection _actionLists;
public override SelectionRules SelectionRules
{
get
{
if (TheStackPanel.AutoSize) // 如果AutoSize
{
return SelectionRules.Moveable; // 则只能移动, 不能手动改变大小
}
else // 否则可以改变大小
{
return SelectionRules.Moveable | SelectionRules.AllSizeable;
}
}
}
public override System.ComponentModel.Design.DesignerActionListCollection ActionLists
{
get
{
if (_actionLists == null)
{
_actionLists = new DesignerActionListCollection();
// 给 Smart Tag 添加 StackPanelActionList 里的选项
_actionLists.Add(new StackPanelActionList(this.Component));
// 给 Smart Tag 添加 LinearGradientPanelActionList 里的选项 , 因为 StackPanel 继承了 LinearGradientPanel
_actionLists.Add(new LinearGradientPanelActionList(this.Component));
}
return _actionLists;
}
}
private StackPanel TheStackPanel
{
get
{
return (StackPanel)Control; // Designer 所 Design 的 Control
}
}
}
}
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms.Design;
using System.ComponentModel.Design;
namespace Dah.Framework.Windows.Design
{
internal class StackPanelDesigner : ParentControlDesigner // 这个类在System.Design.dll里, 一般的控件Designer可以继承ControlDesigner..
{
DesignerActionListCollection _actionLists;
public override SelectionRules SelectionRules
{
get
{
if (TheStackPanel.AutoSize) // 如果AutoSize
{
return SelectionRules.Moveable; // 则只能移动, 不能手动改变大小
}
else // 否则可以改变大小
{
return SelectionRules.Moveable | SelectionRules.AllSizeable;
}
}
}
public override System.ComponentModel.Design.DesignerActionListCollection ActionLists
{
get
{
if (_actionLists == null)
{
_actionLists = new DesignerActionListCollection();
// 给 Smart Tag 添加 StackPanelActionList 里的选项
_actionLists.Add(new StackPanelActionList(this.Component));
// 给 Smart Tag 添加 LinearGradientPanelActionList 里的选项 , 因为 StackPanel 继承了 LinearGradientPanel
_actionLists.Add(new LinearGradientPanelActionList(this.Component));
}
return _actionLists;
}
}
private StackPanel TheStackPanel
{
get
{
return (StackPanel)Control; // Designer 所 Design 的 Control
}
}
}
}
如果要加上自己的SmartTag就还得写ActionList类, 如下面的StackPanelActionList:
using System;
using System.Collections.Generic;
using System.Text;
using System.ComponentModel;
using System.ComponentModel.Design;
using System.Drawing;
namespace Dah.Framework.Windows.Design
{
/// <summary>
/// 定义了 StackPanel 的 Smart Tag 选项
/// </summary>
internal class StackPanelActionList : DesignerActionList
{
private StackPanel _stackPanel;
public StackPanelActionList(IComponent component)
: base(component)
{
this._stackPanel = component as StackPanel;
}
private PropertyDescriptor GetPropertyByName(String propName)
{
PropertyDescriptor prop;
prop = TypeDescriptor.GetProperties(_stackPanel)[propName];
if (null == prop)
throw new ArgumentException("Matching StackPanel property not found!", propName);
else
return prop;
}
private void SetValue(string propertyName, object value)
{
GetPropertyByName(propertyName).SetValue(_panel, value);
}
//要有哪些属性的选项, 都得这样写一遍
public bool AutoSize
{
get { return _stackPanel.AutoSize; }
set { SetValue("AutoSize", value); }
}
public bool CenterAlign
{
get { return _stackPanel.CenterAlign; }
set { SetValue("CenterAlign", value); }
}
public StackPanelOrientation Orientation
{
get { return _stackPanel.Orientation; }
set { SetValue("Orientation", value); }
}
//这个方法在下面用到了, 可以用来调用控件的方法
public void RefreshChildrenPosition()
{
_stackPanel.RefreshChildrenPosition();
}
//这个方法指定了Smart Tag到底有哪些选项
public override DesignerActionItemCollection GetSortedActionItems()
{
DesignerActionItemCollection items = new DesignerActionItemCollection();
string headerName = "StackPanel Options";
//添加一个选项 Category
items.Add(new DesignerActionHeaderItem(headerName));
//下面的各种选项都属于这个Category, 用headerName来指定
items.Add(new DesignerActionPropertyItem("AutoSize", "Auto Size", headerName));
items.Add(new DesignerActionPropertyItem("CenterAlign", "Center Align", headerName));
items.Add(new DesignerActionPropertyItem("Orientation", "Orientation", headerName));
//上面三个都是控件属性的设置, 这个则可以给Smart Tag添加一个LinkButton来执行某些方法
//this, 说明了"RefreshChildrenPosition"这个方法在这个类中实现
items.Add(new DesignerActionMethodItem(this, "RefreshChildrenPosition", "Refresh children position", headerName));
return items;
}
}
}
using System.Collections.Generic;
using System.Text;
using System.ComponentModel;
using System.ComponentModel.Design;
using System.Drawing;
namespace Dah.Framework.Windows.Design
{
/// <summary>
/// 定义了 StackPanel 的 Smart Tag 选项
/// </summary>
internal class StackPanelActionList : DesignerActionList
{
private StackPanel _stackPanel;
public StackPanelActionList(IComponent component)
: base(component)
{
this._stackPanel = component as StackPanel;
}
private PropertyDescriptor GetPropertyByName(String propName)
{
PropertyDescriptor prop;
prop = TypeDescriptor.GetProperties(_stackPanel)[propName];
if (null == prop)
throw new ArgumentException("Matching StackPanel property not found!", propName);
else
return prop;
}
private void SetValue(string propertyName, object value)
{
GetPropertyByName(propertyName).SetValue(_panel, value);
}
//要有哪些属性的选项, 都得这样写一遍
public bool AutoSize
{
get { return _stackPanel.AutoSize; }
set { SetValue("AutoSize", value); }
}
public bool CenterAlign
{
get { return _stackPanel.CenterAlign; }
set { SetValue("CenterAlign", value); }
}
public StackPanelOrientation Orientation
{
get { return _stackPanel.Orientation; }
set { SetValue("Orientation", value); }
}
//这个方法在下面用到了, 可以用来调用控件的方法
public void RefreshChildrenPosition()
{
_stackPanel.RefreshChildrenPosition();
}
//这个方法指定了Smart Tag到底有哪些选项
public override DesignerActionItemCollection GetSortedActionItems()
{
DesignerActionItemCollection items = new DesignerActionItemCollection();
string headerName = "StackPanel Options";
//添加一个选项 Category
items.Add(new DesignerActionHeaderItem(headerName));
//下面的各种选项都属于这个Category, 用headerName来指定
items.Add(new DesignerActionPropertyItem("AutoSize", "Auto Size", headerName));
items.Add(new DesignerActionPropertyItem("CenterAlign", "Center Align", headerName));
items.Add(new DesignerActionPropertyItem("Orientation", "Orientation", headerName));
//上面三个都是控件属性的设置, 这个则可以给Smart Tag添加一个LinkButton来执行某些方法
//this, 说明了"RefreshChildrenPosition"这个方法在这个类中实现
items.Add(new DesignerActionMethodItem(this, "RefreshChildrenPosition", "Refresh children position", headerName));
return items;
}
}
}
准备工作完毕, 给自定义控件加个DesignerAttribute就O了~:
[Designer(typeof(Dah.Framework.Windows.Design.StackPanelDesigner))]
public class StackPanel : LinearGradientPanel
{
public event EventHandler ContentMarginChanged;
public class StackPanel : LinearGradientPanel
{
public event EventHandler ContentMarginChanged;
看看我们美丽的自定义Designer和Smart Tag吧~
久不发文... 仅此灌水一篇~
更多的有关如何扩展控件设计时行为的文章在MSDN Library:
http://msdn2.microsoft.com/en-us/library/37899azc.aspx