@code-coaching/vuetiful 0.16.6 → 0.17.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.
Files changed (52) hide show
  1. package/README.md +2 -3
  2. package/dist/style.css +1 -1
  3. package/dist/styles/all.css +70 -2
  4. package/dist/types/components/index.d.ts +2 -2
  5. package/dist/types/components/molecules/VListbox/VListbox.test.d.ts +1 -0
  6. package/dist/types/components/molecules/VListbox/VListbox.vue.d.ts +100 -0
  7. package/dist/types/components/molecules/VListbox/VListboxButton.test.d.ts +1 -0
  8. package/dist/types/components/molecules/VListbox/VListboxButton.vue.d.ts +23 -0
  9. package/dist/types/components/molecules/VListbox/VListboxItem.test.d.ts +1 -0
  10. package/dist/types/components/molecules/VListbox/VListboxItem.vue.d.ts +12 -0
  11. package/dist/types/components/molecules/VListbox/VListboxItems.test.d.ts +1 -0
  12. package/dist/types/components/molecules/VListbox/VListboxItems.vue.d.ts +23 -0
  13. package/dist/types/components/molecules/VListbox/VListboxLabel.test.d.ts +1 -0
  14. package/dist/types/components/molecules/VListbox/VListboxLabel.vue.d.ts +14 -0
  15. package/dist/types/components/molecules/index.d.ts +6 -1
  16. package/dist/vuetiful.es.mjs +792 -185
  17. package/dist/vuetiful.umd.js +13 -13
  18. package/package.json +1 -1
  19. package/src/components/atoms/VAvatar.vue +7 -1
  20. package/src/components/atoms/VBadge.test.ts +1 -1
  21. package/src/components/atoms/VChip.test.ts +1 -1
  22. package/src/components/atoms/VCodeBlock.test.ts +2 -2
  23. package/src/components/atoms/VLightSwitch.test.ts +2 -2
  24. package/src/components/atoms/VRadio/VRadioDescription.vue +3 -3
  25. package/src/components/atoms/VRadio/VRadioGroup.test.ts +4 -4
  26. package/src/components/atoms/VRadio/VRadioItem.test.ts +14 -14
  27. package/src/components/atoms/VSwitch/VSwitch.test.ts +4 -27
  28. package/src/components/atoms/VSwitch/VSwitchDescription.test.ts +1 -2
  29. package/src/components/atoms/VSwitch/VSwitchDescription.vue +2 -2
  30. package/src/components/atoms/VSwitch/VSwitchGroup.test.ts +2 -2
  31. package/src/components/atoms/VSwitch/VSwitchGroup.vue +2 -2
  32. package/src/components/atoms/VSwitch/VSwitchLabel.test.ts +3 -3
  33. package/src/components/atoms/VSwitch/VSwitchLabel.vue +3 -3
  34. package/src/components/index.ts +2 -2
  35. package/src/components/molecules/VDrawer.test.ts +2 -2
  36. package/src/components/molecules/VDrawer.vue +1 -1
  37. package/src/components/molecules/VListbox/VListbox.test.ts +119 -0
  38. package/src/components/molecules/VListbox/VListbox.vue +119 -0
  39. package/src/components/molecules/VListbox/VListboxButton.test.ts +57 -0
  40. package/src/components/molecules/VListbox/VListboxButton.vue +48 -0
  41. package/src/components/molecules/VListbox/VListboxItem.test.ts +51 -0
  42. package/src/components/molecules/VListbox/VListboxItem.vue +29 -0
  43. package/src/components/molecules/VListbox/VListboxItems.test.ts +44 -0
  44. package/src/components/molecules/VListbox/VListboxItems.vue +31 -0
  45. package/src/components/molecules/VListbox/VListboxLabel.test.ts +31 -0
  46. package/src/components/molecules/VListbox/VListboxLabel.vue +14 -0
  47. package/src/components/molecules/VPreview.test.ts +2 -2
  48. package/src/components/molecules/VRail.test.ts +2 -2
  49. package/src/components/molecules/VRailTile.test.ts +2 -2
  50. package/src/components/molecules/VShell.test.ts +2 -2
  51. package/src/components/molecules/index.ts +17 -1
  52. package/src/styles/elements/buttons.css +1 -1
