You are looking at the documentation of the work in progress Hope UI 1.0, examples and information may be broken or outdated.

Introduction

Learn the basics

Get familiar with core Hope UI concepts by building a simple Card component.

Yosemite National Park

Yosemite National Park

Nature

Yosemite National Park is an American national park in California, surrounded on the southeast by the Sierra National Forest and on the northwest by the Stanislaus National Forest.

Building a Card

Layout

First, we define the structure of the Card using two layout components from Hope UI:

  • Box: The most abstract Hope UI component, it is basically a div with superpowers.
  • Flex: A Box with display: flex.
tsx
import { Box, Flex } from "@hope-ui/core";
export function Card() {
return (
<Flex>
<img src="https://bit.ly/3CVFryX" alt="Yosemite National Park" />
<Box>
<Flex>
<span>Yosemite National Park</span>
<Flex>
<span>Nature</span>
</Flex>
</Flex>
<p>
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</p>
<button>Learn more</button>
</Box>
</Flex>
);
}
tsx
import { Box, Flex } from "@hope-ui/core";
export function Card() {
return (
<Flex>
<img src="https://bit.ly/3CVFryX" alt="Yosemite National Park" />
<Box>
<Flex>
<span>Yosemite National Park</span>
<Flex>
<span>Nature</span>
</Flex>
</Flex>
<p>
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</p>
<button>Learn more</button>
</Box>
</Flex>
);
}

Typography

We are using native HTML elements like span and p to render our text content. Let's replace them by one of Hope UI's typography components:

Text.  Text renders a p tag by default and comes with a size prop that we can use to adjust the size of the text and keep it legible.

Also, since it's a built-in Hope UI component, it will also make our life easier when it comes to styling later on.

tsx
import { Box, Flex, Text } from "@hope-ui/core";
export function Card() {
return (
<Flex>
<img src="https://bit.ly/3CVFryX" alt="Yosemite National Park" />
<Box>
<Flex>
<Text as="span">Yosemite National Park</Text>
<Flex>
<Text as="span" size="xs">
Nature
</Text>
</Flex>
</Flex>
<Text size="sm">
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<button>Learn more</button>
</Box>
</Flex>
);
}
tsx
import { Box, Flex, Text } from "@hope-ui/core";
export function Card() {
return (
<Flex>
<img src="https://bit.ly/3CVFryX" alt="Yosemite National Park" />
<Box>
<Flex>
<Text as="span">Yosemite National Park</Text>
<Flex>
<Text as="span" size="xs">
Nature
</Text>
</Flex>
</Flex>
<Text size="sm">
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<button>Learn more</button>
</Box>
</Flex>
);
}

Notice the use of the as prop on the first two Text components which allows changing the rendered DOM element.

More built-in components

The last two native HTML elements that we can replace are img and button. Let's use their Hope UI counterparts: Image and Button.

tsx
import { Box, Button, Flex, Image, Text } from "@hope-ui/core";
export function Card() {
return (
<Flex>
<Image src="https://bit.ly/3CVFryX" alt="Yosemite National Park" />
<Box>
<Flex>
<Text as="span">Yosemite National Park</Text>
<Flex>
<Text as="span" size="xs">
Nature
</Text>
</Flex>
</Flex>
<Text size="sm">
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<Button variant="soft" colorScheme="primary" isFullWidth>
Learn more
</Button>
</Box>
</Flex>
);
}
tsx
import { Box, Button, Flex, Image, Text } from "@hope-ui/core";
export function Card() {
return (
<Flex>
<Image src="https://bit.ly/3CVFryX" alt="Yosemite National Park" />
<Box>
<Flex>
<Text as="span">Yosemite National Park</Text>
<Flex>
<Text as="span" size="xs">
Nature
</Text>
</Flex>
</Flex>
<Text size="sm">
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<Button variant="soft" colorScheme="primary" isFullWidth>
Learn more
</Button>
</Box>
</Flex>
);
}

Styling

Hope UI uses the concept of "Style Props", popularized by Chakra UI which allows us to apply styles simply by passing props to our components.

