Многоколоночная легенда в Matlab - PullRequest
1 голос
/ 25 ноября 2011

Я хотел бы иметь возможность создать легенду с заданным количеством столбцов (по умолчанию функция легенды имеет уникальный столбец в Matlab). Например, в приведенном ниже коде мне нужно три столбца в легенде, чтобы в нем было две строки и три строки столбца.

X = 0:pi/100:0.25*pi;
Y1 = sin(X);
Y2 = cos(X);
Y3 = tan(X);
Y4 = 0.5;
fh = figure('toolbar','none','menubar','none','Units','characters');
Pan1 = uipanel(fh,'Units','normalized','Position',[0 0 0.5 1],'title',...
    'Panel1');
Pan2 = uipanel(fh,'Units','normalized','Position',[0.5 0 0.5 1],'title',...
    'Panel2');
haxes = axes('Parent',Pan2,'Units', 'normalized','Position',...
[0.125 0.1 0.75 0.75]);
hplot = plot(haxes,X,Y1,X,Y2,X,Y3,X,Y4);
xlabel(haxes,'Time (second)');
ylabel(haxes,'Amplitude (meter)');
title(haxes,'Trigonometric functions');
Ley = {'Sine function','Cosine function','Tangent function','Constant'};
legend(haxes,Ley,'Location','SouthOutside');

Я пытался использовать приложение под названием gridlegend на Matlab File Exchange , заменяющем

legend(haxes,Ley,'Location','SouthOutside');

с

gridLegend(hplot,2,Ley,'Location','SouthOutside');

и

gridLegend(hplot,3,Ley,'Location','SouthOutside');

Однако полученные результаты являются недействительными, поскольку содержание легенды выглядит перекрывающимся и включающим, для случая 3, неверное.

P.D. Я также пробовал приложение под названием columnlegend на Matlab File Exchange , но мне нужно, чтобы это расположение легенды было SouthOutside, поэтому оно не работает для меня.

1 Ответ

0 голосов
/ 04 декабря 2011

Вот мое решение для легенды с местоположением «SouthOutside» (я предположил, что графический объект осей имеет «нормализованные» единицы и его «Положение» равно [0,1 0,1 0,8 0,8]):

function CLegend(hax,numcol,Ley)
%# Inputs
% hax : handle of the axes object to which belongs the legend
% numcol: number of columns for the legend
% Ley: text strings (labels) for the legend

set(hax,'Units','normalized','Position',[0.1 0.1 0.8 0.8]);
set(hax,'Units','characters');
posAx = get(hax,'Position');
insAx = get(hax,'TightInset');

[legend_h,object_h] = legend(hax,Ley,'Units','characters','Location',...
    'South','Orientation','vertical');
posl = get(legend_h,'Position');
numlines = length(Ley);
if (numlines<numcol)
    numcol = numlines;
end

numpercolumn = ceil(numlines/numcol);

if (mod(numlines,numpercolumn) == 0)
    numcol = numlines/numpercolumn;
end

l = zeros(1,numlines);
a = zeros(1,numlines);
h = zeros(1,4);
for j=1:numlines
    h = get(object_h(j),'Extent');
    l(j) = h(3);
    a(j) = h(4);
    set(object_h(j),'Units','characters');
end

lmax = posl(3)*max(l);
hmax = posl(4)*max(a);
hLine = object_h(numlines+1);
xdata = get(hLine, 'xdata');
dx = xdata(2)-xdata(1);
di = 2;

sheight = hmax;     
height = hmax*numpercolumn-sheight/2;            
line_width = dx*posl(3);                
spacer = xdata(1)*posl(3);              
delta1 = spacer + line_width + spacer + lmax;
delta2 = line_width + spacer + lmax + spacer;
delta3 = lmax + spacer + line_width + spacer;
factx = 1/(posl(3)*numcol);
facty = 1/(hmax*numpercolumn);
width_l = numcol*delta1;

set(legend_h, 'Position', [posAx(1) + 0.5*(posAx(3)-width_l) posl(2) ...
   width_l  numpercolumn*hmax]);

col_ind = -1;
row_ind = -1;
j = 0;
for i=1:numlines,

    if strcmpi(orient,'horizontal'),
        if mod(i,numcol)==1,
            row_ind = row_ind+1;
        end
        col_ind = mod(i,numcol)-1;
        if col_ind == -1,
             col_ind = numcol-1;
        end

    else
        if numpercolumn==1 || mod(i,numpercolumn)==1,
            col_ind = col_ind+1;
        end

        row_ind = mod(i,numpercolumn)-1;
        if row_ind == -1,
             row_ind = numpercolumn-1;
        end   
    end

    if (i==1)
        linenum = i+numlines;
    else
        linenum = linenum+di;
    end
    labelnum = i;

    set(object_h(linenum), 'ydata',facty*[height-row_ind*sheight ...
        height-row_ind*sheight]);
    set(object_h(linenum), 'xdata', factx*[spacer + j*delta2 ...
                spacer + j*delta2 + line_width]);
    set(object_h(linenum+1), 'ydata',facty*(height-row_ind*sheight));
    set(object_h(linenum+1), 'xdata', factx*(spacer+line_width/2));
    set(object_h(labelnum), 'Position', [j*delta3+spacer*2+line_width ...
        height-row_ind*sheight]);
    if (mod(i,numpercolumn)== 0)
        j = j + 1;   
    end
end
opl = get(legend_h,'OuterPosition');
set(hax, 'Position',[posAx(1) posAx(2)+opl(4) posAx(3) posAx(4)-opl(4)]);

set(legend_h, 'OuterPosition',[opl(1) (posAx(2)-insAx(2))/2 opl(3) opl(4)]);
set([hax,legend_h],'Units','normalized');
end
...