fixed simple_example.py

This commit is contained in:
Tom Schimansky 2022-05-05 20:25:37 +02:00
parent 8c0f1d2c43
commit 3eb0d411c5
8 changed files with 113 additions and 17 deletions

View File

@ -67,6 +67,15 @@ def set_default_color_theme(color_string):
CTkThemeManager.load_theme(color_string)
def deactivate_dpi_awareness(deactivate_awareness: bool):
CTkSettings.deactivate_automatic_dpi_awareness = deactivate_awareness
def set_user_scaling(scaling_value: float):
ScalingTracker.set_spacing_scaling(scaling_value)
ScalingTracker.set_widget_scaling(scaling_value)
# Load fonts:
if sys.platform.startswith("win"):
from ctypes import windll, byref, create_unicode_buffer, create_string_buffer
@ -106,7 +115,7 @@ if sys.platform.startswith("win"):
"Using 'circle_shapes' instead. The rendering quality will be very bad!")
CTkSettings.preferred_drawing_method = "circle_shapes"
elif sys.platform == "linux":
elif sys.platform.startswith("linux"):
try:
if not os.path.isdir(os.path.expanduser('~/.fonts/')):
os.mkdir(os.path.expanduser('~/.fonts/'))

View File

@ -4,15 +4,18 @@ import sys
class CTkSettings:
circle_font_is_ready = False
preferred_drawing_method = None
radius_to_char_fine = None
preferred_drawing_method: str = None # 'polygon_shapes', 'font_shapes', 'circle_shapes'
radius_to_char_fine: dict = None # set in self.init_font_character_mapping()
cursor_manipulation_enabled = True
deactivate_macos_window_header_manipulation = False
deactivate_windows_window_header_manipulation = False
deactivate_automatic_dpi_awareness = False
@classmethod
def init_font_character_mapping(cls):
""" optimizations made for Windows 10, 11 only """
radius_to_char_warped = {19: 'B', 18: 'B', 17: 'B', 16: 'B', 15: 'B', 14: 'B', 13: 'B', 12: 'B', 11: 'B', 10: 'B',
9: 'C', 8: 'D', 7: 'C', 6: 'E', 5: 'F', 4: 'G', 3: 'H', 2: 'H', 1: 'H', 0: 'A'}
@ -30,7 +33,6 @@ class CTkSettings:
else: # macOS and Linux
cls.radius_to_char_fine = radius_to_char_fine_windows_10
@classmethod
def init_drawing_method(cls):
""" possible: 'polygon_shapes', 'font_shapes', 'circle_shapes' """

View File

@ -1,6 +1,8 @@
import tkinter
import sys
from .ctk_settings import CTkSettings
class ScalingTracker:
@ -58,9 +60,14 @@ class ScalingTracker:
def update_scaling_callbacks(cls):
for window, callback_list in cls.window_widgets_dict.items():
for callback in callback_list:
callback(cls.window_dpi_scaling_dict[window] * cls.widget_scaling,
cls.window_dpi_scaling_dict[window] * cls.spacing_scaling,
cls.window_dpi_scaling_dict[window] * cls.window_scaling)
if not CTkSettings.deactivate_automatic_dpi_awareness:
callback(cls.window_dpi_scaling_dict[window] * cls.widget_scaling,
cls.window_dpi_scaling_dict[window] * cls.spacing_scaling,
cls.window_dpi_scaling_dict[window] * cls.window_scaling)
else:
callback(cls.widget_scaling,
cls.spacing_scaling,
cls.window_scaling)
@classmethod
def add_widget(cls, widget_callback, widget):
@ -88,6 +95,23 @@ class ScalingTracker:
if window not in cls.window_dpi_scaling_dict:
cls.window_dpi_scaling_dict[window] = cls.get_window_dpi_scaling(window)
@classmethod
def activate_high_dpi_awareness(cls):
""" make process DPI aware, customtkinter elemets will get scaled automatically,
only gets activated when CTk object is created """
if not CTkSettings.deactivate_automatic_dpi_awareness:
if sys.platform == "darwin":
pass # high DPI scaling works automatically on macOS
elif sys.platform.startswith("win"):
from ctypes import windll
windll.shcore.SetProcessDpiAwareness(2)
# Microsoft Docs: https://docs.microsoft.com/en-us/windows/win32/api/shellscalingapi/ne-shellscalingapi-process_dpi_awareness
else:
pass # DPI awareness on Linux not implemented
@classmethod
def get_window_dpi_scaling(cls, window):
if sys.platform == "darwin":
@ -105,7 +129,7 @@ class ScalingTracker:
return (x_dpi.value + y_dpi.value) / (2 * DPI100pc)
else:
return 1
return 1 # DPI awareness on Linux not implemented
@classmethod
def check_dpi_scaling(cls):
@ -118,4 +142,3 @@ class ScalingTracker:
continue
cls.update_loop_running = False

