2

According to the Mozilla Doc, the value none for the CSS attribute display does the following:

Turns off the display of an element (it has no effect on layout); all descendant elements also have their display turned off. The document is rendered as though the element did not exist.

I know this means I can't see the element. Since the element has no effect on the layout, it appears as if it does not exist.

My question is: does it still exist in the layout (it still responds to user events)? Or does it not exist in the layout at all (therefore not just appearance)?

Just to clarify:

I know the element still exists in the DOM. I'm asking if interaction with the view can still affect the state of that element. For example, if I click where a hidden element would have existed, does that still trigger an event?

I'm asking because I know you can target hidden elements in CSS like so:

input[type="checkbox"] {
  display: none;
}

input[type="checkbox"]:checked + otherElement {
   ...
}

Some event must be firing or else the second CSS selector would not work.

Can someone explain this?

linstantnoodles
  • 4,350
  • 1
  • 22
  • 24
  • It's hidden. How would you click on it? @Xander: No, you cannot focus hidden inputs. – Bergi Feb 26 '14 at 02:10
  • @Xander: You mean blur *from*, don't you? It is indeed interesing what happens when you hide a field that currently has the focus (Opera glitches for example), the `blur` event might not be fired immediately. – Bergi Feb 26 '14 at 02:24

3 Answers3

2

For example, if I click where a hidden element would have existed, does that still trigger an event?

There is no such thing as "click where a hidden element would have existed".

For example, if a brick was not used in building a house, you can't touch it by touching the line between two other bricks, even if it could have been there otherwise.

So there are no user-caused events that apply to an invisible object not included in the layout.

However I am pretty sure it would still produce other events, for example ones reported by MutationObserver. I would expect events dispatched by dispatchEvent to work as well, though I hadn't tested this.

Andrey Shchekin
  • 21,101
  • 19
  • 94
  • 162
1

It will have no effect on your layout, as if it didn't exist, but the content is still present in the HTML DOM. The CSS attribute display:none is just that - a CSS attribute, and it does not modify your HTML content.

You can still perform javascript functions on the element.

Jaron Gao
  • 466
  • 3
  • 9
  • I know that it still exists in the DOM. I'm wondering if you can still affect the state of the element through interaction with the layout. – linstantnoodles Feb 26 '14 at 01:44
  • You can perform anything you want to it the same way as if it didn't have `display:none`. – Jaron Gao Feb 26 '14 at 01:46
  • @linstantnoodles What do you mean by "state" of the element? Also, interacting with other elements can affect the element if those elements have events tied to them that change it. – Zhihao Feb 26 '14 at 01:46
  • 1
    @linstantnoodles Just read the updated question. No, clicking where the element would have existed does not trigger an event *originating from the element*. This is because it doesn't take up any space on the page, and so you can't actually click on it. As a side note, `visibility: hidden` will make the element invisible but still take up space. – Zhihao Feb 26 '14 at 01:49
1

You cannot affect the state of an element that is display: none by interacting directly with the element, because that element is not rendered. However you can still affect its state by interacting with other elements that fire events that in turn change the state of that element via the DOM.

Some event must be firing or else the second CSS selector would not work.

Can someone explain this?

States and events are completely different. Events do not need to have fired for the state of an element to change, and when an element changes its state it does not necessarily fire any events. Selectors never operate on events; they are always state-based.

In your example, if the input element was already checked via the checked attribute, then the DOM loads with that element in that state to begin with, and no events would be fired, and it would still allow otherElement to match the selector immediately. Furthermore, it would continue to match that selector, until something happens that causes the input to become unchecked (or in CSS selector terms, :not(:checked)).

See my answer to this other question for a little more explanation on states vs events in CSS.

Community
  • 1
  • 1
BoltClock
  • 700,868
  • 160
  • 1,392
  • 1,356
  • 1
    Interesting. So are you saying that the state of the checkbox is actually being affected by bubbling? What's actually changing the state of the unchecked checkbox while it's hidden? – linstantnoodles Feb 26 '14 at 14:45
  • 1
    @linstantnoodles: It can be anything, not just bubbling. You could directly query that element via the DOM using a selector and set its `checked` property there in or out of an event. – BoltClock Feb 26 '14 at 15:35
  • 1
    The state change of the hidden checkbox is caused by mouse click. So technically, the checkbox still exists in the layout or else the browser wouldn't be able to tell that the checkbox was clicked! – linstantnoodles Feb 26 '14 at 21:04
  • 1
    @linstantnoodles: Mouse click where, exactly? It's not supposed to respond to clicks on where it "would have" been had it been rendered. If you have a label that is associated with it, however, then that label could very well toggle the checkbox for you. – BoltClock Feb 27 '14 at 03:06
  • but the label is a sibling - why would the event from the label affect the checkbox? – linstantnoodles Feb 27 '14 at 18:01
  • @linstantnoodles: Because it's just how a label works and it doesn't necessarily have anything to do with events (they work even when JS is turned off)? – BoltClock Feb 28 '14 at 01:49
  • I guess it shouldn't work if the "for" attribute of the label isn't set. I just realized that the example I was referring to actually toggled the `checked` attribute via js (the label wasn't linked to the input). That clears things up. Thanks! – linstantnoodles Feb 28 '14 at 02:46