@@ -10,23 +10,37 @@ import { dispatchConsentEvent } from "@/lib/analytics/consent-manager"
1010/**
1111 * GDPR-compliant cookie consent banner component
1212 * Handles both the UI and consent event dispatching
13+ * Enhanced with improved visibility and user interaction
1314 */
1415export function CookieConsentWrapper ( ) {
1516 const [ cookieDomain , setCookieDomain ] = useState < string | null > ( null )
17+ const [ isVisible , setIsVisible ] = useState ( false )
1618
1719 useEffect ( ( ) => {
1820 // Get the appropriate domain using tldts
1921 if ( typeof window !== "undefined" ) {
2022 const domain = getDomain ( window . location . hostname )
2123 setCookieDomain ( domain )
2224 }
25+
26+ // Check if consent cookie exists
27+ const cookieExists = document . cookie . includes ( CONSENT_COOKIE_NAME )
28+ if ( ! cookieExists ) {
29+ // Delay showing the banner slightly for better animation effect
30+ const timer = setTimeout ( ( ) => {
31+ setIsVisible ( true )
32+ } , 500 )
33+ return ( ) => clearTimeout ( timer )
34+ }
2335 } , [ ] )
2436
2537 const handleAccept = ( ) => {
38+ setIsVisible ( false )
2639 dispatchConsentEvent ( true )
2740 }
2841
2942 const handleDecline = ( ) => {
43+ setIsVisible ( false )
3044 dispatchConsentEvent ( false )
3145 }
3246
@@ -37,75 +51,134 @@ export function CookieConsentWrapper() {
3751 : { }
3852
3953 const containerClasses = `
40- fixed bottom-2 left-2 right-2 z-[999]
54+ cookie-banner-container
55+ fixed bottom-0 left-0 right-0 z-[999]
4156 bg-black/95 dark:bg-white/95
4257 text-white dark:text-black
43- border-t-neutral-800 dark:border-t-gray-200
58+ border-t-2 border-t- neutral-700 dark:border-t-gray-300
4459 backdrop-blur-xl
45- border-t
60+ shadow-2xl
4661 font-semibold
47- rounded-t-lg
48- px-4 py-4 md:px-8 md:py-4
62+ px-4 py-5 md:px-8 md:py-6
4963 flex flex-wrap items-center justify-between gap-4
50- text-sm font-sans
64+ text-sm md:text-base font-sans
5165 ` . trim ( )
5266
5367 const buttonWrapperClasses = `
5468 flex
5569 flex-row-reverse
5670 items-center
57- gap-2
71+ gap-3
5872 ` . trim ( )
5973
6074 const acceptButtonClasses = `
61- bg-white text-black border-neutral-800
62- dark:bg-black dark:text-white dark:border-gray-200
63- hover:opacity-50
64- transition-opacity
65- rounded-md
66- px-4 py-2 mr-2
67- text-sm font-bold
75+ cookie-accept-button
76+ bg-green-600 text-white
77+ dark:bg-green-500 dark:text-white
78+ hover:bg-green-700 dark:hover:bg-green-600
79+ transition-all duration-200
80+ rounded-lg
81+ px-6 py-2.5 md:px-8 md:py-3
82+ text-sm md:text-base font-bold
6883 cursor-pointer
69- focus:outline-none focus:ring-2 focus:ring-offset-2
84+ shadow-lg hover:shadow-xl
85+ focus:outline-none focus:ring-2 focus:ring-green-500 focus:ring-offset-2
86+ transform hover:scale-105
7087 ` . trim ( )
7188
7289 const declineButtonClasses = `
73- dark:bg-white dark:text-black dark:border-gray-200
74- bg-black text-white border-neutral-800
75- hover:opacity-50
76- border border-border
77- transition-opacity
78- rounded-md
79- px-4 py-2
80- text-sm font-bold
90+ dark:bg-gray-200 dark:text-gray-800 dark:border-gray-300
91+ bg-gray-800 text-gray-200 border-gray-600
92+ hover:bg-gray-700 dark:hover:bg-gray-300
93+ border-2
94+ transition-all duration-200
95+ rounded-lg
96+ px-4 py-2.5 md:px-6 md:py-3
97+ text-sm md:text-base font-bold
8198 cursor-pointer
82- focus:outline-none focus:ring-2 focus:ring-offset-2
99+ focus:outline-none focus:ring-2 focus:ring-gray-500 focus:ring- offset-2
83100 ` . trim ( )
84101
102+ // Don't render anything if not visible
103+ if ( ! isVisible ) {
104+ return null
105+ }
106+
85107 return (
86- < div role = "banner" aria-label = "Cookie consent banner" aria-live = "polite" >
87- < ReactCookieConsent
88- location = "bottom"
89- buttonText = "Accept"
90- declineButtonText = "Decline"
91- cookieName = { CONSENT_COOKIE_NAME }
92- expires = { 365 }
93- enableDeclineButton = { true }
94- onAccept = { handleAccept }
95- onDecline = { handleDecline }
96- containerClasses = { containerClasses }
97- buttonClasses = { acceptButtonClasses }
98- buttonWrapperClasses = { buttonWrapperClasses }
99- declineButtonClasses = { declineButtonClasses }
100- extraCookieOptions = { extraCookieOptions }
101- disableStyles = { true }
102- ariaAcceptLabel = { `Accept` }
103- ariaDeclineLabel = { `Decline` } >
104- < div className = "flex items-center gap-2" >
105- < Cookie className = "size-5 hidden md:block" />
106- < span > Like most of the internet, we use cookies. Are you OK with that?</ span >
107- </ div >
108- </ ReactCookieConsent >
109- </ div >
108+ < >
109+ { /* Backdrop overlay */ }
110+ < div
111+ className = "fixed inset-0 bg-black/30 dark:bg-black/20 z-[998] backdrop-blur-[2px]"
112+ style = { {
113+ animation : "fadeIn 0.3s ease-out" ,
114+ } }
115+ />
116+
117+ { /* Banner */ }
118+ < div role = "banner" aria-label = "Cookie consent banner" aria-live = "polite" >
119+ < style
120+ dangerouslySetInnerHTML = { {
121+ __html : `
122+ @keyframes slideUp {
123+ from {
124+ transform: translateY(100%);
125+ opacity: 0;
126+ }
127+ to {
128+ transform: translateY(0);
129+ opacity: 1;
130+ }
131+ }
132+ @keyframes fadeIn {
133+ from {
134+ opacity: 0;
135+ }
136+ to {
137+ opacity: 1;
138+ }
139+ }
140+ @keyframes pulse {
141+ 0%, 100% {
142+ box-shadow: 0 0 0 0 rgba(34, 197, 94, 0.4);
143+ }
144+ 50% {
145+ box-shadow: 0 0 0 8px rgba(34, 197, 94, 0);
146+ }
147+ }
148+ .cookie-banner-container {
149+ animation: slideUp 0.4s ease-out;
150+ }
151+ .cookie-accept-button {
152+ animation: pulse 2s infinite;
153+ }
154+ ` ,
155+ } }
156+ />
157+ < ReactCookieConsent
158+ location = "bottom"
159+ buttonText = "Accept Cookies"
160+ declineButtonText = "Decline"
161+ cookieName = { CONSENT_COOKIE_NAME }
162+ expires = { 365 }
163+ enableDeclineButton = { true }
164+ onAccept = { handleAccept }
165+ onDecline = { handleDecline }
166+ containerClasses = { containerClasses }
167+ buttonClasses = { acceptButtonClasses }
168+ buttonWrapperClasses = { buttonWrapperClasses }
169+ declineButtonClasses = { declineButtonClasses }
170+ extraCookieOptions = { extraCookieOptions }
171+ disableStyles = { true }
172+ ariaAcceptLabel = "Accept all cookies"
173+ ariaDeclineLabel = "Decline non-essential cookies" >
174+ < div className = "flex items-center gap-3" >
175+ < Cookie className = "size-6 md:size-7 flex-shrink-0" />
176+ < span className = "leading-relaxed" >
177+ Like most of the internet, we use cookies to enhance your experience. Are you OK with that?
178+ </ span >
179+ </ div >
180+ </ ReactCookieConsent >
181+ </ div >
182+ </ >
110183 )
111184}
0 commit comments