tkfluent 0.0.2__py3-none-any.whl → 0.0.4__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- tkflu/__init__.py +11 -0
- tkflu/__main__.py +39 -4
- tkflu/badge.py +5 -4
- tkflu/button.py +307 -111
- tkflu/bwm.py +177 -0
- tkflu/constants.py +15 -0
- tkflu/entry.py +67 -20
- tkflu/frame.py +40 -12
- tkflu/icons.py +47 -0
- tkflu/menu.py +103 -0
- tkflu/menubar.py +140 -0
- tkflu/popupmenu.py +56 -0
- tkflu/popupwindow.py +31 -0
- tkflu/text.py +60 -20
- tkflu/thememanager.py +2 -1
- tkflu/togglebutton.py +6 -48
- tkflu/tooltip.py +8 -0
- tkflu/toplevel.py +29 -0
- tkflu/window.py +9 -172
- tkflu/winico.py +25 -0
- {tkfluent-0.0.2.dist-info → tkfluent-0.0.4.dist-info}/METADATA +7 -6
- tkfluent-0.0.4.dist-info/RECORD +31 -0
- {tkfluent-0.0.2.dist-info → tkfluent-0.0.4.dist-info}/WHEEL +1 -1
- tkfluent-0.0.2.dist-info/RECORD +0 -21
tkflu/menubar.py
ADDED
@@ -0,0 +1,140 @@
|
|
1
|
+
from tkinter import Frame, Menu
|
2
|
+
from tkdeft.object import DObject
|
3
|
+
|
4
|
+
|
5
|
+
class FluMenuBar(Frame, DObject):
|
6
|
+
def __init__(self, *args, mode="light", height=40, **kwargs):
|
7
|
+
self._init(mode)
|
8
|
+
|
9
|
+
super().__init__(*args, height=height, **kwargs)
|
10
|
+
|
11
|
+
self._draw(None)
|
12
|
+
|
13
|
+
self.bind("<Configure>", self._event_configure, add="+")
|
14
|
+
|
15
|
+
def _init(self, mode):
|
16
|
+
|
17
|
+
from easydict import EasyDict
|
18
|
+
|
19
|
+
self.attributes = EasyDict(
|
20
|
+
{
|
21
|
+
"back_color": "#f3f3f3",
|
22
|
+
|
23
|
+
"actions": {}
|
24
|
+
}
|
25
|
+
)
|
26
|
+
|
27
|
+
self.theme(mode=mode)
|
28
|
+
|
29
|
+
def add_command(self, custom_widget=None, width=40, **kwargs):
|
30
|
+
if custom_widget:
|
31
|
+
widget = custom_widget(self)
|
32
|
+
else:
|
33
|
+
from .button import FluButton
|
34
|
+
widget = FluButton(self, width=width)
|
35
|
+
if "label" in kwargs:
|
36
|
+
label = kwargs.pop("label")
|
37
|
+
else:
|
38
|
+
label = ""
|
39
|
+
if "style" in kwargs:
|
40
|
+
style = kwargs.pop("style")
|
41
|
+
else:
|
42
|
+
style = "menu"
|
43
|
+
if "command" in kwargs:
|
44
|
+
command = kwargs.pop("command")
|
45
|
+
else:
|
46
|
+
def empty():
|
47
|
+
pass
|
48
|
+
|
49
|
+
command = empty
|
50
|
+
if "id" in kwargs:
|
51
|
+
id = kwargs.pop("id")
|
52
|
+
else:
|
53
|
+
id = widget._w
|
54
|
+
if hasattr(widget, "dconfigure"):
|
55
|
+
widget.dconfigure(text=label, command=command)
|
56
|
+
else:
|
57
|
+
if hasattr(widget, "configure"):
|
58
|
+
widget.configure(text=label, command=command)
|
59
|
+
if hasattr(widget, "theme"):
|
60
|
+
widget.theme(style=style)
|
61
|
+
|
62
|
+
widget.pack(side="left", padx=5, pady=5)
|
63
|
+
self.dcget("actions")[id] = widget
|
64
|
+
|
65
|
+
from .menu import FluMenu
|
66
|
+
|
67
|
+
def add_cascade(self, custom_widget=None, width=40, menu: FluMenu = None, **kwargs):
|
68
|
+
if custom_widget:
|
69
|
+
widget = custom_widget(self)
|
70
|
+
else:
|
71
|
+
from .button import FluButton
|
72
|
+
widget = FluButton(self, width=width)
|
73
|
+
if "label" in kwargs:
|
74
|
+
label = kwargs.pop("label")
|
75
|
+
else:
|
76
|
+
label = ""
|
77
|
+
if "style" in kwargs:
|
78
|
+
style = kwargs.pop("style")
|
79
|
+
else:
|
80
|
+
style = "menu"
|
81
|
+
if "id" in kwargs:
|
82
|
+
id = kwargs.pop("id")
|
83
|
+
else:
|
84
|
+
id = widget._w
|
85
|
+
|
86
|
+
def command():
|
87
|
+
menu.focus_set()
|
88
|
+
menu.popup(widget.winfo_rootx(), widget.winfo_rooty() + widget.winfo_height())
|
89
|
+
menu.window.deiconify()
|
90
|
+
menu.window.attributes("-topmost")
|
91
|
+
|
92
|
+
if hasattr(widget, "dconfigure"):
|
93
|
+
widget.dconfigure(text=label, command=command)
|
94
|
+
else:
|
95
|
+
if hasattr(widget, "configure"):
|
96
|
+
widget.configure(text=label, command=command)
|
97
|
+
if hasattr(widget, "theme"):
|
98
|
+
widget.theme(style=style)
|
99
|
+
|
100
|
+
widget.pack(side="left", padx=5, pady=5)
|
101
|
+
self.dcget("actions")[id] = widget
|
102
|
+
|
103
|
+
def action(self, id):
|
104
|
+
return self.dcget("actions")[id]
|
105
|
+
|
106
|
+
def theme(self, mode="light"):
|
107
|
+
self.theme_myself(mode=mode)
|
108
|
+
|
109
|
+
actions = self.dcget("actions")
|
110
|
+
|
111
|
+
for key in actions:
|
112
|
+
widget = actions[key]
|
113
|
+
if hasattr(widget, "theme"):
|
114
|
+
widget.theme(mode=mode)
|
115
|
+
if hasattr(widget, "_draw"):
|
116
|
+
widget._draw()
|
117
|
+
widget.update()
|
118
|
+
|
119
|
+
def theme_myself(self, mode="light"):
|
120
|
+
self.mode = mode
|
121
|
+
if mode.lower() == "dark":
|
122
|
+
self._dark()
|
123
|
+
else:
|
124
|
+
self._light()
|
125
|
+
|
126
|
+
def _light(self):
|
127
|
+
self.dconfigure(
|
128
|
+
back_color="#f3f3f3"
|
129
|
+
)
|
130
|
+
|
131
|
+
def _dark(self):
|
132
|
+
self.dconfigure(
|
133
|
+
back_color="#202020"
|
134
|
+
)
|
135
|
+
|
136
|
+
def _draw(self, event=None):
|
137
|
+
self.config(background=self.attributes.back_color)
|
138
|
+
|
139
|
+
def _event_configure(self, event=None):
|
140
|
+
self._draw(event)
|
tkflu/popupmenu.py
ADDED
@@ -0,0 +1,56 @@
|
|
1
|
+
from .frame import FluFrame
|
2
|
+
from .popupwindow import FluPopupWindow
|
3
|
+
|
4
|
+
|
5
|
+
class FluPopupMenuWindow(FluPopupWindow):
|
6
|
+
def __init__(self, *args, **kwargs):
|
7
|
+
super().__init__(*args, **kwargs)
|
8
|
+
|
9
|
+
|
10
|
+
class FluPopupMenu(FluFrame):
|
11
|
+
def __init__(self, *args, width=100, height=46, transparent_color="#ffefa2", style="popupmenu", **kwargs):
|
12
|
+
self.window = FluPopupMenuWindow(transparent_color=transparent_color, width=width, height=height)
|
13
|
+
|
14
|
+
super().__init__(self.window, *args, style=style, **kwargs)
|
15
|
+
|
16
|
+
self.pack(fill="both", expand="yes", padx=5, pady=5)
|
17
|
+
|
18
|
+
def wm_attributes(self, *args, **kwargs):
|
19
|
+
self.window.wm_attributes(*args, **kwargs)
|
20
|
+
|
21
|
+
attributes = wm_attributes
|
22
|
+
|
23
|
+
def wm_protocol(self, *args, **kwargs):
|
24
|
+
self.window.wm_protocol(*args, **kwargs)
|
25
|
+
|
26
|
+
protocol = wm_protocol
|
27
|
+
|
28
|
+
def wm_deiconify(self, *args, **kwargs):
|
29
|
+
self.window.wm_deiconify(*args, **kwargs)
|
30
|
+
|
31
|
+
deiconify = wm_deiconify
|
32
|
+
|
33
|
+
def wm_withdraw(self, *args, **kwargs):
|
34
|
+
self.window.wm_withdraw(*args, **kwargs)
|
35
|
+
|
36
|
+
withdraw = wm_withdraw
|
37
|
+
|
38
|
+
def wm_iconify(self, *args, **kwargs):
|
39
|
+
self.window.wm_iconify(*args, **kwargs)
|
40
|
+
|
41
|
+
iconify = wm_iconify
|
42
|
+
|
43
|
+
def wm_resizable(self, *args, **kwargs):
|
44
|
+
self.window.wm_resizable(*args, **kwargs)
|
45
|
+
|
46
|
+
resizable = wm_resizable
|
47
|
+
|
48
|
+
def wm_geometry(self, *args, **kwargs):
|
49
|
+
self.window.wm_geometry(*args, **kwargs)
|
50
|
+
|
51
|
+
geometry = wm_geometry
|
52
|
+
|
53
|
+
def wm_popup(self, x, y):
|
54
|
+
self.window.popup(x=x, y=y)
|
55
|
+
|
56
|
+
popup = wm_popup
|
tkflu/popupwindow.py
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
from tkinter import Toplevel
|
2
|
+
|
3
|
+
|
4
|
+
class FluPopupWindow(Toplevel):
|
5
|
+
def __init__(self, *args, transparent_color="#ffefa2", mode="light", width=100, height=46, **kwargs):
|
6
|
+
super().__init__(*args, background=transparent_color, **kwargs)
|
7
|
+
|
8
|
+
self.theme(mode=mode)
|
9
|
+
|
10
|
+
self.geometry(f"{width}x{height}")
|
11
|
+
|
12
|
+
self.transient_color = transparent_color
|
13
|
+
self.overrideredirect(True)
|
14
|
+
self.attributes("-transparentcolor", transparent_color)
|
15
|
+
|
16
|
+
self.withdraw()
|
17
|
+
|
18
|
+
self.bind("<FocusOut>", self._event_focusout, add="+")
|
19
|
+
|
20
|
+
def _event_focusout(self, event=None):
|
21
|
+
self.withdraw()
|
22
|
+
|
23
|
+
def popup(self, x, y):
|
24
|
+
self.geometry(f"+{x}+{y}")
|
25
|
+
|
26
|
+
def theme(self, mode=None):
|
27
|
+
if mode:
|
28
|
+
self.mode = mode
|
29
|
+
for widget in self.winfo_children():
|
30
|
+
if hasattr(widget, "theme"):
|
31
|
+
widget.theme(mode=self.mode.lower())
|
tkflu/text.py
CHANGED
@@ -16,7 +16,7 @@ class FluTextDraw(DSvgDraw):
|
|
16
16
|
drawing = self.create_drawing(x2 - x1, y2 - y1, temppath=temppath)
|
17
17
|
border = drawing[1].linearGradient(start=(x1, y1), end=(x1, y2), id="DButton.Border")
|
18
18
|
border.add_stop_color("0%", outline)
|
19
|
-
border.add_stop_color("
|
19
|
+
border.add_stop_color("90%", outline)
|
20
20
|
border.add_stop_color("100%", outline2)
|
21
21
|
drawing[1].defs.add(border)
|
22
22
|
drawing[1].add(
|
@@ -54,6 +54,7 @@ class FluText(FluTextCanvas, DDrawWidget):
|
|
54
54
|
font=None,
|
55
55
|
cursor="xterm",
|
56
56
|
mode="light",
|
57
|
+
state="normal",
|
57
58
|
**kwargs):
|
58
59
|
self._init(mode)
|
59
60
|
|
@@ -70,6 +71,12 @@ class FluText(FluTextCanvas, DDrawWidget):
|
|
70
71
|
|
71
72
|
super().__init__(*args, width=width, height=height, cursor=cursor, **kwargs)
|
72
73
|
|
74
|
+
self.bind("<FocusIn>", self._event_focus_in, add="+")
|
75
|
+
|
76
|
+
self.dconfigure(
|
77
|
+
state=state,
|
78
|
+
)
|
79
|
+
|
73
80
|
if font is None:
|
74
81
|
from tkdeft.utility.fonts import SegoeFont
|
75
82
|
self.attributes.font = SegoeFont()
|
@@ -80,11 +87,11 @@ class FluText(FluTextCanvas, DDrawWidget):
|
|
80
87
|
self.attributes = EasyDict(
|
81
88
|
{
|
82
89
|
"font": None,
|
90
|
+
"state": "normal",
|
83
91
|
|
84
92
|
"rest": {},
|
85
|
-
|
86
|
-
"
|
87
|
-
|
93
|
+
"focus": {},
|
94
|
+
"disabled": {},
|
88
95
|
}
|
89
96
|
)
|
90
97
|
|
@@ -97,20 +104,32 @@ class FluText(FluTextCanvas, DDrawWidget):
|
|
97
104
|
|
98
105
|
self.delete("all")
|
99
106
|
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
+
state = self.dcget("state")
|
108
|
+
|
109
|
+
if state == "normal":
|
110
|
+
self.text.configure(state="normal")
|
111
|
+
if self.isfocus:
|
112
|
+
_back_color = self.attributes.focus.back_color
|
113
|
+
_border_color = self.attributes.focus.border_color
|
114
|
+
_border_color2 = self.attributes.focus.border_color2
|
115
|
+
_border_width = self.attributes.focus.border_width
|
116
|
+
_radius = self.attributes.focus.radius
|
117
|
+
_text_color = self.attributes.focus.text_color
|
118
|
+
else:
|
119
|
+
_back_color = self.attributes.rest.back_color
|
120
|
+
_border_color = self.attributes.rest.border_color
|
121
|
+
_border_color2 = self.attributes.rest.border_color2
|
122
|
+
_border_width = self.attributes.rest.border_width
|
123
|
+
_radius = self.attributes.rest.radius
|
124
|
+
_text_color = self.attributes.rest.text_color
|
107
125
|
else:
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
126
|
+
self.text.configure(state="disabled")
|
127
|
+
_back_color = self.attributes.disabled.back_color
|
128
|
+
_border_color = self.attributes.disabled.border_color
|
129
|
+
_border_color2 = self.attributes.disabled.border_color2
|
130
|
+
_border_width = self.attributes.disabled.border_width
|
131
|
+
_radius = self.attributes.disabled.radius
|
132
|
+
_text_color = self.attributes.disabled.text_color
|
114
133
|
|
115
134
|
self.text.configure(
|
116
135
|
background=_back_color, insertbackground=_text_color, foreground=_text_color,
|
@@ -123,6 +142,11 @@ class FluText(FluTextCanvas, DDrawWidget):
|
|
123
142
|
fill=_back_color, outline=_border_color, outline2=_border_color2, width=_border_width
|
124
143
|
)
|
125
144
|
|
145
|
+
self.element_line = self.create_line(
|
146
|
+
_radius / 3, self.winfo_height() - _radius / 3, self.winfo_width() - _radius / 3, self.winfo_height() - _radius / 3,
|
147
|
+
width=1, fill=_border_color2
|
148
|
+
)
|
149
|
+
|
126
150
|
self.element_text = self.create_window(
|
127
151
|
self.winfo_width() / 2, self.winfo_height() / 2,
|
128
152
|
window=self.text,
|
@@ -151,7 +175,7 @@ class FluText(FluTextCanvas, DDrawWidget):
|
|
151
175
|
self.dconfigure(
|
152
176
|
rest={
|
153
177
|
"back_color": "#ffffff",
|
154
|
-
"border_color": "#
|
178
|
+
"border_color": "#e5e5e5",
|
155
179
|
"border_color2": "#8d8d8d",
|
156
180
|
"border_width": 1,
|
157
181
|
"radius": 6,
|
@@ -159,11 +183,19 @@ class FluText(FluTextCanvas, DDrawWidget):
|
|
159
183
|
},
|
160
184
|
focus={
|
161
185
|
"back_color": "#ffffff",
|
162
|
-
"border_color": "#
|
186
|
+
"border_color": "#e5e5e5",
|
163
187
|
"border_color2": "#005fb8",
|
164
188
|
"border_width": 2,
|
165
189
|
"radius": 6,
|
166
190
|
"text_color": "#636363",
|
191
|
+
},
|
192
|
+
disabled={
|
193
|
+
"back_color": "#fdfdfd",
|
194
|
+
"border_color": "#e5e5e5",
|
195
|
+
"border_color2": "#e5e5e5",
|
196
|
+
"border_width": 1,
|
197
|
+
"radius": 6,
|
198
|
+
"text_color": "#a2a2a2",
|
167
199
|
}
|
168
200
|
)
|
169
201
|
|
@@ -184,5 +216,13 @@ class FluText(FluTextCanvas, DDrawWidget):
|
|
184
216
|
"border_width": 2,
|
185
217
|
"radius": 6,
|
186
218
|
"text_color": "#ffffff",
|
219
|
+
},
|
220
|
+
disabled={
|
221
|
+
"back_color": "#2a2a2a",
|
222
|
+
"border_color": "#303030",
|
223
|
+
"border_color2": "#303030",
|
224
|
+
"border_width": 1,
|
225
|
+
"radius": 6,
|
226
|
+
"text_color": "#787878",
|
187
227
|
}
|
188
|
-
)
|
228
|
+
)
|
tkflu/thememanager.py
CHANGED
@@ -1,8 +1,9 @@
|
|
1
1
|
from .window import FluWindow
|
2
|
+
from .toplevel import FluToplevel
|
2
3
|
|
3
4
|
|
4
5
|
class FluThemeManager(object):
|
5
|
-
def __init__(self, window
|
6
|
+
def __init__(self, window=None, mode: str = "light"):
|
6
7
|
if window:
|
7
8
|
self._window = window
|
8
9
|
else:
|
tkflu/togglebutton.py
CHANGED
@@ -93,57 +93,15 @@ class FluToggleButton(FluToggleButtonCanvas, DDrawWidget):
|
|
93
93
|
"checked": False,
|
94
94
|
|
95
95
|
"uncheck": {
|
96
|
-
"rest": {
|
97
|
-
|
98
|
-
|
99
|
-
"border_color2": None,
|
100
|
-
"border_width": None,
|
101
|
-
"radius": None,
|
102
|
-
"text_color": None,
|
103
|
-
},
|
104
|
-
"hover": {
|
105
|
-
"back_color": None,
|
106
|
-
"border_color": None,
|
107
|
-
"border_color2": None,
|
108
|
-
"border_width": None,
|
109
|
-
"radius": None,
|
110
|
-
"text_color": None,
|
111
|
-
},
|
112
|
-
"pressed": {
|
113
|
-
"back_color": None,
|
114
|
-
"border_color": None,
|
115
|
-
"border_color2": None,
|
116
|
-
"border_width": None,
|
117
|
-
"radius": None,
|
118
|
-
"text_color": None,
|
119
|
-
}
|
96
|
+
"rest": {},
|
97
|
+
"hover": {},
|
98
|
+
"pressed": {}
|
120
99
|
},
|
121
100
|
|
122
101
|
"check": {
|
123
|
-
"rest": {
|
124
|
-
|
125
|
-
|
126
|
-
"border_color2": None,
|
127
|
-
"border_width": None,
|
128
|
-
"radius": None,
|
129
|
-
"text_color": None,
|
130
|
-
},
|
131
|
-
"hover": {
|
132
|
-
"back_color": None,
|
133
|
-
"border_color": None,
|
134
|
-
"border_color2": None,
|
135
|
-
"border_width": None,
|
136
|
-
"radius": None,
|
137
|
-
"text_color": None,
|
138
|
-
},
|
139
|
-
"pressed": {
|
140
|
-
"back_color": None,
|
141
|
-
"border_color": None,
|
142
|
-
"border_color2": None,
|
143
|
-
"border_width": None,
|
144
|
-
"radius": None,
|
145
|
-
"text_color": None,
|
146
|
-
}
|
102
|
+
"rest": {},
|
103
|
+
"hover": {},
|
104
|
+
"pressed": {}
|
147
105
|
}
|
148
106
|
}
|
149
107
|
)
|
tkflu/tooltip.py
ADDED
tkflu/toplevel.py
ADDED
@@ -0,0 +1,29 @@
|
|
1
|
+
from tkinter import Toplevel
|
2
|
+
from tkdeft.object import DObject
|
3
|
+
from .bwm import BWm
|
4
|
+
|
5
|
+
|
6
|
+
class FluToplevel(Toplevel, BWm, DObject):
|
7
|
+
|
8
|
+
"""Fluent设计的子窗口"""
|
9
|
+
|
10
|
+
def __init__(self, *args, mode="light", **kwargs):
|
11
|
+
|
12
|
+
"""
|
13
|
+
初始化类
|
14
|
+
|
15
|
+
:param args: 参照tkinter.TK.__init__
|
16
|
+
:param className: 参照tkinter.TK.__init__
|
17
|
+
:param mode: Fluent主题模式 分为 “light” “dark”
|
18
|
+
:param kwargs: 参照tkinter.TK.__init__
|
19
|
+
"""
|
20
|
+
|
21
|
+
self._init(mode)
|
22
|
+
|
23
|
+
self.custom = False
|
24
|
+
|
25
|
+
Toplevel.__init__(self, *args, **kwargs)
|
26
|
+
|
27
|
+
self.bind("<Configure>", self._event_configure, add="+")
|
28
|
+
self.bind("<Escape>", self._event_key_esc, add="+")
|
29
|
+
self.protocol("WM_DELETE_WINDOW", self._event_delete_window)
|
tkflu/window.py
CHANGED
@@ -1,8 +1,9 @@
|
|
1
|
-
from tkinter import Tk
|
1
|
+
from tkinter import Tk, Toplevel
|
2
2
|
from tkdeft.object import DObject
|
3
|
+
from .bwm import BWm
|
3
4
|
|
4
5
|
|
5
|
-
class FluWindow(Tk, DObject):
|
6
|
+
class FluWindow(Tk, BWm, DObject):
|
6
7
|
|
7
8
|
"""Fluent设计的主窗口"""
|
8
9
|
|
@@ -23,175 +24,11 @@ class FluWindow(Tk, DObject):
|
|
23
24
|
|
24
25
|
super().__init__(*args, className=className, **kwargs)
|
25
26
|
|
26
|
-
|
27
|
+
from .icons import light
|
28
|
+
from tkinter import PhotoImage
|
27
29
|
|
28
|
-
|
30
|
+
self.iconphoto(False, PhotoImage(file=light()))
|
29
31
|
|
30
|
-
"""
|
31
|
-
|
32
|
-
|
33
|
-
:param event:
|
34
|
-
"""
|
35
|
-
|
36
|
-
self.configure(background=self.attributes.back_color)
|
37
|
-
if self.custom:
|
38
|
-
if hasattr(self, "titlebar"):
|
39
|
-
self.titlebar.configure(background=self.attributes.back_color)
|
40
|
-
self.titlebar.update()
|
41
|
-
if hasattr(self, "titlelabel"):
|
42
|
-
self.titlelabel.dconfigure(text_color=self.attributes.text_color)
|
43
|
-
self.titlelabel._draw()
|
44
|
-
if hasattr(self, "closebutton"):
|
45
|
-
self.closebutton.dconfigure(
|
46
|
-
rest={
|
47
|
-
"back_color": self.titlebar.cget("background"),
|
48
|
-
"border_color": "#f0f0f0",
|
49
|
-
"border_color2": "#d6d6d6",
|
50
|
-
"border_width": 0,
|
51
|
-
"radius": 0,
|
52
|
-
"text_color": self.attributes.closebutton.text_color,
|
53
|
-
},
|
54
|
-
hover={
|
55
|
-
"back_color": self.attributes.closebutton.back_color,
|
56
|
-
"border_color": "#f0f0f0",
|
57
|
-
"border_color2": "#d6d6d6",
|
58
|
-
"border_width": 0,
|
59
|
-
"radius": 0,
|
60
|
-
"text_color": self.attributes.closebutton.text_hover_color,
|
61
|
-
},
|
62
|
-
pressed={
|
63
|
-
"back_color": self.attributes.closebutton.back_color,
|
64
|
-
"border_color": "#f0f0f0",
|
65
|
-
"border_color2": "#f0f0f0",
|
66
|
-
"border_width": 0,
|
67
|
-
"radius": 0,
|
68
|
-
"text_color": self.attributes.closebutton.text_hover_color,
|
69
|
-
}
|
70
|
-
)
|
71
|
-
self.closebutton._draw()
|
72
|
-
|
73
|
-
def _event_configure(self, event=None):
|
74
|
-
|
75
|
-
"""
|
76
|
-
触发 `<Configure>` 事件
|
77
|
-
|
78
|
-
:param event:
|
79
|
-
:return:
|
80
|
-
"""
|
81
|
-
|
82
|
-
self._draw()
|
83
|
-
|
84
|
-
def _init(self, mode):
|
85
|
-
from easydict import EasyDict
|
86
|
-
self.attributes = EasyDict(
|
87
|
-
{
|
88
|
-
"back_color": None,
|
89
|
-
"text_color": None,
|
90
|
-
"closebutton": {
|
91
|
-
"back_color": None,
|
92
|
-
"text_color": None,
|
93
|
-
"text_hover_color": None
|
94
|
-
}
|
95
|
-
}
|
96
|
-
)
|
97
|
-
|
98
|
-
self.theme(mode)
|
99
|
-
|
100
|
-
def theme(self, mode: str):
|
101
|
-
|
102
|
-
"""
|
103
|
-
同 `theme_myself`
|
104
|
-
|
105
|
-
:param mode:
|
106
|
-
:return:
|
107
|
-
"""
|
108
|
-
|
109
|
-
self.theme_myself(mode=mode)
|
110
|
-
|
111
|
-
def theme_myself(self, mode: str):
|
112
|
-
|
113
|
-
"""
|
114
|
-
修改该窗口的Fluent主题
|
115
|
-
|
116
|
-
:param mode:
|
117
|
-
:return:
|
118
|
-
"""
|
119
|
-
|
120
|
-
self.mode = mode
|
121
|
-
if mode.lower() == "dark":
|
122
|
-
self._dark()
|
123
|
-
else:
|
124
|
-
self._light()
|
125
|
-
|
126
|
-
def _light(self):
|
127
|
-
self.dconfigure(
|
128
|
-
back_color="#ffffff",
|
129
|
-
text_color="#000000",
|
130
|
-
closebutton={
|
131
|
-
"back_color": "red",
|
132
|
-
"text_color": "#000000",
|
133
|
-
"text_hover_color": "#ffffff"
|
134
|
-
}
|
135
|
-
)
|
136
|
-
|
137
|
-
def _dark(self):
|
138
|
-
self.dconfigure(
|
139
|
-
back_color="#202020",
|
140
|
-
text_color="#ffffff",
|
141
|
-
closebutton={
|
142
|
-
"back_color": "red",
|
143
|
-
"text_color": "#ffffff",
|
144
|
-
"text_hover_color": "#000000"
|
145
|
-
}
|
146
|
-
)
|
147
|
-
|
148
|
-
def wincustom(self, wait=200, way=1):
|
149
|
-
|
150
|
-
"""
|
151
|
-
自定义窗口 仅限`Windows系统`
|
152
|
-
|
153
|
-
:param wait: 直接执行自定义窗口容易出错误 需要一点时间等待才能执行 同`after()`中的`ms`
|
154
|
-
:param way: 取0时保留原版边框,但稳定性很差,容易崩溃。取1时不保留原版边框,但稳定性较好。
|
155
|
-
:return:
|
156
|
-
"""
|
157
|
-
|
158
|
-
from sys import platform
|
159
|
-
from .button import FluButton
|
160
|
-
from .label import FluLabel
|
161
|
-
from tkinter import Frame
|
162
|
-
self.titlebar = Frame(self, width=180, height=35, background=self.attributes.back_color)
|
163
|
-
self.titlelabel = FluLabel(self.titlebar, text=self.title(), width=50)
|
164
|
-
self.titlelabel.pack(fill="y", side="left")
|
165
|
-
self.closebutton = FluButton(self.titlebar, text="", width=32, height=32, command=lambda: self.quit())
|
166
|
-
self.closebutton.pack(fill="y", side="right")
|
167
|
-
self.titlebar.pack(fill="x", side="top")
|
168
|
-
|
169
|
-
if platform == "win32":
|
170
|
-
if way == 0:
|
171
|
-
from .customwindow import CustomWindow
|
172
|
-
self.customwindow = CustomWindow(self, wait=wait)
|
173
|
-
self.customwindow.bind_drag(self.titlebar)
|
174
|
-
self.customwindow.bind_drag(self.titlelabel)
|
175
|
-
else:
|
176
|
-
self.overrideredirect(True)
|
177
|
-
try:
|
178
|
-
from win32gui import GetParent, GetWindowLong, SetWindowLong
|
179
|
-
from win32con import GWL_EXSTYLE, WS_EX_APPWINDOW, WS_EX_TOOLWINDOW
|
180
|
-
hwnd = GetParent(self.winfo_id())
|
181
|
-
style = GetWindowLong(hwnd, GWL_EXSTYLE)
|
182
|
-
style = style & ~WS_EX_TOOLWINDOW
|
183
|
-
style = style | WS_EX_APPWINDOW
|
184
|
-
SetWindowLong(hwnd, GWL_EXSTYLE, style)
|
185
|
-
self.after(30, lambda: self.withdraw())
|
186
|
-
self.after(60, lambda: self.deiconify())
|
187
|
-
except:
|
188
|
-
pass
|
189
|
-
|
190
|
-
self.wm_attributes("-topmost", True)
|
191
|
-
|
192
|
-
from .customwindow2 import WindowDragArea
|
193
|
-
self.dragarea = WindowDragArea(self)
|
194
|
-
self.dragarea.bind(self.titlebar)
|
195
|
-
self.dragarea.bind(self.titlelabel)
|
196
|
-
|
197
|
-
self.custom = True
|
32
|
+
self.bind("<Configure>", self._event_configure, add="+")
|
33
|
+
self.bind("<Escape>", self._event_key_esc, add="+")
|
34
|
+
self.protocol("WM_DELETE_WINDOW", self._event_delete_window)
|