项目:连线的避障实现

转自:http://blog.csdn.net/li_canhui/article/details/6798380

先看看gef进阶的router部分:http://www.ibm.com/developerworks/cn/opensource/os-ecl-gef/part2/index.html

ConnectionRouter(连线路由器)

图形之间连线的路线,是由连线路由器来决定的。在Shapes Examples中,使用了最短路径路由器,这个路由器会帮我们绕开图形之间的障碍,选择一条最短路径进行连接,如图1所示:

图1. ShortestPathConnectionRouter效果图

我们看到左右两边图形的连线绕过了中间的图形,在两处发生了转折。这就是使用了最短路径路由器的效果。连线路由器可以安装到Connection Layer(连接层,关于层的概念我们在本系列下一篇中讲述),也可以针对某一条连接,所以只要你愿意,每条连线都可以有不同的路由器。如果你没有为某条连线指定一个路由器,那么缺省会使用连接层的路由器。Draw2D自带了一些路由器的实现,除了图1的ShortestPathConnectionRouter,还有ManhattanConnectionRouter等路由器实现,如果这些自带的路由器不能满足我们的需要,我们所要做的就是实现ConnectionRouter接口,实现一个自定义路由器。ConnectionRouter接口并不复杂,如下所示:

  • Object getConstraint(Connection connection);
  • void setConstraint(Connection connection, Object constraint);
  • void invalidate(Connection connection);
  • void route(Connection connection);
  • void remove(Connection connection);

setConstraint和getConstraint用来设置/得到连接上的Constraint(约束),所谓Constraint是指加在某个连线上的一些参数。我们可以看到constraint是一个Object类型,因为不同的路由器可能对constraint有不同的要求,对于ShortestPathConnectionRouter来说,constraint需要是一个List对象,里面包含了所有的转折点。

invalidate方法可以将一个连线置为无效,这样在下一次布局操作时,无效的连接将被重新路由。

remove方法是将连线从路由器中删除,也就是路由器不会再负责这条连线的布局,一般只有在删除一条连线的时候才会调用到,我们可以在里面做一些清除工作,比如释放和连线相关的cache。

route方法是路由操作真正发生的地方,我们一般只需要实现route方法就可以了,如果你还想做一些其他的操作,可以考虑实现其他方法。同样,一般是不推荐直接实现ConnectionRouter接口的,我们可以继承AbstractRouter类,这个类提供了一些简单的或者空的实现,还提供了两个额外的方法getStartPoint()和getEndPoint()方便我们得到连线的两个端点。

SingleBendpointConnectionRouter

我们将实现一个自定义的路由器,叫做SingleBendpointConnectionRouter,它采用一种走直角的方式连接两个图形,如图2所示:

图2. SingleBendpointConnectionRouter效果图

路由器实现的前提

显然我们无法凭空的计算出线路的走向,一条连线的具体路线和很多因素有关,比如锚点、图形的位置和大小,图形之间的相互关系,等等。所以我们需要能够访问到这些必须的信息,在Connection接口中,我们有getTargetAnchor()和getSourceAnchor()可以让我们得到锚点,而在ConnectionAnchor接口中(参见本系列第一部分),我们有getOwner()这样的方法,可以得到图形。这些必要的方法为我们实现路由器提供了可能。

实现route方法

route方法的代码如下:

 1 public void route(Connection conn) {
 2         // 清空连线的所有点
 3         PointList points = conn.getPoints();
 4         points.removeAllPoints();
 5
 6         // 得到目标和源参考点
 7         Point sourceRef = conn.getSourceAnchor().getReferencePoint();
 8         Point targetRef = conn.getTargetAnchor().getReferencePoint();
 9         A_POINT.setLocation(sourceRef.x, targetRef.y);
10
11         // 得到起始点和结束点
12         Point startPoint = conn.getSourceAnchor().getLocation(A_POINT);
13         Point endPoint = conn.getTargetAnchor().getLocation(A_POINT);
14
15         // 添加起始点
16         A_POINT.setLocation(startPoint);
17         conn.translateToRelative(A_POINT);
18         points.addPoint(A_POINT);
19
20         // 添加转折点
21         A_POINT.setLocation(sourceRef.x, targetRef.y);
22         conn.translateToRelative(A_POINT);
23         points.addPoint(A_POINT);
24
25         // 添加结束点
26         A_POINT.setLocation(endPoint);
27         conn.translateToRelative(A_POINT);
28         points.addPoint(A_POINT);
29
30         // 设置连线经过的所有点
31         conn.setPoints(points);
32     }

