extension-qr-code

extension-qr-code

使用摄像头扫描二维码。

0Star
0Fork
更新于 2026/7/13
SKILL.md
readonly只读
name
extension-qr-code
description

使用摄像头扫描二维码。

version
0.1.4

二维码扫描器

用于 Caffeine AI 的二维码扫描扩展。

概述

此技能通过设备摄像头添加二维码扫描功能。基于摄像头组件和 jsQR 解码库构建。

前端

对于二维码扫描器的支持:

有一个从 @caffeinelabs/qr-code 导入的预置 React 钩子,不可修改。

import { RefObject } from 'react';
import { CameraConfig, CameraError } from '@caffeineai/camera';

export interface QRResult {
  // 解码后的二维码数据
  data: string;
  // 二维码扫描时的时间戳
  timestamp: number;
}

export interface QRScannerConfig extends CameraConfig {
  // 扫描二维码的间隔(毫秒,默认:100)
  scanInterval?: number;
  // 历史记录中保留的最大结果数(默认:10)
  maxResults?: number;
  // 加载 jsQR 库的 URL(默认:jsdelivr CDN)
  jsQRUrl?: string;
}

export interface UseQRScannerReturn {
  // 扫描到的二维码数组(最新在前)
  qrResults: QRResult[];
  // 当前是否正在扫描二维码
  isScanning: boolean;
  // jsQR 库是否已加载
  jsQRLoaded: boolean;
  
  // 摄像头状态(从 useCamera 透传)
  isActive: boolean;
  isSupported: boolean | null;
  error: CameraError | null;
  isLoading: boolean;
  currentFacingMode: 'user' | 'environment';
  
  // 启动摄像头并开始扫描 - 成功返回 true
  startScanning: () => Promise<boolean>;
  // 停止扫描和摄像头
  stopScanning: () => Promise<void>;
  // 切换摄像头方向 - 成功返回 true
  switchCamera: () => Promise<boolean>;
  // 清除所有扫描结果
  clearResults: () => void;
  // 重置扫描器状态(停止扫描并清除结果)
  reset: () => void;
  // 出错后重试摄像头初始化 - 成功返回 true
  retry: () => Promise<boolean>;
  
  // 附加到视频元素用于摄像头预览的 ref
  videoRef: RefObject<HTMLVideoElement>;
  // 附加到用于二维码处理的 canvas 元素的 ref(可隐藏)
  canvasRef: RefObject<HTMLCanvasElement>;
  
  // 计算状态
  // 扫描器是否准备好使用(jsQR 已加载且摄像头支持)
  isReady: boolean;
  // 是否可以开始扫描(准备好且未加载中)
  canStartScanning: boolean;
}

export declare function useQRScanner(config?: QRScannerConfig): UseQRScannerReturn;

使用示例:

import { useQRScanner } from '@caffeineai/qr-code';

function QRScannerComponent() {
    const { 
        qrResults,
        isScanning,
        isActive,
        isSupported,
        error,
        isLoading,
        canStartScanning,
        startScanning,
        stopScanning,
        switchCamera,
        clearResults,
        videoRef,
        canvasRef 
    } = useQRScanner({ 
        facingMode: 'environment',
        scanInterval: 100,
        maxResults: 5
    });

    if (isSupported === false) {
        return <div>摄像头不受支持</div>;
    }

    return (
        <div>
            <video 
                ref={videoRef} 
                style={{ width: '100%', height: 'auto' }}
                playsInline
                muted
            />
            <canvas ref={canvasRef} style={{ display: 'none' }} />
            
            {error && <div>错误:{error.message}</div>}
            
            <div>
                <button onClick={startScanning} disabled={!canStartScanning}>
                    开始扫描
                </button>
                <button onClick={stopScanning} disabled={isLoading || !isActive}>
                    停止扫描
                </button>
                {/* 仅在移动设备上显示切换摄像头 */}
                {/Android|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent) && (
                    <button onClick={switchCamera} disabled={isLoading || !isActive}>
                        切换摄像头
                    </button>
                )}
            </div>
            
            <div>
                <h3>结果 {qrResults.length > 0 && <button onClick={clearResults}>清除</button>}</h3>
                {qrResults.map(result => (
                    <div key={result.timestamp}>
                        <small>{new Date(result.timestamp).toLocaleTimeString()}</small>
                        <p>{result.data}</p>
                    </div>
                ))}
            </div>
        </div>
    );
}

在应用中正确显示二维码扫描器的错误信息。