前端图片压缩库的选择

kkcode
kkcode
2025-12-10阅读 3657

前端图片上传前压缩,有多个成熟且易用的开源库,覆盖不同场景(简单压缩、高级配置、多格式支持等)。以下是 最推荐的 5 个库,按「易用性 + 功能完整性」排序,附使用场景和快速示例:

一、首选推荐:browser-image-compression(最易用、功能均衡)

核心优势:

  • 零依赖(纯原生 JS),体积小(~10KB)
  • 支持 JPG/PNG/WebP 格式,自动处理透明背景(PNG 转 WebP 不丢透明)
  • 可配置压缩质量、最大宽度/高度、旋转修正(自动修正拍照旋转)
  • 支持 Promise API,异步操作友好,兼容所有现代浏览器 + IE11

适用场景:

  • 大部分常规需求(表单上传、头像压缩、普通图片分享)
  • 追求「开箱即用」,不想写复杂逻辑

快速使用:

npm install browser-image-compression --save
# 或 CDN:<script src="https://cdn.jsdelivr.net/npm/browser-image-compression@2.0.0/dist/browser-image-compression.min.js"></script>
import imageCompression from 'browser-image-compression';

// 监听文件选择事件
document.getElementById('fileInput').addEventListener('change', async (e) => {
  const file = e.target.files[0];
  if (!file) return;

  // 压缩配置
  const options = {
    maxSizeMB: 0.5, // 最大 500KB
    maxWidthOrHeight: 1920, // 最大宽高 1920px
    useWebP: true, // 优先用 WebP(体积更小)
    quality: 0.8, // WebP 质量(0-1)
  };

  try {
    // 压缩文件(返回 Blob 对象,可直接上传)
    const compressedFile = await imageCompression(file, options);
    // 上传到后端(示例:用 FormData)
    const formData = new FormData();
    formData.append('file', compressedFile, compressedFile.name);
    await fetch('/api/upload', { method: 'POST', body: formData });
  } catch (err) {
    console.error('压缩失败:', err);
  }
});

二、高级需求首选:compressorjs(功能最强、自定义性高)

核心优势:

  • 基于 Canvas,支持更精细的压缩控制(裁剪、旋转、缩放、滤镜)
  • 支持批量压缩、预览压缩过程、自定义输出格式
  • 支持图片加载错误处理、压缩进度回调
  • 兼容 IE10+,文档完善,社区活跃(GitHub 12k+ Star)

适用场景:

  • 需高级功能(如裁剪后压缩、自定义压缩算法、批量处理)
  • 复杂表单上传(需预览 + 压缩联动)

快速使用:

npm install compressorjs --save
# 或 CDN:<script src="https://cdn.jsdelivr.net/npm/compressorjs@1.2.1/dist/compressor.min.js"></script>
import Compressor from 'compressorjs';

