在matlab

时间:2016-03-17 18:52:18

标签: matlab customization legend

在matlab图例中添加对标记的基本修改相对简单。由以下代码段(basic legend)生成的图例:

hold on h = plot(inf,inf,'ob',inf,inf,'r+'); legend(h,'Data1','Data2');

可以使用以下代码轻松修改为:modified legend

[~,~,icons,~] = legend(h,'Data1','Data2'); set(icons(1),'LineStyle','-') set(icons(2),'LineStyle','-')

但是,如果我想要正确地传达诸如object1(圆圈不在一条线的中间)或object2之类的物体,那么事情会变得相当复杂(一行的几种颜色带有' +'标记在上面)。我没有找到允许修改图例框中标记位置的任何属性或变通方法,或者在一个图例组中添加多个标记。

是否有人知道包含图例自定义高级信息的文档?或者如何更好地利用matlab提供的图形对象的众多属性来实现上述描述?

1 个答案:

答案 0 :(得分:4)

在最新R2014a的MatLab版本中,legend框实际上是axes,因此通过其句柄修改其内容相对容易。

从版本R2014b开始,legendgraphics object,似乎无法访问轴句柄(参考this post on undocumentedmatlab)。

高达R2014a

给出图中两行的图例:

h = plot((0:.1:2*pi),sin((0:.1:2*pi)),'ob',(0:.1:2*pi),cos((0:.1:2*pi)),'r+');
[a,b,icons,c] = legend(h,'Data1','Data2');
  • a是图例axex
  • 的句柄
  • b是handels的数组:
    • b(1):第一个字符串的句柄
    • b(2):第二个字符串的句柄
    • b(3):第一行的句柄
    • b(4):第一行标记的句柄
    • b(5):第二行的句柄
    • b(6):第二行标记的句柄

如果您想将第一行的marker移动到例如行尾,您可以:

  • 获取该行的XData(存储在b(3)中):它是一个(1x2)数组
  • XData的{​​{1}}(存储在marker中)设置为上一步获得的数组的最后一个值

如果您想添加更多b(4)并使第二行由更多不同颜色的细分组成,您可以:

  • 获取该行的markerXData(存储在YData
  • 通过拆分b(5)数组
  • 生成x coord
  • 使用XData值[{1}}
  • for循环中绘制细分

此方法已在以下代码中实现,其中,图例框也已放大,以使其更具“可读性”。

代码中的注释应该解释不同的步骤。

YData

结果如下:

enter image description here

来自R2014b

由于似乎无法访问图例axex,因此可以(如上面的标题post中所建议的那样添加y coord并将其叠加到图例中。

你可以创造传奇:

% Plot something
h = plot((0:.1:2*pi),sin((0:.1:2*pi)),'ob',(0:.1:2*pi),cos((0:.1:2*pi)),'r+');
% Add trhe legend
[a,b,icons,c] = legend(h,'Data1','Data2');
%
% a ==> handle of the legend axes
% b(1) ==> handle of the first string
% b(2) ==> handle of the second string
% b(3) ==> handle of the first line
% b(4) ==> handle of the marker of the first line
% b(5) ==> handle of the second line
% b(6) ==> handle of the marker of the second line
%
% Get positin and size of the legend box
ax_p=get(a,'position')
% Enlarge the legend box
set(a,'position',[ax_p(1)-.2 ax_p(2) ax_p(3)+.2 ax_p(4)])
% Set the linestyle of the first element on the legend
set(b(3),'linestyle','-')
% Get the XData of the first line
xl_1=get(b(3),'xdata')
% Move the marker of the first line to the end of the line
set(b(4),'xdata',xl_1(2))
% Get the position of the first string
xs_1=get(b(1),'position')
% Move the first string
set(b(1),'position',[xs_1(1)+.2 xs_1(2) xs_1(3)])
% Get the position of the second string
xs_2=get(b(2),'position')
% Move the second string
set(b(2),'position',[xs_2(1)+.2 xs_2(2) xs_2(3)])
% Split the second line in multi-color segment and add more marker on the
% second line
%
% Define the number of segments
n=4;
% Get the XData of the first line
xl_2=get(b(5),'xdata')
% Get the YData of the first line
yl_2=get(b(5),'ydata')
% Define the segments
len=linspace(xl_2(1),xl_2(2),n+1);
% Plot the segments of the second line in different colours
for i=1:n
   plot(a,[len(i) len(i+1)],[yl_2(1) yl_2(2)], ...
      'marker',get(b(6),'marker'),'markeredgecolor', ...
      get(b(6),'markeredgecolor'),'markerfacecolor',get(b(6),'markerfacecolor'), ...
      'color',rand(1,3),'linewidth',2)
end
  • a是axes(try h = plot((0:.1:2*pi),sin((0:.1:2*pi)),'o-',(0:.1:2*pi),cos((0:.1:2*pi)),'r+-'); [a,b,icons,c] = legend(h,'Data1','Data2');
  • 的对象
  • b是matlab.graphics.illustration.Legend个对象的数组(尝试class(a)

与旧版本类似,matlab.graphics.primitive.Data指的是:

  • b(1):first string
  • b(2):第二个字符串
  • b(3):第一行
  • b(4):第一行的标记
  • b(5):第二行
  • b(6):第二行的标记

您可以通过class(b)对象b获取position的{​​{1}}和size

然后,您可以应用上述相同的方法来绘制“更新的”图例。

此方法已在以下代码中实现(注释应解释不同的步骤)。

legend

希望这有帮助。

Qapla'