feat:新增百香果绿色占比计算;tg文件夹下为百香果绿色占比各个结果图实验程序

This commit is contained in:
TG 2024-06-26 19:17:40 +08:00
parent 7c191d9d42
commit 68fd790823
6 changed files with 423 additions and 16 deletions

View File

@ -317,6 +317,40 @@ class Passion_fruit:
return np.zeros_like(rgb_img) return np.zeros_like(rgb_img)
return result return result
def extract_green_pixels_cv(self,image):
'''
提取图像中的绿色像素
:param image:
:return:
'''
image_rgb = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
# Define the HSV range for green
lower_green = np.array([setting.low_H, setting.low_S, setting.low_V])
upper_green = np.array([setting.high_H, setting.high_S, setting.high_V])
# Convert the image to HSV
hsv = cv2.cvtColor(image_rgb, cv2.COLOR_RGB2HSV)
# Create the mask
mask = cv2.inRange(hsv, lower_green, upper_green)
# Bitwise-AND mask and original image
res = cv2.bitwise_and(image_rgb, image_rgb, mask=mask)
# Convert result to BGR for display
res_bgr = cv2.cvtColor(res, cv2.COLOR_RGB2BGR)
return mask
def pixel_comparison(self, defect, mask):
'''
比较两幅图像的像素值如果相同则赋值为0不同则赋值为255
:param defect:
:param mask:
:return:
'''
# 确保图像是二值图像
_, defect_binary = cv2.threshold(defect, 127, 255, cv2.THRESH_BINARY)
_, mask_binary = cv2.threshold(mask, 127, 255, cv2.THRESH_BINARY)
# 执行像素比较
green_img = np.where(defect_binary == mask_binary, 0, 255).astype(np.uint8)
return green_img
#糖度预测模型 #糖度预测模型
class Spec_predict(object): class Spec_predict(object):
def __init__(self, load_from=None, debug_mode=False): def __init__(self, load_from=None, debug_mode=False):
@ -390,35 +424,28 @@ class Data_processing:
return np.zeros_like(image_array) if image_array is not None else np.zeros((100, 100), dtype=np.uint8) return np.zeros_like(image_array) if image_array is not None else np.zeros((100, 100), dtype=np.uint8)
# 应用中值滤波 # 应用中值滤波
image_filtered = cv2.medianBlur(image_array, 5) image_filtered = cv2.medianBlur(image_array, 5)
# 形态学闭操作 # 形态学闭操作
kernel = cv2.getStructuringElement(cv2.MORPH_ELLIPSE, (15, 15)) kernel = cv2.getStructuringElement(cv2.MORPH_ELLIPSE, (15, 15))
image_closed = cv2.morphologyEx(image_filtered, cv2.MORPH_CLOSE, kernel) image_closed = cv2.morphologyEx(image_filtered, cv2.MORPH_CLOSE, kernel)
# 查找轮廓 # 查找轮廓
contours, _ = cv2.findContours(image_closed, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) contours, _ = cv2.findContours(image_closed, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
# 创建空白图像以绘制轮廓 # 创建空白图像以绘制轮廓
image_contours = np.zeros_like(image_array) image_contours = np.zeros_like(image_array)
# 进行多边形拟合并填充轮廓 # 进行多边形拟合并填充轮廓
for contour in contours: for contour in contours:
epsilon = 0.001 * cv2.arcLength(contour, True) epsilon = 0.001 * cv2.arcLength(contour, True)
approx = cv2.approxPolyDP(contour, epsilon, True) approx = cv2.approxPolyDP(contour, epsilon, True)
if cv2.contourArea(approx) > 100: # 仅处理较大的轮廓 if cv2.contourArea(approx) > 100: # 仅处理较大的轮廓
cv2.drawContours(image_contours, [approx], -1, (255, 255, 255), -1) cv2.drawContours(image_contours, [approx], -1, (255, 255, 255), -1)
return image_contours return image_contours
def analyze_ellipse(self, image_array): def analyze_ellipse(self, image_array):
# 查找白色区域的轮廓 # 查找白色区域的轮廓
_, binary_image = cv2.threshold(image_array, 127, 255, cv2.THRESH_BINARY) _, binary_image = cv2.threshold(image_array, 127, 255, cv2.THRESH_BINARY)
contours, _ = cv2.findContours(binary_image, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE) contours, _ = cv2.findContours(binary_image, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
# 初始化变量用于存储最大轮廓的长径和短径 # 初始化变量用于存储最大轮廓的长径和短径
major_axis = 0 major_axis = 0
minor_axis = 0 minor_axis = 0
# 对每个找到的轮廓,找出可以包围它的最小椭圆,并计算长径和短径 # 对每个找到的轮廓,找出可以包围它的最小椭圆,并计算长径和短径
for contour in contours: for contour in contours:
if len(contour) >= 5: # 至少需要5个点来拟合椭圆 if len(contour) >= 5: # 至少需要5个点来拟合椭圆
@ -586,10 +613,13 @@ class Data_processing:
combined_mask = pf.create_mask(hsv_image) combined_mask = pf.create_mask(hsv_image)
combined_mask = pf.apply_morphology(combined_mask) combined_mask = pf.apply_morphology(combined_mask)
max_mask = pf.find_largest_component(combined_mask) max_mask = pf.find_largest_component(combined_mask)
filled_img, defect = self.fill_holes(max_mask) filled_img, defect = self.fill_holes(max_mask)
contour_mask = self.contour_process(max_mask) contour_mask = self.contour_process(max_mask)
fore = pf.bitwise_and_rgb_with_binary(img, contour_mask)
mask = pf.extract_green_pixels_cv(fore)
green_img = pf.pixel_comparison(defect, mask)
green_percentage = np.sum(green_img == 255) / np.sum(contour_mask == 255)
green_percentage = round(green_percentage, 2)
long_axis, short_axis = self.analyze_ellipse(contour_mask) long_axis, short_axis = self.analyze_ellipse(contour_mask)
#重量单位为g加上了一点随机数 #重量单位为g加上了一点随机数
weight_real = self.weight_estimates(long_axis, short_axis) weight_real = self.weight_estimates(long_axis, short_axis)
@ -608,12 +638,13 @@ class Data_processing:
# print(f'直径:{diameter}') # print(f'直径:{diameter}')
if diameter < 2.5: if diameter < 2.5:
diameter = 0 diameter = 0
green_percentage = 0
weight = 0 weight = 0
number_defects = 0 number_defects = 0
total_pixels = 0 total_pixels = 0
rp = cv2.cvtColor(np.ones((setting.n_rgb_rows, setting.n_rgb_cols, setting.n_rgb_bands), rp = cv2.cvtColor(np.ones((setting.n_rgb_rows, setting.n_rgb_cols, setting.n_rgb_bands),
dtype=np.uint8), cv2.COLOR_BGR2RGB) dtype=np.uint8), cv2.COLOR_BGR2RGB)
return diameter, weight, number_defects, total_pixels, rp return diameter, green_percentage, weight, number_defects, total_pixels, rp
def process_data(seif, cmd: str, images: list, spec: any, pipe: Pipe, detector: Spec_predict) -> bool: def process_data(seif, cmd: str, images: list, spec: any, pipe: Pipe, detector: Spec_predict) -> bool:
""" """
@ -644,7 +675,7 @@ class Data_processing:
elif cmd == 'PF': elif cmd == 'PF':
# 百香果 # 百香果
diameter, weight, number_defects, total_pixels, rp = seif.analyze_passion_fruit(img) diameter, green_percentage, weight, number_defects, total_pixels, rp = seif.analyze_passion_fruit(img)
if i <= 2: if i <= 2:
diameter_axis_list.append(diameter) diameter_axis_list.append(diameter)
max_defect_num = max(max_defect_num, number_defects) max_defect_num = max(max_defect_num, number_defects)
@ -652,6 +683,7 @@ class Data_processing:
if i == 1: if i == 1:
rp_result = rp rp_result = rp
weight = weight weight = weight
gp = round(green_percentage, 2)
else: else:
logging.error(f'错误指令,指令为{cmd}') logging.error(f'错误指令,指令为{cmd}')
@ -668,14 +700,12 @@ class Data_processing:
defect_num=max_defect_num, total_defect_area=max_total_defect_area, rp=rp_result) defect_num=max_defect_num, total_defect_area=max_total_defect_area, rp=rp_result)
return response return response
elif cmd == 'PF': elif cmd == 'PF':
green_percentage = 0
brix = detector.predict(spec) brix = detector.predict(spec)
if diameter == 0: if diameter == 0:
brix = 0 brix = 0
# print(f'预测的brix值为{brix}; 预测的直径为:{diameter}; 预测的重量为:{weight}; 预测的绿色比例为:{green_percentage};' # print(f'预测的brix值为{brix}; 预测的直径为:{diameter}; 预测的重量为:{weight}; 预测的绿色比例为:{green_percentage};'
# f' 预测的缺陷数量为:{max_defect_num}; 预测的总缺陷面积为:{max_total_defect_area};') # f' 预测的缺陷数量为:{max_defect_num}; 预测的总缺陷面积为:{max_total_defect_area};')
response = pipe.send_data(cmd=cmd, brix=brix, green_percentage=green_percentage, diameter=diameter, response = pipe.send_data(cmd=cmd, brix=brix, green_percentage=gp, diameter=diameter, weight=weight,
weight=weight,
defect_num=max_defect_num, total_defect_area=max_total_defect_area, rp=rp_result) defect_num=max_defect_num, total_defect_area=max_total_defect_area, rp=rp_result)
return response return response

