Plotting different colored line based on condition(s)
93 Ansichten (letzte 30 Tage)
Ältere Kommentare anzeigen
Nicholas Bragaia
am 6 Okt. 2020
Bearbeitet: Adam Danz
am 6 Okt. 2020
Hello: I am attempting to plot a line that changes colors (between red and green) based upon the value of the data. For example, if I have x=1:1:5 and corresponding y=[-2,-1,1,2,3], I would like the plot to have a red line when y is negative and a green line when y is positive and have a corresponding legend to denote this. P.S. my actual data series is much longer than (5) values so a looping code would be preferable.
0 Kommentare
Akzeptierte Antwort
Chad Greene
am 6 Okt. 2020
Bearbeitet: Chad Greene
am 6 Okt. 2020
What if you create two lines and plot them separately?
x = 0:1000;
y = sind(x);
% duplicate:
y_red = y;
y_red(y>0) = NaN;
y_green = y;
y_green(y<0) = NaN;
figure
plot(x,y_red,'r','linewidth',2)
hold on
plot(x,y_green,'g','linewidth',2)
2 Kommentare
Adam Danz
am 6 Okt. 2020
Bearbeitet: Adam Danz
am 6 Okt. 2020
This is the best method when the x values are already known at y=0. It's simple, effective, and quick. But if the x coordinates are not known when y=0, you'll need to compute them and insert them into the (x,y) vectors.
For example, try approach solution when x = 22:45:1080.
Weitere Antworten (1)
Adam Danz
am 6 Okt. 2020
Bearbeitet: Adam Danz
am 6 Okt. 2020
A line object can only have 1 color. To change the color of values above and below y=0 you have to break up your line into segments. This is relatively easy if you already have y-coordinates at (or very close to) zero and can be solved by simple logical indexing.
However if line segments pass through y=0 you must compute the x-coordinates where y equals 0 and insert those coordinates into your (x,y) vectors.
Here's a demo that steps through that process.
% Define coarse (x,y) coordinates that pass through y=0
x=1:1:15;
y=[-2,-1,1,2,3];
y = [y,fliplr(y),y];
% Plot the original data
figure()
plot(x,y,'b-o','LineWidth',2)
yline(0)
% Get the index of each coordinate just prior to passing y=0 (startSegIdx)
signDiff = [0,diff(sign(y(:)'))];
startSegIdx = unique([find(signDiff(:)'==2)-1, find(signDiff(:)'==-2)-1])
% For each segment that passes through y=0, compute equation
% of the line and solve for y=0
x0 = nan(size(startSegIdx));
for i = 1:numel(startSegIdx)
coeffs = polyfit(x(startSegIdx(i)+[0,1]), y(startSegIdx(i)+[0,1]), 1);
x0(i) = -coeffs(2)/coeffs(1);
end
% (x0,y0) are the y== crossing points. Add those points to the plot
% to check for accuracy
figure()
plot(x,y,'b-o','LineWidth',2)
yline(0)
hold on
plot(x0,zeros(size(x0)),'m*','MarkerSize', 12,'LineWidth',2)
% Insert the new (x0,y0) coordinates in the correct incides of (x,y)
repNum = ones(size(x));
repNum(startSegIdx) = 2;
xNew = repelem(x(:).',1,repNum(:)');
xNew(startSegIdx + (1:numel(startSegIdx))) = x0;
yNew = repelem(y(:).',1,repNum(:)');
yNew(startSegIdx + (1:numel(startSegIdx))) = 0;
% Plot the new line to make sure it matches the old one, plus the 0-crossings
figure()
plot(x,y,'b-o','LineWidth',2)
yline(0)
hold on
plot(x0,zeros(size(x0)),'m*','MarkerSize', 12,'LineWidth',2)
plot(xNew, yNew, 'r:o', 'LineWidth', 1, 'MarkerSize', 16)
% Break up the (xNew,yNew) line into segments below/above y=0
% There will be 1 segment for each time it crosses y=0
% 1. Duplicate values at x=0
segmentSub = unique(find(sign(yNew(:)')==0));
repNum2 = ones(size(xNew));
repNum2(segmentSub) = 2;
xSeg = repelem(xNew, 1, repNum2);
ySeg = repelem(yNew, 1, repNum2);
% create a grouping variable for each element of (xSeg, ySeg) that identifies its segment.
segmentSub2 = [segmentSub + (0:numel(segmentSub)-1), numel(xSeg)];
group = repelem(1:numel(segmentSub2),diff([0,segmentSub2]));
% Plot the line segments
figure()
hold on % important
h = splitapply(@(x,y)plot(x,y,'-o','LineWidth',1),xSeg,ySeg,group);
% Color segment based on the sign of y values
isPositive = arrayfun(@(h)any(h.YData > 0),h);
set(h(isPositive), 'Color', 'g')
set(h(~isPositive), 'Color', 'r')
% add ref line
yline(0)
0 Kommentare
Siehe auch
Kategorien
Mehr zu Annotations finden Sie in Help Center und File Exchange
Produkte
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!