2017-04-15 7 views
0

Ich erstelle eine einfache GUI-Anwendung, um unbekannte Wörter zu verwalten und gleichzeitig eine neue Sprache zu lernen (die App heißt Vocabulary). Die Anwendung lädt/speichert Wörter aus/in ein XML-Dokument._tkinter.TclError: Wenn ich auf ein Element aus der Listbox klicke

Trotzdem habe ich ein Listenfeld:

self.listBox = Listbox(self.master, 
         selectmode='extended', 
         height = 34, 
         width = 38) 
self.listBox.grid(row = 3, column = 0, rowspan = 7, sticky = W) 
self.listBox.bind('<<ListboxSelect>>', self.selectedIndexChanged) 

... mit drei Elementen darin:

Vocabulary

Um das zu erreichen, was ich die Anwendung tun will, ich weiß, dass ich sollte das ausgewählte Ereignis mit geändertem Index behandeln, und hier ist, wie ich das gemacht habe:

Wenn ich auf ein Element (Wort) in der Listbox klicke, sollte jedes seiner Attribute in entsprechenden Text-Widgets angezeigt werden. Aber das Problem ist, dass ich bekomme:

/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 264, in 
selectedIndexChanged 
    self.txt_WordOrPhrase.insert(END, word.wordorphrase) File "/usr/lib/python3.5/tkinter/__init__.py", line 3121, in insert 
    self.tk.call((self._w, 'insert', index, chars) + args) 
_tkinter.TclError: wrong # args: should be ".140540577622616 insert index chars ?tagList chars tagList ...?" 

Was habe ich falsch gemacht?

Hier ist, was ich getan habe:

# Vocabulary.py 
# GUI program to manage unknown words 

from tkinter import * 
from tkinter import ttk 
from tkinter import messagebox 
import xml.etree.ElementTree as ET 
import os 


