检查HTML5拖放文件类型

Mik*_*maa 10 javascript html5 drag-and-drop

我想将放置区背景颜色更改为绿色或红色,具体取决于所包含的有效负载拖动是否包含支持的文件类型(JPEG).

  • Gecko和Webkit是否支持确定拖放文件的文件类型?

  • 如何在这两个浏览器中提取文件类型?

我找到了event.dataTransfer.types API,但对于Firefox来说,它似乎填充了application/x-moz-file,因此我觉得我做错了.

Kon*_*aju 13

您可以使用文件对象在Gecko和webkit支持的浏览器中获取文件类型.

var files =e.dataTransfer.files||e.target.files; // File list
Run Code Online (Sandbox Code Playgroud)

文件对象返回名称,类型和大小.你也可以获得最后修改日期.

var mimeType= files[0].type; //mime type of file list first entry
Run Code Online (Sandbox Code Playgroud)

  • 为什么|| e.target.files后备?它是否考虑到一些意外情况或某些事情? (2认同)
  • 请注意,此MIME类型是使用文件扩展名生成的(即文件名末尾的.gif或.jpeg.)在所有情况下,这绝对不会是文件的真实类型.许多人在保存PNG或BMP文件时会放.jpg ...因为他们知道.jpg意味着"图像". (2认同)

Ale*_*lke 6

在JavaScript中测试文件的类型有点工作,但是新版本的浏览器现在拥有FileReader允许您这样做的对象.

我的实现有一个不完整的引用,它将缓冲区读取为uint8字节,然后检查输入是否是有效的JPEG,GIF,PNG.显然,它会随着时间的推移而增强.要获得更完整的版本,请editor.jssnapwebsites项目的编辑器插件中查找该文件.https://sourceforge.net/p/snapcpp/code/ci/master/tree/snapwebsites/plugins/editor/

// The buffer is expected to be an ArrayBuffer() as read with a FileReader
_buffer2mime: function(buffer)
{
    buf = Uint8Array(buffer);
    if(buf[0] == 0xFF
    && buf[1] == 0xD8
    && buf[2] == 0xFF
    && buf[3] == 0xE0
    && buf[4] == 0x00
    && buf[5] == 0x10
    && buf[6] == 0x4A  // J
    && buf[7] == 0x46  // F
    && buf[8] == 0x49  // I
    && buf[9] == 0x46) // F
    {
        return "image/jpeg";
    }
    if(buf[0] == 0x89
    && buf[1] == 0x50  // P
    && buf[2] == 0x4E  // N
    && buf[3] == 0x47  // G
    && buf[4] == 0x0D  // \r
    && buf[5] == 0x0A) // \n
    {
        return "image/png";
    }
    if(buf[0] == 0x47  // G
    && buf[1] == 0x49  // I
    && buf[2] == 0x46  // F
    && buf[3] == 0x38  // 8
    && buf[4] == 0x39  // 9
    && buf[5] == 0x61) // a
    {
        return "image/gif";
    }

    // unknown
    return "";
},

_droppedImageAssign: function(e){
    var img,id;
    img = new Image();
    img.src = e.target.result;
    ++this._uniqueId;
    id="snap-editor-image-"+this._uniqueId;
    jQuery(img).hide().attr("id",id).appendTo(e.target.snapEditorElement);
    jQuery("#"+id).show();
},

_droppedImage: function(e){
    var mime, r, a, blob;

    mime = snapwebsites.EditorInstance._buffer2mime(e.target.result);
    if(mime.substr(0, 6) == "image/")
    {
        r = new FileReader;
        r.snapEditorElement = e.target.snapEditorElement;
        r.onload = snapwebsites.EditorInstance._droppedImageAssign;
        a = [];
        a.push(e.target.snapEditorFile);
        blob = new Blob(a, {type: mime}); // <- FORCE THE REAL MIME TYPE
        r.readAsDataURL(blob);
    }
},

jQuery("#some-object")
        .on("drop",function(e){
            // always prevent the default dropping mechanism
            // we handle the file manually all the way
            e.preventDefault();
            e.stopPropagation();

            // anything transferred on widget that accepts files?
            if(e.originalEvent.dataTransfer
            && e.originalEvent.dataTransfer.files.length)
            {
                accept_images = jQuery(this).hasClass("image");
                accept_files = jQuery(this).hasClass("attachment");
                if(accept_images || accept_files)
                {
                    for(i = 0; i < e.originalEvent.dataTransfer.files.length; ++i)
                    {
                        // read the image so we can make sure it is indeed an
                        // image and ignore any other type of files
                        r = new FileReader;
                        r.snapEditorElement = this;
                        r.snapEditorFile = e.originalEvent.dataTransfer.files[i];
                        r.onload = snapwebsites.EditorInstance._droppedImage;
                        // Get the first 64 bytes of the file to check the magic code
                        r.readAsArrayBuffer(r.snapEditorFile.slice(0, 64));
                    }
                }
            }

            return false;
        })
Run Code Online (Sandbox Code Playgroud)