Browse Source

est-ce que ça marche ?

master
BARRAUX Arthur 2 years ago
parent
commit
13565516c6
  1. 3
      customtkinter/__init__.py
  2. BIN
      customtkinter/__pycache__/__init__.cpython-310.pyc
  3. BIN
      customtkinter/__pycache__/__init__.cpython-37.pyc
  4. BIN
      customtkinter/assets/.DS_Store
  5. BIN
      customtkinter/assets/icons/.DS_Store
  6. 3
      customtkinter/assets/themes/blue.json
  7. 3
      customtkinter/assets/themes/dark-blue.json
  8. 3
      customtkinter/assets/themes/green.json
  9. BIN
      customtkinter/windows/__pycache__/__init__.cpython-310.pyc
  10. BIN
      customtkinter/windows/__pycache__/__init__.cpython-37.pyc
  11. BIN
      customtkinter/windows/__pycache__/ctk_input_dialog.cpython-310.pyc
  12. BIN
      customtkinter/windows/__pycache__/ctk_tk.cpython-310.pyc
  13. BIN
      customtkinter/windows/__pycache__/ctk_tk.cpython-37.pyc
  14. BIN
      customtkinter/windows/__pycache__/ctk_toplevel.cpython-310.pyc
  15. 25
      customtkinter/windows/ctk_tk.py
  16. 8
      customtkinter/windows/ctk_toplevel.py
  17. 1
      customtkinter/windows/widgets/__init__.py
  18. BIN
      customtkinter/windows/widgets/__pycache__/__init__.cpython-310.pyc
  19. BIN
      customtkinter/windows/widgets/__pycache__/__init__.cpython-37.pyc
  20. BIN
      customtkinter/windows/widgets/__pycache__/ctk_button.cpython-310.pyc
  21. BIN
      customtkinter/windows/widgets/__pycache__/ctk_button.cpython-37.pyc
  22. BIN
      customtkinter/windows/widgets/__pycache__/ctk_checkbox.cpython-310.pyc
  23. BIN
      customtkinter/windows/widgets/__pycache__/ctk_combobox.cpython-310.pyc
  24. BIN
      customtkinter/windows/widgets/__pycache__/ctk_entry.cpython-310.pyc
  25. BIN
      customtkinter/windows/widgets/__pycache__/ctk_frame.cpython-310.pyc
  26. BIN
      customtkinter/windows/widgets/__pycache__/ctk_label.cpython-310.pyc
  27. BIN
      customtkinter/windows/widgets/__pycache__/ctk_optionmenu.cpython-310.pyc
  28. BIN
      customtkinter/windows/widgets/__pycache__/ctk_progressbar.cpython-310.pyc
  29. BIN
      customtkinter/windows/widgets/__pycache__/ctk_radiobutton.cpython-310.pyc
  30. BIN
      customtkinter/windows/widgets/__pycache__/ctk_scrollable_frame.cpython-310.pyc
  31. BIN
      customtkinter/windows/widgets/__pycache__/ctk_scrollbar.cpython-310.pyc
  32. BIN
      customtkinter/windows/widgets/__pycache__/ctk_segmented_button.cpython-310.pyc
  33. BIN
      customtkinter/windows/widgets/__pycache__/ctk_slider.cpython-310.pyc
  34. BIN
      customtkinter/windows/widgets/__pycache__/ctk_switch.cpython-310.pyc
  35. BIN
      customtkinter/windows/widgets/__pycache__/ctk_tabview.cpython-310.pyc
  36. BIN
      customtkinter/windows/widgets/__pycache__/ctk_textbox.cpython-310.pyc
  37. BIN
      customtkinter/windows/widgets/appearance_mode/__pycache__/__init__.cpython-310.pyc
  38. BIN
      customtkinter/windows/widgets/appearance_mode/__pycache__/appearance_mode_base_class.cpython-310.pyc
  39. BIN
      customtkinter/windows/widgets/appearance_mode/__pycache__/appearance_mode_tracker.cpython-310.pyc
  40. 2
      customtkinter/windows/widgets/appearance_mode/appearance_mode_base_class.py
  41. BIN
      customtkinter/windows/widgets/core_rendering/__pycache__/__init__.cpython-310.pyc
  42. BIN
      customtkinter/windows/widgets/core_rendering/__pycache__/__init__.cpython-37.pyc
  43. BIN
      customtkinter/windows/widgets/core_rendering/__pycache__/ctk_canvas.cpython-310.pyc
  44. BIN
      customtkinter/windows/widgets/core_rendering/__pycache__/ctk_canvas.cpython-37.pyc
  45. BIN
      customtkinter/windows/widgets/core_rendering/__pycache__/draw_engine.cpython-310.pyc
  46. BIN
      customtkinter/windows/widgets/core_rendering/__pycache__/draw_engine.cpython-37.pyc
  47. BIN
      customtkinter/windows/widgets/core_widget_classes/__pycache__/__init__.cpython-310.pyc
  48. BIN
      customtkinter/windows/widgets/core_widget_classes/__pycache__/__init__.cpython-37.pyc
  49. BIN
      customtkinter/windows/widgets/core_widget_classes/__pycache__/ctk_base_class.cpython-310.pyc
  50. BIN
      customtkinter/windows/widgets/core_widget_classes/__pycache__/dropdown_menu.cpython-310.pyc
  51. BIN
      customtkinter/windows/widgets/core_widget_classes/__pycache__/dropdown_menu.cpython-37.pyc
  52. 17
      customtkinter/windows/widgets/core_widget_classes/ctk_base_class.py
  53. 6
      customtkinter/windows/widgets/ctk_button.py
  54. 12
      customtkinter/windows/widgets/ctk_entry.py
  55. 2
      customtkinter/windows/widgets/ctk_frame.py
  56. 316
      customtkinter/windows/widgets/ctk_scrollable_frame.py
  57. BIN
      customtkinter/windows/widgets/font/__pycache__/__init__.cpython-310.pyc
  58. BIN
      customtkinter/windows/widgets/font/__pycache__/__init__.cpython-37.pyc
  59. BIN
      customtkinter/windows/widgets/font/__pycache__/ctk_font.cpython-310.pyc
  60. BIN
      customtkinter/windows/widgets/font/__pycache__/ctk_font.cpython-37.pyc
  61. BIN
      customtkinter/windows/widgets/font/__pycache__/font_manager.cpython-310.pyc
  62. BIN
      customtkinter/windows/widgets/image/__pycache__/__init__.cpython-310.pyc
  63. BIN
      customtkinter/windows/widgets/image/__pycache__/ctk_image.cpython-310.pyc
  64. BIN
      customtkinter/windows/widgets/scaling/__pycache__/__init__.cpython-310.pyc
  65. BIN
      customtkinter/windows/widgets/scaling/__pycache__/scaling_base_class.cpython-310.pyc
  66. BIN
      customtkinter/windows/widgets/scaling/__pycache__/scaling_tracker.cpython-310.pyc
  67. BIN
      customtkinter/windows/widgets/theme/__pycache__/__init__.cpython-310.pyc
  68. BIN
      customtkinter/windows/widgets/theme/__pycache__/__init__.cpython-37.pyc
  69. BIN
      customtkinter/windows/widgets/theme/__pycache__/theme_manager.cpython-310.pyc
  70. BIN
      customtkinter/windows/widgets/theme/__pycache__/theme_manager.cpython-37.pyc
  71. BIN
      customtkinter/windows/widgets/utility/__pycache__/__init__.cpython-310.pyc
  72. BIN
      customtkinter/windows/widgets/utility/__pycache__/utility_functions.cpython-310.pyc
  73. 36
      main.py