View File

@ -82,14 +82,14 @@ class CTkButton(CTkBaseClass):
self.draw() # initial draw
def configure_basic_grid(self):
# Configuration of a grid system (2x2) in which all parts of CTkButton are centered on one row and one column
# Configuration of a grid system (2x2) in which all parts of CTkButton are centered
self.grid_rowconfigure(0, weight=1)
self.grid_columnconfigure(0, weight=1)
self.grid_rowconfigure(1, weight=1)
self.grid_columnconfigure(1, weight=1)
def set_scaling(self, *args, **kwargs):
super().set_scaling( *args, **kwargs)
super().set_scaling(*args, **kwargs)
if self.text_label is not None:
self.text_label.destroy()
@ -103,7 +103,6 @@ class CTkButton(CTkBaseClass):
self.draw()
def draw(self, no_color_updates=False):
# print("current_height", self.current_height, "desired", self.desired_height)
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.corner_radius),

View File

@ -17,6 +17,7 @@ class CTk(tkinter.Tk):
fg_color="default_theme",
**kwargs):
ScalingTracker.activate_high_dpi_awareness() # make process DPI aware
self.enable_macos_dark_title_bar()
super().__init__(*args, **kwargs)

View File

@ -1,7 +1,6 @@
import tkinter
import tkinter.messagebox
import customtkinter
import sys
customtkinter.set_appearance_mode("System") # Modes: "System" (standard), "Dark", "Light"
customtkinter.set_default_color_theme("blue") # Themes: "blue" (standard), "green", "dark-blue"

View File

@ -14,10 +14,6 @@ def button_function():
def slider_function(value):
customtkinter.ScalingTracker.set_widget_scaling(value * 2)
customtkinter.ScalingTracker.set_spacing_scaling(value * 2)
customtkinter.ScalingTracker.set_window_scaling(value * 2)
progressbar_1.set(value)

View File

@ -0,0 +1,67 @@
import tkinter
import customtkinter # <- import the CustomTkinter module
customtkinter.ScalingTracker.set_window_scaling(1.5)
customtkinter.ScalingTracker.set_spacing_scaling(1.5)
customtkinter.ScalingTracker.set_widget_scaling(1.5)
customtkinter.set_appearance_mode("dark") # Modes: "System" (standard), "Dark", "Light"
customtkinter.set_default_color_theme("blue") # Themes: "blue" (standard), "green", "dark-blue"
root_tk = customtkinter.CTk() # create CTk window like you do with the Tk window (you can also use normal tkinter.Tk window)
root_tk.geometry("400x480")
root_tk.title("CustomTkinter Test")
print(customtkinter.ScalingTracker.get_window_scaling(root_tk))
def button_function():
print("Button click", label_1.text_label.cget("text"))
def slider_function(value):
progressbar_1.set(value)
def check_box_function():
print("checkbox_1:", checkbox_1.get())
y_padding = 13
frame_1 = customtkinter.CTkFrame(master=root_tk, corner_radius=15)
frame_1.pack(pady=20, padx=60, fill="both", expand=True)
label_1 = customtkinter.CTkLabel(master=frame_1, justify=tkinter.LEFT)
label_1.pack(pady=y_padding, padx=10)
progressbar_1 = customtkinter.CTkProgressBar(master=frame_1)
progressbar_1.pack(pady=y_padding, padx=10)
button_1 = customtkinter.CTkButton(master=frame_1, corner_radius=8, command=button_function)
button_1.pack(pady=y_padding, padx=10)
# button_1.configure(state="disabled")
slider_1 = customtkinter.CTkSlider(master=frame_1, command=slider_function, from_=0, to=1)
slider_1.pack(pady=y_padding, padx=10)
slider_1.set(0.5)
entry_1 = customtkinter.CTkEntry(master=frame_1, placeholder_text="CTkEntry")
entry_1.pack(pady=y_padding, padx=10)
checkbox_1 = customtkinter.CTkCheckBox(master=frame_1, command=check_box_function)
checkbox_1.pack(pady=y_padding, padx=10)
radiobutton_var = tkinter.IntVar(value=1)
radiobutton_1 = customtkinter.CTkRadioButton(master=frame_1, variable=radiobutton_var, value=1)
radiobutton_1.pack(pady=y_padding, padx=10)
radiobutton_2 = customtkinter.CTkRadioButton(master=frame_1, variable=radiobutton_var, value=2)
radiobutton_2.pack(pady=y_padding, padx=10)
s_var = tkinter.StringVar(value="on")
switch_1 = customtkinter.CTkSwitch(master=frame_1)
switch_1.pack(pady=y_padding, padx=10)
root_tk.mainloop()