mirror of
https://github.com/TomSchimansky/CustomTkinter.git
synced 2023-08-10 21:13:13 +03:00
removed spacing_scaling, now widget_scaling is used
This commit is contained in:
@@ -5,6 +5,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|||||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||||
|
|
||||||
ToDo:
|
ToDo:
|
||||||
|
- combine widget and spacing scaling to ui scaling
|
||||||
- complete other theme files
|
- complete other theme files
|
||||||
- auto-scaling of images
|
- auto-scaling of images
|
||||||
- image tuple for light/dark mode
|
- image tuple for light/dark mode
|
||||||
|
@@ -99,11 +99,6 @@ def set_widget_scaling(scaling_value: float):
|
|||||||
ScalingTracker.set_widget_scaling(scaling_value)
|
ScalingTracker.set_widget_scaling(scaling_value)
|
||||||
|
|
||||||
|
|
||||||
def set_spacing_scaling(scaling_value: float):
|
|
||||||
""" set scaling for geometry manager calls (place, pack, grid)"""
|
|
||||||
ScalingTracker.set_spacing_scaling(scaling_value)
|
|
||||||
|
|
||||||
|
|
||||||
def set_window_scaling(scaling_value: float):
|
def set_window_scaling(scaling_value: float):
|
||||||
""" set scaling for window dimensions """
|
""" set scaling for window dimensions """
|
||||||
ScalingTracker.set_window_scaling(scaling_value)
|
ScalingTracker.set_window_scaling(scaling_value)
|
||||||
|
@@ -11,7 +11,6 @@ class ScalingTracker:
|
|||||||
|
|
||||||
widget_scaling = 1 # user values which multiply to detected window scaling factor
|
widget_scaling = 1 # user values which multiply to detected window scaling factor
|
||||||
window_scaling = 1
|
window_scaling = 1
|
||||||
spacing_scaling = 1
|
|
||||||
|
|
||||||
update_loop_running = False
|
update_loop_running = False
|
||||||
update_loop_interval = 600 # ms
|
update_loop_interval = 600 # ms
|
||||||
@@ -22,11 +21,6 @@ class ScalingTracker:
|
|||||||
window_root = cls.get_window_root_of_widget(widget)
|
window_root = cls.get_window_root_of_widget(widget)
|
||||||
return cls.window_dpi_scaling_dict[window_root] * cls.widget_scaling
|
return cls.window_dpi_scaling_dict[window_root] * cls.widget_scaling
|
||||||
|
|
||||||
@classmethod
|
|
||||||
def get_spacing_scaling(cls, widget) -> float:
|
|
||||||
window_root = cls.get_window_root_of_widget(widget)
|
|
||||||
return cls.window_dpi_scaling_dict[window_root] * cls.spacing_scaling
|
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def get_window_scaling(cls, window) -> float:
|
def get_window_scaling(cls, window) -> float:
|
||||||
window_root = cls.get_window_root_of_widget(window)
|
window_root = cls.get_window_root_of_widget(window)
|
||||||
@@ -37,11 +31,6 @@ class ScalingTracker:
|
|||||||
cls.widget_scaling = max(widget_scaling_factor, 0.4)
|
cls.widget_scaling = max(widget_scaling_factor, 0.4)
|
||||||
cls.update_scaling_callbacks_all()
|
cls.update_scaling_callbacks_all()
|
||||||
|
|
||||||
@classmethod
|
|
||||||
def set_spacing_scaling(cls, spacing_scaling_factor: float):
|
|
||||||
cls.spacing_scaling = max(spacing_scaling_factor, 0.4)
|
|
||||||
cls.update_scaling_callbacks_all()
|
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def set_window_scaling(cls, window_scaling_factor: float):
|
def set_window_scaling(cls, window_scaling_factor: float):
|
||||||
cls.window_scaling = max(window_scaling_factor, 0.4)
|
cls.window_scaling = max(window_scaling_factor, 0.4)
|
||||||
@@ -63,11 +52,9 @@ class ScalingTracker:
|
|||||||
for set_scaling_callback in callback_list:
|
for set_scaling_callback in callback_list:
|
||||||
if not cls.deactivate_automatic_dpi_awareness:
|
if not cls.deactivate_automatic_dpi_awareness:
|
||||||
set_scaling_callback(cls.window_dpi_scaling_dict[window] * cls.widget_scaling,
|
set_scaling_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)
|
cls.window_dpi_scaling_dict[window] * cls.window_scaling)
|
||||||
else:
|
else:
|
||||||
set_scaling_callback(cls.widget_scaling,
|
set_scaling_callback(cls.widget_scaling,
|
||||||
cls.spacing_scaling,
|
|
||||||
cls.window_scaling)
|
cls.window_scaling)
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
@@ -75,11 +62,9 @@ class ScalingTracker:
|
|||||||
for set_scaling_callback in cls.window_widgets_dict[window]:
|
for set_scaling_callback in cls.window_widgets_dict[window]:
|
||||||
if not cls.deactivate_automatic_dpi_awareness:
|
if not cls.deactivate_automatic_dpi_awareness:
|
||||||
set_scaling_callback(cls.window_dpi_scaling_dict[window] * cls.widget_scaling,
|
set_scaling_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)
|
cls.window_dpi_scaling_dict[window] * cls.window_scaling)
|
||||||
else:
|
else:
|
||||||
set_scaling_callback(cls.widget_scaling,
|
set_scaling_callback(cls.widget_scaling,
|
||||||
cls.spacing_scaling,
|
|
||||||
cls.window_scaling)
|
cls.window_scaling)
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
|
@@ -27,7 +27,6 @@ class DropdownMenu(tkinter.Menu):
|
|||||||
|
|
||||||
ScalingTracker.add_widget(self._set_scaling, self)
|
ScalingTracker.add_widget(self._set_scaling, self)
|
||||||
self._widget_scaling = ScalingTracker.get_widget_scaling(self)
|
self._widget_scaling = ScalingTracker.get_widget_scaling(self)
|
||||||
self._spacing_scaling = ScalingTracker.get_spacing_scaling(self)
|
|
||||||
|
|
||||||
AppearanceModeTracker.add(self._set_appearance_mode, self)
|
AppearanceModeTracker.add(self._set_appearance_mode, self)
|
||||||
self._appearance_mode = AppearanceModeTracker.get_mode() # 0: "Light" 1: "Dark"
|
self._appearance_mode = AppearanceModeTracker.get_mode() # 0: "Light" 1: "Dark"
|
||||||
@@ -214,9 +213,8 @@ class DropdownMenu(tkinter.Menu):
|
|||||||
f"font=customtkinter.CTkFont(family='<name>', size=<size in px>)\n" +
|
f"font=customtkinter.CTkFont(family='<name>', size=<size in px>)\n" +
|
||||||
f"font=('<name>', <size in px>)\n")
|
f"font=('<name>', <size in px>)\n")
|
||||||
|
|
||||||
def _set_scaling(self, new_widget_scaling, new_spacing_scaling, new_window_scaling):
|
def _set_scaling(self, new_widget_scaling, new_window_scaling):
|
||||||
self._widget_scaling = new_widget_scaling
|
self._widget_scaling = new_widget_scaling
|
||||||
self._spacing_scaling = new_spacing_scaling
|
|
||||||
|
|
||||||
self._configure_menu_for_platforms()
|
self._configure_menu_for_platforms()
|
||||||
|
|
||||||
|
@@ -51,7 +51,6 @@ class CTkBaseClass(tkinter.Frame):
|
|||||||
# scaling
|
# scaling
|
||||||
ScalingTracker.add_widget(self._set_scaling, self) # add callback for automatic scaling changes
|
ScalingTracker.add_widget(self._set_scaling, self) # add callback for automatic scaling changes
|
||||||
self._widget_scaling = ScalingTracker.get_widget_scaling(self)
|
self._widget_scaling = ScalingTracker.get_widget_scaling(self)
|
||||||
self._spacing_scaling = ScalingTracker.get_spacing_scaling(self)
|
|
||||||
|
|
||||||
super().configure(width=self._apply_widget_scaling(self._desired_width),
|
super().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))
|
||||||
@@ -175,8 +174,8 @@ class CTkBaseClass(tkinter.Frame):
|
|||||||
master_widget = self.master
|
master_widget = self.master
|
||||||
|
|
||||||
if isinstance(master_widget, (CTkBaseClass, CTk, CTkToplevel)) and hasattr(master_widget, "_fg_color"):
|
if isinstance(master_widget, (CTkBaseClass, CTk, CTkToplevel)) and hasattr(master_widget, "_fg_color"):
|
||||||
if master_widget._fg_color is not None:
|
if master_widget.cget("fg_color") is not None:
|
||||||
return master_widget._fg_color
|
return master_widget.cget("fg_color")
|
||||||
|
|
||||||
# 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, "master"):
|
||||||
@@ -204,9 +203,8 @@ class CTkBaseClass(tkinter.Frame):
|
|||||||
super().configure(bg=ThemeManager.single_color(self._bg_color, self._appearance_mode))
|
super().configure(bg=ThemeManager.single_color(self._bg_color, self._appearance_mode))
|
||||||
self._draw()
|
self._draw()
|
||||||
|
|
||||||
def _set_scaling(self, new_widget_scaling, new_spacing_scaling, new_window_scaling):
|
def _set_scaling(self, new_widget_scaling, new_window_scaling):
|
||||||
self._widget_scaling = new_widget_scaling
|
self._widget_scaling = new_widget_scaling
|
||||||
self._spacing_scaling = new_spacing_scaling
|
|
||||||
|
|
||||||
super().configure(width=self._apply_widget_scaling(self._desired_width),
|
super().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))
|
||||||
@@ -229,12 +227,6 @@ class CTkBaseClass(tkinter.Frame):
|
|||||||
else:
|
else:
|
||||||
return value
|
return value
|
||||||
|
|
||||||
def _apply_spacing_scaling(self, value: Union[int, float, str]) -> Union[float, str]:
|
|
||||||
if isinstance(value, (int, float)):
|
|
||||||
return value * self._spacing_scaling
|
|
||||||
else:
|
|
||||||
return value
|
|
||||||
|
|
||||||
def _apply_font_scaling(self, font: Union[Tuple, CTkFont]) -> tuple:
|
def _apply_font_scaling(self, font: Union[Tuple, CTkFont]) -> tuple:
|
||||||
""" Takes CTkFont object and returns tuple font with scaled size, has to be called again for every change of font object """
|
""" Takes CTkFont object and returns tuple font with scaled size, has to be called again for every change of font object """
|
||||||
if type(font) == tuple:
|
if type(font) == tuple:
|
||||||
@@ -257,19 +249,19 @@ class CTkBaseClass(tkinter.Frame):
|
|||||||
|
|
||||||
if "pady" in scaled_kwargs:
|
if "pady" in scaled_kwargs:
|
||||||
if isinstance(scaled_kwargs["pady"], (int, float, str)):
|
if isinstance(scaled_kwargs["pady"], (int, float, str)):
|
||||||
scaled_kwargs["pady"] = self._apply_spacing_scaling(scaled_kwargs["pady"])
|
scaled_kwargs["pady"] = self._apply_widget_scaling(scaled_kwargs["pady"])
|
||||||
elif isinstance(scaled_kwargs["pady"], tuple):
|
elif isinstance(scaled_kwargs["pady"], tuple):
|
||||||
scaled_kwargs["pady"] = tuple([self._apply_spacing_scaling(v) for v in scaled_kwargs["pady"]])
|
scaled_kwargs["pady"] = tuple([self._apply_widget_scaling(v) for v in scaled_kwargs["pady"]])
|
||||||
if "padx" in kwargs:
|
if "padx" in kwargs:
|
||||||
if isinstance(scaled_kwargs["padx"], (int, float, str)):
|
if isinstance(scaled_kwargs["padx"], (int, float, str)):
|
||||||
scaled_kwargs["padx"] = self._apply_spacing_scaling(scaled_kwargs["padx"])
|
scaled_kwargs["padx"] = self._apply_widget_scaling(scaled_kwargs["padx"])
|
||||||
elif isinstance(scaled_kwargs["padx"], tuple):
|
elif isinstance(scaled_kwargs["padx"], tuple):
|
||||||
scaled_kwargs["padx"] = tuple([self._apply_spacing_scaling(v) for v in scaled_kwargs["padx"]])
|
scaled_kwargs["padx"] = tuple([self._apply_widget_scaling(v) for v in scaled_kwargs["padx"]])
|
||||||
|
|
||||||
if "x" in scaled_kwargs:
|
if "x" in scaled_kwargs:
|
||||||
scaled_kwargs["x"] = self._apply_spacing_scaling(scaled_kwargs["x"])
|
scaled_kwargs["x"] = self._apply_widget_scaling(scaled_kwargs["x"])
|
||||||
if "y" in scaled_kwargs:
|
if "y" in scaled_kwargs:
|
||||||
scaled_kwargs["y"] = self._apply_spacing_scaling(scaled_kwargs["y"])
|
scaled_kwargs["y"] = self._apply_widget_scaling(scaled_kwargs["y"])
|
||||||
|
|
||||||
return scaled_kwargs
|
return scaled_kwargs
|
||||||
|
|
||||||
|
@@ -97,7 +97,7 @@ class CTk(tkinter.Tk):
|
|||||||
self._current_width = round(detected_width / self._window_scaling) # adjust current size according to new size given by event
|
self._current_width = round(detected_width / self._window_scaling) # adjust current size according to new size given by event
|
||||||
self._current_height = round(detected_height / self._window_scaling) # _current_width and _current_height are independent of the scale
|
self._current_height = round(detected_height / self._window_scaling) # _current_width and _current_height are independent of the scale
|
||||||
|
|
||||||
def _set_scaling(self, new_widget_scaling, new_spacing_scaling, new_window_scaling):
|
def _set_scaling(self, new_widget_scaling, new_window_scaling):
|
||||||
self._window_scaling = new_window_scaling
|
self._window_scaling = new_window_scaling
|
||||||
|
|
||||||
# block update_dimensions_event to prevent current_width and current_height to get updated
|
# block update_dimensions_event to prevent current_width and current_height to get updated
|
||||||
|
@@ -84,7 +84,7 @@ class CTkToplevel(tkinter.Toplevel):
|
|||||||
self._current_width = round(detected_width / self._window_scaling) # adjust current size according to new size given by event
|
self._current_width = round(detected_width / self._window_scaling) # adjust current size according to new size given by event
|
||||||
self._current_height = round(detected_height / self._window_scaling) # _current_width and _current_height are independent of the scale
|
self._current_height = round(detected_height / self._window_scaling) # _current_width and _current_height are independent of the scale
|
||||||
|
|
||||||
def _set_scaling(self, new_widget_scaling, new_spacing_scaling, new_window_scaling):
|
def _set_scaling(self, new_widget_scaling, new_window_scaling):
|
||||||
self._window_scaling = new_window_scaling
|
self._window_scaling = new_window_scaling
|
||||||
|
|
||||||
# force new dimensions on window by using min, max, and geometry
|
# force new dimensions on window by using min, max, and geometry
|
||||||
|
@@ -149,7 +149,6 @@ class App(customtkinter.CTk):
|
|||||||
|
|
||||||
def change_scaling(self, new_scaling: str):
|
def change_scaling(self, new_scaling: str):
|
||||||
new_scaling_float = int(new_scaling.replace("%", "")) / 100
|
new_scaling_float = int(new_scaling.replace("%", "")) / 100
|
||||||
customtkinter.set_spacing_scaling(new_scaling_float)
|
|
||||||
customtkinter.set_widget_scaling(new_scaling_float)
|
customtkinter.set_widget_scaling(new_scaling_float)
|
||||||
|
|
||||||
def sidebar_button_callback(self):
|
def sidebar_button_callback(self):
|
||||||
|
@@ -54,6 +54,9 @@ class App(customtkinter.CTk):
|
|||||||
hover_color="#C77C78", command=self.button_function)
|
hover_color="#C77C78", command=self.button_function)
|
||||||
self.button_5.grid(row=0, column=1, padx=20, pady=20)
|
self.button_5.grid(row=0, column=1, padx=20, pady=20)
|
||||||
|
|
||||||
|
self.scaling_button = customtkinter.CTkSegmentedButton(self, values=[0.8, 0.9, 1.0, 1.1, 1.2, 1.5])
|
||||||
|
self.scaling_button.grid(row=1, column=0, pady=(0, 20))
|
||||||
|
|
||||||
def load_image(self, path, image_size):
|
def load_image(self, path, image_size):
|
||||||
""" load rectangular image with path relative to PATH """
|
""" load rectangular image with path relative to PATH """
|
||||||
return ImageTk.PhotoImage(Image.open(PATH + path).resize((image_size, image_size)))
|
return ImageTk.PhotoImage(Image.open(PATH + path).resize((image_size, image_size)))
|
||||||
|
@@ -13,7 +13,6 @@ frame_2.grid(row=0, column=1, sticky="nsew", padx=10, pady=10)
|
|||||||
|
|
||||||
def set_scaling(scaling):
|
def set_scaling(scaling):
|
||||||
customtkinter.set_widget_scaling(scaling)
|
customtkinter.set_widget_scaling(scaling)
|
||||||
customtkinter.set_spacing_scaling(scaling)
|
|
||||||
|
|
||||||
scaling_button = customtkinter.CTkSegmentedButton(frame_1, values=[0.8, 0.9, 1.0, 1.1, 1.2, 1.3, 1.5, 2.0], command=set_scaling)
|
scaling_button = customtkinter.CTkSegmentedButton(frame_1, values=[0.8, 0.9, 1.0, 1.1, 1.2, 1.3, 1.5, 2.0], command=set_scaling)
|
||||||
scaling_button.pack(pady=(2, 10))
|
scaling_button.pack(pady=(2, 10))
|
||||||
|
@@ -34,7 +34,6 @@ combobox_1 = customtkinter.CTkComboBox(app, variable=variable, values=countries,
|
|||||||
combobox_1.pack(pady=20, padx=10)
|
combobox_1.pack(pady=20, padx=10)
|
||||||
|
|
||||||
def set_new_scaling(scaling):
|
def set_new_scaling(scaling):
|
||||||
customtkinter.set_spacing_scaling(scaling)
|
|
||||||
customtkinter.set_window_scaling(scaling)
|
customtkinter.set_window_scaling(scaling)
|
||||||
customtkinter.set_widget_scaling(scaling)
|
customtkinter.set_widget_scaling(scaling)
|
||||||
|
|
||||||
|
@@ -22,7 +22,6 @@ def button_function():
|
|||||||
|
|
||||||
def slider_function(value):
|
def slider_function(value):
|
||||||
customtkinter.set_widget_scaling(value * 2)
|
customtkinter.set_widget_scaling(value * 2)
|
||||||
customtkinter.set_spacing_scaling(value * 2)
|
|
||||||
customtkinter.set_window_scaling(value * 2)
|
customtkinter.set_window_scaling(value * 2)
|
||||||
progressbar_1.set(value)
|
progressbar_1.set(value)
|
||||||
|
|
||||||
|
@@ -20,12 +20,11 @@ top_tk.geometry("500x500")
|
|||||||
|
|
||||||
def button_function():
|
def button_function():
|
||||||
app.geometry(f"{200}x{200}")
|
app.geometry(f"{200}x{200}")
|
||||||
print("Button click", label_1.text_label.cget("text"))
|
print("Button click", label_1.cget("text"))
|
||||||
|
|
||||||
|
|
||||||
def slider_function(value):
|
def slider_function(value):
|
||||||
customtkinter.set_widget_scaling(value * 2)
|
customtkinter.set_widget_scaling(value * 2)
|
||||||
customtkinter.set_spacing_scaling(value * 2)
|
|
||||||
customtkinter.set_window_scaling(value * 2)
|
customtkinter.set_window_scaling(value * 2)
|
||||||
progressbar_1.set(value)
|
progressbar_1.set(value)
|
||||||
|
|
||||||
|
@@ -2,7 +2,6 @@ import customtkinter
|
|||||||
|
|
||||||
#customtkinter.set_widget_scaling(0.9)
|
#customtkinter.set_widget_scaling(0.9)
|
||||||
#customtkinter.set_window_scaling(0.9)
|
#customtkinter.set_window_scaling(0.9)
|
||||||
#customtkinter.set_spacing_scaling(0.9)
|
|
||||||
|
|
||||||
customtkinter.set_appearance_mode("dark")
|
customtkinter.set_appearance_mode("dark")
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user