tsx
import { Box, Button, Flex, Image, Text } from "@hope-ui/core";
function Card() {
return (
<Flex
flexDirection="column"
border={theme => `1px solid ${theme.vars.colors.neutral["200"]}`}
borderRadius="lg"
boxShadow="lg"
width="full"
maxWidth={96}
background="white"
>
<Image
src="https://bit.ly/3CVFryX"
alt="Yosemite National Park"
objectFit="cover"
borderTopLeftRadius="lg"
borderTopRightRadius="lg"
maxHeight="200px"
/>
<Box padding={5}>
<Flex justifyContent="space-between" alignItems="center" width="full" marginBottom={2}>
<Text fontWeight="semibold">Yosemite National Park</Text>
<Flex
paddingLeft={2}
paddingRight={2}
paddingTop={1}
paddingBottom={1}
alignItems="center"
backgroundColor="success.50"
color="success.800"
borderRadius="full"
>
<Text
as="span"
size="xs"
lineHeight="none"
fontWeight="semibold"
textTransform="uppercase"
>
Nature
</Text>
</Flex>
</Flex>
<Text size="sm" color="neutral.500" marginBottom={3}>
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<Button variant="soft" colorScheme="primary" isFullWidth>
Learn more
</Button>
</Box>
</Flex>
);
}
tsx
import { Box, Button, Flex, Image, Text } from "@hope-ui/core";
function Card() {
return (
<Flex
flexDirection="column"
border={theme => `1px solid ${theme.vars.colors.neutral["200"]}`}
borderRadius="lg"
boxShadow="lg"
width="full"
maxWidth={96}
background="white"
>
<Image
src="https://bit.ly/3CVFryX"
alt="Yosemite National Park"
objectFit="cover"
borderTopLeftRadius="lg"
borderTopRightRadius="lg"
maxHeight="200px"
/>
<Box padding={5}>
<Flex justifyContent="space-between" alignItems="center" width="full" marginBottom={2}>
<Text fontWeight="semibold">Yosemite National Park</Text>
<Flex
paddingLeft={2}
paddingRight={2}
paddingTop={1}
paddingBottom={1}
alignItems="center"
backgroundColor="success.50"
color="success.800"
borderRadius="full"
>
<Text
as="span"
size="xs"
lineHeight="none"
fontWeight="semibold"
textTransform="uppercase"
>
Nature
</Text>
</Flex>
</Flex>
<Text size="sm" color="neutral.500" marginBottom={3}>
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<Button variant="soft" colorScheme="primary" isFullWidth>
Learn more
</Button>
</Box>
</Flex>
);
}

Understanding theme tokens

All the style props above are pretty much self-explanatory, but some values are weird, like:

  • color="success.800"
  • width="full"
  • paddingRight={2}
  • border={theme => '1px solid ${theme.vars.colors.neutral["200"]}'}

This is what we call "Theme Tokens", a set of values (colors, spacing, shadows, etc...) that we can refer to when styling to keep our design consistent.

We can refer to them directly as values of our style props or use the "function form" (like for the border prop above), which gives us access to all available tokens through the vars property on the theme object.

Using shorthand style props

Our Card component is pretty good now, but we can save some typing by using Hope UI "shorthand" style props.

tsx
import { Box, Button, Flex, Image, Text } from "@hope-ui/core";
function Card() {
return (
<Flex
direction="column"
border={theme => `1px solid ${theme.vars.colors.neutral["200"]}`}
rounded="lg"
shadow="lg"
w="full"
maxW={96}
bg="white"
>
<Image
src="https://bit.ly/3CVFryX"
alt="Yosemite National Park"
objectFit="cover"
roundedTop="lg"
maxH="200px"
/>
<Box p={5}>
<Flex justify="space-between" align="center" w="full" mb={2}>
<Text fontWeight="semibold">Yosemite National Park</Text>
<Flex
px={2}
py={1}
align="center"
bgColor="success.50"
color="success.800"
rounded="full"
>
<Text
as="span"
size="xs"
lineHeight="none"
fontWeight="semibold"
textTransform="uppercase"
>
Nature
</Text>
</Flex>
</Flex>
<Text size="sm" color="neutral.500" mb={3}>
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<Button variant="soft" colorScheme="primary" isFullWidth>
Learn more
</Button>
</Box>
</Flex>
);
}
tsx
import { Box, Button, Flex, Image, Text } from "@hope-ui/core";
function Card() {
return (
<Flex
direction="column"
border={theme => `1px solid ${theme.vars.colors.neutral["200"]}`}
rounded="lg"
shadow="lg"
w="full"
maxW={96}
bg="white"
>
<Image
src="https://bit.ly/3CVFryX"
alt="Yosemite National Park"
objectFit="cover"
roundedTop="lg"
maxH="200px"
/>
<Box p={5}>
<Flex justify="space-between" align="center" w="full" mb={2}>
<Text fontWeight="semibold">Yosemite National Park</Text>
<Flex
px={2}
py={1}
align="center"
bgColor="success.50"
color="success.800"
rounded="full"
>
<Text
as="span"
size="xs"
lineHeight="none"
fontWeight="semibold"
textTransform="uppercase"
>
Nature
</Text>
</Flex>
</Flex>
<Text size="sm" color="neutral.500" mb={3}>
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<Button variant="soft" colorScheme="primary" isFullWidth>
Learn more
</Button>
</Box>
</Flex>
);
}

