Categories
JavaScript

Introducing the JavaScript Window Object — VisibilityState and Child Elements

Spread the love

The window object is a global object that has the properties pertaining to the current DOM document, which is the things that are in the tab of a browser. The document property of the window object has the DOM document and associated nodes and methods that we can use to manipulate the DOM nodes and listen to events for each node. Since the window object is global, it’s available in every part of the application. When a variable is declared without the var , let or const keywords, they’re automatically attached to the window object, making them available to every part of your web app. This is only applicable when strict mode is disabled. If it’s enabled, then declaring variables without var , let , or const will be stopped an error since it’s not a good idea to let us declare global variables accidentally. The window object has many properties. They include constructors, value properties and methods. There’re methods to manipulate the current browser tab like opening and closing new popup windows, etc.

In a tabbed browser, each tab has its own window object, so the window object always represent the state of the currently opened tab in which the code is running. However, some properties still apply to all tabs of the browser like the resizeTo method and the innerHeight and innerWidth properties.

Note that we don’t need to reference the window object directly for invoking methods and object properties. For example, if we want to use the window.Image constructor, we can just write new Image() . In this article, we continue to look at what’s in the window object. In the previous sections, we looked at the constructors and some of the properties of the window object, including using the customElemnts to build a Web Component, and the crypto object to do cryptography on the client using symmetric and asymmetric encryption algorithms. In this part, we will continue from Part 9 and look at more properties of the window.document object, including the visibilityState, childElementCount, and firstElementChild properties.

window.document.visibilityState

The visibilityState property is a read only property that returns the visibility status of the document object in which context this element is now visible. It’s useful for knowing if the document is visible in a background or invisible tab or only loaded for pre-rendering. It’s a string property that can have the following possible values:

  • 'visible' — the page content may at least be partially visible. This means the page is in the foreground tab of a non-minimized window.
  • 'hidden' — the page is not visible to the user. This means that the page is either in a background tab, the window has been minimized, or it’s behind a lock screen.
  • 'prerender' — the page is pre-rendering but not visible to the user. The document may start in this state but can’t transition to another value. This value is removed from the standard so might not be returned by many modern browsers.

For example, to watch for the visibility of a browser tab, we can write the following code:

console.log(document.visibilityState);
document.addEventListener('visibilitychange', () => {
  console.log(document.visibilityState);
})

Then when we split off the browser’s development console from the browser tab, then we switch between tabs while looking at the console.log output from the browser development console without the tab being visible. When we do that, we should see that it logs 'visible' when the browser tab is visible and when you switched out of the tab you’re logging the visibilityState from into another tab then the console.log output will become hidden .

window.document.**childElementCount**

The childElementCount is a read only number property that returns unsigned long number that represents the number of child elements in a given element. For example, if we run:

console.log(document.childElementCount);

Then we should get 1 since the only child of document is the html element.

window.document.children

The get the child elements of document we can use the children property, which is a read only property that returns an HTMLCollection array like object with all the child elements of the document object upon it’s called. For example, if we have the following HTML code:

<div>
  A
</div>
<div>
  B
</div>
<div>
  C
  <div>
    D
  </div>
</div>

Then we can loop through the HTMLCollection object with the for...of loop since it’s an array like object like in the following code:

for (const child of document.children) {
  const {
    tagName,
    outerHTML,
    outerText
  } = child
  console.log(tagName);
  console.log(outerHTML);
  console.log(outerText);
}

Then we get output from the console.log statements. First we get:

HTML

from the first console.log line. Then from the second console.log statement we get the following output:

<html><head>
  <meta http-equiv="content-type" content="text/html; charset=UTF-8">
  <title></title>
  <meta http-equiv="content-type" content="text/html; charset=UTF-8">
  <meta name="robots" content="noindex, nofollow">
  <meta name="googlebot" content="noindex, nofollow">
  <meta name="viewport" content="width=device-width, initial-scale=1">

<script type="text/javascript" src="/js/lib/dummy.js"></script>

<link rel="stylesheet" type="text/css" href="/css/result-light.css">

<style id="compiled-css" type="text/css">

  </style>

<!-- TODO: Missing CoffeeScript 2 -->

<script type="text/javascript">//<![CDATA[

window.onload=function(){

for (const child of document.children) {
  const {
    tagName,
    outerHTML,
    outerText
  } = child
  console.log(tagName);
  console.log(outerHTML);
  console.log(outerText);
}

}

//]]></script>

</head>
<body>
    <div>
  A
