""" 命令片段管理对话框 """ from PyQt5.QtCore import Qt from PyQt5.QtWidgets import ( QDialog, QVBoxLayout, QHBoxLayout, QTableWidget, QTableWidgetItem, QPushButton, QLabel, QLineEdit, QTextEdit, QMessageBox, QHeaderView, QAbstractItemView, QSplitter, QWidget, QFormLayout, ) from core.snippets import SnippetManager class SnippetDialog(QDialog): """单个片段的编辑/新增对话框""" def __init__(self, parent=None, name: str = "", cmd: str = ""): super().__init__(parent) self.setWindowTitle("编辑片段" if name else "新增片段") self.setMinimumWidth(460) v = QVBoxLayout(self) form = QFormLayout() self.name_edit = QLineEdit(name) self.name_edit.setPlaceholderText("如:查看端口占用") form.addRow("名称:", self.name_edit) self.cmd_edit = QTextEdit(cmd) self.cmd_edit.setPlaceholderText("如:ss -tlnp | grep :80") self.cmd_edit.setMaximumHeight(80) form.addRow("命令:", self.cmd_edit) v.addLayout(form) btns = QHBoxLayout() btns.addStretch(1) ok = QPushButton("保存") ok.clicked.connect(self._on_ok) cancel = QPushButton("取消") cancel.clicked.connect(self.reject) btns.addWidget(ok) btns.addWidget(cancel) v.addLayout(btns) def _on_ok(self): if not self.name_edit.text().strip(): QMessageBox.warning(self, "提示", "请输入名称") return if not self.cmd_edit.toPlainText().strip(): QMessageBox.warning(self, "提示", "请输入命令") return self.accept() def get_value(self) -> dict: return { "name": self.name_edit.text().strip(), "cmd": self.cmd_edit.toPlainText().strip(), } class SnippetManagerDialog(QDialog): """片段管理主对话框:表格 + 增删改 + 上下移""" def __init__(self, mgr: SnippetManager, parent=None): super().__init__(parent) self.mgr = mgr self.setWindowTitle("命令片段管理") self.setMinimumSize(520, 420) self._build_ui() self._refresh_table() def _build_ui(self): v = QVBoxLayout(self) # 工具栏 toolbar = QHBoxLayout() toolbar.addWidget(QLabel("📋 命令片段列表")) toolbar.addStretch(1) self.btn_add = QPushButton("➕ 新增") self.btn_add.clicked.connect(self._add) self.btn_edit = QPushButton("✏ 编辑") self.btn_edit.clicked.connect(self._edit) self.btn_del = QPushButton("🗑 删除") self.btn_del.clicked.connect(self._delete) self.btn_up = QPushButton("⬆ 上移") self.btn_up.clicked.connect(lambda: self._move(-1)) self.btn_down = QPushButton("⬇ 下移") self.btn_down.clicked.connect(lambda: self._move(1)) for b in (self.btn_add, self.btn_edit, self.btn_del, self.btn_up, self.btn_down): toolbar.addWidget(b) v.addLayout(toolbar) # 表格 self.table = QTableWidget(0, 2) self.table.setHorizontalHeaderLabels(["名称", "命令"]) self.table.horizontalHeader().setSectionResizeMode(0, QHeaderView.ResizeToContents) self.table.horizontalHeader().setSectionResizeMode(1, QHeaderView.Stretch) self.table.setSelectionBehavior(QAbstractItemView.SelectRows) self.table.setEditTriggers(QAbstractItemView.NoEditTriggers) self.table.doubleClicked.connect(self._edit) v.addWidget(self.table) # 关闭按钮 btns = QHBoxLayout() btns.addStretch(1) close = QPushButton("关闭") close.clicked.connect(self.accept) btns.addWidget(close) v.addLayout(btns) def _refresh_table(self): snippets = self.mgr.list_all() self.table.setRowCount(len(snippets)) for i, s in enumerate(snippets): self.table.setItem(i, 0, QTableWidgetItem(s["name"])) cmd_display = s["cmd"][:60] + ("..." if len(s["cmd"]) > 60 else "") self.table.setItem(i, 1, QTableWidgetItem(cmd_display)) self.table.item(i, 0).setToolTip(s["cmd"]) def _add(self): dlg = SnippetDialog(self) if dlg.exec_() == dlg.Accepted: v = dlg.get_value() self.mgr.add(v["name"], v["cmd"]) self._refresh_table() def _edit(self): row = self.table.currentRow() if row < 0: return s = self.mgr.list_all()[row] dlg = SnippetDialog(self, s["name"], s["cmd"]) if dlg.exec_() == dlg.Accepted: v = dlg.get_value() self.mgr.update(row, v["name"], v["cmd"]) self._refresh_table() def _delete(self): row = self.table.currentRow() if row < 0: return s = self.mgr.list_all()[row] if QMessageBox.question( self, "确认删除", f"删除片段「{s['name']}」?", QMessageBox.Yes | QMessageBox.No ) == QMessageBox.Yes: self.mgr.remove(row) self._refresh_table() def _move(self, direction): row = self.table.currentRow() if row < 0: return self.mgr.move(row, direction) new_row = row + direction self._refresh_table() if 0 <= new_row < self.table.rowCount(): self.table.selectRow(new_row)