matlab - 绘制图形 - 不同边的不同线条样式
问题描述
我有一个节点和边图,我(x, y, z)
根据每个节点的坐标绘制。
我想用虚线表示“内”边缘,用直线表示“外”边缘。
LineStyle
可能对我有帮助,但我认为这会使我的所有边缘都变成虚线。我想指定点缀哪些边缘。
这是我用来绘制图表的代码:(G
是图表)
plot(G, 'XData', A(1,:), 'YData', A(2,:), 'ZData', A(3,:))
任何帮助深表感谢!
我有一个创建图表的函数,它给出了这个输出:
G =
graph with properties:
Edges: [11×1 table]
Nodes: [6×0 table]
和一个类似这样的坐标系:
A =
0 1 0 -1 0 0
0 1 3 2 1 2
1 1 1 1 1 1
使用上面的绘图函数,这提供了以下输出:
解决方案
好的,您并没有真正付出足够的努力来让每个人都能轻松回答您的问题,但我对一种方法感到好奇,而且它似乎有效,所以无论如何我都会发布它。
在这些情况下,必须以不同于整个组的方式绘制点/线的子组的经典技巧是:
- 绘制整个组
- 在顶部绘制具有不同线属性的子组
在您的情况下,这意味着您必须找到属于边界的点和边。我将在下面解释一种方法。请注意,此方法仅适用于凸边界(请参阅该方法不起作用的凹集的区别:凹与凸包)。
首先,我需要了解您的问题,所以让我们考虑一下:
%% Initial data
A =[ 0 1 0 -1 0 0
0 1 3 2 1 2
1 1 1 1 1 1 ];
G = graph ;
G = addedge(G,[1 1 1 1 1 2 2 2 3 4 4],[2 3 4 5 6 3 5 6 4 5 6]) ;
plot(G, 'XData', A(1,:), 'YData', A(2,:) , 'LineStyle','--')
grid on ; hold on
np = size(A,2) ; % Number of points/nodes
这将产生一个与您的完全一样的图形,只有一个linestyle
,它被设置为整个图形的虚线。现在的练习是用实线绘制轮廓。
要找到轮廓(至少在像你这样的二维情况下),使用的方法是:
- 找到轮廓的一点(初始点),
x
尽可能低。 - 计算单位向量
ux=[1,0,0]
和所有其他向量(由初始点和矩阵的所有其他点形成)之间的角度。 - 分配轮廓的下一个点(它是向量具有最小角度的点)。您现在有一个当前向量
vec
(在点 1 和 2 之间)和一个当前点pt2
。 - 计算
vec
与所有其他向量(由当前点pt2
和矩阵的所有其他点形成)之间的角度,轮廓的下一个点是向量具有最小角度的那个。 - 重复(3)和(4)直到轮廓的下一个点是起点。
翻译成代码:
%% find a point on the edge
% (I chose to start with the lowest point on Y axis)
[~,idxNext] = min(A(2,:)) ;
%% initialise counters
isOnEdge = false(np,1) ; % this will hold a logical register of contour points
idxEdge = idxNext ; % this will hold the points of the contour, in order
%% setup start conditions
isOnEdge(idxNext) = true ; % initial point
p = A(:,idxNext) ; % initial point
v = [1;0;0] ; % initial vector (start with unit vector oriented Ox)
%% search for contour
isRunning = true ;
iter = 0 ;
while isRunning
iter = iter + 1 ; % make sure we're not stuck in infinite loop
angs = find_angles(v,p,A) ; % find angles between initial vector and all other points
angs(idxNext) = Inf ; % Exclude current point
if numel(idxEdge) > 1 % Exclude last point (if not at first iteration)
angs(idxEdge(end-1)) = Inf ;
end
[~,idxNext] = min(angs) ; % find the index of the minimum angle
if isOnEdge(idxNext)
% we've completed the close profile, bail out
isRunning = false ;
else
% move on to next point/vector
idxEdge = [idxEdge idxNext] ; %#ok<AGROW>
isOnEdge(idxNext) = true ;
p = A(:,idxNext) ;
v = A(:,idxNext) - A(:,idxEdge(end-1)) ;
end
if iter > np
break % make sure we're not stuck in infinite loop
end
end
%% present results
if isRunning
fprintf('Could''t find a closed profile\n')
else
fprintf('Found points defining a closed profile:\n')
disp(idxEdge)
end
%% Plot on top of graph
% create a matrix conataining only the contour points, close the contour by
% replicating the first point in last position
C = [A(:,idxEdge) , A(:,idxEdge(1))] ;
% plot
plot3( C(1,:) , C(2,:) , C(3,:) ,'b', 'LineWidth',2)
view(2)
这将产生:
在上面的脚本中,我使用了函数find_angles.m
。它的代码:
function angs = find_angles(Uin,p,M)
% find angle between Uin vector and the vectors formed between p and
% all the points in M
np = size(M,2) ;
angs = zeros(np,1) ;
for iv=1:np
vec = M(:,iv) - p ;
c = cross(Uin,vec) ;
d = dot(Uin,vec) ;
angs(iv) = rad2deg( atan2( norm(c) , d ) ) * sign( c(3) ) ;
% take care of an edge case
if c(3)==0 && d==-1 ; angs(iv) = 180 ; end
% give [0 360] degree results
if angs(iv) < 0 ; angs(iv) = 180 + (180+angs(iv) ) ; end
end
推荐阅读
- php - Laravel 5 多态多对多关系,其中一个模型中有多个这样的关系
- javascript - 如何修复 jquery 错误 TypeError: 'click' called
- python - 对于循环和矩阵,替换行
- javascript - 如何使用 tocca.js 内联 div
- matlab - 试图离散化连续信号,但我试图绘制给定根的常规信号
- python - 正确使用 loop.create_future
- apache-spark - 如何使用 AirFlow 提取使用 Apache Livy 提交的 Spark 作业客户端日志批量 POST 方法
- node.js - https 路由到节点 js 生产
- python - “流动”而不是“捕捉”到蛇头部位置的蛇段
- c++ - 为什么 int plus float 向我显示奇怪的数字?