uniapp基础 (一)

目录

[UniApp 是什么?有什么优势](#UniApp 是什么?有什么优势)

跨平台高效开发

[Vue.js 技术生态](#Vue.js 技术生态)

插件生态丰富

渐进式开发支持

[UniApp 跨平台兼容的实现原理](#UniApp 跨平台兼容的实现原理)

编译时转

运行时适配层

条件编译

性能优化策略

1.预编译模

2.原生组件混合渲

3.分包加载

[UniApp 的生命周期钩子有哪些?](#UniApp 的生命周期钩子有哪些?)

应用生命周期钩子

页面生命周期钩子

组件生命周期钩子

注意事项

[UniApp 与原生小程序生命周期的区别](#UniApp 与原生小程序生命周期的区别)

生命周期钩子名称不同

生命周期调用顺序不同

组件生命周期支持不同

全局生命周期扩展

兼容性差异

[UniApp 的页面路由?如何实现页面跳转?](#UniApp 的页面路由?如何实现页面跳转?)

路由配置

路由跳转方法

1.navigateTo

2.redirectTo

3.reLaunch

4.switchTab

5.navigateBack

预加载页面(preloadPage)

路由传参

路由拦截

动态路由

注意事项

[UniApp 支持哪些小程序平台](#UniApp 支持哪些小程序平台)

[UniApp 全局样式/局部样式](#UniApp 全局样式/局部样式)

全局样式

局部样式

样式优先级与注意事项

[pages.json 核心字段](#pages.json 核心字段)


UniApp 是什么?有什么优势

UniApp 是一个使用 Vue.js 开发跨平台应用的框架。

跨平台高效开发

  • 采用 "一次编写,多端发布" 模式,显著降低开发成本
  • 支持 14+ 平台编译,覆盖主流移动端、Web 端及小程序生态
  • 开发效率提升约 300%(相较原生多端独立开发)

Vue.js 技术生态

  • 完全兼容 Vue.js 语法,前端开发者零门槛上手
  • 支持 Vuex 状态管理、Vue Router 路由等核心能力
javascript 复制代码
<template>
  <view class="container">
    <text>{{ message }}</text>
  </view>
</template>
<script>
export default {
  data() {
    return { message: "Hello UniApp!" }
  }
}
</script>

插件生态丰富

  • 官方插件市场提供 2000+ 即用组件
  • 支持第三方 SDK 便捷集成(如支付、推送、统计)
  • 示例:一键集成微信登录功能
javascript 复制代码
uni.login({
  provider: 'weixin',
  success: res => console.log(res.code)
})

渐进式开发支持

  • 支持混合开发模式:可嵌入原生页面或与原生代码互调
  • 提供条件编译指令实现平台差异化
javascript 复制代码
// #ifdef H5
console.log("当前运行在Web环境");
// #endif

UniApp 跨平台兼容的实现原理

编译时转

UniApp 使用 Vue.js 作为开发语法,在编译阶段通过条件编译和代码转换技术,将 Vue 代码转换为目标平台(如微信小程序、H5、iOS、Android 等)的原生代码。

运行时适配层

UniApp 在运行时通过统一的 JavaScript 核心引擎(如 V8 或 JavaScriptCore)执行逻辑代码,同时提供一套跨平台的 API 抽象层。这些 API 在调用时动态映射到不同平台的原生 API 上,例如 uni.request 在微信小程序中会转换为 wx.request,在 H5 中则使用 XMLHttpRequestfetch

条件编译

javascript 复制代码
// 条件编译示例
#ifdef MP-WEIXIN
console.log('这是微信小程序环境');
#endif

性能优化策略

1.预编译模

在非 H5 平台(如小程序),模板会在编译时预先转换为目标平台的模板语言,减少运行时的解析开销。

2.原生组件混合渲

对于高性能需求场景(如地图、视频),UniApp 允许直接调用平台原生组件,与框架组件混合渲染。

3.分包加载

支持将应用拆分为多个子包,按需加载以提升启动速度,尤其在微信小程序等对包大小有限制的平台中。

UniApp 的生命周期钩子有哪些?

UniApp 的生命周期钩子分为应用生命周期页面生命周期组件生命周期三部分

应用生命周期钩子

应用生命周期钩子在 App.vue 中定义,用于监听整个应用的全局状态。

  • onLaunch:应用初始化时触发,全局只触发一次。
  • onShow:应用启动或从后台进入前台时触发。
  • onHide:应用从前台进入后台时触发。
  • onError:应用发生脚本错误或 API 调用失败时触发。
  • onUnhandledRejection:应用未处理的 Promise 拒绝事件触发。
javascript 复制代码
// App.vue 示例
export default {
  onLaunch(options) {
    console.log('应用初始化', options);
  },
  onShow(options) {
    console.log('应用显示', options);
  },
  onHide() {
    console.log('应用隐藏');
  }
}

页面生命周期钩子

页面生命周期钩子在页面(.vue 文件)中定义,用于监听页面的加载、显示、隐藏等状态。

  • onLoad:页面加载时触发,接收页面参数。
  • onShow:页面显示时触发。
  • onReady:页面初次渲染完成时触发。
  • onHide:页面隐藏时触发。
  • onUnload:页面卸载时触发。
  • onPullDownRefresh:页面下拉刷新时触发。
  • onReachBottom:页面上拉触底时触发。
  • onShareAppMessage:点击右上角分享时触发。
  • onPageScroll:页面滚动时触发。
  • onResize:页面尺寸变化时触发(如横竖屏切换)。
javascript 复制代码
// 页面示例
export default {
  onLoad(options) {
    console.log('页面加载', options);
  },
  onShow() {
    console.log('页面显示');
  },
  onReady() {
    console.log('页面渲染完成');
  }
}

组件生命周期钩子

组件生命周期钩子在自定义组件中定义,与 Vue 的生命周期类似,但增加了 UniApp 特有的钩子。

  • beforeCreate:组件实例初始化之前触发。
  • created:组件实例创建完成时触发。
  • beforeMount:组件挂载到 DOM 前触发。
  • mounted:组件挂载到 DOM 后触发。
  • beforeUpdate:组件数据更新前触发。
  • updated:组件数据更新后触发。
  • beforeDestroy:组件销毁前触发。
  • destroyed:组件销毁后触发。
  • onBackPress:页面返回按钮按下时触发(仅 H5 和 App 支持)。
javascript 复制代码
// 组件示例
export default {
  created() {
    console.log('组件创建完成');
  },
  mounted() {
    console.log('组件挂载完成');
  },
  onBackPress() {
    console.log('返回按钮按下');
  }
}

注意事项

  1. 应用生命周期App.vue 可用,pages 和组件中无效。
  2. 页面生命周期仅在页面中可用,组件中无效。
  3. 组件生命周期 与 Vue 保持一致,但需注意平台差异(如 onBackPress 仅部分平台支持)。
  4. 部分钩子(如 onPullDownRefresh)需在 pages.json 中配置启用。

UniApp 与原生小程序生命周期的区别

生命周期钩子名称不同

  • 原生小程序的页面生命周期钩子以 on 开头,例如 onLoadonShow
  • UniApp 的生命周期钩子名称与 Vue 类似,例如 createdmounted,同时兼容小程序的钩子。

生命周期调用顺序不同

  • UniApp :在页面加载时,会先触发 Vue 的生命周期(如 createdmounted),再触发小程序的页面生命周期(如 onLoadonShow)。
  • 原生小程序 :仅触发自身的页面生命周期钩子(如 onLoadonShow),没有 Vue 的生命周期。

组件生命周期支持不同

  • UniApp :支持 Vue 的组件生命周期(如 createdmounted),适用于组件开发。
  • 原生小程序 :组件使用 lifetimes 字段定义生命周期(如 attacheddetached),与页面生命周期不同。

全局生命周期扩展

  • UniApp :支持应用级别的生命周期(如 onLaunchonShow),同时兼容 Vue 的全局逻辑。
  • 原生小程序 :仅支持 App 中定义的生命周期(如 onLaunchonShow),无法直接使用 Vue 的全局逻辑。

兼容性差异

  • UniApp 的生命周期设计是为了兼容多端(H5、小程序、App),因此部分钩子在特定平台可能不生效。
  • 原生小程序的生命周期仅针对微信小程序,不存在跨平台兼容问题。

UniApp 的页面路由?如何实现页面跳转?

路由配置

UniApp 的路由配置在 pages.json 文件中完成。每个页面需要在此文件中注册,否则无法跳转。配置示例:

javascript 复制代码
{
  "pages": [
    {
      "path": "pages/index/index",
      "style": {
        "navigationBarTitleText": "首页"
      }
    },
    {
      "path": "pages/detail/detail",
      "style": {
        "navigationBarTitleText": "详情页"
      }
    }
  ]
}

路由跳转方法

1.navigateTo

navigateTo 保留当前页面,跳转到新页面:

javascript 复制代码
uni.navigateTo({
  url: '/pages/detail/detail?id=1'
});

参数通过 URL 传递,目标页面在 onLoad 生命周期中接收:

javascript 复制代码
onLoad(options) {
  console.log(options.id); // 输出 1
}
2.redirectTo

redirectTo 关闭当前页面,跳转到新页面:

javascript 复制代码
uni.redirectTo({
  url: '/pages/detail/detail?id=1'
});
3.reLaunch

reLaunch 关闭所有页面,打开新页面:

javascript 复制代码
uni.reLaunch({
  url: '/pages/index/index'
});
4.switchTab

switchTab 跳转到 TabBar 页面:

javascript 复制代码
uni.switchTab({
  url: '/pages/tabbar/tabbar'
});
5.navigateBack

navigateBack 返回上一页或多页:

javascript 复制代码
uni.navigateBack({
  delta: 1 // 返回层数
});

预加载页面(preloadPage)

提前加载目标页面资源,提升用户体验:

javascript 复制代码
uni.preloadPage({
  url: '/pages/detail/detail'
});

路由传参

跳转时可以传递参数,目标页面通过 onLoad 生命周期接收:

javascript 复制代码
// 跳转时传递参数
uni.navigateTo({
  url: '/pages/detail/detail?id=1&name=test'
});

// 目标页面接收参数
onLoad(options) {
  console.log(options.id); // 输出 1
  console.log(options.name); // 输出 test
}

路由拦截

可以通过全局前置守卫 beforeEach 实现路由拦截:

javascript 复制代码
// main.js 中设置
uni.addInterceptor('navigateTo', {
  invoke(args) {
    if (!hasLogin()) {
      uni.redirectTo({
        url: '/pages/login/login'
      });
      return false;
    }
    return true;
  }
});

动态路由

UniApp 支持动态路由,通过 : 定义参数:

json 复制代码
{
  "path": "pages/detail/:id"
}

跳转时传递动态参数:

javascript 复制代码
uni.navigateTo({
  url: '/pages/detail/1'
});

目标页面通过 this.$route.params 获取参数:

javascript 复制代码
onLoad() {
  console.log(this.$route.params.id); // 输出 1
}

注意事项

  • 跳转 TabBar 页面必须使用 switchTab
  • 跳转路径需以 / 开头,对应 pages.json 中的配置。
  • navigateTo 不能跳转到 TabBar 页面。
  • 路由传参长度有限制,建议传递必要参数。
  • 动态路由需要确保路径匹配,否则可能无法跳转。

UniApp 支持哪些小程序平台

manifest.json 中配置平台

json 复制代码
{
  "mp-weixin": {
    "appid": "微信AppID"
  }
}

UniApp 是一个跨平台开发框架,支持编译到多个小程序平台。以下是目前主流支持的平台:

  1. 微信小程序
  2. 支付宝小程序
  3. 百度智能小程序
  4. 字节跳动小程序(抖音、今日头条等)
  5. QQ小程序
  6. 快手小程序
  7. 飞书小程序
  8. 钉钉小程序
  9. 京东小程序

使用 process.env.UNI_PLATFORM 判断平台,实现差异化逻辑。

UniApp 全局样式/局部样式

全局样式

全局样式适用于整个项目,可通过 App.vue 文件或在 uni.scss 中定义。在 App.vue<style> 标签中编写的样式默认全局生效,但需注意避免样式污染。

uni.scss 中定义 SCSS 变量或混合器,其他文件通过 @import 引入即可使用。例如:

css 复制代码
$primary-color: #007AFF;

项目根目录的 common 文件夹可存放公共样式文件(如 common.css),在需要的页面通过 @import 引入。UniApp 默认会编译所有页面和组件的样式,全局样式无需手动引入。

局部样式

局部样式通过单文件组件(.vue 文件)的 <style> 标签实现。添加 scoped 属性可限制样式仅作用于当前组件,例如:

css 复制代码
<style scoped>
.button {
  background: $primary-color;
}
</style>

样式优先级与注意事项

UniApp 中样式优先级遵循 CSS 规则,但需注意:

  • 全局样式可能被局部样式覆盖
  • !important 会提高样式优先级
  • scoped 样式通过添加属性选择器实现隔离

跨平台样式差异可通过条件编译处理:

vue 复制代码
/* #ifdef H5 */
.h5-style { color: blue; }
/* #endif */

pages.json 核心字段

pages

必填字段,用于配置应用页面路径及窗口表现。每个页面配置包含以下属性:

  • path:页面路径,需在根目录下创建对应文件(如 pages/index/index)。
  • style:页面窗口样式,可覆盖全局配置,支持 navigationBarTitleText(标题)、navigationBarBackgroundColor(导航栏背景色)等。

globalStyle

全局默认窗口样式,适用于所有页面。常见字段包括:

  • navigationBarTextStyle:导航栏标题颜色(black/white)。
  • navigationBarTitleText:默认标题文字。
  • backgroundColor:窗口背景色。
  • enablePullDownRefresh:是否开启下拉刷新(默认为 false)。

tabBar

配置底部或顶部选项卡栏,需包含以下子字段:

  • list:数组形式,每个选项卡需配置 pagePath(页面路径)、text(显示文字)、iconPath(未选中图标路径)、selectedIconPath(选中图标路径)。
  • color:选项卡默认颜色。
  • selectedColor:选中时颜色。
  • backgroundColor:选项卡背景色。

condition

用于配置启动模式的条件,仅开发环境生效。支持模拟路径参数、启动页面等场景。

subPackages

分包加载配置,提升首屏加载速度。需指定 root(分包根目录)和 pages(分包页面路径列表)。

preloadRule

配置预加载规则,通过 network(网络条件)和 packages(预加载的分包)优化性能。

easycom

自动按需引入组件配置,简化组件导入。默认规则为 "autoscan": true,支持自定义匹配规则。

usingComponents

手动配置自定义组件路径,适用于非 easycom 模式的组件引入。

示例代码片段

javascript 复制代码
{
  "pages": [
    {
      "path": "pages/index/index",
      "style": {
        "navigationBarTitleText": "首页"
      }
    }
  ],
  "globalStyle": {
    "navigationBarTextStyle": "black",
    "backgroundColor": "#F8F8F8"
  },
  "tabBar": {
    "list": [
      {
        "pagePath": "pages/index/index",
        "text": "首页",
        "iconPath": "static/icons/home.png",
        "selectedIconPath": "static/icons/home-active.png"
      }
    ]
  }
}