2016-10-19 7 views
1

Итак, я пытаюсь скопировать выделенный элемент из одного QListWidget в другой с помощью перетаскивания.Как получить элемент, созданный из dropEvent, в qlistwidget

В любом случае, я мог бы взломать все, что мне нужно, передавая сериализованные параметры, используя item.setData, но я не могу найти прямой способ получить дескриптор нового элемента, созданного во втором listWidget.

Я думаю, что я мог бы просмотреть все элементы во втором QListWidget и каким-то образом определить, какой из них был только что создан, но кажется, что должен быть более простой способ узнать, какой элемент создается событием drop.

import sys 
from PyQt4 import QtGui , QtCore 


def main(): 

    app = QtGui.QApplication(sys.argv) 

    w = QtGui.QWidget() 
    w.resize(250, 150) 
    w.move(300, 300) 
    w.setWindowTitle('Simple') 
    layout=QtGui.QHBoxLayout(w) 
    dragList=DragDropListWidget() 
    layout.addWidget(dragList) 
    dragList.setDragDropMode(QtGui.QAbstractItemView.InternalMove) 
    dragList.name='dragList' 
    dragList.populate(['one','two','three']) 
    dragList2=DragDropListWidget() 
    dragList2.setDragDropMode(QtGui.QAbstractItemView.DragDrop) 
    dragList2.name='dragList' 


    layout.addWidget(dragList2) 
    w.show() 

    sys.exit(app.exec_()) 

class scriptsWidget(QtGui.QWidget): 


    def __init__(self, parent=None): 
     QtGui.QWidget.__init__(self) 

     self.name='' 

     self.widget_QHBoxLayout = QtGui.QHBoxLayout(self) 
     self.widget_QHBoxLayout.setSpacing(0) 
     self.widget_QHBoxLayout.setContentsMargins(0, 0, 0, 0) 

     self.name_QLabel = QtGui.QLabel(self) 
     self.widget_QHBoxLayout.addWidget(self.name_QLabel) 

     self.user_QLabel = QtGui.QLabel(self) 
     self.widget_QHBoxLayout.addWidget(self.user_QLabel) 

     self.widget_QHBoxLayout.setSpacing(0) 
     self.widget_QHBoxLayout.setContentsMargins(0, 0, 0, 0) 



    def setName(self,name): 
     self.name_QLabel.setText(name) 
     self.name=name 

    def setUser(self,user): 
     self.user_QLabel.setText(user) 

class customQListWidgetItem(QtGui.QListWidgetItem): 


    def __init__(self, parent=None): 
     QtGui.QWidget.__init__(self) 
     self.name='' 

    def setName(self,name): 
     self.name=name 




class DragDropListWidget(QtGui.QListWidget): 
    _drag_info = [] 
    def __init__(self, parent = None): 

     super(DragDropListWidget, self).__init__(parent) 


     self.name='' 


    def dragMoveEvent(self, event): 
     if event.mimeData().hasUrls(): 
      event.setDropAction(QtCore.Qt.CopyAction) 
      event.accept() 

     else: 
      super(DragDropListWidget, self).dragMoveEvent(event) 


    def dropEvent(self, event): 
     print('dropEvent') 
     print event.mimeData().text() 

     if event.mimeData().hasText(): 
      print event.mimeData().text() 
      event.setDropAction(QtCore.Qt.CopyAction) 
      event.accept() 
      links = [] 
      for url in event.mimeData().urls(): 
       links.append(str(url.toLocalFile())) 
      self.emit(QtCore.SIGNAL("dropped"), links) 

     else: 
      event.setDropAction(QtCore.Qt.CopyAction) 
      super(DragDropListWidget, self).dropEvent(event) 
      items = [] 
      for index in xrange(self.count()): 
       items.append(self.item(index)) 
       print self.item(index).data(QtCore.Qt.UserRole).toPyObject() 



    def populate(self,items=[]): 
     self.clear() 
     for i in items: 
      print(i) 
      widget = scriptsWidget() 
      widget.setName(i) 
      widget.setUser('x') 
      item = customQListWidgetItem() 
      item.setName(i) 
      data = (i) 
      item.setData(QtCore.Qt.UserRole, data) 
      self.addItem(item) 
      self.setItemWidget(item,widget) 



if __name__ == '__main__': 
    main() 

ответ

0

Интересно .. а мое решение в конечном итоге в том, чтобы сохранить список элементов во втором listwidget до и затем сделать сравнение после добавления нового элемента, который работает достаточно хорошо и занимает всего несколько строк кода. Затем я перехожу новый элемент в функцию, которая создает объект, используя одни и те же классы, которые были использованы при его создании в первом listwidget и я передал сериализованную информацию о в .data (QtCore.Qt.UserRole)

def dropEvent(self, event): 
    if event.mimeData().hasText(): 
     event.setDropAction(QtCore.Qt.CopyAction) 
     event.accept() 
     links = [] 
     for url in event.mimeData().urls(): 
      links.append(str(url.toLocalFile())) 
     self.emit(QtCore.SIGNAL("dropped"), links) 

    else: 
     event.setDropAction(QtCore.Qt.CopyAction) 
     items = [] 
     for index in xrange(self.count()): 
      items.append(self.item(index)) 

     super(DragDropListWidget, self).dropEvent(event) 

     for index in xrange(self.count()): 
      if self.item(index) not in items: 
       self.populateDrop(self.item(index), index, [self.item(index).data(QtCore.Qt.UserRole).toPyObject()]) 

def populateDrop(self,item,row,items=[]): 
    for i in items: 
     widget = scriptsWidget() 
     widget.setName(i) 
     widget.setUser('x') 
     self.takeItem(row) 
     item = customQListWidgetItem() 
     item.setName(i) 
     item.setWhatsThis(i) 
     data = (i) 
     item.setData(QtCore.Qt.UserRole, data) 
     self.insertItem (row, item) 
     self.setItemWidget(item,widget) 
0

Вы можете подключиться к rowsInserted сигнала на модели списке следует

class DragDropListWidget(...): 

    def __init__(...): 
     ... 
     self._dropping = False 
     self.model().rowsInserted.connect(self.on_rowsInserted) 

    def on_rowsInserted(self, parent_index, start, end): 
     if self._dropping: 
      # Recently dropped items 
      items = [self.item(i) for i in range(start, end + 1)] 

    def dropEvent(self, event): 
     self._dropping = True 
     # code that drops the new rows 
     ... 
     self._dropping = False 
+0

Я проверил это, прежде чем я действительно не помог. Мне все равно нужно сравнить список до и после капли, чтобы узнать, что индекс относится к новому элементу. – obfuscated

+0

@obfuscated Обратный вызов 'on_rowsInserted' должен запускаться только для новых элементов. –

+0

Это может быть так, но другая проблема в том, что если элемент, созданный в том же списке, мне нужно переместить элемент вместо его копирования (я хочу скопировать элемент, если он возник из другого списка). – obfuscated

Смежные вопросы