JQuery - 拖放文件 - 如何获取文件信息?

Posted

技术标签:

【中文标题】JQuery - 拖放文件 - 如何获取文件信息?【英文标题】:JQuery - Drag n Drop Files - How to get file info? 【发布时间】:2012-01-11 21:41:14 【问题描述】:

有兴趣使用 JQuery/AJAX/php 构建我自己的拖放文件上传器。

基本上我想要一个文件上传器,我网站的用户只需将文件从他们的计算机拖到我创建的 div 中,然后它将为他们上传文件到选定的目的地。

我想从头开始构建它,不使用任何插件,以便更好地操纵限制(文件类型、大小、目标文件夹等)

搜索谷歌没有运气,只有插件。无论如何可以引导我朝着正确的方向前进吗?

更新 好的,所以我想出了如何做我想做的事。只需将文件输入字段的不透明度设置为 1,使其隐藏,您仍然可以将文件拖到该一般区域,如果您点击文本字段,它将捕获它。但是,我想知道如何增加文件输入字段的高度/宽度(在文件上尝试了基本的 css,但它只会增加“浏览”按钮的大小,而不是您可以将文件放入的实际字段。任何想法如何做到这一点? 我基本上想要一个大的方形 div,上面写着“在此处放置文件”。所以我需要调整输入字段的大小。

【问题讨论】:

我认为只有支持 html5 的浏览器才能让你这样做。不过,我不是 100% 确定。 您可以使用原生 javascript 通过拖放来做一些非常酷的事情,例如(从网站)拖动托管图像并将其拖放到具有 drop 事件的 div 上,然后获取图像的路径并以该路径作为源创建图像元素。但是,从桌面拖动图像完全是另一回事,而且很可能会被阻止。 【参考方案1】:

您可以使用 HTML5 dragenterdragleave 事件来创建放置区。 然后通过在 dropzone 中放置一个文件输入,并使用 CSS 将其隐藏,您可以在输入的 change 事件触发时上传文件,如下所示

var dropzone = $("#dropzone"),
    input    = dropzone.find('input');

dropzone.on(
    dragenter : dragin,
    dragleave : dragout
);

input.on('change', drop);

function dragin(e)  //function for drag into element, just turns the bix X white
    $(dropzone).addClass('hover');


function dragout(e)  //function for dragging out of element                         
    $(dropzone).removeClass('hover');


function drop(e) 
    var file = this.files[0];
    $('#dropzone').removeClass('hover').addClass('dropped').find('img').remove();

    // upload file here

FIDDLE

【讨论】:

@CMS - 似乎是这样,我已经更新了不依赖外部脚本文件/网站的答案。【参考方案2】:

对于那些感兴趣的人,我发现这个教程/演示很有帮助:http://www.viget.com/inspire/custom-file-inputs-with-a-bit-of-jquery/

基本上使用<span> 来覆盖默认输入字段。

【讨论】:

【参考方案3】:

只是在这里插话,因为过去几天我也一直在这样做。据我了解,如果您通过 jQuery 绑定 drop 事件,您需要通过 jQuery 提供的事件中的 event.originalEvent 对象来访问该 event.dataTransfer 对象。

例子:

在此我绑定到dragoverdrop 事件,因为这是防止它执行默认操作所必需的(在此处找到解决方案:Prevent the default action. Working only in chrome)

$('#dropzone').bind('dragover drop', function(event) 
    event.stopPropagation(); 
    event.preventDefault();
    if (event.type == 'drop') 
        console.log(event.originalEvent.dataTransfer.files);
    
);

似乎还有一个错误,如果你console.log() event.dataTransfer(或event.originalEvent.dataTransfer)它的文件数组是空的,这里指出:event.dataTransfer.files is empty when ondrop is fired?

为了更好地回答 OPs 问题(我刚刚注意到它的其余部分,而且我知道它已经过时,但有些人可能会觉得这很有帮助):

我的实现是在 jQuery 中,所以我希望没问题:

var files = [];

// Attaches to the dropzone to pickup the files dropped on it. In mine this is a div.
$("#dropzone").bind('dragover drop', function(event) 
    // Stop default actions - if you don't it will open the files in the browser
    event.stopPropagation();
    event.preventDefault();

    if (e.type == 'drop') 
        files.push(event.originalEvent.dataTransfer.files);
    
);

// Attach this to a an input type file so it can grab files selected by the input
$("#file-input").bind('change', function(event) 
    files.push(event.target.files);
);

// This is a link or button which when clicked will do the ajax request 
// and upload the files
$("#upload-button").bind('click', function(event) 
    // Stop the default actions
    event.stopPropagation();
    event.preventDefault();

    if (files.length == 0) 
        // Handle what you want to happen if no files were in the "queue" on clicking upload
        return;
    

    var formData = new FormData();
    $.each(files, function(key, value) 
        formData.append(key, value);
    );

    $.ajax(
        url: 'upload-ajax',
        type: 'POST',
        data: formData,
        cache: false,
        dataType: 'json',
        processData: false, // Don't process the files - I actually got this and the next from an SO post but I don't remember where
        contentType: false, // Set content type to false as jQuery will tell the server its a query string request
        success: function(data, textStatus, jqXHR)  /* Handle success */ ,
        error: function(jqXHR, textStatus, errorThrown)  /* Handle error */ 
    );

);

您还可以绑定到已接受答案中的其他事件,以执行诸如使 dropzone 淡入的效果,以便您可以看到它(在我的库的待办事项列表中)。然而,这是我实际使用的 ajax 文件上传的核心。

我真的没有一个方便的方法来测试它,但本质上我就是这样做的(我基本上从我一直在制作的库中获取了所有代码,并对其进行了调整以适应此处的通用代码块以易于理解的方式)。希望这可以帮助一些人。从这里开始实际上很容易继续添加文件队列列表,并能够从队列中删除文件,所以这应该是一个很好的起点。

【讨论】:

以上是关于JQuery - 拖放文件 - 如何获取文件信息?的主要内容,如果未能解决你的问题,请参考以下文章

使用 HTML5/jQuery 上传拖放文件

PYQT5 (十八)文件拖放(drag and drop)并获取文件信息

使用 jquery UI 时如何获取可拖放元素的 id?

jQuery:[1]实现图片上传并预览

有没有好的 jQuery 拖放文件上传插件?

拖放项目并在数据库中更新后,如何在 jQuery Nestable 插件中获取子项和 id?