Skip to content

第9章:样式解决方案

9.1 基础样式写法(全局 CSS、组件内 CSS)

全局 CSS

在 Next.js 中,可以在 app/globals.css 文件中定义全局样式。

示例

css
/* app/globals.css */
* {
  margin: 0;
  padding: 0;
  box-sizing: border-box;
}

body {
  font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
  line-height: 1.6;
  color: #333;
  background-color: #f5f5f5;
}

a {
  color: #0070f3;
  text-decoration: none;
}

a:hover {
  text-decoration: underline;
}

.container {
  max-width: 1200px;
  margin: 0 auto;
  padding: 0 20px;
}

.btn {
  padding: 8px 16px;
  border: none;
  border-radius: 4px;
  cursor: pointer;
  font-size: 14px;
  font-weight: 500;
}

.btn-primary {
  background-color: #0070f3;
  color: white;
}

.btn-secondary {
  background-color: #6c757d;
  color: white;
}

使用

jsx
// app/layout.js
import './globals.css';

export default function RootLayout({ children }) {
  return (
    <html lang="en">
      <body>{children}</body>
    </html>
  );
}

// app/page.js
export default function Home() {
  return (
    <div className="container">
      <h1>Home Page</h1>
      <p>Welcome to my Next.js app!</p>
      <button className="btn btn-primary">Primary Button</button>
      <button className="btn btn-secondary">Secondary Button</button>
    </div>
  );
}

组件内 CSS

可以在组件文件中直接使用 <style> 标签定义组件内样式。

示例

jsx
// app/components/Button.jsx
export default function Button({ children, variant = 'primary' }) {
  return (
    <>
      <button className={`btn btn-${variant}`}>
        {children}
      </button>
      <style jsx>{`
        .btn {
          padding: 8px 16px;
          border: none;
          border-radius: 4px;
          cursor: pointer;
          font-size: 14px;
          font-weight: 500;
        }
        .btn-primary {
          background-color: #0070f3;
          color: white;
        }
        .btn-secondary {
          background-color: #6c757d;
          color: white;
        }
      `}</style>
    </>
  );
}

9.2 CSS 模块化(.module.css,避免样式冲突,实战必备)

CSS 模块化是 Next.js 推荐的样式解决方案,可以避免样式冲突。

创建 CSS 模块文件

创建 .module.css 文件,如 Button.module.css

示例

css
/* components/Button.module.css */
.btn {
  padding: 8px 16px;
  border: none;
  border-radius: 4px;
  cursor: pointer;
  font-size: 14px;
  font-weight: 500;
}

.primary {
  background-color: #0070f3;
  color: white;
}

.secondary {
  background-color: #6c757d;
  color: white;
}

.primary:hover {
  background-color: #0056b3;
}

.secondary:hover {
  background-color: #5a6268;
}

使用 CSS 模块

示例

jsx
// components/Button.jsx
import styles from './Button.module.css';

export default function Button({ children, variant = 'primary' }) {
  return (
    <button className={`${styles.btn} ${styles[variant]}`}>
      {children}
    </button>
  );
}

// app/page.js
import Button from '@/components/Button';

export default function Home() {
  return (
    <div>
      <h1>Home Page</h1>
      <Button>Primary Button</Button>
      <Button variant="secondary">Secondary Button</Button>
    </div>
  );
}

9.3 CSS 预处理器(SCSS、Less 配置与使用)

Next.js 支持 CSS 预处理器,如 SCSS 和 Less。

安装依赖

SCSS

bash
npm install sass

Less

bash
npm install less

使用 SCSS

示例

scss
/* components/Button.module.scss */
.btn {
  padding: 8px 16px;
  border: none;
  border-radius: 4px;
  cursor: pointer;
  font-size: 14px;
  font-weight: 500;
  
  &.primary {
    background-color: #0070f3;
    color: white;
    
    &:hover {
      background-color: #0056b3;
    }
  }
  
  &.secondary {
    background-color: #6c757d;
    color: white;
    
    &:hover {
      background-color: #5a6268;
    }
  }
}

使用

jsx
// components/Button.jsx
import styles from './Button.module.scss';

export default function Button({ children, variant = 'primary' }) {
  return (
    <button className={`${styles.btn} ${styles[variant]}`}>
      {children}
    </button>
  );
}

使用 Less

示例

less
/* components/Button.module.less */
.btn {
  padding: 8px 16px;
  border: none;
  border-radius: 4px;
  cursor: pointer;
  font-size: 14px;
  font-weight: 500;
  
  &.primary {
    background-color: #0070f3;
    color: white;
    
    &:hover {
      background-color: #0056b3;
    }
  }
  
  &.secondary {
    background-color: #6c757d;
    color: white;
    
    &:hover {
      background-color: #5a6268;
    }
  }
}

使用

jsx
// components/Button.jsx
import styles from './Button.module.less';

export default function Button({ children, variant = 'primary' }) {
  return (
    <button className={`${styles.btn} ${styles[variant]}`}>
      {children}
    </button>
  );
}

9.4 第三方样式库集成(Tailwind CSS、Ant Design、Material UI)

Tailwind CSS

Tailwind CSS 是一个实用优先的 CSS 框架,可以快速构建现代网站。

安装与配置

bash
npm install -D tailwindcss postcss autoprefixer
npx tailwindcss init -p

配置 tailwind.config.js

