Create black line on colorbar to mark specific value

15 visualizzazioni (ultimi 30 giorni)
Hi again.
I have been working on a GUI that creates a contour depending on certain slider values.
I have elevated a specific isoline in the contour by marking it black.
Is it possible to elevate the corresponding position on the colorbar? I have uploaded two images. The first one shows the contour as it is, the second one shows it as I would like it to be, with the colorbar elevation added manually by hand:
Here is the code for my contour (p_nb is the value of the elevated isoline):
contour(handles.SKosten,x1,x1,p_sk,'LevelStep',2,'Fill','on')
hold on
contour(handles.SKosten,x1,x1,p_sk, [p_nb p_nb], 'Color','k','LineWidth',1.45)
And here's the code for the colormap:
b = [.091 .153 0;...
.114 .159 0;...
.137 .166 .001;...
.160 .172 .001;...
.184 .178 .001;...
.207 .184 .001;...
.230 .191 .002;...
.253 .197 .002;...
.253 .181 .003;...
.253 .166 .005;...
.253 .150 .006;...
.254 .134 .007;...
.254 .118 .008;...
.254 .103 .010;...
.254 .087 .011];
b = b*1000;
b = b/255;
caxis([20 50]);
cmp = colormap(b);
cbr = colorbar;
set(cbr,'YTick',20:2:50,'FontSize',9)
b actually changes with a switch (depending on the value of p_nb), so that the inside of the elevated isoline is always green and the outside always yellow/red. I think it would be too much to post the whole thing here, but knowing that could be relevant..
Thanks in advance!
Marc

Risposta accettata

Sean de Wolski
Sean de Wolski il 9 Set 2013
Modificato: Sean de Wolski il 9 Set 2013
Good Monday morning brain stimulator!
% Level we care about
level = 0;
% Plot and store colorbar handles
contourf(peaks,-3:3);
hCbar = colorbar;
% Add line to colorbar
line('parent',hCbar,'xdata',[-5 5],...
'ydata',[level level],'color','k','LineWidth',3)
% Note you'll have to swap x/ydata for a horizontal colorbar
% Plot a second contour plot with just the level we care about. Make it
% transparent with a nice thick line
hold on
[~,hCont] = contourf(peaks,[level level]); %contour handles
set(allchild(hCont),'FaceAlpha',0,...
'LineWidth',3,'EdgeColor','k'); %children are patches
  4 Commenti
Dennis
Dennis il 24 Nov 2016
Modificato: Dennis il 24 Nov 2016
Here's one way to plot a line over the colorbar starting from R2014b:
level = 0.45;
h_colorbar = colorbar;
h_axes = axes('position', h_colorbar.Position, 'ylim', h_colorbar.Limits, 'color', 'none', 'visible','off');
line(h_axes.XLim, level*[1 1], 'color', 'white', 'parent', h_axes);
Ryan Stanyard
Ryan Stanyard il 7 Giu 2020
This works beautifully, but when I maximise the figure, the lines are both too elongated and distal from the colorbar. Any thoughts?
I.E.
Versus default (non-maximised)

Accedi per commentare.

Più risposte (2)

Adam Stooke
Adam Stooke il 23 Ott 2015
Somewhere around R2014, colorbar is no longer an axes object. Oi. So my first thought was to pull the colorbar inside the axes, where we can draw another line over it anyway. But the colorbar 'position' property gives the location in terms of figure units--hardly helpful for locating a line over it. Instead, here is some code that manually creates a colorbar within an axes object, using patches.
This setup locates the colorbar using the plot values, so if your axes need to change limits during an animation, this won't work. I guess in that scenario we could create a separate axes object to contain this colorbar.
% colorbar code test.
figure;
axes;
%
% Set up the axes size.
axLim = 1;
axMaxX = 1.2*axLim;
xlim([-axLim,axMaxX])
ylim([-axLim,axLim])
%
% Define the colormap
colormap jet
colorLim = 20;
caxis([-colorLim, colorLim])
nColors = 30;
%
% Get colormap plotting data ready.
% Making these in units of whatever values are plotted on the axes,
% hopefully this doesn't need to change for you (or for me later)!
cbarWidth = axLim*0.1;
cbarHeight = axLim*0.9; % actually half height
cbarLeft = axMaxX-3*cbarWidth;
cbarRight = cbarLeft + cbarWidth;
cbarX = [cbarLeft,cbarRight,cbarRight,cbarLeft];
cbarSeg = cbarHeight*2/nColors;
cbarY = [-cbarSeg,-cbarSeg,0,0] - cbarHeight;
cDataList = linspace(-colorLim,colorLim,nColors);
%
% Create a patch to make the border around the bar.
patch(cbarX,cbarHeight*[-1,-1,1,1],[1,1,1],'linewidth',3)
%
% Create each of the patches in the colorbar.
for iColor = 1:nColors
patch(cbarX,cbarY+iColor*cbarSeg,cDataList(iColor),'edgecolor','none')
end
%
% Put some kind of label on it.
text('String','\leftarrow Label \rightarrow ',...
'Position',[axMaxX-cbarWidth, 0],'HorizontalAlignment','center',...
'Rotation',90,'fontsize',14)
%
% Draw the line on it.
h_line_cbar = line([cbarLeft,cbarRight],[0,0],'color','k','linewidth',4);
%
% Move the line around.
lineHeights = sin(2*pi*(1:100)/50)*cbarHeight;
for i = 1:numel(lineHeights)
set(h_line_cbar,'ydata',[lineHeights(i),lineHeights(i)])
pause(0.05)
end
  2 Commenti
Marc Jakobi
Marc Jakobi il 7 Nov 2015
Hey, Adam. Thanks for the update! I will most likely need this info again, one day :)
Phil
Phil il 13 Ago 2021
Thanks so much! This is super helpful!

Accedi per commentare.


Moreno, M.
Moreno, M. il 31 Ago 2024
My workaround to this problem is to create a second figure for the colorbar. I would then either interpolate a colored region in the new colorbar, or find the closest element to my desired band and color it as desired. The simplest implementation of this approach would replace the colormap values inside of the band by the desired color. Here is my suggestion:
% Create dummy data
figure
tiledlayout(1,100)
nexttile([1,99]);
hold on
contourf(peaks,10,'EdgeColor','none')
contour3(peaks,[5,5],'k')
% Color a specific band in 'val'
val = 5;
lim = caxis;
col = parula(200);
idx = lim(1):(lim(2)-lim(1))/199:lim(2);
[~,idx] = min(abs(idx-val));
col(idx,:) = 0;
% Plot colorbar
nexttile([1,1])
colormap(col)
colorbar
axis off

Categorie

Scopri di più su Color and Styling in Help Center e File Exchange

Community Treasure Hunt

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

Start Hunting!

Translated by