2013-04-12 29 views
12

Tôi đang cố gắng tải lên một số tệp lớn lên máy chủ bằng cách sử dụng XMLHttpRequest và file.slice.
Tôi đã quản lý việc này với sự trợ giúp của tài liệu và các liên kết khác nhau.
Vì tải lên tệp lớn là một công việc lâu dài, tôi muốn cung cấp cho người dùng thanh tiến trình.
Sau một số bài đọc khác, tôi đã xem qua một số example, về mặt lý thuyết, thực hiện chính xác những gì tôi cần.
Bằng cách lấy mẫu mã và thích ứng với nhu cầu của tôi đạtThanh tiến trình trong khi tải lên các tệp lớn với XMLHttpRequest

var upload = 
{ 
blobs: [], 
pageName: '', 
bytesPerChunk: 20 * 1024 * 1024, 
currentChunk: 0, 
loaded: 0, 
total: 0, 
file: null, 
fileName: "", 

uploadChunk: function (blob, fileName, fileType) { 
    var xhr = new XMLHttpRequest(); 

    xhr.onreadystatechange = function() { 
     if (xhr.readyState == 4) { 
      if (xhr.responseText) { 
       // alert(xhr.responseText); 
      } 
     } 
    }; 

    xhr.addEventListener("load", function (evt) { 
     $("#dvProgressPrcent").html("100%"); 
     $get('dvProgress').style.width = '100%'; 
    }, false); 

    xhr.addEventListener("progress", function (evt) { 
     if (evt.lengthComputable) { 
      var progress = Math.ceil(((upload.loaded + evt.loaded)/upload.total) * 100); 
      $("#dvProgressPrcent").html(progress + "%"); 
      $get('dvProgress').style.width = progress + '%'; 
     } 
    }, false); 

    xhr.upload.addEventListener("progress", function (evt) { 
     if (evt.lengthComputable) { 
      var progress = Math.ceil(((upload.loaded + evt.loaded)/upload.total) * 100); 
      $("#dvProgressPrcent").html(progress + "%"); 
      $get('dvProgress').style.width = progress + '%'; 
     } 
    }, false); 

    xhr.open('POST', upload.pageName, false); 

    xhr.setRequestHeader("Content-Type", "multipart/form-data"); 
    xhr.setRequestHeader("X-File-Name", fileName); 
    xhr.setRequestHeader("X-File-Type", fileType); 
    xhr.send(blob); 
}, 
upload: function (file) { 
    var start = 0; 
    var end = 0; 
    var size = file.size; 

    var date = new Date(); 
    upload.fileName = date.format("dd.MM.yyyy_HH.mm.ss") + "_" + file.name; 

    upload.loaded = 0; 
    upload.total = file.size; 

    while (start < size) { 
     end = start + upload.bytesPerChunk; 
     if (end > size) { 
      end = size; 
     } 

     var blob = file.slice(start, end); 
     upload.uploadChunk(blob, upload.fileName, file.type); 
     start = end; 
     upload.loaded += start; 
    } 

    return upload.fileName; 
} 
}; 

Cuộc gọi là loại tương tự (nếu không có sự kiểm chứng thực)

upload.upload(document.getElementById("#upload").files[0]); 

Vấn đề của tôi là trường hợp tiến bộ không kích hoạt.
Tôi đã thử xhr.addEventListener và với xhr.upload.addEventListener (mỗi lần tại một thời điểm và cả hai cùng một lúc) cho sự kiện tiến trình nhưng nó không bao giờ kích hoạt. Các sự kiện onreadystatechange và load chỉ kích hoạt tốt.

tôi sẽ đánh giá rất cao giúp với những gì tôi đang làm sai

Cập nhật
Sau nhiều nỗ lực tôi đã quản lý để mô phỏng một tiến bộ nhưng tôi đã chạy vào một vấn đề khác: giao diện người dùng Chrome không được cập nhật trong suốt tải lên.
Mã này trông như thế này tại

