# Conditional Colormap and colorbar for scatter plot.

92 views (last 30 days)
Sean Freedman on 3 Nov 2020
Commented: Dave B on 26 Jan 2021
Hi,
I am trying to create a colormap that has a lineraly spaced color gradient between two limits. Passed these two limits I would like to use a greyscale gradiant using min and max values as the end point.
Hopefully this diagram can explain better Dave B on 4 Nov 2020
Hi Sean -
I think what you're describing in your diagram is:
• Values between -100 and -5.1 range from black to light gray.
• Values from -5 to -2.5 range from red to yellow
• etc.
Let's start by defining the colors that you're going to interpolate between as RGBs:
clr=nan(9,3);
clr(1,:) = [0 0 0]; % black
clr(2,:) = [.7 .7 .7]; % gray
clr(3,:) = [1 0 0]; % red
clr(4,:) = [1 1 0]; % yellow
clr(5,:) = [0 1 0]; % green
clr(6,:) = [1 1 0]; % yellow
clr(7,:) = [1 0 0]; % red
clr(8,:) = [.7 .7 .7]; % gray
clr(9,:) = [0 0 0]; % black
As a reality check, we should just look at these colors:
figure(1);
imagesc(1:9)
colormap(clr) Now, we need to interpolate across the colors. We can do that separately for each of the 3 RGB values, but note that there are many ways you might want to traverse the color wheel! For the example you provided, I think linear for each channel works pretty nicely.
% Use the values you specified to feed into the interpolant:
cval=[-100 -5.1 -5 -2.5 0 2.5 5 5.1 100];
We can make a colormap with any number of colors, let's do one with 256 colors:
ncolors=256;
Now the interpolation bit. We'll make a variable ci that says where we want the interpolated colors to be. It ranges from min(cval) to max(cval) and has ncolors colors:
ci=linspace(cval(1),cval(end),ncolors);
Now just interpolate separately for each color:
ri=interp1(cval,clr(:,1),ci); % reds
gi=interp1(cval,clr(:,2),ci); % greens
bi=interp1(cval,clr(:,3),ci); % blues
We might as well see that these look like what we'd expect:
imagesc(linspace(0,1,1000));
colormap(my_colormap); This seems correct (though note that I've got an arbitrary x axis here that just has 1000 values), if I interpreted your diagram correctly: a large span of grays with r/y/g colors in the middle.
You mentioned scatter, here's what that might looks like in practice:
x=rand(1000,1);
y=rand(1000,1);
c=rand(1000,1)*200-100; % setting c to range from about -100 to 100:
scatter(x,y,30,c,'filled');
colormap(my_colormap);
set(gca,'CLim',[-100 100])
colorbar; Setting CLim here is crucial, that ensures the colormap (which works with an arbitrary range) is applied to the range we used to interpolate. Values less than -100 or greater than 100 will be black.
Dave B on 26 Jan 2021
Oops, I must have skipped a step! Looking back on this code, it looks like I should have included:
my_colormap=[ri(:) gi(:) bi(:)];