When is lit-element properties `hasChanged` called?

Viewed 2582

I have a simple lit-element with a property that has a hasChanged function.

<html>
<head>
<meta charset="utf-8" /> 
</head>
<body>

<script type="module">
  import {LitElement, html} from 'https://unpkg.com/@polymer/lit-element@0.7.0/lit-element.js?module';

  class MyElement extends LitElement {

    static get properties() {
      return {
        mood: {
          type: String,
          hasChanged: function(value, oldValue) {
            console.log(oldValue, " -> ", value);
            return BOOLEAN; // <== replace with true or false
          }
        }
      };
    }

    constructor() {
      super();
      this.mood = 'default';
    }

    render() {
      return html`${this.mood}`;
    }

  }

  customElements.define('my-element', MyElement);
</script>

<my-element mood="explicit"></my-element>

</body>
</html>

For the displayed result it doesn't matter whether you replace BOOLEAN by true or false. Both display explicit.

But the log outputs are different:

  • with true you get only one line:
undefined  ->  default
  • with false you get two lines:
undefined  ->  default
default  ->  explicit

The 'false' log output is what I expected. With lit-element until 0.6.5 you get the the same two lines also by returning true.

Is this a Bug introduced in lit-element 0.7.0 or is the new behavior valid? And if it is valid, why is no second call done by returning true from the first call.

1 Answers

It was as a performance optimization and always set the value set as attribute without call this function.

After the component is updated first time, this function is called whenever the property is set. You can compare the property’s old and new values, and evaluates whether or not the property has changed.

This function decide if an update will occur (returns true) or not (returns false)

More info: https://lit-element.polymer-project.org/guide/properties#configure-property-changes

Related