FlowDiagrams 简易模型绘图组件
FlowDiagrams 简易模型绘图组件
一、 目录
二、 序言
FlowDiagrams 控件是一个独立的,完全自主版权的强大绘图组件,完全基于 .Net 2.0 实现。支持动态图和Windows 组件绘图,并具备良好的扩展性,可以短时间完成自定义的绘图对象。
三、 特性
l 图的保存/装载,完全基于xml格式
l 可配置画布背景图像
l 采用抗锯齿绘图法
l 支持图像元素旋转
l 支持‘维持’机制,定时执行图元素的‘维持事件’
l 支持五种连线方式,并可以自动调整连线的方向
l 图元素可以遍历,并支持获取对象的有连接关系的对象
l 支持导出9种图像格式
l 图元素在设计状态下可以任意拖动和拾取
l 可组合多个图元素
l 图元素支持阴影,透明度,填充色等特效
四、 技术优势
完全的XML存储
这样,不需要任何转换,您就可以直接将你的文件成果通过外部的编辑器进行扩展,有利于编程。
无限可扩展的自定义属性
灵活的扩充图库的方法,可以无限扩展自定义属性和事件,您可以根据开发需求XML文档中写入您自己的数据逻辑,甚至是将 Windows User Control 组件放入画布内,从而实现了超越控件图形逻辑之外的任意功能。
和.Net无缝结合
FlowDiagrams 控件是一个纯.Net控件,完全采用C# 2.0开发,可以直接和.Net开发环境(VS2005)无缝结合,您可以象使用.Net中其他控件(如按钮(Button))一样拖放式地使用FlowDiagrams。
完全ActiveX Engine
ActiveX Engine 为B/S模式下的ActiveX模式的实现引擎,它实现了任意实现DLL转ActiveX的功能,而FlowDiagrams 可以和它完美兼容,通过ActiveX Engine 的支持,可以将FlowDiagrams 绘图环境完全移植为B/S模式。
完备的设计时状态支持
FlowDiagrams提供了最完备的设计时状态支持,在.Net编辑环境中,您可以很直观地利用属性框控制FlowDiagrams的外观和行为,可以大大减少您的开发工作量。
完全可定义的外部形状和组件库
除了完整的矢量形状绘制功能外,FlowDiagrams通过两种方式实现开发者的定制功能:形状和组件。通过形状,开发者可以实现符合自己的特殊形状的绘制功能,开发者可以实现自己定义的完整对象,包括外观和行为。FlowDiagrams完全支持上述两种方式的定制,并提供了相应的选择器控件,您所需要做的,便是建立起您自己的丰富形状和组件库。
五、 扩展开发
可继承绘图元素类型
类 |
说明 |
Bezier 曲线 |
|
曲线 |
|
椭圆 |
|
直线 |
|
智能连线 |
|
绘图对象基类 |
|
铅笔 |
|
矩形 |
|
Windows 组件 |
开发步骤
a) 继承基础类,图形元素的核心对象(详细帮助请阅读sdk文档)
i. 重载 DoDraw 方法绘制自定义的图形
/// <summary>
/// 到界面上绘制一个Button对象
/// </summary>
[Serializable]
public class DrawButton : DrawWinControl
{
/// <summary>
/// 覆盖tool类,用于设计器注册
/// </summary>
public override FlowDiagrams.Tools.Tool ToolObject
{
get
{
return base.ToolObject;
}
set
{
base.ToolObject = value;
}
}
/// <summary>
/// 重实现Text属性
/// </summary>
public new string Text
{
get
{
if (base.Control == null)
InitButton();
return base.Control.Text;
}
set
{
if (base.Control == null)
InitButton();
base.Text = value;
base.Control.Text = value;
}
}
/// <summary>
/// 公布按钮单击事件
/// </summary>
public event EventHandler<EventArgs> ButtonOnClick;
/// <summary>
/// 初始化一个Button实例
/// </summary>
protected void InitButton()
{
base.Control = new System.Windows.Forms.Button();
base.Control.Text = base.Text;
base.Control.Click += new EventHandler(Control_Click);
}
/// <summary>
/// 内部事件
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
void Control_Click(object sender, EventArgs e)
{
if (ButtonOnClick != null)
ButtonOnClick(sender, e);
}
/// <summary>
/// 构造
/// </summary>
public DrawButton()
{
//初始化Button
InitButton();
}
/// <summary>
/// 构造带初始坐标
/// </summary>
/// <param name="x1"></param>
/// <param name="y1"></param>
/// <param name="x2"></param>
/// <param name="y2"></param>
public DrawButton(int x1, int y1, int x2, int y2)
{
base.Rectangle = new System.Drawing.Rectangle(
x1, y1,
x2 - x1, y2 - y1);
InitButton();
}
/// <summary>
/// 从xml加载时刻
/// </summary>
/// <param name="x"></param>
public override void ReadFrom(System.Xml.XmlTextReader x)
{
base.ReadFrom(x);
//初始化Button
InitButton();
}
/// <summary>
/// 保存到xml时刻
/// </summary>
/// <param name="x"></param>
public override void SaveTo(System.Xml.XmlTextWriter x)
{
base.SaveTo(x);
}
}
b) 继承工具类,辅助类,用于注册到设计器和一些事件驱动(详细帮助请阅读SDK文档)
i. 编写注册的信息
[Serializable]
public class ToolButton : ToolRectangle
{
public ToolButton()
: base()
{
this.Caption = "按钮";
this.Description = "Windows 按钮组件";
this.Key = "DrawButton";
this.IconImage = global::ExtendLibrary.Properties.Resources.StopHS;
}
public override void OnMouseDown(FlowDiagrams.DrawArea drawArea, System.Windows.Forms.MouseEventArgs e)
{
AddNewObject(drawArea, new DrawButton(e.X, e.Y, 2, 2), this);
}
}
六、 实例
动态连线
a) 直线
//清空画布
this.drawArea.ClearGraphics();
//构造矩形
DrawRectangle rect1 = new DrawRectangle(100, 100, 100, 100);
rect1.Id = "A";
DrawRectangle rect2 = new DrawRectangle(300, 100, 100, 100);
rect2.Id = "B";
DrawRectangle rect3 = new DrawRectangle(500, 100, 100, 100);
rect3.Id = "C";
//构造连线
DrawLinkLine line1 = new DrawLinkLine();
line1.StartObjectID = "A"; //起点对象ID
line1.EndObjectID = "B"; //终点对象ID
line1.StartObjectHandlePoint = DrawObjectDirection.Down; //起点对象出口方向
line1.EndObjectHandlePoint = DrawObjectDirection.Up; //终点对象入口方向
line1.AutoOffset = true; //自动连线
//加入图元素到画布
this.drawArea.GraphicsList.Add(rect1);
this.drawArea.GraphicsList.Add(rect2);
this.drawArea.GraphicsList.Add(rect3);
this.drawArea.GraphicsList.Add(line1);
this.drawArea.GraphicsList.Add(line2);
this.drawArea.Refresh();
b) 曲线
this.drawArea.ClearGraphics();
DrawRectangle rect1 = new DrawRectangle(100, 100, 100, 100);
rect1.Id = "A";
DrawRectangle rect2 = new DrawRectangle(300, 100, 100, 100);
rect2.Id = "B";
DrawCurve line1 = new DrawCurve();
line1.StartObjectID = "A";
line1.EndObjectID = "B";
line1.StartObjectHandlePoint = DrawObjectDirection.Down;
line1.EndObjectHandlePoint = DrawObjectDirection.Up;
line1.AutoOffset = true;
line1.StartDistance = 80;
line1.EndDistance = 80;
this.drawArea.GraphicsList.Add(rect1);
this.drawArea.GraphicsList.Add(rect2);
this.drawArea.GraphicsList.Add(line1);
this.drawArea.Refresh();
c) Bezier
this.drawArea.ClearGraphics();
DrawRectangle rect1 = new DrawRectangle(100, 100, 100, 100);
rect1.Id = "A";
DrawRectangle rect2 = new DrawRectangle(300, 100, 100, 100);
rect2.Id = "B";
DrawBezier line1 = new DrawBezier();
line1.StartObjectID = "A";
line1.EndObjectID = "B";
line1.StartObjectHandlePoint = DrawObjectDirection.Down;
line1.EndObjectHandlePoint = DrawObjectDirection.Up;
line1.AutoOffset = true;
line1.StartDistance = 80;
line1.EndDistance = 80;
this.drawArea.GraphicsList.Add(rect1);
this.drawArea.GraphicsList.Add(rect2);
this.drawArea.GraphicsList.Add(line1);
this.drawArea.Refresh();
遍历图对象
//获得联合对象集合
List<UnionObject> luos = this.drawArea.GetUnionObject("A");
string output = "";
foreach (UnionObject uo in luos)
output += "对象:A 的连接对象有:" + uo.Object.Id + " 位置:" + uo.ObjectUnionType.ToString() + "\r\n";
MessageBox.Show(output);