添加链接
link之家
链接快照平台
  • 输入网页链接,自动生成快照
  • 标签化管理网页链接
MATLAB | 如何按照任意比例调整颜色条(colorbar)

MATLAB | 如何按照任意比例调整颜色条(colorbar)

之前写过的setPivot函数只能把颜色条的中点放到0处或者其他数值处:

这次提供的函数可以将任意百分比的点位放置在任意数值处,这个函数大概长这样:

百分比点位设置

function setCMapRatio(varargin)
% @author:slandarer
if nargin==2
    ax=gca;
    oriRatio=sort(varargin{1});
    breakPnt=sort(varargin{2});
elseif nargin==3
    ax=varargin{1};
    oriRatio=sort(varargin{2});
    breakPnt=sort(varargin{3});
% 原始数据处理
CLimit=get(ax,'CLim');
breakPnt=[CLimit(1),breakPnt,CLimit(2)];
newRatio=diff(breakPnt);
oriCMap=colormap(ax);
CLen=size(oriCMap,1);
newRatio=newRatio./diff([0,oriRatio,1]);
newRatio=round(newRatio./max(newRatio).*400);
oriRatio=[oriRatio,1];
% 最开始部分颜色条构造
tempCMap=oriCMap(1:ceil(oriRatio(1).*CLen),:);
CInd2=kron((1:size(tempCMap,1)-1)',ones(newRatio(1),1));
newCMap=tempCMap(CInd2,:);
CInd3=oriRatio(1).*CLen-size(tempCMap,1)+1;
CInd3=round(CInd3.*newRatio(1));
newCMap=[newCMap;repmat(tempCMap(end,:),[CInd3,1])];
% 循环添加新的颜色
for i=2:length(oriRatio)
    CInd1=round(newRatio(i).*(ceil(oriRatio(i-1).*CLen)-oriRatio(i-1).*CLen));
    if abs(ceil(oriRatio(i).*CLen)-oriRatio(i).*CLen)>0
        CInd2=ceil(oriRatio(i-1).*CLen)+1:ceil(oriRatio(i).*CLen)-1;
        CInd2=ceil(oriRatio(i-1).*CLen)+1:ceil(oriRatio(i).*CLen);
    CInd2=kron(CInd2',ones(newRatio(i),1));
    CInd3=round(newRatio(i).*(oriRatio(i).*CLen-floor(oriRatio(i).*CLen)));
    if ceil(oriRatio(i).*CLen)==ceil(oriRatio(i-1).*CLen)
        CInd1=[];
        CInd3=round(newRatio(i).*(oriRatio(i).*CLen-oriRatio(i-1).*CLen));
    newCMap=[newCMap;
        repmat(oriCMap(ceil(oriRatio(i-1).*CLen),:),[CInd1,1]);
        oriCMap(CInd2,:);
        repmat(oriCMap(ceil(oriRatio(i).*CLen),:),[CInd3,1])];
colormap(ax,newCMap);
end

咋使用呢,假设编写了如下代码:

contourf(rand(10,10))
colormap([pink(11);flipud(bone(11))])
cb=colorbar;

画出图来长这样:

这里总共有22种颜色,假如我想让36%的颜色,即第8第9种颜色的分界线放到0.2处,第10第11种颜色分界处放到0.5处,第20第21种颜色分界线放到0.8处,可以编写如下代码:

contourf(rand(10,10))
colormap([pink(11);flipud(bone(11))])
cb=colorbar;
setCMapRatio([8/22,10/22,20/22],[.2,.5,.8])

当然不一定非得8/22这种格式,随便0-1内的数值均可,比如8.12/22,0.123啥的。


非等距标签添加

若是想在colorbar每个颜色交界处加入刻度,但是修改比例后颜色不等距不太容易用linspace获取颜色交界处咋办?写了个简单的函数:

function cbTick=getCBTick(ax)
% @author:slandarer
if nargin<1,ax=gca;end
CMap=colormap(ax);
[~,Cind,~]=unique(CMap,'rows');
Cind=sort(Cind);
Cind=Cind(2:end)-1;
CLimit=get(ax,'CLim');
N=size(CMap,1);
Cind=Cind./N;
cbTick=[CLimit(1);CLimit(1)+(CLimit(2)-CLimit(1)).*Cind;CLimit(2)];
end

还是之前的例子用一下:

contourf(rand(10,10))
colormap([pink(11);flipud(bone(11))])
cb=colorbar;
setCMapRatio([8/22,10/22,20/22],[.2,.5,.8])
% 添加非等距离标签
cb.YTick=getCBTick(gca);
% 调节colorbar刻度长度(这句代码可删掉)
cb.TickLength=.061;

其他实例

再给个例子叭:

imagesc(peaks(1000)+1)
% 随便构造一个colormap
CM=[0.1874    0.0771    0.2162
    0.2881    0.0832    0.3962
    0.3604    0.2090    0.6047
    0.3734    0.3827    0.7065
    0.4129    0.5397    0.7472
    0.5390    0.6785    0.7712
    0.7421    0.7976    0.8227
    0.8856    0.8499    0.8857
    0.8391    0.7587    0.7108
    0.7905    0.5986    0.4866
    0.7382    0.4192    0.3485
    0.6433    0.2587    0.3124
    0.4974    0.1354    0.3141
    0.3126    0.0789    0.2669
    0.1849    0.0794    0.2131];
colormap(CM)