Reputation: 25
I'm trying to figure out how to pass values between a list widget and a line edit widget using PySide2. I have a dictionary with three keys and a list with the same values as the three dictionary keys. When the user clicks on the value in the list box I want it to return the value from the dictionary key value pair. I'm able to retrieve the value from the dictionary if I manually enter the key in the code but I can't get it to accept the value from the list widget. Here's the code I'm trying to use:
import sys
from PySide2.QtGui import *
from PySide2.QtCore import *
from PySide2.QtWidgets import QLineEdit, QApplication, QMessageBox, QListWidget
from PySide2 import QtWidgets
item_dict = {1: "First Item",
2: "Second Item",
3: "Third Item"}
item_list = [1,2,3]
class myListWidget(QListWidget):
def Clicked(self,item):
click_id = self.item.text()
class myTextWidget(QLineEdit):
def change_text(self):
click_id = myListWidget.Clicked
self.setText = item_dict[click_id]
def main():
app = QApplication(sys.argv)
window = QtWidgets.QWidget()
layout = QtWidgets.QVBoxLayout(window)
listWidget = myListWidget()
for i in item_dict:
listWidget.addItem(str(i))
TextWidget = myTextWidget()
#listWidget.itemClicked.connect(listWidget.Clicked)
listWidget.itemClicked.connect(myTextWidget.change_text)
layout.addWidget(listWidget)
layout.addWidget(TextWidget)
window.show()
sys.exit(app.exec_())
if __name__ == '__main__':
main()
When I click in the list widget I get the following error:
Traceback (most recent call last):
File "C:\Users\Mythranor\Desktop\VN Builder\PyQtTut\listview2.py", line 21, in change_text
self.setText = item_dict[click_id]
KeyError: <function myListWidget.Clicked at 0x000002B6286A8F78>
I have also tried calling the listWidget.item.text directly within the change_text function but it says the listWidget variable is not recognized within the class.
Upvotes: 1
Views: 610
Reputation: 244301
Your code has many inconsistencies, for example:
def Clicked(self,item):
click_id = self.item.text()
I presume that this method must return the text of the item but that function does not return anything, so even if it is invoked correctly you will always get None.
class myTextWidget(QLineEdit):
def change_text(self):
click_id = myListWidget.Clicked
self.setText = item_dict[click_id]
You try to use myListWidget.Clicked but this will never work because to use a method you need an object besides that to invoke a function you must use parentheses and pass arguments if necessary.
From the above I presume that you do not have your knowledge of OOP entrenched, so it is recommended that you review your notes on that subject since Qt uses them intensively.
Therefore, the code will have to be rewritten. When you add items to the QListWidget you are converting to string and when you retrieve it it will also be a string so it cannot be used to access the associated value of the dictionary, so to avoid that conversion you can use the Qt::DisplayRole role directly so will show the numbers and the values will be retrieved as a number. On the other hand, never assume that everything works correctly but you have to verify, for example instead of using "[]" you can use "get()", in the first case if the key does not exist an exception will be thrown and in the Second, None or a default value will be returned. Considering the above, the solution is as follows:
import sys
from PySide2 import QtCore, QtGui, QtWidgets
item_dict = {1: "First Item", 2: "Second Item", 3: "Third Item"}
item_list = [1, 2, 3]
class Widget(QtWidgets.QWidget):
def __init__(self, parent=None):
super(Widget, self).__init__(parent)
self.listwidget = QtWidgets.QListWidget()
self.lineedit = QtWidgets.QLineEdit()
lay = QtWidgets.QVBoxLayout(self)
lay.addWidget(self.listwidget)
lay.addWidget(self.lineedit)
for e in item_list:
it = QtWidgets.QListWidgetItem()
it.setData(QtCore.Qt.DisplayRole, e)
self.listwidget.addItem(it)
self.listwidget.itemClicked.connect(self.on_item_clicked)
@QtCore.Slot(QtWidgets.QListWidgetItem)
def on_item_clicked(self, item):
key = item.data(QtCore.Qt.DisplayRole)
value = item_dict.get(key)
if value is not None:
self.lineedit.setText(value)
def main():
app = QtWidgets.QApplication(sys.argv)
window = Widget()
window.show()
sys.exit(app.exec_())
if __name__ == "__main__":
main()
Upvotes: 1