@brumaombra/ui-vintage 0.7.4 → 0.7.7

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@brumaombra/ui-vintage",
3
- "version": "0.7.4",
3
+ "version": "0.7.7",
4
4
  "description": "Source-published Nuxt UI runtime with shared theme tokens and built-in Nuxt integrations.",
5
5
  "private": false,
6
6
  "author": "Mauro Brambilla",
@@ -37,6 +37,7 @@
37
37
  "./style.css": "./src/styles.css",
38
38
  "./alert": "./src/components/ui/alert/index.ts",
39
39
  "./alert-dialog": "./src/components/ui/alert-dialog/index.ts",
40
+ "./accordion": "./src/components/ui/accordion/index.ts",
40
41
  "./background-grid": "./src/components/background-grid/index.ts",
41
42
  "./badge": "./src/components/ui/badge/index.ts",
42
43
  "./blog": "./src/components/blog/index.ts",
@@ -120,7 +121,7 @@
120
121
  "clsx": "2.1.1",
121
122
  "reka-ui": "2.9.2",
122
123
  "tailwind-merge": "3.5.0",
123
- "tailwindcss": "4.2.2",
124
+ "tailwindcss": "4.2.4",
124
125
  "tw-animate-css": "1.4.0"
125
126
  },
126
127
  "devDependencies": {
@@ -1,9 +1,7 @@
1
1
  <script setup>
2
- import { ref, computed } from 'vue';
2
+ import { computed } from 'vue';
3
3
  import { useI18n } from 'vue-i18n';
4
- import { ArrowDown01Icon } from '@hugeicons/core-free-icons';
5
- import { HugeiconsIcon } from '@hugeicons/vue';
6
- import { Card, CardContent } from '../ui/card';
4
+ import { Accordion } from '@brumaombra/ui-vintage/accordion';
7
5
  import BlogSectionTitle from './BlogSectionTitle.vue';
8
6
 
9
7
  // Props
@@ -12,23 +10,7 @@ const props = defineProps({
12
10
  });
13
11
 
14
12
  const { t } = useI18n();
15
- const expandedItems = ref({});
16
13
  const hasValidFAQs = computed(() => props.faqs && props.faqs.length > 0);
17
-
18
- // Toggle expanded state
19
- const toggleItem = index => {
20
- expandedItems.value[index] = !expandedItems.value[index];
21
- };
22
-
23
- // Check if item is expanded
24
- const isExpanded = index => {
25
- return expandedItems.value[index] || false;
26
- };
27
-
28
- // Auto-open first FAQ for better UX
29
- if (hasValidFAQs.value) {
30
- expandedItems.value[0] = true;
31
- }
32
14
  </script>
33
15
 
34
16
  <template>
@@ -37,35 +19,17 @@ if (hasValidFAQs.value) {
37
19
  <BlogSectionTitle :title="t('uiVintage.blog.faq.title')" />
38
20
 
39
21
  <!-- Description -->
40
- <p class="text-base md:text-lg text-[var(--text-secondary-light)] dark:text-[var(--text-secondary-dark)] mb-8">
22
+ <p class="text-base md:text-lg text-(--text-secondary-light) dark:text-(--text-secondary-dark) mb-8">
41
23
  {{ t('uiVintage.blog.faq.description') }}
42
24
  </p>
43
25
 
44
26
  <!-- FAQ Items -->
45
27
  <div class="space-y-4">
46
- <Card v-for="(faq, index) in props.faqs" :key="index" class="!p-0 cursor-pointer" @click="toggleItem(index)">
47
- <CardContent class="!p-0 gap-0">
48
- <!-- Question -->
49
- <div class="flex items-center justify-between p-5 gap-4">
50
- <!-- Question text -->
51
- <h3 class="text-sm md:!text-base font-semibold text-[var(--text-primary-light)] dark:text-[var(--text-primary-dark)] text-left">
52
- {{ faq.question }}
53
- </h3>
54
-
55
- <!-- Toggle icon -->
56
- <div class="flex-shrink-0 w-8 h-8 flex items-center justify-center rounded bg-[var(--bg-card-light)] dark:bg-[var(--bg-card-dark)] border border-[var(--border-light)] dark:border-[var(--border-dark)] transition-transform duration-300" :class="{ 'rotate-180': isExpanded(index) }">
57
- <HugeiconsIcon :icon="ArrowDown01Icon" class="size-4 text-[var(--text-secondary-light)] dark:text-[var(--text-secondary-dark)]" />
58
- </div>
59
- </div>
60
-
61
- <!-- Answer -->
62
- <div class="overflow-hidden transition-all duration-300 ease-in-out" :class="isExpanded(index) ? 'max-h-96 opacity-100' : 'max-h-0 opacity-0'">
63
- <p class="px-5 pb-5 text-xs md:text-sm text-[var(--text-secondary-light)] dark:text-[var(--text-secondary-dark)] leading-relaxed">
64
- {{ faq.answer }}
65
- </p>
66
- </div>
67
- </CardContent>
68
- </Card>
28
+ <Accordion v-for="(faq, index) in props.faqs" :key="index" :title="faq.question" :initially-expanded="index === 0">
29
+ <p class="text-xs md:text-sm text-(--text-secondary-light) dark:text-(--text-secondary-dark) leading-relaxed">
30
+ {{ faq.answer }}
31
+ </p>
32
+ </Accordion>
69
33
  </div>
70
34
  </div>
71
35
  </template>
@@ -1,9 +1,8 @@
1
1
  <script setup>
2
- import { computed, ref } from 'vue';
2
+ import { computed } from 'vue';
3
3
  import { useI18n } from 'vue-i18n';
4
- import { ArrowDown01Icon, Bookmark01Icon } from '@hugeicons/core-free-icons';
5
- import { HugeiconsIcon } from '@hugeicons/vue';
6
- import { Card, CardContent } from '../ui/card';
4
+ import { Bookmark01Icon } from '@hugeicons/core-free-icons';
5
+ import { Accordion } from '../ui/accordion';
7
6
 
8
7
  // Props
9
8
  const props = defineProps({
@@ -11,8 +10,6 @@ const props = defineProps({
11
10
  });
12
11
 
13
12
  const { t } = useI18n();
14
- const isExpanded = ref(false);
15
- const contentBodyRef = ref(null);
16
13
 
17
14
  // Create the headings list
18
15
  const headings = computed(() => {
@@ -50,27 +47,17 @@ const scrollToHeading = id => {
50
47
  }
51
48
  };
52
49
 
53
- // Toggle expanded state
54
- const toggleExpanded = () => {
55
- isExpanded.value = !isExpanded.value;
56
- };
57
-
58
- // Get the current content height for the expand/collapse animation
59
- const contentHeight = computed(() => {
60
- return contentBodyRef.value?.scrollHeight ?? 0;
61
- });
62
-
63
50
  // Get classes for heading button
64
51
  const getHeadingButtonClasses = heading => {
65
52
  // Base classes for all titles
66
- const baseClasses = 'block w-full text-left px-0 py-2 md:px-3 md:py-2 rounded transition-all duration-200 hover:bg-[var(--bg-selected-light)] dark:hover:bg-[var(--bg-selected-dark)] cursor-pointer';
53
+ const baseClasses = 'block w-full text-left px-0 py-2 md:px-3 md:py-2 rounded transition-all duration-200 hover:bg-(--bg-selected-light) dark:hover:bg-(--bg-selected-dark) cursor-pointer';
67
54
 
68
55
  // Add classes based on heading level
69
56
  let levelClasses = '';
70
57
  if (heading.level === 2) {
71
- levelClasses = 'text-[var(--text-primary-light)] dark:text-[var(--text-primary-dark)] font-semibold text-xs md:text-sm';
58
+ levelClasses = 'text-(--text-primary-light) dark:text-(--text-primary-dark) font-semibold text-xs md:text-sm';
72
59
  } else {
73
- levelClasses = 'text-[var(--text-secondary-light)] dark:text-[var(--text-secondary-dark)] !pl-6 text-xs md:text-sm';
60
+ levelClasses = 'text-(--text-secondary-light) dark:text-(--text-secondary-dark) !pl-6 text-xs md:text-sm';
74
61
  }
75
62
 
76
63
  // Return combined classes
@@ -79,36 +66,11 @@ const getHeadingButtonClasses = heading => {
79
66
  </script>
80
67
 
81
68
  <template>
82
- <Card v-if="headings.length > 0" class="!p-0 overflow-hidden">
83
- <CardContent class="!p-0 gap-0">
84
- <!-- Header -->
85
- <button @click="toggleExpanded" class="flex items-center justify-between w-full p-5 gap-4 text-left cursor-pointer">
86
- <div class="flex items-center gap-3 min-w-0">
87
- <!-- Icon -->
88
- <div class="flex items-center justify-center w-8 h-8 md:!w-10 md:!h-10 bg-[var(--bg-card-light)] dark:bg-[var(--bg-card-dark)] border border-[var(--border-light)] dark:border-[var(--border-dark)] rounded-none flex-shrink-0">
89
- <HugeiconsIcon :icon="Bookmark01Icon" class="size-4 text-[var(--text-secondary-light)] dark:text-[var(--text-secondary-dark)]" />
90
- </div>
91
-
92
- <!-- Title -->
93
- <span class="text-sm md:!text-base font-semibold text-[var(--text-primary-light)] dark:text-[var(--text-primary-dark)]">
94
- {{ t('uiVintage.blog.tableOfContents') }}
95
- </span>
96
- </div>
97
-
98
- <!-- Expand/Collapse icon -->
99
- <div class="flex-shrink-0 w-8 h-8 flex items-center justify-center rounded bg-[var(--bg-card-light)] dark:bg-[var(--bg-card-dark)] border border-[var(--border-light)] dark:border-[var(--border-dark)] transition-transform duration-300" :class="{ 'rotate-180': isExpanded }">
100
- <HugeiconsIcon :icon="ArrowDown01Icon" class="size-4 text-[var(--text-secondary-light)] dark:text-[var(--text-secondary-dark)]" />
101
- </div>
69
+ <Accordion v-if="headings.length > 0" :title="t('uiVintage.blog.tableOfContents')" :icon="Bookmark01Icon">
70
+ <nav class="space-y-1">
71
+ <button v-for="heading in headings" :key="heading.id" @click="scrollToHeading(heading.id)" :class="getHeadingButtonClasses(heading)">
72
+ {{ heading.text }}
102
73
  </button>
103
-
104
- <!-- Table of contents list with smooth transition -->
105
- <div class="overflow-hidden transition-[height,opacity] duration-300 ease-in-out" :style="{ height: isExpanded ? `${contentHeight}px` : '0px' }" :class="isExpanded ? 'opacity-100' : 'opacity-0'">
106
- <nav ref="contentBodyRef" class="px-5 pb-5 space-y-1">
107
- <button v-for="heading in headings" :key="heading.id" @click="scrollToHeading(heading.id)" :class="getHeadingButtonClasses(heading)">
108
- {{ heading.text }}
109
- </button>
110
- </nav>
111
- </div>
112
- </CardContent>
113
- </Card>
74
+ </nav>
75
+ </Accordion>
114
76
  </template>
@@ -117,7 +117,7 @@ const getSidebarItemLinkProps = (item: DashboardSidebarItem) => {
117
117
 
118
118
  <!-- Sidebar sections -->
119
119
  <SidebarContent v-if="props.sidebarSections.length">
120
- <SidebarGroup v-for="section in props.sidebarSections" :key="section.id">
120
+ <SidebarGroup v-for="section in props.sidebarSections" :key="section.id" class="space-y-1">
121
121
  <!-- Section label -->
122
122
  <SidebarGroupLabel v-if="section.label">
123
123
  {{ section.label }}
@@ -125,9 +125,9 @@ const getSidebarItemLinkProps = (item: DashboardSidebarItem) => {
125
125
 
126
126
  <!-- Section content -->
127
127
  <SidebarGroupContent>
128
- <SidebarMenu class="gap-3">
128
+ <SidebarMenu :class="cn('gap-3', props.compact && 'gap-2')">
129
129
  <SidebarMenuItem v-for="item in section.items" :key="item.id">
130
- <SidebarMenuButton as-child :is-active="item.active" :class="cn('group h-auto min-h-12 rounded border border-[var(--border-light)] px-3 py-2.5 text-[var(--text-secondary-light)] transition-all duration-200 hover:border-[var(--border-hover-light)] hover:bg-[var(--bg-selected-light)] hover:text-[var(--text-primary-light)] data-[active=true]:border-[var(--border-hover-light)] data-[active=true]:bg-[var(--bg-selected-light)] data-[active=true]:text-[var(--text-primary-light)] dark:border-[var(--border-dark)] dark:text-[var(--text-secondary-dark)] dark:hover:border-[var(--border-hover-dark)] dark:hover:bg-[var(--bg-selected-dark)] dark:hover:text-[var(--text-primary-dark)] dark:data-[active=true]:border-[var(--border-hover-dark)] dark:data-[active=true]:bg-[var(--bg-selected-dark)] dark:data-[active=true]:text-[var(--text-primary-dark)] sm:px-4 sm:py-3', item.description ? 'items-start' : 'items-center')">
130
+ <SidebarMenuButton as-child :is-active="item.active" :class="cn('group h-auto min-h-12 rounded border border-(--border-light) px-3 py-2.5 text-(--text-secondary-light) transition-all duration-200 hover:border-(--border-hover-light) hover:bg-(--bg-selected-light) hover:text-(--text-primary-light) data-[active=true]:border-(--border-hover-light) data-[active=true]:bg-(--bg-selected-light) data-[active=true]:text-(--text-primary-light) dark:border-(--border-dark) dark:text-(--text-secondary-dark) dark:hover:border-(--border-hover-dark) dark:hover:bg-(--bg-selected-dark) dark:hover:text-(--text-primary-dark) dark:data-[active=true]:border-(--border-hover-dark) dark:data-[active=true]:bg-(--bg-selected-dark) dark:data-[active=true]:text-(--text-primary-dark) sm:px-4 sm:py-3', item.description ? 'items-start' : 'items-center')">
131
131
  <component :is="props.sidebarLinkComponent" v-bind="getSidebarItemLinkProps(item)">
132
132
  <!-- Icon -->
133
133
  <HugeiconsIcon v-if="item.icon" :icon="item.icon" :stroke-width="1.8" :class="cn('shrink-0 opacity-90 transition-opacity duration-200 group-hover:opacity-100', item.description ? 'mt-0.5 size-5 sm:h-5 sm:w-5' : 'size-5 self-center sm:h-6 sm:w-6')" />
@@ -24,6 +24,7 @@ export interface LandingFooterSection {
24
24
  interface LandingFooterProps {
25
25
  appName: string;
26
26
  appLogo?: string;
27
+ appLinkTo?: string;
27
28
  appDescription?: string;
28
29
  sections?: LandingFooterSection[];
29
30
  linkComponent?: Component | string;
@@ -40,6 +41,7 @@ interface LandingFooterProps {
40
41
 
41
42
  // Props
42
43
  const props = withDefaults(defineProps<LandingFooterProps>(), {
44
+ appLinkTo: "/",
43
45
  appDescription: "",
44
46
  sections: () => [],
45
47
  linkComponent: "a",
@@ -79,10 +81,10 @@ const getLinkProps = (link: LandingFooterLink) => {
79
81
  <!-- Brand section -->
80
82
  <div :class="cn('max-w-md flex-1', props.brandClass)">
81
83
  <!-- App logo and name -->
82
- <div class="mb-4 inline-flex items-center gap-2 text-lg font-semibold tracking-tight text-foreground">
84
+ <a :href="props.appLinkTo" class="mb-4 inline-flex items-center gap-2 text-lg font-semibold tracking-tight text-foreground transition-opacity hover:opacity-80">
83
85
  <NuxtImg v-if="props.appLogo" :src="props.appLogo" :alt="`${props.appName} logo`" width="32" height="32" :sizes="{ 320: '32px', 1280: '32px' }" loading="lazy" decoding="async" class="size-8 shrink-0 object-contain" />
84
86
  <span>{{ props.appName }}</span>
85
- </div>
87
+ </a>
86
88
 
87
89
  <!-- App description -->
88
90
  <p v-if="props.appDescription" class="max-w-sm text-xs md:text-sm leading-relaxed text-muted-foreground">
@@ -7,6 +7,7 @@ interface LandingNavbarProps {
7
7
  appName?: string;
8
8
  appLogo?: string;
9
9
  appLinkTo?: string;
10
+ logoClass?: HTMLAttributes["class"];
10
11
  class?: HTMLAttributes["class"];
11
12
  containerClass?: HTMLAttributes["class"];
12
13
  leftClass?: HTMLAttributes["class"];
@@ -29,7 +30,7 @@ const props = withDefaults(defineProps<LandingNavbarProps>(), {
29
30
  <slot name="left">
30
31
  <a :href="props.appLinkTo" class="inline-flex items-center gap-2 transition-opacity hover:opacity-80">
31
32
  <!-- App logo -->
32
- <NuxtImg v-if="props.appLogo" :src="props.appLogo" :alt="`${props.appName} logo`" width="44" height="44" :sizes="{ 320: '44px', 640: '36px' }" loading="eager" fetchpriority="high" preload class="size-11 sm:size-9 shrink-0 object-contain" />
33
+ <NuxtImg v-if="props.appLogo" :src="props.appLogo" :alt="`${props.appName} logo`" width="44" height="44" :sizes="{ 320: '44px', 640: '36px' }" loading="eager" fetchpriority="high" :class="cn('size-11 sm:size-9 shrink-0 object-contain', props.logoClass)" />
33
34
 
34
35
  <!-- App name -->
35
36
  <span v-if="props.appName" class="hidden sm:!inline text-xl font-bold tracking-tight text-foreground">
@@ -39,7 +39,7 @@ const handleUpdateModelValue = (value?: number[]) => {
39
39
  </script>
40
40
 
41
41
  <template>
42
- <Card class="space-y-3 px-4 py-4">
42
+ <Card class="px-4 py-4">
43
43
  <!-- Slider header -->
44
44
  <div class="flex items-center justify-between gap-3">
45
45
  <!-- Label and description block -->
@@ -0,0 +1,61 @@
1
+ <script setup lang="ts">
2
+ import type { HTMLAttributes } from "vue";
3
+ import { ref } from "vue";
4
+ import { ArrowDown01Icon } from "@hugeicons/core-free-icons";
5
+ import { HugeiconsIcon } from "@hugeicons/vue";
6
+ import { Card, CardContent } from "@brumaombra/ui-vintage/card";
7
+
8
+ type HugeiconsIconDefinition = readonly (readonly [string, { readonly [key: string]: string | number }])[];
9
+
10
+ interface AccordionProps {
11
+ title: string;
12
+ initiallyExpanded?: boolean;
13
+ icon?: HugeiconsIconDefinition | null;
14
+ iconClass?: HTMLAttributes["class"];
15
+ }
16
+
17
+ // Props
18
+ const props = withDefaults(defineProps<AccordionProps>(), {
19
+ initiallyExpanded: false
20
+ });
21
+
22
+ const expanded = ref(props.initiallyExpanded);
23
+
24
+ // Toggle expanded state
25
+ const toggleExpanded = () => {
26
+ expanded.value = !expanded.value;
27
+ };
28
+ </script>
29
+
30
+ <template>
31
+ <Card class="p-0! overflow-hidden" @click="toggleExpanded">
32
+ <CardContent class="p-0! gap-0">
33
+ <!-- Header -->
34
+ <div class="flex items-center justify-between p-5 gap-4 text-left cursor-pointer">
35
+ <div class="flex items-center gap-3 min-w-0">
36
+ <!-- Icon -->
37
+ <div v-if="props.icon" class="flex h-8 w-8 shrink-0 items-center justify-center rounded bg-(--bg-card-light) border border-(--border-light) dark:bg-(--bg-card-dark) dark:border-(--border-dark) md:h-10 md:w-10">
38
+ <HugeiconsIcon :icon="props.icon" :class="['size-4 text-(--text-secondary-light) dark:text-(--text-secondary-dark)', props.iconClass]" />
39
+ </div>
40
+
41
+ <!-- Title -->
42
+ <div class="text-sm md:text-base! font-semibold text-(--text-primary-light) dark:text-(--text-primary-dark) text-left">
43
+ {{ props.title }}
44
+ </div>
45
+ </div>
46
+
47
+ <!-- Toggle icon -->
48
+ <div class="shrink-0 w-8 h-8 flex items-center justify-center rounded bg-(--bg-card-light) dark:bg-(--bg-card-dark) border border-(--border-light) dark:border-(--border-dark) transition-transform duration-300 cursor-pointer" :class="{ 'rotate-180': expanded }">
49
+ <HugeiconsIcon :icon="ArrowDown01Icon" class="size-4 text-(--text-secondary-light) dark:text-(--text-secondary-dark)" />
50
+ </div>
51
+ </div>
52
+
53
+ <!-- Content -->
54
+ <div :class="['grid transition-all duration-300 ease-in-out', expanded ? 'grid-rows-[1fr] opacity-100' : 'grid-rows-[0fr] opacity-0']">
55
+ <div :class="['overflow-hidden px-5 transition-[padding] duration-300 ease-in-out', expanded ? 'pb-5' : 'pb-0']">
56
+ <slot />
57
+ </div>
58
+ </div>
59
+ </CardContent>
60
+ </Card>
61
+ </template>
@@ -0,0 +1 @@
1
+ export { default as Accordion } from "./Accordion.vue"
@@ -14,7 +14,7 @@ const props = withDefaults(defineProps<PrimitiveProps & { class?: HTMLAttributes
14
14
  data-slot="breadcrumb-link"
15
15
  :as="as"
16
16
  :as-child="asChild"
17
- :class="cn('hover:text-foreground transition-colors', props.class)"
17
+ :class="cn('text-muted-foreground hover:underline', props.class)"
18
18
  >
19
19
  <slot />
20
20
  </Primitive>
@@ -27,10 +27,10 @@ export const buttonVariants: (props?: ButtonVariants & ClassProp) => string = cv
27
27
  size: {
28
28
  "default": "min-h-12 px-4 py-3 has-[>svg]:px-3",
29
29
  "sm": "min-h-10 gap-1.5 px-3 py-2 has-[>svg]:px-2.5",
30
- "lg": "min-h-12 px-6 py-3 has-[>svg]:px-4",
30
+ "lg": "min-h-[52px] px-4 py-3 has-[>svg]:px-4",
31
31
  "icon": "size-12",
32
32
  "icon-sm": "size-10",
33
- "icon-lg": "size-12",
33
+ "icon-lg": "size-[52px]",
34
34
  },
35
35
  },
36
36
  defaultVariants: {
@@ -13,7 +13,7 @@ const forwardedProps = useForwardProps(delegatedProps)
13
13
  </script>
14
14
 
15
15
  <template>
16
- <DialogDescription data-slot="dialog-description" v-bind="forwardedProps" :class="cn('text-xs sm:text-sm leading-6 text-muted-foreground', props.class)">
16
+ <DialogDescription data-slot="dialog-description" v-bind="forwardedProps" :class="cn('text-xs sm:text-sm leading-5 text-muted-foreground', props.class)">
17
17
  <slot />
18
18
  </DialogDescription>
19
19
  </template>
@@ -9,7 +9,7 @@ const props = defineProps<{
9
9
 
10
10
  <template>
11
11
  <p data-slot="field-description" :class="cn(
12
- '!text-xs sm:!text-xs leading-5 font-normal text-(--text-secondary-light) dark:text-(--text-secondary-dark) group-has-[[data-orientation=horizontal]]/field:text-balance',
12
+ 'text-xs leading-5 font-normal text-(--text-secondary-light) dark:text-(--text-secondary-dark) group-has-[[data-orientation=horizontal]]/field:text-balance',
13
13
  'last:mt-0 nth-last-2:-mt-1 [[data-variant=legend]+&]:-mt-1.5',
14
14
  '[&>a:hover]:text-primary [&>a]:underline [&>a]:underline-offset-4',
15
15
  props.class,
@@ -34,7 +34,7 @@ const forwarded = useForwardPropsEmits(delegatedProps, emits)
34
34
  <template>
35
35
  <SelectPortal>
36
36
  <SelectContent data-slot="select-content" v-bind="{ ...$attrs, ...forwarded }" :class="cn(
37
- 'bg-popover text-popover-foreground data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 relative z-50 max-h-(--reka-select-content-available-height) min-w-[8rem] overflow-x-hidden overflow-y-auto rounded border border-border transition-colors duration-300 ease-in-out max-sm:w-[calc(100vw-1rem)] max-sm:max-w-[calc(100vw-1rem)] max-sm:min-w-0',
37
+ 'bg-popover text-popover-foreground data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 relative z-50 max-h-(--reka-select-content-available-height) min-w-32 overflow-x-hidden overflow-y-auto rounded border border-border transition-colors duration-300 ease-in-out max-sm:w-(--reka-select-trigger-width) max-sm:min-w-(--reka-select-trigger-width)',
38
38
  position === 'popper'
39
39
  && 'data-[side=bottom]:translate-y-1 data-[side=left]:-translate-x-1 data-[side=right]:translate-x-1 data-[side=top]:-translate-y-1',
40
40
  props.class,
@@ -72,7 +72,7 @@ provideSidebarContext({
72
72
  <div data-slot="sidebar-wrapper" :style="{
73
73
  '--sidebar-width': SIDEBAR_WIDTH,
74
74
  '--sidebar-width-icon': SIDEBAR_WIDTH_ICON,
75
- }" :class="cn('group/sidebar-wrapper has-data-[variant=inset]:bg-sidebar flex min-h-svh w-full', props.class)" v-bind="$attrs">
75
+ }" :data-compact="props.compact ? 'true' : 'false'" :class="cn('group/sidebar-wrapper has-data-[variant=inset]:bg-sidebar flex min-h-svh w-full', props.class)" v-bind="$attrs">
76
76
  <slot />
77
77
  </div>
78
78
  </TooltipProvider>
@@ -51,8 +51,8 @@ export const sidebarMenuButtonVariants: (props?: SidebarMenuButtonVariants & Cla
51
51
  "bg-background shadow-[0_0_0_1px_hsl(var(--sidebar-border))] hover:bg-sidebar-accent hover:text-sidebar-accent-foreground hover:shadow-[0_0_0_1px_hsl(var(--sidebar-accent))]",
52
52
  },
53
53
  size: {
54
- default: "min-h-8 text-sm group-data-[compact=true]/sidebar-wrapper:min-h-7 group-data-[compact=true]/sidebar-wrapper:text-xs",
55
- sm: "min-h-7 text-xs group-data-[compact=true]/sidebar-wrapper:min-h-6",
54
+ default: "min-h-8 text-sm group-data-[compact=true]/sidebar-wrapper:min-h-7 group-data-[compact=true]/sidebar-wrapper:text-xs group-data-[compact=true]/sidebar-wrapper:py-3",
55
+ sm: "min-h-7 text-xs group-data-[compact=true]/sidebar-wrapper:min-h-6 group-data-[compact=true]/sidebar-wrapper:py-2.5",
56
56
  lg: "min-h-12 text-sm group-data-[compact=true]/sidebar-wrapper:min-h-10 group-data-[collapsible=icon]:p-0!",
57
57
  },
58
58
  },