How to identify which file progress is for?
Asked Answered
M

2

5

Regarding jQuery File Upload, there is a progress event which passes back a data object, which as I understand it, reports the progress for each file.

I'm adding the file and progress bars to my UI via the add() event, and I want to later update their respective progress bars inside the progress() event. The problem I'm having is how do I match them up?

I need to give each file a unique ID so I can pair them, but one isn't provided as far as I can see. How are we supposed to do this?

Is there perhaps some JavaScript hashcode for each File object?

Some code:

$('#fileupload').fileupload({
    url: 'api/combox_upload.php',
    dataType: 'json',
    dropZone: $dropZone,
    done: function (e, data) {
        $.each(data.result, function(index, file) {
            // indicate completeness
        });
    },
    add: function(e, data) {
        $.each(data.files, function(index, file) {
            console.log(file);
            $file_uploads.append($('<li>').text(file.name));
        });
        data.submit(); // start upload immediately
    },
    progress: function(e, data) {
        console.log(data);
    }
});

I think I can attach a unique ID to each file by utilizing $.data like so:

var fileId = 0;

$('#fileupload').fileupload({
    url: 'api/combox_upload.php',
    dataType: 'json',
    dropZone: $dropZone,
    done: function (e, data) {
        $.each(data.result, function(index, file) {
            // indicate completeness
        });
    },
    add: function(e, data) {
        $.each(data.files, function(index, file) {
            //console.log(file);
            console.log(filename, fileId);
            $.data(file, 'id', fileId++);
            $file_uploads.append($('<li>').text(file.name));
        });
        data.submit(); // start upload immediately
    },
    progress: function(e, data) {
        var progress = parseInt(data.loaded / data.total * 100, 10);
        $.each(data.files, function(index, file) {
            console.log($.data(file,'id'), file.name, progress);
        });
        //console.log(data);
    }
});

The part that I'm confused about now is that in the progress event it doesn't just give you a single file, it gives you an array holding 1 file... I'm not sure if that if it's guaranteed to always have exactly 1 file in there (data.files) or not.

Mabe answered 27/12, 2012 at 21:3 Comment(0)
M
4

I should just read the section called How to tie a file to an element node during the life cycle of an upload:

$(function () {
    $('#fileupload').fileupload({
        dataType: 'json',
        add: function (e, data) {
            data.context = $('<p/>').text('Uploading...').appendTo(document.body);
            data.submit();
        },
        done: function (e, data) {
            data.context.text('Upload finished.');
        }
    });
});
Mabe answered 28/12, 2012 at 0:45 Comment(0)
E
3

You didn't post your code that is actually calling file upload or binding to the progress event, but my guess is that you just need to put a $.proxy wrapper around the fileuploadprogress function.

The $.proxy function allows you to specify what this will refer to in the function. Then inside your function you will have access to data and this will be able to provide the context.

Excite answered 27/12, 2012 at 21:13 Comment(5)
But I don't bind the progress event manually for each file...that's all done automatically. How would I set a different context for each file? Posted some code BTW.Mabe
Looking through the documentation / source code for the fileupload widget it has an option called singleFileUploads that is by default set to true. It is capable of doing more than one file, but as long as you don't change that value to false you should be guaranteed that there will only be 1 item in your files array.Excite
Oh.. I didn't notice that was true by default... but I'm not sure how this addresses the issue at all? You only instantiate $.fileupload() once and give it one progress event regardless. With $.proxy you'd have to bind each file to a different callback.Mabe
It appears that the data object is shared between add, progress, and done. I would assume that data.files[i].name would be a reasonable identifier. You could prevent add from calling data.submit() if there is already a file with the same name in the array.Excite
I thought about using the filename as the identifier but users can quite easily select files with the same name in different folders.Mabe

© 2022 - 2024 — McMap. All rights reserved.