3
customtkinter/__init__.py

@ -1,4 +1,4 @@
__version__ = "5.0.5" __version__ = "5.1.2"
import os import os
import sys import sys
@ -33,6 +33,7 @@ from .windows.widgets import CTkSlider
from .windows.widgets import CTkSwitch from .windows.widgets import CTkSwitch
from .windows.widgets import CTkTabview from .windows.widgets import CTkTabview
from .windows.widgets import CTkTextbox from .windows.widgets import CTkTextbox
from .windows.widgets import CTkScrollableFrame
# import windows # import windows
from .windows import CTk from .windows import CTk

BIN
customtkinter/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/__pycache__/__init__.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/assets/.DS_Store

Binary file not shown.

BIN
customtkinter/assets/icons/.DS_Store

Binary file not shown.

3
customtkinter/assets/themes/blue.json

@ -127,6 +127,9 @@
"scrollbar_button_color": ["gray55", "gray41"], "scrollbar_button_color": ["gray55", "gray41"],
"scrollbar_button_hover_color": ["gray40", "gray53"] "scrollbar_button_hover_color": ["gray40", "gray53"]
}, },
"CTkScrollableFrame": {
"label_fg_color": ["gray78", "gray23"]
},
"DropdownMenu": { "DropdownMenu": {
"fg_color": ["gray90", "gray20"], "fg_color": ["gray90", "gray20"],
"hover_color": ["gray75", "gray28"], "hover_color": ["gray75", "gray28"],

3
customtkinter/assets/themes/dark-blue.json

@ -127,6 +127,9 @@
"scrollbar_button_color": ["gray55", "gray41"], "scrollbar_button_color": ["gray55", "gray41"],
"scrollbar_button_hover_color": ["gray40", "gray53"] "scrollbar_button_hover_color": ["gray40", "gray53"]
}, },
"CTkScrollableFrame": {
"label_fg_color": ["gray80", "gray21"]
},
"DropdownMenu": { "DropdownMenu": {
"fg_color": ["gray90", "gray20"], "fg_color": ["gray90", "gray20"],
"hover_color": ["gray75", "gray28"], "hover_color": ["gray75", "gray28"],

3
customtkinter/assets/themes/green.json

@ -127,6 +127,9 @@
"scrollbar_button_color": ["gray55", "gray41"], "scrollbar_button_color": ["gray55", "gray41"],
"scrollbar_button_hover_color": ["gray40", "gray53"] "scrollbar_button_hover_color": ["gray40", "gray53"]
}, },
"CTkScrollableFrame": {
"label_fg_color": ["gray78", "gray23"]
},
"DropdownMenu": { "DropdownMenu": {
"fg_color": ["gray90", "gray20"], "fg_color": ["gray90", "gray20"],
"hover_color": ["gray75", "gray28"], "hover_color": ["gray75", "gray28"],

BIN
customtkinter/windows/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/__pycache__/__init__.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/__pycache__/ctk_input_dialog.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/__pycache__/ctk_tk.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/__pycache__/ctk_tk.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/__pycache__/ctk_toplevel.cpython-310.pyc

Binary file not shown.

25
customtkinter/windows/ctk_tk.py

@ -64,6 +64,9 @@ class CTk(tkinter.Tk, CTkAppearanceModeBaseClass, CTkScalingBaseClass):
self._iconify_called_before_window_exists = False # indicates if iconify() was called before window is first shown through update() or mainloop() self._iconify_called_before_window_exists = False # indicates if iconify() was called before window is first shown through update() or mainloop()
self._block_update_dimensions_event = False self._block_update_dimensions_event = False
# save focus before calling withdraw
self.focused_widget_before_widthdraw = None
# set CustomTkinter titlebar icon (Windows only) # set CustomTkinter titlebar icon (Windows only)
if sys.platform.startswith("win"): if sys.platform.startswith("win"):
self.after(200, self._windows_set_titlebar_icon) self.after(200, self._windows_set_titlebar_icon)
@ -137,24 +140,26 @@ class CTk(tkinter.Tk, CTkAppearanceModeBaseClass, CTkScalingBaseClass):
def update(self): def update(self):
if self._window_exists is False: if self._window_exists is False:
self._window_exists = True
if sys.platform.startswith("win"): if sys.platform.startswith("win"):
if not self._withdraw_called_before_window_exists and not self._iconify_called_before_window_exists: if not self._withdraw_called_before_window_exists and not self._iconify_called_before_window_exists:
# print("window dont exists -> deiconify in update") # print("window dont exists -> deiconify in update")
self.deiconify() self.deiconify()
self._window_exists = True
super().update() super().update()
def mainloop(self, *args, **kwargs): def mainloop(self, *args, **kwargs):
if not self._window_exists: if not self._window_exists:
self._window_exists = True
if sys.platform.startswith("win"): if sys.platform.startswith("win"):
self._windows_set_titlebar_color(self._get_appearance_mode())
if not self._withdraw_called_before_window_exists and not self._iconify_called_before_window_exists: if not self._withdraw_called_before_window_exists and not self._iconify_called_before_window_exists:
# print("window dont exists -> deiconify in mainloop") # print("window dont exists -> deiconify in mainloop")
self.deiconify() self.deiconify()
self._window_exists = True
super().mainloop(*args, **kwargs) super().mainloop(*args, **kwargs)
def resizable(self, width: bool = None, height: bool = None): def resizable(self, width: bool = None, height: bool = None):
@ -220,6 +225,10 @@ class CTk(tkinter.Tk, CTkAppearanceModeBaseClass, CTkScalingBaseClass):
self._iconbitmap_method_called = True self._iconbitmap_method_called = True
super().wm_iconbitmap(bitmap, default) super().wm_iconbitmap(bitmap, default)
def iconbitmap(self, bitmap=None, default=None):
self._iconbitmap_method_called = True
super().wm_iconbitmap(bitmap, default)
def _windows_set_titlebar_icon(self): def _windows_set_titlebar_icon(self):
try: try:
# if not the user already called iconbitmap method, set icon # if not the user already called iconbitmap method, set icon
@ -263,9 +272,11 @@ class CTk(tkinter.Tk, CTkAppearanceModeBaseClass, CTkScalingBaseClass):
# print("window_exists -> state_before_windows_set_titlebar_color: ", self.state_before_windows_set_titlebar_color) # print("window_exists -> state_before_windows_set_titlebar_color: ", self.state_before_windows_set_titlebar_color)
if self._state_before_windows_set_titlebar_color != "iconic" or self._state_before_windows_set_titlebar_color != "withdrawn": if self._state_before_windows_set_titlebar_color != "iconic" or self._state_before_windows_set_titlebar_color != "withdrawn":
self.focused_widget_before_widthdraw = self.focus_get()
super().withdraw() # hide window so that it can be redrawn after the titlebar change so that the color change is visible super().withdraw() # hide window so that it can be redrawn after the titlebar change so that the color change is visible
else: else:
# print("window dont exists -> withdraw and update") # print("window dont exists -> withdraw and update")
self.focused_widget_before_widthdraw = self.focus_get()
super().withdraw() super().withdraw()
super().update() super().update()
@ -294,7 +305,7 @@ class CTk(tkinter.Tk, CTkAppearanceModeBaseClass, CTkScalingBaseClass):
except Exception as err: except Exception as err:
print(err) print(err)
if self._window_exists: if self._window_exists or True:
# print("window_exists -> return to original state: ", self.state_before_windows_set_titlebar_color) # print("window_exists -> return to original state: ", self.state_before_windows_set_titlebar_color)
if self._state_before_windows_set_titlebar_color == "normal": if self._state_before_windows_set_titlebar_color == "normal":
self.deiconify() self.deiconify()
@ -307,6 +318,10 @@ class CTk(tkinter.Tk, CTkAppearanceModeBaseClass, CTkScalingBaseClass):
else: else:
pass # wait for update or mainloop to be called pass # wait for update or mainloop to be called
if self.focused_widget_before_widthdraw is not None:
self.after(1, self.focused_widget_before_widthdraw.focus)
self.focused_widget_before_widthdraw = None
def _set_appearance_mode(self, mode_string: str): def _set_appearance_mode(self, mode_string: str):
super()._set_appearance_mode(mode_string) super()._set_appearance_mode(mode_string)

8
customtkinter/windows/ctk_toplevel.py

@ -70,6 +70,9 @@ class CTkToplevel(tkinter.Toplevel, CTkAppearanceModeBaseClass, CTkScalingBaseCl
self._iconify_called_after_windows_set_titlebar_color = False # indicates if iconify() was called after windows_set_titlebar_color self._iconify_called_after_windows_set_titlebar_color = False # indicates if iconify() was called after windows_set_titlebar_color
self._block_update_dimensions_event = False self._block_update_dimensions_event = False
# save focus before calling withdraw
self.focused_widget_before_widthdraw = None
# set CustomTkinter titlebar icon (Windows only) # set CustomTkinter titlebar icon (Windows only)
if sys.platform.startswith("win"): if sys.platform.startswith("win"):
self.after(200, self._windows_set_titlebar_icon) self.after(200, self._windows_set_titlebar_icon)
@ -238,6 +241,7 @@ class CTkToplevel(tkinter.Toplevel, CTkAppearanceModeBaseClass, CTkScalingBaseCl
if sys.platform.startswith("win") and not self._deactivate_windows_window_header_manipulation: if sys.platform.startswith("win") and not self._deactivate_windows_window_header_manipulation:
self._state_before_windows_set_titlebar_color = self.state() self._state_before_windows_set_titlebar_color = self.state()
self.focused_widget_before_widthdraw = self.focus_get()
super().withdraw() # hide window so that it can be redrawn after the titlebar change so that the color change is visible super().withdraw() # hide window so that it can be redrawn after the titlebar change so that the color change is visible
super().update() super().update()
@ -268,6 +272,10 @@ class CTkToplevel(tkinter.Toplevel, CTkAppearanceModeBaseClass, CTkScalingBaseCl
self._windows_set_titlebar_color_called = True self._windows_set_titlebar_color_called = True
self.after(5, self._revert_withdraw_after_windows_set_titlebar_color) self.after(5, self._revert_withdraw_after_windows_set_titlebar_color)
if self.focused_widget_before_widthdraw is not None:
self.after(10, self.focused_widget_before_widthdraw.focus)
self.focused_widget_before_widthdraw = None
def _revert_withdraw_after_windows_set_titlebar_color(self): def _revert_withdraw_after_windows_set_titlebar_color(self):
""" if in a short time (5ms) after """ """ if in a short time (5ms) after """
if self._windows_set_titlebar_color_called: if self._windows_set_titlebar_color_called:

1
customtkinter/windows/widgets/__init__.py

@ -13,3 +13,4 @@ from .ctk_slider import CTkSlider
from .ctk_switch import CTkSwitch from .ctk_switch import CTkSwitch
from .ctk_tabview import CTkTabview from .ctk_tabview import CTkTabview
from .ctk_textbox import CTkTextbox from .ctk_textbox import CTkTextbox
from .ctk_scrollable_frame import CTkScrollableFrame

BIN
customtkinter/windows/widgets/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/__init__.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_button.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_button.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_checkbox.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_combobox.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_entry.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_frame.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_label.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_optionmenu.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_progressbar.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_radiobutton.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_scrollable_frame.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_scrollbar.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_segmented_button.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_slider.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_switch.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_tabview.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/__pycache__/ctk_textbox.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/appearance_mode/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/appearance_mode/__pycache__/appearance_mode_base_class.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/appearance_mode/__pycache__/appearance_mode_tracker.cpython-310.pyc

Binary file not shown.

2
customtkinter/windows/widgets/appearance_mode/appearance_mode_base_class.py

@ -9,7 +9,7 @@ class CTkAppearanceModeBaseClass:
- destroy() must be called when sub-class is destroyed - destroy() must be called when sub-class is destroyed
- _set_appearance_mode() abstractmethod, gets called when appearance mode changes, must be overridden - _set_appearance_mode() abstractmethod, gets called when appearance mode changes, must be overridden
- _apply_appearance_mode() - _apply_appearance_mode() to convert tuple color
""" """
def __init__(self): def __init__(self):

BIN
customtkinter/windows/widgets/core_rendering/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_rendering/__pycache__/__init__.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_rendering/__pycache__/ctk_canvas.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_rendering/__pycache__/ctk_canvas.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_rendering/__pycache__/draw_engine.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_rendering/__pycache__/draw_engine.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_widget_classes/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_widget_classes/__pycache__/__init__.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_widget_classes/__pycache__/ctk_base_class.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_widget_classes/__pycache__/dropdown_menu.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/core_widget_classes/__pycache__/dropdown_menu.cpython-37.pyc

Binary file not shown.

17
customtkinter/windows/widgets/core_widget_classes/ctk_base_class.py

@ -9,9 +9,6 @@ try:
except ImportError: except ImportError:
from typing_extensions import TypedDict from typing_extensions import TypedDict
# removed due to circular import
# from ...ctk_tk import CTk
# from ...ctk_toplevel import CTkToplevel
from .... import windows # import windows for isinstance checks from .... import windows # import windows for isinstance checks
from ..theme import ThemeManager from ..theme import ThemeManager
@ -74,7 +71,7 @@ class CTkBaseClass(tkinter.Frame, CTkAppearanceModeBaseClass, CTkScalingBaseClas
super().bind('<Configure>', self._update_dimensions_event) super().bind('<Configure>', self._update_dimensions_event)
# overwrite configure methods of master when master is tkinter widget, so that bg changes get applied on child CTk widget as well # overwrite configure methods of master when master is tkinter widget, so that bg changes get applied on child CTk widget as well
if isinstance(self.master, (tkinter.Tk, tkinter.Toplevel, tkinter.Frame, tkinter.LabelFrame, ttk.Frame, ttk.LabelFrame, ttk.Notebook)) and not isinstance(self.master, CTkBaseClass): if isinstance(self.master, (tkinter.Tk, tkinter.Toplevel, tkinter.Frame, tkinter.LabelFrame, ttk.Frame, ttk.LabelFrame, ttk.Notebook)) and not isinstance(self.master, (CTkBaseClass, CTkAppearanceModeBaseClass)):
master_old_configure = self.master.config master_old_configure = self.master.config
def new_configure(*args, **kwargs): def new_configure(*args, **kwargs):
@ -179,8 +176,7 @@ class CTkBaseClass(tkinter.Frame, CTkAppearanceModeBaseClass, CTkScalingBaseClas
elif isinstance(image, CTkImage): elif isinstance(image, CTkImage):
return image return image
else: else:
warnings.warn(f"{type(self).__name__} Warning: Given image is not CTkImage but {type(image)}. " + warnings.warn(f"{type(self).__name__} Warning: Given image is not CTkImage but {type(image)}. Image can not be scaled on HighDPI displays, use CTkImage instead.\n")
f"Image can not be scaled on HighDPI displays, use CTkImage instead.\n")
return image return image
def _update_dimensions_event(self, event): def _update_dimensions_event(self, event):
@ -197,12 +193,15 @@ class CTkBaseClass(tkinter.Frame, CTkAppearanceModeBaseClass, CTkScalingBaseClas
if master_widget is None: if master_widget is None:
master_widget = self.master master_widget = self.master
if isinstance(master_widget, (windows.widgets.core_widget_classes.CTkBaseClass, windows.CTk, windows.CTkToplevel)): if isinstance(master_widget, (windows.widgets.core_widget_classes.CTkBaseClass, windows.CTk, windows.CTkToplevel, windows.widgets.ctk_scrollable_frame.CTkScrollableFrame)):
if master_widget.cget("fg_color") is not None and master_widget.cget("fg_color") != "transparent": if master_widget.cget("fg_color") is not None and master_widget.cget("fg_color") != "transparent":
return master_widget.cget("fg_color") return master_widget.cget("fg_color")
elif isinstance(master_widget, windows.widgets.ctk_scrollable_frame.CTkScrollableFrame):
return self._detect_color_of_master(master_widget.master.master.master)
# if fg_color of master is None, try to retrieve fg_color from master of master # if fg_color of master is None, try to retrieve fg_color from master of master
elif hasattr(master_widget.master, "master"): elif hasattr(master_widget, "master"):
return self._detect_color_of_master(master_widget.master) return self._detect_color_of_master(master_widget.master)
elif isinstance(master_widget, (ttk.Frame, ttk.LabelFrame, ttk.Notebook, ttk.Label)): # master is ttk widget elif isinstance(master_widget, (ttk.Frame, ttk.LabelFrame, ttk.Notebook, ttk.Label)): # master is ttk widget
@ -269,6 +268,8 @@ class CTkBaseClass(tkinter.Frame, CTkAppearanceModeBaseClass, CTkScalingBaseClas
relheight=amount - height of this widget between 0.0 and 1.0 relative to height of master (1.0 is the same height as the master) relheight=amount - height of this widget between 0.0 and 1.0 relative to height of master (1.0 is the same height as the master)
bordermode="inside" or "outside" - whether to take border width of master widget into account bordermode="inside" or "outside" - whether to take border width of master widget into account
""" """
if "width" in kwargs or "height" in kwargs:
raise ValueError("'width' and 'height' arguments must be passed to the constructor of the widget, not the place method")
self._last_geometry_manager_call = {"function": super().place, "kwargs": kwargs} self._last_geometry_manager_call = {"function": super().place, "kwargs": kwargs}
return super().place(**self._apply_argument_scaling(kwargs)) return super().place(**self._apply_argument_scaling(kwargs))

6
customtkinter/windows/widgets/ctk_button.py

@ -40,7 +40,7 @@ class CTkButton(CTkBaseClass):
text: str = "CTkButton", text: str = "CTkButton",
font: Optional[Union[tuple, CTkFont]] = None, font: Optional[Union[tuple, CTkFont]] = None,
textvariable: Union[tkinter.Variable, None] = None, textvariable: Union[tkinter.Variable, None] = None,
image: Union[CTkImage, None] = None, image: Union[CTkImage, "ImageTk.PhotoImage", None] = None,
state: str = "normal", state: str = "normal",
hover: bool = True, hover: bool = True,
command: Union[Callable[[], None], None] = None, command: Union[Callable[[], None], None] = None,
@ -169,8 +169,11 @@ class CTkButton(CTkBaseClass):
def _update_image(self): def _update_image(self):
if self._image_label is not None: if self._image_label is not None:
if isinstance(self._image, CTkImage):
self._image_label.configure(image=self._image.create_scaled_photo_image(self._get_widget_scaling(), self._image_label.configure(image=self._image.create_scaled_photo_image(self._get_widget_scaling(),
self._get_appearance_mode())) self._get_appearance_mode()))
elif self._image is not None:
self._image_label.configure(image=self._image)
def destroy(self): def destroy(self):
if isinstance(self._font, CTkFont): if isinstance(self._font, CTkFont):
@ -425,6 +428,7 @@ class CTkButton(CTkBaseClass):
if "command" in kwargs: if "command" in kwargs:
self._command = kwargs.pop("command") self._command = kwargs.pop("command")
self._set_cursor()
if "compound" in kwargs: if "compound" in kwargs:
self._compound = kwargs.pop("compound") self._compound = kwargs.pop("compound")

12
customtkinter/windows/widgets/ctk_entry.py

@ -133,7 +133,7 @@ class CTkEntry(CTkBaseClass):
self._canvas.configure(width=self._apply_widget_scaling(self._desired_width), self._canvas.configure(width=self._apply_widget_scaling(self._desired_width),
height=self._apply_widget_scaling(self._desired_height)) height=self._apply_widget_scaling(self._desired_height))
self._draw() self._draw(no_color_updates=True)
def _update_font(self): def _update_font(self):
""" pass font to tkinter widgets with applied font scaling and update grid with workaround """ """ pass font to tkinter widgets with applied font scaling and update grid with workaround """
@ -153,14 +153,14 @@ class CTkEntry(CTkBaseClass):
def _draw(self, no_color_updates=False): def _draw(self, no_color_updates=False):
super()._draw(no_color_updates) super()._draw(no_color_updates)
self._canvas.configure(bg=self._apply_appearance_mode(self._bg_color))
requires_recoloring = self._draw_engine.draw_rounded_rect_with_border(self._apply_widget_scaling(self._current_width), requires_recoloring = self._draw_engine.draw_rounded_rect_with_border(self._apply_widget_scaling(self._current_width),
self._apply_widget_scaling(self._current_height), self._apply_widget_scaling(self._current_height),
self._apply_widget_scaling(self._corner_radius), self._apply_widget_scaling(self._corner_radius),
self._apply_widget_scaling(self._border_width)) self._apply_widget_scaling(self._border_width))
if requires_recoloring or no_color_updates is False: if requires_recoloring or no_color_updates is False:
self._canvas.configure(bg=self._apply_appearance_mode(self._bg_color))
if self._apply_appearance_mode(self._fg_color) == "transparent": if self._apply_appearance_mode(self._fg_color) == "transparent":
self._canvas.itemconfig("inner_parts", self._canvas.itemconfig("inner_parts",
fill=self._apply_appearance_mode(self._bg_color), fill=self._apply_appearance_mode(self._bg_color),
@ -342,13 +342,13 @@ class CTkEntry(CTkBaseClass):
return self._entry.get() return self._entry.get()
def focus(self): def focus(self):
return self._entry.focus() self._entry.focus()
def focus_set(self): def focus_set(self):
return self._entry.focus_set() self._entry.focus_set()
def focus_force(self): def focus_force(self):
return self._entry.focus_force() self._entry.focus_force()
def index(self, index): def index(self, index):
return self._entry.index(index) return self._entry.index(index)

2
customtkinter/windows/widgets/ctk_frame.py

@ -24,8 +24,8 @@ class CTkFrame(CTkBaseClass):
bg_color: Union[str, Tuple[str, str]] = "transparent", bg_color: Union[str, Tuple[str, str]] = "transparent",
fg_color: Optional[Union[str, Tuple[str, str]]] = None, fg_color: Optional[Union[str, Tuple[str, str]]] = None,
border_color: Optional[Union[str, Tuple[str, str]]] = None, border_color: Optional[Union[str, Tuple[str, str]]] = None,
background_corner_colors: Union[Tuple[Union[str, Tuple[str, str]]], None] = None,
background_corner_colors: Union[Tuple[Union[str, Tuple[str, str]]], None] = None,
overwrite_preferred_drawing_method: Union[str, None] = None, overwrite_preferred_drawing_method: Union[str, None] = None,
**kwargs): **kwargs):

316
customtkinter/windows/widgets/ctk_scrollable_frame.py

@ -0,0 +1,316 @@
from typing import Union, Tuple, Optional
try:
from typing import Literal
except ImportError:
from typing_extensions import Literal
import tkinter
import sys
from .ctk_frame import CTkFrame
from .ctk_scrollbar import CTkScrollbar
from .appearance_mode import CTkAppearanceModeBaseClass
from .scaling import CTkScalingBaseClass
from .core_widget_classes import CTkBaseClass
from .ctk_label import CTkLabel
from .font import CTkFont
from .theme import ThemeManager
class CTkScrollableFrame(tkinter.Frame, CTkAppearanceModeBaseClass, CTkScalingBaseClass):
def __init__(self,
master: any,
width: int = 200,
height: int = 200,
corner_radius: Optional[Union[int, str]] = None,
border_width: Optional[Union[int, str]] = None,
bg_color: Union[str, Tuple[str, str]] = "transparent",
fg_color: Optional[Union[str, Tuple[str, str]]] = None,
border_color: Optional[Union[str, Tuple[str, str]]] = None,
scrollbar_fg_color: Optional[Union[str, Tuple[str, str]]] = None,
scrollbar_button_color: Optional[Union[str, Tuple[str, str]]] = None,
scrollbar_button_hover_color: Optional[Union[str, Tuple[str, str]]] = None,
label_fg_color: Optional[Union[str, Tuple[str, str]]] = None,
label_text_color: Optional[Union[str, Tuple[str, str]]] = None,
label_text: str = "",
label_font: Optional[Union[tuple, CTkFont]] = None,
label_anchor: str = "center",
orientation: Literal["vertical", "horizontal"] = "vertical"):
self._orientation = orientation
# dimensions independent of scaling
self._desired_width = width # _desired_width and _desired_height, represent desired size set by width and height
self._desired_height = height
self._parent_frame = CTkFrame(master=master, width=0, height=0, corner_radius=corner_radius,
border_width=border_width, bg_color=bg_color, fg_color=fg_color, border_color=border_color)
self._parent_canvas = tkinter.Canvas(master=self._parent_frame, highlightthickness=0)
self._set_scroll_increments()
if self._orientation == "horizontal":
self._scrollbar = CTkScrollbar(master=self._parent_frame, orientation="horizontal", command=self._parent_canvas.xview,
fg_color=scrollbar_fg_color, button_color=scrollbar_button_color, button_hover_color=scrollbar_button_hover_color)
self._parent_canvas.configure(xscrollcommand=self._scrollbar.set)
elif self._orientation == "vertical":
self._scrollbar = CTkScrollbar(master=self._parent_frame, orientation="vertical", command=self._parent_canvas.yview,
fg_color=scrollbar_fg_color, button_color=scrollbar_button_color, button_hover_color=scrollbar_button_hover_color)
self._parent_canvas.configure(yscrollcommand=self._scrollbar.set)
self._label_text = label_text
self._label = CTkLabel(self._parent_frame, text=label_text, anchor=label_anchor, font=label_font,
corner_radius=self._parent_frame.cget("corner_radius"), text_color=label_text_color,
fg_color=ThemeManager.theme["CTkScrollableFrame"]["label_fg_color"] if label_fg_color is None else label_fg_color)
tkinter.Frame.__init__(self, master=self._parent_canvas, highlightthickness=0)
CTkAppearanceModeBaseClass.__init__(self)
CTkScalingBaseClass.__init__(self, scaling_type="widget")
self._create_grid()
self._parent_canvas.configure(width=self._apply_widget_scaling(self._desired_width),
height=self._apply_widget_scaling(self._desired_height))
self.bind("<Configure>", lambda e: self._parent_canvas.configure(scrollregion=self._parent_canvas.bbox("all")))
self._parent_canvas.bind("<Configure>", self._fit_frame_dimensions_to_canvas)
self.bind_all("<MouseWheel>", self._mouse_wheel_all, add="+")
self.bind_all("<KeyPress-Shift_L>", self._keyboard_shift_press_all, add="+")
self.bind_all("<KeyPress-Shift_R>", self._keyboard_shift_press_all, add="+")
self.bind_all("<KeyRelease-Shift_L>", self._keyboard_shift_release_all, add="+")
self.bind_all("<KeyRelease-Shift_R>", self._keyboard_shift_release_all, add="+")
self._create_window_id = self._parent_canvas.create_window(0, 0, window=self, anchor="nw")
if self._parent_frame.cget("fg_color") == "transparent":
tkinter.Frame.configure(self, bg=self._apply_appearance_mode(self._parent_frame.cget("bg_color")))
self._parent_canvas.configure(bg=self._apply_appearance_mode(self._parent_frame.cget("bg_color")))
else:
tkinter.Frame.configure(self, bg=self._apply_appearance_mode(self._parent_frame.cget("fg_color")))
self._parent_canvas.configure(bg=self._apply_appearance_mode(self._parent_frame.cget("fg_color")))
self._shift_pressed = False
def destroy(self):
tkinter.Frame.destroy(self)
CTkAppearanceModeBaseClass.destroy(self)
CTkScalingBaseClass.destroy(self)
def _create_grid(self):
border_spacing = self._apply_widget_scaling(self._parent_frame.cget("corner_radius") + self._parent_frame.cget("border_width"))
if self._orientation == "horizontal":
self._parent_frame.grid_columnconfigure(0, weight=1)
self._parent_frame.grid_rowconfigure(1, weight=1)
self._parent_canvas.grid(row=1, column=0, sticky="nsew", padx=border_spacing, pady=(border_spacing, 0))
self._scrollbar.grid(row=2, column=0, sticky="nsew", padx=border_spacing)
if self._label_text is not None and self._label_text != "":
self._label.grid(row=0, column=0, sticky="ew", padx=border_spacing, pady=border_spacing)
else:
self._label.grid_forget()
elif self._orientation == "vertical":
self._parent_frame.grid_columnconfigure(0, weight=1)
self._parent_frame.grid_rowconfigure(1, weight=1)
self._parent_canvas.grid(row=1, column=0, sticky="nsew", padx=(border_spacing, 0), pady=border_spacing)
self._scrollbar.grid(row=1, column=1, sticky="nsew", pady=border_spacing)
if self._label_text is not None and self._label_text != "":
self._label.grid(row=0, column=0, columnspan=2, sticky="ew", padx=border_spacing, pady=border_spacing)
else:
self._label.grid_forget()
def _set_appearance_mode(self, mode_string):
super()._set_appearance_mode(mode_string)
if self._parent_frame.cget("fg_color") == "transparent":
tkinter.Frame.configure(self, bg=self._apply_appearance_mode(self._parent_frame.cget("bg_color")))
self._parent_canvas.configure(bg=self._apply_appearance_mode(self._parent_frame.cget("bg_color")))
else:
tkinter.Frame.configure(self, bg=self._apply_appearance_mode(self._parent_frame.cget("fg_color")))
self._parent_canvas.configure(bg=self._apply_appearance_mode(self._parent_frame.cget("fg_color")))
def _set_scaling(self, new_widget_scaling, new_window_scaling):
super()._set_scaling(new_widget_scaling, new_window_scaling)
self._parent_canvas.configure(width=self._apply_widget_scaling(self._desired_width),
height=self._apply_widget_scaling(self._desired_height))
def _set_dimensions(self, width=None, height=None):
if width is not None:
self._desired_width = width
if height is not None:
self._desired_height = height
self._parent_canvas.configure(width=self._apply_widget_scaling(self._desired_width),
height=self._apply_widget_scaling(self._desired_height))
def configure(self, **kwargs):
if "width" in kwargs:
self._set_dimensions(width=kwargs.pop("width"))
if "height" in kwargs:
self._set_dimensions(height=kwargs.pop("height"))
if "corner_radius" in kwargs:
new_corner_radius = kwargs.pop("corner_radius")
self._parent_frame.configure(corner_radius=new_corner_radius)
if self._label is not None:
self._label.configure(corner_radius=new_corner_radius)
self._create_grid()
if "border_width" in kwargs:
self._parent_frame.configure(border_width=kwargs.pop("border_width"))
self._create_grid()
if "fg_color" in kwargs:
self._parent_frame.configure(fg_color=kwargs.pop("fg_color"))
if self._parent_frame.cget("fg_color") == "transparent":
tkinter.Frame.configure(self, bg=self._apply_appearance_mode(self._parent_frame.cget("bg_color")))
self._parent_canvas.configure(bg=self._apply_appearance_mode(self._parent_frame.cget("bg_color")))
else:
tkinter.Frame.configure(self, bg=self._apply_appearance_mode(self._parent_frame.cget("fg_color")))
self._parent_canvas.configure(bg=self._apply_appearance_mode(self._parent_frame.cget("fg_color")))
for child in self.winfo_children():
if isinstance(child, CTkBaseClass):
child.configure(bg_color=self._parent_frame.cget("fg_color"))
if "scrollbar_fg_color" in kwargs:
self._scrollbar.configure(fg_color=kwargs.pop("scrollbar_fg_color"))
if "scrollbar_button_color" in kwargs:
self._scrollbar.configure(fg_color=kwargs.pop("scrollbar_button_color"))
if "scrollbar_button_hover_color" in kwargs:
self._scrollbar.configure(fg_color=kwargs.pop("scrollbar_button_hover_color"))
if "label_text" in kwargs:
self._label_text = kwargs.pop("label_text")
self._label.configure(text=self._label_text)
self._create_grid()
if "label_font" in kwargs:
self._label.configure(font=kwargs.pop("label_font"))
if "label_text_color" in kwargs:
self._label.configure(text_color=kwargs.pop("label_text_color"))
if "label_fg_color" in kwargs:
self._label.configure(fg_color=kwargs.pop("label_fg_color"))
if "label_anchor" in kwargs:
self._label.configure(anchor=kwargs.pop("label_anchor"))
self._parent_frame.configure(**kwargs)
def cget(self, attribute_name: str):
if attribute_name == "width":
return self._desired_width
elif attribute_name == "height":
return self._desired_height
elif attribute_name == "label_text":
return self._label_text
elif attribute_name == "label_font":
return self._label.cget("font")
elif attribute_name == "label_text_color":
return self._label.cget("_text_color")
elif attribute_name == "label_fg_color":
return self._label.cget("fg_color")
elif attribute_name == "label_anchor":
return self._label.cget("anchor")
elif attribute_name.startswith("scrollbar_fg_color"):
return self._scrollbar.cget("fg_color")
elif attribute_name.startswith("scrollbar_button_color"):
return self._scrollbar.cget("button_color")
elif attribute_name.startswith("scrollbar_button_hover_color"):
return self._scrollbar.cget("button_hover_color")
else:
return self._parent_frame.cget(attribute_name)
def _fit_frame_dimensions_to_canvas(self, event):
if self._orientation == "horizontal":
self._parent_canvas.itemconfigure(self._create_window_id, height=self._parent_canvas.winfo_height())
elif self._orientation == "vertical":
self._parent_canvas.itemconfigure(self._create_window_id, width=self._parent_canvas.winfo_width())
def _set_scroll_increments(self):
if sys.platform.startswith("win"):
self._parent_canvas.configure(xscrollincrement=1, yscrollincrement=1)
elif sys.platform == "darwin":
self._parent_canvas.configure(xscrollincrement=4, yscrollincrement=8)
def _mouse_wheel_all(self, event):
if self.check_if_master_is_canvas(event.widget):
if sys.platform.startswith("win"):
if self._shift_pressed:
if self._parent_canvas.xview() != (0.0, 1.0):
self._parent_canvas.xview("scroll", -int(event.delta / 6), "units")
else:
if self._parent_canvas.yview() != (0.0, 1.0):
self._parent_canvas.yview("scroll", -int(event.delta / 6), "units")
elif sys.platform == "darwin":
if self._shift_pressed:
if self._parent_canvas.xview() != (0.0, 1.0):
self._parent_canvas.xview("scroll", -event.delta, "units")
else:
if self._parent_canvas.yview() != (0.0, 1.0):
self._parent_canvas.yview("scroll", -event.delta, "units")
else:
if self._shift_pressed:
if self._parent_canvas.xview() != (0.0, 1.0):
self._parent_canvas.xview("scroll", -event.delta, "units")
else:
if self._parent_canvas.yview() != (0.0, 1.0):
self._parent_canvas.yview("scroll", -event.delta, "units")
def _keyboard_shift_press_all(self, event):
self._shift_pressed = True
def _keyboard_shift_release_all(self, event):
self._shift_pressed = False
def check_if_master_is_canvas(self, widget):
if widget == self._parent_canvas:
return True
elif widget.master is not None:
return self.check_if_master_is_canvas(widget.master)
else:
return False
def pack(self, **kwargs):
self._parent_frame.pack(**kwargs)
def place(self, **kwargs):
self._parent_frame.place(**kwargs)
def grid(self, **kwargs):
self._parent_frame.grid(**kwargs)
def pack_forget(self):
self._parent_frame.pack_forget()
def place_forget(self, **kwargs):
self._parent_frame.place_forget()
def grid_forget(self, **kwargs):
self._parent_frame.grid_forget()
def grid_remove(self, **kwargs):
self._parent_frame.grid_remove()
def grid_propagate(self, **kwargs):
self._parent_frame.grid_propagate()
def grid_info(self, **kwargs):
return self._parent_frame.grid_info()
def lift(self, aboveThis=None):
self._parent_frame.lift(aboveThis)
def lower(self, belowThis=None):
self._parent_frame.lower(belowThis)

BIN
customtkinter/windows/widgets/font/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/font/__pycache__/__init__.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/font/__pycache__/ctk_font.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/font/__pycache__/ctk_font.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/font/__pycache__/font_manager.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/image/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/image/__pycache__/ctk_image.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/scaling/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/scaling/__pycache__/scaling_base_class.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/scaling/__pycache__/scaling_tracker.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/theme/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/theme/__pycache__/__init__.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/theme/__pycache__/theme_manager.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/theme/__pycache__/theme_manager.cpython-37.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/utility/__pycache__/__init__.cpython-310.pyc

Binary file not shown.

BIN
customtkinter/windows/widgets/utility/__pycache__/utility_functions.cpython-310.pyc

Binary file not shown.

36
main.py

@ -64,11 +64,13 @@ class Expression:
def valeurs_de_fonction(self, start, end): def valeurs_de_fonction(self, start, end):
""" Calcul les valeurs entre start et end""" """ Calcul les valeurs entre start et end"""
result = [] result = []
for i in range(start, end+1): pas = (end - start) / 1000
while start <= end:
try: try:
result.append((i, self.evalue(i))) result.append((start, self.evalue(start)))
except: except:
pass pass
start += pas
return result return result
@ -121,6 +123,18 @@ class App(ctk.CTk):
self.fonction_frame = ctk.CTkFrame(self, fg_color="transparent") self.fonction_frame = ctk.CTkFrame(self, fg_color="transparent")
self.fonction_bornes_frame = ctk.CTkFrame(self.fonction_frame, corner_radius=None)
self.fonction_bornes_entry = ctk.CTkEntry(self.fonction_bornes_frame)
self.fonction_bornes_entry.insert(0, "-100,100")
self.fonction_bornes_entry.grid(sticky="ew", row=1, padx=10)
self.fonction_bornes_text = ctk.CTkLabel(self.fonction_bornes_frame, text="Entrez les bornes de tracé: (min, max)")
self.fonction_bornes_text.grid(sticky="ew", row=0)
self.fonction_bornes_frame.grid(sticky="ns", column=0, rowspan=2)
self.fonction_screen = ctk.CTkCanvas(self.fonction_frame) self.fonction_screen = ctk.CTkCanvas(self.fonction_frame)
self.fonction_screen.grid(sticky="nsew", column=1, row=0) self.fonction_screen.grid(sticky="nsew", column=1, row=0)
self.fonction_entry = ctk.CTkEntry(self.fonction_frame) self.fonction_entry = ctk.CTkEntry(self.fonction_frame)
@ -238,7 +252,7 @@ class App(ctk.CTk):
ordonnee = max_x / (abs(min_x)+abs(max_x)) ordonnee = max_x / (abs(min_x)+abs(max_x))
for i in range(20): # dessin des lignes verticales for i in range(20): # dessin des lignes verticales
if i == int(20*ordonnee): if i == int(20 - 20*ordonnee):
self.fonction_screen.create_line(0 + i * self.fonction_screen_width/20, 0 self.fonction_screen.create_line(0 + i * self.fonction_screen_width/20, 0
, 0 + i * self.fonction_screen_width/20, self.fonction_screen_height , 0 + i * self.fonction_screen_width/20, self.fonction_screen_height
, fill='red', width=4) , fill='red', width=4)
@ -257,7 +271,7 @@ class App(ctk.CTk):
nb_abscisse_lines = int(20*ratio) # nombre de lignes horizontales à tracer nb_abscisse_lines = int(20*ratio) # nombre de lignes horizontales à tracer
for i in range(nb_abscisse_lines): # dessin des lignes horizontales for i in range(nb_abscisse_lines): # dessin des lignes horizontales
if i == int(nb_abscisse_lines * abscisse): # tracer de l'axe des abscisses if i == math.ceil(nb_abscisse_lines * abscisse): # tracer de l'axe des abscisses
self.fonction_screen.create_line(0, 0 + i * self.fonction_screen_width/20 self.fonction_screen.create_line(0, 0 + i * self.fonction_screen_width/20
, self.fonction_screen_width , self.fonction_screen_width
, 0 + i * self.fonction_screen_width/20, fill='red' , 0 + i * self.fonction_screen_width/20, fill='red'
@ -292,12 +306,13 @@ class App(ctk.CTk):
def draw_graph(self): def draw_graph(self):
"""Dessine les points du graphique""" """Dessine les points du graphique"""
self.fonction_screen.delete('all') self.fonction_screen.delete('all')
fonction_points = npi2tree(inf2npi(parse_string_to_list(self.fonction_entry.get()))).valeurs_de_fonction(-100, 100) min_x, max_x = map(int, self.fonction_bornes_entry.get().split(','))
fonction_points = npi2tree(inf2npi(parse_string_to_list(self.fonction_entry.get()))).valeurs_de_fonction(min_x, max_x)
max_y = max(fonction_points, key=lambda item: item[1])[1] max_y = max(fonction_points, key=lambda item: item[1])[1]
min_y = min(fonction_points, key=lambda item: item[1])[1] min_y = min(fonction_points, key=lambda item: item[1])[1]
self.draw_framing(-1000, 1000, min_y, max_y) self.draw_framing(min_x, max_x, min_y, max_y)
for x, y in fonction_points: for i, (x, y) in enumerate(fonction_points):
image_x = self.fonction_screen_width / 2 + x * (self.fonction_screen_width/len(fonction_points)) image_x = i * (self.fonction_screen_width/len(fonction_points))
image_y = self.fonction_screen_height - (y - min_y) * self.fonction_screen_height / (abs(max_y)+abs(min_y)) image_y = self.fonction_screen_height - (y - min_y) * self.fonction_screen_height / (abs(max_y)+abs(min_y))
self.fonction_screen.create_rectangle(image_x, image_y, image_x, image_y) self.fonction_screen.create_rectangle(image_x, image_y, image_x, image_y)
@ -319,11 +334,9 @@ def parse_string_to_list(text: str) -> list:
if len(buffer_function) == 0: if len(buffer_function) == 0:
number_first = True number_first = True
elif char.isalpha(): elif char.isalpha():
print(char)
buffer_function += char buffer_function += char
else: else:
if number_first: if number_first:
print("number", char)
result.append(float(buffer_number)) result.append(float(buffer_number))
buffer_number = "" buffer_number = ""
number_first = False number_first = False
@ -332,7 +345,6 @@ def parse_string_to_list(text: str) -> list:
result.append(buffer_function) result.append(buffer_function)
buffer_function = "" buffer_function = ""
elif char == '(': elif char == '(':
print("()")
result.append('*') result.append('*')
else: else:
@ -351,7 +363,6 @@ def parse_string_to_list(text: str) -> list:
result.append(buffer_function) result.append(buffer_function)
elif len(buffer_function) != 0: elif len(buffer_function) != 0:
result.append(buffer_function) result.append(buffer_function)
print(result)
return result return result
def npi2tree(expr: list) -> Expression: def npi2tree(expr: list) -> Expression:
@ -399,7 +410,6 @@ def inf2npi(expr: list) -> list:
operator_stack.empiler(val) operator_stack.empiler(val)
while not operator_stack.est_vide(): while not operator_stack.est_vide():
output.append(operator_stack.depiler()) output.append(operator_stack.depiler())
print(output)
return output return output

Loading…
Cancel
Save