0

I am creating Vocabulary, a GUI program to manage unknown words. I am getting:

/usr/bin/python3.5 /home/cali/PycharmProjects/Vocabulary/Vocabulary.py Exception in Tkinter callback Traceback (most recent call last):
File "/usr/lib/python3.5/tkinter/init.py", line 1553, in call return self.func(*args) File "/home/cali/PycharmProjects/Vocabulary/Vocabulary.py", line 86, in add_item self.listBox.insert(END, self.get_word()) AttributeError: 'Vocabulary' object has no attribute 'listBox'

Process finished with exit code 0

... when I try to add an item to the listbox.

Here is what I have done:

#!/usr/bin/env python

# Vocabulary.py
#   GUI program to manage unknown words

from tkinter import *

class Word:

    def __init__(self, wordorphrase, explanation, translation, example):
        self.wordorphrase = wordorphrase
        self.explanation = explanation
        self.translation = translation
        self.example = example

class Vocabulary(Frame):

    def __init__(self, master):
        Frame.__init__(self, master)
        self.master = master
        self.master.resizable(width = False, height = False)
        self.master.title("Vocabulary")
        self.create_widgets()

    def create_widgets(self):

        lblWordsOrPhrases = Label(self.master, text = 'Words or Phrases:')
        lblWordsOrPhrases.grid(row = 0, column = 0)

        lblWordOrPhrase = Label(self.master, text = 'Word or phrase:')
        lblWordOrPhrase.grid(row = 0, column = 1, sticky = W)

        listBox = Listbox(self.master,
                          height = 34,
                          width = 30)
        listBox.grid(row = 1, column = 0, rowspan = 7)

        txt_WordOrPhrase = Text(self.master,
                                height = 1,
                                width = 40)
        txt_WordOrPhrase.grid(row = 1, column = 1, sticky = N)

        lblExplanation = Label(self.master, text = 'Explanation:')
        lblExplanation.grid(row = 2, column = 1, sticky = W)

        txt_Explanation = Text(self.master,
                               height = 10,
                               width = 40)
        txt_Explanation.grid(row = 3, column = 1, sticky = N)

        lblTranslation = Label(self.master, text = 'Translation:')
        lblTranslation.grid(row = 4, column = 1, sticky = W)

        txt_Explanation = Text(self.master,
                               height = 10,
                               width = 40)
        txt_Explanation.grid(row = 5, column = 1, sticky = N)


        lblExamples = Label(self.master, text = 'Example(s):')
        lblExamples.grid(row = 6, column = 1, sticky = W)

        txt_Explanation = Text(self.master,
                               height = 10,
                               width = 40)
        txt_Explanation.grid(row = 7, column = 1, sticky = S)

        btn_Add = Button(self.master,
                         text = 'Add',
                         command = self.add_item)
        btn_Add.grid(row = 8, column = 0, sticky = W)

    def get_word(self):
        return self.txt_WordOrPhrase.get('1.0', '1.0 lineend')

    def get_explanation(self):
        return self.txt_Explanation.get('1.0', '1.0 lineend')

    def get_translation(self):
        return self.txt_Translation.get('1.0', '1.0 lineend')

    def get_example(self):
        return self.txt_Example.get('1.0', '1.0 lineend')

    def add_item(self):
        self.listBox.insert(END, self.get_word())

def main():
    root = Tk()
    Vocabulary(root)
    root.mainloop()

if __name__ == '__main__':
    main()

I'm using Python 3.5.

1 Answers1

2

You listbox is a variable local to create_widgets since it is not set with self. In order to make the variable available instance-wide, you need to contain it in self.

Change the line in create_widgets to self.listBox = Listbox(self.master, height = 34, width = 30) and change every reference to listBox to self.listBox in order to apply this change.

You might want to defined self.listBox in __init__(), as it might help keep track of instance variables.

Ziyad Edher
  • 2,150
  • 18
  • 31
  • Thank you very much, I added self in front of everything in create_widgets() since I had other problems after that as well. It works now. –  Apr 07 '17 at 16:41
  • Great! Since you are adding a lot of instance variables, I'd suggest that you manage them in `__init__()` as to not lose track. Be sure to mark your question as solved! – Ziyad Edher Apr 07 '17 at 16:43
  • When it comes to managing instance variables in __init__(), can you explain me further since I'm still a newbie. –  Apr 07 '17 at 16:49
  • Check out the following StackOverflow question for some details on that! http://stackoverflow.com/questions/20661448/python-should-all-member-variables-be-initialized-in-init – Ziyad Edher Apr 07 '17 at 16:50