applying fill colors to a grid based on threshold value?

10 visualizaciones (últimos 30 días)
Dan Siegal
Dan Siegal el 1 de Feb. de 2021
Comentada: Dan Siegal el 2 de Feb. de 2021
Hi Community
I've got a question about how to set the fill colors on a grid generated with surface() (or something similar).
For background, I've generated a temperature profile image using contourf() and overlaid a grid over top of it like so:
[X,Y]=meshgrid(xrange,yrange);
hold on;
plot(X,Y,'k');
plot(Y,X,'k');
(See attached figure.) Now I was hoping to generate another figure with the same grid, but with the squares filled with a color based on some threshold--i.e., if the temperature is above threshold in a grid region, fill color is red, and if temperature is below, the fill color is green. I'm not really sure how to do this, although some internet sleuthing pointed me to surface():
surface(X,Y,foo);
To test this I generated a figure with 'foo' as a binary matrix ( randi([0 1],length(X)) ) and I can get some fill colors. The problem is I don't know how to specify RGB colors in that matrix.
I suspect there's an easy solution to this and I'm just too new to MATLAB...
Thanks for the help!

Respuesta aceptada

Adam Danz
Adam Danz el 1 de Feb. de 2021
Editada: Adam Danz el 2 de Feb. de 2021
I understand that you want to create a contour map with two levels of color to show values above and below a threshold within a grid.
The trickiest part is setting up the colorbar to show where the binary levels change at the threshold point.
This demo includes the original contour plot (subplot 1), a binary contour plot prior to applying the grid (subplot 2) and the gridded "contour" produced with imagesc() and the underlying contour lines for comparison.
See inline comments for details.
Generate basic contour plot
% Generate data
[X,Y,Z] = peaks(40);
X = (X-min(X(:)))/range(X(:))*24;
Y = (Y-min(Y(:)))/range(Y(:))*24;
% Create basic contour plot
figure()
contourf(X,Y,Z);
axis equal
set(gca,'xtick',0:2:24, 'ytick', 0:2:24)
grid on
colormap('jet')
colorbar()
cm = get(gca,'Colormap');
title('Original contour')
Replicate the contour plot with binary color scale
% Plot altered ZData
figure()
contourf(X,Y,Z);
axis equal
set(gca,'xtick',0:2:24, 'ytick', 0:2:24)
grid on
title('Bi-level contour')
% Define where colorbar changes based on the ZData (temperature)
zThreshold = 2.0;
% Create binary colorbar that changes at threshold
cbIncr = round(range(caxis)/100,1,'significant');
cbRng = [min(Z(:)), max(Z(:))];
cbSegments = unique([(zThreshold : -cbIncr : cbRng(1)),(zThreshold : cbIncr : cbRng(2))]);
cmap = [1 0 0] .* ones(numel(cbSegments)-1,1); % peak color
cmap(cbSegments<zThreshold,:) = [0 1 0] .*ones(sum(cbSegments<zThreshold),1); % trough color
colormap(gca,cmap)
cl = [min(cbSegments), max(cbSegments)];
caxis(cl)
cb = colorbar();
cb.Ticks = [min(cbSegments), zThreshold, max(cbSegments)];
Create grid and compute the mean z-value for each 2D bin
This mean can easily be replaced with the median, max, min, or whatever other statistic you want to use.
% Create bin edges
gridSpace = 2;
xg = min(X(:)) : gridSpace : max(X(:))+mod(max(X(:)), gridSpace);
yg = min(Y(:)) : gridSpace : max(Y(:))+mod(max(Y(:)), gridSpace);
% Identify the bin of each z-value
xbinID = discretize(X, xg);
ybinID = discretize(Y, yg);
% Average the values within bins
[~,~,groupID] = unique([xbinID(:),ybinID(:)],'rows','stable');
groupStats = groupsummary(Z(:), groupID, 'mean','IncludeEmptyGroups',true); % <--------- change statistic here
zdata = reshape(groupStats, numel(yg)-1, numel(xg)-1);
% Define where colorbar changes based on the ZData (temperature)
zThreshold = 2.0;
% Set zdata to high and low values based on threshold
zdata(zdata < zThreshold) = min(zdata(:));
zdata(zdata >= zThreshold) = max(zdata(:));
% Plot grided "contour"
figure()
imagesc(xg([1,end])+gridSpace./[2,-2], yg([1,end])+gridSpace./[2,-2], zdata)
axis equal
axis tight
set(gca,'xtick',0:2:24, 'ytick', 0:2:24,'ydir','normal')
colormap(gca,cmap) % See previous section for definition of cmap
caxis([min(cbSegments), max(cbSegments)])
cb = colorbar();
cb.Ticks = [min(cbSegments), zThreshold, max(cbSegments)];
caxis(cl) % see previous section for cl definition
title(sprintf('Grid means (%d unit grid)', gridSpace))
grid on
hold on
% Add grid lines; Note that this is unnecessary since the grid is on
xgridLines = [xg, repelem(xg(1),1,numel(yg)); xg, repelem(xg(end),1,numel(xg))];
ygridLines = [repelem(yg(1),1,numel(xg)), yg; repelem(yg(end),1,numel(xg)), yg];
plot(xgridLines, ygridLines, 'Color', [.2 .2 .2]);
% plot underlying contour for comparison
contour(X,Y,Z,'LineColor', 'k','LineStyle','--');
  9 comentarios
Adam Danz
Adam Danz el 2 de Feb. de 2021
Ahhh good, I see the transpose now.
Generally, the best practice to organize data known as Tidy Data is a matrix where columns are different variables and rows are samples of those variables:

Iniciar sesión para comentar.

Más respuestas (0)

Categorías

Más información sobre Surface and Mesh Plots en Help Center y File Exchange.

Community Treasure Hunt

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

Start Hunting!

Translated by