View File

@ -32,6 +32,14 @@ class Config:
value_target = 25 value_target = 25
value_delta = 10 value_delta = 10
#提取绿色像素参数
low_H = 0
low_S = 100
low_V = 0
high_H = 60
high_S = 180
high_V = 60
#spec_predict #spec_predict
#筛选谱段并未使用在qt取数据时已经筛选 #筛选谱段并未使用在qt取数据时已经筛选
selected_bands = [8, 9, 10, 48, 49, 50, 77, 80, 103, 108, 115, 143, 145] selected_bands = [8, 9, 10, 48, 49, 50, 77, 80, 103, 108, 115, 143, 145]

View File

@ -0,0 +1,53 @@
# -*- coding: utf-8 -*-
# @Time : 2024/6/17 下午3:36
# @Author : TG
# @File : config.py
# @Software: PyCharm
from root_dir import ROOT_DIR
class Config:
#文件相关参数
#预热参数
n_spec_rows, n_spec_cols, n_spec_bands = 25, 30, 13
n_rgb_rows, n_rgb_cols, n_rgb_bands = 613, 800, 3
tomato_img_dir = ROOT_DIR / 'models' / 'TO.bmp'
passion_fruit_img_dir = ROOT_DIR / 'models' / 'PF.bmp'
#模型路径
#糖度模型
brix_model_path = ROOT_DIR / 'models' / 'passion_fruit.joblib'
#图像分类模型
imgclassifier_model_path = ROOT_DIR / 'models' / 'imgclassifier.joblib'
imgclassifier_class_indices_path = ROOT_DIR / 'models' / 'class_indices.json'
#classifer.py参数
#tomato
find_reflection_threshold = 190
extract_g_r_factor = 1.5
#passion_fruit
hue_value = 37
hue_delta = 10
value_target = 25
value_delta = 10
#spec_predict
#筛选谱段并未使用在qt取数据时已经筛选
selected_bands = [8, 9, 10, 48, 49, 50, 77, 80, 103, 108, 115, 143, 145]
#data_processing
#根据标定数据计算的参数,实际长度/像素长度单位cm
pixel_length_ratio = 6.3/425
#绿叶面积阈值,高于此阈值认为连通域是绿叶
area_threshold = 20000
#百香果密度g/cm^3
density = 0.652228972
#百香果面积比例每个像素代表的实际面积cm^2
area_ratio = 0.00021973702422145334
#def analyze_tomato
#s_l通道阈值
threshold_s_l = 180
threshold_fore_g_r_t = 20

