检测元素是否可见(不使用jQuery)

16

我想在不使用jQuery的情况下检测我给定ID的HTML元素是否可见。

背景:

在忘记用户密码页面中,我有一个表单,用户输入他的登录名并点击提交。之后,如果他设置了挑战性问题,它将被显示,他将能够回答这个问题并再次提交(同一个按钮)。

我的问题:

当用户点击提交时,在IE中,如果他点击几次,他会收到每次点击的一个电子邮件。

我的想法:

我想在点击此提交按钮后禁用该按钮,但只有在以下两个条件正确时才能禁用它:

  1. 如果用户已经提交了他的登录名(没有错误)。
  2. 用户注册并正确回答了挑战性问题。

我不能改变这个过程,所以我想在答案字段中添加一个ID,并检查它是否可见。如果它是可见的且用户点击提交按钮,则我想在标签上应用disable按钮属性。但我不知道如何在不使用jQuery的情况下实现这一操作。

使用jQuery,我可以这样做:

if($('#secretAns').is(':visible')) {
    //i think it could be the solution 
    $('#general_Submit.Label').attr( disabled, disabled );

}

申请应用于:

<div id="secretAns" class="loginTxtFieldWrapper">
    <font color='red'>*</font><input type="text" name="secretAns" />
    <input type="hidden" name="isAnswerPage" value="1"/>
</div>
<p id="loginSubmitLink">
    <input id="general_Submit.Label" type="submit" value="general_Submit.Label" />" />
</p>

我发现很难搜索到纯JavaScript的解决方案,因为每个人都倾向于使用jQuery,而我无法在我的应用程序中使用它,所以如果有人能帮助我使用纯JavaScript解决这个问题,我将不胜感激。


查看jQuery源代码,看看它们如何处理":visible"选择器。 - gdoron
可能是重复的问题:Javascript:如何检查元素是否可见? - Ajinkya
1
@Ajinkya,你注意到“duplicate”是一个jQuery问题了吗? - gdoron
那正是我现在要说的.. 我不能使用 jQuery。 - periback2
@ gdoron:刚刚注意到了。谢谢。 - Ajinkya
5个回答

27

谷歌帮助我找到了 jQuery 是如何做到这一点的,您也可以这样做:

在 jQuery 1.3.2 中,如果元素的 offsetWidthoffsetHeight 大于 0,则该元素可见。

发行说明

查看源代码给出了以下结果:

// The way jQuery detect hidden elements, and the isVisible just adds "!".
elem.offsetWidth === 0 && elem.offsetHeight === 0

@gdoron,干得好!这确实是...我会找出解决方案,并在找到时在此发布。谢谢。+1 - periback2
我添加了我的答案,只是为了展示解决我的问题的方法,但是对于我的问题标题的答案可能就是你的答案。我只是不理解offsetwidth或offsetheight是如何工作的。我明白它的检查可见性的方式,但我仍然会继续搜索更多相关信息。非常感谢。 - periback2
从jQuery源代码中。 https://github.com/jquery/jquery/blob/master/src/css/hiddenVisibleSelectors.js#L12 - theeranitp
1
@theeranitp,请注意,这个回答已经有将近7年的历史了,看起来他们现在只是加入了|| elem.getClientRects().length - gdoron

1
我之前写过这个代码,它可以处理很多情况。它实际上检查元素在当前状态下是否被用户看到。它会检查显示、可见性、不透明度、溢出问题,并且会递归地检查直到文档节点。
function isVisible(el) {
        while (el) {
            if (el === document) {
                return true;
            }

            var $style = window.getComputedStyle(el, null);

            if (!el) {
                return false;
            } else if (!$style) {
                return false;
            } else if ($style.display === 'none') {
                return false;
            } else if ($style.visibility === 'hidden') {
                return false;
            } else if (+$style.opacity === 0) {
                return false;
            } else if (($style.display === 'block' || $style.display === 'inline-block') &&
                $style.height === '0px' && $style.overflow === 'hidden') {
                return false;
            } else {
                return $style.position === 'fixed' || isVisible(el.parentNode);
            }
        }
    }

1
当我考虑禁用按钮时,我在这里写下我对解决此问题的想法是错误的,因为使其工作的成本非常高。 因此,在研究、测试一些想法和阅读@gdoron和@AmeyaRote提出的想法后,我发现一个简单的解决方案是在单击“提交”按钮后隐藏它(页面刷新,验证检查后,此过程完成后按钮再次可用)。 因此,这是解决问题的解决方案,以避免用户在无法禁用它的特定情况下多次单击提交按钮(如果单击后禁用,则表单不会被提交):

HTML

我只是添加了onclick属性,调用我创建的javascript函数来隐藏按钮:

<p id="loginSubmitLink">
    <input id="general_Submit.Label" type="submit" onclick ="avoidDoubleSubmit();" value="general_Submit.Label" />" />
</p>

The Javascript

function avoidDoubleSubmit() {
    <c:if test="${not empty secretQues}">
        event_addEvent(window,'load',function(){document.ResetPasswordForm.secretAns.focus();});
        document.getElementById('general_Submit.Label').style.display ='none';
    </c:if>
}

1
请查看这段常用但很少见的代码,可能会有用。
<!DOCTYPE html>
<html>
<body>
<div id="one" style="visibility: hidden;">The content of the body element is displayed in your browser.
</div>

<div id="two" style="visibility: visible;"> I'm Cool
</div>

<div onclick="push();"> Click me </div>
<script>
function push() {
a = document.getElementById("one").style.visibility;
alert("one "+a);

b = document.getElementById("two").style.visibility;
alert("one "+b);
}
</script>
</body>
</html>

以上代码使用其ID作为所需的内容,提供了div的可见性状态。


1
不仅仅是 style.visibilty - gdoron
你可以设置一个可见的计数器变量,并将其用作 if(visible_counter) 的条件,然后编写剩余的代码。 - ameya rote
实际上,如果未设置属性,则style.visibility返回null(我认为这是原因),而.offsetWidth在不可见时返回null,在可见时返回正值。因此,我相信@gdoron走的是最佳之路。 - periback2
它是空的,接受它。但是当它第一次被设置为可见/隐藏时,我们可以初始化它。此外,如果($('#secretAns').is(':visible'))返回null,除非设置了#secretAns的可见性。如果我错了,请纠正我。 - ameya rote

0

在 general_Submit.Label 按钮点击时调用 Callfun() 函数,然后禁用按钮

<input id="general_Submit.Label" onclick="Callfun()" type="submit" value="<ezmi18n:message key="general_Submit.Label" />" />

    function Callfun()
    {
     document.getElementById("general_Submit.Label").disabled = true;
    }

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接