monkeyqt 0.2.1__tar.gz → 0.2.2__tar.gz
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.
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/PKG-INFO +1 -1
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/__init__.py +47 -5
- monkeyqt-0.2.2/monkeyqt/components/basic/__init__.py +14 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/basic/button.py +177 -162
- monkeyqt-0.2.2/monkeyqt/components/basic/checkbox.py +208 -0
- monkeyqt-0.2.2/monkeyqt/components/basic/select_card.py +1094 -0
- monkeyqt-0.2.2/monkeyqt/components/data/console.py +846 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/data/data_table.py +126 -32
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/data/image_compare.py +3 -1
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/data/image_split.py +6 -4
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/data/preview_dialogs.py +41 -25
- monkeyqt-0.2.2/monkeyqt/components/data/pro_table.py +2724 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/data/table.py +93 -5
- monkeyqt-0.2.2/monkeyqt/components/feedback/__init__.py +28 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/feedback/alert.py +57 -22
- monkeyqt-0.2.2/monkeyqt/components/feedback/card.py +414 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/feedback/progress_bar.py +19 -13
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/feedback/progress_ring.py +21 -9
- monkeyqt-0.2.2/monkeyqt/components/feedback/tooltip.py +703 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/auth.py +13 -115
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/captcha.py +210 -208
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/combobox.py +69 -27
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/date_picker.py +55 -22
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/form.py +10 -6
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/input.py +162 -129
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/multicombobox.py +288 -104
- monkeyqt-0.2.2/monkeyqt/components/form/slider.py +484 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/switch.py +7 -4
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/form/upload.py +52 -33
- monkeyqt-0.2.2/monkeyqt/components/layout/__init__.py +23 -0
- monkeyqt-0.2.2/monkeyqt/components/layout/page.py +49 -0
- monkeyqt-0.2.2/monkeyqt/components/layout/scroll_area.py +134 -0
- monkeyqt-0.2.2/monkeyqt/components/layout/widget.py +667 -0
- monkeyqt-0.2.2/monkeyqt/components/layout/window.py +1859 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/layout/window_shell.py +3 -2
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/navigation/__init__.py +19 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/navigation/avatar_menu.py +9 -7
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/navigation/breadcrumb.py +41 -29
- monkeyqt-0.2.2/monkeyqt/components/navigation/dropdown.py +87 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/navigation/history.py +73 -26
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/navigation/pagination.py +98 -43
- monkeyqt-0.2.2/monkeyqt/components/navigation/segmented.py +889 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/navigation/sidebar.py +256 -112
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/navigation/tabs.py +60 -29
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/navigation/topbar.py +64 -35
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/core/icons.py +49 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/__init__.py +2 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/adapter.py +4521 -4292
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/components/theme_selector.py +50 -22
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/engine.py +329 -39
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/manager.py +26 -9
- monkeyqt-0.2.2/monkeyqt/themes/palette_theme.py +109 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/style_utils.py +73 -3
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/tokens.py +3 -4
- monkeyqt-0.2.2/monkeyqt/themes/unified_qss.py +698 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt.egg-info/PKG-INFO +1 -1
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt.egg-info/SOURCES.txt +11 -0
- monkeyqt-0.2.1/monkeyqt/components/basic/checkbox.py +0 -122
- monkeyqt-0.2.1/monkeyqt/components/data/console.py +0 -281
- monkeyqt-0.2.1/monkeyqt/components/feedback/__init__.py +0 -0
- monkeyqt-0.2.1/monkeyqt/components/feedback/card.py +0 -272
- monkeyqt-0.2.1/monkeyqt/components/form/slider.py +0 -220
- monkeyqt-0.2.1/monkeyqt/components/layout/window.py +0 -1093
- monkeyqt-0.2.1/monkeyqt/components/navigation/dropdown.py +0 -71
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/LICENSE +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/README.md +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/common/enums.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/data/__init__.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/data/avatar.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/components/layout/box.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/core/theme.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/core/theme_data.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/designer/plugins.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/icons.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/__main__.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/components/__init__.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/gallery.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt/themes/names.py +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt.egg-info/dependency_links.txt +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt.egg-info/requires.txt +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/monkeyqt.egg-info/top_level.txt +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/pyproject.toml +0 -0
- {monkeyqt-0.2.1 → monkeyqt-0.2.2}/setup.cfg +0 -0
|
@@ -1,11 +1,19 @@
|
|
|
1
1
|
# -*- coding: utf-8 -*-
|
|
2
2
|
from .components.basic.button import MkButton
|
|
3
3
|
from .components.basic.checkbox import MkCheckBox
|
|
4
|
+
from .components.basic.select_card import MkSelectItem, MkSelectCard, MkItemActionButton, MkSelectGroupHeader
|
|
4
5
|
# Navigation
|
|
5
6
|
from .components.navigation.sidebar import MkMenu
|
|
6
7
|
from .components.navigation.topbar import MkTopbar
|
|
7
8
|
from .components.navigation.breadcrumb import MkBreadcrumb
|
|
8
9
|
from .components.navigation.tabs import MkTabs
|
|
10
|
+
from .components.navigation.segmented import (
|
|
11
|
+
MkSegmented,
|
|
12
|
+
MkSegmentedTabs,
|
|
13
|
+
MkSegmentedControl,
|
|
14
|
+
MkCapsuleTabs,
|
|
15
|
+
SegmentedTabBar,
|
|
16
|
+
)
|
|
9
17
|
from .components.navigation.pagination import MkPagination
|
|
10
18
|
from .components.navigation.dropdown import MkDropdown
|
|
11
19
|
from .components.navigation.history import MkAnimatedStackedWidget, MkHistoryNavigation
|
|
@@ -25,8 +33,7 @@ from .components.form.multicombobox import MkMultiComboBox
|
|
|
25
33
|
|
|
26
34
|
# Data
|
|
27
35
|
from .components.data.avatar import MkAvatar
|
|
28
|
-
from .components.data.
|
|
29
|
-
from .components.data.data_table import MkDataTable
|
|
36
|
+
from .components.data.pro_table import MkProTable
|
|
30
37
|
from .components.data.image_compare import MkImageCompare
|
|
31
38
|
from .components.data.image_split import MkImageSplit
|
|
32
39
|
from .components.data.console import MkConsole
|
|
@@ -36,11 +43,25 @@ from .components.feedback.alert import MkAlert
|
|
|
36
43
|
from .components.feedback.progress_bar import MkProgressBar
|
|
37
44
|
from .components.feedback.progress_ring import MkProgressRing
|
|
38
45
|
from .components.feedback.card import MkCard
|
|
46
|
+
from .components.feedback.tooltip import (
|
|
47
|
+
MkTooltipPopover,
|
|
48
|
+
MkInfoIcon,
|
|
49
|
+
MkInfoIconButton,
|
|
50
|
+
MkTooltip,
|
|
51
|
+
create_field_header,
|
|
52
|
+
create_input_field,
|
|
53
|
+
create_switch_field,
|
|
54
|
+
)
|
|
39
55
|
|
|
40
56
|
# Layout
|
|
41
57
|
from .components.layout.window import MkTitleBar, MkWindow
|
|
42
58
|
from .components.layout.window_shell import MkWindowShell
|
|
43
59
|
from .components.layout.box import MkQVBoxLayout, MkQHBoxLayout, MkVBox, MkHBox
|
|
60
|
+
from .components.layout.widget import MkQWidget, MkWidget
|
|
61
|
+
from .components.layout.scroll_area import MkScrollArea, MkStackedWidget
|
|
62
|
+
from .components.layout.page import MkPage
|
|
63
|
+
|
|
64
|
+
|
|
44
65
|
|
|
45
66
|
|
|
46
67
|
# Themes (68 UI Styles)
|
|
@@ -55,17 +76,26 @@ from .themes import (
|
|
|
55
76
|
exclude_from_theme,
|
|
56
77
|
include_in_theme,
|
|
57
78
|
MkThemeSelector,
|
|
79
|
+
modern_scrollbar_qss,
|
|
58
80
|
)
|
|
59
81
|
|
|
60
|
-
__version__ = "0.2.
|
|
82
|
+
__version__ = "0.2.2"
|
|
61
83
|
|
|
62
84
|
__all__ = [
|
|
63
85
|
"MkButton",
|
|
64
86
|
"MkCheckBox",
|
|
87
|
+
"MkSelectItem",
|
|
88
|
+
"MkSelectCard",
|
|
89
|
+
"MkItemActionButton",
|
|
65
90
|
"MkMenu",
|
|
66
91
|
"MkTopbar",
|
|
67
92
|
"MkBreadcrumb",
|
|
68
93
|
"MkTabs",
|
|
94
|
+
"MkSegmented",
|
|
95
|
+
"MkSegmentedTabs",
|
|
96
|
+
"MkSegmentedControl",
|
|
97
|
+
"MkCapsuleTabs",
|
|
98
|
+
"SegmentedTabBar",
|
|
69
99
|
"MkPagination",
|
|
70
100
|
"MkDropdown",
|
|
71
101
|
"MkAnimatedStackedWidget",
|
|
@@ -83,8 +113,7 @@ __all__ = [
|
|
|
83
113
|
"MkMessage",
|
|
84
114
|
"MkUpload",
|
|
85
115
|
"MkAvatar",
|
|
86
|
-
"
|
|
87
|
-
"MkDataTable",
|
|
116
|
+
"MkProTable",
|
|
88
117
|
"MkImageCompare",
|
|
89
118
|
"MkImageSplit",
|
|
90
119
|
"MkConsole",
|
|
@@ -92,6 +121,13 @@ __all__ = [
|
|
|
92
121
|
"MkProgressBar",
|
|
93
122
|
"MkProgressRing",
|
|
94
123
|
"MkCard",
|
|
124
|
+
"MkTooltipPopover",
|
|
125
|
+
"MkInfoIcon",
|
|
126
|
+
"MkInfoIconButton",
|
|
127
|
+
"MkTooltip",
|
|
128
|
+
"create_field_header",
|
|
129
|
+
"create_input_field",
|
|
130
|
+
"create_switch_field",
|
|
95
131
|
"MkTitleBar",
|
|
96
132
|
"MkWindow",
|
|
97
133
|
"MkWindowShell",
|
|
@@ -99,6 +135,11 @@ __all__ = [
|
|
|
99
135
|
"MkQHBoxLayout",
|
|
100
136
|
"MkVBox",
|
|
101
137
|
"MkHBox",
|
|
138
|
+
"MkQWidget",
|
|
139
|
+
"MkWidget",
|
|
140
|
+
"MkScrollArea",
|
|
141
|
+
"MkStackedWidget",
|
|
142
|
+
"MkPage",
|
|
102
143
|
# Theme engine and helpers
|
|
103
144
|
"ThemeEngine",
|
|
104
145
|
"apply_monkeyqt_theme",
|
|
@@ -110,4 +151,5 @@ __all__ = [
|
|
|
110
151
|
"exclude_from_theme",
|
|
111
152
|
"include_in_theme",
|
|
112
153
|
"MkThemeSelector",
|
|
154
|
+
"modern_scrollbar_qss",
|
|
113
155
|
]
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
# -*- coding: utf-8 -*-
|
|
2
|
+
from .button import MkButton
|
|
3
|
+
from .checkbox import MkCheckBox
|
|
4
|
+
from .select_card import MkSelectItem, MkSelectCard, MkItemActionButton, MkSelectGroupHeader, MkItemIndicator
|
|
5
|
+
|
|
6
|
+
__all__ = [
|
|
7
|
+
"MkButton",
|
|
8
|
+
"MkCheckBox",
|
|
9
|
+
"MkSelectItem",
|
|
10
|
+
"MkSelectCard",
|
|
11
|
+
"MkItemActionButton",
|
|
12
|
+
"MkSelectGroupHeader",
|
|
13
|
+
"MkItemIndicator",
|
|
14
|
+
]
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
# -*- coding: utf-8 -*-
|
|
2
|
+
from monkeyqt.themes.engine import ThemeEngine as _MkThemeEngine
|
|
2
3
|
from PySide6.QtWidgets import QPushButton, QWidget, QGraphicsDropShadowEffect
|
|
3
4
|
from PySide6.QtCore import Qt, QPropertyAnimation, QEasingCurve, Property, QRect
|
|
4
|
-
from PySide6.QtGui import QPainter, QColor, QPen, QBrush, QPainterPath, QFont, QLinearGradient
|
|
5
|
+
from PySide6.QtGui import QPainter, QColor, QPen, QBrush, QPainterPath, QFont, QLinearGradient, QIcon
|
|
5
6
|
from monkeyqt.themes.engine import ThemeEngine
|
|
6
7
|
from monkeyqt.themes.style_utils import (
|
|
7
8
|
darken,
|
|
@@ -91,119 +92,9 @@ class MkButton(QPushButton):
|
|
|
91
92
|
if hasattr(self, "_liquid_timer") and self._liquid_timer.isActive():
|
|
92
93
|
self._liquid_timer.stop()
|
|
93
94
|
|
|
94
|
-
primary = t.get("--primary", "#409EFF")
|
|
95
|
-
bg = t.get("--bg", "#FFFFFF")
|
|
96
|
-
fg = t.get("--fg", "#1E293B")
|
|
97
|
-
border = t.get("--border", "#E2E8F0")
|
|
98
|
-
radius = t.get("--radius", "6px")
|
|
99
|
-
border_w = t.get("--border-width", "1px")
|
|
100
|
-
|
|
101
|
-
if t.is_neumorphic() or t.is_glass() or t.is_brutal() or t.is_glow() or t.is_pixel():
|
|
102
|
-
text = t.get("--glass-text", fg) if t.is_glass() else fg
|
|
103
|
-
self.setStyleSheet(f"""
|
|
104
|
-
QPushButton {{
|
|
105
|
-
background: transparent;
|
|
106
|
-
border: none;
|
|
107
|
-
color: {text};
|
|
108
|
-
padding: 8px 20px;
|
|
109
|
-
font-weight: 700;
|
|
110
|
-
}}
|
|
111
|
-
QPushButton:disabled {{
|
|
112
|
-
color: #94A3B8;
|
|
113
|
-
}}
|
|
114
|
-
""")
|
|
115
|
-
self.setGraphicsEffect(None)
|
|
116
|
-
self._apply_size_qss()
|
|
117
|
-
self.update()
|
|
118
|
-
return
|
|
119
|
-
|
|
120
|
-
hover_primary = t._lighten_hex(primary, 0.15) if primary.startswith("#") else primary
|
|
121
|
-
press_primary = t._darken_hex(primary, 0.1) if primary.startswith("#") else primary
|
|
122
|
-
|
|
123
|
-
if self._btn_type == "primary":
|
|
124
|
-
btn_bg = primary
|
|
125
|
-
btn_fg = "#FFFFFF"
|
|
126
|
-
btn_border = primary
|
|
127
|
-
btn_hover_bg = hover_primary
|
|
128
|
-
btn_press_bg = press_primary
|
|
129
|
-
elif self._btn_type == "danger":
|
|
130
|
-
btn_bg = "#EF4444"
|
|
131
|
-
btn_fg = "#FFFFFF"
|
|
132
|
-
btn_border = "#EF4444"
|
|
133
|
-
btn_hover_bg = "#F87171"
|
|
134
|
-
btn_press_bg = "#DC2626"
|
|
135
|
-
elif self._btn_type == "success":
|
|
136
|
-
btn_bg = "#22C55E"
|
|
137
|
-
btn_fg = "#FFFFFF"
|
|
138
|
-
btn_border = "#22C55E"
|
|
139
|
-
btn_hover_bg = "#4ADE80"
|
|
140
|
-
btn_press_bg = "#16A34A"
|
|
141
|
-
elif self._btn_type == "warning":
|
|
142
|
-
btn_bg = "#F59E0B"
|
|
143
|
-
btn_fg = "#FFFFFF"
|
|
144
|
-
btn_border = "#F59E0B"
|
|
145
|
-
btn_hover_bg = "#FBBF24"
|
|
146
|
-
btn_press_bg = "#D97706"
|
|
147
|
-
elif self._btn_type == "secondary":
|
|
148
|
-
btn_bg = "transparent"
|
|
149
|
-
btn_fg = primary
|
|
150
|
-
btn_border = primary
|
|
151
|
-
btn_hover_bg = t._lighten_hex(primary, 0.9) if primary.startswith("#") else "#F0F4FF"
|
|
152
|
-
btn_press_bg = t._lighten_hex(primary, 0.8) if primary.startswith("#") else "#E0E7FF"
|
|
153
|
-
else:
|
|
154
|
-
neutral = self._neutral_palette()
|
|
155
|
-
btn_bg = neutral["background"]
|
|
156
|
-
btn_fg = neutral["foreground"]
|
|
157
|
-
btn_border = neutral["border"]
|
|
158
|
-
btn_hover_bg = neutral["hover_background"]
|
|
159
|
-
btn_press_bg = neutral["pressed_background"]
|
|
160
|
-
|
|
161
|
-
if self._btn_type in ("default", "info"):
|
|
162
|
-
neutral = self._neutral_palette()
|
|
163
|
-
btn_hover_fg = neutral["hover_foreground"]
|
|
164
|
-
btn_press_fg = neutral["pressed_foreground"]
|
|
165
|
-
btn_hover_border = neutral["hover_border"]
|
|
166
|
-
btn_press_border = neutral["pressed_border"]
|
|
167
|
-
disabled_bg = neutral["disabled_background"]
|
|
168
|
-
disabled_fg = neutral["disabled_foreground"]
|
|
169
|
-
disabled_border = neutral["disabled_border"]
|
|
170
|
-
else:
|
|
171
|
-
btn_hover_fg = btn_fg
|
|
172
|
-
btn_press_fg = btn_fg
|
|
173
|
-
btn_hover_border = btn_border
|
|
174
|
-
btn_press_border = btn_border
|
|
175
|
-
disabled_bg = "#E2E8F0"
|
|
176
|
-
disabled_fg = "#94A3B8"
|
|
177
|
-
disabled_border = "#E2E8F0"
|
|
178
|
-
|
|
179
|
-
self.setStyleSheet(f"""
|
|
180
|
-
QPushButton {{
|
|
181
|
-
background-color: {btn_bg};
|
|
182
|
-
color: {btn_fg};
|
|
183
|
-
border: {border_w} solid {btn_border};
|
|
184
|
-
border-radius: {radius};
|
|
185
|
-
padding: 8px 20px;
|
|
186
|
-
font-weight: 600;
|
|
187
|
-
}}
|
|
188
|
-
QPushButton:hover {{
|
|
189
|
-
background-color: {btn_hover_bg};
|
|
190
|
-
color: {btn_hover_fg};
|
|
191
|
-
border-color: {btn_hover_border};
|
|
192
|
-
}}
|
|
193
|
-
QPushButton:pressed {{
|
|
194
|
-
background-color: {btn_press_bg};
|
|
195
|
-
color: {btn_press_fg};
|
|
196
|
-
border-color: {btn_press_border};
|
|
197
|
-
}}
|
|
198
|
-
QPushButton:disabled {{
|
|
199
|
-
opacity: 0.5;
|
|
200
|
-
background-color: {disabled_bg};
|
|
201
|
-
color: {disabled_fg};
|
|
202
|
-
border-color: {disabled_border};
|
|
203
|
-
}}
|
|
204
|
-
""")
|
|
205
95
|
self.setGraphicsEffect(None)
|
|
206
96
|
self._apply_size_qss()
|
|
97
|
+
self.update()
|
|
207
98
|
|
|
208
99
|
def _neutral_palette(self):
|
|
209
100
|
"""Build theme-aware states for the neutral default and info variants."""
|
|
@@ -218,40 +109,98 @@ class MkButton(QPushButton):
|
|
|
218
109
|
dark_theme = t.is_dark()
|
|
219
110
|
is_info = self._btn_type == "info"
|
|
220
111
|
|
|
221
|
-
|
|
112
|
+
if dark_theme:
|
|
113
|
+
# 严格参考暗黑现代化按钮规范:
|
|
114
|
+
# (正常态): 深炭灰底色 #212121,纯白文字 #FAFAFA,暗细边框 #303030
|
|
115
|
+
# (悬停态): 现代反转高亮浅白灰底色 #E5E5E5,深黑清晰文字 #171717
|
|
116
|
+
# (禁用态): 纯中灰底色 #7E7E7E,暗灰弱化文字 #212121
|
|
117
|
+
if is_info:
|
|
118
|
+
background = surface_muted if surface_muted != bg else "#262626"
|
|
119
|
+
foreground = "#F5F5F5"
|
|
120
|
+
btn_border = border if border != "#E2E8F0" else "#383838"
|
|
121
|
+
hover_background = "#3A3A3A"
|
|
122
|
+
hover_foreground = "#FFFFFF"
|
|
123
|
+
hover_border = "#505050"
|
|
124
|
+
pressed_background = "#1C1C1C"
|
|
125
|
+
pressed_foreground = "#E5E5E5"
|
|
126
|
+
pressed_border = "#2A2A2A"
|
|
127
|
+
disabled_background = "#7E7E7E"
|
|
128
|
+
disabled_foreground = "#212121"
|
|
129
|
+
disabled_border = "#7E7E7E"
|
|
130
|
+
else:
|
|
131
|
+
background = "#212121"
|
|
132
|
+
foreground = "#FAFAFA"
|
|
133
|
+
btn_border = "#303030"
|
|
134
|
+
hover_background = "#282828"
|
|
135
|
+
hover_foreground = "#FAFAFA"
|
|
136
|
+
hover_border = "#383838"
|
|
137
|
+
pressed_background = "#1C1C1C"
|
|
138
|
+
pressed_foreground = "#FAFAFA"
|
|
139
|
+
pressed_border = "#2A2A2A"
|
|
140
|
+
disabled_background = "#7E7E7E"
|
|
141
|
+
disabled_foreground = "#212121"
|
|
142
|
+
disabled_border = "#7E7E7E"
|
|
143
|
+
|
|
144
|
+
return {
|
|
145
|
+
"background": background,
|
|
146
|
+
"foreground": foreground,
|
|
147
|
+
"border": btn_border,
|
|
148
|
+
"hover_background": hover_background,
|
|
149
|
+
"hover_foreground": hover_foreground,
|
|
150
|
+
"hover_border": hover_border,
|
|
151
|
+
"pressed_background": pressed_background,
|
|
152
|
+
"pressed_foreground": pressed_foreground,
|
|
153
|
+
"pressed_border": pressed_border,
|
|
154
|
+
"disabled_background": disabled_background,
|
|
155
|
+
"disabled_foreground": disabled_foreground,
|
|
156
|
+
"disabled_border": disabled_border,
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
# 雅致亮色 (Light Mode) 现代化中性与行动按钮规范 (严格参考用户图一至图五):
|
|
160
|
+
# 图一 (默认态 Default - Connect GitHub): 纯白底色 #FFFFFF,深黑文字 #0F172A,浅灰细边框 #E2E8F0
|
|
161
|
+
# 图二 (中灰填色 Info/Add): 中灰底色 #8B8B8B,纯白文字 #FFFFFF,边框 #8B8B8B
|
|
162
|
+
# 图三 (悬停态 Hover - Connect GitHub): 浅白灰底色 #F5F5F5,深黑文字 #0F172A,浅灰边框 #CBD5E1
|
|
163
|
+
# 按压态 (Pressed): 浅白灰底色 #E5E5E5,深黑文字 #0F172A,浅灰边框 #94A3B8
|
|
222
164
|
if is_info:
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
165
|
+
background = "#8B8B8B"
|
|
166
|
+
foreground = "#FFFFFF"
|
|
167
|
+
btn_border = "#8B8B8B"
|
|
168
|
+
hover_background = "#71717A"
|
|
169
|
+
hover_foreground = "#FFFFFF"
|
|
170
|
+
hover_border = "#71717A"
|
|
171
|
+
pressed_background = "#52525B"
|
|
172
|
+
pressed_foreground = "#FFFFFF"
|
|
173
|
+
pressed_border = "#52525B"
|
|
174
|
+
disabled_background = "#E2E8F0"
|
|
175
|
+
disabled_foreground = "#94A3B8"
|
|
176
|
+
disabled_border = "#E2E8F0"
|
|
229
177
|
else:
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
178
|
+
background = "#FFFFFF"
|
|
179
|
+
foreground = _button_text_color(fg, "#FFFFFF")
|
|
180
|
+
btn_border = qss_color(border, "#E2E8F0")
|
|
181
|
+
hover_background = "#F5F5F5"
|
|
182
|
+
hover_foreground = _button_text_color(fg, hover_background)
|
|
183
|
+
hover_border = "#CBD5E1"
|
|
184
|
+
pressed_background = "#E5E5E5"
|
|
185
|
+
pressed_foreground = _button_text_color(fg, pressed_background)
|
|
186
|
+
pressed_border = "#94A3B8"
|
|
187
|
+
disabled_background = "#F8FAFC"
|
|
188
|
+
disabled_foreground = qss_color(text_muted, "#94A3B8")
|
|
189
|
+
disabled_border = qss_color(border, "#E2E8F0")
|
|
241
190
|
|
|
242
191
|
return {
|
|
243
|
-
"background":
|
|
244
|
-
"foreground":
|
|
245
|
-
"border":
|
|
246
|
-
"hover_background":
|
|
247
|
-
"hover_foreground":
|
|
248
|
-
"hover_border":
|
|
249
|
-
"pressed_background":
|
|
250
|
-
"pressed_foreground":
|
|
251
|
-
"pressed_border":
|
|
252
|
-
"disabled_background":
|
|
253
|
-
"disabled_foreground":
|
|
254
|
-
"disabled_border":
|
|
192
|
+
"background": background,
|
|
193
|
+
"foreground": foreground,
|
|
194
|
+
"border": btn_border,
|
|
195
|
+
"hover_background": hover_background,
|
|
196
|
+
"hover_foreground": hover_foreground,
|
|
197
|
+
"hover_border": hover_border,
|
|
198
|
+
"pressed_background": pressed_background,
|
|
199
|
+
"pressed_foreground": pressed_foreground,
|
|
200
|
+
"pressed_border": pressed_border,
|
|
201
|
+
"disabled_background": disabled_background,
|
|
202
|
+
"disabled_foreground": disabled_foreground,
|
|
203
|
+
"disabled_border": disabled_border,
|
|
255
204
|
}
|
|
256
205
|
|
|
257
206
|
def _apply_size_qss(self):
|
|
@@ -260,16 +209,13 @@ class MkButton(QPushButton):
|
|
|
260
209
|
size_qss = "padding: 12px 19px; font-size: 14px;"
|
|
261
210
|
elif getattr(self, "_mk_size", "default") == "small":
|
|
262
211
|
size_qss = "padding: 5px 11px; font-size: 12px; border-radius: 3px;"
|
|
212
|
+
qss = "QPushButton { background: transparent; border: none; outline: none; }"
|
|
263
213
|
if size_qss:
|
|
264
|
-
|
|
214
|
+
qss += f"\nQPushButton {{ {size_qss} }}"
|
|
215
|
+
_MkThemeEngine.apply_style_sheet(self, qss)
|
|
265
216
|
|
|
266
217
|
def paintEvent(self, event):
|
|
267
218
|
t = ThemeEngine
|
|
268
|
-
|
|
269
|
-
if not (t.is_neumorphic() or t.is_glass() or t.is_glow() or t.is_brutal() or t.is_pixel()):
|
|
270
|
-
super().paintEvent(event)
|
|
271
|
-
return
|
|
272
|
-
|
|
273
219
|
painter = QPainter(self)
|
|
274
220
|
painter.setRenderHint(QPainter.RenderHint.Antialiasing)
|
|
275
221
|
rect = self.rect()
|
|
@@ -307,12 +253,23 @@ class MkButton(QPushButton):
|
|
|
307
253
|
text_color = qcolor(neutral["foreground"])
|
|
308
254
|
else:
|
|
309
255
|
if not self.isEnabled():
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
256
|
+
if t.is_dark():
|
|
257
|
+
btn_color = qcolor("#7E7E7E")
|
|
258
|
+
text_color = qcolor("#212121")
|
|
259
|
+
else:
|
|
260
|
+
btn_color = qcolor("#CBD5E1")
|
|
261
|
+
text_color = qcolor("#64748B")
|
|
262
|
+
elif self._hovered:
|
|
263
|
+
# 若主色为深黑/炭黑(如雅致亮色 #171717,参考图四与图五),悬停转换为炭灰 #454545,避免 lighter 无效
|
|
264
|
+
if self._btn_type == "primary" and btn_color.lightness() < 60:
|
|
265
|
+
btn_color = qcolor("#454545")
|
|
266
|
+
else:
|
|
267
|
+
btn_color = btn_color.lighter(115)
|
|
268
|
+
elif self._pressed:
|
|
269
|
+
if self._btn_type == "primary" and btn_color.lightness() < 60:
|
|
270
|
+
btn_color = qcolor("#0A0A0A")
|
|
271
|
+
else:
|
|
272
|
+
btn_color = btn_color.darker(110)
|
|
316
273
|
|
|
317
274
|
if t.is_neumorphic():
|
|
318
275
|
inset = rect.adjusted(4, 4, -4, -4)
|
|
@@ -392,6 +349,47 @@ class MkButton(QPushButton):
|
|
|
392
349
|
painter.drawRect(inset)
|
|
393
350
|
painter.setPen(QPen(QColor("#000000"), 2))
|
|
394
351
|
painter.drawRect(inset)
|
|
352
|
+
else:
|
|
353
|
+
inset = rect.adjusted(1, 1, -1, -1)
|
|
354
|
+
border_w = t.get("--border-width", "1px")
|
|
355
|
+
bw = parse_px(border_w, 1, 0, 8)
|
|
356
|
+
|
|
357
|
+
if self._btn_type == "secondary":
|
|
358
|
+
if t.is_dark():
|
|
359
|
+
border_color = qcolor(primary)
|
|
360
|
+
if self._hovered: btn_color = qcolor("rgba(255, 255, 255, 0.12)")
|
|
361
|
+
elif self._pressed: btn_color = qcolor("rgba(255, 255, 255, 0.20)")
|
|
362
|
+
else: btn_color = QColor(0, 0, 0, 0)
|
|
363
|
+
else:
|
|
364
|
+
if self._hovered:
|
|
365
|
+
btn_color = qcolor("#F5F5F5")
|
|
366
|
+
border_color = qcolor("#CBD5E1")
|
|
367
|
+
elif self._pressed:
|
|
368
|
+
btn_color = qcolor("#E5E5E5")
|
|
369
|
+
border_color = qcolor("#94A3B8")
|
|
370
|
+
else:
|
|
371
|
+
btn_color = QColor(0, 0, 0, 0)
|
|
372
|
+
border_color = qcolor("#E2E8F0")
|
|
373
|
+
elif self._btn_type in ("default", "info"):
|
|
374
|
+
neutral = self._neutral_palette()
|
|
375
|
+
border_color = qcolor(neutral["border"])
|
|
376
|
+
if not self.isEnabled():
|
|
377
|
+
border_color = qcolor(neutral["disabled_border"])
|
|
378
|
+
elif self._hovered:
|
|
379
|
+
border_color = qcolor(neutral["hover_border"])
|
|
380
|
+
elif self._pressed:
|
|
381
|
+
border_color = qcolor(neutral["pressed_border"])
|
|
382
|
+
else:
|
|
383
|
+
border_color = btn_color
|
|
384
|
+
if not self.isEnabled():
|
|
385
|
+
border_color = qcolor("#7E7E7E" if t.is_dark() else "#CBD5E1")
|
|
386
|
+
|
|
387
|
+
painter.setBrush(QBrush(btn_color))
|
|
388
|
+
if border_color and bw > 0:
|
|
389
|
+
painter.setPen(QPen(border_color, bw))
|
|
390
|
+
else:
|
|
391
|
+
painter.setPen(Qt.PenStyle.NoPen)
|
|
392
|
+
painter.drawRoundedRect(inset, radius, radius)
|
|
395
393
|
|
|
396
394
|
if self._btn_type in ("default", "info") and not self.isEnabled():
|
|
397
395
|
text_color = qcolor(self._neutral_palette()["disabled_foreground"])
|
|
@@ -470,8 +468,8 @@ class MkButton(QPushButton):
|
|
|
470
468
|
return readable_text(qcolor(primary))
|
|
471
469
|
elif self._btn_type in ("danger", "success", "warning"):
|
|
472
470
|
return "#FFFFFF"
|
|
473
|
-
elif self._btn_type in ("text", "outline"):
|
|
474
|
-
return
|
|
471
|
+
elif self._btn_type in ("text", "outline", "secondary"):
|
|
472
|
+
return fg if not t.is_dark() else "#FAFAFA"
|
|
475
473
|
|
|
476
474
|
if t.is_glow():
|
|
477
475
|
return primary
|
|
@@ -482,7 +480,15 @@ class MkButton(QPushButton):
|
|
|
482
480
|
return fg
|
|
483
481
|
|
|
484
482
|
def setIcon(self, icon):
|
|
485
|
-
if
|
|
483
|
+
if isinstance(icon, str):
|
|
484
|
+
try:
|
|
485
|
+
from monkeyqt.icons import Ph
|
|
486
|
+
pm = Ph.pixmap(icon, size=16, color=self._get_button_text_color())
|
|
487
|
+
if pm and not pm.isNull():
|
|
488
|
+
icon = QIcon(pm)
|
|
489
|
+
except Exception:
|
|
490
|
+
pass
|
|
491
|
+
elif hasattr(icon, "_ph_spec"):
|
|
486
492
|
self._ph_icon_spec = getattr(icon, "_ph_spec", None)
|
|
487
493
|
try:
|
|
488
494
|
spec = dict(self._ph_icon_spec)
|
|
@@ -495,18 +501,28 @@ class MkButton(QPushButton):
|
|
|
495
501
|
super().setIcon(icon)
|
|
496
502
|
|
|
497
503
|
def set_theme_style(self, style_name: str = None):
|
|
504
|
+
self._update_style()
|
|
498
505
|
if getattr(self, "_ph_icon_spec", None):
|
|
499
506
|
try:
|
|
500
|
-
|
|
501
507
|
spec = dict(self._ph_icon_spec)
|
|
502
508
|
orig_color = spec.get("color")
|
|
503
509
|
if orig_color in (None, "auto", "default", "fg", "foreground", "currentcolor"):
|
|
504
510
|
spec["color"] = self._get_button_text_color()
|
|
505
511
|
new_icon = Ph.icon(**spec)
|
|
506
512
|
super().setIcon(new_icon)
|
|
507
|
-
except Exception
|
|
513
|
+
except Exception:
|
|
508
514
|
pass
|
|
509
|
-
|
|
515
|
+
t = ThemeEngine
|
|
516
|
+
if t.is_liquid_glass():
|
|
517
|
+
if not hasattr(self, "_liquid_timer"):
|
|
518
|
+
from PySide6.QtCore import QTimer
|
|
519
|
+
self._liquid_timer = QTimer(self)
|
|
520
|
+
self._liquid_timer.timeout.connect(self._on_liquid_timeout)
|
|
521
|
+
if not self._liquid_timer.isActive():
|
|
522
|
+
self._liquid_timer.start(33)
|
|
523
|
+
else:
|
|
524
|
+
if hasattr(self, "_liquid_timer") and self._liquid_timer.isActive():
|
|
525
|
+
self._liquid_timer.stop()
|
|
510
526
|
self.update()
|
|
511
527
|
|
|
512
528
|
@Property(str)
|
|
@@ -543,5 +559,4 @@ class MkButton(QPushButton):
|
|
|
543
559
|
self._mk_size = value
|
|
544
560
|
self.setProperty("mk_size", value)
|
|
545
561
|
self._update_style()
|
|
546
|
-
self.
|
|
547
|
-
self.style().polish(self)
|
|
562
|
+
self.update()
|