初始提交

This commit is contained in:
2026-02-25 09:42:51 +08:00
parent c25276c481
commit d84d886f35
182 changed files with 18438 additions and 0 deletions

View File

@ -0,0 +1,87 @@
import matplotlib
import matplotlib.pyplot as plt
matplotlib.use('TkAgg')
from plantcv import plantcv as pcv
import numpy as np
import cv2
def process_images_background(full_bil_path, mask, outdir='None', debug="None"):
# 初始化参数
class options:
def __init__(self):
self.image = full_bil_path # 输入的光谱图像路径
self.debug = debug # 设置调试模式:'plot' 或 'print'
self.writeimg = False # 是否保存图片
self.result = outdir # 输出结果文件路径
self.outdir = outdir # 输出文件夹路径
args = options()
# 设置 PlantCV 的全局参数
pcv.params.debug = args.debug
pcv.params.dpi = 100 # 设置 DPI
pcv.params.text_size = 1 # 文本大小
pcv.params.text_thickness = 1 # 文本粗细
# 读取光谱图像ENVI 格式)
spectral_array = pcv.readimage(filename=args.image, mode='envi')
bath_100 = spectral_array.array_data[:, :, 100]
bath_over = pcv.threshold.binary(gray_img=bath_100, threshold=5500, object_type='light')
# 将PIL 16位掩膜转换为8位二值化格式
# 如果mask是非零值则设置为255塑料区域否则为0背景
mask_array = np.array(mask) if not isinstance(mask, np.ndarray) else mask
b_thresh_unit8 = ((mask_array > 0).astype(np.uint8)) * 255
# 填充小的孔洞,并反转掩膜
b_fill = pcv.fill(bin_img=b_thresh_unit8, size=250)
b_fill_inverted = pcv.invert(b_fill)
# 创建形态统计和光谱统计掩膜
dilate_img = pcv.dilate(gray_img=b_fill_inverted, ksize=3, i=4)
bath_erode = pcv.erode(gray_img=bath_over, ksize=3, i=4)
# 塑料掩膜的反转和非黑色背景的掩膜相乘
dilate_img = dilate_img * bath_erode / 255
dilate_img = pcv.fill(bin_img=dilate_img, size=10000)
# 使用cv2.connectedComponents代替pcv.create_labels避免污染plantcv outputs
num1, labeled_spectral_mask = cv2.connectedComponents(dilate_img.astype(np.uint8))
# plt.figure(figsize=(10, 8))
# plt.imshow(dilate_img, cmap='nipy_spectral')
# plt.colorbar(label='Object Label')
# plt.title(f'Labeled Spectral Mask - {num1} objects detected')
# plt.xlabel('X coordinate')
# plt.ylabel('Y coordinate')
# plt.show()
print(f"Number of objects (second mask): {num1 - 1}") # -1 because first label is background
# 直接计算每个对象的面积并找到最大面积的对象
max_area = 0
max_label = 0
# 遍历所有标签从1开始0是背景
for label in range(1, num1):
# 创建当前标签的掩膜
obj_mask = labeled_spectral_mask == label
# 计算面积
area = np.sum(obj_mask)
if area > max_area:
max_area = area
max_label = label
# 提取最大面积对象的光谱
if max_label > 0:
max_obj_mask = labeled_spectral_mask == max_label
# 获取最大对象在所有波段的光谱值
spectral_values = spectral_array.array_data[max_obj_mask, :]
# 计算平均光谱
mean_spectrum = np.mean(spectral_values, axis=0)
# 返回最大面积对象的平均光谱
return mean_spectrum/10000
else:
# 如果没有找到有效背景对象,返回全零光谱
return np.zeros(spectral_array.array_data.shape[-1]) / 10000