Javascript函数调用太快[重复]
Posted
技术标签:
【中文标题】Javascript函数调用太快[重复]【英文标题】:Javascript function called too soon [duplicate] 【发布时间】:2017-04-01 04:12:33 【问题描述】:我遇到了一个 javascript 函数的问题,该函数显然被调用得太早了。我有预感这是一个吊装问题,但我不确定。
所以,我有一个分配给onclick
的<img>
的函数:
function setModalPicture(picName)
//Build the path to the picture
var pic= 'assets/img/art/'+picName;
//Set the picture
$('#g-modal-img').attr('src', pic);
adjustModalPadding();
意图是将#g-modal-img 的src 属性设置为img
,然后才应调用adjustModalPadding
。这是因为adjustModalPadding
需要#g-modal-img
的高度,在src 设置为<img>
之前为零。但是,我注意到这不能正常工作,如果我让adjustModalPaddin
g 将#g-modal-img
的高度记录到控制台,它显示为零。我认为这意味着该函数在 src 设置为<img>
之前被调用。
【问题讨论】:
问题是图像的尺寸在图像成功加载之前是未知的。您需要为图像添加一个onload
侦听器。有关重复问题,请参阅 ***.com/a/626505/1902010。
吊装不会很快执行你的功能。
而 JavaScript 是一种“常规”编程语言。
我并不是故意不尊重 Javascript。 :) 我认为这是一个提升问题,并且由于我在 Javascript 之前从未见过提升,因此从这个意义上说,它对我来说不是一种“常规”语言。没有冒犯的意思。 :)
另外,当然是关于图像尚未加载的问题!抱歉,没有考虑清楚。我实际上在教程中看到了类似的东西,但我一生都记不起那里是如何处理的。
【参考方案1】:
您需要等待图片加载:
function setModalPicture(picName)
//Build the path to the picture
var pic= 'assets/img/art/'+picName;
//Set the picture
var img = $('#g-modal-img');
img.one("load", adjustModalPadding).attr('src', pic);
if (img[0].complete)
img.off("load", adjustModalPadding);
adjustModalPadding();
注意上面的顺序,因为它很重要:
-
首先,使用一次性处理程序 (
one
) 挂钩 load
事件。
然后,设置src
。
检查图像是否已经完成:如果是,删除处理程序并立即调用您的函数;否则,当load
触发时,它将调用adjustModalPadding
并将其作为处理程序删除。
您可能想要添加错误处理...
这是一个工作示例:
function setModalPicture(picName)
//Build the path to the picture
var pic = picName; // 'assets/img/art/'+picName;
//Set the picture
var img = $('#g-modal-img');
img.one("load", adjustModalPadding).attr('src', pic);
console.log("img[0].complete after setting src: " + img[0].complete);
if (img[0].complete)
img.off("load", adjustModalPadding);
adjustModalPadding();
function adjustModalPadding()
var img = $("#g-modal-img")[0];
console.log("Size: " + img.width + "x" + img.height);
$("input[type=button]").on("click", function()
console.log("img[0].complete before starting: " + $("#g-modal-img")[0].complete);
setModalPicture("https://graph.facebook.com/1035045703246692/picture?type=large");
);
<!-- In a comment, you said it starts out with src="" -->
<img id="g-modal-img" src="">
<input type="button" value="Click Me">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
这在 Chrome、Firefox 和 IE11 中适用于我。
或者,您可以通过克隆创建替换 img
元素:
function setModalPicture(picName)
//Build the path to the picture
var pic = picName; // 'assets/img/art/'+picName;
//Set the picture
var img = $("#g-modal-img");
var newImage = img.clone();
img.replaceWith(newImage);
newImage.one("load", adjustModalPadding).attr('src', pic);
console.log("newImage[0].complete after setting src: " + newImage[0].complete);
if (newImage[0].complete)
newImage.off("load", adjustModalPadding);
adjustModalPadding();
function adjustModalPadding()
var img = $("#g-modal-img")[0];
console.log("Size: " + img.width + "x" + img.height);
$("input[type=button]").on("click", function()
console.log("img[0].complete before starting: " + $("#g-modal-img")[0].complete);
setModalPicture("https://graph.facebook.com/1035045703246692/picture?type=large");
);
<!-- In a comment, you said it starts out with src="" -->
<img id="g-modal-img" src="">
<input type="button" value="Click Me">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
这在 Chrome、Firefox 和 IE11 中也适用于我。
最后,您可以从头开始创建替换 img
元素(不是克隆):
function setModalPicture(picName)
//Build the path to the picture
var pic = picName; // 'assets/img/art/'+picName;
//Set the picture
var img = $("#g-modal-img");
var newImage = $("<img>").attr("id", "g-modal-img");
img.replaceWith(newImage);
newImage.one("load", adjustModalPadding).attr('src', pic);
console.log("newImage[0].complete after setting src: " + newImage[0].complete);
if (newImage[0].complete)
newImage.off("load", adjustModalPadding);
adjustModalPadding();
function adjustModalPadding()
var img = $("#g-modal-img")[0];
console.log("Size: " + img.width + "x" + img.height);
$("input[type=button]").on("click", function()
console.log("img[0].complete before starting: " + $("#g-modal-img")[0].complete);
setModalPicture("https://graph.facebook.com/1035045703246692/picture?type=large");
);
<!-- In a comment, you said it starts out with src="" -->
<img id="g-modal-img" src="">
<input type="button" value="Click Me">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
【讨论】:
@richdotjs:不,one
,不是on
。这是一个一次性的处理程序。
嗯。我尝试了你的方法——例如,我照原样复制粘贴了你的代码——但它的行为方式完全相同。执行 adjustModalPadding 时,图片的高度仍然为零。完成一个实际的方法/属性吗?我会说不是(缺少 () 并且它没有显示在自动完成菜单中)。也许您的意思是“检查图像是否完整”的简写,但实际上我不知道该怎么做。
@Nicola:complete
是一个实际属性:w3.org/TR/html5/embedded-content-0.html#dom-img-complete 如果上述方法不起作用,我会相当惊讶。但如果不是,您可以考虑替换 #g-modal-img
用一个全新的img
元素,而不是仅仅更改它的src
(在设置src
之前再次挂钩load
等.).
我试试,谢谢
我正在使用 Firefox,但我通过找到一种 CSS 方法来解决此问题,以执行 adjustModalPadding 正在执行的操作。不再需要检查图像是否已加载 :) 感谢您的帮助!【参考方案2】:
可以在图片加载时使用事件:
var logo = document.getElementById('g-modal-img');
logo.addEventListener("load", function()
adjustModalPadding();
;
【讨论】:
我尽量避免使用.onload
,而是使用.addEventListener("load", () = )
是的,这是更好的选择:)
与上面的答案相同-尝试了您的方法,但图片的高度仍记录为零。
如何计算高度以上是关于Javascript函数调用太快[重复]的主要内容,如果未能解决你的问题,请参考以下文章