文件API

在HTML5之前的,从网页上传文件一次只能上传一个文件,而且也无法对要上传的文件做更深一步的操作。

HTML5提供了一个系列关于文件操在的API,通过使用这些API,对于从Web页面访问本地文件系统的相关处理将会变的非常简单。

File和FileList对象

<input>的type属性为 file 的时候,那么它就可以访问本地文件系统了。在HTML5之前,一次只能选择一个文件。HTML5中,给<input>添加属性 multiple 则可以一次选择多个文件。

注意:multiple或multiple=’multiple’ 两种写法都可以。

<form action="#" enctype="multipart/form-data">
    <input type="file" multiple>
</form>

用户选择的每一个文件都是一个File对象,而如果选择了多个File,则FileList表示这些多个File对象的列表集合。

File对象提供了关于文件的一些信息并且允许Javascript去访问这些信息。

File注意提供了3个属性(包括从Blob中的继承的)

  1. File.lastModified:表示的文件的最后修改时间。以毫秒为单位。
  2. File.name:获取的是文件的文件名。由于安全考虑,这个地方的文件名不包含路径。
  3. File.size:获取到文件大小。以字节为单位。

注意:上面的属性都是readonly的。

FileList是多个File的列表集合:

  1. FileList.item(index):获取列表中的File

具体使用参考下面的代码:

<form action="#" enctype="multipart/form-data">
    <input type="file" multiple>
</form>
<button>获取文件相关信息</button>
<p id="content"></p>
<script type="text/javascript">
    var btn = document.getElementsByTagName("button")[0];
    //1. 获取文件元素
    var inputFile = document.getElementsByTagName("input")[0];
    btn.onclick = function () {
        //2. 得到FileList
        var files = inputFile.files;
        for(var i = 0; i < files.length; i++){ //files.length:返回类别中File对象的数量
            //3. files.itemt(i) 获取到每个文件。  
            var msg = `第${i + 1}个文件的文件名:${files.item(i).name}, 最后修改时间:${files.item(i).lastModified},文件长度:${files.item(i).size}`;
            content.innerHTML += msg + "<br>";
        }
    }
</script>

Blob对象

表示二进制原始文件。前面见到的File对象也继承了Blob对象。

注意包括两个属性:size和type。

size:表示Blob对象的字节长度。 File文件的size就是继承这里的size

type:表示Blob的MIME类型。如果未知则返回一个长度为 0 的字符串。FIle对象也继承了这个属性。

仍然以File对象来演示Blob对象:

for(var i = 0; i < files.length; i++){ //files.length:返回类别中File对象的数量

       var file = files.item(i);
       var msg = `第${i + 1}个文件的MIME类型:${file.type}<br>`;
       content.innerHTML += msg
}

FileReader

FileReader对象运行Web 应用程序以异步的方式读取文件的内容,使用File对象或Blob对象指定要读取的文件

FileReader对象主要包括3个属性和5个方法、6个事件。

3个属性:

  • FileReader.error: 读取文件的时候发生的错误信息
  • FileReader.readyState:0-2数字,表示FileReader的状态
EMPTY0No data has been loaded yet.还没有加载到数据
LOADING1Data is currently being loaded.这正在加载数据
DONE2The entire read request has been completed.数据加载完成

- FileReader.result:这个是最重要的属性。读取到的内容都存储在了这个属性中。只能在readyState DONE之后才能读取这个属性值。读取到的数据类型取决于用什么的方法去读取的文件。

5个方法:

  • FileReader.abort():终止读取文件的操作。这个方法一点结束,则readyState就成为了DONE
  • FileReader.readAsArrayBuffer():开始读取文件的内容,一旦完成,则把文件的数据存储在ArrayBuffer中。当然ArrayBuffer自然会存储在FileReader的result属性中。
  • FileReader.readAsBinaryString():以二进制的形式读取文件的内容。这个方法是非标准方法,不要使用。
  • FileReader.readAsDataURL():将文件读取为DateUrl
  • FileReader.readAsText():将文件的内容读取文本。读取纯文本内容的时候使用。

6个事件:

  • FileReader.onabort:数据读取被中断时触发。

    A handler for the abort event. This event is triggered each time the reading operation is aborted.

  • FileReader.onerror:数据读取发生错误时触发。

    A handler for the error event. This event is triggered each time the reading operation encounter an error.

  • FileReader.onload:数据读取成功后触发。

    A handler for the load event. This event is triggered each time the reading operation is successfully completed.

  • FileReader.onloadstart:数据开始读取时触发。

    A handler for the loadstart event. This event is triggered each time the reading is starting.

  • FileReader.onloadend:数据读取完成后触发。不管数据读取成功还是失败都会触发。

    A handler for the loadend event. This event is triggered each time the reading operation is completed (either in success or failure).

  • FileReader.onprogress:数据读取过程中触发。

    A handler for the progress event. This event is triggered while reading a Blob content.

<input type="file" multiple id="file">
<br><button id="readBtn">读取文件内容</button>
<p id="content">此处显示读取到的文件内容</p>