javascript
/** @type {import('tailwindcss').Config} */
export default {
  content: [
    "./app/**/*.{js,ts,jsx,tsx}",
    "./components/**/*.{js,ts,jsx,tsx}",
  ],
  theme: {
    extend: {},
  },
  plugins: [],
}

配置 globals.css

css
/* app/globals.css */
@tailwind base;
@tailwind components;
@tailwind utilities;

* {
  margin: 0;
  padding: 0;
  box-sizing: border-box;
}

使用

jsx
// app/page.js
export default function Home() {
  return (
    <div className="container mx-auto px-4 py-8">
      <h1 className="text-3xl font-bold mb-4">Home Page</h1>
      <p className="mb-6">Welcome to my Next.js app!</p>
      <button className="bg-blue-500 text-white px-4 py-2 rounded hover:bg-blue-600">
        Primary Button
      </button>
      <button className="bg-gray-500 text-white px-4 py-2 rounded hover:bg-gray-600 ml-2">
        Secondary Button
      </button>
    </div>
  );
}

Ant Design

Ant Design 是一个企业级 UI 组件库。

安装

bash
npm install antd

使用

jsx
// app/components/AntButton.jsx
'use client';

import { Button } from 'antd';

export default function AntButton({ children, type = 'primary' }) {
  return <Button type={type}>{children}</Button>;
}

// app/page.js
import AntButton from '@/components/AntButton';

export default function Home() {
  return (
    <div style={{ padding: '20px' }}>
      <h1>Home Page</h1>
      <p>Welcome to my Next.js app!</p>
      <AntButton>Primary Button</AntButton>
      <AntButton type="default" style={{ marginLeft: '8px' }}>Default Button</AntButton>
      <AntButton type="dashed" style={{ marginLeft: '8px' }}>Dashed Button</AntButton>
      <AntButton type="text" style={{ marginLeft: '8px' }}>Text Button</AntButton>
    </div>
  );
}

Material UI

Material UI 是一个基于 Material Design 的 UI 组件库。

安装

bash
npm install @mui/material @emotion/react @emotion/styled

使用

jsx
// app/components/MuiButton.jsx
'use client';

import Button from '@mui/material/Button';

export default function MuiButton({ children, variant = 'contained' }) {
  return <Button variant={variant}>{children}</Button>;
}

// app/page.js
import MuiButton from '@/components/MuiButton';

export default function Home() {
  return (
    <div style={{ padding: '20px' }}>
      <h1>Home Page</h1>
      <p>Welcome to my Next.js app!</p>
      <MuiButton>Contained Button</MuiButton>
      <MuiButton variant="outlined" style={{ marginLeft: '8px' }}>Outlined Button</MuiButton>
      <MuiButton variant="text" style={{ marginLeft: '8px' }}>Text Button</MuiButton>
    </div>
  );
}

9.5 样式组件(Styled Components 集成 Next.js)

Styled Components 是一个 CSS-in-JS 库,可以在 JavaScript 中编写 CSS。

安装

bash
npm install styled-components

配置

创建 babel.config.js

javascript
module.exports = {
  presets: ['next/babel'],
  plugins: ['styled-components'],
};

使用

jsx
// components/StyledButton.jsx
'use client';

import styled from 'styled-components';

const Button = styled.button`
  padding: 8px 16px;
  border: none;
  border-radius: 4px;
  cursor: pointer;
  font-size: 14px;
  font-weight: 500;
  
  ${props => props.variant === 'primary' && `
    background-color: #0070f3;
    color: white;
    
    &:hover {
      background-color: #0056b3;
    }
  `}
  
  ${props => props.variant === 'secondary' && `
    background-color: #6c757d;
    color: white;
    
    &:hover {
      background-color: #5a6268;
    }
  `}
`;

export default function StyledButton({ children, variant = 'primary' }) {
  return <Button variant={variant}>{children}</Button>;
}

// app/page.js
import StyledButton from '@/components/StyledButton';

export default function Home() {
  return (
    <div style={{ padding: '20px' }}>
      <h1>Home Page</h1>
      <p>Welcome to my Next.js app!</p>
      <StyledButton>Primary Button</StyledButton>
      <StyledButton variant="secondary" style={{ marginLeft: '8px' }}>Secondary Button</StyledButton>
    </div>
  );
}

小结

本章介绍了 Next.js 的样式解决方案,包括基础样式、CSS 模块化、CSS 预处理器、第三方样式库集成和样式组件。通过本章的学习,你应该已经掌握了:

  1. 基础样式写法:全局 CSS 和组件内 CSS
  2. CSS 模块化:使用 .module.css 文件避免样式冲突
  3. CSS 预处理器:配置和使用 SCSS、Less
  4. 第三方样式库集成:Tailwind CSS、Ant Design、Material UI
  5. 样式组件:使用 Styled Components 进行 CSS-in-JS 开发

选择合适的样式解决方案对于构建美观、可维护的 Next.js 应用至关重要。在实际开发中,建议:

  • 对于简单项目,使用基础样式或 CSS 模块化
  • 对于需要快速开发的项目,使用 Tailwind CSS
  • 对于企业级应用,使用 Ant Design 或 Material UI
  • 对于需要高度自定义的项目,使用 Styled Components

接下来,我们将学习 Next.js 的 API 路由开发,这是 Next.js 内置的后端能力。

© 2026 编程马·菜鸟教程 版权所有