Ich habe Probleme herauszufinden, wie ich mithilfe von Tkinter ein Menü dort anzeigen kann, wo sich das übergeordnete ElPython

Python-Programme
Anonymous
 Ich habe Probleme herauszufinden, wie ich mithilfe von Tkinter ein Menü dort anzeigen kann, wo sich das übergeordnete El

Post by Anonymous »

Kann mir jemand helfen, herauszufinden, wie ich ein Menü-Widget dort anzeigen kann, wo sich eine Schaltfläche befindet?
Ich arbeite an einer Anwendung, die mithilfe von yt-dlp Videos aus dem Internet herunterlädt (ich befürworte keine Piraterie, möchte das nur klarstellen). Jeder Download innerhalb einer Liste verfügt über eine Schaltfläche, die ein Menü öffnet. Allerdings wird jedes Mal, wenn ich auf diese Schaltfläche klicke, das Menü in der oberen linken Ecke meines Bildschirms geöffnet und nicht dort, wo sich die Schaltfläche befindet.

Code: Select all

from tkinter import *
from tkinter import ttk

from swiperdl.utils.gui import get_icon, load_image_tkinter

class DownloadItem(ttk.Frame):
"""Class for a displayed download item"""
def __init__(self, master=None, title: str = "", dl_path: str = "", url: str = "", status: str = "", progress: dict = None) -> None:
super().__init__(master)

self.title = StringVar()
self.title.set(title)
self.window_coords: dict = {
"x": 0,
"y": 0
}
self.dl_path = dl_path
self.url = url
self.status = status
self.status_text = StringVar()
self.progress_bytes = IntVar()
self.progress_bytes.set(progress.get("bytes", 0))
self.progress_total = progress.get("total", 100)

self.setup_widgets()

def setup_widgets(self) -> None:
self.title_display = ttk.Label(self, textvariable=self.title)
self.status_display = ttk.Label(self, textvariable=self.status_text)
self.progress_bar = ttk.Progressbar(self, orient="horizontal", length=200, mode="determinate", variable=self.progress_bytes, maximum=self.progress_total)
self.info_button = ttk.Button(self, text="...", command=self.open_info_menu)
self.title_display.pack(side="left", anchor="center", padx=50)
self.status_display.pack(side="left", anchor="center", padx=50)
self.progress_bar.pack(side="left", anchor="center", padx=50)
self.info_button.pack(side="right", anchor="center", padx=50)
self.info_menu = Menu(self.info_button)
self.info_menu.add_command(label="Open with associated application")
self.info_menu.add_command(label="Open download link")
self.info_menu.add_command(label="View output")
self.info_menu.add_command(label="Cancel download")
self.info_menu.add_command(label="Remove from list")

def open_info_menu(self) -> None:
self.info_menu.tk_popup(self.window_coords["x"], self.window_coords["y"])

class MainWindow(Tk):
"""Class for the main window GUI."""
def __init__(self) -> None:
super().__init__()
# Basic window settings
self.title("SwiperDL")
self.icon = load_image_tkinter(get_icon("swiperdl"))
self.wm_iconphoto(True, self.icon)
self.geometry("1480x800")
self.protocol("WM_DELETE_WINDOW", self.close)

# A list of predefined formats to choose from.
self.formats = [
...
]

# A list of downloads to be displayed.
# Just a sample, I won't use this in production.
self.downloads = [
{
"title": "Me at the zoo.mp4",
"dl_path": "/home//Me at the zoo.mp4",
"status": "downloading",
"url": "https://www.youtube.com/watch?v=jNQXAC9IVRw",
"progress": {
"bytes": 0,
"total": 100
}
}
]

self.detect_clipboard = StringVar() # Configuration for automatic clipboard detection.
self.selected_format = StringVar() # Holds the selected format to download using the backend.
self.selected_format.set(self.formats[0])

# Start creating the widgets
self.create_menu()
self.create_widgets()

def create_widgets(self) ->  None:
self.main_frame = ttk.Frame(self)
self.main_frame.pack(anchor="center", side="top", expand=True, fill="both")