在我们这个路由器的设计里,一条连线由三个点组成:分别是起始点,转折点和结束点,它们构成了两条垂直的直线。起始点和结束点(也就是锚点)我们都已经了解如何得到了,中间的转折点,也很容易得出,我们就不解释了。要指出的是,我们需要把它们的坐标转换为相对坐标再添加,同时在添加完成之后,我们还需要调用setPoints()方法,这样才会生效。

所以说实现一个路由器的过程是很简单的,复杂之处在于路由算法。

改变连接层的路由器

我们只是实现了路由器,还没有把这个路由器设置为缺省的路由器,所以我们还要做一点小修改,在DiagramEditPart的createFigure()方法里,将ShortestPathConnectionRouter替换为SingleBendpointConnectionRouter即可。

待改进的地方

我们的自定义路由器很简单,但是它也有一点小问题,当两个图形在垂直或水平方向有重叠时,连线看上去有点不正常,如图3所示:

图3. 一点小bug

这只是由于我们的路由器算法不是很完善,没有考虑到所有情况而已。需要改进路由算法。

所以总结下:

1.创建新类:SingleBendpointConnectionRouter

2.在connectionEditPart的createFigure()方法里,将ShortestPathConnectionRouter替换为SingleBendpointConnectionRouter。

常见的 ConnectionRouter 为 BendpointConnectionRouter, FanRouter,ConnectionRouter.NullConnectionRouter,ManhattanConnectionRouter, ShortestPathConnectionRouter。

setConnectionRouter(ConnectionRouter cr)

所以重点在于自定义的router类里面的东西。



to be continued。

时间: 2024-10-15 01:51:26

项目:连线的避障实现的相关文章

具有避障和寻线功能的Arduino小车

标签:  Arduino  乐高  机器人 创客对于成年人来说,多半是科技娱乐,或者是一种是一种向往科技的人生态度,总是希望自己不仅可以看到或者听到科技的资讯,还希望能够亲身制作科技玩意,从而更好地体验科技. 说到科技娱乐,也就是做东西,不需要什么指标,高兴即可,所以做些容易的,也是OK的.这次带来的作品又是Arduino与乐高结合的小车,小车具有简单的避障和寻线功能. 避障传感器是夏普GP2Y0A21红外测距传感器,它是模拟量传感器,该传感器测距范围为10cm~80cm.Arduino模拟量信

[TPYBoard - Micropython 之会python就能做硬件 9] 五分种学会用TPYBoard V102 制作避障小车(升级版)

转载请注明:@小五义 http://www.cnblogs.com/xiaowuyi 欢迎加入讨论群 64770604 感谢山东萝卜电子科技公司授权 一.实验器材 1.TPYboard V102板  1块 2.电机驱动模块L298N   1个 3.电机 2块 4.小车底盘 1个 5.超声波模块 1个 6.舵机 1个 7.SG90舵机支架 1个 8.超声波云台支架 1个 二.超声波模块 1.什么是超声波模块 超声波传感器是利用超声波的特性研制而成的传感器, 它是通过传送一个超声波(远高于人的听觉范

2016山东省机器人比赛避障组小结