document.getElementById('fileInput').addEventListener('change', (e) => {
  const file = e.target.files[0];
  if (!file) return;

  // 初始化压缩器
  new Compressor(file, {
    quality: 0.7, // 压缩质量
    width: 1280, // 目标宽度(高度自动等比)
    format: 'webp', // 输出格式
    // 压缩成功回调
    success(result) {
      // result 是 Blob 对象,可直接上传
      const formData = new FormData();
      formData.append('file', result);
      fetch('/api/upload', { method: 'POST', body: formData });
    },
    // 失败回调
    error(err) {
      console.error('压缩失败:', err.message);
    },
  });

三、轻量极简:image-conversion(仅 2KB,专注压缩)

核心优势:

  • 超小体积(gzip 后 ~2KB),无多余依赖
  • 支持按「大小/宽高/质量」压缩,API 极简
  • 支持 JPG/PNG/WebP 互转,兼容现代浏览器

适用场景:

  • 对体积敏感的项目(如移动端 H5、小程序)
  • 仅需基础压缩功能,无需复杂配置

快速使用:

npm install image-conversion --save
# 或 CDN:<script src="https://cdn.jsdelivr.net/npm/image-conversion@2.1.1/dist/image-conversion.min.js"></script>
import * as imageConversion from 'image-conversion';

document.getElementById('fileInput').addEventListener('change', async (e) => {
  const file = e.target.files[0];
  if (!file) return;

  // 压缩到指定大小(如 300KB),返回 Blob
  const compressedBlob = await imageConversion.compress(file, 300);
  // 或按质量压缩:imageConversion.compress(file, { quality: 0.6 })

  // 上传
  const formData = new FormData();
  formData.append('file', compressedBlob);
  await fetch('/api/upload', { method: 'POST', body: formData });
});

四、小程序/跨端首选:TinyPNG API(非库,但压缩效果最佳)

核心优势:

  • 基于 TinyPNG 官方算法,压缩比最高(同等质量下体积最小)
  • 支持 JPG/PNG/WebP/AVIF 格式,自动优化透明背景
  • 提供免费 API(每月 500 次调用),付费版无限制
  • 支持 Node.js/浏览器/小程序(需配置跨域)

适用场景:

  • 对压缩质量要求极高(如电商商品图、海报图)
  • 小程序/跨端项目(原生库体积敏感,API 调用更轻量)

快速使用:

  1. 先去 TinyPNG 官网 申请 API Key
  2. 调用 API 压缩(需处理跨域,建议后端转发,或前端配置 CORS):
// 前端直接调用(需 TinyPNG 允许跨域,或用代理)
async function compressWithTinyPNG(file) {
  const apiKey = '你的 API Key';
  const formData = new FormData();
  formData.append('image', file);

  const response = await fetch('https://api.tinify.com/shrink', {
    method: 'POST',
    headers: {
      Authorization: `Basic ${btoa(`api:${apiKey}`)}`, // Base64 编码 API Key
    },
    body: formData,
  });

  // 压缩后的图片 URL(需下载后上传到自己的服务器)
  const { output } = await response.json();
  const compressedBlob = await fetch(output.url).then(res => res.blob());
  return compressedBlob;
}

// 使用
document.getElementById('fileInput').addEventListener('change', async (e) => {
  const file = e.target.files[0];
  const compressedBlob = await compressWithTinyPNG(file);
  // 上传到自己的后端...
});

五、小众但实用:localResizeIMG(专注移动端,兼容旧设备)

核心优势:

  • 专为移动端设计,支持 iOS/Android 旧设备(如 iOS 9+、Android 4.4+)
  • 支持自动旋转(解决移动端拍照旋转问题)、批量压缩
  • 体积小(~8KB),API 简洁

适用场景:

  • 兼容旧设备的移动端 H5 项目
  • 需处理移动端拍照旋转问题

快速使用:

npm install local-resize-img --save
# 或 CDN:<script src="https://cdn.jsdelivr.net/npm/local-resize-img@4.9.32/dist/lrz.bundle.js"></script>
import lrz from 'local-resize-img';

document.getElementById('fileInput').addEventListener('change', (e) => {
  const file = e.target.files[0];
  if (!file) return;

  // 压缩配置
  lrz(file, {
    width: 1080, // 最大宽度
    quality: 0.7, // 质量
    fieldName: 'file', // 上传字段名
  }).then((rst) => {
    // rst.formData 已封装好 FormData,可直接上传
    fetch('/api/upload', {
      method: 'POST',
      body: rst.formData,
    });
  });
});

六、库的对比与选型建议

库名体积核心优势适用场景
browser-image-compression~10KB零依赖、易用、均衡大多数常规需求(首选)
compressorjs~20KB功能强、自定义性高高级需求(裁剪、批量、滤镜)
image-conversion~2KB超轻量、极简 API体积敏感项目(移动端/H5)
TinyPNG API无(API)压缩比最高、质量最好高质量需求(电商、海报)
localResizeIMG~8KB兼容旧设备、移动端优化旧设备兼容、移动端拍照

额外注意事项

  1. 格式选择:WebP 格式压缩比最优(同等质量下体积比 JPG 小 30%-50%),但需确认后端是否支持(主流后端均支持);如需兼容 IE,可降级为 JPG/PNG。
  2. 压缩策略:优先按「最大体积(maxSizeMB)」配置,再辅助「宽高/质量」,用户体验更好。
  3. 跨域问题:TinyPNG API 前端直接调用需配置跨域,建议通过后端转发(避免暴露 API Key + 解决跨域)。
  4. 小程序兼容:browser-image-compression、image-conversion 均支持小程序(需适配文件路径),TinyPNG API 需通过云函数转发。

根据你的项目场景选择即可,大部分情况用 browser-image-compression 就能满足需求,复杂场景选 compressorjs,轻量场景选 image-conversion~

评论数量:0