Generating dynamic legend without duplicates

6 次查看(过去 30 天)
So, I have a number of datasets stored in two row vectors each, the first storing x-values and the second y-values of a number of points. At a particular point, where the x-value exceeds a certain value, I split both vectors in two, generating two smaller sub-datasets. Each of these two are then fitted with a logarithmic function and plotted. Both of these plots are supposed to share legend labels, color scheme and marker scheme. This process is then repeated multiple times. (Current code is a WIP, finished code is supposed to loop, code is blocked for demonstration purposes only.) To do this, I have attempted to use a solution like this one here. My issue is that using this code I have been unable to find a way to hide duplicated legends. I feel like I have not fully grasped the function of legend(gca,'off') and I am not confident enough in my MATLAB knowledge to know whether using legend('-DynamicLegend'); would be smart to use in this case.
I have included a demo of my code below:
% Clear old vars before run
clear
clc
% myPalette8 = []
myPalette16 = ["#2f4f4f" "#006400" "#bdb76b" "#4b0082" "#48d1cc" ...
"#ff0000" "#ffa500" "#ffff00" "#00ff00" "#00fa9a" "#0000ff" ...
"#d8bfd8" "#ff00ff" "#1e90ff" "#fa8072" "#ff1493"]
myPalette16 = 1x16 string array
Columns 1 through 13 "#2f4f4f" "#006400" "#bdb76b" "#4b0082" "#48d1cc" "#ff0000" "#ffa500" "#ffff00" "#00ff00" "#00fa9a" "#0000ff" "#d8bfd8" "#ff00ff" Columns 14 through 16 "#1e90ff" "#fa8072" "#ff1493"
myPalette24 = ["#2f4f4f" "#556b2f" "#800000" "#483d8b" "#008000" ...
"#9acd32" "#00008b" "#daa520" "#8b008b" "#ff0000" "#ffff00" ...
"#7cfc00" "#40e0d0" "#00ff7f" "#00bfff" "#0000ff" "#d8bfd8" ...
"#ff7f50" "#ff00ff" "#1e90ff" "#db7093" "#ff1493" "#ee82ee" ...
"#ffe4b5"]
myPalette24 = 1x24 string array
Columns 1 through 13 "#2f4f4f" "#556b2f" "#800000" "#483d8b" "#008000" "#9acd32" "#00008b" "#daa520" "#8b008b" "#ff0000" "#ffff00" "#7cfc00" "#40e0d0" Columns 14 through 24 "#00ff7f" "#00bfff" "#0000ff" "#d8bfd8" "#ff7f50" "#ff00ff" "#1e90ff" "#db7093" "#ff1493" "#ee82ee" "#ffe4b5"
myPalette36 = ["#696969" "#c0c0c0" "#556b2f" "#a0522d" "#228b22" ...
"#808000" "#483d8b" "#008080" "#4682b4" "#9acd32" "#00008b" ...
"#32cd32" "#daa520" "#8fbc8f" "#8b008b" "#b03060" "#ff0000" ...
"#00ced1" "#ff8c00" "#7fff00" "#9400d3" "#00fa9a" "#dc143c" ...
"#0000ff" "#ff00ff" "#1e90ff" "#f0e68c" "#fa8072" "#ffff54" ...
"#dda0dd" "#ff1493" "#7b68ee" "#ee82ee" "#87cefa" "#7fffd4" ...
"#ffb6c1"]
myPalette36 = 1x36 string array
Columns 1 through 13 "#696969" "#c0c0c0" "#556b2f" "#a0522d" "#228b22" "#808000" "#483d8b" "#008080" "#4682b4" "#9acd32" "#00008b" "#32cd32" "#daa520" Columns 14 through 26 "#8fbc8f" "#8b008b" "#b03060" "#ff0000" "#00ced1" "#ff8c00" "#7fff00" "#9400d3" "#00fa9a" "#dc143c" "#0000ff" "#ff00ff" "#1e90ff" Columns 27 through 36 "#f0e68c" "#fa8072" "#ffff54" "#dda0dd" "#ff1493" "#7b68ee" "#ee82ee" "#87cefa" "#7fffd4" "#ffb6c1"
mySelectedPalette = myPalette24
mySelectedPalette = 1x24 string array
Columns 1 through 13 "#2f4f4f" "#556b2f" "#800000" "#483d8b" "#008000" "#9acd32" "#00008b" "#daa520" "#8b008b" "#ff0000" "#ffff00" "#7cfc00" "#40e0d0" Columns 14 through 24 "#00ff7f" "#00bfff" "#0000ff" "#d8bfd8" "#ff7f50" "#ff00ff" "#1e90ff" "#db7093" "#ff1493" "#ee82ee" "#ffe4b5"
hold all
% Code Block 1
% Provide Data
FirstDataUnits = [1 11 20 49 67 86 101 104 108 111 115 119 123 127 ...
132 137 142 147 152 158 164 170 177 183 190 197 205 212 220 ...
228 236 244 253 262 270 279 288 297 306]
FirstDataUnits = 1×39
1 11 20 49 67 86 101 104 108 111 115 119 123 127 132 137 142 147 152 158 164 170 177 183 190 197 205 212 220 228
<mw-icon class=""></mw-icon>
<mw-icon class=""></mw-icon>
FirstDataValue = [179 181 182 183 185 186 187 189 190 191 192 194 ...
195 196 198 199 200 202 203 204 205 207 208 209 211 212 213 ...
215 216 217 218 220 221 222 224 225 226 228 229]
FirstDataValue = 1×39
179 181 182 183 185 186 187 189 190 191 192 194 195 196 198 199 200 202 203 204 205 207 208 209 211 212 213 215 216 217
<mw-icon class=""></mw-icon>
<mw-icon class=""></mw-icon>
% Split input data into a section below trade excess threshold and one
% above the threshold
excess = 100
excess = 100
firstIndexOverExcess = find(FirstDataUnits>excess,1,'first')
firstIndexOverExcess = 7
% trimdata trims first values, latter part the end values
% Two row vectors are created and fed into a cell array
FirstDataUnitsSplit = {trimdata(FirstDataUnits,firstIndexOverExcess-1), FirstDataUnits(firstIndexOverExcess:end)}
FirstDataUnitsSplit = 1x2 cell array
{[1 11 20 49 67 86]} {1x33 double}
% trimdata trims first values, creating two row vectors for unit cost
FirstDataValueSplit = {trimdata(FirstDataValue,firstIndexOverExcess-1), FirstDataValue(firstIndexOverExcess:end)}
FirstDataValueSplit = 1x2 cell array
{[179 181 182 183 185 186]} {1x33 double}
for i = 1:2
% Plot both parts
DataFitOne = fit(transpose(FirstDataUnitsSplit{1,i}), transpose(FirstDataValueSplit{1,i}),'log')
DataPlotOne = plot(DataFitOne, FirstDataUnitsSplit{1,i}, FirstDataValueSplit{1,i})
% Optional: Plot confidence interval
%plot(heavyMachChicOpen300Units{1,i},predint(heavyMachChicOpen300Fit,heavyMachChicOpen300Units{1,i},0.95,'functional','on'),'m--')
DataPlotOne(1).Color = mySelectedPalette(9); % sth
DataPlotOne(1).Marker = '*'; % circle
DataPlotOne(2).Color = mySelectedPalette(10); % sth
legend(DataPlotOne, 'Data Points One', 'Fit Function One')
end
DataFitOne =
Linear model Log: DataFitOne(x) = a*log(x) + b Coefficients (with 95% confidence bounds): a = 1.455 (0.6779, 2.231) b = 178.3 (175.7, 180.9)
DataPlotOne =
2x1 Line array: Line (Data) Line (Fitted curve)
DataFitOne =
Linear model Log: DataFitOne(x) = a*log(x) + b Coefficients (with 95% confidence bounds): a = 36.71 (36.28, 37.13) b = 18.2 (15.98, 20.42)
DataPlotOne =
2x1 Line array: Line (Data) Line (Fitted curve)
% Code Block 2
% Provide Data
SecondDataUnits = [1 101 230 307 323 341 360 381 404 429 457 ...
487 520 556 594 636 682 730 781 836 893 952 1014 1078 1142 1209 ...
1277 1345 1414 1483]
SecondDataUnits = 1×30
1 101 230 307 323 341 360 381 404 429 457 487 520 556 594 636 682 730 781 836 893 952 1014 1078 1142 1209 1277 1345 1414 1483
<mw-icon class=""></mw-icon>
<mw-icon class=""></mw-icon>
SecondDataValue = [125 126 127 129 130 131 133 134 135 137 ...
138 139 140 142 143 144 146 147 148 150 151 152 153 155 156 157 ...
159 160 161 163]
SecondDataValue = 1×30
125 126 127 129 130 131 133 134 135 137 138 139 140 142 143 144 146 147 148 150 151 152 153 155 156 157 159 160 161 163
<mw-icon class=""></mw-icon>
<mw-icon class=""></mw-icon>
% Split input data into a section below trade excess threshold and one
% above the threshold
excess = 300
excess = 300
firstIndexOverExcess = find(SecondDataUnits>excess,1,'first')
firstIndexOverExcess = 4
% trimdata trims first values, latter part the end values
% Two row vectors are created and fed into a cell array
SecondDataUnitsSplit = {trimdata(SecondDataUnits,firstIndexOverExcess-1), SecondDataUnits(firstIndexOverExcess:end)}
SecondDataUnitsSplit = 1x2 cell array
{[1 101 230]} {1x27 double}
% trimdata trims first values, creating two row vectors for unit cost
SecondDataValueSplit = {trimdata(SecondDataValue,firstIndexOverExcess-1), SecondDataValue(firstIndexOverExcess:end)}
SecondDataValueSplit = 1x2 cell array
{[125 126 127]} {1x27 double}
for i = 1:2
% Plot both parts
DataFitTwo = fit(transpose(SecondDataUnitsSplit{1,i}), transpose(SecondDataValueSplit{1,i}),'log')
DataPlotTwo = plot(DataFitTwo, SecondDataUnitsSplit{1,i}, SecondDataValueSplit{1,i})
% Optional: Plot confidence interval
%plot(heavyMachChicOpen300Units{1,i},predint(heavyMachChicOpen300Fit,heavyMachChicOpen300Units{1,i},0.95,'functional','on'),'m--')
DataPlotTwo(1).Color = mySelectedPalette(11); % sth
DataPlotTwo(1).Marker = '*'; % circle
DataPlotTwo(2).Color = mySelectedPalette(12); % sth
legend(DataPlotTwo, 'Data Points Two', 'Fit Function Two')
end
DataFitTwo =
Linear model Log: DataFitTwo(x) = a*log(x) + b Coefficients (with 95% confidence bounds): a = 0.3165 (-1.302, 1.935) b = 124.9 (118.3, 131.6)
DataPlotTwo =
2x1 Line array: Line (Data) Line (Fitted curve)
DataFitTwo =
Linear model Log: DataFitTwo(x) = a*log(x) + b Coefficients (with 95% confidence bounds): a = 20.59 (20.2, 20.98) b = 11.38 (8.822, 13.94)
DataPlotTwo =
2x1 Line array: Line (Data) Line (Fitted curve)
% [MORE CODE BLOCKS LIKE ABOVE]
% legend(gca, 'off') is paired with the line directly below it.
% Essentially it turns the legend off (the line below turns it back on),
% which forces Matlab to refresh and display new legend changes.
legend(gca,'off');
legend('show');

