@keenmate/pure-admin-core 1.0.0-rc01
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.
- package/LICENSE +21 -0
- package/README.md +172 -0
- package/dist/css/main.css +11542 -0
- package/dist/fonts/Delivery/Delivery_W_Bd.woff2 +0 -0
- package/dist/fonts/Delivery/Delivery_W_BdIt.woff2 +0 -0
- package/dist/fonts/Delivery/Delivery_W_CdBlk.woff2 +0 -0
- package/dist/fonts/Delivery/Delivery_W_CdLt.woff2 +0 -0
- package/dist/fonts/Delivery/Delivery_W_It.woff2 +0 -0
- package/dist/fonts/Delivery/Delivery_W_Lt.woff2 +0 -0
- package/dist/fonts/Delivery/Delivery_W_LtIt.woff2 +0 -0
- package/dist/fonts/Delivery/Delivery_W_Rg.woff2 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8UH-qVHQ.woff2 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8UH-qVHQ.woff2.1 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8UH-qVHQ.woff2.2 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8VH-qVHQ.woff2 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8VH-qVHQ.woff2.1 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8VH-qVHQ.woff2.2 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8bH-o.woff2 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8bH-o.woff2.1 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8fH-qVHQ.woff2 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8fH-qVHQ.woff2.1 +0 -0
- package/dist/fonts/google/3y976aknfjLm_3lMKjiMgmUUYBs04Y8fH-qVHQ.woff2.2 +0 -0
- package/dist/fonts/google/6aez4K2oVqwIvtE2H68T.woff2 +0 -0
- package/dist/fonts/google/6aez4K2oVqwIvtU2Hw.woff2 +0 -0
- package/dist/fonts/google/6aez4K2oVqwIvtY2H68T.woff2 +0 -0
- package/dist/fonts/google/6aez4K2oVqwIvtg2H68T.woff2 +0 -0
- package/dist/fonts/google/6aez4K2oVqwIvto2H68T.woff2 +0 -0
- package/dist/fonts/google/6aez4K2oVqwIvts2H68T.woff2 +0 -0
- package/dist/fonts/google/7Auup_AqnyWWAxW2Wk3swUz56MS91Eww8SX21nejog.woff2 +0 -0
- package/dist/fonts/google/7Auup_AqnyWWAxW2Wk3swUz56MS91Eww8SX21nijogp5.woff2 +0 -0
- package/dist/fonts/google/7Auup_AqnyWWAxW2Wk3swUz56MS91Eww8SX21nmjogp5.woff2 +0 -0
- package/dist/fonts/google/PN_xRfK9oXHga0XdZ8g_vT0.woff2 +0 -0
- package/dist/fonts/google/PN_xRfK9oXHga0XdZsg_.woff2 +0 -0
- package/dist/fonts/google/PN_xRfK9oXHga0XdaMg_vT0.woff2 +0 -0
- package/dist/fonts/google/TK3tWkYFABsmjsphPho.woff2 +0 -0
- package/dist/fonts/google/TK3tWkYFABsmjspuPho7vA.woff2 +0 -0
- package/dist/fonts/google/TK3tWkYFABsmjspvPho7vA.woff2 +0 -0
- package/dist/fonts/google/dg45_pLmvrkcOkBnKsOzXyGWTBcmg-X6VjTYJwQj.woff2 +0 -0
- package/dist/fonts/google/dg45_pLmvrkcOkBnKsOzXyGWTBcmg-X6VjXYJwQj.woff2 +0 -0
- package/dist/fonts/google/dg45_pLmvrkcOkBnKsOzXyGWTBcmg-X6Vj_YJwQj.woff2 +0 -0
- package/dist/fonts/google/dg45_pLmvrkcOkBnKsOzXyGWTBcmg-X6VjbYJwQj.woff2 +0 -0
- package/dist/fonts/google/dg45_pLmvrkcOkBnKsOzXyGWTBcmg-X6VjvYJw.woff2 +0 -0
- package/dist/fonts/google/fonts-tracklist.txt +48 -0
- package/dist/fonts/google/vEFO2_JTCgwQ5ejvMV0O96D01E8J0tJXHKbBjM4.woff2 +0 -0
- package/dist/fonts/google/vEFO2_JTCgwQ5ejvMV0O96D01E8J0tJXHKbOjM7sfA.woff2 +0 -0
- package/dist/fonts/google/vEFO2_JTCgwQ5ejvMV0O96D01E8J0tJXHKbPjM7sfA.woff2 +0 -0
- package/dist/fonts/google/wEOhEADFm8hSaQTFG18FErVhsC9x-tarUfLtrftV.woff2 +0 -0
- package/dist/fonts/google/wEOhEADFm8hSaQTFG18FErVhsC9x-tarUfXtrftV.woff2 +0 -0
- package/dist/fonts/google/wEOhEADFm8hSaQTFG18FErVhsC9x-tarUfbtrQ.woff2 +0 -0
- package/dist/fonts/google/wEOhEADFm8hSaQTFG18FErVhsC9x-tarUfjtrftV.woff2 +0 -0
- package/dist/fonts/google/wEOhEADFm8hSaQTFG18FErVhsC9x-tarUfntrftV.woff2 +0 -0
- package/dist/fonts/google/wEOhEADFm8hSaQTFG18FErVhsC9x-tarUfrtrftV.woff2 +0 -0
- package/dist/fonts/google/wEOhEADFm8hSaQTFG18FErVhsC9x-tarUfvtrftV.woff2 +0 -0
- package/dist/fonts/google/xn7_YHE41ni1AdIRqAuZuw1Bx9mbZk79FN_B-bnBeA.woff2 +0 -0
- package/dist/fonts/google/xn7_YHE41ni1AdIRqAuZuw1Bx9mbZk79FN_C-bk.woff2 +0 -0
- package/dist/fonts/google/xn7_YHE41ni1AdIRqAuZuw1Bx9mbZk79FN_G-bnBeA.woff2 +0 -0
- package/dist/fonts/google/xn7_YHE41ni1AdIRqAuZuw1Bx9mbZk79FN_M-bnBeA.woff2 +0 -0
- package/dist/fonts/google/xn7_YHE41ni1AdIRqAuZuw1Bx9mbZk79FN_N-bnBeA.woff2 +0 -0
- package/dist/fonts/google/xn7_YHE41ni1AdIRqAuZuw1Bx9mbZk79FN_P-bnBeA.woff2 +0 -0
- package/package.json +60 -0
- package/snippets/alerts.html +281 -0
- package/snippets/badges.html +212 -0
- package/snippets/buttons.html +287 -0
- package/snippets/cards.html +393 -0
- package/snippets/checkbox-lists.html +490 -0
- package/snippets/code.html +225 -0
- package/snippets/command-palette.html +210 -0
- package/snippets/comparison.html +428 -0
- package/snippets/customization.html +142 -0
- package/snippets/forms.html +477 -0
- package/snippets/grid.html +338 -0
- package/snippets/layout.html +598 -0
- package/snippets/lists.html +232 -0
- package/snippets/loaders.html +183 -0
- package/snippets/manifest.json +388 -0
- package/snippets/modal-dialogs.html +411 -0
- package/snippets/modals.html +310 -0
- package/snippets/popconfirm.html +253 -0
- package/snippets/profile.html +264 -0
- package/snippets/tables.html +317 -0
- package/snippets/tabs.html +930 -0
- package/snippets/timeline.html +364 -0
- package/snippets/toasts.html +154 -0
- package/snippets/tooltips.html +411 -0
- package/snippets/typography.html +101 -0
- package/snippets/utilities.html +595 -0
- package/snippets/virtual-scroll.html +322 -0
- package/snippets/web-daterangepicker.html +634 -0
- package/snippets/web-multiselect.html +362 -0
- package/src/scss/.claude/settings.local.json +11 -0
- package/src/scss/_base-css-variables.scss +348 -0
- package/src/scss/_core.scss +99 -0
- package/src/scss/_fonts.scss +67 -0
- package/src/scss/_purecss-grid-responsive.scss +138 -0
- package/src/scss/_purecss-grid.scss +58 -0
- package/src/scss/_variables.scss +14 -0
- package/src/scss/core-components/_alerts.scss +212 -0
- package/src/scss/core-components/_badges.scss +16 -0
- package/src/scss/core-components/_base.scss +124 -0
- package/src/scss/core-components/_buttons.scss +473 -0
- package/src/scss/core-components/_cards.scss +285 -0
- package/src/scss/core-components/_checkbox-lists.scss +289 -0
- package/src/scss/core-components/_code.scss +141 -0
- package/src/scss/core-components/_command-palette.scss +518 -0
- package/src/scss/core-components/_comparison.scss +172 -0
- package/src/scss/core-components/_file-selector.scss +780 -0
- package/src/scss/core-components/_forms.scss +16 -0
- package/src/scss/core-components/_grid.scss +264 -0
- package/src/scss/core-components/_layout.scss +15 -0
- package/src/scss/core-components/_lists.scss +211 -0
- package/src/scss/core-components/_loaders.scss +277 -0
- package/src/scss/core-components/_logic-tree.scss +280 -0
- package/src/scss/core-components/_modals.scss +209 -0
- package/src/scss/core-components/_notifications.scss +253 -0
- package/src/scss/core-components/_pagers.scss +141 -0
- package/src/scss/core-components/_popconfirm.scss +170 -0
- package/src/scss/core-components/_profile.scss +281 -0
- package/src/scss/core-components/_settings-panel.scss +128 -0
- package/src/scss/core-components/_statistics.scss +200 -0
- package/src/scss/core-components/_tables.scss +555 -0
- package/src/scss/core-components/_tabs.scss +438 -0
- package/src/scss/core-components/_timeline.scss +589 -0
- package/src/scss/core-components/_toasts.scss +281 -0
- package/src/scss/core-components/_tooltips.scss +503 -0
- package/src/scss/core-components/_utilities.scss +241 -0
- package/src/scss/core-components/_web-components-theme.scss +294 -0
- package/src/scss/core-components/badges/_badge-base.scss +131 -0
- package/src/scss/core-components/badges/_badge-group.scss +25 -0
- package/src/scss/core-components/badges/_composite-badge-variants.scss +396 -0
- package/src/scss/core-components/badges/_composite-badge.scss +70 -0
- package/src/scss/core-components/badges/_index.scss +10 -0
- package/src/scss/core-components/badges/_labels.scss +155 -0
- package/src/scss/core-components/forms/_checkboxes-radios.scss +205 -0
- package/src/scss/core-components/forms/_form-inputs.scss +100 -0
- package/src/scss/core-components/forms/_form-layout.scss +66 -0
- package/src/scss/core-components/forms/_form-states.scss +89 -0
- package/src/scss/core-components/forms/_index.scss +12 -0
- package/src/scss/core-components/forms/_input-groups.scss +149 -0
- package/src/scss/core-components/forms/_input-wrapper.scss +89 -0
- package/src/scss/core-components/forms/_query-editor.scss +313 -0
- package/src/scss/core-components/layout/_index.scss +11 -0
- package/src/scss/core-components/layout/_layout-container.scss +105 -0
- package/src/scss/core-components/layout/_layout-responsive.scss +100 -0
- package/src/scss/core-components/layout/_navbar-elements.scss +238 -0
- package/src/scss/core-components/layout/_navbar.scss +71 -0
- package/src/scss/core-components/layout/_sidebar-states.scss +228 -0
- package/src/scss/core-components/layout/_sidebar.scss +177 -0
- package/src/scss/main.scss +7 -0
- package/src/scss/themes/_dark-base.scss +207 -0
- package/src/scss/themes/audi-light.scss +311 -0
- package/src/scss/themes/audi.scss +288 -0
- package/src/scss/themes/corporate.scss +203 -0
- package/src/scss/themes/dark-blue.scss +152 -0
- package/src/scss/themes/dark-green.scss +156 -0
- package/src/scss/themes/dark-red.scss +160 -0
- package/src/scss/themes/dark.scss +145 -0
- package/src/scss/themes/express.scss +281 -0
- package/src/scss/themes/minimal.scss +121 -0
- package/src/scss/utilities.scss +481 -0
- package/src/scss/variables/_base.scss +81 -0
- package/src/scss/variables/_colors.scss +148 -0
- package/src/scss/variables/_components.scss +509 -0
- package/src/scss/variables/_index.scss +13 -0
- package/src/scss/variables/_layout.scss +65 -0
- package/src/scss/variables/_spacing.scss +66 -0
- package/src/scss/variables/_system.scss +80 -0
- package/src/scss/variables/_typography.scss +37 -0
|
@@ -0,0 +1,310 @@
|
|
|
1
|
+
<!-- ================================
|
|
2
|
+
MODAL SNIPPETS
|
|
3
|
+
Pure Admin Visual Framework
|
|
4
|
+
================================ -->
|
|
5
|
+
|
|
6
|
+
<!--
|
|
7
|
+
MODAL WRAPPER CLASSES:
|
|
8
|
+
- pa-modal: Base modal wrapper
|
|
9
|
+
- pa-modal--show: Show the modal (add/remove via JavaScript)
|
|
10
|
+
- pa-modal--top: Position modal near top instead of center (useful for search/command interfaces)
|
|
11
|
+
- pa-modal--primary: Primary themed modal (blue header)
|
|
12
|
+
- pa-modal--success: Success themed modal (green header)
|
|
13
|
+
- pa-modal--warning: Warning themed modal (orange header)
|
|
14
|
+
- pa-modal--danger: Danger themed modal (red header)
|
|
15
|
+
- pa-modal--info: Info themed modal (cyan header)
|
|
16
|
+
|
|
17
|
+
CONTAINER SIZE CLASSES:
|
|
18
|
+
- pa-modal__container--sm: Small (20rem / 320px)
|
|
19
|
+
- pa-modal__container: Medium/default (30rem / 480px)
|
|
20
|
+
- pa-modal__container--lg: Large (50rem / 800px)
|
|
21
|
+
- pa-modal__container--xl: Extra large (70rem / 1120px)
|
|
22
|
+
- pa-modal__container--xxl: Extra extra large (90rem / 1440px)
|
|
23
|
+
- pa-modal__container--fw: Full width (constrained by viewport margins)
|
|
24
|
+
|
|
25
|
+
BODY CLASSES:
|
|
26
|
+
- pa-modal__body: Base body class
|
|
27
|
+
- pa-modal__body--scrollable: Scrollable body with max-height (header/footer fixed)
|
|
28
|
+
|
|
29
|
+
HEADER THEME CLASSES (alternative to modal-level themes):
|
|
30
|
+
- pa-modal__header--primary: Blue themed header
|
|
31
|
+
- pa-modal__header--success: Green themed header
|
|
32
|
+
- pa-modal__header--warning: Orange themed header
|
|
33
|
+
- pa-modal__header--danger: Red themed header
|
|
34
|
+
-->
|
|
35
|
+
|
|
36
|
+
<!-- BASIC MODAL (Centered) -->
|
|
37
|
+
|
|
38
|
+
<!-- Modal Structure -->
|
|
39
|
+
<div class="pa-modal pa-modal--show" id="basicModal">
|
|
40
|
+
<div class="pa-modal__backdrop"></div>
|
|
41
|
+
<div class="pa-modal__container">
|
|
42
|
+
<div class="pa-modal__header">
|
|
43
|
+
<h3 class="pa-modal__title">Modal Title</h3>
|
|
44
|
+
<button class="pa-btn pa-btn--primary pa-btn--icon-only pa-btn--sm" onclick="closeModal('basicModal')">✕</button>
|
|
45
|
+
</div>
|
|
46
|
+
<div class="pa-modal__body">
|
|
47
|
+
<p>Modal body content goes here.</p>
|
|
48
|
+
</div>
|
|
49
|
+
<div class="pa-modal__footer">
|
|
50
|
+
<button class="pa-btn pa-btn--secondary" onclick="closeModal('basicModal')">Close</button>
|
|
51
|
+
<button class="pa-btn pa-btn--primary">Save changes</button>
|
|
52
|
+
</div>
|
|
53
|
+
</div>
|
|
54
|
+
</div>
|
|
55
|
+
|
|
56
|
+
<!-- TOP-ALIGNED MODAL -->
|
|
57
|
+
|
|
58
|
+
<!-- Modal positioned near top (5vh from top) -->
|
|
59
|
+
<div class="pa-modal pa-modal--top pa-modal--show" id="topModal">
|
|
60
|
+
<div class="pa-modal__backdrop"></div>
|
|
61
|
+
<div class="pa-modal__container">
|
|
62
|
+
<div class="pa-modal__header">
|
|
63
|
+
<h3 class="pa-modal__title">Top-Aligned Modal</h3>
|
|
64
|
+
<button class="pa-btn pa-btn--primary pa-btn--icon-only pa-btn--sm" onclick="closeModal('topModal')">✕</button>
|
|
65
|
+
</div>
|
|
66
|
+
<div class="pa-modal__body">
|
|
67
|
+
<p>This modal appears near the top of the viewport.</p>
|
|
68
|
+
<p>Useful for search interfaces, quick actions, or command palettes.</p>
|
|
69
|
+
</div>
|
|
70
|
+
<div class="pa-modal__footer">
|
|
71
|
+
<button class="pa-btn pa-btn--secondary" onclick="closeModal('topModal')">Close</button>
|
|
72
|
+
<button class="pa-btn pa-btn--primary">Confirm</button>
|
|
73
|
+
</div>
|
|
74
|
+
</div>
|
|
75
|
+
</div>
|
|
76
|
+
|
|
77
|
+
|
|
78
|
+
<!-- MODAL SIZES -->
|
|
79
|
+
|
|
80
|
+
<!-- Small Modal -->
|
|
81
|
+
<div class="pa-modal" id="smallModal">
|
|
82
|
+
<div class="pa-modal__backdrop"></div>
|
|
83
|
+
<div class="pa-modal__container pa-modal__container--sm">
|
|
84
|
+
<!-- content -->
|
|
85
|
+
</div>
|
|
86
|
+
</div>
|
|
87
|
+
|
|
88
|
+
<!-- Medium Modal (Default) -->
|
|
89
|
+
<div class="pa-modal" id="mediumModal">
|
|
90
|
+
<div class="pa-modal__backdrop"></div>
|
|
91
|
+
<div class="pa-modal__container">
|
|
92
|
+
<!-- content -->
|
|
93
|
+
</div>
|
|
94
|
+
</div>
|
|
95
|
+
|
|
96
|
+
<!-- Large Modal -->
|
|
97
|
+
<div class="pa-modal" id="largeModal">
|
|
98
|
+
<div class="pa-modal__backdrop"></div>
|
|
99
|
+
<div class="pa-modal__container pa-modal__container--lg">
|
|
100
|
+
<!-- content -->
|
|
101
|
+
</div>
|
|
102
|
+
</div>
|
|
103
|
+
|
|
104
|
+
<!-- Extra Large Modal -->
|
|
105
|
+
<div class="pa-modal" id="xlModal">
|
|
106
|
+
<div class="pa-modal__backdrop"></div>
|
|
107
|
+
<div class="pa-modal__container pa-modal__container--xl">
|
|
108
|
+
<!-- content -->
|
|
109
|
+
</div>
|
|
110
|
+
</div>
|
|
111
|
+
|
|
112
|
+
<!-- 2XL Modal -->
|
|
113
|
+
<div class="pa-modal" id="xxlModal">
|
|
114
|
+
<div class="pa-modal__backdrop"></div>
|
|
115
|
+
<div class="pa-modal__container pa-modal__container--xxl">
|
|
116
|
+
<!-- content -->
|
|
117
|
+
</div>
|
|
118
|
+
</div>
|
|
119
|
+
|
|
120
|
+
<!-- Full Width Modal -->
|
|
121
|
+
<div class="pa-modal" id="fwModal">
|
|
122
|
+
<div class="pa-modal__backdrop"></div>
|
|
123
|
+
<div class="pa-modal__container pa-modal__container--fw">
|
|
124
|
+
<!-- content -->
|
|
125
|
+
</div>
|
|
126
|
+
</div>
|
|
127
|
+
|
|
128
|
+
|
|
129
|
+
<!-- THEMED MODALS -->
|
|
130
|
+
|
|
131
|
+
<!-- Primary Modal -->
|
|
132
|
+
<div class="pa-modal pa-modal--primary" id="primaryModal">
|
|
133
|
+
<div class="pa-modal__backdrop"></div>
|
|
134
|
+
<div class="pa-modal__container">
|
|
135
|
+
<div class="pa-modal__header">
|
|
136
|
+
<h3 class="pa-modal__title">Primary Modal</h3>
|
|
137
|
+
<button class="pa-btn pa-btn--primary pa-btn--icon-only pa-btn--sm">✕</button>
|
|
138
|
+
</div>
|
|
139
|
+
<div class="pa-modal__body">
|
|
140
|
+
Content here.
|
|
141
|
+
</div>
|
|
142
|
+
</div>
|
|
143
|
+
</div>
|
|
144
|
+
|
|
145
|
+
<!-- Success Modal -->
|
|
146
|
+
<div class="pa-modal pa-modal--success" id="successModal">
|
|
147
|
+
<div class="pa-modal__backdrop"></div>
|
|
148
|
+
<div class="pa-modal__container">
|
|
149
|
+
<div class="pa-modal__header">
|
|
150
|
+
<h3 class="pa-modal__title">Success Modal</h3>
|
|
151
|
+
<button class="pa-btn pa-btn--primary pa-btn--icon-only pa-btn--sm">✕</button>
|
|
152
|
+
</div>
|
|
153
|
+
<div class="pa-modal__body">
|
|
154
|
+
Content here.
|
|
155
|
+
</div>
|
|
156
|
+
</div>
|
|
157
|
+
</div>
|
|
158
|
+
|
|
159
|
+
<!-- Warning Modal -->
|
|
160
|
+
<div class="pa-modal pa-modal--warning" id="warningModal">
|
|
161
|
+
<div class="pa-modal__backdrop"></div>
|
|
162
|
+
<div class="pa-modal__container">
|
|
163
|
+
<div class="pa-modal__header">
|
|
164
|
+
<h3 class="pa-modal__title">Warning Modal</h3>
|
|
165
|
+
<button class="pa-btn pa-btn--primary pa-btn--icon-only pa-btn--sm">✕</button>
|
|
166
|
+
</div>
|
|
167
|
+
<div class="pa-modal__body">
|
|
168
|
+
Content here.
|
|
169
|
+
</div>
|
|
170
|
+
</div>
|
|
171
|
+
</div>
|
|
172
|
+
|
|
173
|
+
<!-- Danger Modal -->
|
|
174
|
+
<div class="pa-modal pa-modal--danger" id="dangerModal">
|
|
175
|
+
<div class="pa-modal__backdrop"></div>
|
|
176
|
+
<div class="pa-modal__container">
|
|
177
|
+
<div class="pa-modal__header">
|
|
178
|
+
<h3 class="pa-modal__title">Danger Modal</h3>
|
|
179
|
+
<button class="pa-btn pa-btn--primary pa-btn--icon-only pa-btn--sm">✕</button>
|
|
180
|
+
</div>
|
|
181
|
+
<div class="pa-modal__body">
|
|
182
|
+
Content here.
|
|
183
|
+
</div>
|
|
184
|
+
</div>
|
|
185
|
+
</div>
|
|
186
|
+
|
|
187
|
+
|
|
188
|
+
<!-- SCROLLABLE MODAL BODY -->
|
|
189
|
+
|
|
190
|
+
<!-- Modal with Scrollable Content -->
|
|
191
|
+
<div class="pa-modal" id="scrollableModal">
|
|
192
|
+
<div class="pa-modal__backdrop"></div>
|
|
193
|
+
<div class="pa-modal__container pa-modal__container--lg">
|
|
194
|
+
<div class="pa-modal__header">
|
|
195
|
+
<h3 class="pa-modal__title">Terms and Conditions</h3>
|
|
196
|
+
<button class="pa-btn pa-btn--primary pa-btn--icon-only pa-btn--sm">✕</button>
|
|
197
|
+
</div>
|
|
198
|
+
<div class="pa-modal__body pa-modal__body--scrollable">
|
|
199
|
+
<!-- Long content that requires scrolling -->
|
|
200
|
+
<h4>1. Introduction</h4>
|
|
201
|
+
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.</p>
|
|
202
|
+
<h4>2. Terms of Service</h4>
|
|
203
|
+
<p>Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.</p>
|
|
204
|
+
<h4>3. Privacy Policy</h4>
|
|
205
|
+
<p>Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur.</p>
|
|
206
|
+
<h4>4. User Responsibilities</h4>
|
|
207
|
+
<p>Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
|
|
208
|
+
<h4>5. Disclaimer</h4>
|
|
209
|
+
<p>Sed ut perspiciatis unde omnis iste natus error sit voluptatem accusantium doloremque laudantium.</p>
|
|
210
|
+
<!-- More content... -->
|
|
211
|
+
</div>
|
|
212
|
+
<div class="pa-modal__footer">
|
|
213
|
+
<button class="pa-btn pa-btn--secondary">Decline</button>
|
|
214
|
+
<button class="pa-btn pa-btn--primary">Accept</button>
|
|
215
|
+
</div>
|
|
216
|
+
</div>
|
|
217
|
+
</div>
|
|
218
|
+
|
|
219
|
+
<!--
|
|
220
|
+
SCROLLABLE BODY NOTES:
|
|
221
|
+
- Use pa-modal__body--scrollable for content that may exceed viewport height
|
|
222
|
+
- Body gets max-height and overflow-y: auto
|
|
223
|
+
- Header and footer remain fixed, only body scrolls
|
|
224
|
+
- Recommended for: Terms of service, long forms, data tables, file lists
|
|
225
|
+
-->
|
|
226
|
+
|
|
227
|
+
|
|
228
|
+
<!-- MODAL WITH FORM -->
|
|
229
|
+
|
|
230
|
+
<!-- Form Modal -->
|
|
231
|
+
<div class="pa-modal" id="formModal">
|
|
232
|
+
<div class="pa-modal__backdrop"></div>
|
|
233
|
+
<div class="pa-modal__container">
|
|
234
|
+
<div class="pa-modal__header">
|
|
235
|
+
<h3 class="pa-modal__title">User Information</h3>
|
|
236
|
+
<button class="pa-btn pa-btn--primary pa-btn--icon-only pa-btn--sm">✕</button>
|
|
237
|
+
</div>
|
|
238
|
+
<div class="pa-modal__body">
|
|
239
|
+
<form>
|
|
240
|
+
<div class="pa-form-group">
|
|
241
|
+
<label class="pa-form-label">Name</label>
|
|
242
|
+
<input type="text" class="pa-input">
|
|
243
|
+
</div>
|
|
244
|
+
<div class="pa-form-group">
|
|
245
|
+
<label class="pa-form-label">Email</label>
|
|
246
|
+
<input type="email" class="pa-input">
|
|
247
|
+
</div>
|
|
248
|
+
</form>
|
|
249
|
+
</div>
|
|
250
|
+
<div class="pa-modal__footer">
|
|
251
|
+
<button class="pa-btn pa-btn--secondary">Cancel</button>
|
|
252
|
+
<button class="pa-btn pa-btn--primary">Submit</button>
|
|
253
|
+
</div>
|
|
254
|
+
</div>
|
|
255
|
+
</div>
|
|
256
|
+
|
|
257
|
+
|
|
258
|
+
<!-- JAVASCRIPT -->
|
|
259
|
+
<script>
|
|
260
|
+
function openModal(modalId) {
|
|
261
|
+
const modal = document.getElementById(modalId);
|
|
262
|
+
if (modal) {
|
|
263
|
+
// Calculate scrollbar width to prevent layout shift
|
|
264
|
+
const scrollbarWidth = window.innerWidth - document.documentElement.clientWidth;
|
|
265
|
+
|
|
266
|
+
modal.classList.add('pa-modal--show');
|
|
267
|
+
document.body.style.overflow = 'hidden'; // Prevent background scrolling
|
|
268
|
+
document.body.style.paddingRight = scrollbarWidth + 'px'; // Compensate for scrollbar
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
function closeModal(modalId) {
|
|
273
|
+
const modal = document.getElementById(modalId);
|
|
274
|
+
if (modal) {
|
|
275
|
+
modal.classList.remove('pa-modal--show');
|
|
276
|
+
document.body.style.overflow = ''; // Restore scrolling
|
|
277
|
+
document.body.style.paddingRight = ''; // Remove compensation
|
|
278
|
+
}
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
// Close modal with Escape key
|
|
282
|
+
document.addEventListener('keydown', function(e) {
|
|
283
|
+
if (e.key === 'Escape') {
|
|
284
|
+
const openModal = document.querySelector('.pa-modal--show');
|
|
285
|
+
if (openModal) {
|
|
286
|
+
closeModal(openModal.id);
|
|
287
|
+
}
|
|
288
|
+
}
|
|
289
|
+
});
|
|
290
|
+
|
|
291
|
+
// Close modal when clicking backdrop
|
|
292
|
+
document.querySelectorAll('.pa-modal__backdrop').forEach(backdrop => {
|
|
293
|
+
backdrop.addEventListener('click', function() {
|
|
294
|
+
const modal = this.closest('.pa-modal');
|
|
295
|
+
if (modal) {
|
|
296
|
+
closeModal(modal.id);
|
|
297
|
+
}
|
|
298
|
+
});
|
|
299
|
+
});
|
|
300
|
+
|
|
301
|
+
// Close modal when clicking close button
|
|
302
|
+
document.querySelectorAll('.pa-modal .pa-btn--icon-only').forEach(btn => {
|
|
303
|
+
btn.addEventListener('click', function() {
|
|
304
|
+
const modal = this.closest('.pa-modal');
|
|
305
|
+
if (modal) {
|
|
306
|
+
closeModal(modal.id);
|
|
307
|
+
}
|
|
308
|
+
});
|
|
309
|
+
});
|
|
310
|
+
</script>
|
|
@@ -0,0 +1,253 @@
|
|
|
1
|
+
<!-- ================================
|
|
2
|
+
POPCONFIRM SNIPPETS
|
|
3
|
+
Pure Admin Visual Framework
|
|
4
|
+
================================ -->
|
|
5
|
+
|
|
6
|
+
<!--
|
|
7
|
+
POPCONFIRM COMPONENT:
|
|
8
|
+
Small confirmation dialogs anchored to trigger buttons.
|
|
9
|
+
Perfect for delete confirmations and quick yes/no decisions.
|
|
10
|
+
|
|
11
|
+
BENEFITS OVER MODALS:
|
|
12
|
+
- Appears directly below/above the trigger button
|
|
13
|
+
- More contextual (stays near the action)
|
|
14
|
+
- Lighter weight (no backdrop)
|
|
15
|
+
- Better for quick decisions
|
|
16
|
+
- Ideal for table row actions
|
|
17
|
+
|
|
18
|
+
POSITION CLASSES:
|
|
19
|
+
- pa-popconfirm--bottom: Arrow on top, popconfirm below button (default)
|
|
20
|
+
- pa-popconfirm--top: Arrow on bottom, popconfirm above button
|
|
21
|
+
- pa-popconfirm--right: Arrow on left, popconfirm to the right
|
|
22
|
+
- pa-popconfirm--left: Arrow on right, popconfirm to the left
|
|
23
|
+
|
|
24
|
+
SIZE VARIANTS:
|
|
25
|
+
- pa-popconfirm--compact: Smaller padding and dimensions
|
|
26
|
+
|
|
27
|
+
ICON VARIANTS (for message):
|
|
28
|
+
- pa-popconfirm__icon--danger: Shows delete icon (🗑️)
|
|
29
|
+
- pa-popconfirm__icon--warning: Shows warning icon (⚠️)
|
|
30
|
+
- pa-popconfirm__icon--info: Shows info icon (ℹ️)
|
|
31
|
+
|
|
32
|
+
JAVASCRIPT REQUIRED:
|
|
33
|
+
- Floating UI library for positioning (loaded globally)
|
|
34
|
+
- Automatic collision detection via flip() middleware
|
|
35
|
+
- Edge detection via shift() middleware
|
|
36
|
+
- Click outside to close
|
|
37
|
+
- Reposition on scroll/resize
|
|
38
|
+
-->
|
|
39
|
+
|
|
40
|
+
<!-- BASIC POPCONFIRM -->
|
|
41
|
+
|
|
42
|
+
<!-- HTML Structure -->
|
|
43
|
+
<button
|
|
44
|
+
class="pa-btn pa-btn--danger"
|
|
45
|
+
onclick="togglePopconfirm(event, 'popconfirm-delete')"
|
|
46
|
+
>
|
|
47
|
+
Delete Item
|
|
48
|
+
</button>
|
|
49
|
+
|
|
50
|
+
<div id="popconfirm-delete" class="pa-popconfirm pa-popconfirm--bottom">
|
|
51
|
+
<div class="pa-popconfirm__arrow"></div>
|
|
52
|
+
<div class="pa-popconfirm__content">
|
|
53
|
+
<div class="pa-popconfirm__message pa-popconfirm__icon pa-popconfirm__icon--danger">
|
|
54
|
+
<p>Are you sure you want to delete this item? This action cannot be undone.</p>
|
|
55
|
+
</div>
|
|
56
|
+
<div class="pa-popconfirm__actions">
|
|
57
|
+
<button class="pa-btn pa-btn--secondary" onclick="closePopconfirm('popconfirm-delete')">Cancel</button>
|
|
58
|
+
<button class="pa-btn pa-btn--danger" onclick="confirmAction('popconfirm-delete')">Delete</button>
|
|
59
|
+
</div>
|
|
60
|
+
</div>
|
|
61
|
+
</div>
|
|
62
|
+
|
|
63
|
+
|
|
64
|
+
<!-- COMPACT POPCONFIRM -->
|
|
65
|
+
|
|
66
|
+
<!-- Smaller variant for table actions -->
|
|
67
|
+
<button
|
|
68
|
+
class="pa-btn pa-btn--xs pa-btn--danger"
|
|
69
|
+
onclick="togglePopconfirm(event, 'popconfirm-compact')"
|
|
70
|
+
>
|
|
71
|
+
Delete
|
|
72
|
+
</button>
|
|
73
|
+
|
|
74
|
+
<div id="popconfirm-compact" class="pa-popconfirm pa-popconfirm--bottom pa-popconfirm--compact">
|
|
75
|
+
<div class="pa-popconfirm__arrow"></div>
|
|
76
|
+
<div class="pa-popconfirm__content">
|
|
77
|
+
<div class="pa-popconfirm__message">
|
|
78
|
+
<p>Delete this item?</p>
|
|
79
|
+
</div>
|
|
80
|
+
<div class="pa-popconfirm__actions">
|
|
81
|
+
<button class="pa-btn pa-btn--secondary" onclick="closePopconfirm('popconfirm-compact')">No</button>
|
|
82
|
+
<button class="pa-btn pa-btn--danger" onclick="confirmAction('popconfirm-compact')">Yes</button>
|
|
83
|
+
</div>
|
|
84
|
+
</div>
|
|
85
|
+
</div>
|
|
86
|
+
|
|
87
|
+
|
|
88
|
+
<!-- WITHOUT ICON -->
|
|
89
|
+
|
|
90
|
+
<!-- Simple message without icon -->
|
|
91
|
+
<div id="popconfirm-simple" class="pa-popconfirm pa-popconfirm--bottom">
|
|
92
|
+
<div class="pa-popconfirm__arrow"></div>
|
|
93
|
+
<div class="pa-popconfirm__content">
|
|
94
|
+
<div class="pa-popconfirm__message">
|
|
95
|
+
<p>Are you sure you want to proceed with this action?</p>
|
|
96
|
+
</div>
|
|
97
|
+
<div class="pa-popconfirm__actions">
|
|
98
|
+
<button class="pa-btn pa-btn--secondary" onclick="closePopconfirm('popconfirm-simple')">Cancel</button>
|
|
99
|
+
<button class="pa-btn pa-btn--primary" onclick="confirmAction('popconfirm-simple')">Confirm</button>
|
|
100
|
+
</div>
|
|
101
|
+
</div>
|
|
102
|
+
</div>
|
|
103
|
+
|
|
104
|
+
|
|
105
|
+
<!-- TABLE USAGE EXAMPLE -->
|
|
106
|
+
|
|
107
|
+
<!-- Common pattern: Delete action in table -->
|
|
108
|
+
<table class="pa-table pa-table--striped">
|
|
109
|
+
<thead>
|
|
110
|
+
<tr>
|
|
111
|
+
<th>Name</th>
|
|
112
|
+
<th>Status</th>
|
|
113
|
+
<th class="col-auto">Actions</th>
|
|
114
|
+
</tr>
|
|
115
|
+
</thead>
|
|
116
|
+
<tbody>
|
|
117
|
+
<tr>
|
|
118
|
+
<td>John Doe</td>
|
|
119
|
+
<td><span class="pa-badge pa-badge--success">Active</span></td>
|
|
120
|
+
<td class="col-auto">
|
|
121
|
+
<div class="pa-btn-group">
|
|
122
|
+
<button class="pa-btn pa-btn--xs pa-btn--primary">Edit</button>
|
|
123
|
+
<button
|
|
124
|
+
class="pa-btn pa-btn--xs pa-btn--danger"
|
|
125
|
+
onclick="togglePopconfirm(event, 'popconfirm-user-1')"
|
|
126
|
+
>
|
|
127
|
+
Delete
|
|
128
|
+
</button>
|
|
129
|
+
</div>
|
|
130
|
+
</td>
|
|
131
|
+
</tr>
|
|
132
|
+
</tbody>
|
|
133
|
+
</table>
|
|
134
|
+
|
|
135
|
+
<!-- Popconfirm for table row -->
|
|
136
|
+
<div id="popconfirm-user-1" class="pa-popconfirm pa-popconfirm--bottom pa-popconfirm--compact">
|
|
137
|
+
<div class="pa-popconfirm__arrow"></div>
|
|
138
|
+
<div class="pa-popconfirm__content">
|
|
139
|
+
<div class="pa-popconfirm__message">
|
|
140
|
+
<p>Delete John Doe?</p>
|
|
141
|
+
</div>
|
|
142
|
+
<div class="pa-popconfirm__actions">
|
|
143
|
+
<button class="pa-btn pa-btn--secondary" onclick="closePopconfirm('popconfirm-user-1')">No</button>
|
|
144
|
+
<button class="pa-btn pa-btn--danger" onclick="confirmAction('popconfirm-user-1')">Yes</button>
|
|
145
|
+
</div>
|
|
146
|
+
</div>
|
|
147
|
+
</div>
|
|
148
|
+
|
|
149
|
+
|
|
150
|
+
<!-- JAVASCRIPT FUNCTIONS -->
|
|
151
|
+
|
|
152
|
+
<script>
|
|
153
|
+
// Popconfirm positioning and interaction
|
|
154
|
+
let currentPopconfirm = null;
|
|
155
|
+
let currentTrigger = null;
|
|
156
|
+
|
|
157
|
+
function togglePopconfirm(event, popconfirmId) {
|
|
158
|
+
event.stopPropagation();
|
|
159
|
+
|
|
160
|
+
const trigger = event.currentTarget;
|
|
161
|
+
const popconfirm = document.getElementById(popconfirmId);
|
|
162
|
+
|
|
163
|
+
// Close current if different
|
|
164
|
+
if (currentPopconfirm && currentPopconfirm !== popconfirm) {
|
|
165
|
+
currentPopconfirm.classList.remove('is-open');
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
// Toggle this popconfirm
|
|
169
|
+
const isOpen = popconfirm.classList.contains('is-open');
|
|
170
|
+
|
|
171
|
+
if (isOpen) {
|
|
172
|
+
popconfirm.classList.remove('is-open');
|
|
173
|
+
currentPopconfirm = null;
|
|
174
|
+
currentTrigger = null;
|
|
175
|
+
} else {
|
|
176
|
+
// Position and show
|
|
177
|
+
positionPopconfirm(trigger, popconfirm);
|
|
178
|
+
popconfirm.classList.add('is-open');
|
|
179
|
+
currentPopconfirm = popconfirm;
|
|
180
|
+
currentTrigger = trigger;
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
function closePopconfirm(popconfirmId) {
|
|
185
|
+
const popconfirm = document.getElementById(popconfirmId);
|
|
186
|
+
popconfirm.classList.remove('is-open');
|
|
187
|
+
|
|
188
|
+
if (currentPopconfirm === popconfirm) {
|
|
189
|
+
currentPopconfirm = null;
|
|
190
|
+
currentTrigger = null;
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
function confirmAction(popconfirmId) {
|
|
195
|
+
console.log('Confirmed:', popconfirmId);
|
|
196
|
+
closePopconfirm(popconfirmId);
|
|
197
|
+
|
|
198
|
+
// Perform your action here (e.g., delete API call)
|
|
199
|
+
}
|
|
200
|
+
|
|
201
|
+
async function positionPopconfirm(trigger, popconfirm) {
|
|
202
|
+
// Get the initial position class (or default to bottom)
|
|
203
|
+
const classMatch = popconfirm.className.match(/pa-popconfirm--(top|bottom|left|right)/);
|
|
204
|
+
const placement = classMatch ? classMatch[1] : 'bottom';
|
|
205
|
+
|
|
206
|
+
// Use Floating UI for automatic positioning with collision detection
|
|
207
|
+
const { computePosition, flip, shift, offset } = window.FloatingUIDOM;
|
|
208
|
+
|
|
209
|
+
const { x, y, placement: finalPlacement } = await computePosition(trigger, popconfirm, {
|
|
210
|
+
placement: placement,
|
|
211
|
+
middleware: [
|
|
212
|
+
offset(8), // 8px gap from trigger
|
|
213
|
+
flip(), // Flip to opposite side if not enough space
|
|
214
|
+
shift({ padding: 10 }) // Keep 10px from viewport edges
|
|
215
|
+
]
|
|
216
|
+
});
|
|
217
|
+
|
|
218
|
+
// Update position class to match actual placement
|
|
219
|
+
popconfirm.className = popconfirm.className
|
|
220
|
+
.replace(/pa-popconfirm--(top|bottom|left|right)/g, '')
|
|
221
|
+
.trim() + ' pa-popconfirm--' + finalPlacement;
|
|
222
|
+
|
|
223
|
+
// Apply positioning
|
|
224
|
+
Object.assign(popconfirm.style, {
|
|
225
|
+
left: `${x}px`,
|
|
226
|
+
top: `${y}px`
|
|
227
|
+
});
|
|
228
|
+
}
|
|
229
|
+
|
|
230
|
+
// Close popconfirm when clicking outside
|
|
231
|
+
document.addEventListener('click', (e) => {
|
|
232
|
+
if (currentPopconfirm &&
|
|
233
|
+
!currentPopconfirm.contains(e.target) &&
|
|
234
|
+
currentTrigger !== e.target) {
|
|
235
|
+
currentPopconfirm.classList.remove('is-open');
|
|
236
|
+
currentPopconfirm = null;
|
|
237
|
+
currentTrigger = null;
|
|
238
|
+
}
|
|
239
|
+
});
|
|
240
|
+
|
|
241
|
+
// Reposition on scroll/resize
|
|
242
|
+
window.addEventListener('scroll', () => {
|
|
243
|
+
if (currentPopconfirm && currentTrigger) {
|
|
244
|
+
positionPopconfirm(currentTrigger, currentPopconfirm);
|
|
245
|
+
}
|
|
246
|
+
});
|
|
247
|
+
|
|
248
|
+
window.addEventListener('resize', () => {
|
|
249
|
+
if (currentPopconfirm && currentTrigger) {
|
|
250
|
+
positionPopconfirm(currentTrigger, currentPopconfirm);
|
|
251
|
+
}
|
|
252
|
+
});
|
|
253
|
+
</script>
|