<script type="text/javascript">
    var fileInput = document.getElementById("file");
    var readBtn = document.getElementById("readBtn");
    var content = document.getElementById("content");

    readBtn.onclick = function () {
        //1. 检测当前浏览器是否支持FileReader
        if(!FileReader) {
            content.innerHTML = "你的文件不支持FileApi";
            return;
        }
        //2. 获取到用户选择的所有文件
        var files = fileInput.files;
        for(var i = 0; i < files.length; i++){
            //3. 获取用户选择的每一个文件
            var file = files.item(i);
            //4. 判断文件的类型,如果是文本文件就显示在p标签中,其他类型不处理
            if(file.type.startsWith("text")){
                //5. 创建FileReader对象
                var reader = new FileReader();
                //6. 定义数据读取成功的回调函数
                reader.onload = function (event) {
                    content.innerHTML += "<hr>" + reader.result;
                }
                //7. 开始读取文件数据
                reader.readAsText(file, "utf-8");
              //如果是图片文件,就以dataURL的形式读取。把读取到结果是一个url,给img标签的src
            }
        }
    }

</script>

拖放API

在HTML5中,提供了直接支持拖放操作的API。新的拖放API已经支持浏览器与其他应用程序之间的互相拖动。相比以前的使用mousedown、mouseover、mouseup实现的拖放,新的API大大简化了拖放的代码。

实现拖放的步骤

步骤1:

把要拖放的对象的元素的draggable属性设为true(draggable=”true”)。另外对<img><a>元素(指定href属性)默认允许拖放。

步骤2:

编写与拖放有关的事件处理代码。

共有8个与拖放有关的事件!

事件产生事件的元素描述
dragstart被拖动的元素或文本This event is fired when the user starts dragging an element or text selection。当开始拖动选择的元素或文本的时候出发
drag被拖动的元素或文本This event is fired when an element or text selection is being dragged。在元素在拖动的过程中触发。(会重复触发)
dragenter拖放的目标元素This event is fired when a dragged element or text selection enters a valid drop target。元素进入目标元素区域的时候触发。
dragover拖放的目标元素This event is fired when an element or text selection is being dragged over a valid drop target (every few hundred milliseconds).在目标元素领域经过的时候触发
dragleave拖放的目标元素This event is fired when a dragged element or text selection leaves a valid drop target.当离开目标元素的时候触发。
dragend拖放的目标元素This event is fired when a drag operation is being ended (by releasing a mouse button or hitting the escape key).当拖放操作完成后触发(松开了鼠标键或者按下了esc键)
dragexit被拖动的元素This event is fired when an element is no longer the drag operation’s immediate selection target.当元素不再是拖动操作的直接目标时触发
drop被拖动的元素This event is fired when an element or text selection is dropped on a valid drop target。当在有效的目标上放下拖动的元素后触发

示例:

<!DOCTYPE html>
<html>
<head>
    <title>Title</title>
    <meta charset="utf-8">
    <style>
        #draggable {
            width: 200px;
            height: 20px;
            text-align: center;
            background: white;
            margin: 0 auto;
        }
        .dropzone {
            box-sizing: border-box;
            width: 400px;
            height: 60px;
            background: blueviolet;
            margin: 10px auto;
            padding: 20px;
        }
    </style>
</head>
<body>
<!--dropzone:表示可释放的区域-->
<div class="dropzone">
    <!--可拖动的元素 draggable="true"-->
    <div id="draggable" draggable="true" >
        来拖动我啊
    </div>
</div>
<div class="dropzone"></div>
<div class="dropzone"></div>
<div class="dropzone"></div>


<script>
    /*储存拖动的目标*/
    var dragged;


    /*开始拖动的时触发。 只触发一次*/
    document.addEventListener("dragstart", function (event) {
//        console.log("开始拖动了");
        // 保存被拖动的元素对象
        dragged = event.target;
        // 把拖动元素的该成半透明。
        event.target.style.opacity = .3;
    }, false);

    /* 拖动的过程中触发。 只要元素在拖动,会一直重复触发 */
    document.addEventListener("drag", function (event) {
//        console.log("被拖的感觉真爽")
    }, false);

    /*进入另外一个元素的区域时触发*/
    document.addEventListener("dragenter", function (event) {
        // 判断当前的目标是否进入了潜在的 dropzone区域,如果是则高量这个潜在的目标区域
        if (event.target.className == "dropzone") {
//            console.log("进入潜在的目标区域");
            event.target.style.background = "purple";
        }

    }, false);

    /* 在潜在目标区域的上方的时候会重复触发 */
    document.addEventListener("dragover", function (event) {
//        console.log("在潜在的目前区域上方");
        // 因为默认情况下,拖放目标是不允许接受元素的。阻值默认行为,可以随时是否元素。
        event.preventDefault();  //必须阻止默认行为,否则的后面的drop事件不会触发
    }, false);

    /*松开鼠标拖放结束。*/
    document.addEventListener("dragend", function (event) {
        console.log("拖放结束");
        // 把元素的透明重新设置为1
        event.target.style.opacity = "1";
    }, false);

    /*从潜在目标元素上方离开的时候触发*/
    document.addEventListener("dragleave", function (event) {
        console.log("离开目标元素");
        // 因为进入一个元素的时候更改了目标元素的北京,所以离开的时候要重置背景
        if (event.target.className == "dropzone") {
            event.target.style.background = "";
        }

    }, false);

    /*释放拖动元素的时候触发。  这个事件是在dropend事件触发前触发。*/
    document.addEventListener("drop", function (event) {
        console.log("drog.....");
        // prevent default action (open as link for some elements)
        event.preventDefault();
        // 把拖动的元素移动目标区域中
        if (event.target.className == "dropzone") {
            event.target.style.background = "";
            //把拖动元素从他原来的父节点中移除。
            dragged.parentNode.removeChild(dragged);
            //插入到目标元素中。
            event.target.appendChild(dragged);
        }

    }, false);
</script>
</body>
</html>
Logo

CSDN联合极客时间,共同打造面向开发者的精品内容学习社区,助力成长!

更多推荐