You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Expo-Camera网页端拍照仅获640x480分辨率问题咨询

问题

在移动端Chrome 127/128、Firefox 127浏览器中使用expo-camera拍照时,即使设置pictureSize属性或takePictureAsync的quality=1参数,捕获的图像分辨率始终固定为640×480。但在Android/iOS原生Expo环境下,可通过pictureSize正常修改分辨率。

依赖版本:

  • expo: ^51.0.31
  • expo-camera: ^15.0.15
  • react-native: 0.74.3

已尝试:调用getAvailablePictureSizesAsync获取可用尺寸并切换pictureSize,但问题未解决。


原因分析

expo-camera在Web端(包括移动端浏览器)的实现基于浏览器原生getUserMedia API和canvas渲染,存在以下限制:

  1. 浏览器对摄像头捕获流有默认分辨率限制,部分移动端浏览器会强制将默认流压缩至640×480
  2. expo-camera的Web适配层未完全兼容pictureSize参数,takePictureAsync的quality参数在Web端的压缩逻辑与原生环境不同
  3. 自动处理流程(如skipProcessing=false时的压缩)会忽略自定义分辨率设置

解决方案

方案1:直接使用浏览器原生API捕获高分辨率图像

绕过expo-camera的Web限制,直接调用getUserMedia获取原始摄像头流,通过canvas导出高分辨率图像:

import { useState, useRef, useEffect } from 'react';

const WebCameraCapture = () => {
  const videoRef = useRef(null);
  const canvasRef = useRef(null);
  const [capturedPhotos, setCapturedPhotos] = useState([]);

  useEffect(() => {
    const startCamera = async () => {
      try {
        const stream = await navigator.mediaDevices.getUserMedia({
          video: {
            width: { ideal: 3840 }, // 设置理想分辨率,浏览器会匹配最接近的可用值
            height: { ideal: 2160 },
            facingMode: 'environment' // 指定后置摄像头
          }
        });
        if (videoRef.current) {
          videoRef.current.srcObject = stream;
        }
      } catch (err) {
        console.error('摄像头启动失败:', err);
      }
    };

    startCamera();
    // 组件卸载时停止摄像头流
    return () => {
      if (videoRef.current?.srcObject) {
        const stream = videoRef.current.srcObject;
        stream.getTracks().forEach(track => track.stop());
      }
    };
  }, []);

  const takePicture = () => {
    if (!videoRef.current || !canvasRef.current) return;

    const video = videoRef.current;
    const canvas = canvasRef.current;
    // 同步canvas尺寸与视频实际分辨率
    canvas.width = video.videoWidth;
    canvas.height = video.videoHeight;
    
    const ctx = canvas.getContext('2d');
    ctx.drawImage(video, 0, 0, canvas.width, canvas.height);
    
    // 导出为PNG格式的DataURL
    const dataUrl = canvas.toDataURL('image/png');
    setCapturedPhotos(prev => [...prev, dataUrl]);
    console.log(`捕获图像尺寸: ${canvas.width}x${canvas.height}`);
  };

  return (
    <div>
      <video ref={videoRef} autoPlay playsInline style={{ width: '100%', height: 'auto' }} />
      <canvas ref={canvasRef} style={{ display: 'none' }} />
      <button onClick={takePicture}>拍照</button>
      {capturedPhotos.map((url, idx) => (
        <img key={idx} src={url} style={{ maxWidth: '200px', margin: '10px' }} alt={`捕获的照片${idx}`} />
      ))}
    </div>
  );
};

export default WebCameraCapture;

方案2:调整expo-camera的Web配置与参数

  1. 在app.json中添加Web摄像头权限与分辨率配置:
{
  "expo": {
    "web": {
      "permissions": {
        "camera": {
          "description": "需要访问摄像头进行拍照"
        }
      },
      "config": {
        "camera": {
          "video": {
            "width": 3840,
            "height": 2160
          }
        }
      }
    }
  }
}
  1. 修改takePictureAsync参数,跳过自动处理流程:
const options = {
  quality: 1,
  imageType: 'png',
  skipProcessing: true, // 跳过Web端的自动压缩处理
  exif: true,
};

方案3:确认浏览器支持的分辨率并适配

先查询当前设备摄像头支持的实际分辨率,再针对性设置pictureSize:

const getSupportedResolutions = async () => {
  const devices = await navigator.mediaDevices.enumerateDevices();
  const videoDevices = devices.filter(device => device.kind === 'videoinput');
  
  for (const device of videoDevices) {
    const stream = await navigator.mediaDevices.getUserMedia({
      video: { deviceId: device.deviceId }
    });
    const track = stream.getVideoTracks()[0];
    const settings = track.getSettings();
    console.log(`设备${device.label}支持的分辨率: ${settings.width}x${settings.height}`);
    track.stop();
  }
};

// 组件初始化时调用查询
useEffect(() => {
  getSupportedResolutions();
}, []);

根据查询结果,设置pictureSize为浏览器支持的最高分辨率(Web端格式为widthxheight,与Android的heightxwidth区分)。


内容的提问来源于stack exchange,提问作者user27023380

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.19 02:17:14