sam_rox
sam_rox

Reputation: 747

plotting a surface plot in two colours depending on condition on z axis

z is 200*200 array and I have a surf plot using Matlab surf(x,y,z). I am trying to plot the surf plot so that when z<10 it will be blue and when z>10 it will be red. At the moment the surf plot is like this. Can someone please suggest a way to do this in Matlab?

enter image description here

Upvotes: 0

Views: 784

Answers (3)

Hoki
Hoki

Reputation: 11812

One way to achieve that (there are several ways) is to use a custom colormap: Build a colormap with only the color you want to appear in your graph, then just adjust the levels so the midpoint is for Z=10.

The first part of the code shows how to create your custom colormap and apply it:

Zt = 10 ;       % threshold level for Z
z  = peaks+Zt ; % dummy test data

% build a colormap with your 2 custom color
%     [%Red %green %blue]
cmap = [0.79 0.22 0.81   ; % some kind of purple
        0    0    1    ] ; % pure blue

surf(z) ;           % plot the surface
colormap(cmap) ;    % apply the custom colormap
hcb = colorbar ;

This produces a surface with your two chosen colors: 2 color surface

But wait! The separation is not exactly at the Z=10 level. No problem, if we adjust the boundaries of the colormap so your threshold level is bang in the middle, Matlab will take care of adjusting the coloring for us:

%% Now center the colormap boundaries around your threshold level
% get the minimum and maximum
zmax = ceil(  max(max(z)) ) ;
zmin = floor( min(min(z)) ) ;

span = max( [zmax-Zt, Zt-zmin] ) ;  % calculate the span each side of [Zt]
caxis([Zt-span , Zt+span]) ;        % center the colormap around [Zt]

Threshold adjusted

The last bit of code above allow to define an equal span around your chosen threshold level and take the content of the Z data into account. If you know in advance the limits of your data you don't need to do the calculations. On the example above I could also have simply use the last line with some hard coded values:

caxis([0 , 20]) ;

As long as the interval you specify for caxis is centered around your threshold level it will work.


Edit:

To control the labels of the colorbar, I usually set the Ticks and TickLabels after the colorbar (or axes) is created. For this you need the handle of the colorbar object.

Note that in the code above I modified the last line of the first code block. I changed colorbar, to hcb=colorbar;. This way we have the handle of the colorbar, which allow us to set any arbitrary tick and associated label.

The most straightforward way to get your result for this specific example is:

hcb.Ticks      = [   5 , 10 , 15  ] ;
hcb.TickLabels = {'<10','10','>10'} ;

However if you want a more generic solution which can work with any threshold Zt then you can use:

%% adjust colorbar labels
zl = caxis ;            % get the limits of the color scale
Zstr = num2str(Zt) ;    % get a string representing the threshold
hcb.Ticks      = [ (Zt+zl(1))/2 , Zt   , (zl(2)+Zt)/2  ] ;
hcb.TickLabels = { ['<' Zstr]   , Zstr ,  ['>' Zstr]   } ;

For your example, both options produce:

Final image

Upvotes: 3

Atif
Atif

Reputation: 401

try this

surf(x,y,z)
map = [0.0 0.0 1.0
       1.0 0.0 0.0];
colormap(map);
caxis([0 20]);

Upvotes: 0

Thales
Thales

Reputation: 1316

Adapted from MATLAB Answers

z = peaks+10; % sample data generated between 3.4 and 18.1
% Make colors be red above 10, and blue below 10.
redChannel = z > 10;
greenChannel = 0*z;
blueChannel = z < 10;
% Make the RGB image.
colors = double(cat(3, redChannel, greenChannel, blueChannel));
% Plot the surface with those colors.
surf(z, colors);

Upvotes: 1

Related Questions