要绘制电容,首先在FxClassLibrary目录下创建一个类文件(这里就以创建一个名为“FxBox_dianrong.cs“的类文件为例),接着要在FxControlle目录下的VerticalToolTabs文件中ToolWindowHost文件中创建一个“电容”按钮,要,其中就包括电阻图形以及节点的绘制代码。下面我们就来详细讨论下电阻和节点以及连线是怎样绘制的。
1、在FxClassLibrary目录下创建一个名为“FxBox_dianrong.cs“的类文件。并在其中设置定义一些将要在绘制“电阻”所要的一些变量。这里我们添加如下代码:
privateFontTxtFont; //文字
privatePen LinePen; //直线笔 , 用来绘制图像线条的
privatePen RectPen; //矩形笔,用来绘制图形被选中时的边框¨°
private Color LineColor; //直线颜色
private Color RectColor; //矩形框颜色
private Pen LinePen_Selected; //选中时的笔
private Color LineColor_Selected;
private Pen PointPen; //连接点
private Color PointColor; //连接点颜色¦
2、然后就是把电阻类文件与电阻按钮事件关联起来。此处主要是在ToolWindowHost创建一个名为“电容”的按钮并在按钮事件中添加如下代码:
if (frmDesign != null)
{
System.Collections.Hashtable ht =new System.Collections.Hashtable();
ht.Add("Class", "Box_dianrong");
this.frmDesign.CreateFxLibraryModelObject(ACTION.CreatLibraryModelObject, ht);
}
然后在FormDesignView.cs 中添加如下代码:
case "Box_dianrong":
{
FxClassLibrary.FxBox_dianrong box =new FxClassLibrary.FxBox_dianrong();
this.NewObject = (FxCAD.Core.LibraryModelObject.LibObject)(box);
break;
}
3、根据1、2步把类文件和按钮事件相关联起来后,就要在类文件(这里还是以FxBox_dianrong.cs为例说明)中实现“电容”图形的绘制,以及为以后图形的绘制做准备,就是要在绘制“电容”的过程中实现对节点的设置和绘制:
① 、因为在FxCAD中,绘制“电容”图形,主要是为了实现“电容”之间以及“电容”和其他图形之间的连接,所以在实现“电容”图形的绘制时,就要定义相应的节点(其坐标设置看后面具体的“电容”绘制数据),并且还要计算需要多少个节点。在此,以在FxBox_dianzu.cs中“电容”绘制的构造函数中定义节点,并且还要实现对节点个数的计算(在FxBox_dianrong.cs实现对节点个数的计算是函数“Init()”)。代码如下:
public FxBox_dianrong()
{
//构造函数
this.FxBoxNodeType = (int)FxBox_dianrong.LIGHT_NODE_TYPE.general;
Nodes = new ArrayList();
SetName(Guid.NewGuid().ToString());/
Nodes.Add(new NODE("电容A", 0));
Nodes.Add(new NODE("电容B", 0));
this.Init(2);
}
private void Init(int NodeNum)
{
OBJ_TYPE = (int)LibObject.ObjectType.LibObject;
LineColor = Color.Black;
RectColor = Color.Red;
LinePen = new Pen(LineColor, 2);
RectPen = new Pen(RectColor, 1);
RectPen.DashStyle = System.Drawing.Drawing2D.DashStyle.Dash;//DashStyle.Dash;
LineColor_Selected = Color.Red;
LinePen_Selected = newPen(LineColor_Selected, 2);
PointColor = Color.Red;
PointPen = new Pen(PointColor, 2);
TxtFont = new Font("宋体", 12);
this.NodeNum = NodeNum;//保存接点数
}
② 、在FxBox_dianrong.cs文件中创建一个绘图函数
public overridevoid DrawGraphics(System.Drawing.Graphics g)
{
}
③ 、其次就是对“电容”在与其他图形实现连线的状态分析:要实现电阻之间,电容器之间以及电阻和电容器之间的连接,就要判断电阻之间,电容器之间以及电阻和电容器之间是处于一种什么样的状态(是已连接、还是被选中等)。在此,把它们之间的状态分为3种状态,分别是Normal(正常)、Selected (选中)、Linking(连接)。根据这种状态分别绘制不同的图形(这里主要以电阻的颜色来区分)。为了更好的观看“被选中”((Selected (选中)),在此还定义了一个函数,实现在“选中”图形的外面画一个红色的虚线矩形。其主要代码是:
private void DrawSelectedRect(Graphics g, Pen RectPen)
{
//绘制边框 (选中时绘制)
g.DrawRectangle(RectPen, P0.X - 40, P0.Y - 10, Weight + 140, Height + 40);
}
③ 、由于要实现对“电容”之间,以及“电容”与其他图形之间的连线,在绘制“电容”图形就要在“电容”图形中设置相应的节点坐标。并绘制出相应的“节点”图形。在此,定义如下的“节点”函数:
privatevoid DrawNode(Graphics g,Pen LinePen)
{
}
④ 、根据③的“电容”状态分析在此就可以实现①、②中对“电容”状态和节点的实现具体的绘制:
publicoverride void DrawGraphics(System.Drawing.Graphics g)
{
switch (OBJ_STATE)
{
case (int)LibObject.ObjectState.Normal:
{
this.DrawNode(g, LinePen);
break;
}
case (int)LibObject.ObjectState.Selected:
{
this.DrawNode(g, LinePen_Selected);
this.DrawSelectedRect(g, RectPen);
break;
}
case (int)LibObject.ObjectState.Linking:
{
this.DrawNode(g, LinePen_Selected);
this.DrawSelectedRect(g, RectPen);
break;
}
}
}
4、电容绘制
在winform中的坐标轴和我们平时接触的平面直角坐标轴不同,winform中的坐标轴方向完全相反:窗体的左上角为原点(0,0),水平向左则X增大,垂直下向则Y增大
在此处我们绘制电容的代码如下
g.DrawLine(new Pen(Color.Red, 2), P0.X, P0.Y + 11, P0.X - 30, P0.Y + 11);
g.DrawLine(new Pen(Color.Red, 2), P0.X + 20, P0.Y + 11, P0.X + 50, P0.Y + 11);
g.DrawLine(new Pen(Color.Red, 2), P0.X, P0.Y, P0.X, P0.Y + 25);
g.DrawLine(new Pen(Color.Red, 2), P0.X + 20, P0.Y, P0.X + 20, P0.Y + 25);
5、根据上面(4、电容的绘制)的图形分析就可以在节点函数中个实现对具体节点坐标的设置,并且根据节点坐标绘制相应的节点。因为节点能否被看见主要是取决于图形是否被选中,以及该节点是否被其他图形连接过,所以,这里要根据图形的选中状态和节点的连接与否来设置节点绘制节点:
①、首先就是要初始化节点
LinkPoint_FLag = false; //初始态没有连接点
②、其次就是根据电阻、节点状态来设置、绘制节点
node.SetLinkPoint(P0.X + x, P0.Y + 11);//设置连接点
g.DrawRectangle(PointPen, (P0.X + x) - 5 / 2-1, (P0.Y + 10) - 5 / 2, 5, 5);
③、然后就是判断节点是否被连接过,根据判断来设置节点
if (node.LinkLineObj == null) //没有连接过才能连接
{
if (mX > node_x0 - 20 && mX < node_x0 + 20 && mY > P0.Y + 2 && mY < P0.Y + 22)
{
PointNode = node; //在该区域有连接点
g.FillEllipse(Brushes.Black, (P0.X + x) - 5 / 2-1, (P0.Y + 10) - 5 / 2, 5, 5);
LinkPoint_FLag = true; //找到连接点
}
}
④、就是保存连接点的坐标
LinkPoint.X = P0.X-30;
LinkPoint.Y = P0.Y +11;
程序运行结果如下: