代码之家  ›  专栏  ›  技术社区  ›  Rewind

FileReader-准备新文件,即使是相同的文件

  •  0
  • Rewind  · 技术社区  · 8 年前

    我有几个加载文件html元素,例如:

    <input type="file" id="loadFiles0" class="filesclass" name="file" />
    <input type="file" id="loadFiles1" class="filesclass" name="file" />
    

    我为它们添加了一个事件监听器,以捕捉更改:

    // Elsewhere
    function myFunction(event){
        // Stuff
    }
    
    var el;
    el = document.getElementById("loadFiles0");
    el.addEventListener('change', myFunction, false);
    

    许多人都知道,要使负载第二次工作,即使它是相同的文件名,也必须将html元素的“值”设置为“”。这就是问题所在。我需要知道哪个加载文件元素进行了调用。是“加载文件0”还是“加载文件1”等。

    myFunction看起来像这样-只是重要的部分:

    function myFunction(evt){
    
        ...
    
    
        // We need to remove it so this is not handled again when we set value = ""
        this.removeEventListener('change', myFunction, false);
    
        ...
    
        var reader = new FileReader();
        reader.onload = function (e) {
            ...
    
            // HERE IS THE PROBLEM
            // I need a reference to the dom element that this is working on - call it 'ptr'
            // I cannot use 'this' in this function, because that refers to 'reader'
            // I need it so I can set its value to "", so even if the person reloads the same file, it will trigger a change
            // But I cannot be certain if it was 'loadFiles0' or 'loadFiles1' etc
            ptr.value = "";
            ptr.addEventListener('change', myFunction, false);
        };
    }
    

    所以问题是,如何在阅读器的onload函数中获得ptr?

    1 回复  |  直到 8 年前
        1
  •  1
  •   T.J. Crowder    8 年前

    我需要知道哪个加载文件元素进行了调用。是“加载文件0”还是“加载文件1”等。

    会的 this 在事件回调中 myFunction ,然后您可以在变量中记住( ptr

    具有 ptr :

    function myFunction(evt){
    
        // ...
    
    
        this.removeEventListener('change', myFunction, false);
    
        var ptr = this; // *******
    
        // ...
    
        var reader = new FileReader();
        reader.onload = function (e) {
            ptr.value = "";
            ptr.addEventListener('change', myFunction, false);
        };
    }
    

    或具有ES2015+箭头功能:

    function myFunction(evt){
    
        // ...
    
    
        this.removeEventListener('change', myFunction, false);
    
        // ...
    
        var reader = new FileReader();
        reader.onload = e => {                                   // ***
            this.value = "";                                     // ***
            this.addEventListener('change', myFunction, false);  // ***
        };
    }
    

    示例使用 setTimeout 仿效 reader.onload 回调:

    function myFunction(e) {
      var ptr = this;
      // This emulates the reader.onload callback:
      setTimeout(function() {
        console.log("reader.onload for " + ptr.id);
      }, 10);
    }
    Array.prototype.forEach.call(
      document.querySelectorAll("input[type=file]"),
      function(input) {
        input.addEventListener("change", myFunction, false);
      }
    );
    <input type="file" id="loadFiles0">
    <input type="file" id="loadFiles1">
    <input type="file" id="loadFiles2">

    箭头函数示例:

    // ES2015 or higher (you can transpile if necessary)
    function myFunction(e) {
      // This emulates the reader.onload callback:
      setTimeout(() => {
        console.log("reader.onload for " + this.id);
      }, 10);
    }
    Array.prototype.forEach.call(
      document.querySelectorAll("input[type=file]"),
      function(input) {
        input.addEventListener("change", myFunction, false);
      }
    );
    <输入type=“file”id=“loadFiles0”>
    <输入type=“file”id=“loadFiles1”>
    <输入type=“file”id=“loadFiles2”>