回答(1 个)

Matt J
Matt J 2025-4-27
编辑:Matt J 2025-4-27
One way:
load Inputs
mySelectedPalette = myPalette24;
% Code Block 1
% Split input data into a section below trade excess threshold and one
% above the threshold
excess = 100;
addLines(FirstDataUnits,FirstDataValue,excess, mySelectedPalette(9:10), ...
'Data Points One', 'Fit Function One');
% Code Block 2
excess = 300;
addLines(SecondDataUnits,SecondDataValue,excess, mySelectedPalette(11:12), ...
'Data Points Two', 'Fit Function Two');
legend(gca,'off');
legend('show');
function addLines(DataUnits,DataValue,excess, mySelectedPalette, varargin)
firstIndexOverExcess = find(DataUnits>excess,1,'first');
% trimdata trims first values, latter part the end values
% Two row vectors are created and fed into a cell array
DataUnitsSplit = {trimdata(DataUnits,firstIndexOverExcess-1), DataUnits(firstIndexOverExcess:end)};
% trimdata trims first values, creating two row vectors for unit cost
DataValueSplit = {trimdata(DataValue,firstIndexOverExcess-1), DataValue(firstIndexOverExcess:end)};
hold on
for i = 1:2
% Plot both parts
DataFit = fit(transpose(DataUnitsSplit{1,i}), transpose(DataValueSplit{1,i}),'log');
DataPlot = plot(DataFit, DataUnitsSplit{1,i}, DataValueSplit{1,i});
% Optional: Plot confidence interval
%plot(heavyMachChicOpen300Units{1,i},predint(heavyMachChicOpen300Fit,heavyMachChicOpen300Units{1,i},0.95,'functional','on'),'m--')
DataPlot(1).Color = mySelectedPalette(1); % sth
DataPlot(1).Marker = '*'; % circle
DataPlot(2).Color = mySelectedPalette(2); % sth
[DataPlot.DisplayName] = deal(varargin{:}) ;
if i>1
DataPlot(1).Annotation.LegendInformation.IconDisplayStyle = 'off'; % Hides from legend
DataPlot(2).Annotation.LegendInformation.IconDisplayStyle = 'off'; % Hides from legend
end
end
hold off
end

类别

Help CenterFile Exchange 中查找有关 2-D and 3-D Plots 的更多信息

产品


版本

R2024a

Community Treasure Hunt

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

Start Hunting!

Translated by