Javascript HTML5文件API-将文件发送到服务器进行处理

Javascript HTML5文件API-将文件发送到服务器进行处理,javascript,php,jquery,html,Javascript,Php,Jquery,Html,我有以下表格: <form> ... <input type="file" multiple="multiple" id="images" /> <a id="add">Add</a> ... <input type="submit" value="Submit" /> </form> 但是,两个集合都不包含提交的图像的项目。我想知道我做错了什么?谢谢好的,我认为您这里的问题是由Fi

我有以下表格:

<form>
    ...
    <input type="file" multiple="multiple" id="images" />
    <a id="add">Add</a>
    ...
    <input type="submit" value="Submit" />
</form>

但是,两个集合都不包含提交的图像的项目。我想知道我做错了什么?谢谢

好的,我认为您这里的问题是由FileReader的加载事件处理程序引起的,该处理程序将这些数据URL附加到表单中,并在表单提交到服务器后调用

您可以解决这个问题,去掉多余的images变量,通过在Add链接的click处理程序中将这些项添加到表单中来提交事件处理程序。您还可以利用此机会进行一点客户端验证,以防止重复的数据URL上载到服务器,甚至可以为所选图像添加预览/删除选项

此外,您可以通过将其单击处理程序替换为附加到文件输入的更改处理程序来删除添加链接

编辑nfplee:

var images = [];

$("#add").click(function() {
    var files = $("#images")[0].files;

    for (var i = 0; i < files.length; i++) {
        var reader = new FileReader();

        reader.onload = (function(file) {
            return function(e) {
                images.push({ name: file.name, file: e.target.result });
            };
        })(files[i]);

        reader.readAsDataURL(files[i]);
    }

    $("#images").val("");
});

var form = $("form");

form.submit(function() {
    for (var i = 0; i < images.length; i++) {
        $("<input>").attr({ type: "hidden",
            name: "images[" + i + "][name]" }).val(images[i].name).appendTo(form);
        $("<input>").attr({ type: "hidden",
            name: "images[" + i + "][file]" }).val(images[i].file).appendTo(form);
    }
});

您是否有多个具有相同id的项目?如果是这样的话,你需要改变这一点。HTML页面中不允许重复id。不,我只有一个名为images的元素。我也用不同的名字测试过,但似乎没有任何效果。控制台中有错误吗?例如,此行使用images.push[files[i];不好。看起来您实际上没有读取任何包含您正在创建的FileReader对象的文件,因此将输入元素添加到表单中的onload事件可能实际上没有触发。没有,没有javascript错误。我还使用开发人员工具对其进行了检查,并正确地为添加的每个图像执行了onload事件当表单提交时。谢谢@Aaraon。你的回答帮助我找到了正确的方向。我不确定你是否完全正确,但我发现将FileReader的加载事件移动到图像更改或添加单击事件处理程序可以很好地工作。我猜提交表单时FileReader不工作。不过它看起来更干净现在不管怎样。图像收集的原因是,我实际上使用javascript模板引擎来观察收集并在更新时更新ui。我将用最终代码编辑您的答案。太好了!我很高兴您能让它工作起来。FWIW,我认为初始方法的问题更多地与javascript调度的顺序有关与FileReader对象本身相比,dules事件和执行它们的处理程序。您正在侦听的那些加载事件被添加到事件队列中,在提交事件之后,侦听器被绑定到这些FileReader。对于任何感兴趣的人,都可以在上获取有关JavaScript事件计时的便捷刷新。
var form = $("form");

form.submit(function() {
    for (var i = 0; i < images.length; i++) {
        var reader = new FileReader();

        reader.onload = function(e) {
            $("<input>").attr({ type: "hidden", name: "images[]" }).val(e.target.result).appendTo(form);
        };

        reader.readAsDataURL(images[i]);
    }
});
print_r($_POST);
print_r($_FILES);
var images = [];

$("#add").click(function() {
    var files = $("#images")[0].files;

    for (var i = 0; i < files.length; i++) {
        var reader = new FileReader();

        reader.onload = (function(file) {
            return function(e) {
                images.push({ name: file.name, file: e.target.result });
            };
        })(files[i]);

        reader.readAsDataURL(files[i]);
    }

    $("#images").val("");
});

var form = $("form");

form.submit(function() {
    for (var i = 0; i < images.length; i++) {
        $("<input>").attr({ type: "hidden",
            name: "images[" + i + "][name]" }).val(images[i].name).appendTo(form);
        $("<input>").attr({ type: "hidden",
            name: "images[" + i + "][file]" }).val(images[i].file).appendTo(form);
    }
});