From 5adada0422e1a4932e81c9250a19832aed6d436f Mon Sep 17 00:00:00 2001 From: maotovisk Date: Fri, 8 Aug 2025 15:31:36 -0300 Subject: [PATCH] add(frontend): remove htmx import and add animations --- web/resources/css/input.css | 128 +++++ web/static/css/output.css | 846 ++++++++++++++++++++++++++++++- web/templates/layouts/main.templ | 5 +- web/templates/pages/home.templ | 339 ++++++++++++- 4 files changed, 1285 insertions(+), 33 deletions(-) diff --git a/web/resources/css/input.css b/web/resources/css/input.css index d91314f..bd42c8c 100644 --- a/web/resources/css/input.css +++ b/web/resources/css/input.css @@ -140,3 +140,131 @@ "calt" 1; } } + +@layer utilities { + /* Custom animations for the URL shortener */ + + @keyframes pulse-slow { + 0%, 100% { + opacity: 1; + } + 50% { + opacity: 0.7; + } + } + + @keyframes bounce-in { + 0% { + transform: scale(0.3); + opacity: 0; + } + 50% { + transform: scale(1.05); + } + 70% { + transform: scale(0.9); + } + 100% { + transform: scale(1); + opacity: 1; + } + } + + @keyframes slide-up { + from { + opacity: 0; + transform: translateY(30px); + } + to { + opacity: 1; + transform: translateY(0); + } + } + + @keyframes fade-in-scale { + from { + opacity: 0; + transform: scale(0.95); + } + to { + opacity: 1; + transform: scale(1); + } + } + + @keyframes success-pulse { + 0% { + transform: scale(1); + box-shadow: 0 0 0 0 rgb(34, 197, 94, 0.7); + } + 70% { + transform: scale(1.05); + box-shadow: 0 0 0 10px rgb(34, 197, 94, 0); + } + 100% { + transform: scale(1); + box-shadow: 0 0 0 0 rgb(34, 197, 94, 0); + } + } + + @keyframes confetti-fall { + 0% { + opacity: 1; + transform: translate(-50%, -50%) translateX(0) translateY(0) rotateZ(0deg); + } + 100% { + opacity: 0; + transform: translate(-50%, -50%) translateX(var(--end-x)) translateY(var(--end-y)) rotateZ(var(--rotation)); + } + } + + @keyframes celebrate-bounce { + 0%, 20%, 50%, 80%, 100% { + transform: translateY(0); + } + 40% { + transform: translateY(-10px); + } + 60% { + transform: translateY(-5px); + } + } + + .animate-pulse-slow { + animation: pulse-slow 3s ease-in-out infinite; + } + + .animate-bounce-in { + animation: bounce-in 0.6s ease-out; + } + + .animate-slide-up { + animation: slide-up 0.5s ease-out; + } + + .animate-fade-in-scale { + animation: fade-in-scale 0.4s ease-out; + } + + .animate-success-pulse { + animation: success-pulse 0.6s ease-out; + } + + .animate-celebrate-bounce { + animation: celebrate-bounce 1s ease-in-out; + } + + body.success-animation h2 { + animation: celebrate-bounce 1s ease-in-out; + } + + .delay-100 { animation-delay: 100ms; } + .delay-200 { animation-delay: 200ms; } + .delay-300 { animation-delay: 300ms; } + .delay-400 { animation-delay: 400ms; } + .delay-500 { animation-delay: 500ms; } + .delay-600 { animation-delay: 600ms; } + .delay-700 { animation-delay: 700ms; } + .delay-800 { animation-delay: 800ms; } + .delay-900 { animation-delay: 900ms; } +} diff --git a/web/static/css/output.css b/web/static/css/output.css index e42d8e6..d5c8eaf 100644 --- a/web/static/css/output.css +++ b/web/static/css/output.css @@ -7,12 +7,50 @@ "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji"; --font-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace; + --color-red-50: oklch(97.1% 0.013 17.38); + --color-red-300: oklch(80.8% 0.114 19.571); + --color-red-400: oklch(70.4% 0.191 22.216); --color-red-500: oklch(63.7% 0.237 25.331); + --color-red-600: oklch(57.7% 0.245 27.325); + --color-red-800: oklch(44.4% 0.177 26.899); + --color-red-900: oklch(39.6% 0.141 25.723); + --color-red-950: oklch(25.8% 0.092 26.042); + --color-amber-50: oklch(98.7% 0.022 95.277); + --color-amber-300: oklch(87.9% 0.169 91.605); + --color-amber-400: oklch(82.8% 0.189 84.429); + --color-amber-600: oklch(66.6% 0.179 58.318); + --color-amber-800: oklch(47.3% 0.137 46.201); + --color-amber-900: oklch(41.4% 0.112 45.904); + --color-amber-950: oklch(27.9% 0.077 45.635); --color-yellow-500: oklch(79.5% 0.184 86.047); + --color-green-50: oklch(98.2% 0.018 155.826); --color-green-500: oklch(72.3% 0.219 149.579); + --color-green-950: oklch(26.6% 0.065 152.934); + --color-emerald-50: oklch(97.9% 0.021 166.113); + --color-emerald-100: oklch(95% 0.052 163.051); + --color-emerald-300: oklch(84.5% 0.143 164.978); + --color-emerald-400: oklch(76.5% 0.177 163.223); + --color-emerald-500: oklch(69.6% 0.17 162.48); + --color-emerald-600: oklch(59.6% 0.145 163.225); + --color-emerald-700: oklch(50.8% 0.118 165.612); + --color-emerald-800: oklch(43.2% 0.095 166.913); + --color-emerald-900: oklch(37.8% 0.077 168.94); + --color-emerald-950: oklch(26.2% 0.051 172.552); + --color-sky-50: oklch(97.7% 0.013 236.62); + --color-sky-300: oklch(82.8% 0.111 230.318); + --color-sky-400: oklch(74.6% 0.16 232.661); + --color-sky-600: oklch(58.8% 0.158 241.966); + --color-sky-800: oklch(44.3% 0.11 240.79); + --color-sky-900: oklch(39.1% 0.09 240.876); + --color-sky-950: oklch(29.3% 0.066 243.157); --color-blue-500: oklch(62.3% 0.214 259.815); --color-gray-300: oklch(87.2% 0.01 258.338); --color-gray-500: oklch(55.1% 0.027 264.364); + --color-zinc-50: oklch(98.5% 0 0); + --color-zinc-200: oklch(92% 0.004 286.32); + --color-zinc-800: oklch(27.4% 0.006 286.033); + --color-zinc-900: oklch(21% 0.006 285.885); + --color-white: #fff; --spacing: 0.25rem; --container-2xl: 42rem; --text-sm: 0.875rem; @@ -26,7 +64,12 @@ --font-weight-medium: 500; --font-weight-semibold: 600; --font-weight-bold: 700; + --radius-2xl: 1rem; + --ease-in: cubic-bezier(0.4, 0, 1, 1); --ease-out: cubic-bezier(0, 0, 0.2, 1); + --animate-spin: spin 1s linear infinite; + --animate-pulse: pulse 2s cubic-bezier(0.4, 0, 0.6, 1) infinite; + --blur-sm: 8px; --default-transition-duration: 150ms; --default-transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1); --default-font-family: var(--font-sans); @@ -182,6 +225,9 @@ .pointer-events-auto { pointer-events: auto; } + .pointer-events-none { + pointer-events: none; + } .collapse { visibility: collapse; } @@ -203,24 +249,30 @@ .top-0 { top: calc(var(--spacing) * 0); } - .top-1 { - top: calc(var(--spacing) * 1); - } .top-1\/2 { top: calc(1/2 * 100%); } + .top-2 { + top: calc(var(--spacing) * 2); + } .right-0 { right: calc(var(--spacing) * 0); } + .right-2 { + right: calc(var(--spacing) * 2); + } + .right-4 { + right: calc(var(--spacing) * 4); + } .bottom-0 { bottom: calc(var(--spacing) * 0); } + .bottom-4 { + bottom: calc(var(--spacing) * 4); + } .left-0 { left: calc(var(--spacing) * 0); } - .left-1 { - left: calc(var(--spacing) * 1); - } .left-1\/2 { left: calc(1/2 * 100%); } @@ -251,11 +303,14 @@ max-width: 96rem; } } + .mt-0\.5 { + margin-top: calc(var(--spacing) * 0.5); + } .mt-1 { margin-top: calc(var(--spacing) * 1); } - .mt-4 { - margin-top: calc(var(--spacing) * 4); + .mt-2 { + margin-top: calc(var(--spacing) * 2); } .mr-3 { margin-right: calc(var(--spacing) * 3); @@ -288,6 +343,12 @@ .h-1 { height: calc(var(--spacing) * 1); } + .h-4 { + height: calc(var(--spacing) * 4); + } + .h-5 { + height: calc(var(--spacing) * 5); + } .h-6 { height: calc(var(--spacing) * 6); } @@ -306,12 +367,27 @@ .h-full { height: 100%; } + .min-h-full { + min-height: 100%; + } + .w-4 { + width: calc(var(--spacing) * 4); + } + .w-5 { + width: calc(var(--spacing) * 5); + } .w-6 { width: calc(var(--spacing) * 6); } + .w-8 { + width: calc(var(--spacing) * 8); + } .w-24 { width: calc(var(--spacing) * 24); } + .w-\[min\(380px\,92vw\)\] { + width: min(380px, 92vw); + } .w-full { width: 100%; } @@ -324,9 +400,6 @@ .flex-1 { flex: 1; } - .flex-shrink { - flex-shrink: 1; - } .flex-shrink-0 { flex-shrink: 0; } @@ -336,19 +409,16 @@ .shrink-0 { flex-shrink: 0; } - .border-collapse { - border-collapse: collapse; - } - .-translate-x-1 { - --tw-translate-x: calc(var(--spacing) * -1); - translate: var(--tw-translate-x) var(--tw-translate-y); - } .-translate-x-1\/2 { --tw-translate-x: calc(calc(1/2 * 100%) * -1); translate: var(--tw-translate-x) var(--tw-translate-y); } - .-translate-y-1 { - --tw-translate-y: calc(var(--spacing) * -1); + .translate-x-0 { + --tw-translate-x: calc(var(--spacing) * 0); + translate: var(--tw-translate-x) var(--tw-translate-y); + } + .translate-x-4 { + --tw-translate-x: calc(var(--spacing) * 4); translate: var(--tw-translate-x) var(--tw-translate-y); } .-translate-y-1\/2 { @@ -359,16 +429,61 @@ --tw-translate-y: calc(var(--spacing) * -4); translate: var(--tw-translate-x) var(--tw-translate-y); } + .translate-y-0 { + --tw-translate-y: calc(var(--spacing) * 0); + translate: var(--tw-translate-x) var(--tw-translate-y); + } + .translate-y-2 { + --tw-translate-y: calc(var(--spacing) * 2); + translate: var(--tw-translate-x) var(--tw-translate-y); + } .translate-y-4 { --tw-translate-y: calc(var(--spacing) * 4); translate: var(--tw-translate-x) var(--tw-translate-y); } + .translate-y-8 { + --tw-translate-y: calc(var(--spacing) * 8); + translate: var(--tw-translate-x) var(--tw-translate-y); + } + .scale-0 { + --tw-scale-x: 0%; + --tw-scale-y: 0%; + --tw-scale-z: 0%; + scale: var(--tw-scale-x) var(--tw-scale-y); + } + .scale-95 { + --tw-scale-x: 95%; + --tw-scale-y: 95%; + --tw-scale-z: 95%; + scale: var(--tw-scale-x) var(--tw-scale-y); + } + .scale-100 { + --tw-scale-x: 100%; + --tw-scale-y: 100%; + --tw-scale-z: 100%; + scale: var(--tw-scale-x) var(--tw-scale-y); + } .scale-3d { scale: var(--tw-scale-x) var(--tw-scale-y) var(--tw-scale-z); } + .scale-\[0\.98\] { + scale: 0.98; + } + .rotate-0 { + rotate: 0deg; + } + .rotate-180 { + rotate: 180deg; + } .transform { transform: var(--tw-rotate-x,) var(--tw-rotate-y,) var(--tw-rotate-z,) var(--tw-skew-x,) var(--tw-skew-y,); } + .animate-pulse { + animation: var(--animate-pulse); + } + .animate-spin { + animation: var(--animate-spin); + } .cursor-not-allowed { cursor: not-allowed; } @@ -390,9 +505,15 @@ .flex-col { flex-direction: column; } + .flex-col-reverse { + flex-direction: column-reverse; + } .items-center { align-items: center; } + .items-end { + align-items: flex-end; + } .justify-between { justify-content: space-between; } @@ -408,9 +529,29 @@ .gap-2 { gap: calc(var(--spacing) * 2); } + .gap-3 { + gap: calc(var(--spacing) * 3); + } .gap-4 { gap: calc(var(--spacing) * 4); } + .gap-6 { + gap: calc(var(--spacing) * 6); + } + .space-y-2 { + :where(& > :not(:last-child)) { + --tw-space-y-reverse: 0; + margin-block-start: calc(calc(var(--spacing) * 2) * var(--tw-space-y-reverse)); + margin-block-end: calc(calc(var(--spacing) * 2) * calc(1 - var(--tw-space-y-reverse))); + } + } + .space-y-4 { + :where(& > :not(:last-child)) { + --tw-space-y-reverse: 0; + margin-block-start: calc(calc(var(--spacing) * 4) * var(--tw-space-y-reverse)); + margin-block-end: calc(calc(var(--spacing) * 4) * calc(1 - var(--tw-space-y-reverse))); + } + } .truncate { overflow: hidden; text-overflow: ellipsis; @@ -419,6 +560,15 @@ .overflow-hidden { overflow: hidden; } + .rounded { + border-radius: 0.25rem; + } + .rounded-2xl { + border-radius: var(--radius-2xl); + } + .rounded-full { + border-radius: calc(infinity * 1px); + } .rounded-lg { border-radius: var(--radius); } @@ -429,21 +579,71 @@ border-style: var(--tw-border-style); border-width: 1px; } + .border-b { + border-bottom-style: var(--tw-border-style); + border-bottom-width: 1px; + } + .border-dashed { + --tw-border-style: dashed; + border-style: dashed; + } + .border-amber-300\/40 { + border-color: color-mix(in srgb, oklch(87.9% 0.169 91.605) 40%, transparent); + @supports (color: color-mix(in lab, red, red)) { + border-color: color-mix(in oklab, var(--color-amber-300) 40%, transparent); + } + } .border-destructive { border-color: var(--destructive); } + .border-emerald-300\/40 { + border-color: color-mix(in srgb, oklch(84.5% 0.143 164.978) 40%, transparent); + @supports (color: color-mix(in lab, red, red)) { + border-color: color-mix(in oklab, var(--color-emerald-300) 40%, transparent); + } + } .border-input { border-color: var(--input); } + .border-red-300\/40 { + border-color: color-mix(in srgb, oklch(80.8% 0.114 19.571) 40%, transparent); + @supports (color: color-mix(in lab, red, red)) { + border-color: color-mix(in oklab, var(--color-red-300) 40%, transparent); + } + } + .border-sky-300\/40 { + border-color: color-mix(in srgb, oklch(82.8% 0.111 230.318) 40%, transparent); + @supports (color: color-mix(in lab, red, red)) { + border-color: color-mix(in oklab, var(--color-sky-300) 40%, transparent); + } + } + .border-zinc-200 { + border-color: var(--color-zinc-200); + } + .bg-amber-50 { + background-color: var(--color-amber-50); + } .bg-background { background-color: var(--background); } .bg-blue-500 { background-color: var(--color-blue-500); } + .bg-card { + background-color: var(--card); + } .bg-destructive { background-color: var(--destructive); } + .bg-emerald-50 { + background-color: var(--color-emerald-50); + } + .bg-emerald-100 { + background-color: var(--color-emerald-100); + } + .bg-emerald-500 { + background-color: var(--color-emerald-500); + } .bg-gray-300 { background-color: var(--color-gray-300); } @@ -453,27 +653,69 @@ .bg-green-500 { background-color: var(--color-green-500); } + .bg-muted\/30 { + background-color: var(--muted); + @supports (color: color-mix(in lab, red, red)) { + background-color: color-mix(in oklab, var(--muted) 30%, transparent); + } + } + .bg-muted\/50 { + background-color: var(--muted); + @supports (color: color-mix(in lab, red, red)) { + background-color: color-mix(in oklab, var(--muted) 50%, transparent); + } + } .bg-popover { background-color: var(--popover); } .bg-primary { background-color: var(--primary); } + .bg-red-50 { + background-color: var(--color-red-50); + } .bg-red-500 { background-color: var(--color-red-500); } .bg-secondary { background-color: var(--secondary); } + .bg-sky-50 { + background-color: var(--color-sky-50); + } .bg-transparent { background-color: transparent; } + .bg-white { + background-color: var(--color-white); + } .bg-yellow-500 { background-color: var(--color-yellow-500); } + .bg-gradient-to-r { + --tw-gradient-position: to right in oklab; + background-image: linear-gradient(var(--tw-gradient-stops)); + } + .from-emerald-50 { + --tw-gradient-from: var(--color-emerald-50); + --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position)); + } + .to-green-50 { + --tw-gradient-to: var(--color-green-50); + --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position)); + } + .p-1 { + padding: calc(var(--spacing) * 1); + } + .p-3 { + padding: calc(var(--spacing) * 3); + } .p-4 { padding: calc(var(--spacing) * 4); } + .p-6 { + padding: calc(var(--spacing) * 6); + } .px-3 { padding-inline: calc(var(--spacing) * 3); } @@ -492,15 +734,24 @@ .py-4 { padding-block: calc(var(--spacing) * 4); } + .pt-2 { + padding-top: calc(var(--spacing) * 2); + } .pt-5 { padding-top: calc(var(--spacing) * 5); } .pr-8 { padding-right: calc(var(--spacing) * 8); } + .pr-9 { + padding-right: calc(var(--spacing) * 9); + } .pb-4 { padding-bottom: calc(var(--spacing) * 4); } + .font-mono { + font-family: var(--font-mono); + } .text-4xl { font-size: var(--text-4xl); line-height: var(--tw-leading, var(--text-4xl--line-height)); @@ -517,6 +768,10 @@ font-size: var(--text-xl); line-height: var(--tw-leading, var(--text-xl--line-height)); } + .leading-5 { + --tw-leading: calc(var(--spacing) * 5); + line-height: calc(var(--spacing) * 5); + } .leading-none { --tw-leading: 1; line-height: 1; @@ -533,18 +788,42 @@ --tw-font-weight: var(--font-weight-semibold); font-weight: var(--font-weight-semibold); } + .break-all { + word-break: break-all; + } .whitespace-nowrap { white-space: nowrap; } + .text-amber-600 { + color: var(--color-amber-600); + } + .text-amber-900 { + color: var(--color-amber-900); + } .text-blue-500 { color: var(--color-blue-500); } + .text-card-foreground { + color: var(--card-foreground); + } .text-destructive { color: var(--destructive); } + .text-emerald-600 { + color: var(--color-emerald-600); + } + .text-emerald-700 { + color: var(--color-emerald-700); + } + .text-emerald-900 { + color: var(--color-emerald-900); + } .text-green-500 { color: var(--color-green-500); } + .text-muted-foreground { + color: var(--muted-foreground); + } .text-popover-foreground { color: var(--popover-foreground); } @@ -557,12 +836,27 @@ .text-red-500 { color: var(--color-red-500); } + .text-red-600 { + color: var(--color-red-600); + } + .text-red-900 { + color: var(--color-red-900); + } .text-secondary-foreground { color: var(--secondary-foreground); } + .text-sky-600 { + color: var(--color-sky-600); + } + .text-sky-900 { + color: var(--color-sky-900); + } .text-yellow-500 { color: var(--color-yellow-500); } + .text-zinc-900 { + color: var(--color-zinc-900); + } .italic { font-style: italic; } @@ -575,22 +869,39 @@ .opacity-0 { opacity: 0%; } + .opacity-25 { + opacity: 25%; + } .opacity-50 { opacity: 50%; } + .opacity-70 { + opacity: 70%; + } .opacity-75 { opacity: 75%; } + .opacity-80 { + opacity: 80%; + } .opacity-90 { opacity: 90%; } + .opacity-100 { + opacity: 100%; + } + .shadow-md { + --tw-shadow: 0 4px 6px -1px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 2px 4px -2px var(--tw-shadow-color, rgb(0 0 0 / 0.1)); + box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow); + } + .shadow-sm { + --tw-shadow: 0 1px 3px 0 var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 1px 2px -1px var(--tw-shadow-color, rgb(0 0 0 / 0.1)); + box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow); + } .shadow-xs { --tw-shadow: 0 1px 2px 0 var(--tw-shadow-color, rgb(0 0 0 / 0.05)); box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow); } - .ring-destructive { - --tw-ring-color: var(--destructive); - } .ring-destructive\/20 { --tw-ring-color: var(--destructive); @supports (color: color-mix(in lab, red, red)) { @@ -601,6 +912,11 @@ outline-style: var(--tw-outline-style); outline-width: 1px; } + .backdrop-blur-sm { + --tw-backdrop-blur: blur(var(--blur-sm)); + -webkit-backdrop-filter: var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,); + backdrop-filter: var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,); + } .transition { transition-property: color, background-color, border-color, outline-color, text-decoration-color, fill, stroke, --tw-gradient-from, --tw-gradient-via, --tw-gradient-to, opacity, box-shadow, transform, translate, scale, rotate, filter, -webkit-backdrop-filter, backdrop-filter, display, visibility, content-visibility, overlay, pointer-events; transition-timing-function: var(--tw-ease, var(--default-transition-timing-function)); @@ -616,10 +932,52 @@ transition-timing-function: var(--tw-ease, var(--default-transition-timing-function)); transition-duration: var(--tw-duration, var(--default-transition-duration)); } + .transition-colors { + transition-property: color, background-color, border-color, outline-color, text-decoration-color, fill, stroke, --tw-gradient-from, --tw-gradient-via, --tw-gradient-to; + transition-timing-function: var(--tw-ease, var(--default-transition-timing-function)); + transition-duration: var(--tw-duration, var(--default-transition-duration)); + } + .transition-transform { + transition-property: transform, translate, scale, rotate; + transition-timing-function: var(--tw-ease, var(--default-transition-timing-function)); + transition-duration: var(--tw-duration, var(--default-transition-duration)); + } + .delay-50 { + transition-delay: 50ms; + } + .delay-100 { + transition-delay: 100ms; + } + .delay-400 { + transition-delay: 400ms; + } + .delay-500 { + transition-delay: 500ms; + } + .duration-200 { + --tw-duration: 200ms; + transition-duration: 200ms; + } .duration-300 { --tw-duration: 300ms; transition-duration: 300ms; } + .duration-500 { + --tw-duration: 500ms; + transition-duration: 500ms; + } + .duration-700 { + --tw-duration: 700ms; + transition-duration: 700ms; + } + .duration-1000 { + --tw-duration: 1000ms; + transition-duration: 1000ms; + } + .ease-in { + --tw-ease: var(--ease-in); + transition-timing-function: var(--ease-in); + } .ease-out { --tw-ease: var(--ease-out); transition-timing-function: var(--ease-out); @@ -687,6 +1045,33 @@ color: var(--muted-foreground); } } + .hover\:scale-105 { + &:hover { + @media (hover: hover) { + --tw-scale-x: 105%; + --tw-scale-y: 105%; + --tw-scale-z: 105%; + scale: var(--tw-scale-x) var(--tw-scale-y); + } + } + } + .hover\:scale-110 { + &:hover { + @media (hover: hover) { + --tw-scale-x: 110%; + --tw-scale-y: 110%; + --tw-scale-z: 110%; + scale: var(--tw-scale-x) var(--tw-scale-y); + } + } + } + .hover\:scale-\[1\.02\] { + &:hover { + @media (hover: hover) { + scale: 1.02; + } + } + } .hover\:bg-accent { &:hover { @media (hover: hover) { @@ -711,6 +1096,23 @@ } } } + .hover\:bg-emerald-600 { + &:hover { + @media (hover: hover) { + background-color: var(--color-emerald-600); + } + } + } + .hover\:bg-muted\/70 { + &:hover { + @media (hover: hover) { + background-color: var(--muted); + @supports (color: color-mix(in lab, red, red)) { + background-color: color-mix(in oklab, var(--muted) 70%, transparent); + } + } + } + } .hover\:bg-primary\/90 { &:hover { @media (hover: hover) { @@ -738,6 +1140,16 @@ } } } + .hover\:text-primary\/80 { + &:hover { + @media (hover: hover) { + color: var(--primary); + @supports (color: color-mix(in lab, red, red)) { + color: color-mix(in oklab, var(--primary) 80%, transparent); + } + } + } + } .hover\:underline { &:hover { @media (hover: hover) { @@ -752,6 +1164,14 @@ } } } + .hover\:shadow-lg { + &:hover { + @media (hover: hover) { + --tw-shadow: 0 10px 15px -3px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 4px 6px -4px var(--tw-shadow-color, rgb(0 0 0 / 0.1)); + box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow); + } + } + } .focus-visible\:border-ring { &:focus-visible { border-color: var(--ring); @@ -779,6 +1199,14 @@ } } } + .active\:scale-95 { + &:active { + --tw-scale-x: 95%; + --tw-scale-y: 95%; + --tw-scale-z: 95%; + scale: var(--tw-scale-x) var(--tw-scale-y); + } + } .disabled\:pointer-events-none { &:disabled { pointer-events: none; @@ -833,11 +1261,41 @@ line-height: var(--tw-leading, var(--text-sm--line-height)); } } + .dark\:border-amber-800 { + &:where(.dark, .dark *) { + border-color: var(--color-amber-800); + } + } + .dark\:border-emerald-800 { + &:where(.dark, .dark *) { + border-color: var(--color-emerald-800); + } + } .dark\:border-input { &:where(.dark, .dark *) { border-color: var(--input); } } + .dark\:border-red-800 { + &:where(.dark, .dark *) { + border-color: var(--color-red-800); + } + } + .dark\:border-sky-800 { + &:where(.dark, .dark *) { + border-color: var(--color-sky-800); + } + } + .dark\:border-zinc-800 { + &:where(.dark, .dark *) { + border-color: var(--color-zinc-800); + } + } + .dark\:bg-amber-950 { + &:where(.dark, .dark *) { + background-color: var(--color-amber-950); + } + } .dark\:bg-destructive\/60 { &:where(.dark, .dark *) { background-color: var(--destructive); @@ -846,6 +1304,19 @@ } } } + .dark\:bg-emerald-900\/50 { + &:where(.dark, .dark *) { + background-color: color-mix(in srgb, oklch(37.8% 0.077 168.94) 50%, transparent); + @supports (color: color-mix(in lab, red, red)) { + background-color: color-mix(in oklab, var(--color-emerald-900) 50%, transparent); + } + } + } + .dark\:bg-emerald-950 { + &:where(.dark, .dark *) { + background-color: var(--color-emerald-950); + } + } .dark\:bg-input\/30 { &:where(.dark, .dark *) { background-color: var(--input); @@ -854,6 +1325,94 @@ } } } + .dark\:bg-red-950 { + &:where(.dark, .dark *) { + background-color: var(--color-red-950); + } + } + .dark\:bg-sky-950 { + &:where(.dark, .dark *) { + background-color: var(--color-sky-950); + } + } + .dark\:bg-zinc-900 { + &:where(.dark, .dark *) { + background-color: var(--color-zinc-900); + } + } + .dark\:from-emerald-950\/20 { + &:where(.dark, .dark *) { + --tw-gradient-from: color-mix(in srgb, oklch(26.2% 0.051 172.552) 20%, transparent); + @supports (color: color-mix(in lab, red, red)) { + --tw-gradient-from: color-mix(in oklab, var(--color-emerald-950) 20%, transparent); + } + --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position)); + } + } + .dark\:to-green-950\/20 { + &:where(.dark, .dark *) { + --tw-gradient-to: color-mix(in srgb, oklch(26.6% 0.065 152.934) 20%, transparent); + @supports (color: color-mix(in lab, red, red)) { + --tw-gradient-to: color-mix(in oklab, var(--color-green-950) 20%, transparent); + } + --tw-gradient-stops: var(--tw-gradient-via-stops, var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position)); + } + } + .dark\:text-amber-50 { + &:where(.dark, .dark *) { + color: var(--color-amber-50); + } + } + .dark\:text-amber-400 { + &:where(.dark, .dark *) { + color: var(--color-amber-400); + } + } + .dark\:text-emerald-50 { + &:where(.dark, .dark *) { + color: var(--color-emerald-50); + } + } + .dark\:text-emerald-100 { + &:where(.dark, .dark *) { + color: var(--color-emerald-100); + } + } + .dark\:text-emerald-300 { + &:where(.dark, .dark *) { + color: var(--color-emerald-300); + } + } + .dark\:text-emerald-400 { + &:where(.dark, .dark *) { + color: var(--color-emerald-400); + } + } + .dark\:text-red-50 { + &:where(.dark, .dark *) { + color: var(--color-red-50); + } + } + .dark\:text-red-400 { + &:where(.dark, .dark *) { + color: var(--color-red-400); + } + } + .dark\:text-sky-50 { + &:where(.dark, .dark *) { + color: var(--color-sky-50); + } + } + .dark\:text-sky-400 { + &:where(.dark, .dark *) { + color: var(--color-sky-400); + } + } + .dark\:text-zinc-50 { + &:where(.dark, .dark *) { + color: var(--color-zinc-50); + } + } .dark\:ring-destructive\/40 { &:where(.dark, .dark *) { --tw-ring-color: var(--destructive); @@ -1009,6 +1568,135 @@ font-feature-settings: "rlig" 1, "calt" 1; } } +@layer utilities { + @keyframes pulse-slow { + 0%, 100% { + opacity: 1; + } + 50% { + opacity: 0.7; + } + } + @keyframes bounce-in { + 0% { + transform: scale(0.3); + opacity: 0; + } + 50% { + transform: scale(1.05); + } + 70% { + transform: scale(0.9); + } + 100% { + transform: scale(1); + opacity: 1; + } + } + @keyframes slide-up { + from { + opacity: 0; + transform: translateY(30px); + } + to { + opacity: 1; + transform: translateY(0); + } + } + @keyframes fade-in-scale { + from { + opacity: 0; + transform: scale(0.95); + } + to { + opacity: 1; + transform: scale(1); + } + } + @keyframes success-pulse { + 0% { + transform: scale(1); + box-shadow: 0 0 0 0 rgb(34, 197, 94, 0.7); + } + 70% { + transform: scale(1.05); + box-shadow: 0 0 0 10px rgb(34, 197, 94, 0); + } + 100% { + transform: scale(1); + box-shadow: 0 0 0 0 rgb(34, 197, 94, 0); + } + } + @keyframes confetti-fall { + 0% { + opacity: 1; + transform: translate(-50%, -50%) translateX(0) translateY(0) rotateZ(0deg); + } + 100% { + opacity: 0; + transform: translate(-50%, -50%) translateX(var(--end-x)) translateY(var(--end-y)) rotateZ(var(--rotation)); + } + } + @keyframes celebrate-bounce { + 0%, 20%, 50%, 80%, 100% { + transform: translateY(0); + } + 40% { + transform: translateY(-10px); + } + 60% { + transform: translateY(-5px); + } + } + .animate-pulse-slow { + animation: pulse-slow 3s ease-in-out infinite; + } + .animate-bounce-in { + animation: bounce-in 0.6s ease-out; + } + .animate-slide-up { + animation: slide-up 0.5s ease-out; + } + .animate-fade-in-scale { + animation: fade-in-scale 0.4s ease-out; + } + .animate-success-pulse { + animation: success-pulse 0.6s ease-out; + } + .animate-celebrate-bounce { + animation: celebrate-bounce 1s ease-in-out; + } + body.success-animation h2 { + animation: celebrate-bounce 1s ease-in-out; + } + .delay-100 { + animation-delay: 100ms; + } + .delay-200 { + animation-delay: 200ms; + } + .delay-300 { + animation-delay: 300ms; + } + .delay-400 { + animation-delay: 400ms; + } + .delay-500 { + animation-delay: 500ms; + } + .delay-600 { + animation-delay: 600ms; + } + .delay-700 { + animation-delay: 700ms; + } + .delay-800 { + animation-delay: 800ms; + } + .delay-900 { + animation-delay: 900ms; + } +} @property --tw-translate-x { syntax: "*"; inherits: false; @@ -1059,11 +1747,58 @@ syntax: "*"; inherits: false; } +@property --tw-space-y-reverse { + syntax: "*"; + inherits: false; + initial-value: 0; +} @property --tw-border-style { syntax: "*"; inherits: false; initial-value: solid; } +@property --tw-gradient-position { + syntax: "*"; + inherits: false; +} +@property --tw-gradient-from { + syntax: ""; + inherits: false; + initial-value: #0000; +} +@property --tw-gradient-via { + syntax: ""; + inherits: false; + initial-value: #0000; +} +@property --tw-gradient-to { + syntax: ""; + inherits: false; + initial-value: #0000; +} +@property --tw-gradient-stops { + syntax: "*"; + inherits: false; +} +@property --tw-gradient-via-stops { + syntax: "*"; + inherits: false; +} +@property --tw-gradient-from-position { + syntax: ""; + inherits: false; + initial-value: 0%; +} +@property --tw-gradient-via-position { + syntax: ""; + inherits: false; + initial-value: 50%; +} +@property --tw-gradient-to-position { + syntax: ""; + inherits: false; + initial-value: 100%; +} @property --tw-leading { syntax: "*"; inherits: false; @@ -1142,6 +1877,42 @@ inherits: false; initial-value: solid; } +@property --tw-backdrop-blur { + syntax: "*"; + inherits: false; +} +@property --tw-backdrop-brightness { + syntax: "*"; + inherits: false; +} +@property --tw-backdrop-contrast { + syntax: "*"; + inherits: false; +} +@property --tw-backdrop-grayscale { + syntax: "*"; + inherits: false; +} +@property --tw-backdrop-hue-rotate { + syntax: "*"; + inherits: false; +} +@property --tw-backdrop-invert { + syntax: "*"; + inherits: false; +} +@property --tw-backdrop-opacity { + syntax: "*"; + inherits: false; +} +@property --tw-backdrop-saturate { + syntax: "*"; + inherits: false; +} +@property --tw-backdrop-sepia { + syntax: "*"; + inherits: false; +} @property --tw-duration { syntax: "*"; inherits: false; @@ -1150,6 +1921,16 @@ syntax: "*"; inherits: false; } +@keyframes spin { + to { + transform: rotate(360deg); + } +} +@keyframes pulse { + 50% { + opacity: 0.5; + } +} @layer properties { @supports ((-webkit-hyphens: none) and (not (margin-trim: inline))) or ((-moz-orient: inline) and (not (color:rgb(from red r g b)))) { *, ::before, ::after, ::backdrop { @@ -1164,7 +1945,17 @@ --tw-rotate-z: initial; --tw-skew-x: initial; --tw-skew-y: initial; + --tw-space-y-reverse: 0; --tw-border-style: solid; + --tw-gradient-position: initial; + --tw-gradient-from: #0000; + --tw-gradient-via: #0000; + --tw-gradient-to: #0000; + --tw-gradient-stops: initial; + --tw-gradient-via-stops: initial; + --tw-gradient-from-position: 0%; + --tw-gradient-via-position: 50%; + --tw-gradient-to-position: 100%; --tw-leading: initial; --tw-font-weight: initial; --tw-shadow: 0 0 #0000; @@ -1182,6 +1973,15 @@ --tw-ring-offset-color: #fff; --tw-ring-offset-shadow: 0 0 #0000; --tw-outline-style: solid; + --tw-backdrop-blur: initial; + --tw-backdrop-brightness: initial; + --tw-backdrop-contrast: initial; + --tw-backdrop-grayscale: initial; + --tw-backdrop-hue-rotate: initial; + --tw-backdrop-invert: initial; + --tw-backdrop-opacity: initial; + --tw-backdrop-saturate: initial; + --tw-backdrop-sepia: initial; --tw-duration: initial; --tw-ease: initial; } diff --git a/web/templates/layouts/main.templ b/web/templates/layouts/main.templ index a33327a..1ce897e 100644 --- a/web/templates/layouts/main.templ +++ b/web/templates/layouts/main.templ @@ -3,7 +3,6 @@ package layouts import ( "maot-shortner/web/templates/components/input" "maot-shortner/web/templates/components/label" - "maot-shortner/web/templates/components/toast" "maot-shortner/web/templates/modules" ) @@ -17,9 +16,6 @@ templ MainLayout() { @input.Script() @label.Script() - @toast.Script() - -
@@ -28,6 +24,7 @@ templ MainLayout() { { children... }
+ } diff --git a/web/templates/pages/home.templ b/web/templates/pages/home.templ index d0a9502..5291eee 100644 --- a/web/templates/pages/home.templ +++ b/web/templates/pages/home.templ @@ -9,24 +9,351 @@ import ( templ Home() { @layouts.MainLayout() { -
- @icon.Link(icon.Props{Class: "w-24 h-24"}) -

shorten your urls...

-
+ // Componente Alpine +
+
+ @icon.Link(icon.Props{Class: "w-24 h-24"}) +
+

shorten your urls...

+
@input.Input(input.Props{ ID: "URL", Type: input.TypeURL, Placeholder: "https://very-long-url.com/", + Attributes: map[string]any{ + "x-model": "longUrl", + "class": "transition-all duration-300", + ":class": "loading ? 'animate-pulse' : ''", + }, }) @button.Button(button.Props{ ID: "Shorten", Variant: button.VariantGhost, Type: button.TypeSubmit, + Attributes: map[string]any{ + ":disabled": "loading || !isValid", + "class": "disabled:opacity-50", + }, }) { - @icon.Send(icon.Props{Size: 20}) + + @icon.Send(icon.Props{Size: 20}) + + + + + + + Encurtando... + } +
+
+
-
+
+ } }