前言: 2016山东省机器人比赛差不多过去一年了,及时总结一下,给后来人一些经验,下文基本没有逻辑,全凭回忆,仅供参考,抛砖引玉. 比赛时间: 务必在7.10日之前完成报名,加入2017山东省机器人比赛官群和山科大机器人比赛官群,并及时确认报名是否完成.校赛2016年是国庆回来之后的第一个周,2016省赛好像是国庆一个月之后,可以看官方报名通知. 比赛准备: 工具:尖嘴钳.螺丝刀.万用表.剥线钳.电烙铁.焊锡等等 材料:常见的电阻电容等元器件.合适的电机.小车后轮(推荐跟买的电机配套的,务必要大

ROS Navigation 局部避障的动态窗口法(DWA)

耳熟能详的局部避障动态窗口法(Dynamic Window Approach) 概述:机器人局比避障规划方法有很多,ROS中主要采用的是动态窗口法(和原来的论文中的dwa方法不一样).动态窗口法主要是在速度(v,w)空间中采样多组速度,并模拟机器人在这些速度下一定时间内的轨迹.在得到多组轨迹后,对这些轨迹进行评价,选取最优得轨迹所对应的速度来驱动机器人运动.该算法的图书店在于动态窗口这个名词,它的含义是依据移动机器人的加减速性能限定速度采样空间在一个可行的动态范围. 1.机器人运动模型 见本博客

ROS(14)----局部避障的动态窗口算法(DWA)

Dynamic Window Approach(DWA)是重要的局部轨迹规划算法,ROS中使用了DWA算法获得了很好的局部路径规划的效果.这里收集了些很不错的资料. 参考资料: [1]. 机器人局部避障的动态窗口法(dynamic window approach)(*****) [2]. Autonomous Robot Navigation [3]. Circular Motion in 2D for graphics and robotics [4]. A Tutorial and Elem

SLAM+语音机器人DIY系列:(六)SLAM建图与自主避障导航——3.ros-navigation机器人自主避障导航

摘要 通过前面的基础学习,本章进入最为激动的机器人自主导航的学习.在前面的学习铺垫后,终于迎来了最大乐趣的时刻,就是赋予我们的miiboo机器人能自由行走的生命.本章将围绕机器人SLAM建图.导航避障.巡航.监控等内容展开.本章内容: 1.在机器人上使用传感器 2.google-cartographer机器人SLAM建图 3.ros-navigation机器人自主避障导航 4.多目标点导航及任务调度 5.机器人巡航与现场监控 3.ros-navigation机器人自主避障导航 前面的学习教程打好

4.9-移动,避障与导航

现在出现了两种开发模式(框架) 第一种,在ROS下针对机器人本体,相机,机械臂等开发接口,形成很多独立的包 这种是根据设备来对包进行分类,分模块开发 第二种,使用ROS的MoveIt!开发包,在这个大框架下,针对不同的机器人和机器人功能进行开发 这种是根据功能的不同,进行接口开发! 第二种貌似开始流行了!! 进行接口开发!! 目标:弄懂原理,看怎么样在不载入地图的情况下实现移动和避障行为,机器人行为设计 不载入地图是否意味着可以载入一个空的地图?(就算不是空的,也只给一个全局围墙,像一个矩形似的

Node.js项目的线上服务器部署与发布

课程目录:第1章 课程预热对整个部署思路进行全流程介绍,通过 5 个不同类型项目,来演示从本地的仓库到最终线上稳定运行的整个项目部署发布流程,来帮助始终编程在一线的前端或者后端工程师,甚至是有 Coding 能力的产品经理,从操作流程和架构形态上,掌握从零开始的项目上线环节,掌握这关键一步,跨过去前端到后端,本地到线上,开发到生产...第2章 待部署的 5 个本地 Nodejs 项目分别介绍五个技术架构和产品形态的项目背景,一个 Nodejs 静态网站,普通的带数据库电影网站,手机 App 场景

ESB雏形 -- 项目企业服务总线初始

今天要厚着脸皮给大家推荐一个自己做的通信中间件——ServiceAnt,目前已经在我们团队的两个产品线上投入了使用. ServiceAnt是什么 它最初的定位是ESB(企业服务总线),但目前还没有达到这个高度,主要是还是没有提供分布式的实现,有机会会补上. 现在它只能工作于进程内,与 Mediator 的角色非常类似. 可能有同学不知道 Mediator, Automapper 总该听过吧?它们的作者是一个人. ServiceAnt 部分的设计也参考了 Mediator,当然还有别的一些框架,比