class Word: 

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

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() 
     self.words = [] 
     self.load_words() 

    def on_closing(self): 

     self.save_all() 

     if messagebox.askokcancel("Quit", "Do you want to quit?"): 
      self.master.destroy() 

    def create_widgets(self): 

     self.buttons_frame = Frame(self.master) 
     self.buttons_frame.grid(row = 10, sticky = W) 

     self.search_frame = Frame(self.master) 
     self.search_frame.grid(row = 1, sticky = W, columnspan = 2) 

     self.comboBox = ttk.Combobox(self.search_frame, 
            width = 3) 
     self.comboBox.grid(row = 0, column = 14, sticky = W) 
     self.comboBox['values'] = ('A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z') 

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

     self.btn_Remove = Button(self.buttons_frame, 
           text = 'Remove', 
           command = self.remove_item) 

     self.btn_Remove.grid(row = 0, column = 1, sticky = W) 

     self.btn_Edit = Button(self.buttons_frame, 
           text = 'Edit', 
           command = self.edit_item) 
     self.btn_Edit.grid(row = 0, column = 2, sticky = W) 

     self.btn_Save = Button(self.buttons_frame, 
           text = 'Save', 
           command = self.save_item) 
     self.btn_Save.grid(row = 0, column = 3, sticky = W) 

     self.btn_Refresh = Button(self.buttons_frame, 
            text = 'Refresh', 
            command = self.refresh_all) 
     self.btn_Refresh.grid(row = 0, column = 4, sticky = W) 

     self.lblSearch = Label(self.search_frame, text = 'SEARCH: ') 
     self.lblSearch.grid(row = 0, column = 5, sticky = W) 

     self.txt_Search = Text(self.search_frame, 
           height = 1, 
           width = 70) 
     self.txt_Search.grid(row = 0, column = 6, columnspan = 3, sticky = W) 

     self.lblWordsOrPhrases = Label(self.master, text = 'WORDS/PHRASES:') 
     self.lblWordsOrPhrases.grid(row = 2, column = 0) 

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

     self.listBox = Listbox(self.master, 
           selectmode='extended', 
           height = 34, 
           width = 38) 
     self.listBox.grid(row = 3, column = 0, rowspan = 7, sticky = W) 
     self.listBox.bind('<<ListboxSelect>>', self.selectedIndexChanged) 

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

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

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

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

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

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

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

    def load_words(self): 

     self.listBox.delete(0, END) 
     self.words.clear() 

     path = os.path.expanduser('~/Desktop') 
     vocabulary = os.path.join(path, 'Vocabulary', 'Words.xml') 

     if not os.path.exists(vocabulary): 
      if not os.path.exists(os.path.dirname(vocabulary)): 
       os.mkdir(os.path.dirname(vocabulary)) 
      doc = ET.Element('Words') 
      tree = ET.ElementTree(doc) 
      tree.write(vocabulary) 
     else: 
      tree = ET.ElementTree(file=vocabulary) 

     for node in tree.findall('WordOrPhrase'): 
      w = Word(node.find('Word').text, node.find('Explanation').text, node.find('Translation').text, 
        node.find('Examples').text) 

      self.words.append(w) 
      self.listBox.insert(END, w.wordorphrase) 

    def save_all(self): 

     path = os.path.expanduser('~/Desktop') 
     vocabulary = os.path.join(path, 'Vocabulary', 'Words.xml') 

     tree = ET.ElementTree(file=vocabulary) 

     for xNode in tree.getroot().findall('WordOrPhrase'): 
      tree.getroot().remove(xNode) 

     for w in self.words: 
      xTop = ET.Element('WordOrPhrase') 
      xWord = ET.Element('Word') 
      xExplanation = ET.Element('Explanation') 
      xTranslation = ET.Element('Translation') 
      xExamples = ET.Element('Examples') 

      xWord.text = w.wordorphrase 
      xExplanation.text = w.explanation 
      xTranslation.text = w.translation 
      xExamples.text = w.example 

      xTop.append(xWord) 
      xTop.append(xExplanation) 
      xTop.append(xTranslation) 
      xTop.append(xExamples) 

      tree.getroot().append(xTop) 

     tree.write(vocabulary) 

    def add_item(self): 

     w = Word(self.get_word(), self.get_explanation(), self.get_translation(), self.get_example()) 

     self.words.append(w) 

     self.listBox.insert(END, w.wordorphrase) 

     self.clear_all() 

     self.save_all() 

    def remove_item(self): 
     for index in reversed(self.listBox.curselection()): 
      self.listBox.delete(index) 
      del self.words[index] 

    def edit_item(self): 

     if len(self.listBox.curselection()) > 0: 
      self.read_only_OFF() 

     else: 
      messagebox.showinfo("Nothing is selected!", "Notification") 
      self.btn_Edit.config(state = 'normal') 
      self.read_only_ON() 

     self.sync() 


    def save_item(self): 

     if len(self.listBox.curselection()) > 0: 
      word = self.find_word(self.listBox.selection.get()) 
      word.wordorphrase = self.get_word() 
      word.explanation = self.get_explanation() 
      word.translation = self.get_translation() 
      word.example = self.get_example() 

      index = self.listBox.index('active') 
      self.listBox.delete(index) 
      self.listBox.insert(index, self.get_word()) 
      self.listBox.select_set(index) 

    def sync(self): 
     pass 

    def clear_all(self): 
     self.txt_WordOrPhrase.delete('1.0', END) 
     self.txt_Explanation.delete('1.0', END) 
     self.txt_Translation.delete('1.0', END) 
     self.txt_Example.delete('1.0', END) 

    def refresh_all(self): 
     self.clear_all() 
     self.read_only_OFF() 
     self.btn_Edit.config(state = 'disabled') 
     self.word_count() 
     self.sync() 

    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 find_word(self, word): 
     for x in self.words: 
      if x.wordorphrase == word: 
       return x 

    def selectedIndexChanged(self, event = None): 

     selected = self.listBox.curselection() 

     if len(selected) == 0: 
      return 

     word = self.words[selected[0]] 
     self.clear_all() 

     self.txt_WordOrPhrase.insert(END, word.wordorphrase) 
     self.txt_Explanation.insert(END, word.explanation) 
     self.txt_Translation.insert(END, word.translation) 
     self.txt_Example.insert(END, word.example) 

    def read_only_ON(self): 

     self.txt_WordOrPhrase.config(state = 'disabled') 
     self.txt_Explanation.config(state = 'disabled') 
     self.txt_Translation.config(state = 'disabled') 
     self.txt_Example.config(state = 'disabled') 

    def read_only_OFF(self): 

     self.txt_WordOrPhrase.config(state = 'normal') 
     self.txt_Explanation.config(state = 'normal') 
     self.txt_Translation.config(state = 'normal') 
     self.txt_Example.config(state = 'normal') 


def main(): 
    root = Tk() 
    gui = Vocabulary(root) 
    root.protocol('WM_DELETE_WINDOW', gui.on_closing) 
    root.mainloop() 

if __name__ == '__main__': 
    main() 
+0

Was ist 'word.wordorphase' in genau diesem Fall? Ist es ein Objekt? Eine Liste? Ein Faden? –

+0

Es ist ein Objekt. –

+0

Ich werde die Frage bearbeiten, um meinen gesamten Code einzuschließen, damit Sie sehen können, was was ist. –

Antwort

0

In den Kommentaren Sie sagen, dass word.wordorphrase ist ein Objekt. Sie können keine Objekte in eine Listbox einfügen. Sie können nur Zeichenfolgen einfügen.

Verwandte Themen