@xenterprises/nuxt-x-marketing 1.0.2 → 1.1.0
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/README.md +130 -11
- package/app/components/X/Mark/CodeBlock/index.vue +19 -7
- package/app/components/X/Mark/Divider/Glow.vue +25 -19
- package/app/components/X/Mark/Section/Stitch.vue +45 -31
- package/app/composables/{useParallax.ts → useParallax.js} +6 -7
- package/app/composables/{useScrollReveal.ts → useScrollReveal.js} +4 -4
- package/nuxt.config.ts +1 -11
- package/package.json +1 -1
- package/.claude/settings.local.json +0 -23
- package/.nuxtrc +0 -1
- package/.playground/app.config.ts +0 -74
- package/.playground/app.vue +0 -269
- package/.playground/components/AppFooter.vue +0 -103
- package/.playground/components/AppHeader.vue +0 -41
- package/.playground/components/CodeExample.vue +0 -70
- package/.playground/components/ComponentPlayground.vue +0 -117
- package/.playground/components/DocsHeader.vue +0 -19
- package/.playground/layouts/default.vue +0 -15
- package/.playground/layouts/docs-layout.vue +0 -161
- package/.playground/layouts/docs.vue +0 -11
- package/.playground/nuxt.config.ts +0 -5
- package/.playground/package-lock.json +0 -6
- package/.playground/pages/blog/author.vue +0 -145
- package/.playground/pages/blog/card.vue +0 -149
- package/.playground/pages/blog/cta.vue +0 -131
- package/.playground/pages/blog/detail.vue +0 -471
- package/.playground/pages/blog/list.vue +0 -261
- package/.playground/pages/blog/navigation.vue +0 -228
- package/.playground/pages/blog/sidebar.vue +0 -279
- package/.playground/pages/config.vue +0 -289
- package/.playground/pages/content/comparison.vue +0 -253
- package/.playground/pages/content/cta.vue +0 -245
- package/.playground/pages/content/features.vue +0 -217
- package/.playground/pages/content/newsletter-section.vue +0 -260
- package/.playground/pages/content/newsletter.vue +0 -200
- package/.playground/pages/content/pricing.vue +0 -335
- package/.playground/pages/content/testimonials.vue +0 -188
- package/.playground/pages/hero.vue +0 -257
- package/.playground/pages/index.vue +0 -381
- package/.playground/pages/layout/footer.vue +0 -210
- package/.playground/pages/layout/legal-footer.vue +0 -121
- package/.playground/pages/layout/navbar.vue +0 -285
- package/.playground/pages/layout/section.vue +0 -266
- package/.playground/pages/layout/x-legal.vue +0 -199
- package/.playground/pages/modals/feature-modal.vue +0 -320
- package/.playground/pages/modals/image-lightbox.vue +0 -277
- package/.playground/pages/modals/video-modal.vue +0 -222
- package/.playground/pages/notifications/announcement-bar.vue +0 -164
- package/.playground/pages/notifications/cookie-banner.vue +0 -210
- package/.playground/pages/notifications/cookie-toast.vue +0 -143
- package/.playground/pages/notifications/gdpr.vue +0 -276
- package/.playground/pages/notifications/social-proof-toast.vue +0 -515
- package/.playground/pages/ui/badge.vue +0 -161
- package/.playground/pages/ui/bg-pattern.vue +0 -177
- package/.playground/pages/ui/glass-card.vue +0 -179
- package/.playground/pages/ui/glow-divider.vue +0 -179
- package/.playground/pages/ui/promo-card.vue +0 -259
- package/.playground/pages/ui/section-stitch.vue +0 -411
- package/.playground/pages/utilities/back-to-top.vue +0 -153
- package/.playground/pages/utilities/popup-chat.vue +0 -224
- package/componentList.json +0 -2129
- package/screenshots/playground-home.png +0 -0
- package/tsconfig.json +0 -3
- /package/app/composables/{useXBlog.ts → useXBlog.js} +0 -0
|
@@ -1,143 +0,0 @@
|
|
|
1
|
-
<template>
|
|
2
|
-
<div class="min-h-screen">
|
|
3
|
-
<div class="bg-white dark:bg-neutral-900 border-b border-neutral-200 dark:border-neutral-800 px-8 py-6">
|
|
4
|
-
<h1 class="text-2xl font-bold text-neutral-900 dark:text-white">Cookie Toast</h1>
|
|
5
|
-
<p class="mt-2 text-neutral-600 dark:text-neutral-400">Lightweight cookie consent using Nuxt UI toast notifications.</p>
|
|
6
|
-
</div>
|
|
7
|
-
|
|
8
|
-
<div class="p-8 space-y-12">
|
|
9
|
-
<!-- Demo -->
|
|
10
|
-
<section>
|
|
11
|
-
<h2 class="text-lg font-semibold mb-4">Demo</h2>
|
|
12
|
-
<p class="text-sm text-neutral-500 mb-4">Click to trigger the cookie toast notification</p>
|
|
13
|
-
<div class="flex gap-3">
|
|
14
|
-
<UButton @click="showCookieToast">Show Cookie Toast</UButton>
|
|
15
|
-
<UButton color="neutral" variant="outline" @click="resetToast">Reset</UButton>
|
|
16
|
-
</div>
|
|
17
|
-
<XMarkPrivacyCookieToast v-if="showComponent" />
|
|
18
|
-
</section>
|
|
19
|
-
|
|
20
|
-
<!-- How It Works -->
|
|
21
|
-
<section>
|
|
22
|
-
<h2 class="text-lg font-semibold mb-4">How It Works</h2>
|
|
23
|
-
<p class="text-neutral-600 dark:text-neutral-400 mb-4">
|
|
24
|
-
The CookieToast component uses the Nuxt UI <code class="px-1 py-0.5 bg-neutral-100 dark:bg-neutral-800 rounded text-sm">useToast()</code> composable to show a cookie consent notification.
|
|
25
|
-
</p>
|
|
26
|
-
<div class="bg-neutral-100 dark:bg-neutral-800 rounded-lg p-6">
|
|
27
|
-
<p class="text-sm font-medium mb-2">Preview:</p>
|
|
28
|
-
<div class="bg-white dark:bg-neutral-900 rounded-lg shadow-lg p-4 max-w-sm">
|
|
29
|
-
<div class="flex gap-3">
|
|
30
|
-
<UIcon name="i-lucide-cookie" class="w-5 h-5 text-neutral-600 mt-0.5" />
|
|
31
|
-
<div class="flex-1">
|
|
32
|
-
<h4 class="font-medium text-sm">We use cookies</h4>
|
|
33
|
-
<p class="text-xs text-neutral-500 mt-1">We use cookies to enhance your browsing experience...</p>
|
|
34
|
-
<div class="flex gap-2 mt-3">
|
|
35
|
-
<UButton size="xs">Accept</UButton>
|
|
36
|
-
<UButton size="xs" variant="outline" color="neutral">Decline</UButton>
|
|
37
|
-
</div>
|
|
38
|
-
</div>
|
|
39
|
-
</div>
|
|
40
|
-
</div>
|
|
41
|
-
</div>
|
|
42
|
-
</section>
|
|
43
|
-
|
|
44
|
-
<!-- Usage -->
|
|
45
|
-
<section>
|
|
46
|
-
<h2 class="text-lg font-semibold mb-4">Usage</h2>
|
|
47
|
-
<p class="text-neutral-600 dark:text-neutral-400 mb-4">
|
|
48
|
-
Simply include the component in your layout. It will automatically show on mount if consent hasn't been given.
|
|
49
|
-
</p>
|
|
50
|
-
<pre class="bg-neutral-100 dark:bg-neutral-800 p-4 rounded-lg text-sm overflow-x-auto"><code><template>
|
|
51
|
-
<div>
|
|
52
|
-
<!-- Your page content -->
|
|
53
|
-
<NuxtPage />
|
|
54
|
-
|
|
55
|
-
<!-- Cookie consent toast -->
|
|
56
|
-
<XMarkPrivacyCookieToast />
|
|
57
|
-
</div>
|
|
58
|
-
</template></code></pre>
|
|
59
|
-
</section>
|
|
60
|
-
|
|
61
|
-
<!-- Implementation -->
|
|
62
|
-
<section>
|
|
63
|
-
<h2 class="text-lg font-semibold mb-4">Implementation Details</h2>
|
|
64
|
-
<ul class="space-y-3 text-neutral-600 dark:text-neutral-400">
|
|
65
|
-
<li class="flex gap-2">
|
|
66
|
-
<UIcon name="i-lucide-check" class="w-5 h-5 text-green-500 flex-shrink-0" />
|
|
67
|
-
<span>Uses localStorage key <code class="px-1 py-0.5 bg-neutral-100 dark:bg-neutral-800 rounded text-xs">gdpr-cookies-accepted</code></span>
|
|
68
|
-
</li>
|
|
69
|
-
<li class="flex gap-2">
|
|
70
|
-
<UIcon name="i-lucide-check" class="w-5 h-5 text-green-500 flex-shrink-0" />
|
|
71
|
-
<span>Only shows once per user (persists acceptance)</span>
|
|
72
|
-
</li>
|
|
73
|
-
<li class="flex gap-2">
|
|
74
|
-
<UIcon name="i-lucide-check" class="w-5 h-5 text-green-500 flex-shrink-0" />
|
|
75
|
-
<span>Non-blocking - appears as toast notification</span>
|
|
76
|
-
</li>
|
|
77
|
-
<li class="flex gap-2">
|
|
78
|
-
<UIcon name="i-lucide-check" class="w-5 h-5 text-green-500 flex-shrink-0" />
|
|
79
|
-
<span>Accept and Decline buttons with proper handling</span>
|
|
80
|
-
</li>
|
|
81
|
-
</ul>
|
|
82
|
-
</section>
|
|
83
|
-
|
|
84
|
-
<!-- Comparison -->
|
|
85
|
-
<section>
|
|
86
|
-
<h2 class="text-lg font-semibold mb-4">When to Use</h2>
|
|
87
|
-
<div class="grid md:grid-cols-3 gap-4">
|
|
88
|
-
<div class="p-4 rounded-lg border border-neutral-200 dark:border-neutral-700">
|
|
89
|
-
<h3 class="font-medium mb-2">CookieToast</h3>
|
|
90
|
-
<p class="text-sm text-neutral-500">Minimal, non-intrusive. Best for simple cookie consent without customization options.</p>
|
|
91
|
-
</div>
|
|
92
|
-
<div class="p-4 rounded-lg border border-neutral-200 dark:border-neutral-700">
|
|
93
|
-
<h3 class="font-medium mb-2">CookieBanner</h3>
|
|
94
|
-
<p class="text-sm text-neutral-500">Bottom banner. Good for standard compliance with accept/reject options.</p>
|
|
95
|
-
</div>
|
|
96
|
-
<div class="p-4 rounded-lg border border-neutral-200 dark:border-neutral-700">
|
|
97
|
-
<h3 class="font-medium mb-2">GDPR Modal</h3>
|
|
98
|
-
<p class="text-sm text-neutral-500">Full preferences modal. Required for granular category consent.</p>
|
|
99
|
-
</div>
|
|
100
|
-
</div>
|
|
101
|
-
</section>
|
|
102
|
-
|
|
103
|
-
<!-- Code Example -->
|
|
104
|
-
<section>
|
|
105
|
-
<h2 class="text-lg font-semibold mb-4">Code Example</h2>
|
|
106
|
-
<CodeExample title="Cookie Toast Usage" :code="codeExample" />
|
|
107
|
-
</section>
|
|
108
|
-
</div>
|
|
109
|
-
</div>
|
|
110
|
-
</template>
|
|
111
|
-
|
|
112
|
-
<script setup>
|
|
113
|
-
const codeExample = `<!-- Add to your layout - shows automatically if consent not given -->
|
|
114
|
-
<template>
|
|
115
|
-
<div>
|
|
116
|
-
<NuxtPage />
|
|
117
|
-
<XMarkPrivacyCookieToast />
|
|
118
|
-
</div>
|
|
119
|
-
</template>
|
|
120
|
-
|
|
121
|
-
<!-- The component uses useToast() internally -->
|
|
122
|
-
<!-- It checks localStorage for 'gdpr-cookies-accepted' -->
|
|
123
|
-
<!-- Only shows once per user until they accept/decline -->`
|
|
124
|
-
|
|
125
|
-
const toast = useToast()
|
|
126
|
-
const showComponent = ref(false)
|
|
127
|
-
|
|
128
|
-
const showCookieToast = () => {
|
|
129
|
-
// Reset localStorage and remount component
|
|
130
|
-
localStorage.removeItem('gdpr-cookies-accepted')
|
|
131
|
-
toast.clear()
|
|
132
|
-
showComponent.value = false
|
|
133
|
-
nextTick(() => {
|
|
134
|
-
showComponent.value = true
|
|
135
|
-
})
|
|
136
|
-
}
|
|
137
|
-
|
|
138
|
-
const resetToast = () => {
|
|
139
|
-
localStorage.removeItem('gdpr-cookies-accepted')
|
|
140
|
-
toast.clear()
|
|
141
|
-
showComponent.value = false
|
|
142
|
-
}
|
|
143
|
-
</script>
|
|
@@ -1,276 +0,0 @@
|
|
|
1
|
-
<template>
|
|
2
|
-
<div class="min-h-screen">
|
|
3
|
-
<div class="bg-white dark:bg-neutral-900 border-b border-neutral-200 dark:border-neutral-800 px-8 py-6">
|
|
4
|
-
<h1 class="text-2xl font-bold text-neutral-900 dark:text-white">GDPR Preferences</h1>
|
|
5
|
-
<p class="mt-2 text-neutral-600 dark:text-neutral-400">Detailed cookie consent modal with category toggles.</p>
|
|
6
|
-
</div>
|
|
7
|
-
|
|
8
|
-
<div class="p-8 space-y-12">
|
|
9
|
-
<!-- Demo -->
|
|
10
|
-
<section>
|
|
11
|
-
<h2 class="text-lg font-semibold mb-4">GDPR Modal Demo</h2>
|
|
12
|
-
<p class="text-sm text-neutral-500 mb-4">Click to open the GDPR preferences modal</p>
|
|
13
|
-
<div class="flex gap-3">
|
|
14
|
-
<XMarkPrivacyGDPR
|
|
15
|
-
:categories="categories"
|
|
16
|
-
:button="{ label: 'Open GDPR Preferences', color: 'primary', variant: 'solid' }"
|
|
17
|
-
@accept="handleAccept"
|
|
18
|
-
@reject="handleReject"
|
|
19
|
-
@save="handleSave"
|
|
20
|
-
/>
|
|
21
|
-
<UButton color="neutral" variant="outline" @click="resetPreferences">Reset Preferences</UButton>
|
|
22
|
-
</div>
|
|
23
|
-
</section>
|
|
24
|
-
|
|
25
|
-
<!-- Button Object -->
|
|
26
|
-
<section>
|
|
27
|
-
<h2 class="text-lg font-semibold mb-4">Button Object</h2>
|
|
28
|
-
<p class="text-sm text-neutral-500 mb-4">Configure the trigger button with a single object prop.</p>
|
|
29
|
-
<div class="flex flex-wrap gap-4">
|
|
30
|
-
<XMarkPrivacyGDPR
|
|
31
|
-
:categories="categories"
|
|
32
|
-
:button="{ label: 'Cookie Settings' }"
|
|
33
|
-
/>
|
|
34
|
-
<XMarkPrivacyGDPR
|
|
35
|
-
:categories="categories"
|
|
36
|
-
:button="{ label: 'Privacy Preferences', color: 'primary', icon: 'i-lucide-shield' }"
|
|
37
|
-
/>
|
|
38
|
-
<XMarkPrivacyGDPR
|
|
39
|
-
:categories="categories"
|
|
40
|
-
:button="{ label: 'Manage Cookies', size: 'lg', variant: 'ghost' }"
|
|
41
|
-
/>
|
|
42
|
-
</div>
|
|
43
|
-
</section>
|
|
44
|
-
|
|
45
|
-
<!-- Custom Categories -->
|
|
46
|
-
<section>
|
|
47
|
-
<h2 class="text-lg font-semibold mb-4">Custom Categories</h2>
|
|
48
|
-
<p class="text-sm text-neutral-500 mb-4">Define your own cookie categories.</p>
|
|
49
|
-
<XMarkPrivacyGDPR
|
|
50
|
-
title="Manage Your Privacy"
|
|
51
|
-
description="Choose which types of cookies you want to allow."
|
|
52
|
-
:categories="customCategories"
|
|
53
|
-
privacy-link="/privacy-policy"
|
|
54
|
-
cookie-link="/cookie-policy"
|
|
55
|
-
:button="{ label: 'Custom Categories', color: 'secondary' }"
|
|
56
|
-
@save="handleSave"
|
|
57
|
-
/>
|
|
58
|
-
</section>
|
|
59
|
-
|
|
60
|
-
<!-- Custom Trigger -->
|
|
61
|
-
<section>
|
|
62
|
-
<h2 class="text-lg font-semibold mb-4">Custom Trigger (Slot)</h2>
|
|
63
|
-
<p class="text-sm text-neutral-500 mb-4">Use the default slot for a completely custom trigger.</p>
|
|
64
|
-
<XMarkPrivacyGDPR :categories="categories">
|
|
65
|
-
<UButton size="lg" label="Advanced Cookie Settings" variant="outline" color="neutral" leading-icon="i-lucide-settings" />
|
|
66
|
-
</XMarkPrivacyGDPR>
|
|
67
|
-
</section>
|
|
68
|
-
|
|
69
|
-
<!-- Props -->
|
|
70
|
-
<section>
|
|
71
|
-
<h2 class="text-lg font-semibold mb-4">Props</h2>
|
|
72
|
-
<table class="w-full text-sm">
|
|
73
|
-
<thead>
|
|
74
|
-
<tr class="border-b border-neutral-200 dark:border-neutral-700">
|
|
75
|
-
<th class="text-left py-3 px-4">Prop</th>
|
|
76
|
-
<th class="text-left py-3 px-4">Type</th>
|
|
77
|
-
<th class="text-left py-3 px-4">Default</th>
|
|
78
|
-
<th class="text-left py-3 px-4">Description</th>
|
|
79
|
-
</tr>
|
|
80
|
-
</thead>
|
|
81
|
-
<tbody class="divide-y divide-neutral-200 dark:divide-neutral-700">
|
|
82
|
-
<tr><td class="py-3 px-4 font-mono text-xs">title</td><td class="py-3 px-4">String</td><td class="py-3 px-4">Privacy Preferences</td><td class="py-3 px-4">Modal title</td></tr>
|
|
83
|
-
<tr><td class="py-3 px-4 font-mono text-xs">description</td><td class="py-3 px-4">String</td><td class="py-3 px-4">We use cookies...</td><td class="py-3 px-4">Modal description</td></tr>
|
|
84
|
-
<tr><td class="py-3 px-4 font-mono text-xs">categories</td><td class="py-3 px-4">Array</td><td class="py-3 px-4">[defaults]</td><td class="py-3 px-4">Cookie category definitions</td></tr>
|
|
85
|
-
<tr><td class="py-3 px-4 font-mono text-xs">button</td><td class="py-3 px-4">Object</td><td class="py-3 px-4">{}</td><td class="py-3 px-4">{ label, color, variant, size, icon }</td></tr>
|
|
86
|
-
<tr><td class="py-3 px-4 font-mono text-xs">privacyLink</td><td class="py-3 px-4">String</td><td class="py-3 px-4">/privacy</td><td class="py-3 px-4">Privacy policy URL</td></tr>
|
|
87
|
-
<tr><td class="py-3 px-4 font-mono text-xs">cookieLink</td><td class="py-3 px-4">String</td><td class="py-3 px-4">/cookies</td><td class="py-3 px-4">Cookie policy URL</td></tr>
|
|
88
|
-
<tr><td class="py-3 px-4 font-mono text-xs">storageKey</td><td class="py-3 px-4">String</td><td class="py-3 px-4">gdpr-preferences</td><td class="py-3 px-4">LocalStorage key</td></tr>
|
|
89
|
-
</tbody>
|
|
90
|
-
</table>
|
|
91
|
-
</section>
|
|
92
|
-
|
|
93
|
-
<!-- Button Object Properties -->
|
|
94
|
-
<section>
|
|
95
|
-
<h2 class="text-lg font-semibold mb-4">Button Object Properties</h2>
|
|
96
|
-
<table class="w-full text-sm">
|
|
97
|
-
<thead>
|
|
98
|
-
<tr class="border-b border-neutral-200 dark:border-neutral-700">
|
|
99
|
-
<th class="text-left py-3 px-4">Property</th>
|
|
100
|
-
<th class="text-left py-3 px-4">Type</th>
|
|
101
|
-
<th class="text-left py-3 px-4">Default</th>
|
|
102
|
-
</tr>
|
|
103
|
-
</thead>
|
|
104
|
-
<tbody class="divide-y divide-neutral-200 dark:divide-neutral-700">
|
|
105
|
-
<tr><td class="py-3 px-4 font-mono text-xs">label</td><td class="py-3 px-4">String</td><td class="py-3 px-4">'Cookie Settings'</td></tr>
|
|
106
|
-
<tr><td class="py-3 px-4 font-mono text-xs">color</td><td class="py-3 px-4">String</td><td class="py-3 px-4">'neutral'</td></tr>
|
|
107
|
-
<tr><td class="py-3 px-4 font-mono text-xs">variant</td><td class="py-3 px-4">String</td><td class="py-3 px-4">'outline'</td></tr>
|
|
108
|
-
<tr><td class="py-3 px-4 font-mono text-xs">size</td><td class="py-3 px-4">String</td><td class="py-3 px-4">'md'</td></tr>
|
|
109
|
-
<tr><td class="py-3 px-4 font-mono text-xs">icon</td><td class="py-3 px-4">String</td><td class="py-3 px-4">'i-lucide-cookie'</td></tr>
|
|
110
|
-
</tbody>
|
|
111
|
-
</table>
|
|
112
|
-
</section>
|
|
113
|
-
|
|
114
|
-
<!-- Category Structure -->
|
|
115
|
-
<section>
|
|
116
|
-
<h2 class="text-lg font-semibold mb-4">Category Structure</h2>
|
|
117
|
-
<pre class="bg-neutral-100 dark:bg-neutral-800 p-4 rounded-lg text-sm overflow-x-auto"><code>categories: [
|
|
118
|
-
{
|
|
119
|
-
id: 'necessary', // Unique identifier
|
|
120
|
-
name: 'Necessary', // Display name
|
|
121
|
-
description: 'Essential...', // Description text
|
|
122
|
-
required: true // Cannot be disabled
|
|
123
|
-
},
|
|
124
|
-
{
|
|
125
|
-
id: 'analytics',
|
|
126
|
-
name: 'Analytics',
|
|
127
|
-
description: 'Cookies that help...',
|
|
128
|
-
required: false // User can toggle
|
|
129
|
-
},
|
|
130
|
-
// ... more categories
|
|
131
|
-
]</code></pre>
|
|
132
|
-
</section>
|
|
133
|
-
|
|
134
|
-
<!-- Events -->
|
|
135
|
-
<section>
|
|
136
|
-
<h2 class="text-lg font-semibold mb-4">Events</h2>
|
|
137
|
-
<table class="w-full text-sm">
|
|
138
|
-
<thead>
|
|
139
|
-
<tr class="border-b border-neutral-200 dark:border-neutral-700">
|
|
140
|
-
<th class="text-left py-3 px-4">Event</th>
|
|
141
|
-
<th class="text-left py-3 px-4">Payload</th>
|
|
142
|
-
<th class="text-left py-3 px-4">Description</th>
|
|
143
|
-
</tr>
|
|
144
|
-
</thead>
|
|
145
|
-
<tbody class="divide-y divide-neutral-200 dark:divide-neutral-700">
|
|
146
|
-
<tr><td class="py-3 px-4 font-mono text-xs">@accept</td><td class="py-3 px-4">-</td><td class="py-3 px-4">User clicked Accept All</td></tr>
|
|
147
|
-
<tr><td class="py-3 px-4 font-mono text-xs">@reject</td><td class="py-3 px-4">-</td><td class="py-3 px-4">User clicked Reject All</td></tr>
|
|
148
|
-
<tr><td class="py-3 px-4 font-mono text-xs">@save</td><td class="py-3 px-4">Object</td><td class="py-3 px-4">User saved preferences { categoryId: boolean, ... }</td></tr>
|
|
149
|
-
</tbody>
|
|
150
|
-
</table>
|
|
151
|
-
</section>
|
|
152
|
-
|
|
153
|
-
<!-- Default Categories -->
|
|
154
|
-
<section>
|
|
155
|
-
<h2 class="text-lg font-semibold mb-4">Default Categories</h2>
|
|
156
|
-
<div class="grid md:grid-cols-2 gap-4">
|
|
157
|
-
<div v-for="cat in categories" :key="cat.id" class="p-4 rounded-lg border border-neutral-200 dark:border-neutral-700">
|
|
158
|
-
<div class="flex items-center gap-2 mb-2">
|
|
159
|
-
<h3 class="font-medium">{{ cat.name }}</h3>
|
|
160
|
-
<UBadge v-if="cat.required" label="Required" size="xs" variant="subtle" />
|
|
161
|
-
</div>
|
|
162
|
-
<p class="text-sm text-neutral-500">{{ cat.description }}</p>
|
|
163
|
-
</div>
|
|
164
|
-
</div>
|
|
165
|
-
</section>
|
|
166
|
-
|
|
167
|
-
<!-- Code Example -->
|
|
168
|
-
<section>
|
|
169
|
-
<h2 class="text-lg font-semibold mb-4">Code Example</h2>
|
|
170
|
-
<CodeExample title="GDPR Preferences Usage" :code="codeExample" />
|
|
171
|
-
</section>
|
|
172
|
-
</div>
|
|
173
|
-
</div>
|
|
174
|
-
</template>
|
|
175
|
-
|
|
176
|
-
<script setup>
|
|
177
|
-
const codeExample = `<!-- With button trigger (object) -->
|
|
178
|
-
<XMarkPrivacyGDPR
|
|
179
|
-
:categories="categories"
|
|
180
|
-
:button="{ label: 'Cookie Settings', color: 'neutral', icon: 'i-lucide-cookie' }"
|
|
181
|
-
@accept="handleAcceptAll"
|
|
182
|
-
@reject="handleRejectAll"
|
|
183
|
-
@save="handleSavePreferences"
|
|
184
|
-
/>
|
|
185
|
-
|
|
186
|
-
<!-- With custom categories -->
|
|
187
|
-
<XMarkPrivacyGDPR
|
|
188
|
-
title="Manage Your Privacy"
|
|
189
|
-
description="Choose which cookies you want to allow."
|
|
190
|
-
:categories="[
|
|
191
|
-
{ id: 'necessary', name: 'Necessary', description: 'Essential cookies.', required: true },
|
|
192
|
-
{ id: 'analytics', name: 'Analytics', description: 'Help us understand usage.', required: false },
|
|
193
|
-
{ id: 'marketing', name: 'Marketing', description: 'Used for ads.', required: false }
|
|
194
|
-
]"
|
|
195
|
-
privacy-link="/privacy"
|
|
196
|
-
cookie-link="/cookies"
|
|
197
|
-
:button="{ label: 'Privacy Settings', icon: 'i-lucide-shield' }"
|
|
198
|
-
@save="prefs => console.log(prefs)"
|
|
199
|
-
/>
|
|
200
|
-
|
|
201
|
-
<!-- Custom trigger (slot) -->
|
|
202
|
-
<XMarkPrivacyGDPR :categories="categories">
|
|
203
|
-
<UButton size="lg" label="Advanced Settings" leading-icon="i-lucide-settings" />
|
|
204
|
-
</XMarkPrivacyGDPR>`
|
|
205
|
-
|
|
206
|
-
const categories = [
|
|
207
|
-
{
|
|
208
|
-
id: 'necessary',
|
|
209
|
-
name: 'Necessary',
|
|
210
|
-
description: 'Essential cookies required for the website to function properly.',
|
|
211
|
-
required: true
|
|
212
|
-
},
|
|
213
|
-
{
|
|
214
|
-
id: 'analytics',
|
|
215
|
-
name: 'Analytics',
|
|
216
|
-
description: 'Cookies that help us understand how visitors interact with our website.',
|
|
217
|
-
required: false
|
|
218
|
-
},
|
|
219
|
-
{
|
|
220
|
-
id: 'marketing',
|
|
221
|
-
name: 'Marketing',
|
|
222
|
-
description: 'Cookies used for advertising and promotional purposes.',
|
|
223
|
-
required: false
|
|
224
|
-
},
|
|
225
|
-
{
|
|
226
|
-
id: 'preferences',
|
|
227
|
-
name: 'Preferences',
|
|
228
|
-
description: 'Cookies that remember your preferences and settings.',
|
|
229
|
-
required: false
|
|
230
|
-
}
|
|
231
|
-
]
|
|
232
|
-
|
|
233
|
-
const customCategories = [
|
|
234
|
-
{
|
|
235
|
-
id: 'essential',
|
|
236
|
-
name: 'Essential',
|
|
237
|
-
description: 'Core functionality like security and network management.',
|
|
238
|
-
required: true
|
|
239
|
-
},
|
|
240
|
-
{
|
|
241
|
-
id: 'performance',
|
|
242
|
-
name: 'Performance',
|
|
243
|
-
description: 'Help us measure and improve site performance.',
|
|
244
|
-
required: false
|
|
245
|
-
},
|
|
246
|
-
{
|
|
247
|
-
id: 'targeting',
|
|
248
|
-
name: 'Targeting',
|
|
249
|
-
description: 'Used by advertising partners for personalized ads.',
|
|
250
|
-
required: false
|
|
251
|
-
},
|
|
252
|
-
{
|
|
253
|
-
id: 'social',
|
|
254
|
-
name: 'Social Media',
|
|
255
|
-
description: 'Enable social sharing features and embedded content.',
|
|
256
|
-
required: false
|
|
257
|
-
}
|
|
258
|
-
]
|
|
259
|
-
|
|
260
|
-
const resetPreferences = () => {
|
|
261
|
-
localStorage.removeItem('gdpr-preferences')
|
|
262
|
-
localStorage.removeItem('cookie-consent')
|
|
263
|
-
}
|
|
264
|
-
|
|
265
|
-
const handleAccept = () => {
|
|
266
|
-
console.log('All cookies accepted')
|
|
267
|
-
}
|
|
268
|
-
|
|
269
|
-
const handleReject = () => {
|
|
270
|
-
console.log('Non-essential cookies rejected')
|
|
271
|
-
}
|
|
272
|
-
|
|
273
|
-
const handleSave = (prefs) => {
|
|
274
|
-
console.log('Preferences saved:', prefs)
|
|
275
|
-
}
|
|
276
|
-
</script>
|