self.toolbar = ttk.Frame(self.main_frame)
self.toolbar.pack(side="top", anchor="n", fill="x", ipady=20)
self.toolbar_left_spacer = ttk.Frame(self.toolbar, height=1)
self.toolbar_left_spacer.pack(side="left", anchor="w", expand=True, fill="y")
self.url_bar = ttk.Frame(self.toolbar, height=125)
self.clipboard_toggle_icon = load_image_tkinter(get_icon("clipboard_enabled"))
self.clipboard_toggle = ttk.Button(self.url_bar, text="Toggle Clipboard", image=self.clipboard_toggle_icon)
self.clipboard_toggle.pack(side="left", anchor="w")
self.default_text = StringVar()
self.default_text.set("Enter URL or search query here")
self.url_field = ttk.Entry(self.url_bar, textvariable=self.default_text)
self.url_field.pack(side="right", anchor="e", fill="x", padx=50, ipadx=86)
self.url_bar.pack(side="left", anchor="center", expand=False, ipadx=10)

self.basic_config_frame = ttk.Frame(self.toolbar, height=125)
self.basic_config_frame.pack(side="left", anchor="e")
self.format_selection_box = ttk.Combobox(self.basic_config_frame, textvariable=self.selected_format, value=self.formats)
self.format_selection_box.pack(side="left", anchor="w", padx=25)
self.cookies_icon = load_image_tkinter(get_icon("cookies"))
self.cookies_from_browser_toggle = ttk.Button(self.basic_config_frame, text="Use browser cookies", image=self.cookies_icon)
self.cookies_from_browser_toggle.pack(side="left", anchor="e")
self.metadata_icon = load_image_tkinter(get_icon("metadata_enabled"))
self.extract_metadata_toggle = ttk.Button(self.basic_config_frame, text="Extract metadata", image=self.metadata_icon)
self.extract_metadata_toggle.pack(side="left", anchor="e")
self.settings_icon = load_image_tkinter(get_icon("settings"))
self.toolbar_settings_shortcut = ttk.Button(self.basic_config_frame, text="Open settings", image=self.settings_icon)
self.toolbar_settings_shortcut.pack(side="left", anchor="e")
self.toolbar_right_spacer = ttk.Frame(self.toolbar, height=1)
self.toolbar_right_spacer.pack(side="right", anchor="e", expand=True, fill="y")
self.toolbar_separator = ttk.Separator(self.main_frame, orient="horizontal")
self.toolbar_separator.pack(side="top", anchor="n", fill="x")

self.centre_frame = ttk.Frame(self.main_frame)
self.centre_frame.pack(side="top", anchor="center", expand=True, fill="both")
self.download_view_frame = ttk.Frame(self.centre_frame)
self.download_view_frame.pack(side="top", anchor="center", expand=True, fill="both")
for dl in self.downloads:
self.download = DownloadItem(self.download_view_frame, dl.get("title", ""), dl.get("dl_path", ""), dl.get("url", ""), dl.get("status", ""), dl.get("progress", {"bytes": 0, "total": 0}))
self.download.pack(side="top", anchor="n", fill="x")

def create_menu(self) ->  None:
# This is to make sure the menu stays in place.
self.option_add("*tearOff", FALSE)

self.menubar = Menu()
self['menu'] = self.menubar

# Menu for doing stuff with the program
self.appmenu = Menu(self.menubar)
self.appmenu.add_command(label="Add download")
self.appmenu.add_checkbutton(label="Clipboard detection", variable=self.detect_clipboard,
onvalue=1, offvalue=0)
self.appmenu.add_separator()
self.appmenu.add_command(label="Open settings")
self.appmenu.add_separator()
self.appmenu.add_command(label="Quit", command=self.close)
self.menubar.add_cascade(label="SwiperDL", menu=self.appmenu)

# Menu for getting information about the program
self.aboutmenu = Menu(self.menubar)
self.aboutmenu.add_command(label="About SwiperDL")
self.aboutmenu.add_separator()
self.aboutmenu.add_command(label="Support")
self.aboutmenu.add_command(label="Website")
self.aboutmenu.add_command(label="GitHub")
self.aboutmenu.add_command(label="PyPI.org")
self.menubar.add_cascade(label="About", menu=self.aboutmenu)

def open(self) -> None:
self.mainloop()

def close(self) -> None:
self.destroy()
Wenn mir jemand einen Rat geben könnte, wäre ich sehr dankbar! :)
Vielen Dank
EDIT: Der Code funktioniert jetzt wie erwartet dank https://stackoverflow.com/a/79865318.

Quick Reply

Change Text Case: 
   
  • Similar Topics
    Replies
    Views
    Last post