(Cảnh cáo ưu tiên: Nếu bạn bị cám dỗ đánh dấu mục này là trùng lặp, hãy lưu ý rằng các câu hỏi khác dường như hỏi "tại sao tôi gặp lỗi này?" 'm nhận được lỗi này; Tôi muốn biết làm thế nào tôi có thể phát hiện lỗi trong mã JavaScript của tôi. Nó chỉ xuất hiện trong giao diện điều khiển Firebug và, tất nhiên, hiển nhiên đối với người dùng khi hình ảnh được tải.)Phát hiện "hình ảnh bị hỏng hoặc cắt ngắn" trong Firefox
I đang sử dụng picturefill cho hình ảnh phản hồi. Tôi có một cuộc gọi lại được kích hoạt cho sự kiện tải trên hình ảnh. Vì vậy, cuộc gọi lại chạy mỗi lần ai đó thay đổi kích thước cửa sổ trình duyệt sao cho một hình ảnh khác được tải qua hình ảnh.
Bên trong hàm gọi lại, tôi đang chuyển đổi dữ liệu hình ảnh thành dataURL qua canvas để tôi có thể lưu trữ dữ liệu hình ảnh trong localStorage để có sẵn cho người dùng ngay cả khi họ ngoại tuyến.
Lưu ý một phần về "ngoại tuyến". Đó là lý do tại sao tôi không thể dựa vào bộ nhớ cache của trình duyệt. Và bộ nhớ cache ứng dụng ngoại tuyến HTML5 không đáp ứng nhu cầu của tôi vì hình ảnh phản hồi. (Xem "Application Cache is a Douchebag" để giải thích về sự không tương thích của hình ảnh phản hồi với bộ nhớ cache ứng dụng ngoại tuyến HTML.)
Trên Firefox 14.0.1 trên máy Mac, hình ảnh tải sẽ kích hoạt nếu tôi thay đổi kích thước trình duyệt thành thứ gì đó thực sự lớn và sau đó thay đổi kích thước quay trở lại một cái gì đó nhỏ một lần nữa trước khi hình ảnh lớn có một cơ hội để tải đầy đủ. Nó kết thúc báo cáo "Hình ảnh bị hỏng hoặc cắt ngắn" trong bảng điều khiển Firebug, nhưng không ném ngoại lệ hoặc kích hoạt sự kiện lỗi. Không có dấu hiệu gì sai trong mã. Chỉ trong giao diện điều khiển Firebug. Trong khi đó, nó lưu trữ một hình ảnh cắt ngắn trong localStorage.
Làm cách nào để phát hiện sự cố này một cách đáng tin cậy và hiệu quả trong JavaScript để tôi không lưu hình ảnh đó?
Đây là cách tôi lặp qua các divs picturefill để tìm thẻ img đã được chèn vào bởi picturefill:
var errorLogger = function() {
window.console.log('Error loading image.');
this.removeEventListener('load', cacheImage, false);
};
for(var i = 0, il = ps.length; i < il; i++){
if(ps[ i ].getAttribute("data-picture") !== null){
image = ps[ i ].getElementsByTagName("img")[0];
if (image) {
if ((imageSrc = image.getAttribute("src")) !== null) {
if (imageSrc.substr(0,5) !== "data:") {
image.addEventListener("load", cacheImage, false);
image.addEventListener('error', errorLogger, false);
}
}
}
}
}
Và đây là những gì các cacheImage()
callback trông giống như:
var cacheImage = function() {
var canvas,
ctx,
imageSrc;
imageSrc = this.getAttribute("src");
if ((pf_index.hasOwnProperty('pf_s_' + imageSrc)) ||
(imageSrc.substr(0,5) === "data:") ||
(imageSrc === null) || (imageSrc.length === 0)) {
return;
}
canvas = w.document.createElement("canvas");
canvas.width = this.width;
canvas.height = this.height;
ctx = canvas.getContext("2d");
ctx.drawImage(this, 0, 0);
try {
dataUri = canvas.toDataURL();
} catch (e) {
// TODO: Improve error handling here. For now, if canvas.toDataURL()
// throws an exception, don't cache the image and move on.
return;
}
// Do not cache if the resulting cache item will take more than 128Kb.
if (dataUri.length > 131072) {
return;
}
pf_index["pf_s_"+imageSrc] = 1;
try {
localStorage.setItem("pf_s_"+imageSrc, dataUri);
localStorage.setItem("pf_index", JSON.stringify(pf_index));
} catch (e) {
// Caching failed. Remove item from index object so next cached item
// doesn't wrongly indicate this item was successfully cached.
delete pf_index["pf_s_"+imageSrc];
}
};
Cuối cùng, đây là nội dung đầy đủ về những gì tôi thấy trong Firebug với URL đã thay đổi để bảo vệ sự phạm tội:
ảnh bị hỏng hoặc cắt ngắn: http://www.example.com/pf/external/imgs/extralarge.png
Nó không kích hoạt sự kiện 'lỗi' trên phần tử'
'? –
MaxArt
Bạn có thể hỏi tại sao bạn đang cố gắng triển khai bộ nhớ đệm hình ảnh của riêng mình trong bộ nhớ cục bộ thay vì chỉ để bộ nhớ cache của trình duyệt hoạt động? – jfriend00
@ jfriend00 Tôi đang lưu vào bộ nhớ cache hình ảnh để sử dụng ngoại tuyến. Tôi nói điều này trong câu hỏi, nhưng tôi đã nói nó như một bên. Tôi đã chỉnh sửa các câu hỏi để cung cấp cho các bit ẩn sự chú ý hơn. Dù sao thì, câu hỏi hiển nhiên tiếp theo là tại sao không sử dụng ứng dụng HTML5 offline appcaching. Để giải thích lý do tại sao hình ảnh phản hồi và HTML5 appcaching không tương thích, hãy xem http://www.alistapart.com/articles/application-cache-is-a-douchebag/ – Trott