首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 更多程式語言 >> 程式設計疑難解答

JavaScript 實現多圖片預覽與刪除:File API + FileReader 完整方案

     編輯:程式設計疑難解答

需求分析

原代碼僅支持單圖預覽(input.files[0]),需擴展為:多文件選擇、同時預覽、每張圖片可單獨刪除、總數限制(如最多 9 張)。

核心技術點

  • input[multiple] 允許一次選多文件
  • FileReader.readAsDataURL() 異步讀取生成 Base64 預覽
  • 動態創建 <img>、刪除按鈕、隱藏 <input type="file"> 形成預覽組
  • 用閉包/數據屬性綁定「刪除」事件,移除對應 DOM 節點

完整實現代碼

<input type="file" id="fileInput" multiple accept="image/*" />
<div id="previewContainer"></div>

<script>
const MAX_IMAGES = 9;
const fileInput = document.getElementById('fileInput');
const previewContainer = document.getElementById('previewContainer');
let fileIndex = 0;

fileInput.addEventListener('change', handleFiles);

function handleFiles(e) {
  const files = Array.from(e.target.files);
  files.forEach(file => {
    if (previewContainer.children.length >= MAX_IMAGES) {
      alert(`最多只能上傳 ${MAX_IMAGES} 張圖片!`);
      return;
    }
    if (!file.type.startsWith('image/')) return;

    const reader = new FileReader();
    reader.onload = (evt) => {
      const wrapper = document.createElement('div');
      wrapper.className = 'preview-item';
      wrapper.dataset.index = fileIndex++;

      const img = document.createElement('img');
      img.src = evt.target.result;
      img.alt = file.name;

      const delBtn = document.createElement('button');
      delBtn.textContent = '×';
      delBtn.onclick = () => wrapper.remove();

      const hiddenInput = document.createElement('input');
      hiddenInput.type = 'file';
      hiddenInput.name = 'images[]';
      hiddenInput.style.display = 'none';
      // 此處需配合 FormData 手動追加 file,或改用隱藏 input 存 Base64

      wrapper.append(img, delBtn, hiddenInput);
      previewContainer.appendChild(wrapper);
    };
    reader.readAsDataURL(file);
  });
  // 重置 value 以便再次選擇同一文件觸發 change
  fileInput.value = '';
}
</script>

<style>
.preview-item { position: relative; display: inline-block; margin: 5px; }
.preview-item img { width: 100px; height: 100px; object-fit: cover; }
.preview-item button { position: absolute; top: 0; right: 0; background: rgba(0,0,0,.6); color: #fff; border: none; border-radius: 50%; width: 20px; height: 20px; cursor: pointer; }
</style>

關鍵細節

  1. 多文件屬性:<input multiple> 讓用戶可按住 Ctrl/Shift 多選。
  2. 預覽容器管理:每張圖片獨立 div,刪除時直接 remove()。
  3. 表單提交:因動態創建的 input[type=file] 無法直接賦值 File 對象,實際項目建議用 FormData.append('images[]', file) 在提交時組裝,或將 Base64 存隱藏域(體積增大 33%)。
  4. 重置 value:fileInput.value = '' 允許連續選擇同一文件觸發 change 事件。

進階:生產環境建議引入 exif-js 修正手機拍照旋轉、WebUploader 或 Uppy 等成熟上傳庫處理分片、斷點續傳、壓縮等複雜場景。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved