更新记录

1.0.0(2026-11-11) 下载此版本

首个版本发布。

新增

  • 基于 camera 组件 scanCode 模式的扫码界面,支持 App-Android / App-iOS
  • 自定义扫描框尺寸、四角颜色、扫描线颜色、遮罩颜色
  • 单向扫描线动画,逐帧推进实现,双端表现一致
  • 真闪光灯控制(flash="torch")
  • 连续扫码模式,支持同一内容时间窗口去重
  • 手动输入弹窗,支持无摄像头场景兜底
  • 识别成功震动反馈,可关闭
  • 自动适配状态栏高度与底部安全区
  • 相机权限被拒绝时给出可读提示
  • 支持 v-model:visible 双向绑定
  • 暴露 open / close / toggleTorch / isTorchOn 方法
  • 提供 right 具名插槽,可在标题栏右侧扩展按钮

说明

  • 相册图片识别未内置:uni-app x 未提供图片条码解码 API,需要原生插件配合,组件仅抛出 album 事件
  • 使用前必须在 manifest.json 中勾选 uni-barcode-scanning 模块

平台兼容性

uni-app x(4.71)

Chrome Safari Android iOS 鸿蒙 微信小程序
× × √ √ √ √

其他

多语言 暗黑模式 宽屏模式 蒸汽模式
√ √ √ √

erha-scan-code 自定义扫码

uni-app x 自定义扫码界面组件。基于官方 camera 组件的 scanCode 模式封装,把「能识别」升级成「好看、好用、能定制」。

支持平台:App-Android / App-iOS 最低版本:HBuilderX 4.71+(camera 组件扫码能力自 4.71 起提供)


为什么需要它

官方 uni.scanCode 在 Android / iOS 上调用的是内置开源页面,扫出来的界面长什么样由不得你改。而 camera 组件的 scanCode 模式虽然能自定义,但要自己处理取景框、遮罩、扫描线、闪光灯、重复识别、返回键……一个细节没做好,用户就会觉得「这像个半成品」。

本组件把这些都做好了,你只需要写一行标签。

能力 说明
自定义扫描框 尺寸、四角颜色、扫描线颜色均可配置
扫描线动画 逐帧推进的单向扫描线,Android / iOS 表现一致
真闪光灯 基于 flash="torch",是真正的补光灯,不是调屏幕亮度
连续扫码 开启后可连续识别,内置时间窗口去重,避免一次对准触发多次
手动输入 弹窗输入内容,扫码枪/无摄像头场景的兜底
震动反馈 识别成功触发短震动
安全区适配 自动处理状态栏高度与底部安全区
沉浸式全屏 全屏遮罩,盖在当前页面上,不跳页
权限失败提示 相机被拒绝时给出可读的引导文案

安装

把 uni_modules/erha-scan-code 整个目录丢进你项目的 uni_modules/ 下。easycom 已配置好,不需要 import。

your-project/
├── uni_modules/
│   └── erha-scan-code/
├── pages/
└── manifest.json

必看:配置扫码模块

这是唯一一个「漏了就跑不起来」的步骤。camera 的扫码能力由独立模块提供,不勾选的话相机会正常预览,但永远不会触发 scancode 事件。

在 manifest.json 中配置:

{
  "app-android": {
    "distribute": {
      "modules": {
        "uni-barcode-scanning": {}
      }
    }
  },
  "app-ios": {
    "distribute": {
      "modules": {
        "uni-barcode-scanning": {}
      }
    }
  }
}

用 HBuilderX 图形界面操作则是:manifest.json → App 其他配置 → 模块配置 → 勾选「uni-barcode-scanning(相机组件扫码)」。

同时在 Android 端声明相机权限:

"permissions": [
  "<uses-permission android:name=\"android.permission.CAMERA\"/>"
]

iOS 端需要相机用途描述:

"privacyDescription": {
  "NSCameraUsageDescription": "需要使用相机扫描二维码和条形码"
}

快速开始

<template>
  <view>
    <button @click="scanVisible = true">***</button>

    <erha-scan-code
      v-model:visible="scanVisible"
      title="***"
      @success="onScanSuccess"
    />
  </view>
</template>

<script setup>
  import { ErhaScanResult } from '@/uni_modules/erha-scan-code/components/erha-scan-code/type.uts'

  const scanVisible = ref(false)

  function onScanSuccess(res : ErhaScanResult) {
    console.log('内容:', res.result)
    console.log('码类型:', res.scanType)
  }
</script>

v-model:visible 会自动双向同步。识别成功后组件会自动关闭(连续扫码模式除外)。


Props

