/*! * All material copyright ESRI, All Rights Reserved, unless otherwise specified. * See https://github.com/Esri/calcite-components/blob/master/LICENSE.md for details. * v1.0.0-beta.97 */ import { h, Host } from "@stencil/core"; import { focusElement, toAriaBoolean } from "../../utils/dom"; import { connectLabel, disconnectLabel, getLabelText } from "../../utils/label"; import { connectForm, disconnectForm, HiddenFormInputSlot } from "../../utils/form"; import { updateHostInteraction } from "../../utils/interactive"; import { isActivationKey } from "../../utils/key"; export class Switch { constructor() { //-------------------------------------------------------------------------- // // Properties // //-------------------------------------------------------------------------- /** When `true`, interaction is prevented and the component is displayed with lower opacity. */ this.disabled = false; /** Specifies the size of the component. */ this.scale = "m"; /** * When `true`, the component is checked. * * @deprecated use `checked` instead. */ this.switched = false; /** When `true`, the component is checked. */ this.checked = false; //-------------------------------------------------------------------------- // // Private Methods // //-------------------------------------------------------------------------- this.keyDownHandler = (event) => { if (!this.disabled && isActivationKey(event.key)) { this.toggle(); event.preventDefault(); } }; this.clickHandler = () => { this.toggle(); }; this.setSwitchEl = (el) => { this.switchEl = el; }; } switchedWatcher(switched) { this.checked = switched; } //-------------------------------------------------------------------------- // // Public Methods // //-------------------------------------------------------------------------- /** Sets focus on the component. */ async setFocus() { focusElement(this.switchEl); } onLabelClick() { if (!this.disabled) { this.toggle(); this.setFocus(); } } toggle() { this.checked = !this.checked; this.calciteSwitchChange.emit({ switched: this.checked }); } //-------------------------------------------------------------------------- // // Lifecycle // //-------------------------------------------------------------------------- connectedCallback() { const initiallyChecked = this.checked || this.switched; if (initiallyChecked) { // if either prop is set, we ensure both are synced initially this.switched = this.checked = initiallyChecked; } connectLabel(this); connectForm(this); } disconnectedCallback() { disconnectLabel(this); disconnectForm(this); } componentDidRender() { updateHostInteraction(this); } // -------------------------------------------------------------------------- // // Render Methods // // -------------------------------------------------------------------------- render() { return (h(Host, { onClick: this.clickHandler, onKeyDown: this.keyDownHandler }, h("div", { "aria-checked": toAriaBoolean(this.checked), "aria-label": getLabelText(this), class: "container", ref: this.setSwitchEl, role: "switch", tabIndex: 0 }, h("div", { class: "track" }, h("div", { class: "handle" })), h(HiddenFormInputSlot, { component: this })))); } static get is() { return "calcite-switch"; } static get encapsulation() { return "shadow"; } static get originalStyleUrls() { return { "$": ["switch.scss"] }; } static get styleUrls() { return { "$": ["switch.css"] }; } static get properties() { return { "disabled": { "type": "boolean", "mutable": false, "complexType": { "original": "boolean", "resolved": "boolean", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "When `true`, interaction is prevented and the component is displayed with lower opacity." }, "attribute": "disabled", "reflect": true, "defaultValue": "false" }, "label": { "type": "string", "mutable": false, "complexType": { "original": "string", "resolved": "string", "references": {} }, "required": false, "optional": true, "docs": { "tags": [], "text": "Accessible name for the component." }, "attribute": "label", "reflect": false }, "name": { "type": "string", "mutable": false, "complexType": { "original": "string", "resolved": "string", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "Specifies the name of the component on form submission." }, "attribute": "name", "reflect": true }, "scale": { "type": "string", "mutable": false, "complexType": { "original": "Scale", "resolved": "\"l\" | \"m\" | \"s\"", "references": { "Scale": { "location": "import", "path": "../interfaces" } } }, "required": false, "optional": false, "docs": { "tags": [], "text": "Specifies the size of the component." }, "attribute": "scale", "reflect": true, "defaultValue": "\"m\"" }, "switched": { "type": "boolean", "mutable": true, "complexType": { "original": "boolean", "resolved": "boolean", "references": {} }, "required": false, "optional": false, "docs": { "tags": [{ "name": "deprecated", "text": "use `checked` instead." }], "text": "When `true`, the component is checked." }, "attribute": "switched", "reflect": true, "defaultValue": "false" }, "checked": { "type": "boolean", "mutable": true, "complexType": { "original": "boolean", "resolved": "boolean", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "When `true`, the component is checked." }, "attribute": "checked", "reflect": true, "defaultValue": "false" }, "value": { "type": "any", "mutable": false, "complexType": { "original": "any", "resolved": "any", "references": {} }, "required": false, "optional": false, "docs": { "tags": [], "text": "The component's value." }, "attribute": "value", "reflect": false } }; } static get events() { return [{ "method": "calciteSwitchChange", "name": "calciteSwitchChange", "bubbles": true, "cancelable": false, "composed": true, "docs": { "tags": [], "text": "Fires when the `checked` value has changed.\n\n**Note:** The event payload is deprecated, use the component's `checked` property instead." }, "complexType": { "original": "DeprecatedEventPayload", "resolved": "any", "references": { "DeprecatedEventPayload": { "location": "import", "path": "../interfaces" } } } }]; } static get methods() { return { "setFocus": { "complexType": { "signature": "() => Promise", "parameters": [], "references": { "Promise": { "location": "global" } }, "return": "Promise" }, "docs": { "text": "Sets focus on the component.", "tags": [] } } }; } static get elementRef() { return "el"; } static get watchers() { return [{ "propName": "switched", "methodName": "switchedWatcher" }]; } }