有没有办法确定图像路径是否会导致实际图像,即检测到图像无法在Javascript中加载。
对于Web应用程序,我正在解析xml文件并从图像路径列表中动态创建HTML图像。服务器上可能不再存在某些图像路径,因此我希望通过检测哪些图像无法加载并删除该HTML img元素来优雅地失败。
注意JQuery解决方案无法使用(老板不想使用JQuery,是的,我知道不要让我开始)。我知道JQuery中有一种方法可以检测图像何时加载,但不知道它是否失败。
我的代码用于创建img元素但是如何检测img路径是否导致无法加载图像?
var imgObj = new Image(); // document.createElement("img");
imgObj.src = src;
答案 0 :(得分:90)
您可以尝试以下代码。我不能担保浏览器兼容性,所以你必须测试它。
function testImage(URL) {
var tester=new Image();
tester.onload=imageFound;
tester.onerror=imageNotFound;
tester.src=URL;
}
function imageFound() {
alert('That image is found and loaded');
}
function imageNotFound() {
alert('That image was not found.');
}
testImage("http://foo.com/bar.jpg");
我对jQuery抗拒老板的同情!
答案 1 :(得分:32)
答案很好,但它引入了一个问题。只要您直接指定onload
或onerror
,它就可以替换之前分配的回调。这就是为什么有一个很好的方法,“在MDN上对他们在上调用的EventTarget上注册指定的监听器。您可以在同一事件中注册任意数量的侦听器。
让我稍微改写一下答案。
function testImage(url) {
var tester = new Image();
tester.addEventListener('load', imageFound);
tester.addEventListener('error', imageNotFound);
tester.src = url;
}
function imageFound() {
alert('That image is found and loaded');
}
function imageNotFound() {
alert('That image was not found.');
}
testImage("http://foo.com/bar.jpg");
因为外部资源加载过程是异步的,所以使用具有promise的现代JavaScript会更好,例如:
function testImage(url) {
// Define the promise
const imgPromise = new Promise(function imgPromise(resolve, reject) {
// Create the image
const imgElement = new Image();
// When image is loaded, resolve the promise
imgElement.addEventListener('load', function imgOnLoad() {
resolve(this);
});
// When there's an error during load, reject the promise
imgElement.addEventListener('error', function imgOnError() {
reject();
})
// Assign URL
imgElement.src = url;
});
return imgPromise;
}
testImage("http://foo.com/bar.jpg").then(
function fulfilled(img) {
console.log('That image is found and loaded', img);
},
function rejected() {
console.log('That image was not found');
}
);
答案 2 :(得分:13)
此:
<img onerror="this.src='/images/image.png'" src="...">
答案 3 :(得分:4)
/**
* Tests image load.
* @param {String} url
* @returns {Promise}
*/
function testImageUrl(url) {
return new Promise(function(resolve, reject) {
var image = new Image();
image.addEventListener('load', resolve);
image.addEventListener('error', reject);
image.src = url;
});
}
return testImageUrl(imageUrl).then(function imageLoaded(e) {
return imageUrl;
})
.catch(function imageFailed(e) {
return defaultImageUrl;
});
答案 4 :(得分:3)
这是我为另一个答案写的函数:Javascript Image Url Verify。我不知道它是否正是您所需要的,但它使用了您将使用的各种技术,其中包括onload
,onerror
,onabort
和一般超时的处理程序。
由于图像加载是异步的,因此您可以使用图像调用此函数,然后稍后使用结果调用回调。
答案 5 :(得分:3)
使用jQuery这对我有用:
$('img').error(function() {
$(this).attr('src', '/no-img.png').addClass('no-img');
});
我可以在我的网站上随处使用这张图片,无论其大小如何,具有以下CSS3属性:
img.no-img {
object-fit: cover;
object-position: 50% 50%;
}
提示1:使用至少800 x 800像素的方形图像。
提示2:与人物肖像一起使用时,请使用
object-position: 20% 50%;
对于缺少背景图片,我还在每个background-image
声明中添加了以下内容:
background-image: url('path-to-image.png'), url('no-img.png');
注意:不适用于透明图像。
另一个解决方案是使用Apache检测丢失的图像,然后发送到浏览器并使用默认的no-img.png内容重新设置它。
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_URI} /images/.*\.(gif|jpg|jpeg|png)$
RewriteRule .* /images/no-img.png [L,R=307]
答案 6 :(得分:0)
这是@emil.c 答案的变体,但根据图像加载与否使用真/假解决(而不是在失败时抛出错误):
function testImage(url) {
if (!url || typeof url !== 'string') return Promise.resolve(false);
return new Promise((resolve) => {
const imgElement = new Image();
imgElement.addEventListener('load', () => resolve(true));
imgElement.addEventListener('error', () => resolve(false));
imgElement.src = url;
});
}
答案 7 :(得分:-17)
如下所示:
var img = new Image();
img.src = imgUrl;
if (!img.complete) {
//has picture
}
else //not{
}