从零搭建 React 移动端项目

React 作为前端三大框架之一,凭借组件化、虚拟 DOM 等特性成为移动端开发的热门选择。本文将从环境准备、项目初始化、移动端适配、UI 库集成到核心功能开发,完整讲解 React 移动端项目的搭建流程,覆盖 React 18 + Vite 生态,适合前端初学者和想系统化学习 React 移动端开发的同学。

一、前期准备:开发环境搭建

在创建 React 移动端项目前,需先配置好基础环境,确保后续流程无阻碍。

1. 安装 Node.js 和包管理工具

React 项目依赖 Node.js 的 npm/yarn/pnpm,建议安装 LTS 长期支持版:

  • 下载地址:Node.js 官网(推荐 18.x/20.x 版本)

  • 验证安装:打开终端执行以下命令,显示版本号即成功: bash

    运行

    复制代码
    node -v  # 查看Node版本
    npm -v   # 查看npm版本
  • 优化配置(解决下载慢问题): bash

    运行

    复制代码
    # 替换npm镜像源
    npm config set registry https://registry.npmmirror.com
    # 可选:安装pnpm(推荐,比npm/yarn更快更节省磁盘)
    npm install -g pnpm
    pnpm -v  # 验证安装

2. 确认脚手架工具

React 官方推荐使用 Vite 创建项目(替代传统的 create-react-app),Vite 启动速度更快、打包更高效,尤其适合移动端开发。无需全局安装 Vite,创建项目时自动拉取即可。

二、创建 React 移动端项目(Vite 版)

1. 初始化项目

执行以下命令创建基于 Vite 的 React 项目,本文以 JavaScript 版本为例(TypeScript 版本可按需选择):

bash

运行

复制代码
# 使用npm创建
npm create vite@latest react-mobile-demo -- --template react
# 或使用pnpm(推荐)
pnpm create vite react-mobile-demo -- --template react
  • 命令说明:
    • react-mobile-demo:自定义项目名称
    • --template react:指定模板为 React(JavaScript 版),如需 TypeScript 则用react-ts

2. 安装依赖并启动项目

bash

运行

复制代码
# 进入项目目录
cd react-mobile-demo
# 安装依赖
npm install  # 或 pnpm install
# 启动开发服务器
npm run dev  # 或 pnpm dev

