如何使用列表迭代添加带有删除按钮的 qlabels,可以删除它们

问题描述

这里有很多关于使用 QButton 创建 QLabels 以删除它们的问题。但是,没有任何关于如何使用字符串列表迭代创建这些标签并将删除按钮附加到它们的内容。

我已经用下面的代码试过了。它生成一个 lineEdit,您可以将多个文件放入其中,它将生成这些文件的列表,它将迭代地转换为标签和相应的删除按钮。但是,它可以工作,但是,当我按下每个标签上的删除按钮时,我得到“运行时错误:QLabel 类型的包装 C/C++ 对象已被删除”。我想那是因为我已经设法创建了标签列表,但删除按钮仅附加到其中一个标签上。

请参阅下面的代码:

import sys
from PyQt5 import QtCore,QtGui,QtWidgets,uic
from PyQt5.QtCore import Qt
from PyQt5.QtWidgets import QLineEdit,QLabel,QApplication,QWidget,QPushButton,QMainWindow,QHBoxLayout,QVBoxLayout


global search_list
search_list = []

class LocationDrag(QLineEdit):

    def __init__(self,*args,**kwargs):
        QLineEdit.__init__(self,**kwargs)
    
    
        self.setAcceptDrops(True)

    def dragEnterEvent(self,event):
        print(event)
        if event.mimeData().hasText():
            event.accept()
        else:
            event.ignore()

    def dragMoveEvent(self,event):
        if event.mimeData().hasText():
            event.accept()
        else:
            event.ignore()
                
    def dropEvent(self,event):
        if event.mimeData().hasText():
            event.setDropAction(Qt.CopyAction)
            
            dragged_files = event.mimeData().urls()
            dragged_files_paths = [url.toLocalFile() for url in event.mimeData().urls()]
            
            global search_list
            search_list.extend(dragged_files_paths)
            for item in search_list:
                name = QtWidgets.QLabel(item)
                name.setStyleSheet('QLabel{ width:90; height:30; background-color: rgb(27,29,35); border-radius: 5px; border: 2px solid rgb(27,35); padding: 5px;}')

                deletebutton = QtWidgets.QPushButton("x")
                deletebutton.setStyleSheet('QPushButton {color: red; font-weight:bold; padding:5px}')

                deletebutton.clicked.connect(lambda:delete_location(self,(name,deletebutton),item))

                demo.mainLayout.addWidget(name,alignment=QtCore.Qt.AlignLeft)
                demo.mainLayout.addWidget(deletebutton)
                    
        

def delete_location(self,widgets,search_item):
    if search_list:
        name,deletebutton = widgets
        name.deleteLater()
        deletebutton.deleteLater()
        search_list.remove(search_item)
        

class AppDemo(QWidget):
    def __init__(self):
        super().__init__()
        self.resize(400,400)
        self.setAcceptDrops(True)
 
        self.mainLayout = QVBoxLayout()

        self.lineEdit_2 = LocationDrag()
        self.lineEdit_2.setGeometry(10,35,350,30)
        self.lineEdit_2.setStyleSheet("QLineEdit {\n"
        "    background-color: rgb(27,35);\n"
        "    border-radius: 5px;\n"
        "    border: 2px solid rgb(27,35);\n"
        "    padding-left: 10px;\n"
        "}\n"
        "QLineEdit:hover {\n"
        "    border: 2px solid rgb(64,71,88);\n"
        "}\n"
        "QLineEdit:focus {\n"
        "    border: 2px solid rgb(91,101,124);\n"
        "}")

        self.mainLayout.addWidget(self.lineEdit_2)
        self.setLayout(self.mainLayout)
 
app = QApplication(sys.argv)
demo = AppDemo()
demo.show()
sys.exit(app.exec_())

解决方法

您变得太复杂了,因为您将许多任务留给了几个类,例如 LocationDrag 应该只获取路线,而不应该将其添加到窗口中。另一方面,最好创建一个代表 QLabel + QPushButton 行的小部件,然后每次按下按钮时,该行小部件都会被消除,这种消除意味着它将从布局中移除。

import sys
from PyQt5.QtCore import pyqtSignal,Qt
from PyQt5.QtWidgets import (
    QLineEdit,QLabel,QApplication,QWidget,QPushButton,QMainWindow,QHBoxLayout,QVBoxLayout,)


class LocationDrag(QLineEdit):
    filesChanged = pyqtSignal(list)

    def __init__(self,*args,**kwargs):
        QLineEdit.__init__(self,**kwargs)
        self.setAcceptDrops(True)

    def dragEnterEvent(self,event):
        if event.mimeData().hasText():
            event.accept()
        else:
            event.ignore()

    def dragMoveEvent(self,event):
        if event.mimeData().hasText():
            event.accept()
        else:
            event.ignore()

    def dropEvent(self,event):
        if event.mimeData().hasText():
            event.setDropAction(Qt.CopyAction)
            files = []
            for url in event.mimeData().urls():
                if url.isLocalFile():
                    files.append(url.toLocalFile())
            if files:
                self.filesChanged.emit(files)


class RowWidget(QWidget):
    def __init__(self,name,parent=None):
        super().__init__(parent)
        nameLabel = QLabel(name)
        nameLabel.setStyleSheet(
            "QLabel{background-color: rgb(27,29,35); border-radius: 5px; border: 2px solid rgb(27,35); padding: 5px;}"
        )
        deletebutton = QPushButton("x")
        deletebutton.setStyleSheet(
            "QPushButton {color: red; font-weight:bold; padding:5px}"
        )

        lay = QVBoxLayout(self)
        lay.addWidget(nameLabel,alignment=Qt.AlignLeft)
        lay.addWidget(deletebutton)
        self.setContentsMargins(0,0)

        deletebutton.clicked.connect(self.deleteLater)


class AppDemo(QWidget):
    def __init__(self):
        super().__init__()
        self.resize(400,400)
        self.setAcceptDrops(True)

        self.mainLayout = QVBoxLayout(self)

        self.lineEdit = LocationDrag()
        self.lineEdit.setStyleSheet(
            "QLineEdit {"
            "    background-color: rgb(27,35);"
            "    border-radius: 5px;"
            "    border: 2px solid rgb(27,35);"
            "    padding-left: 10px;"
            "}"
            "QLineEdit:hover {"
            "    border: 2px solid rgb(64,71,88);"
            "}"
            "QLineEdit:focus {"
            "    border: 2px solid rgb(91,101,124);"
            "}"
        )

        self.mainLayout.addWidget(self.lineEdit,alignment=Qt.AlignTop)
        self.lineEdit.filesChanged.connect(self.handle_files_changed)

    def handle_files_changed(self,files):
        for file in files:
            rowWidget = RowWidget(file)
            self.mainLayout.addWidget(rowWidget,alignment=Qt.AlignTop)


app = QApplication(sys.argv)
demo = AppDemo()
demo.show()
sys.exit(app.exec_())

相关问答

依赖报错 idea导入项目后依赖报错,解决方案:https://blog....
错误1:代码生成器依赖和mybatis依赖冲突 启动项目时报错如下...
错误1:gradle项目控制台输出为乱码 # 解决方案:https://bl...
错误还原:在查询的过程中,传入的workType为0时,该条件不起...
报错如下,gcc版本太低 ^ server.c:5346:31: 错误:‘struct...