最近有一项工作需要用到大规模影像,镶嵌成一版图,后期需要用到匀光匀色,由于需要集成到代码库中,所以只能自己实现了。重点参考了论文-《
崔浩, 张力, 艾海滨,等. 利用基准色调的大范围卫星影像色彩一致性处理算法[J]. 测绘学报, 2017, v.46(12):62-73.》,感谢作者的建议,在此再次表示感谢。不多说了,
在具体实现的时候,我将所有uint16位影像,全部转为uint8位,采用线性拉伸的方式:
clear tic fprintf(' ... Read Imagery ... ...\n'); [Img, R] = geotiffread('LongQuanYi_2020_FirstSeason.tif'); info = geotiffinfo('LongQuanYi_2020_FirstSeason.tif'); % Img = uint16(Img*10000); per = 0.01; % 线性拉伸比例 backValue = 0; % 背景像素值 % 这里默认输入图像为单通道 [ylen, xlen, channel] = size(Img); for i = 1:channel img = Img(:,:,i); fprintf(' ... Img Xlen: %d pixels\n', xlen); fprintf(' ... Img Ylen: %d pixels\n\n\n', ylen); % 线性拉伸 max_val = max(img(:)); min_val = min(img(:)); if min_val == backValue min_val = backValue + 1; % 背景值不能当最小值 end fprintf(' ... ... ... ... ... ... ... ... ... ...\n'); fprintf(' ... Min Val is %d \n', min_val); fprintf(' ... Max Val is %d \n', max_val); fprintf(' ... ... ... ... ... ... ... ... ... ...\n\n'); % 统计直方图 % 输入图像为16位,取值范围为 0 到 65535 bins = 1:65535; % 背景值不要参与统计 histcount = histcounts(img(:)', bins); %清除临时变量 clear bins max_val min_val; % 直方图裁剪,计算左值和右值 [l_val, r_val] = calc_lr_val(histcount, xlen*ylen, per); % 根据左值和右值,将图像由16位映射至8位 img_8bit = img_map(img, l_val, r_val); Img(:,:,i) = img_8bit; end %% 真彩色影像组合 Img = cat(3,Img(:,:,3),Img(:,:,2),Img(:,:,1)); % 保存结果 geotiffwrite('LongQuanYi_2020_FirstSeason_uint8.tif', uint8(Img), R, 'GeoKeyDirectoryTag', ... info.GeoTIFFTags.GeoKeyDirectoryTag); toc
完了后,采用原论文中的方法,进行匀光匀色,这个方法主要是依据参考影像底图进行处理,我用的100米分辨率google底图,与目前很多匀光匀色软件一致,比如colormap等等,但是
,个人看法是,这些商业软件吹嘘成分过多,看结果吧:
再看一下细节部分:
整个算法的计算效率还是非常高的,但是有一点需要改进的就是,细节部分还需要优化,行吧,就写到这里,随意了。如需代码,QQ:1044625113,备注:匀光匀色!