Sorry, but you either have no stories or none are selected somehow.
If the problem persists, check the browser console, or the terminal you've run Storybook from.
The component failed to render properly, likely due to a configuration issue in Storybook. Here are some common causes and how you can address them:
For best practices for writing for specific components, like alerts, errors, or confirmation dialogs, check out the individual component pages.
The way we access design tokens is becoming increasingly important as we move away from a single theme and towards a system of themes. The best way to access design tokens is through our semantic colors, which are are tied intrinsically to ColorModes. This means that when you use a semantic color, you are guaranteed to get the right color for the right theme. Using variants and and its related utilities will also guarantee you have access to the right tokens, typings, and state going forward. It is also safer!
Think of our semantic color names as a variable referencing what the primary use of the color is within each color mode. For example - an icon set to the text
color will match the primary color of text within that color mode.
For specific semantic name to color, please see the ColorMode documentation.
gamut-styles
with ColorMode semantic color names + shorthandsimport { css, states, variant } from '@codecademy/gamut-styles'; import styled from '@emotion/styled'; // Single value const Box = styled.div(css({ p: 4 })); // Mutiple values const OtherCoolThing = styled.div(css({ color: 'primary', p: 4 })); // Need some variants? const Anchor = styled.a( variant({ base: { p: 4 }, defaultVariant: 'interface', variants: { interface: { color: 'text', '&:hover': { color: 'text-accent', }, }, inline: { color: 'primary', '&:hover': { color: 'secondary', }, }, }, }) ); // Need some boolean states? const UtilityBox = styled.div( states({ base: { mx: 4, my: 8, p: 16 }, disabled: { bg: 'background-disabled', color: 'text-disabled', }, center: { alignItems: 'center', justifyContent: 'center', }, }) ); <UtilityBox disabled center />;
import { states } from '@codecademy/gamut-styles'; import { StyleProps } from '@codecademy/variance'; import styled from '@emotion/styled'; import React from 'react'; const someWrapperStates = states({ absolute: { position: 'absolute', left: 'calc(50% - 85px)' }, danger: { color: 'text', bg: 'danger' }, }); const SomeWrapper = styled.div(someWrapperStates); export interface CoolNumberComponentProps extends StyleProps<typeof someWrapperStates> { coolNumber: number; anotherCoolNumber: number; } export const CoolNumberComponent: React.FC<CoolNumberComponentProps> = ({ coolNumber, anotherCoolNumber, ...rest //where your state props are! }) => <SomeWrapper {...rest} />;
System props are a core part of our new approach to dynamic and customized styling. Where writing custom styles is painful, system props are here to make it painless.
import { Box } from '@codecademy/gamut'; const MyContainer = ({ children }) => ( <Box paddingX={[16, 32, 64, , 96]}>{children}</Box> ); const MyOtherContainer = ({ children }) => ( <Box mb={40} px={{ _: 0, md: 64 }} display={{ _: 'block', md: 'flex' }} width={{ _: 'initial', md: `${pxRem(420)}` }} > {children} </Box> );
Intellisense + Typesafety - Many system props are tied to specific design token scales. You can be sure that you are using the correct tokens between contexts. All props will autosuggest possible values for the scale that you are in.
Responsive Syntax - Docs All system props accept 2 responsive syntaxes for easily creating responsive layouts. System prop media queries are mobile first (Greater Than or Equal To).
The typings behind the scenes:
type MediaQueryMap<T> = { _?: T; xs?: T; sm?: T; md?: T; lg?: T; xl?: T; }; type MediaQueryArray<T> = [ T?, // base T?, // xs T?, // sm T?, // md T?, // lg T? // xl ]; type SystemProp<T> = T | MediaQueryMap<T> | MediaQueryArray<T>;
Usage:
import { Box } from '@codecademy/gamut'; // Object Syntax <Box width={{ _: "100%", sm: "50%" }} /> // Array Syntax <Box width={["100%", ,"50%"]} />
Mobile / Desktop specific content
import { Box } from '@codecademy/gamut'; const App = () => ( <main> <h1>Title</h1> <Box display={{ _: 'none', sm: 'block' }}>Desktop Only Content</Box> <Box display={{ _: 'block', sm: 'none' }}>Mobile Only Content</Box> </main> );
Adaptive Layouts - 3 columns ⇒ 2 columns
import { GridBox } from '@codecademy/gamut'; const SomeCoolLayout = ({ children }) => ( <GridBox gridTemplateColumns={['1fr 1fr', , '1fr 1fr 1fr']}> {children} </GridBox> );
Design Token Access - Responsively accessing tokens by key.
const CardLikeThing = ({ children }) => ( <Box backgroundColor={{ _: 'background', md: 'text' }} textColor={{ _: 'text', md: 'background' }} > {children} </Box> ); const Content = ({ children }) => ( <Box padding={{ _: 16, md: 32 }}>{children}</Box> );
Nested selectors can cause a huge amount of side effects unwittingly and make it very hard to maintain consistent behavior while making updates. We politely ask (and will shortly lint) that you refrain from using:
*
div
p
span
Box
//❌ Don't do this❌ const App = styled.main` * { box-sizing: content-box; } `; //❌ Don't do this❌ const App = styled.main` display: flex; ${Box} { align-self: start; } `; // ✅ Do this ✅ const App = ({ children }) => ( <FlexBox as="main"> <Box alignSelf="start">{children}</Box> </FlexBox>