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

如何在JavaScript中根据上传文件类型显示单个预览

解决方案:根据文件类型显示单一预览

你的核心问题在于当前代码同时为图片和视频元素设置了数据源,且通过file_picker.value提取扩展名的方式不可靠(浏览器会返回 fakepath,且扩展名不如MIME类型准确)。以下是修改方案:

关键改进点

  • 存储文件时同时保存MIME类型,而非仅依赖扩展名判断
  • 根据MIME类型动态显示/隐藏图片或视频预览元素
  • 初始化和清空时统一处理预览元素的显示状态

修改后的代码

HTML(调整初始隐藏状态)

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <link rel="stylesheet"  href="/styles/index.css">
</head>

<body id="upload_body">
    <div class="upload_container">
        <div class="container">
            <input type="file" id="file_picker" accept="image/*,video/mp4"><br>
            <div class="preview-container">
                <button type="button" id="button_clear" style="display:none;">CLEAR</button><br>
                <!-- 初始隐藏预览元素 -->
                <img id="image" src="" height="300px" width="auto" style="display:none;"><br>
                <video id="video" src=""  height="300px" width="auto" autoplay="true" loop muted style="display:none;"></video>
            </div>
        </div>
        <h3 class="lead">
            Follow Us <br><br>
            <a href="https://twitter.com/DevTopia_">
                <img src="/assets/twitter.png" alt="twitter profile link" height="32px"/>
            </a>
            <a href="https://discord.gg/GAHDdWyj">
                <img src="/assets/discord.png" alt="discord profile link" height="32px"/>
            </a>
        </h3>
    </div>
    <script type="application/javascript" src="/js/file_picker.js"></script>
    <script type="application/javascript" src="/js/content_script.js"></script>
</body>
</html>

JavaScript(核心修改部分)

function storage_onChanged(changes, areaName) {
  let settings = {};
  if (areaName == "local") {
    if (changes.image_data_url) {
      settings.image_data_url = changes.image_data_url.newValue ?? "";
    }
    if (changes.image_filename) {
      settings.image_filename = changes.image_filename.newValue ?? "none";
    }
    if (changes.file_type) {
      settings.file_type = changes.file_type.newValue ?? "";
    }
  }
  set_preview(settings);
}

// 重命名为更准确的函数名
function set_preview(settings) {
  const image = document.getElementById("image");
  const video = document.getElementById("video");
  const clearBtn = document.getElementById("button_clear");

  // 先隐藏所有预览元素和按钮
  image.style.display = "none";
  video.style.display = "none";
  clearBtn.style.display = "none";

  if (!settings.image_data_url) return;

  // 根据MIME类型判断显示哪个预览
  if (settings.file_type.startsWith("image/")) {
    image.src = settings.image_data_url;
    image.alt = settings.image_filename;
    image.style.display = "block";
    clearBtn.style.display = "block";
  } else if (settings.file_type.startsWith("video/")) {
    video.src = settings.image_data_url;
    video.alt = settings.image_filename;
    video.style.display = "block";
    clearBtn.style.display = "block";
  }
}

function remove_image() {
  chrome.storage.local.remove(["image_data_url", "image_filename", "file_type"]);
}

function store_image() {
  if (this.files.length > 0) {
    const file = this.files[0];
    const reader = new FileReader();
    reader.addEventListener("load", () => {
      chrome.storage.local.set({
        image_data_url: reader.result,
        image_filename: file.name,
        file_type: file.type // 新增存储文件MIME类型
      });
    });
    reader.readAsDataURL(file);
  }
}

// Initialization
chrome.storage.local.get(["image_data_url", "image_filename", "file_type"]).then((items) => {
  set_preview({
    image_data_url: items.image_data_url ?? "",
    image_filename: items.image_filename ?? "none",
    file_type: items.file_type ?? ""
  });
});

// Event Listeners
const file_picker = document.querySelector("#file_picker");
if (file_picker) {
  file_picker.addEventListener("change", store_image);
}

const button_clear = document.getElementById("button_clear");
if (button_clear) {
  button_clear.addEventListener("click", remove_image);
}

chrome.storage.onChanged.addListener(storage_onChanged);

为什么这样修改?

  1. MIME类型更可靠:直接使用File对象的type属性判断文件类型,比通过扩展名判断更准确,避免了扩展名伪造或大小写问题
  2. 统一状态管理:每次设置预览前先隐藏所有元素,确保不会同时显示两个预览
  3. 按钮状态同步:只有当有预览内容时才显示清空按钮,提升用户体验

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.12 22:25:41