spicykatsu 0.0.43 → 0.0.52

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.
Files changed (62) hide show
  1. package/README.md +2 -0
  2. package/dist/lib/SpicyAccordion/SpicyAccordion.css +1 -0
  3. package/dist/lib/SpicyAccordion/SpicyAccordion.js +64 -0
  4. package/dist/lib/SpicyAlert/SpicyAlert.css +1 -0
  5. package/dist/lib/SpicyAlert/SpicyAlert.js +81 -0
  6. package/dist/lib/SpicyBtn/SpicyBtn.css +1 -0
  7. package/dist/lib/SpicyBtn/SpicyBtn.js +77 -0
  8. package/dist/lib/SpicyCarousel/SpicyCarousel.css +1 -0
  9. package/dist/lib/SpicyCarousel/SpicyCarousel.js +131 -0
  10. package/dist/lib/SpicyDivider/SpicyDivider.js +30 -0
  11. package/dist/lib/SpicyDropdown/SpicyDropdown.css +1 -0
  12. package/dist/lib/SpicyDropdown/SpicyDropdown.js +68 -0
  13. package/dist/lib/SpicyFileInput/SpicyFileInput.css +1 -0
  14. package/dist/lib/SpicyFileInput/SpicyFileInput.js +105 -0
  15. package/dist/lib/SpicyModal/SpicyModal.css +1 -0
  16. package/dist/lib/SpicyModal/SpicyModal.js +89 -0
  17. package/dist/lib/SpicyProgress/SpicyProgress.css +1 -0
  18. package/dist/lib/SpicyProgress/SpicyProgress.js +74 -0
  19. package/dist/lib/SpicySheet/SpicySheet.css +1 -0
  20. package/dist/lib/SpicySheet/SpicySheet.js +23 -0
  21. package/dist/lib/SpicySlider/SpicySlider.css +1 -0
  22. package/dist/lib/SpicySlider/SpicySlider.js +43 -0
  23. package/dist/lib/SpicyTabs/SpicyTabs.css +1 -0
  24. package/dist/lib/SpicyTabs/SpicyTabs.js +83 -0
  25. package/dist/lib/SpicyTextArea/SpicyTextArea.css +1 -0
  26. package/dist/lib/SpicyTextArea/SpicyTextArea.js +36 -0
  27. package/dist/lib/SpicyTextField/SpicyTextField.css +1 -0
  28. package/dist/lib/SpicyTextField/SpicyTextField.js +71 -0
  29. package/dist/lib/SpicyToggle/SpicyToggle.css +1 -0
  30. package/dist/lib/SpicyToggle/SpicyToggle.js +47 -0
  31. package/dist/lib/SpicyTooltip/SpicyTooltip.css +1 -0
  32. package/dist/lib/SpicyTooltip/SpicyTooltip.js +78 -0
  33. package/dist/lib/SpicyTree/SpicyTree.css +1 -0
  34. package/dist/lib/SpicyTree/SpicyTree.js +22 -0
  35. package/dist/lib/SpicyTreeNode/SpicyTreeNode.css +1 -0
  36. package/dist/lib/SpicyTreeNode/SpicyTreeNode.js +55 -0
  37. package/dist/lib/main/main.js +4 -0
  38. package/dist/lib/ripple/ripple.js +4 -0
  39. package/dist/spicykatsu.es.js +124 -971
  40. package/dist/spicykatsu.umd.js +1 -1
  41. package/dist/style.css +1 -1
  42. package/dist/types/components/SpicyAlert.vue.d.ts +2 -2
  43. package/dist/types/components/SpicyBtn.vue.d.ts +1 -6
  44. package/dist/types/components/SpicyCarousel.vue.d.ts +2 -0
  45. package/dist/types/components/SpicyDivider.vue.d.ts +8 -6
  46. package/dist/types/components/SpicyFileInput.vue.d.ts +43 -0
  47. package/dist/types/components/SpicyModal.vue.d.ts +5 -0
  48. package/dist/types/components/SpicyProgress.vue.d.ts +1 -1
  49. package/dist/types/components/SpicySheet.vue.d.ts +2 -0
  50. package/dist/types/components/SpicySlider.vue.d.ts +1 -1
  51. package/dist/types/components/SpicyTabs.vue.d.ts +7 -3
  52. package/dist/types/components/SpicyTextField.vue.d.ts +45 -0
  53. package/dist/types/components/SpicyToggle.vue.d.ts +1 -1
  54. package/dist/types/components/SpicyTree.vue.d.ts +11 -0
  55. package/dist/types/components/SpicyTreeNode.vue.d.ts +18 -0
  56. package/dist/types/directives/spicyDrag.d.ts +5 -1
  57. package/dist/types/index.d.ts +6 -10
  58. package/package.json +18 -9
  59. package/dist/types/components/SpicyLabel.vue.d.ts +0 -29
  60. package/dist/types/scripts/dateUtils.d.ts +0 -75
  61. package/dist/types/scripts/objUtils.d.ts +0 -8
  62. package/dist/types/components/{SpicyTextarea.vue.d.ts → SpicyTextArea.vue.d.ts} +1 -1
