UNPKG

@figliolia/size-observer

Version:
102 lines (101 loc) 2.89 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.SizeObserver = void 0; /** * Size Observer * * A light-weight wrapper around the native Resize Observer API * * ```typescript * import { SizeObserver } from "@figliolia/size-observer"; * * const node = document.getElementByID("myDOMNode"); * const observer = new SizeObserver(node, { * width: true, * height: true, * onChange: ({ height, width }) => {} * }); * * // Clean up * observer.destroy(); * ``` */ class SizeObserver { constructor(node, options) { this.width = 0; this.height = 0; if (!node) { throw new Error("Element Observer: node reference is undefined"); } this.node = node; this.options = options; this.initialize(); } setOptions(options) { let reconnect = false; if (this.options.type !== options.type) { reconnect = true; } this.options = options; if (reconnect) { this.destroy(); this.initialize(); } } initialize() { var _a; this.initializeLayout(); this.observer = new ResizeObserver(entries => { let emit = false; for (const entry of entries) { if (this.options.type === "content-box") { emit = this.parseBlock(entry.contentBoxSize); } else if (this.options.type === "device-pixel-content-box") { emit = this.parseBlock(entry.devicePixelContentBoxSize); } else { emit = this.parseBlock(entry.borderBoxSize); } } if (emit) { this.emit(); } }); this.observer.observe(this.node, { box: (_a = this.options.type) !== null && _a !== void 0 ? _a : "border-box", }); } destroy() { this.observer.disconnect(); } initializeLayout() { const { height, width } = this.node.getBoundingClientRect(); this.width = width; this.height = height; this.emit(); } parseBlock(entry) { let emit = false; const { height, width } = this.options; for (const block of entry) { if (block.blockSize !== this.height) { this.height = block.blockSize; if (height) { emit = true; } } if (block.inlineSize !== this.width) { this.width = block.inlineSize; if (width) { emit = true; } } } return emit; } emit() { this.options.onChange({ width: this.width, height: this.height }, this.node); } } exports.SizeObserver = SizeObserver;