
1. 热红外数据工程化处理的整体设计思路1.1 为什么需要工程化处理大疆行业级无人机挂载热红外相机如Zenmuse H20T、XT2、H30T等采集回来的原始数据默认输出的是RJPG格式。RJPG本质上是带温度信息的JPEG——它在标准JPEG的APP段里嵌入了R-JPEG私有数据块包含原始辐射值、发射率参数、环境温度、距离、湿度等元数据。直接用普通看图软件打开你看到的只是一张伪彩色图温度信息完全读不出来。很多人第一次接触RJPG会以为用Pix4D直接拖进去就能出温度正射影像。实测下来Pix4D对RJPG的支持是能读伪彩图但读不出绝对温度。也就是说你拿到的正射影像只有颜色没有温度值。要得到真正可用的温度正射影像每个像素对应一个摄氏度数值必须先把RJPG里的辐射数据解出来转成Pix4D能识别的带温度信息的TIFF再走空三和正射流程。这套工作流的核心价值在于把只能看的热红外图变成能算的温度数据。农业估产、建筑热损检测、光伏板热斑定位、电力巡检、地暖漏水排查这些场景要的不是一张好看的伪彩图而是能导出温度矩阵、能做阈值分析、能生成温度等值线的正射成果。1.2 整体流程拆解整个工作流我把它拆成四个阶段每个阶段都有明确的输入输出阶段输入核心操作输出数据提取RJPG原始文件TSDK解析辐射数据带温度TIFF 元数据JSON数据校验温度TIFF温度范围检查、坏帧剔除合格影像集空三与正射温度TIFFPix4D空三、正射生成温度正射影像成果应用温度正射温度矩阵导出、分析温度报告/等值线这个拆法的逻辑是把数据解析和摄影测量彻底分开。TSDK负责把物理量辐射值还原成温度Pix4D负责把二维影像还原成三维空间位置。两者各司其职中间用标准TIFF做接口。这样做的好处是任何一步出问题都能单独排查不会混在一起。1.3 工具选型背后的考量为什么用TSDK而不是自己解析RJPGRJPG的私有数据块格式大疆没有完全公开网上能找到的解析代码大多是逆向出来的版本兼容性很差。TSDKThermal SDK是大疆官方提供的支持Windows和Linux提供C接口和Python绑定。它内部处理了不同相机型号XT2、H20T、H30T的差异你只需要调用irdata相关接口就能拿到原始辐射值。自己逆向的话换个固件版本可能就崩了。为什么用Pix4D而不是其他空三软件热红外影像有个特点分辨率低通常640×512、纹理弱、对比度差。普通可见光空三软件在热红外图上经常匹配失败。Pix4D的Aerial Grid模式和自定义模板对低纹理影像的匹配策略更成熟而且它支持导入带地理信息的TIFF能直接读取温度波段。另一个原因是Pix4D的成果导出格式灵活能输出GeoTIFF方便后续用Python做温度分析。为什么中间要转TIFF而不是直接用RJPGPix4D读RJPG时只取伪彩图温度信息丢失。转成TIFF时我们把温度值写入像素值比如温度×100存为16位整数同时把地理坐标、相机参数写进TIFF的元数据。这样Pix4D既能看到影像又能保留温度数值。用16位整数而不是浮点是因为Pix4D对浮点TIFF的支持不稳定16位整数范围-32768到32767按温度×100存能覆盖-327.68℃到327.67℃足够所有常规场景。2. TSDK环境搭建与RJPG解析核心细节2.1 TSDK安装与Python环境配置TSDK的Python绑定安装是第一个坑。官方文档写得比较简略实际配置时容易卡在依赖上。Windows环境# 建议用conda建独立环境避免和系统Python冲突 conda create -n thermal python3.9 conda activate thermal # 安装TSDK Python包注意版本要和相机固件匹配 pip install dji-thermal-sdk # 核心依赖 pip install numpy opencv-python pillow gdal这里Python版本建议3.8到3.103.11以上有些依赖轮子还没跟上。dji-thermal-sdk安装后还需要把TSDK的动态库路径加到系统PATH里否则import时会报找不到dll。Linux环境# Ubuntu 20.04/22.04实测可用 sudo apt install libusb-1.0-0-dev libopencv-dev pip install dji-thermal-sdkLinux下要注意权限问题TSDK访问相机USB设备需要udev规则但纯离线解析RJPG文件不需要连相机所以这一步可以跳过。注意TSDK的Python包在不同平台上的接口名略有差异Windows下是dji_thermal_sdkLinux下可能是dji_thermalimport前先确认。2.2 RJPG文件结构解析RJPG文件里其实藏着三层数据第一层是标准JPEG图像数据就是你能看到的伪彩图分辨率通常是640×512或1280×1024。第二层是R-JPEG私有段存在APP1或APP2标记里包含原始辐射值矩阵16位、发射率、反射温度、大气温度、湿度、距离、镜头参数等。第三层是XMP元数据记录GPS坐标、云台姿态、拍摄时间。TSDK解析时核心是调用irdata接口import dji_thermal_sdk as dts # 初始化 dts.init() # 读取RJPG ir_data dts.irdata_create_from_rjpeg(DJI_0001_R.JPG) # 获取温度矩阵单位摄氏度 temp_matrix dts.irdata_get_temperature_matrix(ir_data) # 获取元数据 emissivity dts.irdata_get_emissivity(ir_data) ambient_temp dts.irdata_get_ambient_temperature(ir_data) distance dts.irdata_get_object_distance(ir_data) # 释放 dts.irdata_destroy(ir_data)temp_matrix是一个numpy数组形状和影像分辨率一致每个元素是摄氏度浮点值。这一步拿到的就是真温度不是伪彩图的颜色映射。2.3 温度矩阵转TIFF的关键参数拿到温度矩阵后不能直接存成TIFF要做几个处理温度值缩放Pix4D读16位TIFF时默认按整数处理。我们把温度×100存为int16这样0.01℃的精度能保留。读取时再除以100还原。import numpy as np import rasterio # 温度矩阵转int16 temp_scaled (temp_matrix * 100).astype(np.int16) # 写入TIFF带地理信息 with rasterio.open( DJI_0001_T.TIF, w, driverGTiff, heighttemp_scaled.shape[0], widthtemp_scaled.shape[1], count1, dtypenp.int16, crsEPSG:4326, transformfrom_origin(lon, lat, pixel_size, pixel_size) ) as dst: dst.write(temp_scaled, 1)地理信息写入从XMP里读GPS坐标和云台姿态计算每个像素的地理位置。如果嫌麻烦也可以先不写地理信息让Pix4D从EXIF里读但实测下来Pix4D对热红外影像的EXIF解析经常出问题手动写入更稳。发射率设置这是最容易忽略的参数。TSDK默认发射率是0.95但实际场景中水体发射率约0.98混凝土约0.92金属约0.1到0.3。发射率设错温度能差好几度。如果拍摄时没在相机里设置后期可以在TSDK里重新计算# 重新设置发射率并计算温度 dts.irdata_set_emissivity(ir_data, 0.92) temp_matrix dts.irdata_get_temperature_matrix(ir_data)提示发射率、反射温度、距离、湿度这四个参数任何一个变了都要重新计算温度矩阵。建议在解析时就把这些参数记到JSON里方便追溯。3. Pix4D温度正射影像生成实操3.1 工程创建与影像导入Pix4D新建工程时选New Project然后导入转换好的温度TIFF。这里有个关键设置在Image Properties里把影像类型选为Thermal如果有这个选项或者选Multispectral再手动配置波段。Pix4D 4.5以上版本对热红外TIFF的支持比较好但要注意不要勾选Use EXIF GPS因为热红外影像的EXIF经常不准用手动写入的GeoTIFF坐标更可靠。在Processing Options里把Camera Model选为Custom然后手动输入热红外相机的内参。大疆H20T的热红外镜头焦距是13.5mm传感器尺寸是640×512像素间距12μm。这些参数在TSDK的元数据里能读到。# 从TSDK读取相机内参 focal_length dts.irdata_get_focal_length(ir_data) # 单位mm sensor_width dts.irdata_get_sensor_width(ir_data) # 单位mm3.2 空三处理的关键参数调整热红外影像空三是整个流程最容易失败的地方。默认参数下匹配点数量经常不够导致空三失败或精度很差。我踩过的坑和对应的调整策略匹配策略调整在Processing Options → Matching里把Image Scale从默认的1/2改成1/1全分辨率匹配。热红外影像本身分辨率就低再降采样就没法匹配了。关键点数量把Keypoint Density调到High。热红外影像纹理弱需要更多关键点才能找到足够的匹配对。匹配对数量把Minimum Number of Matches从默认的6降到4。热红外影像对比度低匹配质量差降低阈值能增加匹配对但要注意后续用Tie Point Editor手动剔除错误匹配。初始对准如果影像有重叠度不够的区域可以在Initial Processing里勾选Use GPS for Initial Alignment用GPS做初始位置估计减少匹配搜索范围。实测下来一套200张的H20T热红外数据默认参数空三成功率大概60%调整后能到90%以上。剩下的10%通常是影像重叠度不够或者飞行高度太高导致分辨率不足。3.3 正射影像生成与温度值保留空三完成后生成正射影像时要注意输出格式选GeoTIFF不要选JPEG或PNG否则温度值会丢失。输出分辨率热红外影像本身分辨率低正射影像分辨率不要设得太高否则会插值出很多虚假细节。建议按GSD地面采样距离设置H20T在50米高度飞行时GSD约4cm正射影像分辨率设4cm/像素比较合适。温度值映射Pix4D生成正射影像时会把多个影像的温度值做加权平均。这里有个问题如果不同影像的发射率设置不一致平均后的温度值没有物理意义。所以前期解析时一定要确保所有影像的发射率参数一致。# 正射影像生成后读取温度值 import rasterio with rasterio.open(orthomosaic.tif) as src: temp_scaled src.read(1) temp_matrix temp_scaled / 100.0 # 还原摄氏度 print(f温度范围: {temp_matrix.min():.2f} ~ {temp_matrix.max():.2f} ℃)3.4 温度正射影像的质量检查生成正射影像后不能直接就用要做几个检查温度范围检查正常场景温度范围应该在-20℃到150℃之间。如果出现-200℃或500℃这种异常值说明有坏帧或者解析错误。空间一致性检查同一物体在不同影像上的温度应该接近。如果同一栋楼在相邻两张正射图上温度差超过5℃说明空三精度不够或者发射率设置有问题。边缘检查正射影像边缘区域温度值容易异常因为边缘影像少加权平均不稳定。建议裁剪掉边缘10%的区域。4. 常见问题排查与避坑经验4.1 TSDK解析常见报错报错信息原因解决方法irdata_create_from_rjpeg failedRJPG文件损坏或版本不兼容用官方工具确认文件可读升级TSDK版本temperature matrix is None相机型号不支持或元数据缺失检查相机型号确认RJPG包含R-JPEG段emissivity out of range发射率设置超出0.1-1.0检查元数据手动设置合理值dll load failed动态库路径未配置把TSDK的lib目录加到PATH4.2 Pix4D空三失败排查空三失败最常见的原因是影像重叠度不够。热红外相机视场角比可见光小同样飞行航线热红外影像的重叠度会低10%到20%。建议飞行时把重叠度设到80%以上。另一个原因是影像纹理太弱。比如拍水面、雪地、均匀墙面热红外图上几乎没纹理匹配点找不到。这种情况可以在Pix4D里手动加控制点或者用可见光影像做空三然后把热红外影像配准上去。4.3 温度值偏差排查如果发现温度值整体偏高或偏低按这个顺序排查发射率设置是否正确金属、玻璃、水面要用对应的发射率。反射温度是否设置反射温度是环境背景辐射室内拍摄时影响很大。距离参数是否正确TSDK计算温度时会用距离做大气衰减校正距离设错会导致温度偏差。湿度参数是否设置高湿度环境下大气衰减明显湿度设错能差1到2℃。提示如果拍摄时没记录这些参数可以用黑体校准。在拍摄现场放一个已知温度的黑体后期用黑体的温度值反推参数。4.4 成果应用中的注意事项温度正射影像导出后用Python做分析时要注意温度矩阵的单位是摄氏度如果要转开尔文加273.15。正射影像的NoData值通常是-32768分析前要剔除。温度值有噪声做阈值分析前建议先做高斯滤波。import cv2 import numpy as np # 读取温度正射 temp cv2.imread(orthomosaic.tif, cv2.IMREAD_ANYDEPTH) / 100.0 # 剔除NoData temp[temp -100] np.nan # 高斯滤波去噪 temp_smooth cv2.GaussianBlur(temp, (5, 5), 0) # 阈值分析找高温区域 hot_spots temp_smooth 60 print(f高温区域面积: {np.sum(hot_spots)} 像素)这套工作流我从2022年开始用前后处理过几十个项目从农业到建筑到电力巡检都跑过。最深的体会是热红外数据的工程化处理难点不在软件操作而在参数设置。发射率、反射温度、距离、湿度这四个参数任何一个设错温度就能差好几度。而很多项目现场根本没条件测这些参数只能靠经验估计。我的建议是如果项目对温度精度要求高一定要在现场做黑体校准哪怕只是用一个已知温度的热水袋也比完全靠默认参数强。