参数 类型 默认值 说明
visible Boolean false 是否显示,支持 v-model:visible
title String '***' 顶部标题
tipText String '将二维码/条码放入框内,即可自动识别' 扫描框下方提示,传空串隐藏
frameSize Number 240 扫描框边长,单位 px
frameColor String '#22D3A6' 扫描框四角颜色
scanLineColor String '#22D3A6' 扫描线颜色,传空串隐藏扫描线
maskColor String 'rgba(0, 0, 0, 0.55)' 扫描框外遮罩颜色
tipColor String '#FFFFFF' 提示文字与操作按钮文字颜色
headerBgColor String 'rgba(0, 0, 0, 0.35)' 顶部标题栏背景色
headerTextColor String '#FFFFFF' 顶部标题文字颜色
showHeader Boolean true 是否显示顶部标题栏
showActions Boolean true 是否显示底部操作栏
showTorch Boolean true 是否显示闪光灯按钮
showManual Boolean true 是否显示手动输入按钮
showAlbum Boolean false 是否显示相册按钮(见下方说明)
continuous Boolean false 连续扫码,识别后不自动关闭
scanInterval Number 1500 连续扫码时同一内容的去重间隔,单位 ms
vibrate Boolean true 识别成功是否震动
manualPlaceholder String '请输入二维码/条码内容' 手动输入框占位文字
themeColor String '#22D3A6' 主题色(确认按钮、闪光灯高亮)
resolution String 'high' 相机预览分辨率:low / medium / high

关于 showAlbum

uni-app x 没有提供「解码图片中的条码」的 API,纯 UTS 无法实现相册识别,需要原生插件配合。

因此本组件不内置相册识别,showAlbum 只负责显示一个按钮位并抛出 album 事件,由你接入自己的识别服务或原生插件。默认关闭,避免给出看起来能用、实际不行的假功能。


Events

事件 参数 说明
success ErhaScanResult 识别成功
fail ErhaScanFail 相机启动失败等错误
close - 用户点了返回或识别成功后自动关闭
album - 点了相册按钮(需 showAlbum)
torchChange Boolean 闪光灯开关变化
update:visible Boolean 配合 v-model:visible

ErhaScanResult

{
  result : string    // 识别内容
  scanType : string  // 码类型,qrCode / barCode / datamatrix / pdf417
  rawData : string   // 原始数据
  charSet : string   // 字符编码
  scanArea : number[] // 码在画面中的区域,部分设备为空
}

方法

通过 ref 调用:

<erha-scan-code ref="scanRef" :visible="false" />

<script setup>
  const scanRef = ref<ErhaScanCodeExpose | null>(null)

  scanRef.value?.open()          // 打开
  scanRef.value?.close()         // 关闭
  scanRef.value?.toggleTorch()   // 开关闪光灯
  scanRef.value?.isTorchOn()     // 当前闪光灯状态
</script>

重要:安卓返回键处理

onBackPress 是页面级生命周期,写在自定义组件里不会生效。如果不处理,用户在全屏扫码时按安卓返回键,会直接退出当前页面。

请在使用组件的页面里加这段:

<script setup>
  const scanVisible = ref(false)

  onBackPress(() : boolean => {
    if (scanVisible.value) {
      scanVisible.value = false
      return true   // 拦截返回,只关闭扫码
    }
    return false
  })
</script>

demo 页面 pages/index/index.uvue 中已有完整实现,可直接照抄。


常见问题

Q:相机能预览,但扫不出结果、success 不触发?

99% 是没勾选 uni-barcode-scanning 模块。见上方「必看:配置扫码模块」。改完需要重新打包基座,热刷新不生效。

Q:H5 / 小程序能跑吗?

不能。camera 组件的 scanCode 模式仅 App-Android / App-iOS 支持。H5 端浏览器会提示 camera 不支持,小程序端请直接用平台的 uni.scanCode。

Q:想改扫描框的形状(圆形 / 带圆角)?

组件把扫描框暴露为 .zj-scan__frame,可通过父级样式覆盖:

/* 注意:需要关闭样式隔离或在组件内调整 */
.zj-scan__frame {
  border-radius: 24px;
}

如需深度定制,直接改组件源码中的 <style> 即可,源码无混淆。

Q:识别距离太近 / 太远?

调整 resolution(默认 high 兼顾清晰度与速度)。若追求识别速度,可改为 medium。

Q:能改成一打开就扫码、不要按钮吗?

<erha-scan-code v-model:visible="scanVisible" title="" :show-actions="false" :show-header="false" />

此时需要自己在页面上放一个关闭入口,或依赖返回键。


更新日志

见 changelog.md。

License

MIT

隐私、权限声明

1. 本插件需要申请的系统权限列表:

相机

2. 本插件采集的数据、发送的服务器地址、以及数据用途说明:

无

3. 本插件是否包含广告,如包含需详细说明广告表达方式、展示频率:

无

许可协议

MIT协议

暂无用户评论。