@veristone/nuxt-v-app 0.2.7 → 0.2.9
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/app/components/{Va/Blocks/VaBlockGridCharts.vue → V/A/Block/GridCharts.vue} +2 -3
- package/app/components/{Va/Blocks/VaBlockGridKPI.vue → V/A/Block/GridKPI.vue} +3 -3
- package/app/components/{Va/Blocks/VaBlockGridTables.vue → V/A/Block/GridTables.vue} +3 -3
- package/app/components/{Va/Cards/VaCardWithActiveUsers.vue → V/A/Card/WithActiveUsers.vue} +5 -5
- package/app/components/{Va/Cards/VaCardWithChart.vue → V/A/Card/WithChart.vue} +7 -7
- package/app/components/V/A/Card/index.vue +132 -0
- package/app/components/{Va/Charts/VaChartAreaMini.vue → V/A/Chart/AreaMini.vue} +2 -2
- package/app/components/V/A/Dashboard/PricePlan.vue +87 -0
- package/app/components/V/A/Table/index.vue +48 -36
- package/app/layouts/default.vue +3 -3
- package/app/layouts/legacy.vue +4 -4
- package/app/pages/playground/blocks.vue +15 -15
- package/app/pages/playground/cards.vue +43 -43
- package/app/pages/playground/charts.vue +64 -64
- package/app/pages/playground/dashboard.vue +22 -22
- package/app/pages/playground/index.vue +123 -106
- package/app/pages/playground/layout.vue +19 -19
- package/package.json +2 -2
- package/app/components/V/A/Card.vue +0 -108
- package/app/components/Va/Dashboard/VaDashboardPricePlan.vue +0 -102
- /package/app/components/{Va/Blocks/VaBlockKpiGrid.vue → V/A/Block/KpiGrid.vue} +0 -0
- /package/app/components/{Va/Blocks/VaBlockSessionFilterBar.vue → V/A/Block/SessionFilterBar.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardDonutChart.vue → V/A/Card/DonutChart.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardHeader.vue → V/A/Card/Header.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardKpi.vue → V/A/Card/Kpi.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardKpi2.vue → V/A/Card/Kpi2.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardLatestOrders.vue → V/A/Card/LatestOrders.vue} +0 -0
- /package/app/components/V/A/{Card.legacy.vue → Card/Legacy.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardPopularProducts.vue → V/A/Card/PopularProducts.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardRevenueBarChart.vue → V/A/Card/RevenueBarChart.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardSubtitle.vue → V/A/Card/Subtitle.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardTitle.vue → V/A/Card/Title.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardWithChartBlock.vue → V/A/Card/WithChartBlock.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardWithIndicator.vue → V/A/Card/WithIndicator.vue} +0 -0
- /package/app/components/{Va/Cards/VaCardWithProgressCircle.vue → V/A/Card/WithProgressCircle.vue} +0 -0
- /package/app/components/{Va/Cards/types.ts → V/A/Card/card-types.ts} +0 -0
- /package/app/components/{Va/Charts/VaChartAppPerformanceBar.vue → V/A/Chart/AppPerformanceBar.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartAppPerformanceBarChart.vue → V/A/Chart/AppPerformanceBarChart.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartBarMini.vue → V/A/Chart/BarMini.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartCardinalMulti.vue → V/A/Chart/CardinalMulti.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartColorBarChart.vue → V/A/Chart/ColorBarChart.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartDonutHalf.vue → V/A/Chart/DonutHalf.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartDonutMini.vue → V/A/Chart/DonutMini.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartExpensesBar.vue → V/A/Chart/ExpensesBar.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartFinanceSummary.vue → V/A/Chart/FinanceSummary.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartGoogleSearchConsole.vue → V/A/Chart/GoogleSearchConsole.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartIncomeBar.vue → V/A/Chart/IncomeBar.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartLegend.vue → V/A/Chart/Legend.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartLineMini.vue → V/A/Chart/LineMini.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartRealtimeTraffic.vue → V/A/Chart/RealtimeTraffic.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartRevenue.vue → V/A/Chart/Revenue.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartRevenueLine.vue → V/A/Chart/RevenueLine.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartRevenuevsCost.vue → V/A/Chart/RevenuevsCost.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartSearchIntent.vue → V/A/Chart/SearchIntent.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartSpendingTrend.vue → V/A/Chart/SpendingTrend.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartStackedHorizontal.vue → V/A/Chart/StackedHorizontal.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartStepMinimal.vue → V/A/Chart/StepMinimal.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartStockComparisonLine.vue → V/A/Chart/StockComparisonLine.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartStocksPortfolioLine.vue → V/A/Chart/StocksPortfolioLine.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartStocksSectorLine.vue → V/A/Chart/StocksSectorLine.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartTasksCategories.vue → V/A/Chart/TasksCategories.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartTasksProgress.vue → V/A/Chart/TasksProgress.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartTrafficOverview.vue → V/A/Chart/TrafficOverview.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartWebPerformanceLineChart.vue → V/A/Chart/WebPerformanceLineChart.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartWinLostBar.vue → V/A/Chart/WinLostBar.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartWinLostDonut.vue → V/A/Chart/WinLostDonut.vue} +0 -0
- /package/app/components/{Va/Charts/VaChartWinLostLine.vue → V/A/Chart/WinLostLine.vue} +0 -0
- /package/app/components/{Va/Charts/types.ts → V/A/Chart/chart-types.ts} +0 -0
- /package/app/components/{Va/Dashboard/VaDashboardKPICard.vue → V/A/Dashboard/KPICard.vue} +0 -0
- /package/app/components/{Va → V/A}/Dashboard/Navigation/types.ts +0 -0
- /package/app/components/{Va/Dashboard/VaDashboardNavigation.vue → V/A/Dashboard/Navigation.vue} +0 -0
- /package/app/components/{Va/Dashboard/VaDashboardUsageChart.vue → V/A/Dashboard/UsageChart.vue} +0 -0
- /package/app/components/{Va/Dashboard/VaDashboardUsageRequestChart.vue → V/A/Dashboard/UsageRequestChart.vue} +0 -0
- /package/app/components/{Va → V/A}/Layout/NotificationsSlideover.vue +0 -0
- /package/app/components/{Va → V/A}/Layout/SideNav/types.ts +0 -0
- /package/app/components/{Va → V/A}/Layout/SideNav.vue +0 -0
- /package/app/components/{Va → V/A}/Layout/TeamsMenu.vue +0 -0
- /package/app/components/{Va → V/A}/Layout/UserMenu.vue +0 -0
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
<script setup lang="ts">
|
|
2
2
|
import { RevenueData, RevenueCategoriesMultiple, xFormatter, yFormatter, DonutData } from '~/data/dashboardData';
|
|
3
|
-
import { computed } from 'vue';
|
|
4
3
|
|
|
5
4
|
const props = defineProps<{ childOrder: [0 | 1, 0 | 1] }>();
|
|
6
5
|
|
|
@@ -11,7 +10,7 @@ const flexDirection = computed(() =>
|
|
|
11
10
|
<template>
|
|
12
11
|
<div :class="`flex flex-col ${flexDirection} w-full px-4 md:px-8 mb-6 gap-6`">
|
|
13
12
|
<div class="w-full md:w-8/12">
|
|
14
|
-
<
|
|
13
|
+
<VACardRevenueBarChart
|
|
15
14
|
title="Revenue"
|
|
16
15
|
total-value="$4589.00"
|
|
17
16
|
:data="RevenueData"
|
|
@@ -22,7 +21,7 @@ const flexDirection = computed(() =>
|
|
|
22
21
|
/>
|
|
23
22
|
</div>
|
|
24
23
|
<div class="w-full md:w-4/12 relative">
|
|
25
|
-
<
|
|
24
|
+
<VACardDonutChart
|
|
26
25
|
title="Revenue"
|
|
27
26
|
total-value="$4589.00"
|
|
28
27
|
:data="DonutData"
|
|
@@ -5,7 +5,7 @@ import { SalesData, RevenueDataCard, ReturnsData } from '~/data/dashboardData';
|
|
|
5
5
|
<template>
|
|
6
6
|
<div class="grid grid-cols-1 gap-6 md:grid-cols-2 xl:grid-cols-6 w-full px-4 md:px-8 mb-6">
|
|
7
7
|
<div class="w-full md:col-span-1 xl:col-span-2">
|
|
8
|
-
<
|
|
8
|
+
<VACardSalesCard
|
|
9
9
|
title="Sales"
|
|
10
10
|
value="1,245"
|
|
11
11
|
:chart-data="SalesData.chartData"
|
|
@@ -13,7 +13,7 @@ import { SalesData, RevenueDataCard, ReturnsData } from '~/data/dashboardData';
|
|
|
13
13
|
/>
|
|
14
14
|
</div>
|
|
15
15
|
<div class="w-full md:col-span-1 xl:col-span-2">
|
|
16
|
-
<
|
|
16
|
+
<VACardRevenueCard
|
|
17
17
|
title="Revenue"
|
|
18
18
|
value="$58,981.00"
|
|
19
19
|
:chart-data="RevenueDataCard.chartData"
|
|
@@ -21,7 +21,7 @@ import { SalesData, RevenueDataCard, ReturnsData } from '~/data/dashboardData';
|
|
|
21
21
|
/>
|
|
22
22
|
</div>
|
|
23
23
|
<div class="w-full md:col-span-2">
|
|
24
|
-
<
|
|
24
|
+
<VACardReturnsCard
|
|
25
25
|
title="Returns"
|
|
26
26
|
value="32"
|
|
27
27
|
:chart-data="ReturnsData.chartData"
|
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
<script setup lang="ts">
|
|
2
|
-
import
|
|
3
|
-
import
|
|
2
|
+
import VACardLatestOrders from '../Card/LatestOrders.vue';
|
|
3
|
+
import VACardPopularProducts from '../Card/PopularProducts.vue';
|
|
4
4
|
import { orders, products } from '~/data/dashboardData';
|
|
5
5
|
|
|
6
6
|
defineProps<{ childOrder: [0 | 1, 0 | 1] }>();
|
|
7
7
|
|
|
8
|
-
const cardComponents = [
|
|
8
|
+
const cardComponents = [VACardLatestOrders, VACardPopularProducts] as const;
|
|
9
9
|
</script>
|
|
10
10
|
<template>
|
|
11
11
|
<div class="grid grid-cols-1 gap-6 md:grid-cols-2 xl:grid-cols-6 w-full px-4 md:px-8 mb-6">
|
|
@@ -9,16 +9,16 @@ defineProps<{
|
|
|
9
9
|
<template>
|
|
10
10
|
<UCard>
|
|
11
11
|
<div class="space-y-2">
|
|
12
|
-
<
|
|
12
|
+
<VACardSubtitle>
|
|
13
13
|
{{ metric }}
|
|
14
|
-
</
|
|
14
|
+
</VACardSubtitle>
|
|
15
15
|
|
|
16
16
|
<div class="flex items-center justify-start gap-4">
|
|
17
|
-
<
|
|
17
|
+
<VACardTitle>
|
|
18
18
|
{{ current }}
|
|
19
|
-
</
|
|
19
|
+
</VACardTitle>
|
|
20
20
|
|
|
21
|
-
<div class="flex
|
|
21
|
+
<div class="flex flex-col items-start text-sm">
|
|
22
22
|
<div class="flex items-center gap-1">
|
|
23
23
|
<UIcon
|
|
24
24
|
:name="
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
<script setup lang="ts">
|
|
2
|
-
import type { BulletLegendItemInterface, ChartData } from './types'
|
|
2
|
+
import type { BulletLegendItemInterface, ChartData } from './card-types'
|
|
3
3
|
|
|
4
4
|
defineProps<{
|
|
5
5
|
name: string
|
|
@@ -91,10 +91,10 @@ const data: ChartData[] = [
|
|
|
91
91
|
|
|
92
92
|
<template>
|
|
93
93
|
<UCard>
|
|
94
|
-
<
|
|
95
|
-
<
|
|
94
|
+
<VACardHeader>
|
|
95
|
+
<VACardSubtitle>
|
|
96
96
|
{{ name }}
|
|
97
|
-
</
|
|
97
|
+
</VACardSubtitle>
|
|
98
98
|
<template #action>
|
|
99
99
|
<UButton
|
|
100
100
|
icon="i-lucide-ellipsis-vertical"
|
|
@@ -102,11 +102,11 @@ const data: ChartData[] = [
|
|
|
102
102
|
variant="subtle"
|
|
103
103
|
/>
|
|
104
104
|
</template>
|
|
105
|
-
</
|
|
105
|
+
</VACardHeader>
|
|
106
106
|
<div class="space-y-2">
|
|
107
|
-
<
|
|
107
|
+
<VACardTitle>
|
|
108
108
|
{{ value }}
|
|
109
|
-
</
|
|
109
|
+
</VACardTitle>
|
|
110
110
|
<h5 class="text-sm text-muted">
|
|
111
111
|
{{ name }}
|
|
112
112
|
</h5>
|
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
/**
|
|
3
|
+
* VACard - Veristone Card
|
|
4
|
+
* Matches XACard API exactly.
|
|
5
|
+
*/
|
|
6
|
+
const props = withDefaults(
|
|
7
|
+
defineProps<{
|
|
8
|
+
title?: string;
|
|
9
|
+
description?: string;
|
|
10
|
+
icon?: string;
|
|
11
|
+
collapsible?: boolean;
|
|
12
|
+
collapsed?: boolean;
|
|
13
|
+
padding?: boolean;
|
|
14
|
+
divider?: boolean;
|
|
15
|
+
variant?: "default" | "error" | "warning" | "success";
|
|
16
|
+
}>(),
|
|
17
|
+
{
|
|
18
|
+
title: "",
|
|
19
|
+
description: "",
|
|
20
|
+
icon: "",
|
|
21
|
+
collapsible: false,
|
|
22
|
+
collapsed: false,
|
|
23
|
+
padding: true,
|
|
24
|
+
divider: true,
|
|
25
|
+
variant: "default",
|
|
26
|
+
}
|
|
27
|
+
);
|
|
28
|
+
|
|
29
|
+
const isCollapsed = ref(props.collapsed);
|
|
30
|
+
watch(
|
|
31
|
+
() => props.collapsed,
|
|
32
|
+
(val) => (isCollapsed.value = val)
|
|
33
|
+
);
|
|
34
|
+
|
|
35
|
+
const toggleCollapse = () => {
|
|
36
|
+
if (props.collapsible) isCollapsed.value = !isCollapsed.value;
|
|
37
|
+
};
|
|
38
|
+
|
|
39
|
+
const variantClass = computed(() => {
|
|
40
|
+
switch (props.variant) {
|
|
41
|
+
case "error":
|
|
42
|
+
return "border-red-200 dark:border-red-900 bg-red-50/50 dark:bg-red-900/10";
|
|
43
|
+
case "warning":
|
|
44
|
+
return "border-amber-200 dark:border-amber-900 bg-amber-50/50 dark:bg-amber-900/10";
|
|
45
|
+
case "success":
|
|
46
|
+
return "border-green-200 dark:border-green-900 bg-green-50/50 dark:bg-green-900/10";
|
|
47
|
+
default:
|
|
48
|
+
return "border-gray-200 dark:border-gray-800 bg-white dark:bg-gray-900";
|
|
49
|
+
}
|
|
50
|
+
});
|
|
51
|
+
</script>
|
|
52
|
+
|
|
53
|
+
<template>
|
|
54
|
+
<div
|
|
55
|
+
class="va-card rounded-xl border transition-all duration-200 shadow-[0_2px_9px_rgba(0,0,0,0.08)] hover:shadow-[0_4px_12px_rgba(61,113,136,0.12)]"
|
|
56
|
+
:class="variantClass"
|
|
57
|
+
>
|
|
58
|
+
<!-- Header -->
|
|
59
|
+
<div
|
|
60
|
+
v-if="title || $slots['header-actions'] || icon"
|
|
61
|
+
class="flex items-center justify-between"
|
|
62
|
+
:class="[
|
|
63
|
+
padding ? 'px-5 py-4' : 'px-4 py-3',
|
|
64
|
+
divider && !isCollapsed
|
|
65
|
+
? 'border-b border-gray-100 dark:border-gray-800'
|
|
66
|
+
: '',
|
|
67
|
+
]"
|
|
68
|
+
>
|
|
69
|
+
<div class="flex items-center gap-3 overflow-hidden">
|
|
70
|
+
<slot name="header">
|
|
71
|
+
<div
|
|
72
|
+
v-if="icon"
|
|
73
|
+
class="flex-shrink-0 p-1.5 rounded-md bg-gray-100 dark:bg-gray-800 text-gray-500"
|
|
74
|
+
>
|
|
75
|
+
<UIcon :name="icon" class="w-5 h-5" />
|
|
76
|
+
</div>
|
|
77
|
+
<div class="min-w-0">
|
|
78
|
+
<div class="flex items-center gap-2">
|
|
79
|
+
<h3
|
|
80
|
+
class="font-bold text-gray-900 dark:text-white truncate text-base"
|
|
81
|
+
>
|
|
82
|
+
{{ title }}
|
|
83
|
+
</h3>
|
|
84
|
+
|
|
85
|
+
<button
|
|
86
|
+
v-if="collapsible"
|
|
87
|
+
@click="toggleCollapse"
|
|
88
|
+
class="ml-1 text-gray-400 hover:text-gray-600 dark:hover:text-gray-200 transition-colors focus:outline-none"
|
|
89
|
+
>
|
|
90
|
+
<UIcon
|
|
91
|
+
name="i-lucide-chevron-down"
|
|
92
|
+
class="w-4 h-4 transition-transform duration-300"
|
|
93
|
+
:class="{ '-rotate-180': !isCollapsed }"
|
|
94
|
+
/>
|
|
95
|
+
</button>
|
|
96
|
+
</div>
|
|
97
|
+
<p
|
|
98
|
+
v-if="description"
|
|
99
|
+
class="text-xs text-gray-500 dark:text-gray-400 truncate mt-0.5 font-medium"
|
|
100
|
+
>
|
|
101
|
+
{{ description }}
|
|
102
|
+
</p>
|
|
103
|
+
</div>
|
|
104
|
+
</slot>
|
|
105
|
+
</div>
|
|
106
|
+
|
|
107
|
+
<!-- XACard uses 'header-actions' slot -->
|
|
108
|
+
<div
|
|
109
|
+
v-if="$slots['header-actions']"
|
|
110
|
+
class="flex-shrink-0 flex items-center gap-2 ml-4"
|
|
111
|
+
>
|
|
112
|
+
<slot name="header-actions" />
|
|
113
|
+
</div>
|
|
114
|
+
</div>
|
|
115
|
+
|
|
116
|
+
<!-- Body -->
|
|
117
|
+
<div v-show="!isCollapsed" class="transition-all duration-300 ease-in-out">
|
|
118
|
+
<div :class="{ 'p-5': padding, 'p-0': !padding }">
|
|
119
|
+
<slot />
|
|
120
|
+
</div>
|
|
121
|
+
|
|
122
|
+
<!-- Footer -->
|
|
123
|
+
<div
|
|
124
|
+
v-if="$slots.footer"
|
|
125
|
+
class="bg-gray-50 dark:bg-gray-800/50 border-t border-gray-100 dark:border-gray-800"
|
|
126
|
+
:class="padding ? 'px-5 py-3' : 'px-4 py-2'"
|
|
127
|
+
>
|
|
128
|
+
<slot name="footer" />
|
|
129
|
+
</div>
|
|
130
|
+
</div>
|
|
131
|
+
</div>
|
|
132
|
+
</template>
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
<script setup lang="ts">
|
|
2
|
-
import type { SpendingData, BulletLegendItemInterface } from './types'
|
|
2
|
+
import type { SpendingData, BulletLegendItemInterface } from './chart-types'
|
|
3
3
|
|
|
4
4
|
const chartData = ref<SpendingData[]>([
|
|
5
5
|
{
|
|
@@ -70,7 +70,7 @@ const categories: Record<string, BulletLegendItemInterface> = {
|
|
|
70
70
|
color: '#22c55e'
|
|
71
71
|
},
|
|
72
72
|
previous: {
|
|
73
|
-
name: 'Last
|
|
73
|
+
name: 'Last Year',
|
|
74
74
|
color: '#00BCFF'
|
|
75
75
|
}
|
|
76
76
|
}
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
<script setup lang="ts">
|
|
2
|
+
interface Feature {
|
|
3
|
+
label: string;
|
|
4
|
+
available: boolean;
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
export interface PricePlanProps {
|
|
8
|
+
name: string;
|
|
9
|
+
description: string;
|
|
10
|
+
price: string;
|
|
11
|
+
priceSuffix?: string;
|
|
12
|
+
per?: string;
|
|
13
|
+
features: Feature[];
|
|
14
|
+
current?: boolean;
|
|
15
|
+
badge?: string;
|
|
16
|
+
buttonLabel?: string;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
defineProps<PricePlanProps>();
|
|
20
|
+
</script>
|
|
21
|
+
|
|
22
|
+
<template>
|
|
23
|
+
<UCard
|
|
24
|
+
:class="[
|
|
25
|
+
'relative transition-all duration-200',
|
|
26
|
+
current ? 'ring-2 ring-success bg-success/5' : ' ',
|
|
27
|
+
]"
|
|
28
|
+
>
|
|
29
|
+
<div v-if="badge" class="absolute -top-3 left-1/2 -translate-x-1/2">
|
|
30
|
+
<UBadge :label="badge" variant="solid" color="success" size="sm" />
|
|
31
|
+
</div>
|
|
32
|
+
|
|
33
|
+
<div class="text-center">
|
|
34
|
+
<div>
|
|
35
|
+
<h3 class="text-xl font-bold text-highlighted">
|
|
36
|
+
{{ name }}
|
|
37
|
+
</h3>
|
|
38
|
+
<p class="text-dimmed mt-1">
|
|
39
|
+
{{ description }}
|
|
40
|
+
</p>
|
|
41
|
+
</div>
|
|
42
|
+
|
|
43
|
+
<div class="border-y border-default my-4 py-4">
|
|
44
|
+
<div class="mb-4">
|
|
45
|
+
<div class="text-3xl font-bold text-success space-x-2">
|
|
46
|
+
<span>{{ price }}</span>
|
|
47
|
+
<span v-if="priceSuffix" class="text-base text-toned">{{
|
|
48
|
+
priceSuffix
|
|
49
|
+
}}</span>
|
|
50
|
+
</div>
|
|
51
|
+
<div v-if="per" class="text-sm text-muted">
|
|
52
|
+
{{ per }}
|
|
53
|
+
</div>
|
|
54
|
+
</div>
|
|
55
|
+
|
|
56
|
+
<UButton
|
|
57
|
+
:label="buttonLabel"
|
|
58
|
+
:variant="current ? 'outline' : 'solid'"
|
|
59
|
+
:color="current ? 'success' : 'success'"
|
|
60
|
+
class="w-full justify-center"
|
|
61
|
+
:disabled="current"
|
|
62
|
+
:icon="current ? 'i-lucide-check' : 'i-lucide-arrow-up-right'"
|
|
63
|
+
/>
|
|
64
|
+
</div>
|
|
65
|
+
|
|
66
|
+
<div class="space-y-4 mt-8">
|
|
67
|
+
<div
|
|
68
|
+
v-for="(feature, i) in features"
|
|
69
|
+
:key="i"
|
|
70
|
+
class="flex items-center justify-start gap-2 text-sm"
|
|
71
|
+
>
|
|
72
|
+
<UIcon
|
|
73
|
+
:name="feature.available ? 'i-lucide-check' : 'i-lucide-x'"
|
|
74
|
+
:class="feature.available ? 'text-success' : 'text-error'"
|
|
75
|
+
size="16"
|
|
76
|
+
/>
|
|
77
|
+
<span
|
|
78
|
+
:class="{
|
|
79
|
+
'text-dimmed': !feature.available,
|
|
80
|
+
}"
|
|
81
|
+
>{{ feature.label }}</span
|
|
82
|
+
>
|
|
83
|
+
</div>
|
|
84
|
+
</div>
|
|
85
|
+
</div>
|
|
86
|
+
</UCard>
|
|
87
|
+
</template>
|
|
@@ -59,6 +59,8 @@
|
|
|
59
59
|
class="w-40"
|
|
60
60
|
/>
|
|
61
61
|
</template>
|
|
62
|
+
|
|
63
|
+
<slot name="toolbar-left" />
|
|
62
64
|
</div>
|
|
63
65
|
|
|
64
66
|
<div class="flex items-center gap-2">
|
|
@@ -120,7 +122,7 @@
|
|
|
120
122
|
}"
|
|
121
123
|
empty="Nothing to show."
|
|
122
124
|
v-bind="$attrs"
|
|
123
|
-
|
|
125
|
+
:on-select="props.onRowClick ? (_e: any, row: any) => handleRowClick(row) : undefined"
|
|
124
126
|
>
|
|
125
127
|
<template v-for="slotEntry in forwardedSlots" :key="slotEntry.target" #[slotEntry.target]="slotProps">
|
|
126
128
|
<slot :name="slotEntry.source" v-bind="slotProps" />
|
|
@@ -163,40 +165,50 @@
|
|
|
163
165
|
</UCard>
|
|
164
166
|
</template>
|
|
165
167
|
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
168
|
+
/**
|
|
169
|
+
* VATable - Veristone data table component built on Nuxt UI's UTable + TanStack Table.
|
|
170
|
+
*
|
|
171
|
+
* @props
|
|
172
|
+
* name - Optional card header title
|
|
173
|
+
* data - Row data array
|
|
174
|
+
* columns - TanStack TableColumn definitions; supports `meta.preset` for cell rendering
|
|
175
|
+
* loading - Shows skeleton on initial load; shows inline spinner on subsequent refreshes
|
|
176
|
+
* initialPageLimit - Default page size (default: 10)
|
|
177
|
+
* selectable - Enables row checkboxes; exposes `selectedRows` via template ref
|
|
178
|
+
* showSearch - Renders a global search input in the toolbar
|
|
179
|
+
* filters - Array of { key, label, options } for toolbar USelect dropdowns
|
|
180
|
+
* onRefresh - Async callback; shows a refresh spinner button in the toolbar
|
|
181
|
+
* onRowClick - Called with the row's original data when a row is clicked
|
|
182
|
+
* defaultSort - Column key to sort by on mount
|
|
183
|
+
* defaultSortDesc - Sort descending when defaultSort is set (default: false)
|
|
184
|
+
* manualPagination - Enables server-side pagination mode
|
|
185
|
+
* total - Total row count for server-side pagination
|
|
186
|
+
*
|
|
187
|
+
* @models (v-model)
|
|
188
|
+
* sorting - SortingState — sync sort state with parent
|
|
189
|
+
* filterValues - Record<string, unknown> — sync active filter values with parent
|
|
190
|
+
* globalFilter - string — sync search input value with parent
|
|
191
|
+
* page - number (1-based) — current page in manual pagination mode
|
|
192
|
+
* itemsPerPage - number — page size in manual pagination mode
|
|
193
|
+
*
|
|
194
|
+
* @slots
|
|
195
|
+
* header-right - Content rendered on the right side of the card header
|
|
196
|
+
* toolbar-left - Custom controls (e.g. filter selects) injected into the toolbar
|
|
197
|
+
* next to the search input and built-in filter dropdowns
|
|
198
|
+
* Example:
|
|
199
|
+
* <template #toolbar-left>
|
|
200
|
+
* <USelect v-model="status" :items="opts" placeholder="Status" size="sm" />
|
|
201
|
+
* </template>
|
|
202
|
+
* bulk-actions - Shown in the toolbar when rows are selected; receives
|
|
203
|
+
* { selected, count, clear }
|
|
204
|
+
* actions-cell - Renders an "Actions" column; receives { row }
|
|
205
|
+
* [column]-cell - Override cell rendering for a specific column by accessor key
|
|
206
|
+
*
|
|
207
|
+
* @exposes
|
|
208
|
+
* selectedRows - Array of selected row originals
|
|
209
|
+
* rowSelection - Raw TanStack row selection state
|
|
210
|
+
* clearSelection - Clears the current row selection
|
|
211
|
+
*/
|
|
200
212
|
|
|
201
213
|
// Sorting state - v-model support
|
|
202
214
|
const sorting = defineModel<SortingState>("sorting", {
|
|
@@ -472,7 +484,7 @@ const tableColumns = computed(() => {
|
|
|
472
484
|
|
|
473
485
|
const forwardedSlots = computed(() => {
|
|
474
486
|
const passthrough = Object.keys(slots).filter((name) => {
|
|
475
|
-
return !['default', 'header-right', 'bulk-actions'].includes(name);
|
|
487
|
+
return !['default', 'header-right', 'bulk-actions', 'toolbar-left'].includes(name);
|
|
476
488
|
});
|
|
477
489
|
|
|
478
490
|
return passthrough.map((source) => {
|
package/app/layouts/default.vue
CHANGED
|
@@ -134,7 +134,7 @@ const groups = computed(() => [
|
|
|
134
134
|
</template>
|
|
135
135
|
|
|
136
136
|
<template #default="{ collapsed }">
|
|
137
|
-
<
|
|
137
|
+
<VALayoutSideNav :items="links[0]!" :collapsed="collapsed" />
|
|
138
138
|
|
|
139
139
|
<!-- Accounts section commented out - requires /analytics.svg asset
|
|
140
140
|
<div class="space-y-1 mt-4">
|
|
@@ -167,7 +167,7 @@ const groups = computed(() => [
|
|
|
167
167
|
</template>
|
|
168
168
|
|
|
169
169
|
<template #footer="{ collapsed }">
|
|
170
|
-
<
|
|
170
|
+
<VALayoutUserMenu :collapsed="collapsed" />
|
|
171
171
|
</template>
|
|
172
172
|
</UDashboardSidebar>
|
|
173
173
|
|
|
@@ -176,6 +176,6 @@ const groups = computed(() => [
|
|
|
176
176
|
<div class="flex-1 overflow-y-auto">
|
|
177
177
|
<slot />
|
|
178
178
|
</div>
|
|
179
|
-
<
|
|
179
|
+
<VALayoutNotificationsSlideover />
|
|
180
180
|
</UDashboardGroup>
|
|
181
181
|
</template>
|
package/app/layouts/legacy.vue
CHANGED
|
@@ -29,11 +29,11 @@ const links: NavigationMenuItem[][] = [
|
|
|
29
29
|
:max-size="18"
|
|
30
30
|
>
|
|
31
31
|
<template #header="{ collapsed }">
|
|
32
|
-
<
|
|
32
|
+
<VALayoutTeamsMenu :collapsed="collapsed" />
|
|
33
33
|
</template>
|
|
34
34
|
|
|
35
35
|
<template #default="{ collapsed }">
|
|
36
|
-
<
|
|
36
|
+
<VALayoutSideNav
|
|
37
37
|
:items="links[0]!"
|
|
38
38
|
:collapsed="collapsed"
|
|
39
39
|
/>
|
|
@@ -49,13 +49,13 @@ const links: NavigationMenuItem[][] = [
|
|
|
49
49
|
</template>
|
|
50
50
|
|
|
51
51
|
<template #footer="{ collapsed }">
|
|
52
|
-
<
|
|
52
|
+
<VALayoutUserMenu :collapsed="collapsed" />
|
|
53
53
|
</template>
|
|
54
54
|
</UDashboardSidebar>
|
|
55
55
|
|
|
56
56
|
<slot name="header" />
|
|
57
57
|
<slot name="header-actions" />
|
|
58
58
|
<slot />
|
|
59
|
-
<
|
|
59
|
+
<VALayoutNotificationsSlideover />
|
|
60
60
|
</UDashboardGroup>
|
|
61
61
|
</template>
|
|
@@ -7,8 +7,8 @@
|
|
|
7
7
|
Block components are larger, composite components that combine multiple elements into organized layouts.
|
|
8
8
|
</p>
|
|
9
9
|
|
|
10
|
-
<!--
|
|
11
|
-
<h2 class="text-2xl font-semibold mb-4 mt-8">
|
|
10
|
+
<!-- VABlockKpiGrid Section -->
|
|
11
|
+
<h2 class="text-2xl font-semibold mb-4 mt-8">VABlockKpiGrid</h2>
|
|
12
12
|
<p class="text-gray-600 dark:text-gray-400 mb-4">KPI grid layout block displaying key performance indicators.</p>
|
|
13
13
|
<div class="mb-8">
|
|
14
14
|
<UCard>
|
|
@@ -16,13 +16,13 @@
|
|
|
16
16
|
<h3 class="font-semibold">KPI Grid Layout</h3>
|
|
17
17
|
</template>
|
|
18
18
|
<ClientOnly>
|
|
19
|
-
<
|
|
19
|
+
<VABlockKpiGrid :items="kpiGridItems" />
|
|
20
20
|
</ClientOnly>
|
|
21
21
|
</UCard>
|
|
22
22
|
</div>
|
|
23
23
|
|
|
24
|
-
<!--
|
|
25
|
-
<h2 class="text-2xl font-semibold mb-4 mt-8">
|
|
24
|
+
<!-- VABlockSessionFilterBar Section -->
|
|
25
|
+
<h2 class="text-2xl font-semibold mb-4 mt-8">VABlockSessionFilterBar</h2>
|
|
26
26
|
<p class="text-gray-600 dark:text-gray-400 mb-4">Session filter bar for filtering data by date range, status, and category.</p>
|
|
27
27
|
<div class="mb-8">
|
|
28
28
|
<UCard>
|
|
@@ -30,7 +30,7 @@
|
|
|
30
30
|
<h3 class="font-semibold">Session Filter Bar</h3>
|
|
31
31
|
</template>
|
|
32
32
|
<ClientOnly>
|
|
33
|
-
<
|
|
33
|
+
<VABlockSessionFilterBar
|
|
34
34
|
:filters="mockFilters"
|
|
35
35
|
@update:filters="handleFilterUpdate"
|
|
36
36
|
/>
|
|
@@ -38,8 +38,8 @@
|
|
|
38
38
|
</UCard>
|
|
39
39
|
</div>
|
|
40
40
|
|
|
41
|
-
<!--
|
|
42
|
-
<h2 class="text-2xl font-semibold mb-4 mt-8">
|
|
41
|
+
<!-- VABlockGridKPI Section -->
|
|
42
|
+
<h2 class="text-2xl font-semibold mb-4 mt-8">VABlockGridKPI</h2>
|
|
43
43
|
<p class="text-gray-600 dark:text-gray-400 mb-4">KPI cards grid layout block with sales, revenue, and returns data.</p>
|
|
44
44
|
<div class="mb-8">
|
|
45
45
|
<UCard>
|
|
@@ -47,13 +47,13 @@
|
|
|
47
47
|
<h3 class="font-semibold">KPI Cards Grid</h3>
|
|
48
48
|
</template>
|
|
49
49
|
<ClientOnly>
|
|
50
|
-
<
|
|
50
|
+
<VABlockGridKPI />
|
|
51
51
|
</ClientOnly>
|
|
52
52
|
</UCard>
|
|
53
53
|
</div>
|
|
54
54
|
|
|
55
|
-
<!--
|
|
56
|
-
<h2 class="text-2xl font-semibold mb-4 mt-8">
|
|
55
|
+
<!-- VABlockGridCharts Section -->
|
|
56
|
+
<h2 class="text-2xl font-semibold mb-4 mt-8">VABlockGridCharts</h2>
|
|
57
57
|
<p class="text-gray-600 dark:text-gray-400 mb-4">Charts grid layout block with revenue bar chart and donut chart visualization.</p>
|
|
58
58
|
<div class="mb-8">
|
|
59
59
|
<UCard>
|
|
@@ -61,13 +61,13 @@
|
|
|
61
61
|
<h3 class="font-semibold">Charts Grid Layout</h3>
|
|
62
62
|
</template>
|
|
63
63
|
<ClientOnly>
|
|
64
|
-
<
|
|
64
|
+
<VABlockGridCharts :child-order="[0, 1]" />
|
|
65
65
|
</ClientOnly>
|
|
66
66
|
</UCard>
|
|
67
67
|
</div>
|
|
68
68
|
|
|
69
|
-
<!--
|
|
70
|
-
<h2 class="text-2xl font-semibold mb-4 mt-8">
|
|
69
|
+
<!-- VABlockGridTables Section -->
|
|
70
|
+
<h2 class="text-2xl font-semibold mb-4 mt-8">VABlockGridTables</h2>
|
|
71
71
|
<p class="text-gray-600 dark:text-gray-400 mb-4">Tables grid layout block with latest orders and popular products data.</p>
|
|
72
72
|
<div class="mb-8">
|
|
73
73
|
<UCard>
|
|
@@ -75,7 +75,7 @@
|
|
|
75
75
|
<h3 class="font-semibold">Tables Grid Layout</h3>
|
|
76
76
|
</template>
|
|
77
77
|
<ClientOnly>
|
|
78
|
-
<
|
|
78
|
+
<VABlockGridTables :child-order="[0, 1]" />
|
|
79
79
|
</ClientOnly>
|
|
80
80
|
</UCard>
|
|
81
81
|
</div>
|