如何在 Chakra UI 和 React JS 中创建现代卡片⚡️
有时,打造出色的 UI 不仅需要时间,还需要专注。即使是某些卡片式设计,对结构、间距、配色等等的关注也至关重要。
如今,我们可以肯定地说,卡片已经成为网站和移动应用程序 UI 的设计趋势和主要元素,我们有来自 Revolut、Apple 和 Google 等大公司的例子,它们在其网站和应用程序上使用交互式现代卡片,为客户和用户提供使用其解决方案的绝佳体验!
因此,当我们开始设计和开发卡片时,我们需要考虑一些重要方面:
-
卡片内容应该非常紧凑和直观,所以我们需要将其保持在单一的卡片结构中。
-
整个卡片应该非常易于阅读和使用。这决定了UI和UX的优劣。因此,我们需要注意使其简洁通透(设计技巧:不要害怕使用留白,尽可能多地使用)。
-
卡片应该只包含能够展现信息的重要元素,正如我上面所说,我们需要保持卡片简洁明了。例如,CTA 卡片应该包含标题、副标题、或许还有一张图片,以及一个可以触发操作的 CTA 按钮。
定义 UI 卡片流行的另一个重要方面是它们有助于响应式 UI 设计,由于它们的方形形状可以完美适合任何网格结构,因此它们可以轻松缩小到任何设备分辨率。
让我们直接看卡片示例!
在今天的示例中,我们将制作三张符合最新 UI 趋势的简单卡片。我们从 Horizon UI React 卡片中汲取了一些设计灵感,您可以在他们的网站上看到更多类似的精彩免费 React 卡片。
太好了,让我们对它们进行编码吧!
正如你已经看到的,我们今天要用来构建精美卡片的 React JS 库是 Chakra UI。此外,我们还将借助Chakra 主题工具和React 图标等工具。
首先,让我们安装 Chakra UI 及其上述附加组件:
npm i @chakra-ui/react @chakra-ui/theme @chakra-ui/theme-tools react-icons
之后,我们需要创建一个style.js文件并输入以下样式:
// @src/theme/styles.js
import { mode } from "@chakra-ui/theme-tools";
export const globalStyles = {
colors: {
gray: {
700: "#1f2733",
},
navy: {
50: "#d0dcfb",
100: "#aac0fe",
200: "#a3b9f8",
300: "#728fea",
400: "#3652ba",
500: "#1b3bbb",
600: "#24388a",
700: "#1b254b",
800: "#111c44",
900: "#0b1437",
},
brand: {
50: "#cbbff8",
100: "#876cea",
200: "#582CFF",
300: "#542de1",
400: "#7551FF",
500: "#4318FF",
600: "#300eaa",
700: "#1c0377",
800: "#130156",
900: "#0e0042",
},
},
styles: {
global: (props) => ({
body: {
overflowX: "hidden",
bg: mode("gray.50", "#1B254B")(props),
},
html: {
fontFamily: "Helvetica, sans-serif",
},
}),
},
};
太棒了!在/theme目录下的components文件夹中,我们修改了各种 Chakra UI 组件,例如 或 。要使用它们,我们需要为每个组件创建一个包含所有样式文件(badge.js、button.js和breakpoints.js)的特殊文件夹!
为以下组件创建一个特殊文件:
徽章.js
// @src/theme/components/badge.js
export const badgeStyles = {
components: {
Badge: {
sizes: {
md: {
width: "65px",
height: "25px"
}
},
baseStyle: {
textTransform: "capitalize"
}
}
}
}
按钮.js
// @src/theme/components/button.js
import { mode } from "@chakra-ui/theme-tools";
export const buttonStyles = {
components: {
Button: {
variants: {
primary: {
fontSize: "10px",
bg: "blue.400",
color: "#fff",
_hover: { bg: "blue.300" },
_focus: { bg: "blue.300" },
_active: { bg: "blue.300" },
},
navy: {
fontSize: "10px",
bg: "navy.900",
color: "#fff",
_hover: { bg: "navy.900" },
_focus: { bg: "navy.900" },
_active: { bg: "navy.900" },
},
"no-effects": {
_hover: "none",
_active: "none",
_focus: "none",
},
danger: () => ({
color: "white",
bg: "red.500",
fontSize: "10px",
_hover: "red.400",
_focus: "red.400",
_active: "red.400",
}),
outlined: (props) => ({
color: mode("blue.400", "white")(props),
bg: "transparent",
fontSize: "10px",
border: "1px solid",
borderColor: { bg: mode("blue.400", "white")(props)},
_hover: { bg: mode("blue.50", "transparent")(props) },
_focus: { bg: mode("blue.50", "transparent")(props) },
_active: { bg: mode("blue.50", "transparent")(props) },
}),
dark: (props) => ({
color: "white",
bg: mode("gray.700", "blue.500")(props),
fontSize: "10px",
_hover: { bg: mode("gray.700", "blue.500")(props) },
_focus: { bg: mode("gray.700", "blue.600")(props) },
_active: { bg: mode("gray.700", "blue.400")(props) },
}),
light: (props) => ({
color: mode("gray.700", "gray.700")(props),
bg: mode("gray.100", "white")(props),
fontSize: "10px",
_hover: { bg: mode("gray.50", "white")(props) },
_focus: { bg: mode("gray.50", "white")(props) },
_active: { bg: mode("gray.50", "white")(props) },
}),
},
baseStyle: {
fontWeight: "bold",
borderRadius: "8px",
fontSize: "10px",
},
},
},
};
修改完常规样式后,设置其他断点以提高响应式准确性也会很有帮助。使用以下代码创建breakpoints.js文件:
// @src/theme/theme.js
import { extendTheme } from "@chakra-ui/react";
import { globalStyles } from "./styles";
import { breakpoints } from "./foundations/breakpoints";
import { buttonStyles } from "./components/button";
import { badgeStyles } from "./components/badge";
export default extendTheme(
{ breakpoints }, // Breakpoints
globalStyles, // Global styles
buttonStyles, // Button styles
badgeStyles, // Badge styles
);
此后,在index.js中,将主题添加到成分:
// @src/index.js
import React from 'react';
import ReactDOM from 'react-dom';
import App from 'App';
import { ChakraProvider } from "@chakra-ui/react";
// Custom Chakra theme
import theme from "theme/theme.js";
ReactDOM.render(
<ChakraProvider theme={theme} resetCss={false} position="relative">
<App />
</ChakraProvider>,
document.getElementById("root")
);
太棒了!让我们开始编写 Chakra UI + React 卡片的结构吧!⚡️
我们需要做的就是为每个文件创建一个特殊的文件并粘贴以下代码:
Chakra UI - 个人资料卡
// @src/components/Profile.js
import React from "react";
// Chakra imports
import { Flex, Image, Text, useColorModeValue } from "@chakra-ui/react";
function Profile() {
let boxBg = useColorModeValue("white !important", "#111c44 !important");
let mainText = useColorModeValue("gray.800", "white");
let secondaryText = useColorModeValue("gray.400", "gray.400");
return (
<Flex
borderRadius='20px'
bg={boxBg}
p='20px'
h='345px'
w={{ base: "315px", md: "345px" }}
alignItems='center'
direction='column'>
<Image
src='https://i.ibb.co/xmP2pS6/Profile.png'
maxW='100%'
borderRadius='20px'
/>
<Flex flexDirection='column' mb='30px'>
<Image
src='https://i.ibb.co/B3gYTYs/Profile-Image.png'
border='5px solid red'
mx='auto'
borderColor={boxBg}
width='68px'
height='68px'
mt='-38px'
borderRadius='50%'
/>
<Text
fontWeight='600'
color={mainText}
textAlign='center'
fontSize='xl'>
Adela Parkson
</Text>
<Text
color={secondaryText}
textAlign='center'
fontSize='sm'
fontWeight='500'>
Product Designer
</Text>
</Flex>
<Flex justify='space-between' w='100%' px='36px'>
<Flex flexDirection='column'>
<Text
fontWeight='600'
color={mainText}
fontSize='xl'
textAlign='center'>
17
</Text>
<Text color={secondaryText} fontWeight='500'>
Posts
</Text>
</Flex>
<Flex flexDirection='column'>
<Text
fontWeight='600'
color={mainText}
fontSize='xl'
textAlign='center'>
9.7k
</Text>
<Text color={secondaryText} fontWeight='500'>
Followers
</Text>
</Flex>
<Flex flexDirection='column'>
<Text
fontWeight='600'
fontSize='xl'
color={mainText}
textAlign='center'>
274
</Text>
<Text color={secondaryText} fontWeight='500'>
Following
</Text>
</Flex>
</Flex>
</Flex>
);
}
export default Profile;
Chakra UI - 团队卡
// @src/components/Teams.js
import React from "react";
// Chakra imports
import {
Avatar,
AvatarGroup,
Badge,
Flex,
Button,
Icon,
Image,
Text,
DarkMode,
useColorModeValue,
} from "@chakra-ui/react";
// Assets
import { MdPeople } from "react-icons/md";
import { IoEllipsisHorizontalSharp } from "react-icons/io5";
function Teams() {
let boxBg = useColorModeValue("white !important", "#111c44 !important");
let mainText = useColorModeValue("gray.800", "white");
let iconBox = useColorModeValue("gray.100", "whiteAlpha.200");
let iconColor = useColorModeValue("brand.200", "white");
return (
<Flex
borderRadius='20px'
bg={boxBg}
p='20px'
h='345px'
w={{ base: "315px", md: "345px" }}
alignItems='center'
direction='column'>
<Flex w='100%' mb='18px'>
<Flex
w='38px'
h='38px'
align='center'
justify='center'
borderRadius='50%'
me='12px'
bg={iconBox}>
<Icon w='24px' h='24px' as={MdPeople} color={iconColor} />
</Flex>
<Text
my='auto'
fontWeight='600'
color={mainText}
textAlign='center'
fontSize='xl'
me='auto'>
Teams
</Text>
<Button
w='38px'
h='38px'
align='center'
justify='center'
borderRadius='12px'
me='12px'
bg={iconBox}>
<Icon
w='24px'
h='24px'
as={IoEllipsisHorizontalSharp}
color={iconColor}
/>
</Button>
</Flex>
<Image
src='https://i.ibb.co/KVwmVGW/Teams-Image.png'
maxW='100%'
borderRadius='20px'
mb='10px'
/>
<Text
fontWeight='600'
color={mainText}
textAlign='start'
fontSize='xl'
w='100%'>
Simmmple Web
</Text>
<Flex mt='auto' justify='space-between' w='100%' align='center'>
<DarkMode>
<Badge
borderRadius='9px'
size='md'
colorScheme='green'
color='green.400'
textAlign='center'
display='flex'
justifyContent='center'
alignItems='center'>
Design
</Badge>
</DarkMode>
<AvatarGroup
size='sm'
max={4}
color={iconColor}
fontSize='9px'
fontWeight='700'>
<Avatar src='https://i.ibb.co/CmxNdhQ/avatar1.png' />
<Avatar src='https://i.ibb.co/cFWc59B/avatar2.png' />
<Avatar src='https://i.ibb.co/vLQJVFy/avatar3.png' />
<Avatar src='https://i.ibb.co/8mcrvQk/avatar4.png' />
<Avatar src='https://i.ibb.co/CmxNdhQ/avatar1.png' />
<Avatar src='https://i.ibb.co/cFWc59B/avatar2.png' />
<Avatar src='https://i.ibb.co/vLQJVFy/avatar3.png' />
<Avatar src='https://i.ibb.co/8mcrvQk/avatar4.png' />
</AvatarGroup>
</Flex>
</Flex>
);
}
export default Teams;
Chakra UI - 产品卡
// @src/components/Product.js
import React from "react";
// Chakra imports
import {
Avatar,
AvatarGroup,
Box,
Flex,
Button,
Icon,
Image,
Text,
useColorModeValue,
} from "@chakra-ui/react";
// Assets
import { MdTimer, MdVideoLibrary } from "react-icons/md";
import { IoEllipsisHorizontalSharp } from "react-icons/io5";
function Product() {
let boxBg = useColorModeValue("white !important", "#111c44 !important");
let secondaryBg = useColorModeValue("gray.50", "whiteAlpha.100");
let mainText = useColorModeValue("gray.800", "white");
let iconBox = useColorModeValue("gray.100", "whiteAlpha.200");
let iconColor = useColorModeValue("brand.200", "white");
return (
<Flex
borderRadius='20px'
bg={boxBg}
h='345px'
w={{ base: "315px", md: "345px" }}
direction='column'>
<Box p='20px'>
<Flex w='100%' mb='10px'>
<Image src='https://i.ibb.co/ZWxRPRq/Venus-Logo.png' me='auto' />
<Button
w='38px'
h='38px'
align='center'
justify='center'
borderRadius='12px'
me='12px'
bg={iconBox}>
<Icon
w='24px'
h='24px'
as={IoEllipsisHorizontalSharp}
color={iconColor}
/>
</Button>
</Flex>
<Box>
<Text fontWeight='600' color={mainText} w='100%' fontSize='2xl'>
Venus Product
</Text>
<AvatarGroup
size='sm'
max={4}
color={iconColor}
fontSize='9px'
fontWeight='700'>
<Avatar src='https://i.ibb.co/CmxNdhQ/avatar1.png' />
<Avatar src='https://i.ibb.co/cFWc59B/avatar2.png' />
<Avatar src='https://i.ibb.co/vLQJVFy/avatar3.png' />
<Avatar src='https://i.ibb.co/8mcrvQk/avatar4.png' />
<Avatar src='https://i.ibb.co/CmxNdhQ/avatar1.png' />
<Avatar src='https://i.ibb.co/cFWc59B/avatar2.png' />
<Avatar src='https://i.ibb.co/vLQJVFy/avatar3.png' />
<Avatar src='https://i.ibb.co/8mcrvQk/avatar4.png' />
</AvatarGroup>
</Box>
</Box>
<Flex
bg={secondaryBg}
w='100%'
p='20px'
borderBottomLeftRadius='inherit'
borderBottomRightRadius='inherit'
height='100%'
direction='column'>
<Text
fontSize='sm'
color='gray.500'
lineHeight='24px'
pe='40px'
fontWeight='500'
mb='auto'>
You have the opportunity to play this game of life you need to
appreciate every moment.
</Text>
<Flex>
<Flex me='25px'>
<Icon as={MdTimer} w='20px' h='20px' me='6px' color='green.400' />
<Text color={mainText} fontSize='sm' my='auto' fontWeight='500'>
85 mins
</Text>
</Flex>
<Flex>
<Icon
as={MdVideoLibrary}
w='20px'
h='20px'
me='6px'
color='red.500'
/>
<Text color={mainText} fontSize='sm' my='auto' fontWeight='500'>
Video Format
</Text>
</Flex>
</Flex>
</Flex>
</Flex>
);
}
export default Product;
恭喜!🎉
太棒了!现在,我们将在App.js中导入之前创建的卡片组件!导入代码如下:
// Components Import
import Product from "./components/Product";
import Profile from "./components/Profile";
import Teams from "./components/Teams";
结论和资源⭐️
在本文中,我们成功使用 Chakra UI 构建了完整且完全响应式的卡片。希望本文对您有所帮助,也希望您觉得本文有趣!
在这里您可以找到包含上述卡片的今天项目的 .zip 文件!
另外,我强烈推荐你看看并尝试一下Horizon UI,你会发现更多像本文中提到的精彩卡片、现代图表以及许多其他令人惊叹的 UI 元素。它们都包含在一个功能完善、响应式、适用于所有设备的管理面板中!而且它还是免费开源的! ⚡️
感谢阅读!
文章来源:https://dev.to/fredy/how-to-create-modern-cards-in-chakra-ui-react-js-j1b