Scatter plot legend with multiple column ?

10 views (last 30 days)
Luca Ricci
Luca Ricci on 4 Oct 2024
Edited: dpb on 7 Oct 2024
Hi everyone,
I saw an interesting plot on a presentation for its legend (content apart):
I am wondering how I can recreate a plot with a similar legend. I am using Matlab2024a. Something like this would greatly improve the readibility of my plot beacuse it reduces the numer of marker shapes.
EXAMPLE --> Let us say each point in my scatter plot belong to two categories: apple and oranges. However, there are different kinds of these fruits. Therefore, I would like to classify them based on their kinds in the legend. In practice, the items on the legend should be similar to the one above. Filled and not filled markers to distinguish the kind of fruits. In the bottom of the legend, something similar to "Single-channel" and "Time-interleaving" above to put the names of the kinds. Different markers, instead, expresses apple and oranges.
Do you have any idea if this is possible in matlab ?
Thank you in advance !

Answers (2)

dpb
dpb on 4 Oct 2024
Actually, it's not difficult, just turn off the annotation labels for one of two scatter objects and then use the legend for both with the two column. Note the empty annotation is for the first so the blank space is first to make the two symbols appear together; if it were reversed, the two symbols would bracket the displayed names...
I didn't try to see if there's any way to change the spacing any; the recent changes to the label object have made it much more opaque to the user; the underlying axes object itself is no longer accessible...
tbl = readtable('patients.xls');
s1=scatter(tbl(tbl.Weight<155,:),'Weight',{'Systolic','Diastolic'},'DisplayName','');
hold on
s2=scatter(tbl(tbl.Weight>155,:),'Weight',{'Systolic','Diastolic'},'filled');
hL=legend([s1 s2],'NumColumns',2);
  1 Comment
dpb
dpb on 5 Oct 2024
"I didn't try to see if there's any way to change the spacing any;..."
I did later -- trying to shorten the width to cause the two symbols to appear closer together didn't work;
pos=hL.Position; % return the legend position
pos(3)=0.9*pos(3); % reduce width 10$
hL.Position=pos; % set to new position
ran without warning/error, but the end position/size of the legend was unchanged...

Sign in to comment.


Kanishk
Kanishk on 7 Oct 2024
Hi Luca,
I understand you want to create a plot with grouped legend markers. @dpb suggested a method, but here is another approach.
To create a similar plot
  • Plot all the filled marker data points.
  • Plot data points with unfilled markers.
  • Create a legend with empty strings for filled markers and group labels for unfilled markers. Set the ‘NumColumns’ property to 2 to organize the legend into two columns.
  • Add dummy plots with arrow markers to represent the filled and unfilled markers.
In MATLAB R2024b, IconColumnWidth property can also be used to modify the width of the legend icons.
Below is the code for the implementation.
% Sample data
x = 1:10;
y1 = rand(1, 10);
y2 = rand(1, 10);
y3 = rand(1, 10);
y4 = rand(1, 10);
y5 = rand(1, 10);
y6 = rand(1, 10);
% Plot the first group with filled markers
h1 = scatter(x, y1, 'o', 'MarkerFaceColor', 'b');
hold on;
h2 = scatter(x, y1, '^', 'MarkerFaceColor', 'b');
h3 = scatter(x, y1, 'x', 'MarkerFaceColor', 'b');
% Dummy plots
h4 = plot(nan,nan, 'k>');
h5 = plot(nan,nan, "Marker",'none', 'LineStyle','none', 'Color', 'none');
% Plot the first group with unfilled markers
h1u = scatter(x, y2, 'o', 'MarkerFaceColor', 'none');
h2u = scatter(x, y2, '^', 'MarkerFaceColor', 'none');
h3u = scatter(x, y2, 'x', 'MarkerFaceColor', 'none');
% Dummy plots
h4u = plot(nan,nan, "Marker",'none', 'LineStyle','none', 'Color', 'none');
h5u = plot(nan,nan, 'k>');
lgd = legend([h1 h2 h3 h4 h5 h1u h2u h3u h4u h5u], {'', '', '','','', 'G1', 'G2', 'G3','Apples', 'Oranges'}, 'NumColumns', 2);
To learn more, please go through this official MATLAB Documentation of ‘legend’ function and ‘IconColoumnWidth.
Hope this helps
Thanks
  1 Comment
dpb
dpb on 7 Oct 2024
Edited: dpb on 7 Oct 2024
This is identically the same as mine other than noting there is a new property available in legend that I was unaware of...that's a good catch; for other reasons I've stayed with R2021b and hadn't investigated the update notes recently.
Unfortunately, 'IconColumnWidth' is only a single global value and so doesn't really allow the customization that would be desireable here of shortening the gap between the two columns; setting the column width to 50% of the default width still leaves a sizable gap where the empty string label would go; the size of the two columns is the same. What one needs is an array of widths so each can be set individually.

Sign in to comment.

Products


Release

R2024a

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!