最近有点忙,上来写的时间不多。
今天就把之前写的一个选型的简易程序,供大家参考。

代码:
python
import sys
from PyQt5.QtWidgets import (QApplication, QMainWindow, QWidget, QVBoxLayout, QHBoxLayout,
QLabel, QLineEdit, QPushButton, QGroupBox, QFormLayout,
QComboBox, QFileDialog, QMessageBox)
from PyQt5.QtCore import Qt
class CameraLensCalculator(QMainWindow):
def __init__(self):
super().__init__()
self.setWindowTitle("相机与镜头选型工具")
self.setFixedSize(600, 650)
# 主窗口布局
central_widget = QWidget()
self.setCentralWidget(central_widget)
main_layout = QVBoxLayout(central_widget)
# 输入参数区域
self.setup_input_group()
main_layout.addWidget(self.input_group)
# 计算按钮
self.calculate_btn = QPushButton("计算", clicked=self.calculate)
main_layout.addWidget(self.calculate_btn, alignment=Qt.AlignCenter)
# 结果显示区域
self.setup_result_group()
main_layout.addWidget(self.result_group)
# 保存按钮
self.save_btn = QPushButton("保存报告", clicked=self.save_report)
self.save_btn.setEnabled(False)
main_layout.addWidget(self.save_btn, alignment=Qt.AlignCenter)
# 设置默认值
self.set_default_values()
def setup_input_group(self):
"""初始化输入参数区域"""
self.input_group = QGroupBox("输入参数")
layout = QFormLayout()
# 物体尺寸
self.obj_width = QLineEdit()
self.obj_height = QLineEdit()
layout.addRow(QLabel("物体宽度 (mm):"), self.obj_width)
layout.addRow(QLabel("物体高度 (mm):"), self.obj_height)
# 边缘余量
self.margin = QLineEdit()
layout.addRow(QLabel("边缘余量 (%):"), self.margin)
# 检测精度
self.accuracy = QLineEdit()
layout.addRow(QLabel("检测精度 (mm):"), self.accuracy)
# 工作距离
self.working_distance = QLineEdit()
layout.addRow(QLabel("工作距离 (mm):"), self.working_distance)
# 传感器类型(下拉选择)
self.sensor_combo = QComboBox()
self.sensor_combo.addItems([
"1/2\" (6.4x4.8mm)",
"1/1.8\" (7.2x5.3mm)",
"2/3\" (8.8x6.6mm)",
"自定义"
])
self.sensor_combo.currentTextChanged.connect(self.handle_sensor_change)
layout.addRow(QLabel("传感器类型:"), self.sensor_combo)
# 自定义传感器尺寸(默认隐藏)
self.sensor_custom = QLineEdit()
self.sensor_custom.setPlaceholderText("输入宽x高(如 10.0x8.0)")
self.sensor_custom.setVisible(False)
layout.addRow(QLabel("自定义尺寸:"), self.sensor_custom)
# 光圈值(景深计算用)
self.aperture = QLineEdit()
self.aperture.setPlaceholderText("F值(如 2.8)")
layout.addRow(QLabel("光圈 (F):"), self.aperture)
self.input_group.setLayout(layout)
def setup_result_group(self):
"""初始化结果显示区域"""
self.result_group = QGroupBox("计算结果")
self.result_label = QLabel("请填写参数后点击计算")
self.result_label.setAlignment(Qt.AlignLeft)
self.result_label.setStyleSheet("font-family: monospace;")
layout = QVBoxLayout()
layout.addWidget(self.result_label)
self.result_group.setLayout(layout)
def handle_sensor_change(self, text):
"""切换传感器类型时显示/隐藏自定义输入框"""
self.sensor_custom.setVisible(text == "自定义")
def set_default_values(self):
"""设置默认参数值"""
self.obj_width.setText("100")
self.obj_height.setText("50")
self.margin.setText("20")
self.accuracy.setText("0.1")
self.working_distance.setText("400")
self.aperture.setText("4.0")
def calculate(self):
"""执行计算逻辑"""
try:
# 获取输入值
obj_w = float(self.obj_width.text())
obj_h = float(self.obj_height.text())
margin = float(self.margin.text()) / 100 # 转为小数
accuracy = float(self.accuracy.text())
wd = float(self.working_distance.text())
aperture = float(self.aperture.text()) if self.aperture.text() else 4.0
# 解析传感器尺寸
sensor_text = self.sensor_combo.currentText()
if sensor_text == "自定义":
sensor_w, sensor_h = map(float, self.sensor_custom.text().split('x'))
else:
sensor_str = sensor_text.split('(')[1].split(')')[0].replace('mm', '')
sensor_w, sensor_h = map(float, sensor_str.split('x'))
# 计算FOV(含余量)
fov_w = obj_w * (1 + margin)
fov_h = obj_h * (1 + margin)
# 计算分辨率(安全系数1.5)
res_w = int((fov_w / accuracy) * 1.5)
res_h = int((fov_h / accuracy) * 1.5)
mp = (res_w * res_h) / 1e4 # 万像素
# 计算焦距(公式:f = (WD * 传感器尺寸) / FOV)
focal_w = (wd * sensor_w) / fov_w
focal_h = (wd * sensor_h) / fov_h
focal_length = max(focal_w, focal_h)
# 计算景深(简化公式)
coc = 0.005 # 容许模糊圆直径(默认0.005mm)
depth_of_field = (2 * coc * aperture * (wd ** 2)) / (focal_length ** 2)
# 显示结果
result_text = f"""
=== 计算结果 ===
视场(FOV): {fov_w:.2f} mm × {fov_h:.2f} mm
所需分辨率: {res_w} × {res_h} 像素
推荐相机: ≥ {mp:.1f} 万像素
镜头焦距: ≈ {focal_length:.1f} mm
景深(DoF): ≈ {depth_of_field:.2f} mm
(基于传感器: {sensor_w}x{sensor_h} mm, 光圈 F{aperture})
"""
self.result_label.setText(result_text.strip())
self.save_btn.setEnabled(True)
self.calculation_result = result_text # 保存结果用于导出
except Exception as e:
QMessageBox.warning(self, "错误", f"参数输入无效!\n{str(e)}")
def save_report(self):
"""保存计算结果到文件"""
try:
file_path, _ = QFileDialog.getSaveFileName(
self, "保存报告", "", "Text Files (*.txt);;All Files (*)"
)
if file_path:
with open(file_path, 'w') as f:
f.write("=== 相机与镜头选型报告 ===\n")
f.write(f"物体尺寸: {self.obj_width.text()}x{self.obj_height.text()} mm\n")
f.write(f"边缘余量: {self.margin.text()}%\n")
f.write(f"检测精度: {self.accuracy.text()} mm\n")
f.write(f"工作距离: {self.working_distance.text()} mm\n")
f.write(f"传感器: {self.sensor_combo.currentText()}\n")
f.write(f"光圈: F{self.aperture.text()}\n")
f.write("\n" + self.calculation_result.strip())
QMessageBox.information(self, "成功", "报告已保存!")
except Exception as e:
QMessageBox.critical(self, "错误", f"保存失败!\n{str(e)}")
if __name__ == "__main__":
app = QApplication(sys.argv)
window = CameraLensCalculator()
window.show()
sys.exit(app.exec_())
以上对选型提供初步的想法,具体可以根据个人需求进一步优化。