vb.net cad 块表最后的实体_[CAD二次开发]一步一回顾——方法与代码重构

本文介绍了如何通过VB.NET进行CAD二次开发,将绘制直线的步骤封装成函数,以提高效率。文章详细讲解了函数的概念,展示了如何创建一个将实体绘制到数据库中的静态拓展方法,并通过数组参数实现批量绘制。同时,还引入了异常检测以增强程序的稳定性。
摘要由CSDN通过智能技术生成

    书接上回,上一篇介绍了在CAD中绘制一条直线并且在编辑栏中输出字符串,这个步骤以及代码量告诉我们,如果在二次开发的过程中,每绘制一个图形就用如此繁琐的步骤,那么效率会大大下降,本篇我们的目标是优化这个过程,将绘制直线的几个步骤做成函数,以便一行代码就可以将其调用。

    所谓函数(在面向对象编程的语境下更多的被称为方法),可以理解为一个数据的加工机器,数学中的函数是给它参数之后,就会输出相应的函数值,在编程中,函数(方法),在获得了参数之后,就会进行返回,这里有可能有返回值,有可能没有返回值(以void为返回值函数,大多是在执行一个过程)。

说道这里,让我们来观察一下上一篇中的代码:

020695b34740e4bfdd01f7279d716dbc.png

    在绘制一条直线的过程中,调用了数据库、事务处理、块表、块表记录等等数据,但是无论是绘制直线还是圆,无论是绘制这一条直线还是那一条直线,这个过程都可以视为向一个数据库中添加了一个实体。所以,我们可以用函数的思维这样看待这个问题:把当前数据库和即将绘制的实体作为函数参数,函数执行之后,我们不需要返回值,但是需要完成支线绘制的过程,在C#语言中,这个函数要这样声明:

public void AddToModelSpace(Database db,Entity entity){}

    其中void表示函数没有返回值,方法调用操作符(就是那组小括号)里面的数据库和实体就是参数(CAD中,实体是Entity类,直线等图形继承于Entity类,这里如果没了解过相关语法也不要紧,先按字面意思读即可,具体展开还是像上一篇一样,在挖的那个语法补充的坑里面补上)所以,整句话的意思就是,将数据库和实体传给函数,通过执行大括号里面的代码,完成一个将实体绘制于数据库中的过程,于是乎这里我们这样补全括号里面的代码,完成函数:

//函数所在的类类public class Class4{    //函数声明    public void AddToModelSpace(Database db,Entity entity)    {        //事务处理        using (Transaction trans=db.TransactionManager.StartTransaction())        {            //获取块表            BlockTable bt = trans.GetObject(db.BlockTableId,OpenMode.ForRead) as BlockTable;            //找到模型空间所对应的块表记录            BlockTableRecord btr = trans.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;            //将直线记录添加到模型空间的块表记录中            btr.AppendEntity(entity);            //将直线添加进事务处理中            trans.AddNewlyCreatedDBObject(entity,true);            //提交事务处理            trans.Commit();        }    }}

   这里说明一点,C#语言面向对象的特点非常坚决,所以任何函数都是出现在类里面的,由于这个类是Public类,所以在别的类中调用这个函数要这样:

//声明一个类的实例Class4 class4 = new Class4();//调用方法class4.AddToModelSpace(db,line);

    这样一个已经简化了图形绘制过程的过程,其实还有三个问题:

    1.CAD类库中的类已经够多了,我们还要再记一个,并且还要声明,这里显然又不简洁了,所以我们需要保留这个方法的功能,将他改为数据库的拓展方法,这样保留功能优化代码的过程一般称为重构(专业解释:重构就是在不改变软件系统外部行为的前提下,改善它的内部结构),这里,我们过河拆桥,使用拓展方法的方式让Class4这个类不在代码中出现(老规矩,拓展方法,以及下面出现的数组参数和异常检测这三个概念,在另一个系列里简述。这里只需要了解使用拓展方法的时候,需要将类和方法改为静态的,并且在一个参数的前面加一个this修饰符)

//函数声明public static void AddToModelSpace(this Database db,Entity entity){}//............................................................//调用方法 db.AddToModelSpace(line);

    这里的方法调用仿佛这个方法是数据库的方法,这样的调用方式也是我个人理解拓展方法这个名字的来历。

    2.只绘制一个实体过于片面,那么,如果有多个怎么一句话解决呢,这里使用数组参数。所谓数组参数,顾名思义,就是将数组作为参数,在参数前面加上params修饰符,并且在数据类型后面加上[]

//函数声明 public static void AddToModelSpace(this Database db, params Entity[] ents){}

    函数体里面,通过循环遍历(foreach循环)数组中的每一个参数,于是乎,代码被重构成了这样子:

//函数声明public static void AddToModelSpace(this Database db, params Entity[] ents){    //事务处理    using (Transaction trans = db.TransactionManager.StartTransaction())    {        //获取块表        BlockTable bt = trans.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;        //找到模型空间所对应的块表记录        BlockTableRecord btr = trans.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;        //遍历数组中的元素        foreach (var ent in ents)        {            //将直线记录添加到模型空间的块表记录中            btr.AppendEntity(ent);            //将直线添加进事务处理中            trans.AddNewlyCreatedDBObject(ent, true);        }          //提交事务处理         trans.Commit();     }}

    3.由于entity是所有图形的基类,所以在事务处理的过程中可能出现异常(也就是说不知道什么原因,没画上去),这里后果可能比较严重,甚至直接导致程序中断,数据丢失,所以我们通过异常检测(try…catch…语句块),来提高一下安全性。(这个问题坦诚一些要从硬币的两面去说:一方面,在开发过程中,我们会尽量减小程序坏掉的可能性,另外一方面,希望使用这种二次开发程序的朋友在画图过程中随手保存几下)。

//函数声明public static void AddToModelSpace(this Database db, params Entity[] ents){    //事务处理    using (Transaction trans = db.TransactionManager.StartTransaction())    {        //获取块表        BlockTable bt = trans.GetObject(db.BlockTableId, OpenMode.ForRead) as BlockTable;        //找到模型空间所对应的块表记录        BlockTableRecord btr = trans.GetObject(bt[BlockTableRecord.ModelSpace], OpenMode.ForWrite) as BlockTableRecord;        //遍历数组中的元素        foreach (var ent in ents)        {            //将直线记录添加到模型空间的块表记录中            btr.AppendEntity(ent);            //将直线添加进事务处理中            trans.AddNewlyCreatedDBObject(ent, true);        }        //try提交事务处理        try        {            trans.Commit();        }        //捕捉到异常,则取消事务处理        catch (System.Exception)        {            trans.Abort();        }    }}

    至此,今日目标完成21c74f1952ecd0bca20649a972343f2d.png。我们通过方法以及代码的重构优化了向数据库中添加实体的过程,同时也留下了这样几个关于C#语法的坑需要填:拓展方法,数组参数,异常,循环。关于这个系列,笔者的目标是给自己留下一个备忘录的同时,告诉大家CAD的二次开发可以做什么,方便讨论和集思广益,从而写出更好的功能,也给感兴趣于这个话题的朋友一个参考,方便大家讨论。有什么建议或意见,或者错误之处,敬请指出。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值