</div>
<div>
  B
</div>
<div>
  C
  <div>
    D
  </div>
</div>

<script>
    // tell the embed parent frame the height of the content
    if (window.parent && window.parent.parent){
      window.parent.parent.postMessage(["resultsFrame", {
        height: document.body.getBoundingClientRect().height,
        slug: ""
      }], "*")
    }

// always overwrite window.name, in case users try to set it manually
    window.name = "result"
  </script>

</body></html>

Then from the third console.log line we get:

A
B
C
D

Since we’re getting the children property from the document object, we have the html element as the only child, so we only have one object from the children property.

window.document.**firstElementChild**

The firstElementChild property is a read only property that returns the document ‘s first child. It only has one child which is the html element, so that’s what will be returned. The returned object will be an Element object, which has the properties of an HTML element. If there’s no child then null is returned. An Element object also has the following properties:

  • attributes — a read only property that has the NamedNodeMap object that contains the assigned attributes of the HTML element
  • classList — a read only property that has the list of class attrbiutes.
  • className — a read only string property that has the class of the element
  • cilentHeight — a read only number property that has the inner height of the element
  • clientLeft — a read only number property that has the width of the left border of the element
  • clientTop — a read only number property that has the width of the top border of the element
  • cilentWidth — a read only number property that has the inner width of the element
  • computedName — a read only string property that has the label exposed to accessibility.
  • computedRole — a read only string property that has the ARIA role that’s applied to the particular element.
  • id — a string that has the ID of the element
  • innerHTML — a string that has the HTML markup of the element’s content
  • localName — a read only string that has the local part of the qualified name of the element
  • namespaceURI — a read only property that has the namespace URL of them element or null if there’s no namespace
  • nextElementSibling — a read only property that has another Element object that represents the element which immediately follows the current element, or null if there’s no sibling node.
  • outerHTML — a string that represents the markup of the element including its content. It can also be set so that it replaces the content of the element with the HTML that we assign to this property
  • part — has the part identifiers which are set using the part attribute.
  • prefix — a read only string property that has the namespace prefix of the element, or null if no prefix is specified
  • previousElementSibling— a read only property that has another Element object that represents the element which is immediately before the current element, or null if there’s no such node.
  • scrollHeight — a read only number property that has the scroll view height of the element
  • scrollLeft — a number property that has the left scroll offset of the element. This can be getter or a setter
  • scroolLeftMax — a read only number property that has the maximum left scroll offset possible for the element
  • scrollTop — a number property that has the number of pixels of the top of the document that’s scrolled vertically
  • scrollTopMax — a read only property hat has the maximum top scroll offset possible for the element
  • scrollWidth — a read only number property that has the scroll view width of the element
  • shadowRoot — a read only property that has the open shadow root that’s hosted by the element, or null if no open shadow root is present
  • openOrClosedShadowRoot — a read only property that’s only available WebExtensions that has the shadow root hosted by the element regardless of status.
  • slot — the name of the shadow DOM slot the element is inserted in
  • tabStop — a boolean property that indicates if the element can receive input focus by pressing the tab key
  • tagName — a read only with the string that has the tag name of the given element

For example, we can use it like in the following code:

console.log(document.firstElementChild);

Then we should get something like:

<body>
    <div>
  A
</div>
<div>
  B
</div>
<div>
  C
  <div>
    D
  </div>
</div>

<script>
    // tell the embed parent frame the height of the content
    if (window.parent && window.parent.parent){
      window.parent.parent.postMessage(["resultsFrame", {
        height: document.body.getBoundingClientRect().height,
        slug: ""
      }], "*")
    }

// always overwrite window.name, in case users try to set it manually
    window.name = "result"
  </script>

</body>

We can also get the individual properties of the html Element object like in the following code:

const {
  clientLeft,
  innerHTML,
  outerHTML
} = document.firstElementChild;

console.log(clientLeft);
console.log(innerHTML);
console.log(outerHTML);

Then we should get the width of the left border of the html element which is 0 and get the HTML content of the document logged for the last 2 console logs.

With the document object, we have some handy properties to let us get the elements in the document by using its handy properties. The visibilityState property let us know if the browser tab’s document is visible or not. The childElementCount property get us the number of child elements of the document object which should be 1 since the document object’s only child is the html element. The firstElementChild property should get us the first child element of the document object which should be the html element since it’s the only child element of the document object.

By John Au-Yeung

Web developer specializing in React, Vue, and front end development.

Leave a Reply

Your email address will not be published. Required fields are marked *