astro-component-kit 0.0.1 → 0.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 +218 -119
- package/package.json +25 -52
- package/src/components/index.ts +207 -0
- package/src/components/lib/AnimatedGalaxy.astro +185 -0
- package/src/components/lib/Galaxy3D.astro +308 -0
- package/src/components/lib/GlassNavbar.astro +13 -11
- package/src/components/lib/LogoWithGalaxy.astro +63 -0
- package/src/components/lib/buttons/3dPushButton.astro +9 -0
- package/src/components/lib/buttons/AnimatedIconButton.astro +10 -0
- package/src/components/lib/buttons/BorderDrawButton.astro +9 -0
- package/src/components/lib/buttons/CyberpunkButton.astro +10 -0
- package/src/components/lib/buttons/DoubleBorderButton.astro +9 -0
- package/src/components/lib/buttons/GhostOutlineButton.astro +10 -0
- package/src/components/lib/buttons/GlassButton.astro +13 -32
- package/src/components/lib/buttons/GlowButton.astro +9 -0
- package/src/components/lib/buttons/LiquidButton.astro +9 -0
- package/src/components/lib/buttons/LoadingButton.astro +10 -0
- package/src/components/lib/buttons/MagneticButton.astro +10 -0
- package/src/components/lib/buttons/MinimalPillButton.astro +9 -0
- package/src/components/lib/buttons/NeumorphicButton.astro +10 -0
- package/src/components/lib/buttons/PulseButton.astro +10 -0
- package/src/components/lib/buttons/RetroArcadeButton.astro +9 -0
- package/src/components/lib/buttons/RetroShadowButton.astro +9 -0
- package/src/components/lib/buttons/ShimmerButton.astro +9 -0
- package/src/components/lib/buttons/ShinyButton.astro +9 -0
- package/src/components/lib/buttons/TiltGlowButton.astro +10 -0
- package/src/components/lib/cards/BlogHorizontalCard.astro +46 -13
- package/src/components/lib/cards/CyberFeatureCard.astro +50 -6
- package/src/components/lib/cards/EcommerceProductCard.astro +69 -16
- package/src/components/lib/cards/GlassCard.astro +8 -0
- package/src/components/lib/cards/GlassEventCard.astro +53 -12
- package/src/components/lib/cards/GlowPortfolioCard.astro +46 -9
- package/src/components/lib/cards/InteractiveTiltCard.astro +47 -7
- package/src/components/lib/cards/KanbanItemCard.astro +40 -9
- package/src/components/lib/cards/MinimalLinkCard.astro +37 -7
- package/src/components/lib/cards/MusicPlayerMini.astro +54 -14
- package/src/components/lib/cards/NeumorphicCard.astro +32 -2
- package/src/components/lib/cards/NotificationCard.astro +44 -9
- package/src/components/lib/cards/PricingCard.astro +47 -9
- package/src/components/lib/cards/ProfileCard.astro +50 -11
- package/src/components/lib/cards/RetroGameCard.astro +37 -9
- package/src/components/lib/cards/StatCard.astro +43 -8
- package/src/components/lib/cards/TaskKanbanCard.astro +50 -11
- package/src/components/lib/cards/TestimonialCardClean.astro +43 -12
- package/src/components/lib/cards/WeatherWidgetCard.astro +36 -10
- package/src/components/lib/feedback/AnimatedCheckmark.astro +58 -9
- package/src/components/lib/feedback/Badge.astro +47 -12
- package/src/components/lib/feedback/CircleProgress.astro +56 -13
- package/src/components/lib/feedback/ConfettiFeedback.astro +74 -11
- package/src/components/lib/feedback/CyberGlitchAlert.astro +69 -6
- package/src/components/lib/feedback/EmptyStateCard.astro +55 -7
- package/src/components/lib/feedback/GlassAlert.astro +59 -13
- package/src/components/lib/feedback/GlassModal.astro +99 -14
- package/src/components/lib/feedback/GlassProgress.astro +39 -5
- package/src/components/lib/feedback/IndicatorBadgeMinimal.astro +56 -3
- package/src/components/lib/feedback/NeonSpinner.astro +40 -3
- package/src/components/lib/feedback/PulseDot.astro +51 -7
- package/src/components/lib/feedback/RatingPill.astro +38 -8
- package/src/components/lib/feedback/ShakeErrorGroup.astro +44 -3
- package/src/components/lib/feedback/SimpleTooltip.astro +53 -4
- package/src/components/lib/feedback/SkeletonList.astro +59 -13
- package/src/components/lib/feedback/Spotlight.astro +49 -4
- package/src/components/lib/feedback/StepProgress.astro +96 -9
- package/src/components/lib/feedback/ToastNotif.astro +60 -6
- package/src/components/lib/feedback/TypingIndicator.astro +52 -7
- package/src/components/lib/forms/AnimatedInput.astro +47 -5
- package/src/components/lib/forms/ChipInput.astro +116 -8
- package/src/components/lib/forms/ColorPickerInput.astro +53 -6
- package/src/components/lib/forms/CurrencyInput.astro +59 -6
- package/src/components/lib/forms/CustomRadioGroup.astro +61 -9
- package/src/components/lib/forms/CyberpunkCheckbox.astro +64 -8
- package/src/components/lib/forms/DragDropUpload.astro +87 -7
- package/src/components/lib/forms/ErrorInput.astro +31 -4
- package/src/components/lib/forms/FloatingPassword.astro +48 -10
- package/src/components/lib/forms/FormGroupVertical.astro +63 -9
- package/src/components/lib/forms/GlassSlider.astro +84 -3
- package/src/components/lib/forms/GlassTextarea.astro +39 -6
- package/src/components/lib/forms/ModernSelect.astro +66 -10
- package/src/components/lib/forms/NeumorphicSwitch.astro +54 -26
- package/src/components/lib/forms/OTPInput.astro +84 -12
- package/src/components/lib/forms/RatingStars.astro +66 -10
- package/src/components/lib/forms/SearchReveal.astro +44 -6
- package/src/components/lib/forms/SegmentedControl.astro +61 -7
- package/src/components/lib/forms/SimpleFileInput.astro +57 -6
- package/src/components/lib/forms/StepperInput.astro +101 -9
- package/src/components/lib/layout/FeatureHero.astro +70 -6
- package/src/components/lib/layout/FooterCenteredMinimal.astro +5 -2
- package/src/components/lib/navigation/GlassNavbar.astro +10 -5
- package/src/components/lib/navigation/MinimalSidebar.astro +6 -3
- package/src/components/lib/navigation/SimpleFooterGlass.astro +6 -2
- package/src/components/lib/overlays/SplashIntroOverlay.astro +6 -3
- package/src/components/lib/sections/ButtonsShowcase.astro +182 -0
- package/src/components/lib/sections/CardsShowcase.astro +376 -0
- package/src/components/lib/sections/DataShowcase.astro +329 -0
- package/src/components/lib/sections/FeedbackShowcase.astro +320 -0
- package/src/components/lib/sections/FormsShowcase.astro +347 -0
- package/src/components/lib/sections/HeroGlass.astro +202 -0
- package/src/components/lib/sections/HeroGradient.astro +143 -0
- package/src/components/lib/sections/HeroSplit.astro +210 -0
- package/src/components/lib/sections/LayoutShowcase.astro +317 -0
- package/src/components/lib/sections/NavigationShowcase.astro +285 -0
- package/src/components/lib/sections/OverlaysShowcase.astro +373 -0
- package/src/components/lib/sections/TypographyShowcase.astro +239 -0
- package/src/components/lib/sections/index.ts +9 -0
- package/src/components/types.d.ts +6 -0
- package/{dist → src}/styles/global.css +5 -5
- package/dist/AnimatedInput.astro +0 -82
- package/dist/Badge.astro +0 -52
- package/dist/GlassButton.astro +0 -87
- package/dist/GlassCard.astro +0 -72
- package/dist/GlassNavbar.astro +0 -65
- package/dist/GlowButton.astro +0 -60
- package/dist/buttons/3dPushButton.astro +0 -136
- package/dist/buttons/AnimatedIconButton.astro +0 -146
- package/dist/buttons/BorderDrawButton.astro +0 -112
- package/dist/buttons/CyberpunkButton.astro +0 -148
- package/dist/buttons/DoubleBorderButton.astro +0 -131
- package/dist/buttons/GhostOutlineButton.astro +0 -109
- package/dist/buttons/GlassButton.astro +0 -165
- package/dist/buttons/GlowButton.astro +0 -119
- package/dist/buttons/LiquidButton.astro +0 -167
- package/dist/buttons/LoadingButton.astro +0 -148
- package/dist/buttons/MagneticButton.astro +0 -134
- package/dist/buttons/MinimalPillButton.astro +0 -102
- package/dist/buttons/NeumorphicButton.astro +0 -158
- package/dist/buttons/PulseButton.astro +0 -111
- package/dist/buttons/RetroArcadeButton.astro +0 -105
- package/dist/buttons/RetroShadowButton.astro +0 -82
- package/dist/buttons/ShimmerButton.astro +0 -113
- package/dist/buttons/ShinyButton.astro +0 -121
- package/dist/buttons/TiltGlowButton.astro +0 -145
- package/dist/buttons/index.mjs +0 -19
- package/dist/buttons/index.ts +0 -19
- package/dist/cards/BlogHorizontalCard.astro +0 -18
- package/dist/cards/CyberFeatureCard.astro +0 -12
- package/dist/cards/EcommerceProductCard.astro +0 -24
- package/dist/cards/GlassCard.astro +0 -17
- package/dist/cards/GlassEventCard.astro +0 -19
- package/dist/cards/GlowPortfolioCard.astro +0 -16
- package/dist/cards/InteractiveTiltCard.astro +0 -25
- package/dist/cards/KanbanItemCard.astro +0 -15
- package/dist/cards/MinimalLinkCard.astro +0 -12
- package/dist/cards/MusicPlayerMini.astro +0 -21
- package/dist/cards/NeumorphicCard.astro +0 -6
- package/dist/cards/NotificationCard.astro +0 -15
- package/dist/cards/PricingCard.astro +0 -17
- package/dist/cards/ProfileCard.astro +0 -17
- package/dist/cards/RetroGameCard.astro +0 -15
- package/dist/cards/StatCard.astro +0 -15
- package/dist/cards/TaskKanbanCard.astro +0 -18
- package/dist/cards/TestimonialCardClean.astro +0 -20
- package/dist/cards/WeatherWidgetCard.astro +0 -17
- package/dist/cards/index.mjs +0 -19
- package/dist/cards/index.ts +0 -19
- package/dist/data/AccordionGroupGlass.astro +0 -21
- package/dist/data/AvatarGroupStack.astro +0 -15
- package/dist/data/CalendarGridView.astro +0 -18
- package/dist/data/DataChipsGroup.astro +0 -16
- package/dist/data/DescriptionListHoriz.astro +0 -14
- package/dist/data/FileTreeView.astro +0 -22
- package/dist/data/GanttChartMinimal.astro +0 -12
- package/dist/data/GlassTable.astro +0 -23
- package/dist/data/KeyValuePillGroup.astro +0 -12
- package/dist/data/PriceCompareTable.astro +0 -22
- package/dist/data/ProgressListSmall.astro +0 -17
- package/dist/data/RatingBreakdownBar.astro +0 -13
- package/dist/data/SparklineStatCard.astro +0 -16
- package/dist/data/StatsGridDashboard.astro +0 -16
- package/dist/data/StepperDataVertical.astro +0 -15
- package/dist/data/TagCloudData.astro +0 -14
- package/dist/data/TimelineHorizSteps.astro +0 -18
- package/dist/data/TreeItemInteractive.astro +0 -18
- package/dist/data/UserDirectoryItem.astro +0 -15
- package/dist/data/VerticalTimeline.astro +0 -21
- package/dist/data/index.mjs +0 -20
- package/dist/data/index.ts +0 -20
- package/dist/feedback/AnimatedCheckmark.astro +0 -13
- package/dist/feedback/Badge.astro +0 -19
- package/dist/feedback/CircleProgress.astro +0 -22
- package/dist/feedback/ConfettiFeedback.astro +0 -18
- package/dist/feedback/CyberGlitchAlert.astro +0 -11
- package/dist/feedback/EmptyStateCard.astro +0 -13
- package/dist/feedback/GlassAlert.astro +0 -20
- package/dist/feedback/GlassModal.astro +0 -19
- package/dist/feedback/GlassProgress.astro +0 -10
- package/dist/feedback/IndicatorBadgeMinimal.astro +0 -10
- package/dist/feedback/NeonSpinner.astro +0 -7
- package/dist/feedback/PulseDot.astro +0 -12
- package/dist/feedback/RatingPill.astro +0 -13
- package/dist/feedback/ShakeErrorGroup.astro +0 -7
- package/dist/feedback/SimpleTooltip.astro +0 -10
- package/dist/feedback/SkeletonList.astro +0 -20
- package/dist/feedback/Spotlight.astro +0 -9
- package/dist/feedback/StepProgress.astro +0 -14
- package/dist/feedback/ToastNotif.astro +0 -11
- package/dist/feedback/TypingIndicator.astro +0 -12
- package/dist/feedback/index.mjs +0 -20
- package/dist/feedback/index.ts +0 -20
- package/dist/forms/AnimatedInput.astro +0 -16
- package/dist/forms/ChipInput.astro +0 -13
- package/dist/forms/ColorPickerInput.astro +0 -13
- package/dist/forms/CurrencyInput.astro +0 -11
- package/dist/forms/CustomRadioGroup.astro +0 -13
- package/dist/forms/CyberpunkCheckbox.astro +0 -15
- package/dist/forms/DragDropUpload.astro +0 -12
- package/dist/forms/ErrorInput.astro +0 -11
- package/dist/forms/FloatingPassword.astro +0 -20
- package/dist/forms/FormGroupVertical.astro +0 -14
- package/dist/forms/GlassSlider.astro +0 -7
- package/dist/forms/GlassTextarea.astro +0 -14
- package/dist/forms/ModernSelect.astro +0 -16
- package/dist/forms/NeumorphicSwitch.astro +0 -55
- package/dist/forms/OTPInput.astro +0 -22
- package/dist/forms/RatingStars.astro +0 -15
- package/dist/forms/SearchReveal.astro +0 -13
- package/dist/forms/SegmentedControl.astro +0 -13
- package/dist/forms/SimpleFileInput.astro +0 -11
- package/dist/forms/StepperInput.astro +0 -14
- package/dist/forms/index.mjs +0 -20
- package/dist/forms/index.ts +0 -20
- package/dist/index.js +0 -1
- package/dist/index.mjs +0 -1
- package/dist/layout/BentoGrid3.astro +0 -14
- package/dist/layout/CenterFixedBox.astro +0 -6
- package/dist/layout/CenteredContainer.astro +0 -8
- package/dist/layout/ClusterHorizontal.astro +0 -6
- package/dist/layout/FeatureHero.astro +0 -17
- package/dist/layout/FooterCenteredMinimal.astro +0 -11
- package/dist/layout/FullBleedSection.astro +0 -6
- package/dist/layout/GalleryGrid4.astro +0 -7
- package/dist/layout/GlassCardGrid.astro +0 -6
- package/dist/layout/GlassSectionHeader.astro +0 -15
- package/dist/layout/LandingSectionSplit.astro +0 -13
- package/dist/layout/MasonryGrid.astro +0 -7
- package/dist/layout/MinimalFooterGrid.astro +0 -20
- package/dist/layout/ScrollSnapSection.astro +0 -7
- package/dist/layout/SectionDividerText.astro +0 -7
- package/dist/layout/SidebarLayoutWrapper.astro +0 -11
- package/dist/layout/SplitScreenLayout.astro +0 -11
- package/dist/layout/StepLayoutVertical.astro +0 -21
- package/dist/layout/StickySidebarWrapper.astro +0 -10
- package/dist/layout/VerticalStack.astro +0 -8
- package/dist/layout/index.mjs +0 -20
- package/dist/layout/index.ts +0 -20
- package/dist/navigation/AnchorSideNav.astro +0 -13
- package/dist/navigation/BottomNavMobile.astro +0 -13
- package/dist/navigation/BreadcrumbsMinimal.astro +0 -16
- package/dist/navigation/BurgerMorphIcon.astro +0 -12
- package/dist/navigation/CommandPaletteUI.astro +0 -17
- package/dist/navigation/DotNavigationSlider.astro +0 -13
- package/dist/navigation/FloatingTabBar.astro +0 -12
- package/dist/navigation/GlassNavbar.astro +0 -19
- package/dist/navigation/LangSwitcherPill.astro +0 -17
- package/dist/navigation/MegaMenuGlass.astro +0 -25
- package/dist/navigation/MinimalSidebar.astro +0 -18
- package/dist/navigation/PaginationGlass.astro +0 -20
- package/dist/navigation/PaginationInfiniteUI.astro +0 -11
- package/dist/navigation/RadialIconMenu.astro +0 -15
- package/dist/navigation/RetroArcadeMenu.astro +0 -12
- package/dist/navigation/ScrollProgressTop.astro +0 -15
- package/dist/navigation/SimpleFooterGlass.astro +0 -21
- package/dist/navigation/TabUnderline.astro +0 -14
- package/dist/navigation/UserProfileNav.astro +0 -21
- package/dist/navigation/VerticalTabs.astro +0 -14
- package/dist/navigation/index.mjs +0 -20
- package/dist/navigation/index.ts +0 -20
- package/dist/overlays/AgeVerificationOverlay.astro +0 -20
- package/dist/overlays/BackdropBlurMask.astro +0 -6
- package/dist/overlays/BottomSheetMobile.astro +0 -16
- package/dist/overlays/CommandDialog.astro +0 -19
- package/dist/overlays/ContextMenuOverlay.astro +0 -17
- package/dist/overlays/CookieBannerGlass.astro +0 -14
- package/dist/overlays/ExitIntentOverlay.astro +0 -19
- package/dist/overlays/FloatingTrayActions.astro +0 -13
- package/dist/overlays/HelpBubbleOverlay.astro +0 -11
- package/dist/overlays/LightboxOverlay.astro +0 -13
- package/dist/overlays/LoadingOverlayFull.astro +0 -10
- package/dist/overlays/MobileNavOverlay.astro +0 -18
- package/dist/overlays/OverlayModal.astro +0 -24
- package/dist/overlays/PopoverMenuGlass.astro +0 -17
- package/dist/overlays/SearchOverlayFullscreen.astro +0 -15
- package/dist/overlays/SideDrawerRight.astro +0 -16
- package/dist/overlays/SplashIntroOverlay.astro +0 -11
- package/dist/overlays/SpotlightIndicator.astro +0 -6
- package/dist/overlays/ToastStackOverlay.astro +0 -12
- package/dist/overlays/TooltipActionTray.astro +0 -14
- package/dist/overlays/index.mjs +0 -20
- package/dist/overlays/index.ts +0 -20
- package/dist/typography/AnimatedUnderlineLink.astro +0 -10
- package/dist/typography/BackgroundClipMask.astro +0 -7
- package/dist/typography/CodeInlineGlass.astro +0 -6
- package/dist/typography/CyberpunkGlitchText.astro +0 -20
- package/dist/typography/DropCapParagraph.astro +0 -7
- package/dist/typography/FadedVerticalText.astro +0 -6
- package/dist/typography/FloatingTextLabel.astro +0 -10
- package/dist/typography/GlassBlockQuote.astro +0 -13
- package/dist/typography/GlassTextReveal.astro +0 -7
- package/dist/typography/GradientHeading.astro +0 -9
- package/dist/typography/GradientUnderlineLink.astro +0 -7
- package/dist/typography/KbdIndicator.astro +0 -6
- package/dist/typography/LetterSpacingWide.astro +0 -6
- package/dist/typography/MinimalListMarkers.astro +0 -10
- package/dist/typography/MonospaceStatLine.astro +0 -6
- package/dist/typography/NeonTextHighlight.astro +0 -6
- package/dist/typography/ShadowRevealText.astro +0 -7
- package/dist/typography/StrokeHeadingOutline.astro +0 -8
- package/dist/typography/Text3DLayer.astro +0 -7
- package/dist/typography/TypewriterText.astro +0 -15
- package/dist/typography/index.mjs +0 -20
- package/dist/typography/index.ts +0 -20
- package/dist/utilities/AspectRatioBox.astro +0 -11
- package/dist/utilities/BackgroundDotPattern.astro +0 -6
- package/dist/utilities/CircularMask.astro +0 -7
- package/dist/utilities/ClickRippleWrapper.astro +0 -7
- package/dist/utilities/FadeInWrapper.astro +0 -11
- package/dist/utilities/FixedRatioImage.astro +0 -7
- package/dist/utilities/GlassBlurLayer.astro +0 -6
- package/dist/utilities/GradientBorderMask.astro +0 -7
- package/dist/utilities/HoverLift.astro +0 -7
- package/dist/utilities/ResponsiveSpacer.astro +0 -15
- package/dist/utilities/ResponsiveVisToggle.astro +0 -11
- package/dist/utilities/ScrollLockParent.astro +0 -11
- package/dist/utilities/ScrollMarginTarget.astro +0 -10
- package/dist/utilities/SlideUpReveal.astro +0 -7
- package/dist/utilities/SmoothAnchorLink.astro +0 -22
- package/dist/utilities/StackLayering.astro +0 -12
- package/dist/utilities/StickyObserver.astro +0 -8
- package/dist/utilities/TextTruncate.astro +0 -10
- package/dist/utilities/TruncateSingleLine.astro +0 -6
- package/dist/utilities/VisuallyHidden.astro +0 -6
- package/dist/utilities/index.mjs +0 -20
- package/dist/utilities/index.ts +0 -20
- package/src/components/lib/utilities/AspectRatioBox.astro +0 -11
- package/src/components/lib/utilities/BackgroundDotPattern.astro +0 -6
- package/src/components/lib/utilities/CircularMask.astro +0 -7
- package/src/components/lib/utilities/ClickRippleWrapper.astro +0 -7
- package/src/components/lib/utilities/FadeInWrapper.astro +0 -11
- package/src/components/lib/utilities/FixedRatioImage.astro +0 -7
- package/src/components/lib/utilities/GlassBlurLayer.astro +0 -6
- package/src/components/lib/utilities/GradientBorderMask.astro +0 -7
- package/src/components/lib/utilities/HoverLift.astro +0 -7
- package/src/components/lib/utilities/ResponsiveSpacer.astro +0 -15
- package/src/components/lib/utilities/ResponsiveVisToggle.astro +0 -11
- package/src/components/lib/utilities/ScrollLockParent.astro +0 -11
- package/src/components/lib/utilities/ScrollMarginTarget.astro +0 -10
- package/src/components/lib/utilities/SlideUpReveal.astro +0 -7
- package/src/components/lib/utilities/SmoothAnchorLink.astro +0 -22
- package/src/components/lib/utilities/StackLayering.astro +0 -12
- package/src/components/lib/utilities/StickyObserver.astro +0 -8
- package/src/components/lib/utilities/TextTruncate.astro +0 -10
- package/src/components/lib/utilities/TruncateSingleLine.astro +0 -6
- package/src/components/lib/utilities/VisuallyHidden.astro +0 -6
- package/src/components/lib/utilities/index.ts +0 -20
|
@@ -1,15 +1,71 @@
|
|
|
1
1
|
---
|
|
2
|
+
/**
|
|
3
|
+
* CyberpunkCheckbox — A bold, neon-themed checkbox with angular borders and glitch-toggle effect.
|
|
4
|
+
*
|
|
5
|
+
* @param {string} label - Text label displayed alongside the checkbox.
|
|
6
|
+
* @param {string} id - HTML ID for the checkbox.
|
|
7
|
+
* @param {string} name - HTML name binding.
|
|
8
|
+
* @param {boolean} checked - Initial toggle state.
|
|
9
|
+
*/
|
|
10
|
+
interface Props {
|
|
11
|
+
label: string;
|
|
12
|
+
id: string;
|
|
13
|
+
name?: string;
|
|
14
|
+
checked?: boolean;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
const { label, id, name, checked = false } = Astro.props;
|
|
2
18
|
---
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
<
|
|
6
|
-
<
|
|
19
|
+
|
|
20
|
+
<label class="cyber-check" for={id}>
|
|
21
|
+
<input type="checkbox" {id} {name} {checked} />
|
|
22
|
+
<span class="checkmark" aria-hidden="true"></span>
|
|
23
|
+
<span class="cyber-text">{label}</span>
|
|
7
24
|
</label>
|
|
25
|
+
|
|
8
26
|
<style>
|
|
9
|
-
.cyber-check {
|
|
27
|
+
.cyber-check {
|
|
28
|
+
display: flex; align-items: center; gap: var(--sp-4, 1rem);
|
|
29
|
+
cursor: pointer;
|
|
30
|
+
color: var(--c-primary-light, #00e0ff);
|
|
31
|
+
font-family: 'Courier New', Courier, monospace;
|
|
32
|
+
font-weight: 800;
|
|
33
|
+
text-transform: uppercase;
|
|
34
|
+
user-select: none;
|
|
35
|
+
padding: var(--sp-2, 0.5rem);
|
|
36
|
+
transition: 0.2s;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
.cyber-check:hover .checkmark { border-color: var(--c-primary-light); }
|
|
40
|
+
|
|
10
41
|
.cyber-check input { display: none; }
|
|
11
|
-
|
|
12
|
-
.
|
|
13
|
-
|
|
42
|
+
|
|
43
|
+
.checkmark {
|
|
44
|
+
width: 20px; height: 20px;
|
|
45
|
+
border: 2px solid var(--c-primary, #ff003c);
|
|
46
|
+
position: relative; transition: all 0.2s cubic-bezier(0.175, 0.885, 0.32, 1.275);
|
|
47
|
+
flex-shrink: 0;
|
|
48
|
+
clip-path: polygon(10% 0%, 100% 0%, 90% 100%, 0% 100%);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
.cyber-check input:checked + .checkmark {
|
|
52
|
+
background: var(--c-primary, #ff003c);
|
|
53
|
+
box-shadow: 0 0 15px var(--c-primary, #ff003c);
|
|
54
|
+
transform: rotate(5deg) scale(1.1);
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
.checkmark::after {
|
|
58
|
+
content: ''; position: absolute; display: none;
|
|
59
|
+
left: 7px; top: 2px; width: 4px; height: 10px;
|
|
60
|
+
border: solid #fff; border-width: 0 3px 3px 0;
|
|
61
|
+
transform: rotate(45deg);
|
|
62
|
+
}
|
|
63
|
+
|
|
14
64
|
.cyber-check input:checked + .checkmark::after { display: block; }
|
|
65
|
+
|
|
66
|
+
.cyber-text { letter-spacing: 0.05em; font-size: 0.9rem; }
|
|
67
|
+
|
|
68
|
+
.cyber-check input:checked ~ .cyber-text {
|
|
69
|
+
text-shadow: 0 0 8px var(--c-primary-light);
|
|
70
|
+
}
|
|
15
71
|
</style>
|
|
@@ -1,12 +1,92 @@
|
|
|
1
1
|
---
|
|
2
|
+
/**
|
|
3
|
+
* DragDropUpload — A prominent file upload zone with drag-and-drop support and visual feedback.
|
|
4
|
+
*
|
|
5
|
+
* @param {string} label - Primary instruction text. Default is "Drag files here or browse".
|
|
6
|
+
* @param {string} id - HTML ID for the file input.
|
|
7
|
+
* @param {string} name - HTML name binding.
|
|
8
|
+
* @param {string} accept - Allowed file types (e.g. "image/*").
|
|
9
|
+
* @param {boolean} multiple - Enable multiple file selection.
|
|
10
|
+
*/
|
|
11
|
+
interface Props {
|
|
12
|
+
label?: string;
|
|
13
|
+
id: string;
|
|
14
|
+
name?: string;
|
|
15
|
+
accept?: string;
|
|
16
|
+
multiple?: boolean;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
const { label = "Drag files here or browse", id, name, accept, multiple = false } = Astro.props;
|
|
2
20
|
---
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
<
|
|
6
|
-
|
|
21
|
+
|
|
22
|
+
<div class="upload-zone" data-upload-zone>
|
|
23
|
+
<div class="upload-zone__icon" aria-hidden="true">
|
|
24
|
+
<svg width="48" height="48" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round">
|
|
25
|
+
<path d="M21 15v4a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2v-4"/>
|
|
26
|
+
<polyline points="17 8 12 3 7 8"/>
|
|
27
|
+
<line x1="12" y1="3" x2="12" y2="15"/>
|
|
28
|
+
</svg>
|
|
29
|
+
</div>
|
|
30
|
+
<p class="upload-zone__text">
|
|
31
|
+
{label.split('browse').map((part, i) => (
|
|
32
|
+
i === 0 ? <span>{part} <span class="upload-zone__link">browse</span></span> : part
|
|
33
|
+
))}
|
|
34
|
+
</p>
|
|
35
|
+
<input type="file" {id} {name} {accept} {multiple} hidden class="upload-zone__input" data-upload-input />
|
|
7
36
|
</div>
|
|
37
|
+
|
|
8
38
|
<style>
|
|
9
|
-
.upload-zone {
|
|
10
|
-
|
|
11
|
-
|
|
39
|
+
.upload-zone {
|
|
40
|
+
border: 2px dashed var(--c-border, rgba(255,255,255,0.1));
|
|
41
|
+
border-radius: var(--r-xl, 20px);
|
|
42
|
+
padding: var(--sp-12, 3rem);
|
|
43
|
+
text-align: center;
|
|
44
|
+
background: var(--c-bg-elev, rgba(255,255,255,0.02));
|
|
45
|
+
cursor: pointer;
|
|
46
|
+
transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
|
|
47
|
+
color: var(--c-text-2, #94a3b8);
|
|
48
|
+
display: flex;
|
|
49
|
+
flex-direction: column;
|
|
50
|
+
align-items: center;
|
|
51
|
+
gap: var(--sp-4, 1rem);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
.upload-zone:hover, .upload-zone--dragging {
|
|
55
|
+
border-color: var(--c-primary, #6366f1);
|
|
56
|
+
background: rgba(99, 102, 241, 0.05);
|
|
57
|
+
color: var(--c-text-1, #fff);
|
|
58
|
+
transform: translateY(-2px);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
.upload-zone__icon { color: var(--c-primary, #6366f1); transition: transform 0.3s; }
|
|
62
|
+
.upload-zone:hover .upload-zone__icon { transform: translateY(-5px); }
|
|
63
|
+
|
|
64
|
+
.upload-zone__text { font-size: 1rem; margin: 0; }
|
|
65
|
+
.upload-zone__link { color: var(--c-primary, #6366f1); font-weight: 700; text-decoration: underline; text-underline-offset: 4px; }
|
|
12
66
|
</style>
|
|
67
|
+
|
|
68
|
+
<script>
|
|
69
|
+
document.querySelectorAll('[data-upload-zone]').forEach(zone => {
|
|
70
|
+
const input = zone.querySelector('[data-upload-input]') as HTMLInputElement;
|
|
71
|
+
|
|
72
|
+
zone.addEventListener('click', () => input.click());
|
|
73
|
+
|
|
74
|
+
zone.addEventListener('dragover', (e) => {
|
|
75
|
+
e.preventDefault();
|
|
76
|
+
zone.classList.add('upload-zone--dragging');
|
|
77
|
+
});
|
|
78
|
+
|
|
79
|
+
['dragleave', 'drop'].forEach(evt => {
|
|
80
|
+
zone.addEventListener(evt, () => zone.classList.remove('upload-zone--dragging'));
|
|
81
|
+
});
|
|
82
|
+
|
|
83
|
+
zone.addEventListener('drop', (e) => {
|
|
84
|
+
e.preventDefault();
|
|
85
|
+
if ((e as DragEvent).dataTransfer?.files) {
|
|
86
|
+
input.files = (e as DragEvent).dataTransfer!.files;
|
|
87
|
+
// Trigger change
|
|
88
|
+
input.dispatchEvent(new Event('change'));
|
|
89
|
+
}
|
|
90
|
+
});
|
|
91
|
+
});
|
|
92
|
+
</script>
|
|
@@ -1,11 +1,38 @@
|
|
|
1
1
|
---
|
|
2
|
+
/**
|
|
3
|
+
* ErrorInput — A styled input strictly formatted to demonstrate error or invalid validation states.
|
|
4
|
+
*
|
|
5
|
+
* @param {string} id - The ID for the input form element.
|
|
6
|
+
* @param {string} errorMessage - The message text presented below the input field.
|
|
7
|
+
* @param {string} value - Default starting value mimicking failed data.
|
|
8
|
+
* @param {string} placeholder - Optional standard placeholder.
|
|
9
|
+
* @param {string} name - HTML name binding.
|
|
10
|
+
*/
|
|
11
|
+
interface Props {
|
|
12
|
+
id: string;
|
|
13
|
+
errorMessage: string;
|
|
14
|
+
value?: string;
|
|
15
|
+
placeholder?: string;
|
|
16
|
+
name?: string;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
const { id, errorMessage, value = '', placeholder, name } = Astro.props;
|
|
2
20
|
---
|
|
21
|
+
|
|
3
22
|
<div class="error-wrap">
|
|
4
|
-
<input type="text" class="input-error"
|
|
5
|
-
<span class="error-msg">
|
|
23
|
+
<input type="text" {id} {name} {value} {placeholder} class="input-error" aria-invalid="true" aria-describedby={`${id}-error`} />
|
|
24
|
+
<span id={`${id}-error`} class="error-msg" aria-live="polite">{errorMessage}</span>
|
|
6
25
|
</div>
|
|
26
|
+
|
|
7
27
|
<style>
|
|
8
|
-
.error-wrap { display: flex; flex-direction: column; gap: 0.4rem; }
|
|
9
|
-
.input-error {
|
|
28
|
+
.error-wrap { display: flex; flex-direction: column; gap: 0.4rem; width: 100%; box-sizing: border-box; }
|
|
29
|
+
.input-error {
|
|
30
|
+
border: 1px solid var(--c-error, #ef4444) !important;
|
|
31
|
+
background: rgba(239, 68, 68, 0.05) !important;
|
|
32
|
+
padding: var(--sp-3, 0.8rem);
|
|
33
|
+
color: var(--c-text-1, #fff);
|
|
34
|
+
border-radius: var(--r-sm, 10px); outline: none;
|
|
35
|
+
font-family: inherit; font-size: 0.95rem; box-sizing: border-box;
|
|
36
|
+
}
|
|
10
37
|
.error-msg { font-size: 0.75rem; color: #f87171; font-weight: 500; }
|
|
11
38
|
</style>
|
|
@@ -1,20 +1,58 @@
|
|
|
1
1
|
---
|
|
2
|
+
/**
|
|
3
|
+
* FloatingPassword — A password input field featuring a reveal/hide toggle inside the frame.
|
|
4
|
+
*
|
|
5
|
+
* @param {string} id - Unique identifier linking toggle state securely.
|
|
6
|
+
* @param {string} placeholder - Default text visible when empty. Default is "Password".
|
|
7
|
+
* @param {string} name - HTML name binding.
|
|
8
|
+
* @param {boolean} required - HTML required indicator.
|
|
9
|
+
*/
|
|
10
|
+
interface Props {
|
|
11
|
+
id: string;
|
|
12
|
+
placeholder?: string;
|
|
13
|
+
name?: string;
|
|
14
|
+
required?: boolean;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
const { id, placeholder = "Password", name, required = false } = Astro.props;
|
|
2
18
|
---
|
|
19
|
+
|
|
3
20
|
<div class="pass-wrap">
|
|
4
|
-
<input type="password" id
|
|
5
|
-
<button type="button"
|
|
21
|
+
<input type="password" {id} {name} {placeholder} {required} class="pass-input" data-pwd-input />
|
|
22
|
+
<button type="button" class="toggle-pass" aria-label="Toggle password visibility" data-pwd-toggle>👁️</button>
|
|
6
23
|
</div>
|
|
24
|
+
|
|
7
25
|
<style>
|
|
8
26
|
.pass-wrap { position: relative; width: 100%; }
|
|
9
|
-
.pass-
|
|
10
|
-
|
|
27
|
+
.pass-input {
|
|
28
|
+
width: 100%; box-sizing: border-box;
|
|
29
|
+
padding: 0.8rem 3rem 0.8rem 1rem;
|
|
30
|
+
background: var(--c-bg-elev, rgba(0,0,0,0.2));
|
|
31
|
+
border: 1px solid var(--c-border, rgba(255,255,255,0.1));
|
|
32
|
+
border-radius: var(--r-sm, 10px);
|
|
33
|
+
color: var(--c-text-1, #fff); outline: none;
|
|
34
|
+
font-family: inherit; transition: 0.2s;
|
|
35
|
+
}
|
|
36
|
+
.pass-input:focus { border-color: var(--c-primary, #6366f1); }
|
|
37
|
+
.toggle-pass {
|
|
38
|
+
position: absolute; right: 10px; top: 50%; transform: translateY(-50%);
|
|
39
|
+
background: none; border: none; cursor: pointer; opacity: 0.5; transition: 0.2s;
|
|
40
|
+
}
|
|
41
|
+
.toggle-pass:hover { opacity: 1; }
|
|
11
42
|
</style>
|
|
43
|
+
|
|
12
44
|
<script>
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
const
|
|
17
|
-
|
|
18
|
-
btn
|
|
45
|
+
// Setup functional toggle without polluting global namespaces or clashing IDs
|
|
46
|
+
document.querySelectorAll('.pass-wrap').forEach(wrap => {
|
|
47
|
+
const btn = wrap.querySelector('[data-pwd-toggle]');
|
|
48
|
+
const pass = wrap.querySelector('[data-pwd-input]') as HTMLInputElement;
|
|
49
|
+
|
|
50
|
+
if (btn && pass) {
|
|
51
|
+
btn.addEventListener('click', () => {
|
|
52
|
+
const isPass = pass.type === 'password';
|
|
53
|
+
pass.type = isPass ? 'text' : 'password';
|
|
54
|
+
btn.textContent = isPass ? '🙈' : '👁️';
|
|
55
|
+
});
|
|
56
|
+
}
|
|
19
57
|
});
|
|
20
58
|
</script>
|
|
@@ -1,14 +1,68 @@
|
|
|
1
1
|
---
|
|
2
|
+
/**
|
|
3
|
+
* FormGroupVertical — A structural wrapper component for grouping an input with its label and validation messaging.
|
|
4
|
+
*
|
|
5
|
+
* @param {string} label - The descriptive title for the field.
|
|
6
|
+
* @param {string} forId - The target ID of the child input (for label association).
|
|
7
|
+
* @param {string} helpText - Optional secondary guidance text below the input.
|
|
8
|
+
* @param {string} error - Optional error message that applies error styling.
|
|
9
|
+
* @param {boolean} required - Displays a required indicator if true.
|
|
10
|
+
*/
|
|
11
|
+
interface Props {
|
|
12
|
+
label: string;
|
|
13
|
+
forId: string;
|
|
14
|
+
helpText?: string;
|
|
15
|
+
error?: string;
|
|
16
|
+
required?: boolean;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
const { label, forId, helpText, error, required = false } = Astro.props;
|
|
2
20
|
---
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
<
|
|
6
|
-
|
|
21
|
+
|
|
22
|
+
<div class:list={["form-group", { "form-group--error": error }]}>
|
|
23
|
+
<div class="form-group__header">
|
|
24
|
+
<label for={forId} class="form-group__label">
|
|
25
|
+
{label}
|
|
26
|
+
{required && <span class="form-group__req" aria-hidden="true">*</span>}
|
|
27
|
+
</label>
|
|
28
|
+
</div>
|
|
29
|
+
|
|
30
|
+
<div class="form-group__content">
|
|
31
|
+
<slot />
|
|
32
|
+
</div>
|
|
33
|
+
|
|
34
|
+
{error ? (
|
|
35
|
+
<p class="form-group__error" id={`${forId}-error`} role="alert">{error}</p>
|
|
36
|
+
) : helpText ? (
|
|
37
|
+
<p class="form-group__help" id={`${forId}-help`}>{helpText}</p>
|
|
38
|
+
) : null}
|
|
7
39
|
</div>
|
|
40
|
+
|
|
8
41
|
<style>
|
|
9
|
-
.form-group { display: flex; flex-direction: column; gap: 0.5rem; margin-bottom:
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
42
|
+
.form-group { display: flex; flex-direction: column; gap: var(--sp-2, 0.5rem); width: 100%; margin-bottom: var(--sp-4, 1rem); }
|
|
43
|
+
|
|
44
|
+
.form-group__label {
|
|
45
|
+
font-size: 0.8rem; font-weight: 700;
|
|
46
|
+
color: var(--c-text-1, #e2e8f0);
|
|
47
|
+
text-transform: uppercase;
|
|
48
|
+
letter-spacing: 0.05em;
|
|
49
|
+
margin-left: 0.5rem;
|
|
50
|
+
cursor: pointer;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
.form-group__req { color: var(--c-error, #f87171); margin-left: 2px; }
|
|
54
|
+
|
|
55
|
+
.form-group__content { width: 100%; }
|
|
56
|
+
|
|
57
|
+
.form-group__help { font-size: 0.75rem; color: var(--c-text-2, #64748b); margin: 0 0 0 0.5rem; }
|
|
58
|
+
|
|
59
|
+
.form-group__error { font-size: 0.75rem; color: var(--c-error, #f87171); font-weight: 600; margin: 0 0 0 0.5rem; }
|
|
60
|
+
|
|
61
|
+
/* Deep selector to style any input nested inside the group content if it's in an error state */
|
|
62
|
+
.form-group--error :global(input),
|
|
63
|
+
.form-group--error :global(textarea),
|
|
64
|
+
.form-group--error :global(select) {
|
|
65
|
+
border-color: var(--c-error, #ef4444) !important;
|
|
66
|
+
background-color: rgba(239, 68, 68, 0.03) !important;
|
|
67
|
+
}
|
|
14
68
|
</style>
|
|
@@ -1,7 +1,88 @@
|
|
|
1
1
|
---
|
|
2
|
+
/**
|
|
3
|
+
* GlassSlider — A translucent range slider with a glowing thumb and backdrop-blur track.
|
|
4
|
+
*
|
|
5
|
+
* @param {string} label - Optional descriptive text title.
|
|
6
|
+
* @param {string} id - HTML ID for the range input.
|
|
7
|
+
* @param {string} name - HTML name binding.
|
|
8
|
+
* @param {number} min - Minimum value. Default is 0.
|
|
9
|
+
* @param {number} max - Maximum value. Default is 100.
|
|
10
|
+
* @param {number} value - Initial starting value. Default is 50.
|
|
11
|
+
* @param {number} step - Step increment. Default is 1.
|
|
12
|
+
*/
|
|
13
|
+
interface Props {
|
|
14
|
+
label?: string;
|
|
15
|
+
id: string;
|
|
16
|
+
name?: string;
|
|
17
|
+
min?: number;
|
|
18
|
+
max?: number;
|
|
19
|
+
value?: number;
|
|
20
|
+
step?: number;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
const { label, id, name, min = 0, max = 100, value = 50, step = 1 } = Astro.props;
|
|
2
24
|
---
|
|
3
|
-
|
|
25
|
+
|
|
26
|
+
<div class="slider-container">
|
|
27
|
+
{label && <div class="slider-header"><label for={id}>{label}</label> <span data-slider-value>{value}</span></div>}
|
|
28
|
+
<input
|
|
29
|
+
type="range"
|
|
30
|
+
class="glass-slider"
|
|
31
|
+
{id}
|
|
32
|
+
{name}
|
|
33
|
+
{min}
|
|
34
|
+
{max}
|
|
35
|
+
{step}
|
|
36
|
+
{value}
|
|
37
|
+
data-slider-input
|
|
38
|
+
/>
|
|
39
|
+
</div>
|
|
40
|
+
|
|
4
41
|
<style>
|
|
5
|
-
.
|
|
6
|
-
.
|
|
42
|
+
.slider-container { width: 100%; display: flex; flex-direction: column; gap: var(--sp-3, 0.75rem); }
|
|
43
|
+
.slider-header { display: flex; justify-content: space-between; font-size: 0.85rem; font-weight: 600; color: var(--c-text-2, #94a3b8); padding: 0 0.5rem; }
|
|
44
|
+
|
|
45
|
+
.glass-slider {
|
|
46
|
+
-webkit-appearance: none;
|
|
47
|
+
width: 100%; height: 8px;
|
|
48
|
+
background: var(--c-bg-elev, rgba(255,255,255,0.1));
|
|
49
|
+
border-radius: var(--r-full, 10px);
|
|
50
|
+
outline: none;
|
|
51
|
+
backdrop-filter: blur(5px);
|
|
52
|
+
border: 1px solid var(--c-border, rgba(255,255,255,0.05));
|
|
53
|
+
cursor: pointer;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
/* Thumb Styling - Webkit */
|
|
57
|
+
.glass-slider::-webkit-slider-thumb {
|
|
58
|
+
-webkit-appearance: none;
|
|
59
|
+
width: 22px; height: 22px;
|
|
60
|
+
border-radius: 50%;
|
|
61
|
+
background: var(--c-primary, #6366f1);
|
|
62
|
+
cursor: pointer;
|
|
63
|
+
border: 3px solid rgba(255,255,255,0.6);
|
|
64
|
+
box-shadow: 0 4px 15px rgba(99, 102, 241, 0.4);
|
|
65
|
+
transition: transform 0.2s;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
.glass-slider::-webkit-slider-thumb:hover { transform: scale(1.15); }
|
|
69
|
+
|
|
70
|
+
/* Thumb Styling - Firefox */
|
|
71
|
+
.glass-slider::-moz-range-thumb {
|
|
72
|
+
width: 18px; height: 18px;
|
|
73
|
+
border-radius: 50%;
|
|
74
|
+
background: var(--c-primary, #6366f1);
|
|
75
|
+
cursor: pointer;
|
|
76
|
+
border: 3px solid rgba(255,255,255,0.6);
|
|
77
|
+
box-shadow: 0 4px 15px rgba(99, 102, 241, 0.4);
|
|
78
|
+
}
|
|
7
79
|
</style>
|
|
80
|
+
|
|
81
|
+
<script>
|
|
82
|
+
document.querySelectorAll('[data-slider-input]').forEach(slider => {
|
|
83
|
+
const display = slider.closest('.slider-container')?.querySelector('[data-slider-value]');
|
|
84
|
+
slider.addEventListener('input', (e) => {
|
|
85
|
+
if (display) display.textContent = (e.target as HTMLInputElement).value;
|
|
86
|
+
});
|
|
87
|
+
});
|
|
88
|
+
</script>
|
|
@@ -1,14 +1,47 @@
|
|
|
1
1
|
---
|
|
2
|
-
|
|
3
|
-
|
|
2
|
+
/**
|
|
3
|
+
* GlassTextarea — A multiline text input with glassmorphism surface styling.
|
|
4
|
+
*
|
|
5
|
+
* @param {string} label - Input grouping label title.
|
|
6
|
+
* @param {string} id - The ID mapping the label to the textbox.
|
|
7
|
+
* @param {number} rows - Starting HTML rows count height. Default is 4.
|
|
8
|
+
* @param {string} placeholder - Displayed placeholder within the box when empty.
|
|
9
|
+
* @param {string} name - Form data extraction name binding.
|
|
10
|
+
* @param {boolean} required - HTML required indicator.
|
|
11
|
+
*/
|
|
12
|
+
interface Props {
|
|
13
|
+
label: string;
|
|
14
|
+
id: string;
|
|
15
|
+
rows?: number;
|
|
16
|
+
placeholder?: string;
|
|
17
|
+
name?: string;
|
|
18
|
+
required?: boolean;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
const { label, id, rows = 4, placeholder = "Start typing...", name, required = false } = Astro.props;
|
|
4
22
|
---
|
|
23
|
+
|
|
5
24
|
<div class="glass-textarea-wrap">
|
|
6
25
|
<label for={id} class="glass-label">{label}</label>
|
|
7
|
-
<textarea {id} {rows} class="glass-textarea"
|
|
26
|
+
<textarea {id} {name} {rows} {placeholder} {required} class="glass-textarea"></textarea>
|
|
8
27
|
</div>
|
|
28
|
+
|
|
9
29
|
<style>
|
|
10
30
|
.glass-textarea-wrap { display: flex; flex-direction: column; gap: 0.5rem; width: 100%; }
|
|
11
|
-
.glass-label { font-size: 0.85rem; font-weight: 600; color: #94a3b8; margin-left: 0.5rem; }
|
|
12
|
-
.glass-textarea {
|
|
13
|
-
|
|
31
|
+
.glass-label { font-size: 0.85rem; font-weight: 600; color: var(--c-text-2, #94a3b8); margin-left: 0.5rem; }
|
|
32
|
+
.glass-textarea {
|
|
33
|
+
width: 100%; padding: var(--sp-4, 1rem);
|
|
34
|
+
background: var(--c-bg-elev, rgba(255, 255, 255, 0.03));
|
|
35
|
+
backdrop-filter: blur(10px);
|
|
36
|
+
border: 1px solid var(--c-border, rgba(255, 255, 255, 0.1));
|
|
37
|
+
border-radius: var(--r-md, 16px);
|
|
38
|
+
color: var(--c-text-1, #fff);
|
|
39
|
+
font-family: inherit; font-size: 0.9rem;
|
|
40
|
+
outline: none; transition: 0.3s; resize: vertical;
|
|
41
|
+
}
|
|
42
|
+
.glass-textarea:focus {
|
|
43
|
+
border-color: rgba(99, 102, 241, 0.4);
|
|
44
|
+
background: rgba(255, 255, 255, 0.06);
|
|
45
|
+
}
|
|
46
|
+
.glass-textarea::placeholder { color: var(--c-text-muted, #475569); }
|
|
14
47
|
</style>
|
|
@@ -1,16 +1,72 @@
|
|
|
1
1
|
---
|
|
2
|
+
/**
|
|
3
|
+
* ModernSelect — A styled dropdown selector with a custom arrow and glassmorphism styling.
|
|
4
|
+
*
|
|
5
|
+
* @param {string} label - Input labeling title.
|
|
6
|
+
* @param {string} id - HTML ID for the select element.
|
|
7
|
+
* @param {string} name - HTML name binding.
|
|
8
|
+
* @param {Array<{label: string, value: string, disabled?: boolean}>} options - List of select options.
|
|
9
|
+
* @param {boolean} required - HTML required attribute.
|
|
10
|
+
*/
|
|
11
|
+
interface Props {
|
|
12
|
+
label: string;
|
|
13
|
+
id: string;
|
|
14
|
+
name?: string;
|
|
15
|
+
options: Array<{ label: string; value: string; disabled?: boolean }>;
|
|
16
|
+
required?: boolean;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
const { label, id, name, options = [], required = false } = Astro.props;
|
|
2
20
|
---
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
<
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
21
|
+
|
|
22
|
+
<div class="select-container">
|
|
23
|
+
<label for={id} class="select-label">{label}</label>
|
|
24
|
+
<div class="select-wrap">
|
|
25
|
+
<select class="custom-select" {id} {name} {required}>
|
|
26
|
+
{options.map(opt => (
|
|
27
|
+
<option value={opt.value} disabled={opt.disabled}>{opt.label}</option>
|
|
28
|
+
))}
|
|
29
|
+
</select>
|
|
30
|
+
<div class="select-arrow" aria-hidden="true">
|
|
31
|
+
<svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="3" stroke-linecap="round" stroke-linejoin="round">
|
|
32
|
+
<path d="M6 9l6 6 6-6"/>
|
|
33
|
+
</svg>
|
|
34
|
+
</div>
|
|
35
|
+
</div>
|
|
11
36
|
</div>
|
|
37
|
+
|
|
12
38
|
<style>
|
|
39
|
+
.select-container { display: flex; flex-direction: column; gap: var(--sp-2, 0.5rem); width: 100%; }
|
|
40
|
+
.select-label { font-size: 0.85rem; font-weight: 600; color: var(--c-text-2, #94a3b8); margin-left: 0.5rem; }
|
|
41
|
+
|
|
13
42
|
.select-wrap { position: relative; width: 100%; }
|
|
14
|
-
|
|
15
|
-
.select
|
|
43
|
+
|
|
44
|
+
.custom-select {
|
|
45
|
+
width: 100%;
|
|
46
|
+
padding: 0.8rem 2.5rem 0.8rem 1rem;
|
|
47
|
+
background: var(--c-bg-elev, rgba(255,255,255,0.04));
|
|
48
|
+
border: 1px solid var(--c-border, rgba(255,255,255,0.1));
|
|
49
|
+
border-radius: var(--r-md, 12px);
|
|
50
|
+
color: var(--c-text-1, #fff);
|
|
51
|
+
appearance: none; cursor: pointer; outline: none;
|
|
52
|
+
font-family: inherit; font-size: 0.95rem;
|
|
53
|
+
transition: border-color 0.2s, background 0.2s;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
.custom-select:focus {
|
|
57
|
+
border-color: var(--c-primary, #6366f1);
|
|
58
|
+
background: rgba(255,255,255,0.06);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
.select-arrow {
|
|
62
|
+
position: absolute; right: 1rem; top: 50%; transform: translateY(-50%);
|
|
63
|
+
color: var(--c-text-2, #64748b);
|
|
64
|
+
pointer-events: none; transition: transform 0.2s;
|
|
65
|
+
display: flex; align-items: center; justify-content: center;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
.custom-select:focus + .select-arrow {
|
|
69
|
+
transform: translateY(-50%) rotate(180deg);
|
|
70
|
+
color: var(--c-primary, #6366f1);
|
|
71
|
+
}
|
|
16
72
|
</style>
|