Fix ResourceWarning on unclosed icon file

This commit is contained in:
DevilXD committed 2023-04-26 17:57:51 +02:00
1 parent ab9b155250
commit 9dc7a1d65f
3 files changed
+25 -21

No files matched your search

+10 -14
View File
@@ -29,7 +29,7 @@ if sys.platform == "win32":
from translate import _ from translate import _
from cache import ImageCache from cache import ImageCache
from exceptions import ExitRequest from exceptions import ExitRequest
from utils import resource_path, Game, _T from utils import resource_path, get_photo_image, Game, _T
from constants import ( from constants import (
SELF_PATH, OUTPUT_FORMATTER, WS_TOPICS_LIMIT, MAX_WEBSOCKETS, WINDOW_TITLE, State SELF_PATH, OUTPUT_FORMATTER, WS_TOPICS_LIMIT, MAX_WEBSOCKETS, WINDOW_TITLE, State
) )
@@ -982,9 +982,13 @@ class TrayIcon:
def __init__(self, manager: GUIManager, master: ttk.Widget): def __init__(self, manager: GUIManager, master: ttk.Widget):
self._manager = manager self._manager = manager
self.icon: pystray.Icon | None = None self.icon: pystray.Icon | None = None
self.icon_image = Image_module.open(resource_path("pickaxe.ico"))
self._button = ttk.Button(master, command=self.minimize, text=_("gui", "tray", "minimize")) self._button = ttk.Button(master, command=self.minimize, text=_("gui", "tray", "minimize"))
self._button.grid(column=0, row=0, sticky="ne") self._button.grid(column=0, row=0, sticky="ne")
def __del__(self) -> None:
self.icon_image.close()
def is_tray(self) -> bool: def is_tray(self) -> bool:
return self.icon is not None return self.icon is not None
@@ -1013,12 +1017,7 @@ class TrayIcon:
pystray.Menu.SEPARATOR, pystray.Menu.SEPARATOR,
pystray.MenuItem(_("gui", "tray", "quit"), bridge(self.quit)), pystray.MenuItem(_("gui", "tray", "quit"), bridge(self.quit)),
) )
self.icon = pystray.Icon( self.icon = pystray.Icon("twitch_miner", self.icon_image, self.get_title(drop), menu)
"twitch_miner",
Image_module.open(resource_path("pickaxe.ico")),
self.get_title(drop),
menu,
)
self.icon.run_detached() self.icon.run_detached()
def stop(self): def stop(self):
@@ -1779,13 +1778,10 @@ class GUIManager:
# withdraw immediately to prevent the window from flashing # withdraw immediately to prevent the window from flashing
self._root.withdraw() self._root.withdraw()
# root.resizable(False, True) # root.resizable(False, True)
root.iconphoto( # window icon icon_photo = get_photo_image(root, resource_path("pickaxe.ico"))
True, root.iconphoto(True, icon_photo) # window icon
PhotoImage( # keep a reference to the PhotoImage to avoid the ResourceWarning
master=root, root._icon_image = icon_photo # type: ignore[attr-defined]
image=Image_module.open(resource_path("pickaxe.ico")),
)
)
root.title(WINDOW_TITLE) # window title root.title(WINDOW_TITLE) # window title
root.bind_all("<KeyPress-Escape>", self.unfocus) # pressing ESC unfocuses selection root.bind_all("<KeyPress-Escape>", self.unfocus) # pressing ESC unfocuses selection
# Image cache for displaying images # Image cache for displaying images
+5 -7
View File
@@ -18,18 +18,15 @@ if __name__ == "__main__":
from tkinter import messagebox from tkinter import messagebox
from typing import IO, NoReturn from typing import IO, NoReturn
from PIL.ImageTk import PhotoImage
from PIL import Image as Image_module
if sys.platform == "win32": if sys.platform == "win32":
import win32gui import win32gui
from translate import _ from translate import _
from twitch import Twitch from twitch import Twitch
from settings import Settings from settings import Settings
from utils import resource_path
from version import __version__ from version import __version__
from exceptions import CaptchaRequired from exceptions import CaptchaRequired
from utils import resource_path, get_photo_image
from constants import CALL, SELF_PATH, FILE_FORMATTER, LOG_PATH, WINDOW_TITLE from constants import CALL, SELF_PATH, FILE_FORMATTER, LOG_PATH, WINDOW_TITLE
warnings.simplefilter("default", ResourceWarning) warnings.simplefilter("default", ResourceWarning)
@@ -95,9 +92,10 @@ if __name__ == "__main__":
root = tk.Tk() root = tk.Tk()
root.overrideredirect(True) root.overrideredirect(True)
root.withdraw() root.withdraw()
root.iconphoto( icon_photo = get_photo_image(root, resource_path("pickaxe.ico"))
True, PhotoImage(master=root, image=Image_module.open(resource_path("pickaxe.ico"))) root.iconphoto(True, icon_photo)
) # keep a reference to the PhotoImage to avoid the ResourceWarning
root._icon_image = icon_photo # type: ignore[attr-defined]
root.update() root.update()
parser = Parser( parser = Parser(
SELF_PATH.name, SELF_PATH.name,
+10
View File
@@ -6,6 +6,7 @@ import string
import asyncio import asyncio
import logging import logging
import traceback import traceback
import tkinter as tk
from enum import Enum from enum import Enum
from pathlib import Path from pathlib import Path
from functools import wraps from functools import wraps
@@ -17,6 +18,8 @@ from typing import (
) )
import yarl import yarl
from PIL.ImageTk import PhotoImage
from PIL import Image as Image_module
from constants import JsonType from constants import JsonType
from exceptions import ExitRequest, ReloadRequest from exceptions import ExitRequest, ReloadRequest
@@ -38,6 +41,13 @@ _JSON_T = TypeVar("_JSON_T", bound=Mapping[Any, Any])
logger = logging.getLogger("TwitchDrops") logger = logging.getLogger("TwitchDrops")
def get_photo_image(master: tk.Misc, path: Path | str) -> PhotoImage:
image = Image_module.open(path)
photo = PhotoImage(master=master, image=image)
image.close()
return photo
async def first_to_complete(coros: abc.Iterable[abc.Coroutine[Any, Any, _T]]) -> _T: async def first_to_complete(coros: abc.Iterable[abc.Coroutine[Any, Any, _T]]) -> _T:
# In Python 3.11, we need to explicitly wrap awaitables # In Python 3.11, we need to explicitly wrap awaitables
tasks = [asyncio.ensure_future(coro) for coro in coros] tasks = [asyncio.ensure_future(coro) for coro in coros]