var upload = 
{ 
    pageName: '', 
    bytesPerChunk: 20 * 1024 * 1024, 
    loaded: 0, 
    total: 0, 
    file: null, 
    fileName: "", 

    uploadFile: function() { 
     var size = upload.file.size; 

     if (upload.loaded > size) return; 

     var end = upload.loaded + upload.bytesPerChunk; 
     if (end > size) { end = size; } 

     var blob = upload.file.slice(upload.loaded, end); 

     var xhr = new XMLHttpRequest(); 

     xhr.open('POST', upload.pageName, false); 

     xhr.setRequestHeader("Content-Type", "multipart/form-data"); 
     xhr.setRequestHeader("X-File-Name", upload.fileName); 
     xhr.setRequestHeader("X-File-Type", upload.file.type); 

     xhr.send(blob); 

     upload.loaded += upload.bytesPerChunk; 

     setTimeout(upload.updateProgress, 100); 
     setTimeout(upload.uploadFile, 100); 
    }, 
    upload: function (file) { 
     upload.file = file; 

     var date = new Date(); 
     upload.fileName = date.format("dd.MM.yyyy_HH.mm.ss") + "_" + file.name; 

     upload.loaded = 0; 
     upload.total = file.size; 

     setTimeout(upload.uploadFile, 100); 


     return upload.fileName; 
    }, 
    updateProgress: function() { 
     var progress = Math.ceil(((upload.loaded)/upload.total) * 100); 
     if (progress > 100) progress = 100; 

     $("#dvProgressPrcent").html(progress + "%"); 
     $get('dvProgress').style.width = progress + '%'; 
    } 
}; 


Cập nhật 2
tôi đã quản lý để sửa chữa nó và mô phỏng một thanh tiến trình làm việc trong chrome quá.
tôi đã cập nhật mẫu mã trước đó với mẫu hoạt động.
Bạn có thể thực hiện thanh 'làm mới' thường xuyên hơn bằng cách giảm kích thước của đoạn tải lên tại một thời điểm Tahnk bạn đã giúp đỡ của bạn

+0

Bạn đang sử dụng một hàm để rút ngắn các cuộc gọi 'document.getElementById'? Có vẻ như đó là những gì '$ get()' đang làm, nhưng tôi không thấy nó được định nghĩa ở bất cứ đâu. – user1091949

+0

có. nhưng tôi không nghĩ đó là vấn đề. nó hoạt động tốt trong sự kiện tải và đặt nó thành 100% – Cioby

+0

@Cioby bạn có thể tải lên JSFiddle về giải pháp của mình không? – frogbandit

Trả lời

3

Như đã nêu trong https://stackoverflow.com/a/3694435/460368, bạn có thể làm:

if(xhr.upload) 
    xhr.upload.onprogress=upload.updateProgress; 

updateProgress: function updateProgress(evt) 
{ 
    if (evt.lengthComputable) { 
     var progress = Math.ceil(((upload.loaded + evt.loaded)/upload.total) * 100); 
     $("#dvProgressPrcent").html(progress + "%"); 
     $get('dvProgress').style.width = progress + '%'; 
    } 
} 
+1

sự kiện tiến trình vẫn chưa được kích hoạt; – Cioby

+0

@Cioby Bạn đã thử làm theo cách không đồng bộ? 'xhr.open ('POST', upload.pageName, true);' http://www.w3.org/TR/XMLHttpRequest/#the-open()-method – Shikiryu

+0

@Cioby và bạn đã thử http: // stackoverflow.com/a/4943774/460368? – Shikiryu

0

có giải pháp của tôi:

function addImages(id) 
{ 


var files= $("#files").prop("files"); 
var file = files[loopGallery]; 
var cList= files.length; 

var fd = new FormData(); 

fd.append("file", file); 
fd.append("galerie", id); 


var xhr = new XMLHttpRequest(); 

xhr.open("POST", "moduls/galerie/uploadimages.php", true); 

xhr.upload.onprogress = function(e) 
{ 

var percentComplete = Math.ceil((e.loaded/e.total) * 100); 

$("#progress").css("display",""); 

$("#progressText").text((loopGallery+1)+" z "+cList); 
$("#progressBar").css("width",percentComplete+"%"); 

}; 


xhr.onload = function() 
{ 

if(this.status == 200) 
{ 
    $("#progressObsah").load("moduls/galerie/showimages.php?ids="+id); 

    if((loopGallery+1) == cList) 
    { 
     loopGallery = 0; 

    } 
    else 
    { 
    $("#progressBar").css("width", "0%"); 
loopGallery++; 
addImages(id); 
} 

}; 

}; 

if(cList < 1) 
{ 

} 
else 
{ 
xhr.send(fd); 
} 


} 
Các vấn đề liên quan