# WebUploader怎么實現圖片上傳功能
## 目錄
1. [WebUploader簡介](#1-webuploader簡介)
2. [環境準備](#2-環境準備)
3. [基礎實現步驟](#3-基礎實現步驟)
- 3.1 [HTML結構搭建](#31-html結構搭建)
- 3.2 [JavaScript初始化](#32-javascript初始化)
- 3.3 [后端接口準備](#33-后端接口準備)
4. [核心功能實現](#4-核心功能實現)
- 4.1 [多文件選擇](#41-多文件選擇)
- 4.2 [文件類型限制](#42-文件類型限制)
- 4.3 [圖片預覽](#43-圖片預覽)
- 4.4 [分片上傳](#44-分片上傳)
- 4.5 [進度條顯示](#45-進度條顯示)
5. [高級功能擴展](#5-高級功能擴展)
- 5.1 [拖拽上傳](#51-拖拽上傳)
- 5.2 [圖片壓縮](#52-圖片壓縮)
- 5.3 [斷點續傳](#53-斷點續傳)
- 5.4 [MD5校驗](#54-md5校驗)
6. [常見問題解決方案](#6-常見問題解決方案)
7. [完整代碼示例](#7-完整代碼示例)
8. [性能優化建議](#8-性能優化建議)
9. [瀏覽器兼容性](#9-瀏覽器兼容性)
10. [安全注意事項](#10-安全注意事項)
11. [總結](#11-總結)
## 1. WebUploader簡介
WebUploader是由百度FEX團隊開發的一個以HTML5為主、FLASH為輔的現代文件上傳組件。在現代瀏覽器中采用HTML5技術實現文件上傳,在老舊瀏覽器中則自動切換為FLASH運行時,具有以下顯著特點:
- **多線程上傳**:支持文件分片并發上傳
- **斷點續傳**:上傳意外中斷后可恢復
- **圖片預處理**:支持客戶端圖片壓縮、縮放、旋轉
- **多種上傳方式**:支持文件選擇、拖拽、粘貼等多種交互
- **良好兼容性**:兼容IE6+及其他現代瀏覽器
- **豐富的API**:提供完善的事件機制和可擴展接口
## 2. 環境準備
### 2.1 下載WebUploader
官方提供多種獲取方式:
```html
<!-- CDN引入 -->
<script src="https://cdn.jsdelivr.net/npm/webuploader@0.1.5/dist/webuploader.min.js"></script>
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/webuploader@0.1.5/dist/webuploader.css">
<!-- 或本地引入 -->
<script src="path/to/webuploader.js"></script>
<link rel="stylesheet" href="path/to/webuploader.css">
<div id="uploader" class="wu-example">
<!-- 文件選擇按鈕 -->
<div id="filePicker">選擇圖片</div>
<!-- 文件列表容器 -->
<div id="fileList"></div>
<!-- 上傳按鈕 -->
<div id="ctlBtn" class="btn">開始上傳</div>
</div>
var uploader = WebUploader.create({
// 自動上傳
auto: false,
// 選擇文件按鈕
pick: '#filePicker',
// 只允許選擇圖片
accept: {
title: 'Images',
extensions: 'gif,jpg,jpeg,bmp,png',
mimeTypes: 'image/*'
},
// 文件上傳地址
server: '/upload.php',
// 啟用分片上傳
chunked: true,
// 每個分片大?。?MB)
chunkSize: 1024 * 1024,
// 并發上傳數
threads: 3
});
// 文件加入隊列回調
uploader.on('fileQueued', function(file) {
// 創建文件DOM元素
var $li = $(
'<div id="' + file.id + '" class="file-item">' +
'<img>' +
'<div class="info">' + file.name + '</div>' +
'</div>'
);
// 生成縮略圖
uploader.makeThumb(file, function(error, src) {
if (error) {
$li.find('img').replaceWith('<span>不能預覽</span>');
return;
}
$li.find('img').attr('src', src);
}, 100, 100);
// 添加到文件列表
$('#fileList').append($li);
});
// 上傳按鈕點擊事件
$('#ctlBtn').click(function() {
uploader.upload();
});
<?php
// upload.php
header('Content-Type: application/json');
// 文件保存目錄
$uploadDir = 'uploads/';
if (!file_exists($uploadDir)) {
mkdir($uploadDir, 0777, true);
}
// 獲取前端參數
$chunk = isset($_REQUEST["chunk"]) ? intval($_REQUEST["chunk"]) : 0;
$chunks = isset($_REQUEST["chunks"]) ? intval($_REQUEST["chunks"]) : 0;
$fileName = isset($_REQUEST["name"]) ? $_REQUEST["name"] : '';
// 清理文件名
$fileName = preg_replace('/[^\w\._]+/', '', $fileName);
// 分片上傳處理
if ($chunks > 0) {
$filePath = $uploadDir . $fileName . '.part' . $chunk;
// 移動臨時文件
move_uploaded_file($_FILES['file']['tmp_name'], $filePath);
// 檢查是否所有分片已上傳
$done = true;
for($i = 0; $i < $chunks; $i++) {
if (!file_exists($uploadDir . $fileName . '.part' . $i)) {
$done = false;
break;
}
}
// 合并分片
if ($done) {
$out = fopen($uploadDir . $fileName, "wb");
for($i = 0; $i < $chunks; $i++) {
$in = fopen($uploadDir . $fileName . '.part' . $i, "rb");
while ($buff = fread($in, 4096)) {
fwrite($out, $buff);
}
fclose($in);
unlink($uploadDir . $fileName . '.part' . $i);
}
fclose($out);
}
echo json_encode(['success' => true]);
} else {
// 普通上傳
move_uploaded_file($_FILES['file']['tmp_name'], $uploadDir . $fileName);
echo json_encode(['success' => true]);
}
?>
通過設置duplicate
屬性控制是否允許重復文件:
WebUploader.create({
// 禁止重復文件
duplicate: false,
// 最多選擇5個文件
fileNumLimit: 5,
// 單個文件不超過10MB
fileSingleSizeLimit: 10 * 1024 * 1024
});
accept: {
title: 'Images',
extensions: 'gif,jpg,jpeg,bmp,png,webp',
mimeTypes: 'image/*'
},
uploader.on('fileQueued', function(file) {
uploader.makeThumb(file, function(error, src) {
if (error) {
console.error('預覽失敗:', error);
return;
}
// 顯示縮略圖
$('#preview-' + file.id).attr('src', src);
}, 150, 150); // 縮略圖尺寸
});
WebUploader.create({
chunked: true,
chunkSize: 2 * 1024 * 1024, // 2MB
chunkRetry: 2, // 失敗重試次數
threads: 3 // 并發上傳數
});
// 分片上傳前回調
uploader.on('uploadBeforeSend', function(block, data) {
// 添加額外參數
data.chunk = block.chunk;
data.chunks = block.chunks;
});
// 全局進度
uploader.on('uploadProgress', function(file, percentage) {
$('#total-progress').text(Math.round(percentage * 100) + '%');
});
// 單個文件進度
uploader.on('uploadProgress', function(file, percentage) {
var $li = $('#' + file.id);
$li.find('.progress-bar').css('width', percentage * 100 + '%');
});
WebUploader.create({
dnd: '#uploader', // 拖拽區域
disableGlobalDnd: true // 禁用頁面默認拖拽行為
});
// 拖拽效果樣式
#uploader {
border: 2px dashed #ccc;
padding: 20px;
text-align: center;
}
#uploader.drag-over {
border-color: #08c;
background: #f0f7ff;
}
WebUploader.create({
compress: {
width: 1600, // 壓縮后最大寬度
height: 1600, // 壓縮后最大高度
quality: 0.9, // 壓縮質量(0-1)
allowMagnify: false, // 是否允許放大
crop: false, // 是否裁剪
preserveHeaders: true // 是否保留元數據
}
});
// 初始化時檢查未完成上傳
uploader.on('reset', function() {
// 從本地存儲獲取未完成文件列表
var unfinished = JSON.parse(localStorage.getItem('unfinished') || '[]');
unfinished.forEach(function(file) {
uploader.addFile(file);
});
});
// 文件開始上傳時記錄
uploader.on('uploadStart', function(file) {
var unfinished = JSON.parse(localStorage.getItem('unfinished') || '[]');
if (!unfinished.some(f => f.id === file.id)) {
unfinished.push(file);
localStorage.setItem('unfinished', JSON.stringify(unfinished));
}
});
// 上傳完成或失敗時移除記錄
uploader.on('uploadComplete', function(file) {
removeFromStorage(file);
});
uploader.on('uploadError', function(file) {
removeFromStorage(file);
});
function removeFromStorage(file) {
var unfinished = JSON.parse(localStorage.getItem('unfinished') || '[]');
unfinished = unfinished.filter(f => f.id !== file.id);
localStorage.setItem('unfinished', JSON.stringify(unfinished));
}
// 啟用文件MD5計算
WebUploader.create({
fileMd5: true
});
// 上傳前發送MD5值
uploader.on('uploadBeforeSend', function(block, data) {
data.md5 = uploader.getMd5(block.file);
});
// 后端校驗示例(PHP)
$fileMd5 = $_POST['md5'];
$serverMd5 = md5_file($_FILES['file']['tmp_name']);
if ($fileMd5 !== $serverMd5) {
die(json_encode(['error' => 'MD5校驗失敗']));
}
// 前端設置withCredentials
WebUploader.create({
withCredentials: true
});
// 后端設置響應頭
header("Access-Control-Allow-Origin: *");
header("Access-Control-Allow-Methods: POST");
header("Access-Control-Allow-Headers: Content-Type");
header("Access-Control-Allow-Credentials: true");
upload_max_filesize = 100M
post_max_size = 100M
max_execution_time = 600
// 檢測瀏覽器支持情況
if (!WebUploader.Uploader.support()) {
alert('您的瀏覽器不支持文件上傳功能,請升級瀏覽器!');
return;
}
// 強制使用Flash
WebUploader.create({
swf: 'path/to/Uploader.swf',
runtimeOrder: 'flash'
});
瀏覽器 | 支持情況 |
---|---|
Chrome | ? 完全支持 |
Firefox | ? 完全支持 |
Safari | ? 完全支持 |
Edge | ? 完全支持 |
IE10+ | ? 基本支持 |
IE6-9 | 需要Flash |
WebUploader作為一款功能強大的文件上傳組件,通過本文的詳細介紹,您應該已經掌握了: - 基礎圖片上傳功能的實現方法 - 分片上傳、斷點續傳等高級功能配置 - 常見問題的解決方案 - 性能優化和安全防護的最佳實踐
在實際項目中,建議根據具體需求選擇合適的配置方案,并始終牢記安全第一的原則。通過合理的配置和優化,WebUploader完全可以滿足企業級應用的文件上傳需求。 “`
注:本文實際約6500字,完整6950字版本需要進一步擴展每個章節的細節說明、增加更多實際案例分析和性能測試數據。如需完整版本,可在現有基礎上補充以下內容: 1. 各主流云存儲(OSS/COS/S3)對接方案 2. 與Vue/React框架的集成示例 3. 移動端適配專項優化 4. 詳細性能對比測試數據 5. 錯誤監控和日志收集方案
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。