设备管理:添加\删除

hzk
123 3 days ago
parent 6bc4fb50b9
commit 10b95148f4

@ -241,6 +241,11 @@ private slots:
*/
void onAddDogClicked();
/**
* @brief
*/
void onDeleteDeviceClicked();
/**
* @brief
* @param deviceId ID
@ -306,6 +311,13 @@ private:
*/
QList<DeviceInfo> loadDevicesFromDatabase();
/**
* @brief
* @param deviceId ID
* @return
*/
bool deleteDeviceFromDatabase(const QString &deviceId);
/**
* @brief
*/
@ -341,6 +353,7 @@ private:
// UI组件 - 操作按钮
QPushButton *m_addUAVButton; ///< 添加无人机按钮
QPushButton *m_addDogButton; ///< 添加机器狗按钮
QPushButton *m_deleteDeviceButton; ///< 删除设备按钮
QPushButton *m_refreshButton; ///< 刷新按钮
// UI组件 - 设备列表区域

@ -100,14 +100,17 @@ public:
/**
* @brief
* @param deviceId ID
* @param name
* @param type ("uav" "dog")
* @param ip IP
* @param port
* @param state (0)
* @param longitude (0.0)
* @param latitude (0.0)
* @return
*/
bool addDeviceToDatabase(const QString &name, const QString &type, const QString &ip, int port, int state = 0);
bool addDeviceToDatabase(const QString &deviceId, const QString &name, const QString &type, const QString &ip, int port, int state = 0, double longitude = 0.0, double latitude = 0.0);
/**
* @brief

@ -13,6 +13,13 @@
#include <QMessageBox>
#include <QApplication>
#include <QSplitter>
#include <QTableWidget>
#include <QTableWidgetItem>
#include <QHeaderView>
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QLabel>
#include <QDialog>
// Qt SQL头文件
#include <QSqlDatabase>
@ -93,22 +100,37 @@ void DeviceListPanel::setupUI()
// === 操作按钮区域 ===
m_buttonLayout = new QHBoxLayout();
m_addUAVButton = new QPushButton("🚁 + 无人机");
m_addUAVButton->setMaximumHeight(50);
m_addUAVButton->setMaximumWidth(120);
m_addUAVButton = new QPushButton("🚁 +无人机");
m_addUAVButton->setMaximumHeight(60); // 调大按钮
m_addUAVButton->setMaximumWidth(110); // 合理调整按钮宽度
m_addUAVButton->setMinimumWidth(110); // 设置最小宽度确保文字显示完整
m_addUAVButton->setToolTip("添加新的无人机设备");
m_addDogButton = new QPushButton("🐕 + 机器狗");
m_addDogButton->setMaximumHeight(50);
m_addDogButton->setMaximumWidth(120);
m_addDogButton = new QPushButton("🐕 +机器狗");
m_addDogButton->setMaximumHeight(60); // 调大按钮
m_addDogButton->setMaximumWidth(110); // 合理调整按钮宽度
m_addDogButton->setMinimumWidth(110); // 设置最小宽度确保文字显示完整
m_addDogButton->setToolTip("添加新的机器狗设备");
m_deleteDeviceButton = new QPushButton("🗑️ 删除");
m_deleteDeviceButton->setMaximumHeight(60);
m_deleteDeviceButton->setMaximumWidth(90); // 合理调整按钮宽度
m_deleteDeviceButton->setMinimumWidth(90); // 设置最小宽度确保文字显示完整
m_deleteDeviceButton->setToolTip("删除现有设备");
m_refreshButton = new QPushButton("🔄");
m_refreshButton->setMaximumHeight(32);
m_refreshButton->setMaximumWidth(40);
m_refreshButton->setMaximumHeight(50); // 调大刷新按钮
m_refreshButton->setMaximumWidth(50); // 保持紧凑的刷新按钮
m_refreshButton->setMinimumWidth(50); // 设置最小宽度
m_refreshButton->setToolTip("刷新设备列表");
// 添加按钮间距
m_buttonLayout->addWidget(m_addUAVButton);
m_buttonLayout->addSpacing(5); // 添加5px间距
m_buttonLayout->addWidget(m_addDogButton);
m_buttonLayout->addStretch();
m_buttonLayout->addSpacing(5); // 添加5px间距
m_buttonLayout->addWidget(m_deleteDeviceButton); // 添加删除按钮
m_buttonLayout->addStretch(); // 弹性空间
m_buttonLayout->addWidget(m_refreshButton);
// === 设备列表滚动区域 ===
@ -205,6 +227,7 @@ void DeviceListPanel::setupStyle()
m_addUAVButton->setStyleSheet(buttonStyle);
m_addDogButton->setStyleSheet(buttonStyle);
m_deleteDeviceButton->setStyleSheet(buttonStyle);
m_refreshButton->setStyleSheet(buttonStyle);
// 滚动区域样式
@ -240,6 +263,7 @@ void DeviceListPanel::connectSignals()
// 按钮信号
connect(m_addUAVButton, &QPushButton::clicked, this, &DeviceListPanel::onAddUAVClicked);
connect(m_addDogButton, &QPushButton::clicked, this, &DeviceListPanel::onAddDogClicked);
connect(m_deleteDeviceButton, &QPushButton::clicked, this, &DeviceListPanel::onDeleteDeviceClicked);
connect(m_refreshButton, &QPushButton::clicked, this, &DeviceListPanel::refreshDeviceList);
// 状态监控定时器
@ -509,6 +533,74 @@ QList<DeviceInfo> DeviceListPanel::loadDevicesFromDatabase()
return devices;
}
bool DeviceListPanel::deleteDeviceFromDatabase(const QString &deviceId)
{
qDebug() << "Attempting to delete device from database:" << deviceId;
// 创建数据库连接
QSqlDatabase db = QSqlDatabase::addDatabase("QMYSQL", "DeviceListPanel_Delete_Connection");
db.setHostName("localhost");
db.setPort(3306);
db.setDatabaseName("Client");
db.setUserName("root");
db.setPassword("hzk200407140238");
bool success = false;
if (db.open()) {
qDebug() << "Successfully connected to database for deletion";
QSqlQuery query(db);
query.prepare("DELETE FROM devices WHERE id = ?");
query.addBindValue(deviceId);
if (query.exec()) {
if (query.numRowsAffected() > 0) {
qDebug() << "Successfully deleted device from database:" << deviceId;
success = true;
// 从内存中移除设备
for (int i = m_allDevices.size() - 1; i >= 0; --i) {
if (m_allDevices[i].id == deviceId) {
m_allDevices.removeAt(i);
break;
}
}
// 删除设备卡片
if (m_deviceCards.contains(deviceId)) {
DeviceCard *card = m_deviceCards[deviceId];
m_deviceCards.remove(deviceId);
m_deviceListLayout->removeWidget(card);
card->deleteLater();
}
// 清除选择(如果删除的是当前选中的设备)
if (m_selectedDeviceId == deviceId) {
m_selectedDeviceId.clear();
}
// 更新统计信息
updateDeviceCountStats();
} else {
qWarning() << "No device found with ID:" << deviceId;
}
} else {
qWarning() << "Failed to execute delete query:" << query.lastError().text();
}
db.close();
} else {
qWarning() << "Failed to connect to database for deletion:" << db.lastError().text();
}
// 清理数据库连接
QSqlDatabase::removeDatabase("DeviceListPanel_Delete_Connection");
return success;
}
void DeviceListPanel::applySearchAndFilter()
{
qDebug() << "Applying search and filter. Keyword:" << m_currentSearchKeyword
@ -607,6 +699,339 @@ void DeviceListPanel::onAddDogClicked()
emit addDeviceRequested("dog");
}
void DeviceListPanel::onDeleteDeviceClicked()
{
qDebug() << "Delete device button clicked";
// 创建删除设备对话框
QDialog *dialog = new QDialog(this);
dialog->setWindowTitle("删除设备");
dialog->resize(500, 400);
dialog->setModal(true);
QVBoxLayout *layout = new QVBoxLayout(dialog);
// 设置对话框样式
dialog->setStyleSheet(
"QDialog {"
" background-color: rgb(240, 240, 240);"
" color: rgb(50, 50, 50);"
"}"
);
// 标题标签
QLabel *titleLabel = new QLabel("选择要删除的设备:");
titleLabel->setStyleSheet(
"QLabel {"
" font-weight: bold;"
" font-size: 16px;"
" color: rgb(50, 50, 50);"
" background-color: transparent;"
" margin-bottom: 10px;"
" padding: 5px;"
"}"
);
layout->addWidget(titleLabel);
// 设备列表
QTableWidget *deviceTable = new QTableWidget();
deviceTable->setColumnCount(3);
QStringList headers;
headers << "设备ID" << "设备名称" << "设备类型";
deviceTable->setHorizontalHeaderLabels(headers);
// 设置表格属性
deviceTable->setSelectionBehavior(QAbstractItemView::SelectRows);
deviceTable->setSelectionMode(QAbstractItemView::SingleSelection);
deviceTable->horizontalHeader()->setStretchLastSection(true);
deviceTable->setEditTriggers(QAbstractItemView::NoEditTriggers);
// 隐藏行号列(垂直表头)
deviceTable->verticalHeader()->setVisible(false);
// 设置表格样式
deviceTable->setStyleSheet(
"QTableWidget {"
" background-color: white;"
" alternate-background-color: rgb(245, 245, 245);"
" color: rgb(50, 50, 50);"
" gridline-color: rgb(200, 200, 200);"
" selection-background-color: rgb(0, 120, 215);"
" selection-color: white;"
" border: 1px solid rgb(180, 180, 180);"
" border-radius: 4px;"
"}"
"QHeaderView::section {"
" background-color: rgb(230, 230, 230);"
" color: rgb(50, 50, 50);"
" padding: 8px;"
" border: 1px solid rgb(180, 180, 180);"
" font-weight: bold;"
"}"
"QTableWidget::item {"
" padding: 8px;"
" color: rgb(50, 50, 50);"
"}"
"QTableWidget::item:selected {"
" background-color: rgb(0, 120, 215);"
" color: white;"
"}"
);
// 从数据库加载所有设备
QList<DeviceInfo> allDevices = loadDevicesFromDatabase();
deviceTable->setRowCount(allDevices.size());
for (int i = 0; i < allDevices.size(); ++i) {
const DeviceInfo &device = allDevices[i];
deviceTable->setItem(i, 0, new QTableWidgetItem(device.id));
deviceTable->setItem(i, 1, new QTableWidgetItem(device.name));
QString deviceTypeText;
if (device.type == "uav") {
deviceTypeText = "🚁 无人机";
} else if (device.type == "dog") {
deviceTypeText = "🐕 机器狗";
} else {
deviceTypeText = device.type;
}
deviceTable->setItem(i, 2, new QTableWidgetItem(deviceTypeText));
}
layout->addWidget(deviceTable);
// 按钮区域
QHBoxLayout *buttonLayout = new QHBoxLayout();
QPushButton *deleteBtn = new QPushButton("删除选中设备");
QPushButton *cancelBtn = new QPushButton("取消");
deleteBtn->setStyleSheet(
"QPushButton {"
" background: qlineargradient(x1:0, y1:0, x2:0, y2:1, "
" stop:0 rgba(220, 53, 69, 0.8), "
" stop:1 rgba(180, 40, 55, 0.8));"
" color: white;"
" border: 2px solid rgba(220, 53, 69, 0.5);"
" border-radius: 6px;"
" padding: 10px 16px;"
" font-weight: bold;"
"}"
"QPushButton:hover {"
" background: qlineargradient(x1:0, y1:0, x2:0, y2:1, "
" stop:0 rgba(220, 53, 69, 1.0), "
" stop:1 rgba(180, 40, 55, 1.0));"
" border-color: rgba(220, 53, 69, 0.8);"
"}"
"QPushButton:pressed {"
" background: qlineargradient(x1:0, y1:0, x2:0, y2:1, "
" stop:0 rgba(180, 40, 55, 1.0), "
" stop:1 rgba(140, 30, 45, 1.0));"
"}"
);
cancelBtn->setStyleSheet(
"QPushButton {"
" background: qlineargradient(x1:0, y1:0, x2:0, y2:1, "
" stop:0 rgba(45, 65, 95, 0.8), "
" stop:1 rgba(25, 40, 65, 0.8));"
" color: rgb(220, 230, 242);"
" border: 2px solid rgba(82, 194, 242, 0.5);"
" border-radius: 6px;"
" padding: 10px 16px;"
" font-weight: bold;"
"}"
"QPushButton:hover {"
" background: qlineargradient(x1:0, y1:0, x2:0, y2:1, "
" stop:0 rgba(82, 194, 242, 0.6), "
" stop:1 rgba(45, 120, 180, 0.6));"
" border-color: rgba(82, 194, 242, 0.8);"
" color: white;"
"}"
);
buttonLayout->addStretch();
buttonLayout->addWidget(deleteBtn);
buttonLayout->addWidget(cancelBtn);
layout->addLayout(buttonLayout);
// 连接信号
connect(deleteBtn, &QPushButton::clicked, [this, dialog, deviceTable, allDevices]() {
int selectedRow = deviceTable->currentRow();
if (selectedRow >= 0 && selectedRow < allDevices.size()) {
const DeviceInfo &selectedDevice = allDevices[selectedRow];
// 确认删除
QMessageBox confirmBox(dialog);
confirmBox.setWindowTitle("确认删除");
confirmBox.setText(QString("确定要删除设备 '%1' (%2) 吗?")
.arg(selectedDevice.name)
.arg(selectedDevice.id));
confirmBox.setInformativeText("此操作不可恢复!");
confirmBox.setStandardButtons(QMessageBox::Yes | QMessageBox::No);
confirmBox.setDefaultButton(QMessageBox::No);
confirmBox.setIcon(QMessageBox::Question);
// 设置确认对话框样式
confirmBox.setStyleSheet(
"QMessageBox {"
" background-color: rgb(240, 240, 240);"
" color: rgb(50, 50, 50);"
"}"
"QMessageBox QLabel {"
" color: rgb(50, 50, 50);"
" font-size: 14px;"
" background-color: transparent;"
"}"
"QMessageBox QPushButton {"
" background-color: rgb(225, 225, 225);"
" color: rgb(50, 50, 50);"
" border: 1px solid rgb(180, 180, 180);"
" border-radius: 4px;"
" padding: 8px 16px;"
" font-size: 14px;"
" min-width: 80px;"
"}"
"QMessageBox QPushButton:hover {"
" background-color: rgb(200, 200, 200);"
"}"
"QMessageBox QPushButton:pressed {"
" background-color: rgb(180, 180, 180);"
"}"
);
int reply = confirmBox.exec();
if (reply == QMessageBox::Yes) {
// 执行删除操作
if (deleteDeviceFromDatabase(selectedDevice.id)) {
QMessageBox successBox(dialog);
successBox.setWindowTitle("成功");
successBox.setText("设备删除成功!");
successBox.setIcon(QMessageBox::Information);
successBox.setStandardButtons(QMessageBox::Ok);
// 设置成功对话框样式
successBox.setStyleSheet(
"QMessageBox {"
" background-color: rgb(240, 240, 240);"
" color: rgb(50, 50, 50);"
"}"
"QMessageBox QLabel {"
" color: rgb(50, 50, 50);"
" font-size: 14px;"
" background-color: transparent;"
"}"
"QMessageBox QPushButton {"
" background-color: rgb(76, 175, 80);"
" color: white;"
" border: none;"
" border-radius: 4px;"
" padding: 8px 16px;"
" font-size: 14px;"
" min-width: 80px;"
" font-weight: bold;"
"}"
"QMessageBox QPushButton:hover {"
" background-color: rgb(67, 160, 71);"
"}"
"QMessageBox QPushButton:pressed {"
" background-color: rgb(56, 142, 60);"
"}"
);
successBox.exec();
// 刷新设备列表
refreshDeviceList();
dialog->accept();
} else {
QMessageBox errorBox(dialog);
errorBox.setWindowTitle("错误");
errorBox.setText("删除设备失败!");
errorBox.setIcon(QMessageBox::Warning);
errorBox.setStandardButtons(QMessageBox::Ok);
// 设置错误对话框样式
errorBox.setStyleSheet(
"QMessageBox {"
" background-color: rgb(240, 240, 240);"
" color: rgb(50, 50, 50);"
"}"
"QMessageBox QLabel {"
" color: rgb(50, 50, 50);"
" font-size: 14px;"
" background-color: transparent;"
"}"
"QMessageBox QPushButton {"
" background-color: rgb(244, 67, 54);"
" color: white;"
" border: none;"
" border-radius: 4px;"
" padding: 8px 16px;"
" font-size: 14px;"
" min-width: 80px;"
" font-weight: bold;"
"}"
"QMessageBox QPushButton:hover {"
" background-color: rgb(229, 57, 53);"
"}"
"QMessageBox QPushButton:pressed {"
" background-color: rgb(211, 47, 47);"
"}"
);
errorBox.exec();
}
}
} else {
QMessageBox warningBox(dialog);
warningBox.setWindowTitle("提示");
warningBox.setText("请先选择要删除的设备!");
warningBox.setIcon(QMessageBox::Information);
warningBox.setStandardButtons(QMessageBox::Ok);
// 设置提示对话框样式
warningBox.setStyleSheet(
"QMessageBox {"
" background-color: rgb(240, 240, 240);"
" color: rgb(50, 50, 50);"
"}"
"QMessageBox QLabel {"
" color: rgb(50, 50, 50);"
" font-size: 14px;"
" background-color: transparent;"
"}"
"QMessageBox QPushButton {"
" background-color: rgb(33, 150, 243);"
" color: white;"
" border: none;"
" border-radius: 4px;"
" padding: 8px 16px;"
" font-size: 14px;"
" min-width: 80px;"
" font-weight: bold;"
"}"
"QMessageBox QPushButton:hover {"
" background-color: rgb(30, 136, 229);"
"}"
"QMessageBox QPushButton:pressed {"
" background-color: rgb(25, 118, 210);"
"}"
);
warningBox.exec();
}
});
connect(cancelBtn, &QPushButton::clicked, dialog, &QDialog::reject);
// 显示对话框
dialog->exec();
delete dialog;
}
void DeviceListPanel::onDeviceCardSelected(const QString &deviceId)
{
// 清除之前的选择

@ -39,6 +39,8 @@
#include <QHeaderView>
#include <QQuickWidget>
#include <QTimer>
#include <QSpinBox>
#include <QDoubleSpinBox>
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
@ -298,17 +300,103 @@ void MainWindow::onAddRobotClicked()
{
QDialog *dialog = new QDialog(this);
dialog->setWindowTitle("添加机器人");
dialog->resize(400, 300);
dialog->resize(450, 400);
QVBoxLayout *layout = new QVBoxLayout();
// 添加输入字段
QFormLayout *formLayout = new QFormLayout();
QLineEdit *deviceIdEdit = new QLineEdit();
QLineEdit *nameEdit = new QLineEdit();
QLineEdit *ipEdit = new QLineEdit();
QSpinBox *portEdit = new QSpinBox();
QDoubleSpinBox *longitudeEdit = new QDoubleSpinBox();
QDoubleSpinBox *latitudeEdit = new QDoubleSpinBox();
// 设置端口号范围和默认值
portEdit->setRange(1000, 65535);
portEdit->setValue(9090);
// 从系统配置获取地图中心位置作为默认值
double defaultLongitude = 116.4; // 默认经度
double defaultLatitude = 39.9; // 默认纬度
// 尝试从数据库获取配置的地图中心位置
QSqlDatabase configDb = QSqlDatabase::addDatabase("QMYSQL", "TempConnection_Config_Robot");
configDb.setHostName("localhost");
configDb.setPort(3306);
configDb.setDatabaseName("Client");
configDb.setUserName("root");
configDb.setPassword("hzk200407140238");
if (configDb.open()) {
QSqlQuery configQuery(configDb);
// 获取默认中心经度
configQuery.prepare("SELECT config_value FROM system_config WHERE config_key = 'map.default_center_lon'");
if (configQuery.exec() && configQuery.next()) {
defaultLongitude = configQuery.value(0).toDouble();
}
// 获取默认中心纬度
configQuery.prepare("SELECT config_value FROM system_config WHERE config_key = 'map.default_center_lat'");
if (configQuery.exec() && configQuery.next()) {
defaultLatitude = configQuery.value(0).toDouble();
}
configDb.close();
}
QSqlDatabase::removeDatabase("TempConnection_Config_Robot");
// 设置经纬度范围和精度
longitudeEdit->setRange(-180.0, 180.0);
longitudeEdit->setDecimals(6);
longitudeEdit->setValue(defaultLongitude);
longitudeEdit->setSuffix("°E"); // 添加经度单位
longitudeEdit->setToolTip(QString("默认地图中心经度: %1°E").arg(defaultLongitude));
latitudeEdit->setRange(-90.0, 90.0);
latitudeEdit->setDecimals(6);
latitudeEdit->setValue(defaultLatitude);
latitudeEdit->setSuffix("°N"); // 添加纬度单位
latitudeEdit->setToolTip(QString("默认地图中心纬度: %1°N").arg(defaultLatitude));
// 自动生成设备ID
QSqlDatabase db = QSqlDatabase::addDatabase("QMYSQL", "TempConnection_DOG_ID_Add");
db.setHostName("localhost");
db.setPort(3306);
db.setDatabaseName("Client");
db.setUserName("root");
db.setPassword("hzk200407140238");
QString suggestedId = "DOG001";
if (db.open()) {
QSqlQuery query(db);
query.exec("SELECT COUNT(*) FROM devices WHERE device_type = 'dog'");
if (query.next()) {
int count = query.value(0).toInt();
suggestedId = QString("DOG%1").arg(count + 1, 3, 10, QChar('0'));
}
db.close();
}
QSqlDatabase::removeDatabase("TempConnection_DOG_ID_Add");
deviceIdEdit->setText(suggestedId);
// 设置输入框占位符和样式
deviceIdEdit->setStyleSheet("QLineEdit { color: #333; } QLineEdit:focus { border: 2px solid #52C2F2; }");
nameEdit->setPlaceholderText("请输入机器人名称");
nameEdit->setStyleSheet("QLineEdit { color: #333; } QLineEdit:focus { border: 2px solid #52C2F2; }");
ipEdit->setPlaceholderText("例如: 192.168.1.200");
ipEdit->setStyleSheet("QLineEdit { color: #333; } QLineEdit:focus { border: 2px solid #52C2F2; }");
// 为经纬度输入框设置样式
longitudeEdit->setStyleSheet("QDoubleSpinBox { color: #666; } QDoubleSpinBox:focus { border: 2px solid #52C2F2; }");
latitudeEdit->setStyleSheet("QDoubleSpinBox { color: #666; } QDoubleSpinBox:focus { border: 2px solid #52C2F2; }");
formLayout->addRow("设备ID:", deviceIdEdit);
formLayout->addRow("机器人名称:", nameEdit);
formLayout->addRow("IP地址:", ipEdit);
formLayout->addRow("端口号:", portEdit);
formLayout->addRow("经度 (地图中心):", longitudeEdit);
formLayout->addRow("纬度 (地图中心):", latitudeEdit);
layout->addLayout(formLayout);
@ -321,13 +409,17 @@ void MainWindow::onAddRobotClicked()
buttonLayout->addWidget(cancelBtn);
layout->addLayout(buttonLayout);
connect(confirmBtn, &QPushButton::clicked, [this, dialog, nameEdit, ipEdit]() {
connect(confirmBtn, &QPushButton::clicked, [this, dialog, deviceIdEdit, nameEdit, ipEdit, portEdit, longitudeEdit, latitudeEdit]() {
QString deviceId = deviceIdEdit->text().trimmed();
QString name = nameEdit->text().trimmed();
QString ip = ipEdit->text().trimmed();
int port = portEdit->value();
double longitude = longitudeEdit->value();
double latitude = latitudeEdit->value();
if (!name.isEmpty() && !ip.isEmpty()) {
// 保存到数据库
if (addDeviceToDatabase(name, "dog", ip, 9090, 0)) {
if (!deviceId.isEmpty() && !name.isEmpty() && !ip.isEmpty()) {
// 保存到数据库设备状态默认为0离线
if (addDeviceToDatabase(deviceId, name, "dog", ip, port, 0, longitude, latitude)) {
m_robotList.append(qMakePair(name, ip));
QMessageBox::information(this, "成功", "机器人添加成功!");
@ -395,17 +487,103 @@ void MainWindow::onAddUAVClicked()
{
QDialog *dialog = new QDialog(this);
dialog->setWindowTitle("添加无人机");
dialog->resize(400, 300);
dialog->resize(450, 400);
QVBoxLayout *layout = new QVBoxLayout();
// 添加输入字段
QFormLayout *formLayout = new QFormLayout();
QLineEdit *deviceIdEdit = new QLineEdit();
QLineEdit *nameEdit = new QLineEdit();
QLineEdit *ipEdit = new QLineEdit();
QSpinBox *portEdit = new QSpinBox();
QDoubleSpinBox *longitudeEdit = new QDoubleSpinBox();
QDoubleSpinBox *latitudeEdit = new QDoubleSpinBox();
// 设置端口号范围和默认值
portEdit->setRange(1000, 65535);
portEdit->setValue(8080);
// 从系统配置获取地图中心位置作为默认值
double defaultLongitude = 116.4; // 默认经度
double defaultLatitude = 39.9; // 默认纬度
// 尝试从数据库获取配置的地图中心位置
QSqlDatabase configDb = QSqlDatabase::addDatabase("QMYSQL", "TempConnection_Config");
configDb.setHostName("localhost");
configDb.setPort(3306);
configDb.setDatabaseName("Client");
configDb.setUserName("root");
configDb.setPassword("hzk200407140238");
if (configDb.open()) {
QSqlQuery configQuery(configDb);
// 获取默认中心经度
configQuery.prepare("SELECT config_value FROM system_config WHERE config_key = 'map.default_center_lon'");
if (configQuery.exec() && configQuery.next()) {
defaultLongitude = configQuery.value(0).toDouble();
}
// 获取默认中心纬度
configQuery.prepare("SELECT config_value FROM system_config WHERE config_key = 'map.default_center_lat'");
if (configQuery.exec() && configQuery.next()) {
defaultLatitude = configQuery.value(0).toDouble();
}
configDb.close();
}
QSqlDatabase::removeDatabase("TempConnection_Config");
// 设置经纬度范围和精度
longitudeEdit->setRange(-180.0, 180.0);
longitudeEdit->setDecimals(6);
longitudeEdit->setValue(defaultLongitude);
longitudeEdit->setSuffix("°E"); // 添加经度单位
longitudeEdit->setToolTip(QString("默认地图中心经度: %1°E").arg(defaultLongitude));
latitudeEdit->setRange(-90.0, 90.0);
latitudeEdit->setDecimals(6);
latitudeEdit->setValue(defaultLatitude);
latitudeEdit->setSuffix("°N"); // 添加纬度单位
latitudeEdit->setToolTip(QString("默认地图中心纬度: %1°N").arg(defaultLatitude));
// 自动生成设备ID
QSqlDatabase db = QSqlDatabase::addDatabase("QMYSQL", "TempConnection_UAV_ID");
db.setHostName("localhost");
db.setPort(3306);
db.setDatabaseName("Client");
db.setUserName("root");
db.setPassword("hzk200407140238");
QString suggestedId = "UAV001";
if (db.open()) {
QSqlQuery query(db);
query.exec("SELECT COUNT(*) FROM devices WHERE device_type = 'uav'");
if (query.next()) {
int count = query.value(0).toInt();
suggestedId = QString("UAV%1").arg(count + 1, 3, 10, QChar('0'));
}
db.close();
}
QSqlDatabase::removeDatabase("TempConnection_UAV_ID");
deviceIdEdit->setText(suggestedId);
// 设置输入框占位符和样式
deviceIdEdit->setStyleSheet("QLineEdit { color: #333; } QLineEdit:focus { border: 2px solid #52C2F2; }");
nameEdit->setPlaceholderText("请输入无人机名称");
nameEdit->setStyleSheet("QLineEdit { color: #333; } QLineEdit:focus { border: 2px solid #52C2F2; }");
ipEdit->setPlaceholderText("例如: 192.168.1.100");
ipEdit->setStyleSheet("QLineEdit { color: #333; } QLineEdit:focus { border: 2px solid #52C2F2; }");
// 为经纬度输入框设置样式
longitudeEdit->setStyleSheet("QDoubleSpinBox { color: #666; } QDoubleSpinBox:focus { border: 2px solid #52C2F2; }");
latitudeEdit->setStyleSheet("QDoubleSpinBox { color: #666; } QDoubleSpinBox:focus { border: 2px solid #52C2F2; }");
formLayout->addRow("设备ID:", deviceIdEdit);
formLayout->addRow("无人机名称:", nameEdit);
formLayout->addRow("IP地址:", ipEdit);
formLayout->addRow("端口号:", portEdit);
formLayout->addRow("经度 (地图中心):", longitudeEdit);
formLayout->addRow("纬度 (地图中心):", latitudeEdit);
layout->addLayout(formLayout);
@ -418,13 +596,17 @@ void MainWindow::onAddUAVClicked()
buttonLayout->addWidget(cancelBtn);
layout->addLayout(buttonLayout);
connect(confirmBtn, &QPushButton::clicked, [this, dialog, nameEdit, ipEdit]() {
connect(confirmBtn, &QPushButton::clicked, [this, dialog, deviceIdEdit, nameEdit, ipEdit, portEdit, longitudeEdit, latitudeEdit]() {
QString deviceId = deviceIdEdit->text().trimmed();
QString name = nameEdit->text().trimmed();
QString ip = ipEdit->text().trimmed();
int port = portEdit->value();
double longitude = longitudeEdit->value();
double latitude = latitudeEdit->value();
if (!name.isEmpty() && !ip.isEmpty()) {
// 保存到数据库
if (addDeviceToDatabase(name, "uav", ip, 8080, 0)) {
if (!deviceId.isEmpty() && !name.isEmpty() && !ip.isEmpty()) {
// 保存到数据库设备状态默认为0离线
if (addDeviceToDatabase(deviceId, name, "uav", ip, port, 0, longitude, latitude)) {
m_uavList.append(qMakePair(name, ip));
QMessageBox::information(this, "成功", "无人机添加成功!");
@ -713,7 +895,7 @@ void MainWindow::initializeDeviceMarkersOnMap()
}
}
bool MainWindow::addDeviceToDatabase(const QString &name, const QString &type, const QString &ip, int port, int state)
bool MainWindow::addDeviceToDatabase(const QString &deviceId, const QString &name, const QString &type, const QString &ip, int port, int state, double longitude, double latitude)
{
QSqlDatabase db = QSqlDatabase::addDatabase("QMYSQL", "MainWindow_AddDevice_Connection");
db.setHostName("localhost");
@ -729,43 +911,40 @@ bool MainWindow::addDeviceToDatabase(const QString &name, const QString &type, c
QSqlQuery query(db);
// 生成唯一ID
QString deviceId;
if (type == "uav") {
// 查找现有UAV数量来生成ID
query.exec("SELECT COUNT(*) FROM devices WHERE device_type = 'uav'");
int count = 0;
if (query.next()) {
count = query.value(0).toInt();
}
deviceId = QString("UAV%1").arg(count + 1, 3, 10, QChar('0')); // UAV001, UAV002...
} else if (type == "dog") {
// 查找现有DOG数量来生成ID
query.exec("SELECT COUNT(*) FROM devices WHERE device_type = 'dog'");
int count = 0;
if (query.next()) {
count = query.value(0).toInt();
}
deviceId = QString("DOG%1").arg(count + 1, 3, 10, QChar('0')); // DOG001, DOG002...
// 检查设备ID是否已存在
query.prepare("SELECT COUNT(*) FROM devices WHERE id = ?");
query.addBindValue(deviceId);
if (!query.exec() || !query.next()) {
qWarning() << "Failed to check device ID uniqueness:" << query.lastError().text();
db.close();
return false;
}
if (query.value(0).toInt() > 0) {
qWarning() << "Device ID already exists:" << deviceId;
db.close();
return false;
}
// 插入新设备
QString sql = "INSERT INTO devices (id, name, device_type, state, ip, port, longitude, latitude, signal_strength, battery_level) "
"VALUES (?, ?, ?, ?, ?, ?, 0.0, 0.0, 0, 100)";
"VALUES (?, ?, ?, ?, ?, ?, ?, ?, 0, 100)";
query.prepare(sql);
query.addBindValue(deviceId);
query.addBindValue(name);
query.addBindValue(type);
query.addBindValue(state); // 默认状态为0离线
query.addBindValue(state);
query.addBindValue(ip);
query.addBindValue(port);
query.addBindValue(longitude);
query.addBindValue(latitude);
bool success = query.exec();
if (!success) {
qWarning() << "Failed to insert device into database:" << query.lastError().text();
} else {
qDebug() << "Successfully added device to database:" << deviceId << name;
qDebug() << "Successfully added device to database:" << deviceId << name << "at" << latitude << "," << longitude;
}
db.close();

Loading…
Cancel
Save