@erplora/outfitkit 0.1.1
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 +457 -0
- package/dist/base/anchor.d.ts +13 -0
- package/dist/base/define.d.ts +1 -0
- package/dist/base/relay.d.ts +1 -0
- package/dist/cdn.d.ts +96 -0
- package/dist/components/ok-app-launcher/ok-app-launcher.d.ts +57 -0
- package/dist/components/ok-audio/ok-audio.d.ts +45 -0
- package/dist/components/ok-avatar/ok-avatar.d.ts +36 -0
- package/dist/components/ok-avatar-group/ok-avatar-group.d.ts +38 -0
- package/dist/components/ok-bar-list/ok-bar-list.d.ts +36 -0
- package/dist/components/ok-bento/ok-bento.d.ts +17 -0
- package/dist/components/ok-bento-item/ok-bento-item.d.ts +34 -0
- package/dist/components/ok-calculator/ok-calculator.d.ts +46 -0
- package/dist/components/ok-calendar/ok-calendar.d.ts +63 -0
- package/dist/components/ok-carousel/ok-carousel.d.ts +48 -0
- package/dist/components/ok-chart/ok-chart.d.ts +55 -0
- package/dist/components/ok-chat/ok-chat.d.ts +54 -0
- package/dist/components/ok-coachmark/ok-coachmark.d.ts +69 -0
- package/dist/components/ok-code/ok-code.d.ts +28 -0
- package/dist/components/ok-color-picker/ok-color-picker.d.ts +63 -0
- package/dist/components/ok-combo/ok-combo.d.ts +46 -0
- package/dist/components/ok-command-palette/ok-command-palette.d.ts +72 -0
- package/dist/components/ok-contact-form/ok-contact-form.d.ts +54 -0
- package/dist/components/ok-cropper/ok-cropper.d.ts +60 -0
- package/dist/components/ok-cta-band/ok-cta-band.d.ts +18 -0
- package/dist/components/ok-currency/ok-currency.d.ts +31 -0
- package/dist/components/ok-data-table/ok-data-table.d.ts +312 -0
- package/dist/components/ok-date-picker/ok-date-picker.d.ts +81 -0
- package/dist/components/ok-detail-list/ok-detail-list.d.ts +30 -0
- package/dist/components/ok-diff/ok-diff.d.ts +38 -0
- package/dist/components/ok-donut/ok-donut.d.ts +38 -0
- package/dist/components/ok-drawer/ok-drawer.d.ts +56 -0
- package/dist/components/ok-dropzone/ok-dropzone.d.ts +48 -0
- package/dist/components/ok-empty-state/ok-empty-state.d.ts +16 -0
- package/dist/components/ok-error-page/ok-error-page.d.ts +77 -0
- package/dist/components/ok-event-card/ok-event-card.d.ts +56 -0
- package/dist/components/ok-feature-card/ok-feature-card.d.ts +23 -0
- package/dist/components/ok-file-item/ok-file-item.d.ts +31 -0
- package/dist/components/ok-file-manager/ok-file-manager.d.ts +145 -0
- package/dist/components/ok-footer/ok-footer.d.ts +10 -0
- package/dist/components/ok-funnel/ok-funnel.d.ts +31 -0
- package/dist/components/ok-gallery/ok-gallery.d.ts +34 -0
- package/dist/components/ok-gauge/ok-gauge.d.ts +49 -0
- package/dist/components/ok-heatmap/ok-heatmap.d.ts +45 -0
- package/dist/components/ok-hero/ok-hero.d.ts +10 -0
- package/dist/components/ok-hover-card/ok-hover-card.d.ts +76 -0
- package/dist/components/ok-icon-tile/ok-icon-tile.d.ts +24 -0
- package/dist/components/ok-image/ok-image.d.ts +56 -0
- package/dist/components/ok-inline-feedback/ok-inline-feedback.d.ts +33 -0
- package/dist/components/ok-invoice/ok-invoice.d.ts +137 -0
- package/dist/components/ok-json-viewer/ok-json-viewer.d.ts +31 -0
- package/dist/components/ok-kanban/ok-kanban.d.ts +56 -0
- package/dist/components/ok-kbd/ok-kbd.d.ts +21 -0
- package/dist/components/ok-keyboard/ok-keyboard.d.ts +35 -0
- package/dist/components/ok-kpi/ok-kpi.d.ts +24 -0
- package/dist/components/ok-language-select/ok-language-select.d.ts +31 -0
- package/dist/components/ok-lightbox/ok-lightbox.d.ts +59 -0
- package/dist/components/ok-logo-cloud/ok-logo-cloud.d.ts +14 -0
- package/dist/components/ok-loyalty-card/ok-loyalty-card.d.ts +35 -0
- package/dist/components/ok-mail/ok-mail.d.ts +117 -0
- package/dist/components/ok-menu/ok-menu.d.ts +75 -0
- package/dist/components/ok-menubar/ok-menubar.d.ts +75 -0
- package/dist/components/ok-navbar/ok-navbar.d.ts +42 -0
- package/dist/components/ok-notification-center/ok-notification-center.d.ts +79 -0
- package/dist/components/ok-org-chart/ok-org-chart.d.ts +67 -0
- package/dist/components/ok-otp/ok-otp.d.ts +31 -0
- package/dist/components/ok-page-header/ok-page-header.d.ts +23 -0
- package/dist/components/ok-pagination/ok-pagination.d.ts +44 -0
- package/dist/components/ok-pdf/ok-pdf.d.ts +32 -0
- package/dist/components/ok-phone/ok-phone.d.ts +48 -0
- package/dist/components/ok-pinpad/ok-pinpad.d.ts +29 -0
- package/dist/components/ok-pricing-card/ok-pricing-card.d.ts +31 -0
- package/dist/components/ok-product-card/ok-product-card.d.ts +25 -0
- package/dist/components/ok-qr/ok-qr.d.ts +24 -0
- package/dist/components/ok-qty-stepper/ok-qty-stepper.d.ts +35 -0
- package/dist/components/ok-range-dual/ok-range-dual.d.ts +38 -0
- package/dist/components/ok-rating/ok-rating.d.ts +33 -0
- package/dist/components/ok-receipt/ok-receipt.d.ts +103 -0
- package/dist/components/ok-reveal/ok-reveal.d.ts +21 -0
- package/dist/components/ok-rich-text/ok-rich-text.d.ts +46 -0
- package/dist/components/ok-scheduler/ok-scheduler.d.ts +74 -0
- package/dist/components/ok-select-card/ok-select-card.d.ts +37 -0
- package/dist/components/ok-signature/ok-signature.d.ts +55 -0
- package/dist/components/ok-skeleton/ok-skeleton.d.ts +40 -0
- package/dist/components/ok-sparkline/ok-sparkline.d.ts +27 -0
- package/dist/components/ok-split-button/ok-split-button.d.ts +49 -0
- package/dist/components/ok-splitter/ok-splitter.d.ts +36 -0
- package/dist/components/ok-stat/ok-stat.d.ts +16 -0
- package/dist/components/ok-status-dot/ok-status-dot.d.ts +24 -0
- package/dist/components/ok-status-pill/ok-status-pill.d.ts +22 -0
- package/dist/components/ok-stepper/ok-stepper.d.ts +33 -0
- package/dist/components/ok-store/ok-store.d.ts +33 -0
- package/dist/components/ok-tag-input/ok-tag-input.d.ts +39 -0
- package/dist/components/ok-testimonial/ok-testimonial.d.ts +21 -0
- package/dist/components/ok-time-picker/ok-time-picker.d.ts +50 -0
- package/dist/components/ok-timeline/ok-timeline.d.ts +33 -0
- package/dist/components/ok-tree/ok-tree.d.ts +46 -0
- package/dist/components/ok-video/ok-video.d.ts +49 -0
- package/dist/components/ok-widget-board/ok-widget-board.d.ts +71 -0
- package/dist/components/ok-wizard/ok-wizard.d.ts +30 -0
- package/dist/define.js +8 -0
- package/dist/erplora.css +112 -0
- package/dist/index.d.ts +158 -0
- package/dist/index.js +197 -0
- package/dist/layout.css +338 -0
- package/dist/ok-app-launcher.js +396 -0
- package/dist/ok-audio.js +308 -0
- package/dist/ok-avatar-group.js +158 -0
- package/dist/ok-avatar.js +179 -0
- package/dist/ok-bar-list.js +189 -0
- package/dist/ok-bento-item.js +168 -0
- package/dist/ok-bento.js +63 -0
- package/dist/ok-calculator.js +406 -0
- package/dist/ok-calendar.js +541 -0
- package/dist/ok-carousel.js +352 -0
- package/dist/ok-chart.js +325 -0
- package/dist/ok-chat.js +320 -0
- package/dist/ok-coachmark.js +500 -0
- package/dist/ok-code.js +190 -0
- package/dist/ok-color-picker.js +569 -0
- package/dist/ok-combo.js +294 -0
- package/dist/ok-command-palette.js +448 -0
- package/dist/ok-contact-form.js +288 -0
- package/dist/ok-cropper.js +404 -0
- package/dist/ok-cta-band.js +134 -0
- package/dist/ok-currency.js +172 -0
- package/dist/ok-data-table.js +1281 -0
- package/dist/ok-date-picker.js +736 -0
- package/dist/ok-detail-list.js +156 -0
- package/dist/ok-diff.js +200 -0
- package/dist/ok-donut.js +280 -0
- package/dist/ok-drawer.js +357 -0
- package/dist/ok-dropzone.js +376 -0
- package/dist/ok-empty-state.js +104 -0
- package/dist/ok-error-page.js +547 -0
- package/dist/ok-event-card.js +384 -0
- package/dist/ok-feature-card.js +152 -0
- package/dist/ok-file-item.js +259 -0
- package/dist/ok-file-manager.js +1116 -0
- package/dist/ok-footer.js +67 -0
- package/dist/ok-funnel.js +181 -0
- package/dist/ok-gallery.js +293 -0
- package/dist/ok-gauge.js +385 -0
- package/dist/ok-heatmap.js +268 -0
- package/dist/ok-hero.js +43 -0
- package/dist/ok-hover-card.js +480 -0
- package/dist/ok-icon-tile.js +123 -0
- package/dist/ok-image.js +471 -0
- package/dist/ok-inline-feedback.js +221 -0
- package/dist/ok-invoice.js +229 -0
- package/dist/ok-json-viewer.js +330 -0
- package/dist/ok-kanban.js +427 -0
- package/dist/ok-kbd.js +159 -0
- package/dist/ok-keyboard.js +402 -0
- package/dist/ok-kpi.js +147 -0
- package/dist/ok-language-select.js +188 -0
- package/dist/ok-lightbox.js +490 -0
- package/dist/ok-logo-cloud.js +92 -0
- package/dist/ok-loyalty-card.js +353 -0
- package/dist/ok-mail.js +562 -0
- package/dist/ok-menu.js +529 -0
- package/dist/ok-menubar.js +628 -0
- package/dist/ok-navbar.js +306 -0
- package/dist/ok-notification-center.js +545 -0
- package/dist/ok-org-chart.js +619 -0
- package/dist/ok-otp.js +199 -0
- package/dist/ok-page-header.js +202 -0
- package/dist/ok-pagination.js +366 -0
- package/dist/ok-pdf.js +160 -0
- package/dist/ok-phone.js +225 -0
- package/dist/ok-pinpad.js +171 -0
- package/dist/ok-pricing-card.js +184 -0
- package/dist/ok-product-card.js +178 -0
- package/dist/ok-qr.js +652 -0
- package/dist/ok-qty-stepper.js +212 -0
- package/dist/ok-range-dual.js +280 -0
- package/dist/ok-rating.js +199 -0
- package/dist/ok-receipt.js +183 -0
- package/dist/ok-reveal.js +94 -0
- package/dist/ok-rich-text.js +538 -0
- package/dist/ok-scheduler.js +518 -0
- package/dist/ok-select-card.js +231 -0
- package/dist/ok-signature.js +267 -0
- package/dist/ok-skeleton.js +345 -0
- package/dist/ok-sparkline.js +150 -0
- package/dist/ok-split-button.js +251 -0
- package/dist/ok-splitter.js +289 -0
- package/dist/ok-stat.js +77 -0
- package/dist/ok-status-dot.js +163 -0
- package/dist/ok-status-pill.js +123 -0
- package/dist/ok-stepper.js +299 -0
- package/dist/ok-store.js +83 -0
- package/dist/ok-tag-input.js +358 -0
- package/dist/ok-testimonial.js +136 -0
- package/dist/ok-time-picker.js +472 -0
- package/dist/ok-timeline.js +251 -0
- package/dist/ok-tree.js +266 -0
- package/dist/ok-video.js +362 -0
- package/dist/ok-widget-board.js +265 -0
- package/dist/ok-wizard.js +153 -0
- package/dist/outfitkit.js +96 -0
- package/dist/shared/anchor.js +14 -0
- package/dist/store/controller.d.ts +17 -0
- package/dist/store/idb.d.ts +16 -0
- package/dist/store/store.d.ts +39 -0
- package/dist/store-controller.js +31 -0
- package/dist/store.js +182 -0
- package/dist/theme.example.css +70 -0
- package/package.json +147 -0
|
@@ -0,0 +1,153 @@
|
|
|
1
|
+
import { LitElement, css, html } from "lit";
|
|
2
|
+
import { property } from "lit/decorators.js";
|
|
3
|
+
import { define } from "./define.js";
|
|
4
|
+
import "./ok-stepper.js";
|
|
5
|
+
var __defProp = Object.defineProperty;
|
|
6
|
+
var __decorateClass = (decorators, target, key, kind) => {
|
|
7
|
+
var result = void 0;
|
|
8
|
+
for (var i = decorators.length - 1, decorator; i >= 0; i--)
|
|
9
|
+
if (decorator = decorators[i])
|
|
10
|
+
result = decorator(target, key, result) || result;
|
|
11
|
+
if (result) __defProp(target, key, result);
|
|
12
|
+
return result;
|
|
13
|
+
};
|
|
14
|
+
class OkWizard extends LitElement {
|
|
15
|
+
constructor() {
|
|
16
|
+
super(...arguments);
|
|
17
|
+
this.steps = [];
|
|
18
|
+
this.current = 0;
|
|
19
|
+
this.backLabel = "Back";
|
|
20
|
+
this.nextLabel = "Next";
|
|
21
|
+
this.finishLabel = "Finish";
|
|
22
|
+
}
|
|
23
|
+
static {
|
|
24
|
+
this.styles = css`
|
|
25
|
+
/* Autocontenido; ancho máximo el del contenedor. */
|
|
26
|
+
:host {
|
|
27
|
+
display: block;
|
|
28
|
+
width: 100%;
|
|
29
|
+
max-width: 100%;
|
|
30
|
+
box-sizing: border-box;
|
|
31
|
+
font-family: var(--ok-font-family, var(--ion-font-family, inherit));
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
.stepper {
|
|
35
|
+
margin-bottom: 1.5rem;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
/* Contenedor del contenido del paso. Solo se muestra el slot del paso actual; el resto se
|
|
39
|
+
oculta vía [hidden]. Min-height para que la barra de navegación no salte entre pasos. */
|
|
40
|
+
.panels {
|
|
41
|
+
min-height: 4rem;
|
|
42
|
+
}
|
|
43
|
+
.panel[hidden] {
|
|
44
|
+
display: none;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
/* Barra de navegación: Atrás a la izquierda, Siguiente/Finalizar a la derecha. */
|
|
48
|
+
.nav {
|
|
49
|
+
display: flex;
|
|
50
|
+
align-items: center;
|
|
51
|
+
justify-content: space-between;
|
|
52
|
+
gap: 0.75rem;
|
|
53
|
+
margin-top: 1.5rem;
|
|
54
|
+
padding-top: 1rem;
|
|
55
|
+
border-top: 1px solid var(--ok-border-color, var(--ion-border-color, #e0e0e0));
|
|
56
|
+
}
|
|
57
|
+
/* Cuando no hay botón Atrás, empujamos el de avance a la derecha. */
|
|
58
|
+
.nav.no-back {
|
|
59
|
+
justify-content: flex-end;
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
@media (max-width: 640px) {
|
|
63
|
+
.stepper {
|
|
64
|
+
margin-bottom: 1rem;
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
`;
|
|
68
|
+
}
|
|
69
|
+
/** Cambia al índice dado (con clamp) y emite ok-step-change si realmente cambia. */
|
|
70
|
+
_goTo(index) {
|
|
71
|
+
const last = this.steps.length - 1;
|
|
72
|
+
const next = Math.max(0, Math.min(index, last));
|
|
73
|
+
if (next === this.current) return;
|
|
74
|
+
this.current = next;
|
|
75
|
+
this.dispatchEvent(
|
|
76
|
+
new CustomEvent("ok-step-change", {
|
|
77
|
+
detail: { index: next },
|
|
78
|
+
bubbles: true,
|
|
79
|
+
composed: true
|
|
80
|
+
})
|
|
81
|
+
);
|
|
82
|
+
}
|
|
83
|
+
/** Retrocede un paso. */
|
|
84
|
+
_back() {
|
|
85
|
+
this._goTo(this.current - 1);
|
|
86
|
+
}
|
|
87
|
+
/** Avanza un paso, o emite ok-finish si es el último. */
|
|
88
|
+
_next() {
|
|
89
|
+
if (this.current >= this.steps.length - 1) {
|
|
90
|
+
this.dispatchEvent(
|
|
91
|
+
new CustomEvent("ok-finish", { bubbles: true, composed: true })
|
|
92
|
+
);
|
|
93
|
+
return;
|
|
94
|
+
}
|
|
95
|
+
this._goTo(this.current + 1);
|
|
96
|
+
}
|
|
97
|
+
/** Navegación desde el stepper (clic en un paso). */
|
|
98
|
+
_onStepSelect(e) {
|
|
99
|
+
const { index } = e.detail;
|
|
100
|
+
e.stopPropagation();
|
|
101
|
+
this._goTo(index);
|
|
102
|
+
}
|
|
103
|
+
render() {
|
|
104
|
+
const isFirst = this.current <= 0;
|
|
105
|
+
const isLast = this.current >= this.steps.length - 1;
|
|
106
|
+
return html`
|
|
107
|
+
<div class="stepper">
|
|
108
|
+
<ok-stepper
|
|
109
|
+
.steps=${this.steps}
|
|
110
|
+
.current=${this.current}
|
|
111
|
+
@ok-step-select=${(e) => this._onStepSelect(e)}
|
|
112
|
+
></ok-stepper>
|
|
113
|
+
</div>
|
|
114
|
+
|
|
115
|
+
<!-- Solo el panel del paso actual es visible; el resto queda oculto pero en el DOM -->
|
|
116
|
+
<div class="panels">
|
|
117
|
+
${this.steps.map(
|
|
118
|
+
(_step, i) => html`<div class="panel" ?hidden=${i !== this.current}>
|
|
119
|
+
<slot name="step-${i}"></slot>
|
|
120
|
+
</div>`
|
|
121
|
+
)}
|
|
122
|
+
</div>
|
|
123
|
+
|
|
124
|
+
<div class="nav ${isFirst ? "no-back" : ""}">
|
|
125
|
+
${isFirst ? "" : html`<ion-button fill="outline" color="medium" @click=${() => this._back()}>
|
|
126
|
+
${this.backLabel}
|
|
127
|
+
</ion-button>`}
|
|
128
|
+
<ion-button color="primary" @click=${() => this._next()}>
|
|
129
|
+
${isLast ? this.finishLabel : this.nextLabel}
|
|
130
|
+
</ion-button>
|
|
131
|
+
</div>
|
|
132
|
+
`;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
__decorateClass([
|
|
136
|
+
property({ attribute: false })
|
|
137
|
+
], OkWizard.prototype, "steps");
|
|
138
|
+
__decorateClass([
|
|
139
|
+
property({ type: Number })
|
|
140
|
+
], OkWizard.prototype, "current");
|
|
141
|
+
__decorateClass([
|
|
142
|
+
property()
|
|
143
|
+
], OkWizard.prototype, "backLabel");
|
|
144
|
+
__decorateClass([
|
|
145
|
+
property()
|
|
146
|
+
], OkWizard.prototype, "nextLabel");
|
|
147
|
+
__decorateClass([
|
|
148
|
+
property()
|
|
149
|
+
], OkWizard.prototype, "finishLabel");
|
|
150
|
+
define("ok-wizard", OkWizard);
|
|
151
|
+
export {
|
|
152
|
+
OkWizard
|
|
153
|
+
};
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import "./ok-store.js";
|
|
2
|
+
import "./store.js";
|
|
3
|
+
import "./ok-data-table.js";
|
|
4
|
+
import "./ok-mail.js";
|
|
5
|
+
import "./ok-tree.js";
|
|
6
|
+
import "./ok-inline-feedback.js";
|
|
7
|
+
import "./ok-empty-state.js";
|
|
8
|
+
import "./ok-kpi.js";
|
|
9
|
+
import "./ok-stat.js";
|
|
10
|
+
import "./ok-stepper.js";
|
|
11
|
+
import "./ok-wizard.js";
|
|
12
|
+
import "./ok-widget-board.js";
|
|
13
|
+
import "./ok-contact-form.js";
|
|
14
|
+
import "./ok-calendar.js";
|
|
15
|
+
import "./ok-kanban.js";
|
|
16
|
+
import "./ok-app-launcher.js";
|
|
17
|
+
import "./ok-split-button.js";
|
|
18
|
+
import "./ok-combo.js";
|
|
19
|
+
import "./ok-tag-input.js";
|
|
20
|
+
import "./ok-rating.js";
|
|
21
|
+
import "./ok-otp.js";
|
|
22
|
+
import "./ok-pinpad.js";
|
|
23
|
+
import "./ok-currency.js";
|
|
24
|
+
import "./ok-phone.js";
|
|
25
|
+
import "./ok-dropzone.js";
|
|
26
|
+
import "./ok-sparkline.js";
|
|
27
|
+
import "./ok-chat.js";
|
|
28
|
+
import "./ok-scheduler.js";
|
|
29
|
+
import "./ok-menubar.js";
|
|
30
|
+
import "./ok-carousel.js";
|
|
31
|
+
import "./ok-signature.js";
|
|
32
|
+
import "./ok-qr.js";
|
|
33
|
+
import "./ok-audio.js";
|
|
34
|
+
import "./ok-video.js";
|
|
35
|
+
import "./ok-pdf.js";
|
|
36
|
+
import "./ok-receipt.js";
|
|
37
|
+
import "./ok-invoice.js";
|
|
38
|
+
import "./ok-timeline.js";
|
|
39
|
+
import "./ok-qty-stepper.js";
|
|
40
|
+
import "./ok-command-palette.js";
|
|
41
|
+
import "./ok-color-picker.js";
|
|
42
|
+
import "./ok-avatar.js";
|
|
43
|
+
import "./ok-status-pill.js";
|
|
44
|
+
import "./ok-drawer.js";
|
|
45
|
+
import "./ok-page-header.js";
|
|
46
|
+
import "./ok-bento.js";
|
|
47
|
+
import "./ok-bento-item.js";
|
|
48
|
+
import "./ok-reveal.js";
|
|
49
|
+
import "./ok-feature-card.js";
|
|
50
|
+
import "./ok-pricing-card.js";
|
|
51
|
+
import "./ok-product-card.js";
|
|
52
|
+
import "./ok-logo-cloud.js";
|
|
53
|
+
import "./ok-testimonial.js";
|
|
54
|
+
import "./ok-cta-band.js";
|
|
55
|
+
import "./ok-language-select.js";
|
|
56
|
+
import "./ok-navbar.js";
|
|
57
|
+
import "./ok-footer.js";
|
|
58
|
+
import "./ok-hero.js";
|
|
59
|
+
import "./ok-pagination.js";
|
|
60
|
+
import "./ok-skeleton.js";
|
|
61
|
+
import "./ok-gauge.js";
|
|
62
|
+
import "./ok-chart.js";
|
|
63
|
+
import "./ok-donut.js";
|
|
64
|
+
import "./ok-heatmap.js";
|
|
65
|
+
import "./ok-funnel.js";
|
|
66
|
+
import "./ok-bar-list.js";
|
|
67
|
+
import "./ok-detail-list.js";
|
|
68
|
+
import "./ok-icon-tile.js";
|
|
69
|
+
import "./ok-status-dot.js";
|
|
70
|
+
import "./ok-kbd.js";
|
|
71
|
+
import "./ok-menu.js";
|
|
72
|
+
import "./ok-hover-card.js";
|
|
73
|
+
import "./ok-notification-center.js";
|
|
74
|
+
import "./ok-coachmark.js";
|
|
75
|
+
import "./ok-select-card.js";
|
|
76
|
+
import "./ok-error-page.js";
|
|
77
|
+
import "./ok-date-picker.js";
|
|
78
|
+
import "./ok-time-picker.js";
|
|
79
|
+
import "./ok-range-dual.js";
|
|
80
|
+
import "./ok-file-item.js";
|
|
81
|
+
import "./ok-rich-text.js";
|
|
82
|
+
import "./ok-code.js";
|
|
83
|
+
import "./ok-json-viewer.js";
|
|
84
|
+
import "./ok-diff.js";
|
|
85
|
+
import "./ok-keyboard.js";
|
|
86
|
+
import "./ok-calculator.js";
|
|
87
|
+
import "./ok-image.js";
|
|
88
|
+
import "./ok-gallery.js";
|
|
89
|
+
import "./ok-lightbox.js";
|
|
90
|
+
import "./ok-cropper.js";
|
|
91
|
+
import "./ok-splitter.js";
|
|
92
|
+
import "./ok-loyalty-card.js";
|
|
93
|
+
import "./ok-event-card.js";
|
|
94
|
+
import "./ok-avatar-group.js";
|
|
95
|
+
import "./ok-org-chart.js";
|
|
96
|
+
import "./ok-file-manager.js";
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
function computeAnchor(trigger, panel, opts = {}) {
|
|
2
|
+
const gap = opts.gap ?? 8;
|
|
3
|
+
const margin = opts.margin ?? 8;
|
|
4
|
+
const t = trigger.getBoundingClientRect();
|
|
5
|
+
const p = panel.getBoundingClientRect();
|
|
6
|
+
const vw = window.innerWidth;
|
|
7
|
+
const vh = window.innerHeight;
|
|
8
|
+
const end = t.left + p.width > vw - margin && t.right - p.width >= margin;
|
|
9
|
+
const above = t.bottom + gap + p.height > vh - margin && t.top - gap - p.height >= margin;
|
|
10
|
+
return { end, above };
|
|
11
|
+
}
|
|
12
|
+
export {
|
|
13
|
+
computeAnchor as c
|
|
14
|
+
};
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { ReactiveController, ReactiveControllerHost } from 'lit';
|
|
2
|
+
import type { Store } from './store.js';
|
|
3
|
+
export declare class StoreController<T = unknown> implements ReactiveController {
|
|
4
|
+
private host;
|
|
5
|
+
private store;
|
|
6
|
+
private key?;
|
|
7
|
+
private unsubscribe?;
|
|
8
|
+
constructor(host: ReactiveControllerHost, store: Store, key?: string);
|
|
9
|
+
/** Valor actual de la clave observada (o `undefined` si el controller observa todo el store). */
|
|
10
|
+
get value(): T | undefined;
|
|
11
|
+
/** Escribe en la clave observada. No-op si el controller no tiene clave. */
|
|
12
|
+
set(value: T): void;
|
|
13
|
+
/** Actualiza la clave observada a partir del valor previo. No-op si no hay clave. */
|
|
14
|
+
update(fn: (prev: T | undefined) => T): void;
|
|
15
|
+
hostConnected(): void;
|
|
16
|
+
hostDisconnected(): void;
|
|
17
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export interface IdbAdapter {
|
|
2
|
+
/** Lee TODO el objectStore como pares [clave, valor] (para hidratar la caché al arrancar). */
|
|
3
|
+
getAll(): Promise<Array<[string, unknown]>>;
|
|
4
|
+
/** Escribe (o reemplaza) un valor por clave. */
|
|
5
|
+
set(key: string, val: unknown): Promise<void>;
|
|
6
|
+
/** Borra una clave. */
|
|
7
|
+
delete(key: string): Promise<void>;
|
|
8
|
+
/** Vacía el objectStore entero. */
|
|
9
|
+
clear(): Promise<void>;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Crea un adaptador IndexedDB para una DB/objectStore concretos. Si no hay soporte de IndexedDB,
|
|
13
|
+
* devuelve un adaptador NO-OP (memoria-solo). La apertura es perezosa y se cachea; si falla, se
|
|
14
|
+
* cae también a NO-OP (sin lanzar). `dbName`/`storeName` por defecto: 'outfitkit' / 'kv'.
|
|
15
|
+
*/
|
|
16
|
+
export declare function createIdb(dbName?: string, storeName?: string): IdbAdapter;
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
/** Callback de suscripción: recibe el nuevo valor y la clave que cambió. En `clear()`, value=undefined. */
|
|
2
|
+
export type StoreSubscriber<T = unknown> = (value: T | undefined, key: string) => void;
|
|
3
|
+
export interface StoreOptions {
|
|
4
|
+
/** Nombre de la base de datos IndexedDB (default: 'outfitkit'). */
|
|
5
|
+
name?: string;
|
|
6
|
+
/** Nombre del objectStore dentro de la DB (default: 'kv'). */
|
|
7
|
+
storeName?: string;
|
|
8
|
+
}
|
|
9
|
+
export interface Store {
|
|
10
|
+
/** Resuelve cuando la caché se ha hidratado desde IndexedDB. Espérala antes de leer al arrancar. */
|
|
11
|
+
readonly ready: Promise<void>;
|
|
12
|
+
/** Lee un valor de la caché (SÍNCRONO). `undefined` si no existe. */
|
|
13
|
+
get<T = unknown>(key: string): T | undefined;
|
|
14
|
+
/** Escribe un valor: actualiza caché, notifica suscriptores y persiste en IndexedDB (fire-and-forget). */
|
|
15
|
+
set<T = unknown>(key: string, value: T): void;
|
|
16
|
+
/** Actualiza un valor a partir del anterior: `fn(prev) => next`. */
|
|
17
|
+
update<T = unknown>(key: string, fn: (prev: T | undefined) => T): void;
|
|
18
|
+
/** Borra una clave. */
|
|
19
|
+
delete(key: string): void;
|
|
20
|
+
/** Alias de `delete`. */
|
|
21
|
+
remove(key: string): void;
|
|
22
|
+
/** Vacía el store entero. */
|
|
23
|
+
clear(): void;
|
|
24
|
+
/** ¿Existe la clave en la caché? */
|
|
25
|
+
has(key: string): boolean;
|
|
26
|
+
/** Claves actuales. */
|
|
27
|
+
keys(): string[];
|
|
28
|
+
/** Pares [clave, valor] actuales. */
|
|
29
|
+
entries(): Array<[string, unknown]>;
|
|
30
|
+
/** Suscríbete a una clave concreta. Devuelve la función de desuscripción. */
|
|
31
|
+
subscribe<T = unknown>(key: string, cb: StoreSubscriber<T>): () => void;
|
|
32
|
+
/** Suscríbete a TODOS los cambios. Devuelve la función de desuscripción. */
|
|
33
|
+
subscribe(cb: StoreSubscriber): () => void;
|
|
34
|
+
/** Resuelve cuando se han escrito a IndexedDB todas las operaciones pendientes. */
|
|
35
|
+
flush(): Promise<void>;
|
|
36
|
+
}
|
|
37
|
+
export declare function createStore(options?: StoreOptions): Store;
|
|
38
|
+
/** Singleton por defecto (DB 'outfitkit', store 'kv'). Cómodo para uso global rápido. */
|
|
39
|
+
export declare const store: Store;
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
class StoreController {
|
|
2
|
+
constructor(host, store, key) {
|
|
3
|
+
this.host = host;
|
|
4
|
+
this.store = store;
|
|
5
|
+
this.key = key;
|
|
6
|
+
host.addController(this);
|
|
7
|
+
}
|
|
8
|
+
/** Valor actual de la clave observada (o `undefined` si el controller observa todo el store). */
|
|
9
|
+
get value() {
|
|
10
|
+
return this.key === void 0 ? void 0 : this.store.get(this.key);
|
|
11
|
+
}
|
|
12
|
+
/** Escribe en la clave observada. No-op si el controller no tiene clave. */
|
|
13
|
+
set(value) {
|
|
14
|
+
if (this.key !== void 0) this.store.set(this.key, value);
|
|
15
|
+
}
|
|
16
|
+
/** Actualiza la clave observada a partir del valor previo. No-op si no hay clave. */
|
|
17
|
+
update(fn) {
|
|
18
|
+
if (this.key !== void 0) this.store.update(this.key, fn);
|
|
19
|
+
}
|
|
20
|
+
hostConnected() {
|
|
21
|
+
const onChange = () => this.host.requestUpdate();
|
|
22
|
+
this.unsubscribe = this.key === void 0 ? this.store.subscribe(onChange) : this.store.subscribe(this.key, onChange);
|
|
23
|
+
}
|
|
24
|
+
hostDisconnected() {
|
|
25
|
+
this.unsubscribe?.();
|
|
26
|
+
this.unsubscribe = void 0;
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
export {
|
|
30
|
+
StoreController
|
|
31
|
+
};
|
package/dist/store.js
ADDED
|
@@ -0,0 +1,182 @@
|
|
|
1
|
+
const DEFAULT_DB = "outfitkit";
|
|
2
|
+
const DEFAULT_STORE = "kv";
|
|
3
|
+
function hasIndexedDB() {
|
|
4
|
+
return typeof indexedDB !== "undefined" && indexedDB !== null;
|
|
5
|
+
}
|
|
6
|
+
function noopAdapter() {
|
|
7
|
+
return {
|
|
8
|
+
getAll: () => Promise.resolve([]),
|
|
9
|
+
set: () => Promise.resolve(),
|
|
10
|
+
delete: () => Promise.resolve(),
|
|
11
|
+
clear: () => Promise.resolve()
|
|
12
|
+
};
|
|
13
|
+
}
|
|
14
|
+
function promisify(req) {
|
|
15
|
+
return new Promise((resolve, reject) => {
|
|
16
|
+
req.onsuccess = () => resolve(req.result);
|
|
17
|
+
req.onerror = () => reject(req.error);
|
|
18
|
+
});
|
|
19
|
+
}
|
|
20
|
+
function createIdb(dbName = DEFAULT_DB, storeName = DEFAULT_STORE) {
|
|
21
|
+
if (!hasIndexedDB()) return noopAdapter();
|
|
22
|
+
let dbPromise = null;
|
|
23
|
+
function openDb() {
|
|
24
|
+
if (dbPromise) return dbPromise;
|
|
25
|
+
dbPromise = new Promise((resolve, reject) => {
|
|
26
|
+
const req = indexedDB.open(dbName, 1);
|
|
27
|
+
req.onupgradeneeded = () => {
|
|
28
|
+
const db = req.result;
|
|
29
|
+
if (!db.objectStoreNames.contains(storeName)) {
|
|
30
|
+
db.createObjectStore(storeName);
|
|
31
|
+
}
|
|
32
|
+
};
|
|
33
|
+
req.onsuccess = () => resolve(req.result);
|
|
34
|
+
req.onerror = () => reject(req.error);
|
|
35
|
+
});
|
|
36
|
+
return dbPromise;
|
|
37
|
+
}
|
|
38
|
+
async function withStore(mode, fn, fallback) {
|
|
39
|
+
try {
|
|
40
|
+
const db = await openDb();
|
|
41
|
+
const tx = db.transaction(storeName, mode);
|
|
42
|
+
const store2 = tx.objectStore(storeName);
|
|
43
|
+
return await fn(store2);
|
|
44
|
+
} catch (err) {
|
|
45
|
+
console.warn("[outfitkit/store] IndexedDB falló, se ignora la operación:", err);
|
|
46
|
+
return fallback;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
return {
|
|
50
|
+
getAll() {
|
|
51
|
+
return withStore(
|
|
52
|
+
"readonly",
|
|
53
|
+
async (store2) => {
|
|
54
|
+
const keys = await promisify(store2.getAllKeys());
|
|
55
|
+
const values = await promisify(store2.getAll());
|
|
56
|
+
const out = [];
|
|
57
|
+
for (let i = 0; i < keys.length; i++) {
|
|
58
|
+
out.push([String(keys[i]), values[i]]);
|
|
59
|
+
}
|
|
60
|
+
return out;
|
|
61
|
+
},
|
|
62
|
+
[]
|
|
63
|
+
);
|
|
64
|
+
},
|
|
65
|
+
set(key, val) {
|
|
66
|
+
return withStore(
|
|
67
|
+
"readwrite",
|
|
68
|
+
async (store2) => {
|
|
69
|
+
await promisify(store2.put(val, key));
|
|
70
|
+
},
|
|
71
|
+
void 0
|
|
72
|
+
);
|
|
73
|
+
},
|
|
74
|
+
delete(key) {
|
|
75
|
+
return withStore(
|
|
76
|
+
"readwrite",
|
|
77
|
+
async (store2) => {
|
|
78
|
+
await promisify(store2.delete(key));
|
|
79
|
+
},
|
|
80
|
+
void 0
|
|
81
|
+
);
|
|
82
|
+
},
|
|
83
|
+
clear() {
|
|
84
|
+
return withStore(
|
|
85
|
+
"readwrite",
|
|
86
|
+
async (store2) => {
|
|
87
|
+
await promisify(store2.clear());
|
|
88
|
+
},
|
|
89
|
+
void 0
|
|
90
|
+
);
|
|
91
|
+
}
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
function createStore(options = {}) {
|
|
95
|
+
const idb = createIdb(options.name, options.storeName);
|
|
96
|
+
const cache = /* @__PURE__ */ new Map();
|
|
97
|
+
const keySubs = /* @__PURE__ */ new Map();
|
|
98
|
+
const allSubs = /* @__PURE__ */ new Set();
|
|
99
|
+
let pending = Promise.resolve();
|
|
100
|
+
function enqueue(op) {
|
|
101
|
+
pending = pending.then(op).catch(() => {
|
|
102
|
+
});
|
|
103
|
+
}
|
|
104
|
+
const ready = idb.getAll().then((rows) => {
|
|
105
|
+
for (const [key, value] of rows) {
|
|
106
|
+
if (!cache.has(key)) cache.set(key, value);
|
|
107
|
+
}
|
|
108
|
+
});
|
|
109
|
+
function notify(key, value) {
|
|
110
|
+
const subs = keySubs.get(key);
|
|
111
|
+
if (subs) for (const cb of [...subs]) cb(value, key);
|
|
112
|
+
for (const cb of [...allSubs]) cb(value, key);
|
|
113
|
+
}
|
|
114
|
+
const store2 = {
|
|
115
|
+
ready,
|
|
116
|
+
get(key) {
|
|
117
|
+
return cache.get(key);
|
|
118
|
+
},
|
|
119
|
+
set(key, value) {
|
|
120
|
+
cache.set(key, value);
|
|
121
|
+
notify(key, value);
|
|
122
|
+
enqueue(() => idb.set(key, value));
|
|
123
|
+
},
|
|
124
|
+
update(key, fn) {
|
|
125
|
+
const next = fn(cache.get(key));
|
|
126
|
+
store2.set(key, next);
|
|
127
|
+
},
|
|
128
|
+
delete(key) {
|
|
129
|
+
const existed = cache.delete(key);
|
|
130
|
+
if (existed) {
|
|
131
|
+
notify(key, void 0);
|
|
132
|
+
enqueue(() => idb.delete(key));
|
|
133
|
+
}
|
|
134
|
+
},
|
|
135
|
+
remove(key) {
|
|
136
|
+
store2.delete(key);
|
|
137
|
+
},
|
|
138
|
+
clear() {
|
|
139
|
+
const keys = [...cache.keys()];
|
|
140
|
+
cache.clear();
|
|
141
|
+
for (const key of keys) notify(key, void 0);
|
|
142
|
+
enqueue(() => idb.clear());
|
|
143
|
+
},
|
|
144
|
+
has(key) {
|
|
145
|
+
return cache.has(key);
|
|
146
|
+
},
|
|
147
|
+
keys() {
|
|
148
|
+
return [...cache.keys()];
|
|
149
|
+
},
|
|
150
|
+
entries() {
|
|
151
|
+
return [...cache.entries()];
|
|
152
|
+
},
|
|
153
|
+
subscribe(keyOrCb, maybeCb) {
|
|
154
|
+
if (typeof keyOrCb === "function") {
|
|
155
|
+
const cb2 = keyOrCb;
|
|
156
|
+
allSubs.add(cb2);
|
|
157
|
+
return () => allSubs.delete(cb2);
|
|
158
|
+
}
|
|
159
|
+
const key = keyOrCb;
|
|
160
|
+
const cb = maybeCb;
|
|
161
|
+
let subs = keySubs.get(key);
|
|
162
|
+
if (!subs) {
|
|
163
|
+
subs = /* @__PURE__ */ new Set();
|
|
164
|
+
keySubs.set(key, subs);
|
|
165
|
+
}
|
|
166
|
+
subs.add(cb);
|
|
167
|
+
return () => {
|
|
168
|
+
subs.delete(cb);
|
|
169
|
+
if (subs.size === 0) keySubs.delete(key);
|
|
170
|
+
};
|
|
171
|
+
},
|
|
172
|
+
flush() {
|
|
173
|
+
return pending;
|
|
174
|
+
}
|
|
175
|
+
};
|
|
176
|
+
return store2;
|
|
177
|
+
}
|
|
178
|
+
const store = createStore();
|
|
179
|
+
export {
|
|
180
|
+
createStore,
|
|
181
|
+
store
|
|
182
|
+
};
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
/* OutfitKit — tokens de tema (PLANTILLA). Cópialo a tu style.css y ajústalo.
|
|
2
|
+
*
|
|
3
|
+
* OutfitKit NO define valores por defecto: aquí decides de dónde salen. La opción más
|
|
4
|
+
* cómoda es heredarlos de Ionic (--ion-*), con lo que el tema claro/oscuro del shell se
|
|
5
|
+
* aplica solo. Si NO usas Ionic (p.ej. landing Django sin Ionic), pon valores propios.
|
|
6
|
+
*
|
|
7
|
+
* Cada token --ok-* tiene fallback interno a --ion-* y a un hex, así que puedes definir
|
|
8
|
+
* solo los que quieras cambiar; el resto degradan con sensatez. */
|
|
9
|
+
|
|
10
|
+
:root {
|
|
11
|
+
/* Heredar de Ionic (recomendado si hay Ionic cargado) */
|
|
12
|
+
--ok-primary: var(--ion-color-primary);
|
|
13
|
+
--ok-primary-contrast: var(--ion-color-primary-contrast);
|
|
14
|
+
--ok-bg: var(--ion-background-color);
|
|
15
|
+
--ok-surface: var(--ion-card-background);
|
|
16
|
+
--ok-text: var(--ion-text-color);
|
|
17
|
+
--ok-border: rgba(var(--ion-text-color-rgb), 0.12);
|
|
18
|
+
|
|
19
|
+
/* Geometría / tipografía */
|
|
20
|
+
--ok-radius: 12px;
|
|
21
|
+
--ok-spacing: 1rem;
|
|
22
|
+
--ok-container-max: 1140px;
|
|
23
|
+
--ok-font: system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
|
|
24
|
+
|
|
25
|
+
/* Micro-interacciones (hover suave en escritorio + feedback de pulsación, sutil) */
|
|
26
|
+
--ok-transition: 150ms ease; /* duración/easing de los estados hover/activo */
|
|
27
|
+
--ok-press-scale: 0.97; /* escala al pulsar (feedback breve, vale en táctil) */
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/* Ejemplo SIN Ionic (descomenta y pon tu marca):
|
|
31
|
+
:root {
|
|
32
|
+
--ok-primary: #1496d6;
|
|
33
|
+
--ok-primary-contrast: #ffffff;
|
|
34
|
+
--ok-bg: #ffffff;
|
|
35
|
+
--ok-surface: #ffffff;
|
|
36
|
+
--ok-text: #18181b;
|
|
37
|
+
--ok-border: rgba(24, 24, 27, 0.12);
|
|
38
|
+
}
|
|
39
|
+
:root.dark, :root[data-theme="dark"] {
|
|
40
|
+
--ok-bg: #09090b;
|
|
41
|
+
--ok-surface: #18181b;
|
|
42
|
+
--ok-text: #fafafa;
|
|
43
|
+
--ok-border: rgba(250, 250, 250, 0.14);
|
|
44
|
+
}
|
|
45
|
+
*/
|
|
46
|
+
|
|
47
|
+
/* ── Overlay estrecho estilo "menú web" ──────────────────────────────────────
|
|
48
|
+
* Los overlays de Ionic (ion-popover / ion-menu / ion-modal) son anchos por
|
|
49
|
+
* defecto. Aplica esta clase con su `css-class`/`cssClass` (o directamente al
|
|
50
|
+
* elemento) para que en ESCRITORIO tengan un ancho máximo acorde a un menú web;
|
|
51
|
+
* en MÓVIL se dejan al ancho nativo de Ionic.
|
|
52
|
+
* <ion-popover css-class="ok-overlay"> … | popover.cssClass = 'ok-overlay'
|
|
53
|
+
*/
|
|
54
|
+
.ok-overlay {
|
|
55
|
+
--width: auto;
|
|
56
|
+
--max-width: var(--ok-overlay-max, 380px);
|
|
57
|
+
/* También aplica a ion-modal / ion-select interface="modal" en ESCRITORIO:
|
|
58
|
+
* tamaño auto y acotado (menú web), no el modal a pantalla completa de Ionic. */
|
|
59
|
+
--height: auto;
|
|
60
|
+
--max-height: 80vh;
|
|
61
|
+
--border-radius: 14px;
|
|
62
|
+
}
|
|
63
|
+
@media (max-width: 768px) {
|
|
64
|
+
.ok-overlay {
|
|
65
|
+
/* En MÓVIL se deja al comportamiento nativo de Ionic (ancho completo). */
|
|
66
|
+
--width: 100%;
|
|
67
|
+
--max-width: 100%;
|
|
68
|
+
--max-height: 80vh;
|
|
69
|
+
}
|
|
70
|
+
}
|