Python Forum
[Tkinter] taking bad listbox items after lowering it to 1 item - Printable Version

+- Python Forum (https://python-forum.io)
+-- Forum: Python Coding (https://python-forum.io/forum-7.html)
+--- Forum: GUI (https://python-forum.io/forum-10.html)
+--- Thread: [Tkinter] taking bad listbox items after lowering it to 1 item (/thread-11606.html)



taking bad listbox items after lowering it to 1 item - deadmarshal - Jul-17-2018

Hi. when user searches the db by typing in Entrybox widget, the list lowers down to that item only, but the whole listbox doesn't come back again when the user deletes the Entrybox. how can i make the list items come back again when the user clears the entrybox?

and also, I want to replace the letters which are in the words = ["ĝ", "ĉ", "ĥ", "ĵ", "ŭ", "ŝ"] with those in char = ["gx", "cx", "hx", "jx", "ux", "sx"]. but now the problem is that when i type for example gx in entrybox, it returns gxĝgx instead of just ĝ. same for other letters.

import sqlite3 as sqlite
import tkinter as tk
from tkinter import ttk
#GUI Widgets


class EsperantoDict:
    def __init__(self, master):

        master.title("EsperantoDict")
        master.iconbitmap("Esperanto.ico")
        master.resizable(False, False)
        master.configure(background='#EAFFCD')
        self.style = ttk.Style()
        self.search_var = tk.StringVar()
        self.search_var.trace("w", lambda name, index, mode: self.update_list())

        self.style = ttk.Style()
        self.style.configure("TFrame", background='#EAFFCD')
        self.style.configure("TButton", background='#C6FF02')
        self.style.configure("TLabel", background='#EAFFCD')

        self.frame_header = ttk.Frame(master, relief=tk.FLAT)
        self.frame_header.config(style="TFrame")
        self.frame_header.pack(side=tk.TOP, padx=5, pady=5)

        self.logo = tk.PhotoImage(file=r'C:\EsperantoDict\eo.png')
        self.small_logo = self.logo.subsample(10, 10)

        ttk.Label(self.frame_header, image=self.small_logo).grid(row=0, column=0, stick="ne", padx=5, pady=5, rowspan=2)
        ttk.Label(self.frame_header, text='EsperantoDict', font=('Arial', 18, 'bold')).grid(row=0, column=1)

        self.frame_content = ttk.Frame(master)
        self.frame_content.config(style="TFrame")
        self.frame_content.pack()

        self.entry_search = ttk.Entry(self.frame_content, textvariable=self.search_var, width=30)
        self.entry_search.bind('<FocusIn>', self.entry_delete)
        self.entry_search.bind('<FocusOut>', self.entry_insert)
        self.entry_search.grid(row=0, column=0, padx=5)
        self.entry_search.focus()
        self.entry_search.bind("<Key>", self.edit_input)

        self.button_search = ttk.Button(self.frame_content, text="Search")
        self.photo_search = tk.PhotoImage(file=r'C:\EsperantoDict\search.png')
        self.small_photo_search = self.photo_search.subsample(3, 3)
        self.button_search.config(image=self.small_photo_search, compound=tk.LEFT, style="TButton")
        self.button_search.grid(row=0, column=2, columnspan=1, sticky='nw', padx=5)

        self.listbox = tk.Listbox(self.frame_content, height=30, width=30)
        self.listbox.grid(row=1, column=0, padx=5)
        self.scrollbar = ttk.Scrollbar(self.frame_content, orient=tk.VERTICAL, command=self.listbox.yview)
        self.scrollbar.grid(row=1, column=1, sticky='nsw')
        self.listbox.config(yscrollcommand=self.scrollbar.set)
        self.listbox.bind('<<ListboxSelect>>', self.enter_meaning)

        self.textbox = tk.Text(self.frame_content, relief=tk.GROOVE, width=60, height=30, borderwidth=2)
        self.textbox.config(wrap='word')
        self.textbox.grid(row=1, column=2, sticky='w', padx=5)

        # SQLite
        self.db = sqlite.connect(r'C:\EsperantoDict\test.db')
        self.cur = self.db.cursor()
        self.cur.execute('SELECT Esperanto FROM Words ORDER BY Esperanto')
        for row in self.cur:
            self.listbox.insert(tk.END, row)
        for row in range(0, self.listbox.size(), 2):
            self.listbox.itemconfigure(row, background="#f0f0ff")
            self.update_list()

    def update_list(self):
        search_term = self.search_var.get()
        for item in self.listbox.get(0, tk.END):
            if search_term.lower() in item:
                self.listbox.delete(0, tk.END)
                self.listbox.insert(tk.END, item)

    def edit_input(self, input):
        words = ["ĝ", "ĉ", "ĥ", "ĵ", "ŭ", "ŝ"]
        char = ["gx", "cx", "hx", "jx", "ux", "sx"]
        result = ''
        if True:
            user_in = self.search_var.get().lower()
            if user_in in char:
                if char[0] in user_in:
                    result = words[0]
                elif char[1] in user_in:
                    result = words[1]
                elif char[2] in user_in:
                    result = words[2]
                elif char[3] in user_in:
                    result = words[3]
                elif char[4] in user_in:
                    result = words[4]
                elif char[5] in user_in:
                    result = words[5]
            return self.entry_search.insert(tk.INSERT, result)

    # SQLite
    def enter_meaning(self, tag):
        for index in self.listbox.curselection():
            esperanto = self.listbox.get(index)
            results = self.cur.execute("SELECT English FROM Words WHERE Esperanto = ?", esperanto)
            for row in results:
                self.textbox.delete(1.0, tk.END)
                self.textbox.insert(tk.END, row)

    def entry_delete(self, tag):
        self.entry_search.delete(0, tk.END)
        return None

    def entry_insert(self, tag):
        self.entry_search.delete(0, tk.END)
        self.entry_search.insert(0, "Type to Search")
        return None


def main():
    root = tk.Tk()
    esperantodict = EsperantoDict(root)
    root.mainloop()


if __name__ == '__main__': main()

# db tbl name: Words
# db first field name: Esperanto
# db second field name: English

I meant "Taking back listbox items after lowering it to 1 item". I couldn't edit the post :(


RE: taking bad listbox items after lowering it to 1 item - woooee - Jul-18-2018

Keep a list of the original items found in the SQL search, then you can update the Listbox from the original list any where in the program by calling the update_listbox() function.
        # SQLite
        self.db = sqlite.connect(r'C:\EsperantoDict\test.db')
        self.cur = self.db.cursor()
        self.cur.execute('SELECT Esperanto FROM Words ORDER BY Esperanto')
        self.original_list=[]
        for row in self.cur:
            self.original_list.append(row)
        ## start=put it in the new, empty listbox
        self.update_listbox()

    def update_listbox():
        self.listbox.delete(0, tk.END)
        ## you can also use enumerate and do it under one for statement
        ## but it doesn't really save any lines of code
        for num, row in enumerate(self.original_list):
            self.listbox.insert(tk.END, row)
            if num % 2:
                self.listbox.itemconfigure(row, background="#f0f0ff") 



RE: taking bad listbox items after lowering it to 1 item - deadmarshal - Jul-18-2018

I wrote this code below with your explanation but i can't use .delete on my listbox. what am i doing wrong?

# SQLite
        self.db = sqlite.connect(r'C:\EsperantoDict\test.db')
        self.cur = self.db.cursor()
        self.cur.execute('SELECT Esperanto FROM Words ORDER BY Esperanto')
        self.listbox = []
        for row in self.cur:
            self.listbox.append(row)
            self.update_listbox()

    def update_listbox(self):
        self.listbox.delete(0, tk.END)
        for num, row in enumerate(self.listbox):
            self.listbox.insert(tk.END, row)
            if num % 2:
                self.listbox.itemconfigure(row, background="#f0f0ff")



RE: taking bad listbox items after lowering it to 1 item - woooee - Jul-18-2018

Don't have a clue as to what code you are now using. Come up with a simple example that just uses a listbox which searchs. deletes items, and resets the listbox to the original list. After you get it working, you can put that in a separate lookup class and pass the search term to a function in the class which will do the rest.