Next.js Discord

Discord Forum

Props & Conditionals

Answered
Himalayan Snowcock posted this in #help-forum
Open in Discord
Avatar
Himalayan SnowcockOP
Hello, I'd like to explain my situation. I have a badge component that has a variant props, which allows me to manage the style of the badge.

When I call my badge component in my main component, I would like to use the state of the badge variant to modify other styles of my main component. For example, to change the color of a text.

The problem is that I can't make the variant conditional in order to check it and change the style of my main component. Can you advise me to proceed in another way?
Image
Answered by American Crow
@Himalayan Snowcock if you want some stronger typing and bit more bulletproof because of tailwind class merging you might want ot have a look:
import { cva, type VariantProps } from 'class-variance-authority'
import * as React from 'react'

import { cn } from '@/lib/utils'

const shellVariants = cva('grid items-center gap-8 pb-8 pt-6 md:py-8', {
  variants: {
    variant: {
      default: 'container',
      sidebar: '',
      centered: 'container flex h-[100dvh] max-w-2xl flex-col justify-center',
      markdown: 'max-w-3xl py-8 md:py-10',
    },
  },
  defaultVariants: {
    variant: 'default',
  },
})

interface ShellProps
  extends React.HTMLAttributes<HTMLDivElement>,
    VariantProps<typeof shellVariants> {
  as?: React.ElementType
}

function Shell({
  className,
  as: Comp = 'section',
  variant,
  ...props
}: ShellProps) {
  return (
    <Comp className={cn(shellVariants({ variant }), className)} {...props} />
  )
}

export { Shell, shellVariants }
View full answer

5 Replies

Avatar
American Crow
you most likely want to create a custom component similar to <GiveawayBadge />. Let's call that new component <Shell />
You make Shell accept a variant <Shell variant='enterprise' > {children} </Shell> and based on the variant you do your styling. Not sure what can be extracted from your layout if you should go with just children or component composition. But you get the idea
Avatar
Himalayan SnowcockOP
Nice thanks for your help !
Image
Image
Image
Avatar
American Crow
yea thats what i meant. well done
Avatar
American Crow
@Himalayan Snowcock if you want some stronger typing and bit more bulletproof because of tailwind class merging you might want ot have a look:
import { cva, type VariantProps } from 'class-variance-authority'
import * as React from 'react'

import { cn } from '@/lib/utils'

const shellVariants = cva('grid items-center gap-8 pb-8 pt-6 md:py-8', {
  variants: {
    variant: {
      default: 'container',
      sidebar: '',
      centered: 'container flex h-[100dvh] max-w-2xl flex-col justify-center',
      markdown: 'max-w-3xl py-8 md:py-10',
    },
  },
  defaultVariants: {
    variant: 'default',
  },
})

interface ShellProps
  extends React.HTMLAttributes<HTMLDivElement>,
    VariantProps<typeof shellVariants> {
  as?: React.ElementType
}

function Shell({
  className,
  as: Comp = 'section',
  variant,
  ...props
}: ShellProps) {
  return (
    <Comp className={cn(shellVariants({ variant }), className)} {...props} />
  )
}

export { Shell, shellVariants }
Answer
Avatar
joulev
Actually I’ll select the latter message as it is a lot better and more detailed