CAD开发__识别相交线之间闭合区域

概述

    在设计过程中,用户需要从一堆相交的线中去找出所有的闭合区域,然后统计面积或者做其他标注。CAD自带的BO命令可以生产面域,但只能一个个操作,显得比较繁琐。为此,给用户开发一个框选线识别闭合区域的功能能够给设计工作带来大大的便利。
在这里插入图片描述
实际工程使用中,相交线可能是直线、圆弧、多段线、样条曲线等(组一);线与线之间可能存在肉眼难以察觉的缺口,没有完全闭合;单条曲线存在多段线或者样条曲线自相交的情况(组二);一片区域内存在多组独立的最大闭合区域(组三);同时还存在多个不同的分组(组一~组三同时处理)。

原理

    闭合区域的识别,大体上有两种思路。
思路一:将曲线扩展,转换成一定宽度的长条形面,通过面的运算去寻找内轮廓,再内轮
       廓扩展得到实际内轮廓;
思路二:通过线与线之间布尔运算,得到首尾相连的曲线集合。
    两种思路各有优缺点。思路一的优点是实现相对简单、算法复杂度低、效率比较高,同时可以很方便地支持一定容差,缺点是线扩展成面以及内轮廓外扩,需要将曲线近似成折线才能处理。思路二的优点是不需要作近似,缺点是算法复杂度较思路一高、识别率偏低、容差比较难处理。
    本文就思路二探讨下实现原理。总实现流程如下:
在这里插入图片描述
    曲线分组流程如下:
在这里插入图片描述
    总流程中的大坐标处理,是指将整组曲线移动到原点附近,生成面域再把面域移动回原来的位置。之所以要进行大坐标处理,是因为一组曲线里面的点X坐标或者Y坐标大于10^8以后,小数部位截断误差太大,无法进行后续的打断处理。

    曲线分解流程如下:
在这里插入图片描述
    寻找可用曲线流程如下:
在这里插入图片描述
    获取最大外轮廓集流程如下:
在这里插入图片描述
    轮廓分解流程:
在这里插入图片描述
    寻找连线流程图如下:
在这里插入图片描述
通过以上步骤,理论上就能找出全部的闭合区域了。

以上步骤显得冗长和复杂,文字显得枯燥,各步骤示意图如下:
在这里插入图片描述

结果

    对于任何形式相交的曲线(直线、圆弧、多段线、样条曲线),都能找出闭合的区域。在保证闭合的情况下,拿实际项目图纸测试,效果如下:

识别前,红颜色的轮廓线
在这里插入图片描述
识别后,绿色的是面域。
在这里插入图片描述
由上图可见,只有两个闭合区域没有识别出来,识别率99%以上。

  • 12
    点赞
  • 34
    收藏
    觉得还不错? 一键收藏
  • 5
    评论
你可以使用 MATLAB 中的 `fill` 函数来涂色。 假设你有两条曲线 `x1` 和 `y1`,以及 `x2` 和 `2`,它们在某一区域相,你可以按照以下步骤来涂色: 1. 使用 `intersect` 函数找出两条曲线的交点,例如: ```matlab [x_intersect, y] = intersect(x1, y1, x2, y2); ``` 2. 将两条曲线分别拆成两个部分,分别涂色。例如,假设 `x_intersect` 和 `y_intersect` 分别表示交点的横坐标和纵坐标,则可以按照以下方式拆分曲线: ```matlab % 拆分曲线 1 x1_1 = x1(1:find(x1==x_intersect)-1); y1_1 = y1(1:find(x1==x_intersect)-1); x1_2 = x1(find(x1==x_intersect):end); y1_2 = y1(find(x1==x_intersect):end); % 拆分曲线 2 x2_1 = x2(1:find(x2==x_intersect)-1); y2_1 = y2(1:find(x2==x_intersect)-1); x2_2 = x2(find(x2==x_intersect):end); y2_2 = y2(find(x2==x_intersect):end); ``` 3. 使用 `fill` 函数分别对拆分后的曲线部分进行涂色。例如: ```matlab % 涂色第一部分 fill([x1_1 x2_1(end:-1:1)], [y1_1 y2_1(end:-1:1)], 'r'); % 涂色第二部分 fill([x1_2 x2_2(end:-1:1)], [y1_2 y2_2(end:-1:1)], 'g'); ``` 完整的代码如下所示: ```matlab % 生成两条曲线 x1 = 0:0.1:10; y1 = sin(x1); x2 = 0:0.1:10; y2 = cos(x2); % 找出两条曲线的交点 [x_intersect, y_intersect] = intersect(x1, y1, x2, y2); % 拆分曲线 1 x1_1 = x1(1:find(x1==x_intersect)-1); y1_1 = y1(1:find(x1==x_intersect)-1); x1_2 = x1(find(x1==x_intersect):end); y1_2 = y1(find(x1==x_intersect):end); % 拆分曲线 2 x2_1 = x2(1:find(x2==x_intersect)-1); y2_1 = y2(1:find(x2==x_intersect)-1); x2_2 = x2(find(x2==x_intersect):end); y2_2 = y2(find(x2==x_intersect):end); % 涂色第一部分 fill([x1_1 x2_1(end:-1:1)], [y1_1 y2_1(end:-1:1)], 'r'); % 涂色第二部分 fill([x1_2 x2_2(end:-1:1)], [y1_2 y2_2(end:-1:1)], 'g'); ``` 运行代码后,你应该可以看到两条曲线相交区域被涂上了不同的颜色。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值