启动成功后,终端会显示本地访问地址(如http://127.0.0.1:5173/),打开浏览器访问,能看到 React 默认页面即项目创建成功。

三、移动端核心配置:适配方案

移动端开发的核心痛点是多设备屏幕适配,本文推荐两种主流方案,按需选择。

方案 1:rem 适配(基于 lib-flexible + postcss-pxtorem)

rem 是相对根节点的单位,通过动态设置 html 的 font-size 实现适配,兼容所有移动端浏览器。

步骤 1:安装依赖

bash

运行

复制代码
# 安装适配核心库
npm install amfe-flexible --save
# 安装px转rem的PostCSS插件
npm install postcss-pxtorem --save-dev
  • amfe-flexible:阿里开源的移动端适配库,动态计算并设置 html 的 font-size
  • postcss-pxtorem:自动将 CSS 中的 px 转换为 rem,无需手动计算
步骤 2:引入 amfe-flexible

在项目入口文件src/main.jsx中引入:

jsx

复制代码
import React from 'react'
import ReactDOM from 'react-dom/client'
import App from './App'
// 引入移动端适配核心库
import 'amfe-flexible'
import './index.css'

ReactDOM.createRoot(document.getElementById('root')).render(
  <React.StrictMode>
    <App />
  </React.StrictMode>
)
步骤 3:配置 postcss-pxtorem

在项目根目录创建postcss.config.js文件,添加以下配置:

js

复制代码
module.exports = {
  plugins: {
    'postcss-pxtorem': {
      rootValue: 37.5, // 设计稿宽度的1/10(假设设计稿为375px)
      propList: ['*'], // 所有CSS属性都转换为rem
      selectorBlackList: ['am-'], // 排除vant组件(vant默认基于375px设计)
      exclude: /node_modules/i // 排除node_modules目录
    }
  }
}

注意:若设计稿为 750px,rootValue 设为 75,但需单独处理 vant 组件(建议统一使用 375px 设计稿)。

方案 2:vw/vh 适配(纯 CSS 方案)

vw/vh 是视口单位,1vw = 视口宽度的 1%,无需 JS 介入,更轻量:

  • 无需安装依赖,直接在 CSS 中使用 vw 单位

  • 示例(设计稿 375px,元素宽度 100px): css

    复制代码
    .box {
      width: 26.667vw; /* 100/375*100 = 26.667 */
      height: 13.333vw; /* 50/375*100 = 13.333 */
    }

优点:无兼容性问题(移动端浏览器全支持),配置简单;缺点:需手动计算或用插件转换 px 到 vw。

四、集成移动端 UI 组件库

React 移动端开发推荐使用成熟的 UI 库,本文以 Ant Design Mobile(简称 Antd Mobile)为例(React 官方推荐的移动端组件库,适配 React 18)。

1. 安装 Antd Mobile

bash

运行

复制代码
# 安装Antd Mobile 8.x(适配React 18)
npm install antd-mobile

2. 按需引入组件(自动按需引入)

Antd Mobile 支持自动按需引入,无需额外配置,直接在组件中使用即可:

jsx

复制代码
// src/components/ButtonDemo.jsx
import React from 'react'
import { Button } from 'antd-mobile'

const ButtonDemo = () => {
  return (
    <Button color="primary" onClick={() => console.log('点击按钮')}>
      主要按钮
    </Button>
  )
}

export default ButtonDemo

3. 全局样式配置(可选)

若需自定义主题,可在src/index.css中覆盖 Antd Mobile 的默认样式:

css

复制代码
/* 自定义按钮颜色 */
:root {
  --adm-color-primary: #ff6700; /* 替换为自己的主色调 */
}

五、移动端核心功能开发示例

1. 路由配置(React Router)

移动端单页应用离不开路由,使用 React Router 6(最新版)实现页面跳转:

步骤 1:安装 React Router

bash

运行

复制代码
npm install react-router-dom
步骤 2:配置路由

src目录下创建router/index.jsx

jsx

复制代码
// src/router/index.jsx
import { createBrowserRouter, RouterProvider } from 'react-router-dom'
import Home from '../views/Home'
import Detail from '../views/Detail'

// 创建路由实例
const router = createBrowserRouter([
  {
    path: '/',
    element: <Home />, // 首页
  },
  {
    path: '/detail/:id', // 详情页(带参数)
    element: <Detail />,
  },
])

// 路由组件导出
const AppRouter = () => {
  return <RouterProvider router={router} />
}

export default AppRouter
步骤 3:修改入口组件

jsx

复制代码
// src/App.jsx
import React from 'react'
import AppRouter from './router'

function App() {
  return (
    <div className="app">
      <AppRouter />
    </div>
  )
}

export default App
步骤 4:页面跳转示例

jsx

复制代码
// src/views/Home.jsx
import React from 'react'
import { Link, useNavigate } from 'react-router-dom'
import { Button, List } from 'antd-mobile'

const Home = () => {
  const navigate = useNavigate()

  // 编程式导航
  const goToDetail = () => {
    navigate('/detail/1', { state: { name: '测试商品' } })
  }

  return (
    <div style={{ padding: '10px' }}>
      <h1>React移动端首页</h1>
      {/* 声明式导航 */}
      <Link to="/detail/2">
        <Button style={{ margin: '10px 0' }}>跳转到详情页(声明式)</Button>
      </Link>
      {/* 编程式导航 */}
      <Button onClick={goToDetail} color="primary">
        跳转到详情页(编程式)
      </Button>
    </div>
  )
}

export default Home

2. 移动端交互功能开发

(1)下拉刷新 / 上拉加载

使用 Antd Mobile 的PullToRefreshInfiniteScroll组件实现:

jsx

复制代码
// src/views/ListDemo.jsx
import React, { useState, useRef } from 'react'
import { PullToRefresh, InfiniteScroll, List, Toast } from 'antd-mobile'

const ListDemo = () => {
  const [data, setData] = useState([])
  const [loading, setLoading] = useState(false)
  const [hasMore, setHasMore] = useState(true)
  const loader = useRef(null)

  // 下拉刷新
  const onRefresh = async () => {
    Toast.loading('刷新中...', 0)
    // 模拟接口请求
    await new Promise(resolve => setTimeout(resolve, 1000))
    setData(Array.from({ length: 10 }, (_, i) => `刷新后数据 ${i + 1}`))
    Toast.hide()
  }

  // 上拉加载
  const loadMore = async () => {
    if (loading) return
    setLoading(true)
    // 模拟接口请求
    await new Promise(resolve => setTimeout(resolve, 1000))
    const newData = Array.from({ length: 10 }, (_, i) => `加载后数据 ${data.length + i + 1}`)
    setData([...data, ...newData])
    setLoading(false)
    // 模拟数据加载完成
    if (data.length + newData.length >= 30) {
      setHasMore(false)
    }
  }

  return (
    <PullToRefresh onRefresh={onRefresh}>
      <InfiniteScroll
        loadMore={loadMore}
        hasMore={hasMore}
        isLoading={loading}
        loader={loader}
        className="infinite-scroll-container"
      >
        <List>
          {data.map((item, index) => (
            <List.Item key={index}>{item}</List.Item>
          ))}
        </List>
      </InfiniteScroll>
    </PullToRefresh>
  )
}

export default ListDemo
(2)移动端点击优化

移动端原生点击有 300ms 延迟,可通过以下方式优化:

  • 使用touchstart事件替代click(注意防止穿透):

    jsx

    复制代码
    <Button onTouchStart={() => console.log('快速点击')}>无延迟按钮</Button>
  • 引入fastclick库(兼容低版本浏览器):

    bash

    运行

    复制代码
    npm install fastclick

    main.jsx中引入:

    jsx

    复制代码
    import FastClick from 'fastclick'
    FastClick.attach(document.body)

六、项目打包与发布

1. 优化打包配置

修改vite.config.js,优化移动端打包体积和性能:

jsx

复制代码
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'
import { resolve } from 'path'

// https://vitejs.dev/config/
export default defineConfig({
  plugins: [react()],
  // 路径别名
  resolve: {
    alias: {
      '@': resolve(__dirname, 'src'),
    },
  },
  // 开发服务器配置(解决跨域)
  server: {
    port: 5173,
    proxy: {
      '/api': {
        target: 'https://api.example.com', // 后端接口地址
        changeOrigin: true,
        rewrite: (path) => path.replace(/^\/api/, ''),
      },
    },
  },
  // 打包配置
  build: {
    outDir: 'dist', // 输出目录
    assetsDir: 'static', // 静态资源目录
    minify: 'terser', // 压缩代码
    terserOptions: {
      compress: {
        drop_console: true, // 移除console.log
        drop_debugger: true, // 移除debugger
      },
    },
    // 分包配置,减小主包体积
    rollupOptions: {
      output: {
        chunkFileNames: 'static/js/[name]-[hash].js',
        entryFileNames: 'static/js/[name]-[hash].js',
        assetFileNames: 'static/[ext]/[name]-[hash].[ext]',
      },
    },
  },
})

2. 执行打包

bash

运行

复制代码
npm run build  # 或 pnpm build

打包完成后,dist目录即为可部署的静态文件。

3. 移动端调试与发布

  • 本地调试:手机连接同一局域网,访问电脑 IP + 端口(如http://192.168.1.100:5173
  • 真机调试:
    • Chrome:打开chrome://inspect,连接安卓设备即可调试
    • Safari:开启 iOS 开发者模式,连接 Mac 进行调试
  • 发布部署:
    • dist目录上传到 Nginx、阿里云 OSS、腾讯云 COS 等静态服务器
    • 也可使用 Netlify、Vercel 等平台一键部署(无需配置服务器)

七、常见问题与解决方案

  1. 适配异常 :部分设备显示比例不对 → 检查amfe-flexible是否引入,postcss-pxtorem的 rootValue 是否匹配设计稿

  2. 组件样式失效:Antd Mobile 组件样式不显示 → 确认组件版本与 React 版本兼容(Antd Mobile 8.x 适配 React 18)

  3. 打包体积过大

    • 开启按需引入(Antd Mobile 默认支持)
    • 使用vite-plugin-imagemin压缩图片
    • 拆分第三方库(如 React、React Router 单独分包)
  4. 移动端键盘遮挡输入框

    jsx

    复制代码
    // 监听键盘弹出事件,调整页面高度
    useEffect(() => {
      const handleResize = () => {
        const windowHeight = window.innerHeight
        document.body.style.minHeight = `${windowHeight}px`
      }
      window.addEventListener('resize', handleResize)
      return () => window.removeEventListener('resize', handleResize)
    }, [])
  5. 路由刷新 404 :部署后刷新页面报 404 → Nginx 配置try_files $uri $uri/ /index.html;,或使用createHashRouter替代createBrowserRouter

八、总结

本文完整覆盖了 React 移动端项目的搭建全流程:从环境准备→项目初始化(Vite+React 18)→移动端适配(rem/vw)→UI 库集成(Antd Mobile)→核心功能开发(路由、下拉刷新、交互优化)→打包发布。

核心要点:

  1. 适配方案优先选择 rem(兼容性好)或 vw(配置简单);
  2. UI 库推荐 Antd Mobile(React 生态适配最好);
  3. 打包优化重点是按需引入和分包,减小移动端加载体积;
  4. 调试时注意移动端特有问题(点击延迟、键盘遮挡、屏幕适配)。

掌握这套流程后,你可以快速搭建电商、资讯、工具类等各类 React 移动端项目,后续可深入学习 React Hooks、状态管理(Redux Toolkit/Zustand)、移动端性能优化等内容,提升项目体验。

相关推荐
智航GIS5 小时前
ArcGIS大师之路500技---035道路线转面
arcgis
智航GIS5 小时前
ArcGIS大师之路500技---018数据驱动
arcgis
智航GIS15 小时前
ArcGIS大师之路500技---008创建渔网
arcgis
智航GIS1 天前
ArcGIS大师之路500技---007自动完成面
arcgis
亚洲小炫风1 天前
静态网页如何国际化
arcgis
智航GIS1 天前
ArcGIS大师之路500技---010属性自动赋值
arcgis
智航GIS1 天前
ArcGIS大师之路500技---006锚点的使用
arcgis
智航GIS1 天前
ArcGIS大师之路500技---009属性映射
arcgis
智航GIS2 天前
ArcGIS大师之路500技---005粘滞移动容差设置
arcgis