import { noChange } from '../lit-html.js'; import { directive, Directive } from '../directive.js'; /** * @license * Copyright 2018 Google LLC * SPDX-License-Identifier: BSD-3-Clause */ // A sentinel that indicates guard() hasn't rendered anything yet const initialValue = {}; class GuardDirective extends Directive { constructor() { super(...arguments); this._previousValue = initialValue; } render(_value, f) { return f(); } update(_part, [value, f]) { if (Array.isArray(value)) { // Dirty-check arrays by item if (Array.isArray(this._previousValue) && this._previousValue.length === value.length && value.every((v, i) => v === this._previousValue[i])) { return noChange; } } else if (this._previousValue === value) { // Dirty-check non-arrays by identity return noChange; } // Copy the value if it's an array so that if it's mutated we don't forget // what the previous values were. this._previousValue = Array.isArray(value) ? Array.from(value) : value; const r = this.render(value, f); return r; } } /** * Prevents re-render of a template function until a single value or an array of * values changes. * * Values are checked against previous values with strict equality (`===`), and * so the check won't detect nested property changes inside objects or arrays. * Arrays values have each item checked against the previous value at the same * index with strict equality. Nested arrays are also checked only by strict * equality. * * Example: * * ```js * html` *
* ${guard([user.id, company.id], () => html`...`)} *
* ` * ``` * * In this case, the template only rerenders if either `user.id` or `company.id` * changes. * * guard() is useful with immutable data patterns, by preventing expensive work * until data updates. * * Example: * * ```js * html` *
* ${guard([immutableItems], () => immutableItems.map(i => html`${i}`))} *
* ` * ``` * * In this case, items are mapped over only when the array reference changes. * * @param value the value to check before re-rendering * @param f the template function */ const guard = directive(GuardDirective); export { guard }; //# sourceMappingURL=guard.js.map