@@ -0,0 +1,48 @@
1
+ <script setup lang="ts">
2
+ import { ListboxButton } from "@headlessui/vue";
3
+
4
+ defineProps({
5
+ as: {
6
+ type: String,
7
+ default: "button",
8
+ },
9
+ hideIcon: {
10
+ type: Boolean,
11
+ default: false,
12
+ },
13
+ });
14
+ </script>
15
+
16
+ <template>
17
+ <ListboxButton
18
+ v-slot="{ open }"
19
+ :as="as"
20
+ class="variant-filled btn flex w-full justify-between active:scale-[100%]"
21
+ >
22
+ <slot />
23
+ <span v-if="!hideIcon">
24
+ <slot v-if="!open" name="open-icon">
25
+ <!-- https://fontawesome.com/icons/chevron-down?f=classic&s=solid -->
26
+ <svg class="icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
27
+ <path
28
+ d="M233.4 406.6c12.5 12.5 32.8 12.5 45.3 0l192-192c12.5-12.5 12.5-32.8 0-45.3s-32.8-12.5-45.3 0L256 338.7 86.6 169.4c-12.5-12.5-32.8-12.5-45.3 0s-12.5 32.8 0 45.3l192 192z"
29
+ />
30
+ </svg>
31
+ </slot>
32
+ <slot v-if="open" name="close-icon">
33
+ <!-- https://fontawesome.com/icons/chevron-up?f=classic&s=solid -->
34
+ <svg class="icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
35
+ <path
36
+ d="M233.4 105.4c12.5-12.5 32.8-12.5 45.3 0l192 192c12.5 12.5 12.5 32.8 0 45.3s-32.8 12.5-45.3 0L256 173.3 86.6 342.6c-12.5 12.5-32.8 12.5-45.3 0s-12.5-32.8 0-45.3l192-192z"
37
+ />
38
+ </svg>
39
+ </slot>
40
+ </span>
41
+ </ListboxButton>
42
+ </template>
43
+
44
+ <style scoped>
45
+ .icon {
46
+ @apply my-1 h-4 w-4 fill-current;
47
+ }
48
+ </style>
@@ -0,0 +1,51 @@
1
+ import { mount } from "@vue/test-utils";
2
+ import { describe, expect, test } from "vitest";
3
+ import { ref } from "vue";
4
+ import VListbox from "./VListbox.vue";
5
+ import VListboxItem from "./VListboxItem.vue";
6
+
7
+ describe("VListboxItem props", () => {
8
+ test("defaults", async () => {
9
+ const listboxValue = ref("John");
10
+ const wrapper = mount({
11
+ setup() {
12
+ return { listboxValue };
13
+ },
14
+ template: /* html */ `
15
+ <v-listbox v-model="listboxValue">
16
+ <v-listbox-item value="John">John Duck</v-listbox-item>
17
+ <v-listbox-item value="Jane">Jane Duck</v-listbox-item>
18
+ </v-listbox>
19
+ `,
20
+ components: {
21
+ "v-listbox": VListbox,
22
+ "v-listbox-item": VListboxItem,
23
+ },
24
+ });
25
+
26
+ const listbox = wrapper.find("[data-test='v-listbox']");
27
+ await listbox.find("button").trigger("click");
28
+
29
+ const listboxItems = listbox.findAll("[data-test='v-listbox-item']");
30
+ const selectedItem = listboxItems[0];
31
+ const normalItem = listboxItems[1];
32
+ expect(selectedItem.classes()).toEqual([
33
+ "vuetiful-listbox-item",
34
+ "px-4",
35
+ "py-1",
36
+ "text-base",
37
+ "rounded-token",
38
+ "variant-filled",
39
+ "cursor-pointer",
40
+ ]);
41
+ expect(normalItem.classes()).toEqual([
42
+ "vuetiful-listbox-item",
43
+ "px-4",
44
+ "py-1",
45
+ "text-base",
46
+ "rounded-token",
47
+ "hover:variant-ghost",
48
+ "cursor-pointer",
49
+ ]);
50
+ });
51
+ });
@@ -0,0 +1,29 @@
1
+ <script setup lang="ts">
2
+ import { ListboxOption } from "@headlessui/vue";
3
+ import { inject } from "vue";
4
+
5
+ defineProps({
6
+ value: {
7
+ type: [String, Number, Boolean, Object],
8
+ required: true,
9
+ },
10
+ });
11
+
12
+ const activeClass = inject("active") as string;
13
+ const hoverClass = inject("hover") as string;
14
+ </script>
15
+
16
+ <template>
17
+ <ListboxOption v-slot="{ selected, disabled, active }" :value="value">
18
+ <div
19
+ data-test="v-listbox-item"
20
+ :class="`vuetiful-listbox-item px-4 py-1 text-base rounded-token ${
21
+ selected ? activeClass : `hover:${hoverClass}`
22
+ } ${disabled ? 'cursor-not-allowed opacity-50' : 'cursor-pointer'} ${
23
+ active && !selected ? hoverClass : ''
24
+ }`"
25
+ >
26
+ <slot />
27
+ </div>
28
+ </ListboxOption>
29
+ </template>
@@ -0,0 +1,44 @@
1
+ import { mount } from "@vue/test-utils";
2
+ import { expect, test } from "vitest";
3
+ import VListbox from "./VListbox.vue";
4
+ import VListboxItem from "./VListboxItem.vue";
5
+
6
+ test("VListboxItems defaults", async () => {
7
+ const wrapper = mount({
8
+ template: /*html*/ `
9
+ <v-listbox>
10
+ <v-listbox-item value="John">John Duck</v-listbox-item>
11
+ </v-listbox>
12
+ `,
13
+ components: {
14
+ "v-listbox": VListbox,
15
+ "v-listbox-item": VListboxItem,
16
+ },
17
+ });
18
+
19
+ const listbox = wrapper.find("[data-test='v-listbox']");
20
+ await listbox.find("button").trigger("click");
21
+
22
+ const listboxItems = listbox.find("[data-test='listbox-items']");
23
+ expect(listboxItems.classes()).toContain("flex-col");
24
+ });
25
+
26
+ test("VListboxItems horizontal", async () => {
27
+ const wrapper = mount({
28
+ template: /*html*/ `
29
+ <v-listbox horizontal>
30
+ <v-listbox-item value="John">John Duck</v-listbox-item>
31
+ </v-listbox>
32
+ `,
33
+ components: {
34
+ "v-listbox": VListbox,
35
+ "v-listbox-item": VListboxItem,
36
+ },
37
+ });
38
+
39
+ const listbox = wrapper.find("[data-test='v-listbox']");
40
+ await listbox.find("button").trigger("click");
41
+
42
+ const listboxItems = listbox.find("[data-test='listbox-items']");
43
+ expect(listboxItems.classes()).not.toContain("flex-col");
44
+ });
@@ -0,0 +1,31 @@
1
+ <script setup lang="ts">
2
+ import { ListboxOptions } from "@headlessui/vue";
3
+ import { inject } from "vue";
4
+
5
+ defineProps({
6
+ as: {
7
+ type: String,
8
+ default: "ul",
9
+ },
10
+ static: {
11
+ type: Boolean,
12
+ default: false,
13
+ },
14
+ });
15
+
16
+ const background = inject("background") as string;
17
+ const text = inject("text") as string;
18
+ const horizontal = inject("horizontal") as boolean;
19
+ </script>
20
+
21
+ <template>
22
+ <ListboxOptions
23
+ :as="as"
24
+ :static="static"
25
+ :class="`p-4 border-token border-surface-400-500-token rounded-container-token ${background} ${text}`"
26
+ >
27
+ <div data-test="listbox-items" :class="`flex ${horizontal ? 'flex' : 'flex-col'} gap-1`">
28
+ <slot />
29
+ </div>
30
+ </ListboxOptions>
31
+ </template>
@@ -0,0 +1,31 @@
1
+ import { mount } from "@vue/test-utils";
2
+ import { expect, test } from "vitest";
3
+ import { ref } from "vue";
4
+ import VListbox from "./VListbox.vue";
5
+
6
+ test("VListboxLabel using slot", () => {
7
+ const wrapper = mount({
8
+ template: `
9
+ <v-listbox></v-listbox>
10
+ `,
11
+ components: {
12
+ "v-listbox": VListbox,
13
+ },
14
+ });
15
+
16
+ expect(wrapper.text()).toBe("Select an option");
17
+ });
18
+
19
+ test("VListboxLabel custom label", () => {
20
+ const wrapper = mount({
21
+ template: `
22
+ <v-listbox label-text="John Duck"></v-listbox>
23
+ `,
24
+ components: {
25
+ "v-listbox": VListbox,
26
+ },
27
+ });
28
+
29
+ const label = wrapper.find("label");
30
+ expect(label.text()).toBe("John Duck");
31
+ });
@@ -0,0 +1,14 @@
1
+ <script setup lang="ts">
2
+ import { ListboxLabel } from "@headlessui/vue";
3
+
4
+ defineProps({
5
+ as: {
6
+ type: String,
7
+ default: "label",
8
+ },
9
+ });
10
+ </script>
11
+
12
+ <template>
13
+ <ListboxLabel :as="as"><slot /></ListboxLabel>
14
+ </template>
@@ -69,5 +69,5 @@ describe("VPreview", () => {
69
69
  expect(after.classes()).toContain("mobile-screen");
70
70
  expect(after.classes()).not.toContain("w-full");
71
71
  });
72
- })
73
- });
72
+ });
73
+ });
@@ -6,9 +6,9 @@ test("VRail", () => {
6
6
  expect(VRail).toBeTruthy();
7
7
  });
8
8
 
9
- // TODO: add tests
9
+ // TODO: add tests
10
10
  test("VRail using slot", () => {
11
11
  const wrapper = mount(VRail);
12
12
 
13
13
  expect(wrapper).toBeTruthy();
14
- });
14
+ });
@@ -6,9 +6,9 @@ test("VRailTile", () => {
6
6
  expect(VRailTile).toBeTruthy();
7
7
  });
8
8
 
9
- // TODO: add tests
9
+ // TODO: add tests
10
10
  test("VRailTile using slot", () => {
11
11
  const wrapper = mount(VRailTile);
12
12
 
13
13
  expect(wrapper).toBeTruthy();
14
- });
14
+ });
@@ -6,9 +6,9 @@ test("VShell", () => {
6
6
  expect(VShell).toBeTruthy();
7
7
  });
8
8
 
9
- // TODO: add tests
9
+ // TODO: add tests
10
10
  test("VShell using slot", () => {
11
11
  const wrapper = mount(VShell);
12
12
 
13
13
  expect(wrapper).toBeTruthy();
14
- });
14
+ });
@@ -3,5 +3,21 @@ import VRail from "./VRail.vue";
3
3
  import VRailTile from "./VRailTile.vue";
4
4
  import VShell from "./VShell.vue";
5
5
  import VPreview from "./VPreview.vue";
6
+ import VListbox from "./VListbox/VListbox.vue";
7
+ import VListboxItem from "./VListbox/VListboxItem.vue";
8
+ import VListboxItems from "./VListbox/VListboxItems.vue";
9
+ import VListboxLabel from "./VListbox/VListboxLabel.vue";
10
+ import VListboxButton from "./VListbox/VListboxButton.vue";
6
11
 
7
- export { VRail, VRailTile, VShell, VDrawer, VPreview };
12
+ export {
13
+ VRail,
14
+ VRailTile,
15
+ VShell,
16
+ VDrawer,
17
+ VPreview,
18
+ VListbox,
19
+ VListboxItem,
20
+ VListboxItems,
21
+ VListboxLabel,
22
+ VListboxButton,
23
+ };
@@ -67,7 +67,7 @@
67
67
 
68
68
  /* File Input Button */
69
69
  input[type="file"]:not(.file-dropzone-input)::file-selector-button {
70
- @apply btn variant-filled btn-sm mr-2 border-0;
70
+ @apply variant-filled btn btn-sm mr-2 border-0;
71
71
  }
72
72
 
73
73
  /* === Button Groups === */