Dark mode support

We can go a step further and add dark mode support to our Card component. Hope UI's style props accept an object as value in which you can set the light and/or dark value.

tsx
import { Box, Button, Flex, Image, Text } from "@hope-ui/core";
export function Card() {
return (
<Flex
direction="column"
border={({ vars }) => `1px solid ${vars.colors.neutral["200"]}`}
borderColor={{ dark: "neutral.800" }}
rounded="lg"
shadow="lg"
w="full"
maxW={96}
bg={{ light: "white", dark: "neutral.900" }}
>
<Image
src="https://bit.ly/3CVFryX"
alt="Yosemite National Park"
objectFit="cover"
roundedTop="lg"
maxH="200px"
/>
<Box p={5}>
<Flex justify="space-between" align="center" w="full" mb={2}>
<Text fontWeight="semibold" color={{ dark: "neutral.300" }}>
Yosemite National Park
</Text>
<Flex
px={2}
py={1}
align="center"
bgColor={{ light: "success.50", dark: "success.900" }}
color={{ light: "success.800", dark: "success.300" }}
rounded="full"
>
<Text
as="span"
size="xs"
lineHeight="none"
fontWeight="semibold"
textTransform="uppercase"
>
Nature
</Text>
</Flex>
</Flex>
<Text size="sm" color={{ light: "neutral.500", dark: "neutral.400" }} mb={3}>
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<Button variant="soft" colorScheme="primary" isFullWidth>
Learn more
</Button>
</Box>
</Flex>
);
}
tsx
import { Box, Button, Flex, Image, Text } from "@hope-ui/core";
export function Card() {
return (
<Flex
direction="column"
border={({ vars }) => `1px solid ${vars.colors.neutral["200"]}`}
borderColor={{ dark: "neutral.800" }}
rounded="lg"
shadow="lg"
w="full"
maxW={96}
bg={{ light: "white", dark: "neutral.900" }}
>
<Image
src="https://bit.ly/3CVFryX"
alt="Yosemite National Park"
objectFit="cover"
roundedTop="lg"
maxH="200px"
/>
<Box p={5}>
<Flex justify="space-between" align="center" w="full" mb={2}>
<Text fontWeight="semibold" color={{ dark: "neutral.300" }}>
Yosemite National Park
</Text>
<Flex
px={2}
py={1}
align="center"
bgColor={{ light: "success.50", dark: "success.900" }}
color={{ light: "success.800", dark: "success.300" }}
rounded="full"
>
<Text
as="span"
size="xs"
lineHeight="none"
fontWeight="semibold"
textTransform="uppercase"
>
Nature
</Text>
</Flex>
</Flex>
<Text size="sm" color={{ light: "neutral.500", dark: "neutral.400" }} mb={3}>
Yosemite National Park is an American national park in California, surrounded on the
southeast by the Sierra National Forest and on the northwest by the Stanislaus National
Forest.
</Text>
<Button variant="soft" colorScheme="primary" isFullWidth>
Learn more
</Button>
</Box>
</Flex>
);
}

To learn more about dark mode, checkout the Color Mode documentation.

Summary

  • Hope UI provides layout components to help achieve common layout scenarios (Flex, Grid, etc...).
  • Hope UI provides typography components to work with texts and headings.
  • Style props are a way to define a component's style by simply passing props to them.
  • Theme Tokens allow styling your application with a consistent set of colors, spacing, shadows, and more.
  • The as prop allows changing the rendered DOM element.
Previous
Getting started