View File

@ -0,0 +1,256 @@
# -*- coding: utf-8 -*-
# @Time : 2024/6/26 下午5:31
# @Author : TG
# @File : passion_fruit_rgb.py
# @Software: PyCharm
import os
import cv2
import numpy as np
import argparse
import logging
from config import Config as setting
class Passion_fruit:
def __init__(self, hue_value=setting.hue_value, hue_delta=setting.hue_delta,
value_target=setting.value_target, value_delta=setting.value_delta):
# 初始化常用参数
self.hue_value = hue_value
self.hue_delta = hue_delta
self.value_target = value_target
self.value_delta = value_delta
def create_mask(self, hsv_image):
# 创建H通道阈值掩码
lower_hue = np.array([self.hue_value - self.hue_delta, 0, 0])
upper_hue = np.array([self.hue_value + self.hue_delta, 255, 255])
hue_mask = cv2.inRange(hsv_image, lower_hue, upper_hue)
# 创建V通道排除中心值的掩码
lower_value_1 = np.array([0, 0, 0])
upper_value_1 = np.array([180, 255, self.value_target - self.value_delta])
lower_value_2 = np.array([0, 0, self.value_target + self.value_delta])
upper_value_2 = np.array([180, 255, 255])
value_mask_1 = cv2.inRange(hsv_image, lower_value_1, upper_value_1)
value_mask_1 = cv2.bitwise_not(value_mask_1)
value_mask_2 = cv2.inRange(hsv_image, lower_value_2, upper_value_2)
value_mask = cv2.bitwise_and(value_mask_1, value_mask_2)
# 合并H通道和V通道掩码
return cv2.bitwise_and(hue_mask, value_mask)
def apply_morphology(self, mask):
# 应用形态学操作
kernel = cv2.getStructuringElement(cv2.MORPH_ELLIPSE, (5, 5))
return cv2.morphologyEx(mask, cv2.MORPH_OPEN, kernel)
def find_largest_component(self, mask):
if mask is None or mask.size == 0 or np.all(mask == 0):
logging.warning("RGB 图像为空或全黑返回一个全黑RGB图像。")
return np.zeros((setting.n_rgb_rows, setting.n_rgb_cols, setting.n_rgb_bands), dtype=np.uint8) \
if mask is None else np.zeros_like(mask)
# 寻找最大连通组件
num_labels, labels, stats, centroids = cv2.connectedComponentsWithStats(mask, 4, cv2.CV_32S)
if num_labels < 2:
return None # 没有找到显著的组件
max_label = 1 + np.argmax(stats[1:, cv2.CC_STAT_AREA]) # 跳过背景
return (labels == max_label).astype(np.uint8) * 255
def draw_contours_on_image(self, original_image, mask_image):
"""
在原图上绘制轮廓
:param original_image: 原图的NumPy数组
:param mask_image: 轮廓mask的NumPy数组
:return: 在原图上绘制轮廓后的图像
"""
# 确保mask_image是二值图像
_, binary_mask = cv2.threshold(mask_image, 127, 255, cv2.THRESH_BINARY)
# 查找mask图像中的轮廓
contours, _ = cv2.findContours(binary_mask, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
# 在原图上绘制轮廓
cv2.drawContours(original_image, contours, -1, (0, 255, 0), 2)
return original_image
def bitwise_and_rgb_with_binary(self, rgb_img, bin_img):
'''
RGB 图像与二值图像进行按位与操作用于将二值区域应用于原始图像
:param rgb_img: 原始 RGB 图像
:param bin_img: 二值图像
:return: 按位与后的结果图像
'''
# 检查 RGB 图像是否为空或全黑
if rgb_img is None or rgb_img.size == 0 or np.all(rgb_img == 0):
logging.warning("RGB 图像为空或全黑返回一个全黑RGB图像。")
return np.zeros((setting.n_rgb_rows, setting.n_rgb_cols, setting.n_rgb_bands), dtype=np.uint8) \
if rgb_img is None else np.zeros_like(rgb_img)
# 检查二值图像是否为空或全黑
if bin_img is None or bin_img.size == 0 or np.all(bin_img == 0):
logging.warning("二值图像为空或全黑返回一个全黑RGB图像。")
return np.zeros((setting.n_rgb_rows, setting.n_rgb_cols, setting.n_rgb_bands), dtype=np.uint8) \
if bin_img is None else np.zeros_like(bin_img)
# 转换二值图像为三通道
try:
bin_img_3channel = cv2.cvtColor(bin_img, cv2.COLOR_GRAY2BGR)
except cv2.error as e:
logging.error(f"转换二值图像时发生错误: {e}")
return np.zeros_like(rgb_img)
# 进行按位与操作
try:
result = cv2.bitwise_and(rgb_img, bin_img_3channel)
except cv2.error as e:
logging.error(f"执行按位与操作时发生错误: {e}")
return np.zeros_like(rgb_img)
return result
def fill_holes(bin_img):
img_filled = bin_img.copy()
height, width = bin_img.shape
mask = np.zeros((height + 2, width + 2), np.uint8)
cv2.floodFill(img_filled, mask, (0, 0), 255)
img_filled_inv = cv2.bitwise_not(img_filled)
img_filled = cv2.bitwise_or(bin_img, img_filled)
img_defect = img_filled_inv[:height, :width]
return img_filled, img_defect
def contour_process(image_array):
# 检查图像是否为空或全黑
if image_array is None or image_array.size == 0 or np.all(image_array == 0):
logging.warning("输入的图像为空或全黑,返回一个全黑图像。")
return np.zeros_like(image_array) if image_array is not None else np.zeros((100, 100), dtype=np.uint8)
# 应用中值滤波
image_filtered = cv2.medianBlur(image_array, 5)
# 形态学闭操作
kernel = cv2.getStructuringElement(cv2.MORPH_ELLIPSE, (15, 15))
image_closed = cv2.morphologyEx(image_filtered, cv2.MORPH_CLOSE, kernel)
# 查找轮廓
contours, _ = cv2.findContours(image_closed, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
# 创建空白图像以绘制轮廓
image_contours = np.zeros_like(image_array)
# 进行多边形拟合并填充轮廓
for contour in contours:
epsilon = 0.001 * cv2.arcLength(contour, True)
approx = cv2.approxPolyDP(contour, epsilon, True)
if cv2.contourArea(approx) > 100: # 仅处理较大的轮廓
cv2.drawContours(image_contours, [approx], -1, (255, 255, 255), -1)
return image_contours
def extract_green_pixels_cv(image):
"""
使用 OpenCV 提取图像中的绿色像素并可选择保存结果图像
参数:
image_path (str): 输入图像的文件路径
save_path (str, optional): 输出图像的保存路径若提供此参数则保存提取的绿色像素图像
返回:
输出图像绿色像素为白色其他像素为黑色
"""
image_rgb = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
# Define the HSV range for green
lower_green = np.array([0, 100, 0])
upper_green = np.array([60, 180, 60])
# Convert the image to HSV
hsv = cv2.cvtColor(image_rgb, cv2.COLOR_RGB2HSV)
# Create the mask
mask = cv2.inRange(hsv, lower_green, upper_green)
# Bitwise-AND mask and original image
res = cv2.bitwise_and(image_rgb, image_rgb, mask=mask)
# Convert result to BGR for display
res_bgr = cv2.cvtColor(res, cv2.COLOR_RGB2BGR)
return mask
def pixel_comparison(defect, mask):
"""
比较两幅图像的像素值如果相同则赋值为0不同则赋值为255
参数:
defect_path (str): 第一幅图像的路径
mask_path (str): 第二幅图像的路径
save_path (str, optional): 结果图像的保存路径
返回:
numpy.ndarray: 处理后的图像数组
"""
# 确保图像是二值图像
_, defect_binary = cv2.threshold(defect, 127, 255, cv2.THRESH_BINARY)
_, mask_binary = cv2.threshold(mask, 127, 255, cv2.THRESH_BINARY)
# 执行像素比较
green_img = np.where(defect_binary == mask_binary, 0, 255).astype(np.uint8)
return green_img
def main():
parser = argparse.ArgumentParser(description='Process some integers.')
parser.add_argument('--dir_path', type=str,
default=r'D:\project\supermachine--tomato-passion_fruit\20240529RGBtest3\tg\test',
help='the directory path of images')
parser.add_argument('--threshold_s_l', type=int, default=180,
help='the threshold for s_l')
parser.add_argument('--threshold_r_b', type=int, default=15,
help='the threshold for r_b')
args = parser.parse_args()
pf = Passion_fruit()
for img_file in os.listdir(args.dir_path):
if img_file.endswith('.bmp'):
img_path = os.path.join(args.dir_path, img_file)
img = cv2.imread(img_path)
cv2.imshow('img', img)
hsv_image = cv2.cvtColor(img, cv2.COLOR_BGR2HSV)
cv2.imshow('hsv', hsv_image)
combined_mask = pf.create_mask(hsv_image)
cv2.imshow('combined_mask1', combined_mask)
combined_mask = pf.apply_morphology(combined_mask)
cv2.imshow('combined_mask2', combined_mask)
max_mask = pf.find_largest_component(combined_mask)
cv2.imshow('max_mask', max_mask)
filled_img, defect = fill_holes(max_mask)
cv2.imshow('filled_img', filled_img)
cv2.imshow('defect', defect)
contour_mask = contour_process(max_mask)
cv2.imshow('contour_mask', contour_mask)
fore = pf.bitwise_and_rgb_with_binary(img, contour_mask)
cv2.imshow('fore', fore)
mask = extract_green_pixels_cv(fore)
cv2.imshow('mask', mask)
green_img = pixel_comparison(defect, mask)
cv2.imshow('green_img', green_img)
green_percentage = np.sum(green_img == 255) / np.sum(contour_mask == 255)
green_percentage = round(green_percentage, 2)
print(np.sum(green_img == 255))
print(np.sum(contour_mask == 255))
print(green_percentage)
edge = pf.draw_contours_on_image(img, contour_mask)
cv2.imshow('edge', edge)
org_defect = pf.bitwise_and_rgb_with_binary(edge, max_mask)
cv2.imshow('org_defect', org_defect)
cv2.waitKey(0)
cv2.destroyAllWindows()
if __name__ == '__main__':
main()

61
20240529RGBtest3/tg/t.py Normal file
View File

@ -0,0 +1,61 @@
# -*- coding: utf-8 -*-
# @Time : 2024/6/26 下午6:15
# @Author : TG
# @File : t.py
# @Software: PyCharm
import cv2
import numpy as np
def nothing(x):
pass
# Create a window
cv2.namedWindow('Green Pixels Selector')
# Create trackbars for color change
cv2.createTrackbar('Lower Hue', 'Green Pixels Selector', 0, 255, nothing)
cv2.createTrackbar('Lower Sat', 'Green Pixels Selector', 100, 255, nothing)
cv2.createTrackbar('Lower Val', 'Green Pixels Selector', 0, 255, nothing)
cv2.createTrackbar('Upper Hue', 'Green Pixels Selector', 60, 255, nothing)
cv2.createTrackbar('Upper Sat', 'Green Pixels Selector', 180, 255, nothing)
cv2.createTrackbar('Upper Val', 'Green Pixels Selector', 60, 255, nothing)
# Load image
image = cv2.imread(r'D:\project\supermachine--tomato-passion_fruit\20240529RGBtest3\tg\test\23.bmp')
image_rgb = cv2.cvtColor(image, cv2.COLOR_BGR2RGB)
while (True):
# Get current positions of the trackbars
lh = cv2.getTrackbarPos('Lower Hue', 'Green Pixels Selector')
ls = cv2.getTrackbarPos('Lower Sat', 'Green Pixels Selector')
lv = cv2.getTrackbarPos('Lower Val', 'Green Pixels Selector')
uh = cv2.getTrackbarPos('Upper Hue', 'Green Pixels Selector')
us = cv2.getTrackbarPos('Upper Sat', 'Green Pixels Selector')
uv = cv2.getTrackbarPos('Upper Val', 'Green Pixels Selector')
# Define the HSV range for green
lower_green = np.array([lh, ls, lv])
upper_green = np.array([uh, us, uv])
# Convert the image to HSV
hsv = cv2.cvtColor(image_rgb, cv2.COLOR_RGB2HSV)
# Create the mask
mask = cv2.inRange(hsv, lower_green, upper_green)
# Bitwise-AND mask and original image
res = cv2.bitwise_and(image_rgb, image_rgb, mask=mask)
# Convert result to BGR for display
res_bgr = cv2.cvtColor(res, cv2.COLOR_RGB2BGR)
# Display the resulting frame
cv2.imshow('Green Pixels Selector', res_bgr)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
# When everything done, release the window
cv2.destroyAllWindows()

View File

@ -209,8 +209,7 @@ class Pipe:
defect_num + total_defect_area + height + width + img_bytes) defect_num + total_defect_area + height + width + img_bytes)
elif cmd == 'PF': elif cmd == 'PF':
brix = int(brix * 1000).to_bytes(2, byteorder='big') brix = int(brix * 1000).to_bytes(2, byteorder='big')
gp = 0 gp = int(green_percentage * 100).to_bytes(1, byteorder='big')
gp = gp.to_bytes(1, byteorder='big')
weight = weight.to_bytes(1, byteorder='big') weight = weight.to_bytes(1, byteorder='big')
send_message = (length + cmd_re + brix + gp + diameter + weight + send_message = (length + cmd_re + brix + gp + diameter + weight +
defect_num + total_defect_area + height + width + img_bytes) defect_num + total_defect_area + height + width + img_bytes)