package/README.md CHANGED
@@ -2,4 +2,6 @@
2
2
 
3
3
  Fun, simple library for Vue3. Something for me to play around with in my projects.
4
4
 
5
+ Feel free to clone the repo and run the `dev` script. The playground has an example of every component and directive.
6
+
5
7
  Docs: [SpicyKatsu Docs](https://satoru8.gitlab.io/spicykatsuvlib/)
@@ -0,0 +1 @@
1
+ .spicyAccordion{border:1px solid #ddd;border-radius:4px;overflow:hidden}.spicyAccordionItem{border-bottom:1px solid #ddd}.spicyAccordionItem:last-child{border-bottom:none}.spicyAccordionHeader{background-color:#f5f5f5;border:none;padding:10px;text-align:left;width:100%;cursor:pointer;display:flex;justify-content:space-between;align-items:center;transition:background-color .2s ease}.spicyAccordionHeader.open{background-color:#e0e0e0}.spicyAccordionHeader.open .accordionArrow{transform:rotate(180deg)}.spicyAccordionContent{padding:10px;background-color:#fff}.accordionToggle{display:flex;align-items:center;transition:transform .2s ease}.accordionArrow{width:20px;height:20px;transition:transform .2s}.fade-enter-active,.fade-leave-active{transition:opacity .2s ease}.fade-enter,.fade-leave-to{opacity:0}
@@ -0,0 +1,64 @@
1
+ import { defineComponent as u, ref as v, openBlock as c, createElementBlock as i, Fragment as m, renderList as _, createElementVNode as o, normalizeClass as f, toDisplayString as g, createCommentVNode as h, createVNode as w, Transition as y, withCtx as C, withDirectives as k, renderSlot as A, vShow as O } from "vue";
2
+ const S = { class: "spicyAccordion" }, B = ["onClick", "aria-expanded"], I = {
3
+ key: 0,
4
+ class: "accordionIcon",
5
+ viewBox: "0 0 24 24",
6
+ xmlns: "http://www.w3.org/2000/svg"
7
+ }, N = ["d"], V = { class: "spicyAccordionContent" }, D = /* @__PURE__ */ u({
8
+ __name: "SpicyAccordion",
9
+ props: {
10
+ sections: {},
11
+ singleOpen: { type: Boolean, default: !1 },
12
+ defaultOpen: {}
13
+ },
14
+ setup(p) {
15
+ const r = p, s = v(r.defaultOpen || []), d = (e) => {
16
+ if (r.singleOpen)
17
+ s.value = s.value.includes(e) ? [] : [e];
18
+ else {
19
+ const t = s.value.indexOf(e);
20
+ t === -1 ? s.value.push(e) : s.value.splice(t, 1);
21
+ }
22
+ }, l = (e) => s.value.includes(e);
23
+ return (e, t) => (c(), i("div", S, [
24
+ (c(!0), i(m, null, _(e.sections, (a, n) => (c(), i("div", {
25
+ key: n,
26
+ class: "spicyAccordionItem"
27
+ }, [
28
+ o("button", {
29
+ class: f(["spicyAccordionHeader", { open: l(n) }]),
30
+ onClick: ($) => d(n),
31
+ "aria-expanded": l(n)
32
+ }, [
33
+ o("span", null, g(a.title), 1),
34
+ a.icon ? (c(), i("svg", I, [
35
+ o("path", {
36
+ d: a.icon
37
+ }, null, 8, N)
38
+ ])) : h("", !0),
39
+ t[0] || (t[0] = o("span", { class: "accordionToggle" }, [
40
+ o("svg", {
41
+ class: "accordionArrow",
42
+ viewBox: "0 0 24 24"
43
+ }, [
44
+ o("path", { d: "M7 10l5 5 5-5H7z" })
45
+ ])
46
+ ], -1))
47
+ ], 10, B),
48
+ w(y, { name: "fade" }, {
49
+ default: C(() => [
50
+ k(o("div", V, [
51
+ A(e.$slots, `section-${n}`)
52
+ ], 512), [
53
+ [O, l(n)]
54
+ ])
55
+ ]),
56
+ _: 2
57
+ }, 1024)
58
+ ]))), 128))
59
+ ]));
60
+ }
61
+ });
62
+ export {
63
+ D as _
64
+ };
@@ -0,0 +1 @@
1
+ .spicyAlert{display:flex;align-items:center;justify-content:center;gap:10px;padding:12px;border-radius:4px}.spicyAlert.info{background-color:#e0e0e0;color:#333}.spicyAlert.success{background-color:#bcf7c9;color:#155724}.spicyAlert.warning{background-color:#fff3cd;color:#856404}.spicyAlert.error{background-color:#ffbdc2;color:#911f2a}.spicyAlertIcon{width:24px;height:24px}.spicyAlertCloseBtn{margin-left:auto;background:none;border:none;cursor:pointer}.spicyAlertCloseBtn svg{width:16px;height:16px}.fade-enter-active,.fade-leave-active{transition:opacity .35s}.fade-enter,.fade-leave-to{opacity:0}
@@ -0,0 +1,81 @@
1
+ import { defineComponent as d, ref as p, watch as u, openBlock as t, createBlock as y, Transition as f, withCtx as m, createElementBlock as o, normalizeClass as h, withKeys as k, toDisplayString as n, createCommentVNode as l, createElementVNode as i, renderSlot as w } from "vue";
2
+ const v = ["aria-label"], _ = {
3
+ key: 0,
4
+ class: "spicyAlertIcon"
5
+ }, B = {
6
+ key: 1,
7
+ class: "spicyAlertIcon",
8
+ viewBox: "0 0 24 24",
9
+ xmlns: "http://www.w3.org/2000/svg"
10
+ }, C = ["d"], b = {
11
+ key: 2,
12
+ class: "spicyAlertText"
13
+ }, g = {
14
+ key: 0,
15
+ viewBox: "0 0 24 24",
16
+ xmlns: "http://www.w3.org/2000/svg"
17
+ }, A = ["d"], I = { key: 1 }, T = /* @__PURE__ */ d({
18
+ __name: "SpicyAlert",
19
+ props: {
20
+ variant: { default: "info" },
21
+ text: {},
22
+ icon: {},
23
+ mdi: {},
24
+ iconOnly: { type: Boolean, default: !1 },
25
+ closable: { type: Boolean, default: !1 },
26
+ autoClose: { default: 0 },
27
+ closeIcon: {}
28
+ },
29
+ setup(r) {
30
+ const c = r, a = p(!0), s = () => {
31
+ a.value = !1;
32
+ };
33
+ return u(
34
+ () => c.autoClose,
35
+ (e) => {
36
+ e && e > 0 && setTimeout(() => {
37
+ s();
38
+ }, e);
39
+ }
40
+ ), (e, O) => (t(), y(f, { name: "fade" }, {
41
+ default: m(() => [
42
+ a.value ? (t(), o("div", {
43
+ key: 0,
44
+ class: h(["spicyAlert", e.variant]),
45
+ "aria-atomic": "true",
46
+ "aria-label": e.text || "Alert",
47
+ role: "alert",
48
+ onKeydown: k(s, ["enter"])
49
+ }, [
50
+ e.iconOnly && e.icon ? (t(), o("span", _, n(e.icon), 1)) : l("", !0),
51
+ e.mdi ? (t(), o("svg", B, [
52
+ i("path", {
53
+ fill: "currentColor",
54
+ class: "spicyAlertMDI",
55
+ d: e.mdi
56
+ }, null, 8, C)
57
+ ])) : l("", !0),
58
+ !e.iconOnly && e.text ? (t(), o("span", b, n(e.text), 1)) : l("", !0),
59
+ e.closable ? (t(), o("button", {
60
+ key: 3,
61
+ class: "spicyAlertCloseBtn",
62
+ onClick: s,
63
+ "aria-label": "Close alert"
64
+ }, [
65
+ e.closeIcon ? (t(), o("svg", g, [
66
+ i("path", {
67
+ fill: "#000",
68
+ d: e.closeIcon
69
+ }, null, 8, A)
70
+ ])) : (t(), o("span", I, "X"))
71
+ ])) : l("", !0),
72
+ e.text ? l("", !0) : w(e.$slots, "default", { key: 4 })
73
+ ], 42, v)) : l("", !0)
74
+ ]),
75
+ _: 3
76
+ }));
77
+ }
78
+ });
79
+ export {
80
+ T as _
81
+ };
@@ -0,0 +1 @@
1
+ .spicyBtn{display:flex;align-items:center;justify-content:center;text-align:center;padding:8px 16px;gap:4px;border:none;border-radius:4px;cursor:pointer;color:var(--skTextColor, #ddd);background-color:var(--skBgColor, #28292a);font-size:var(--skFontSize, 16px);font-weight:var(--skFontWeight, 500);transition:background-color .25s}.spicyBtn.outlined{background-color:transparent;border:2px solid var(--skBorderColor, #515353)}.spicyBtn.disabled{opacity:.5;cursor:not-allowed}.spicyBtn:hover:not(.disabled){background-color:var(--hoverColor, grey)}.spicyBtn.isRound{border-radius:50px;padding:12px}.spicyBtn.large{padding:12px 24px;font-size:22px}.spicyBtn.large.isRound{padding:16px}.spicyBtn.large .spicyBtnIcon{width:40px}.spicyBtn .spicyBtnIcon{width:30px}
@@ -0,0 +1,77 @@
1
+ import { defineComponent as f, computed as s, resolveDirective as C, withDirectives as y, openBlock as t, createElementBlock as i, normalizeClass as h, normalizeStyle as v, createElementVNode as k, createCommentVNode as l, toDisplayString as n, renderSlot as g } from "vue";
2
+ const B = ["disabled", "aria-label", "aria-disabled", "tabindex"], S = {
3
+ key: 0,
4
+ class: "spicyBtnIcon",
5
+ viewBox: "0 0 24 24",
6
+ xmlns: "http://www.w3.org/2000/svg"
7
+ }, z = ["d"], _ = {
8
+ key: 1,
9
+ class: "spicyBtnIcon"
10
+ }, w = {
11
+ key: 2,
12
+ class: "spicyBtnText"
13
+ }, R = /* @__PURE__ */ f({
14
+ __name: "SpicyBtn",
15
+ props: {
16
+ variant: { default: "filled" },
17
+ disabled: { type: Boolean, default: !1 },
18
+ text: {},
19
+ icon: {},
20
+ mdi: {},
21
+ size: {},
22
+ bgColor: {},
23
+ textColor: { default: "#ddd" },
24
+ hoverColor: {},
25
+ borderColor: {},
26
+ fontSize: { default: 16 },
27
+ fontWeight: { default: 500 }
28
+ },
29
+ emits: ["click"],
30
+ setup(a, { emit: d }) {
31
+ const r = d, c = () => {
32
+ e.disabled || r("click");
33
+ }, e = a, p = s(() => ({
34
+ "--skFontSize": typeof e.fontSize == "number" ? `${e.fontSize}px` : e.fontSize,
35
+ "--skFontWeight": e.fontWeight,
36
+ "--skBgColor": e.bgColor,
37
+ "--skTextColor": e.textColor,
38
+ "--skBorderColor": e.borderColor,
39
+ "--hoverColor": e.hoverColor
40
+ })), u = s(() => !e.text && (e.icon || e.mdi)), b = s(() => ({
41
+ spicyBtn: !0,
42
+ outlined: e.variant === "outlined",
43
+ disabled: e.disabled,
44
+ isRound: u.value,
45
+ large: e.size === "large"
46
+ }));
47
+ return (o, x) => {
48
+ const m = C("spicyRipple");
49
+ return y((t(), i("button", {
50
+ class: h(b.value),
51
+ style: v(p.value),
52
+ disabled: o.disabled,
53
+ onClick: c,
54
+ role: "button",
55
+ "aria-label": o.text,
56
+ "aria-disabled": o.disabled,
57
+ tabindex: o.disabled ? -1 : 0
58
+ }, [
59
+ o.mdi ? (t(), i("svg", S, [
60
+ k("path", {
61
+ fill: "currentColor",
62
+ class: "spicyBtnMDI",
63
+ d: o.mdi
64
+ }, null, 8, z)
65
+ ])) : l("", !0),
66
+ o.icon && !o.mdi ? (t(), i("span", _, n(o.icon), 1)) : l("", !0),
67
+ o.text ? (t(), i("span", w, n(o.text), 1)) : l("", !0),
68
+ g(o.$slots, "default")
69
+ ], 14, B)), [
70
+ [m]
71
+ ]);
72
+ };
73
+ }
74
+ });
75
+ export {
76
+ R as _
77
+ };
@@ -0,0 +1 @@
1
+ .spicyCarouselWrapper{position:relative;width:var(--width, 580px);height:var(--height, 360px);padding:30px;display:flex;align-items:center;justify-content:center}.spicyCarouselWrapper .spicyCarouselTitle{position:absolute;top:0;width:var(--width, 580px);background-color:#0009;height:30px;color:#ccc;font-size:18px;font-weight:700}.spicyCarouselWrapper .spicyCarouselContainer{position:relative;overflow:hidden;width:100%;height:100%;border-radius:var(--borderRadius);background-color:#0009}.spicyCarouselWrapper .spicyCarouselSlide{position:absolute;top:0;left:0;width:100%;height:100%;background-size:cover;background-position:center;background-repeat:no-repeat;transition:opacity .3s ease}.spicyCarouselWrapper .spicyCarouselTextOverlay{position:absolute;bottom:10px;left:10px;background-color:#000000bf;padding:10px;color:#ccc;font-size:18px;font-weight:700;text-shadow:2px 2px 4px rgba(0,0,0,.5);border-radius:4px}.spicyCarouselWrapper .spicyCarouselTextOverlay.fullScreen{top:0;right:0;bottom:0;left:0;display:flex;align-items:center;justify-content:center;text-align:center;background-color:#0000004d}.spicyCarouselWrapper .spicyCarouselNavControls{position:absolute;top:0;left:0;width:100%;height:100%;display:flex;justify-content:space-between;align-items:center;pointer-events:none}.spicyCarouselWrapper .spicyCarouselNavControls .spicyCarouselPrevBtn,.spicyCarouselWrapper .spicyCarouselNavControls .spicyCarouselNextBtn{border:none;font-size:24px;color:#ccc;cursor:pointer;background:#0009;height:100%;width:30px;display:flex;align-items:center;justify-content:center;transition:transform .3s;pointer-events:auto;z-index:2}.spicyCarouselWrapper .spicyCarouselNavControls .spicyCarouselPrevBtn:hover,.spicyCarouselWrapper .spicyCarouselNavControls .spicyCarouselNextBtn:hover{background:var(--skPrimaryColor)}.spicyCarouselWrapper .spicyCarouselNavControls .spicyCarouselPrevBtn{border-radius:6px 0 0 6px}.spicyCarouselWrapper .spicyCarouselNavControls .spicyCarouselNextBtn{border-radius:0 6px 6px 0}.spicyCarouselWrapper .spicyCarouselPagination{position:absolute;background:#0009;bottom:0;left:50%;height:30px;width:var(--width, 580px);transform:translate(-50%);display:flex;gap:8px;z-index:2;align-items:center;justify-content:center;pointer-events:auto}.spicyCarouselWrapper .spicyCarouselPagination .spicyCarouselPageBtn{border:none;color:#fff;cursor:pointer;background:#00b7ff80;height:26px;width:26px;border-radius:50%;display:flex;align-items:center;justify-content:center;transition:transform .3s}.spicyCarouselWrapper .spicyCarouselPagination .spicyCarouselPageBtn.active{background:var(--activeColor, var(--skPrimaryColor))}.spicyCarouselWrapper .spicyCarouselPagination .spicyCarouselPageBtn:hover{background:var(--skPrimaryColor)}.spicyCarouselWrapper .pointCursor{cursor:pointer}.spicyCarouselWrapper .slide-enter-active,.spicyCarouselWrapper .slide-leave-active{transition:opacity .3s}.spicyCarouselWrapper .slide-enter,.spicyCarouselWrapper .slide-leave-to{opacity:0}
@@ -0,0 +1,131 @@
1
+ import { defineComponent as X, computed as u, ref as Y, onMounted as A, onUnmounted as V, openBlock as o, createElementBlock as n, normalizeStyle as _, createElementVNode as i, createVNode as $, Transition as z, withCtx as E, normalizeClass as y, toDisplayString as h, createCommentVNode as d, renderSlot as D, Fragment as F, renderList as O } from "vue";
2
+ const U = ["aria-label"], W = { class: "spicyCarouselInfoText" }, j = { class: "spicyCarouselTitle" }, q = { key: 0 }, G = {
3
+ key: 0,
4
+ class: "spicyCarouselNavControls"
5
+ }, H = {
6
+ key: 1,
7
+ class: "spicyCarouselPagination"
8
+ }, J = ["onClick"], K = { class: "spicyCarouselPage" }, Z = /* @__PURE__ */ X({
9
+ __name: "SpicyCarousel",
10
+ props: {
11
+ autoplay: { type: Boolean, default: !1 },
12
+ autoplaySpeed: { default: 5e3 },
13
+ showNavigation: { type: Boolean, default: !0 },
14
+ showPagination: { type: Boolean, default: !0 },
15
+ activeColor: { default: "var(--skPrimaryColor)" },
16
+ loop: { type: Boolean, default: !0 },
17
+ initialSlide: { default: 0 },
18
+ slides: { default: () => [] },
19
+ width: { default: "580px" },
20
+ height: { default: "360px" },
21
+ fullScreen: { type: Boolean, default: !1 },
22
+ enableImageClick: { type: Boolean, default: !1 },
23
+ paginationLimit: { default: 10 }
24
+ },
25
+ setup(w) {
26
+ let f, C, r = !1;
27
+ const t = w, B = u(() => ({
28
+ "--width": t.width,
29
+ "--height": t.height,
30
+ "--activeColor": t.activeColor
31
+ })), m = u(() => t.paginationLimit), I = u(() => {
32
+ var e;
33
+ return (e = t.slides[l.value]) == null ? void 0 : e.title;
34
+ }), b = u(() => c.value.fullScreen === !1 ? !1 : t.fullScreen), l = Y(t.initialSlide), c = u(() => t.slides[l.value]);
35
+ let p;
36
+ const g = () => {
37
+ l.value = (l.value - 1 + t.slides.length) % t.slides.length;
38
+ }, v = () => {
39
+ l.value = (l.value + 1) % t.slides.length;
40
+ }, T = (e) => {
41
+ l.value = e;
42
+ }, S = () => {
43
+ p && clearInterval(p);
44
+ }, k = () => {
45
+ t.autoplay && (p = window.setInterval(v, t.autoplaySpeed));
46
+ }, M = () => {
47
+ window.open(c.value.img);
48
+ }, P = () => {
49
+ t.enableImageClick && M();
50
+ }, N = (e) => {
51
+ f = e.touches[0].clientX, C = e.touches[0].clientY, r = !1;
52
+ }, x = (e) => {
53
+ if (!r) {
54
+ const a = e.touches[0].clientX - f, s = e.touches[0].clientY - C;
55
+ Math.abs(a) > Math.abs(s) && (a > 40 ? (g(), r = !0) : a < -40 && (v(), r = !0));
56
+ }
57
+ }, L = u(() => {
58
+ const e = t.slides.length, a = Math.max(0, l.value - Math.floor(m.value / 2)), s = Math.min(e, a + m.value);
59
+ return [...Array(e).keys()].slice(a, s);
60
+ });
61
+ return A(() => {
62
+ k();
63
+ }), V(() => {
64
+ S();
65
+ }), (e, a) => (o(), n("div", {
66
+ class: "spicyCarouselWrapper",
67
+ style: _({ ...B.value })
68
+ }, [
69
+ i("div", {
70
+ class: "spicyCarouselContainer",
71
+ onMouseenter: S,
72
+ onMouseleave: k,
73
+ onTouchstart: N,
74
+ onTouchmove: x
75
+ }, [
76
+ $(z, {
77
+ name: "slide",
78
+ mode: "out-in"
79
+ }, {
80
+ default: E(() => [
81
+ (o(), n("div", {
82
+ class: y(["spicyCarouselSlide", { pointCursor: t.enableImageClick }]),
83
+ key: l.value,
84
+ style: _({ backgroundImage: `url(${c.value.img})` }),
85
+ onClick: P
86
+ }, [
87
+ e.slides[l.value].text ? (o(), n("div", {
88
+ key: 0,
89
+ class: y(["spicyCarouselTextOverlay", { fullScreen: b.value }]),
90
+ "aria-label": e.slides[l.value].text
91
+ }, [
92
+ i("span", W, h(e.slides[l.value].text), 1)
93
+ ], 10, U)) : d("", !0),
94
+ D(e.$slots, "default")
95
+ ], 6))
96
+ ]),
97
+ _: 3
98
+ })
99
+ ], 32),
100
+ i("div", j, [
101
+ I.value ? (o(), n("h2", q, h(c.value.title), 1)) : d("", !0)
102
+ ]),
103
+ e.showNavigation ? (o(), n("div", G, [
104
+ i("button", {
105
+ class: "spicyCarouselPrevBtn",
106
+ onClick: g
107
+ }, a[0] || (a[0] = [
108
+ i("span", { class: "spicyCarouselPrevBtnIcon" }, "<", -1)
109
+ ])),
110
+ i("button", {
111
+ class: "spicyCarouselNextBtn",
112
+ onClick: v
113
+ }, a[1] || (a[1] = [
114
+ i("span", { class: "spicyCarouselNextBtnIcon" }, ">", -1)
115
+ ]))
116
+ ])) : d("", !0),
117
+ e.showPagination ? (o(), n("div", H, [
118
+ (o(!0), n(F, null, O(L.value, (s) => (o(), n("button", {
119
+ key: s,
120
+ onClick: (Q) => T(s),
121
+ class: y(["spicyCarouselPageBtn", { active: s === l.value }])
122
+ }, [
123
+ i("span", K, h(s + 1), 1)
124
+ ], 10, J))), 128))
125
+ ])) : d("", !0)
126
+ ], 4));
127
+ }
128
+ });
129
+ export {
130
+ Z as _
131
+ };
@@ -0,0 +1,30 @@
1
+ import { defineComponent as a, computed as t, openBlock as l, createElementBlock as s, normalizeClass as c, normalizeStyle as d, renderSlot as p } from "vue";
2
+ const v = ["aria-orientation"], h = /* @__PURE__ */ a({
3
+ __name: "SpicyDivider",
4
+ props: {
5
+ variant: { default: "solid" },
6
+ orientation: { default: "horizontal" },
7
+ length: { default: "100%" },
8
+ size: { default: "1px" },
9
+ color: { default: "#5f5f5f" }
10
+ },
11
+ setup(r) {
12
+ const e = r, i = t(() => e.orientation === "vertical" ? "vertical" : "horizontal"), n = t(() => ({
13
+ [e.orientation === "vertical" ? "height" : "width"]: e.length,
14
+ border: `${e.size} ${e.variant} ${e.color}`,
15
+ borderLeft: e.orientation === "vertical" ? `${e.size} ${e.variant} ${e.color}` : "none",
16
+ borderBottom: e.orientation === "horizontal" ? `${e.size} ${e.variant} ${e.color}` : "none"
17
+ }));
18
+ return (o, f) => (l(), s("div", {
19
+ class: c(["spicyDivider", i.value]),
20
+ style: d(n.value),
21
+ role: "separator",
22
+ "aria-orientation": o.orientation
23
+ }, [
24
+ p(o.$slots, "default")
25
+ ], 14, v));
26
+ }
27
+ });
28
+ export {
29
+ h as _
30
+ };
@@ -0,0 +1 @@
1
+ .spicyDropdown{position:relative;display:inline-block}.spicyDropdownButton{background-color:var(--skBgColor);color:#fff;padding:10px 16px;border:none;cursor:pointer;font-size:16px;display:flex;align-items:center}.spicyDropdownButton .arrow{margin-left:8px;transition:transform .3s ease}.spicyDropdownButton .arrow.open{transform:rotate(180deg)}.dropdownIcon{margin-right:8px}.spicyDropdownMenu{position:absolute;top:100%;background-color:#fff;box-shadow:0 4px 8px #0000001a;z-index:1;padding:10px;border-radius:4px}.fade-enter-active,.fade-leave-active{transition:opacity .3s ease}.fade-enter,.fade-leave-to{opacity:0}
@@ -0,0 +1,68 @@
1
+ import { defineComponent as w, ref as v, computed as r, openBlock as i, createElementBlock as l, normalizeClass as p, createElementVNode as s, createCommentVNode as d, createTextVNode as f, toDisplayString as g, createVNode as m, Transition as y, withCtx as S, normalizeStyle as z, withModifiers as D, renderSlot as k } from "vue";
2
+ const C = ["aria-expanded"], _ = ["width", "height"], x = ["d"], B = ["width", "height"], V = /* @__PURE__ */ w({
3
+ __name: "SpicyDropdown",
4
+ props: {
5
+ label: {},
6
+ align: { default: "left" },
7
+ width: { default: "200px" },
8
+ icon: { default: "" },
9
+ iconSize: { default: "24px" }
10
+ },
11
+ setup(u) {
12
+ const t = u, e = v(!1), c = () => {
13
+ e.value = !e.value;
14
+ }, a = r(() => t.icon || ""), h = r(() => ({
15
+ width: t.width,
16
+ [t.align === "right" ? "right" : "left"]: 0,
17
+ textAlign: t.align
18
+ }));
19
+ return (o, n) => (i(), l("div", {
20
+ class: p(["spicyDropdown", { open: e.value }])
21
+ }, [
22
+ s("button", {
23
+ onClick: c,
24
+ class: "spicyDropdownButton",
25
+ "aria-haspopup": "true",
26
+ "aria-expanded": e.value,
27
+ "aria-controls": "spicyDropdownMenu"
28
+ }, [
29
+ a.value ? (i(), l("svg", {
30
+ key: 0,
31
+ width: o.iconSize,
32
+ height: o.iconSize,
33
+ viewBox: "0 0 24 24",
34
+ class: "dropdownIcon"
35
+ }, [
36
+ s("path", { d: a.value }, null, 8, x)
37
+ ], 8, _)) : d("", !0),
38
+ f(" " + g(o.label) + " ", 1),
39
+ a.value ? d("", !0) : (i(), l("svg", {
40
+ key: 1,
41
+ width: o.iconSize,
42
+ height: o.iconSize,
43
+ viewBox: "0 0 24 24",
44
+ class: p(["arrow", { open: e.value }])
45
+ }, n[1] || (n[1] = [
46
+ s("path", { d: "M7 10l5 5 5-5H7z" }, null, -1)
47
+ ]), 10, B))
48
+ ], 8, C),
49
+ m(y, { name: "fade" }, {
50
+ default: S(() => [
51
+ e.value ? (i(), l("div", {
52
+ key: 0,
53
+ class: "spicyDropdownMenu",
54
+ style: z(h.value),
55
+ onClick: n[0] || (n[0] = D((M) => e.value = !1, ["self"])),
56
+ id: "spicyDropdownMenu"
57
+ }, [
58
+ k(o.$slots, "default")
59
+ ], 4)) : d("", !0)
60
+ ]),
61
+ _: 3
62
+ })
63
+ ], 2));
64
+ }
65
+ });
66
+ export {
67
+ V as _
68
+ };
@@ -0,0 +1 @@
1
+ .spicyFileInputWrapper{display:flex;flex-direction:column;position:relative;border:2px dashed var(--skBorderColor, #515353);padding:16px;border-radius:8px;width:250px;cursor:pointer}.spicyFileInputWrapper.isDragging{background-color:#0000000d;border-color:var(--skPrimaryColor)}.spicyFileInputLabel{font-size:16px;color:var(--textColor, var(--skTextColor));-webkit-user-select:none;user-select:none;cursor:pointer}.spicyFileInput{display:none}.spicyFilePreview{display:flex;flex-direction:column;gap:4px}.spicyFilePreviewItem{display:flex;justify-content:space-between;align-items:center;padding:8px;border:1px solid var(--skBorderColor, #515353);border-radius:4px;font-size:14px;position:relative;max-width:100%}.spicyFilePreviewItem span{overflow:hidden;white-space:nowrap;text-overflow:ellipsis;max-width:90%}.removeButton{background:none;border:none;cursor:pointer;color:red;position:absolute;right:8px;top:50%;transform:translateY(-50%)}.removeButtonMDI{width:24px;height:24px}.clearAllButton{background:none;border:none;font-size:16px;margin-top:8px;cursor:pointer;color:var(--skPrimaryColor)}.spicyFileInputError{color:red;font-size:12px;margin-top:8px}
@@ -0,0 +1,105 @@
1
+ import { defineComponent as B, ref as f, openBlock as a, createElementBlock as t, normalizeClass as _, withModifiers as i, toDisplayString as g, createCommentVNode as u, createElementVNode as h, Fragment as A, renderList as E, renderSlot as L } from "vue";
2
+ const S = ["aria-label"], T = ["multiple", "accept"], W = {
3
+ key: 1,
4
+ class: "spicyFilePreview"
5
+ }, $ = ["onClick"], M = ["onClick"], N = ["d"], P = {
6
+ key: 3,
7
+ class: "spicyFileInputError"
8
+ }, O = /* @__PURE__ */ B({
9
+ __name: "SpicyFileInput",
10
+ props: {
11
+ modelValue: { default: () => [] },
12
+ label: { default: "" },
13
+ error: { default: "" },
14
+ accept: { default: "" },
15
+ multiple: { type: Boolean, default: !1 },
16
+ clearable: { type: Boolean, default: !1 },
17
+ mdi: { default: "" }
18
+ },
19
+ emits: ["update:modelValue", "change", "error"],
20
+ setup(b, { emit: k }) {
21
+ const n = k, p = b, l = f(p.modelValue), s = f(null), d = f(!1), C = (e) => {
22
+ const o = e.target;
23
+ o.files && (l.value = Array.from(o.files), n("update:modelValue", l.value), n("change", l.value));
24
+ }, F = () => {
25
+ l.value = [], n("update:modelValue", l.value), s.value && (s.value.value = "");
26
+ }, y = (e) => {
27
+ l.value.splice(e, 1), n("update:modelValue", l.value), l.value.length === 0 && s.value && (s.value.value = "");
28
+ }, D = () => {
29
+ var e;
30
+ (e = s.value) == null || e.click();
31
+ }, I = () => {
32
+ d.value = !0;
33
+ }, V = () => {
34
+ d.value = !1;
35
+ }, w = (e) => {
36
+ var v;
37
+ const o = (v = e.dataTransfer) == null ? void 0 : v.files;
38
+ if (o) {
39
+ const r = Array.from(o).filter((m) => p.accept ? p.accept.split(",").map((c) => c.trim()).some((c) => c.startsWith(".") ? m.name.endsWith(c) : m.type === c) : !0);
40
+ !p.multiple && r.length > 0 ? l.value = [r[0]] : l.value = r, n("update:modelValue", l.value), n("change", l.value);
41
+ }
42
+ d.value = !1;
43
+ };
44
+ return (e, o) => (a(), t("div", {
45
+ class: _(["spicyFileInputWrapper", { hasError: e.error, isDragging: d.value }]),
46
+ onClick: D,
47
+ onDragover: i(I, ["prevent"]),
48
+ onDragleave: i(V, ["prevent"]),
49
+ onDrop: i(w, ["prevent"])
50
+ }, [
51
+ e.label && !l.value.length ? (a(), t("label", {
52
+ key: 0,
53
+ class: "spicyFileInputLabel",
54
+ "aria-label": e.label
55
+ }, g(e.label), 9, S)) : u("", !0),
56
+ h("input", {
57
+ type: "file",
58
+ multiple: e.multiple,
59
+ accept: e.accept,
60
+ class: "spicyFileInput",
61
+ onChange: C,
62
+ ref_key: "fileInput",
63
+ ref: s
64
+ }, null, 40, T),
65
+ l.value.length ? (a(), t("div", W, [
66
+ (a(!0), t(A, null, E(l.value, (v, r) => (a(), t("div", {
67
+ key: r,
68
+ class: "spicyFilePreviewItem"
69
+ }, [
70
+ h("span", null, g(v.name), 1),
71
+ e.clearable && !e.mdi ? (a(), t("button", {
72
+ key: 0,
73
+ class: "removeButton",
74
+ onClick: i((m) => y(r), ["stop"]),
75
+ "aria-label": "Remove"
76
+ }, " X ", 8, $)) : u("", !0),
77
+ e.clearable && e.mdi ? (a(), t("svg", {
78
+ key: 1,
79
+ class: "removeButtonMDI",
80
+ onClick: i((m) => y(r), ["stop"]),
81
+ "aria-label": "Remove",
82
+ viewBox: "0 0 24 24",
83
+ xmlns: "http://www.w3.org/2000/svg"
84
+ }, [
85
+ h("path", {
86
+ fill: "red",
87
+ d: e.mdi
88
+ }, null, 8, N)
89
+ ], 8, M)) : u("", !0)
90
+ ]))), 128))
91
+ ])) : u("", !0),
92
+ e.clearable && l.value.length > 1 ? (a(), t("button", {
93
+ key: 2,
94
+ class: "clearAllButton",
95
+ onClick: i(F, ["stop"]),
96
+ "aria-label": "Clear All"
97
+ }, " Clear All ")) : u("", !0),
98
+ L(e.$slots, "default"),
99
+ e.error ? (a(), t("span", P, g(e.error), 1)) : u("", !0)
100
+ ], 34));
101
+ }
102
+ });
103
+ export {
104
+ O as _
105
+ };
@@ -0,0 +1 @@
1
+ .spicyModalOverlay{position:fixed;top:0;left:0;right:0;bottom:0;background-color:#0009;display:flex;justify-content:center;align-items:center;z-index:1000}.spicyModal{padding:20px;box-shadow:0 0 6px 2px #0003;transition:transform .3s ease-out;font-size:15px;border-radius:var(--skBorderRadius);background-color:var(--skBgColor);z-index:1001}.spicyModalHeader{text-align:center;font-size:20px;font-weight:700}.spicyModalActions{margin-top:20px;text-align:right}.spicyModalActionBtn{background-color:transparent;border:none;color:var(--skTextColor, #ddd);cursor:pointer}.spicyModalActionBtn:hover{text-decoration:underline}