@scania/tegel
Version:
Tegel Design System
162 lines (161 loc) • 6.17 kB
JavaScript
import { h, Host } from "@stencil/core";
import dfs from "../../../utils/dfs";
/**
* @slot <default> - <b>Unnamed slot.</b> For injecting a native <code><button</code> and <code><a></code> element.
* */
export class TdsSideMenuItem {
constructor() {
/** If the item should appear selected. */
this.selected = false;
/** If the item should appear active. Can be used when the item is
* triggering a dropdown, and the dropdown is open, for example. */
this.active = false;
this.collapsed = false;
this.hasUserComponent = false;
}
findSlottedAndExecute(searchPredicate, callback) {
var _a;
const assignedElements = (_a = this.slotEl) === null || _a === void 0 ? void 0 : _a.assignedElements({ flatten: true });
if (!(assignedElements === null || assignedElements === void 0 ? void 0 : assignedElements.length))
return;
const firstSlottedElement = assignedElements[0];
if (firstSlottedElement) {
const foundElement = dfs(firstSlottedElement, searchPredicate);
if (foundElement) {
callback(foundElement);
}
}
}
/**
* This function is needed because we can't use CSS selectors to style something in the light dom
*/
updateSlottedElements() {
if (this.slotEl) {
const isIconOrSvg = (element) => element.tagName.toLowerCase() === 'tds-icon' || element.tagName.toLowerCase() === 'svg';
const addIconClass = (element) => {
element.classList.add('__tds-side-menu-item-icon');
if (this.collapsed) {
element.classList.add('__tds-side-menu-item-icon-collapsed');
}
else {
element.classList.remove('__tds-side-menu-item-icon-collapsed');
}
};
this.findSlottedAndExecute(isIconOrSvg, addIconClass);
}
}
updateHasUserComponent() {
if (this.slotEl) {
const isUserComponent = (element) => element.tagName.toLowerCase() === 'tds-side-menu-user';
this.hasUserComponent = false;
this.findSlottedAndExecute(isUserComponent, () => {
this.hasUserComponent = true;
});
}
}
connectedCallback() {
var _a;
// closest() will return null if side-menu-item is inside a shadowRoot that
// does not contain a side-menu. This is the case for the side-menu-dropdown.
this.sideMenuEl = this.host.closest('tds-side-menu');
this.collapsed = !!((_a = this.sideMenuEl) === null || _a === void 0 ? void 0 : _a.collapsed);
}
componentDidLoad() {
var _a, _b;
this.slotEl = (_b = (_a = this.host.shadowRoot) === null || _a === void 0 ? void 0 : _a.querySelector('slot')) !== null && _b !== void 0 ? _b : null;
this.updateSlottedElements();
this.updateHasUserComponent();
if (this.slotEl) {
this.slotEl.addEventListener('slotchange', () => {
this.updateSlottedElements();
this.updateHasUserComponent();
});
}
}
collapseSideMenuEventHandler(event) {
this.collapsed = event.detail.collapsed;
this.updateSlottedElements();
this.updateHasUserComponent();
}
render() {
return (h(Host, { key: '540c5825a2cf8913891c0b6c06ad7e338c9546bc' }, h("div", { key: '2482c645b0d4650f1a389eed12e097a8fc35c03f', class: {
'component': true,
'component-selected': this.selected,
'component-active': this.active,
'component-collapsed': this.collapsed,
'component-has-user': this.hasUserComponent,
} }, h("slot", { key: 'b476beffec5acc60afd8c7e60754c16995f43c32' }))));
}
static get is() { return "tds-side-menu-item"; }
static get encapsulation() { return "shadow"; }
static get originalStyleUrls() {
return {
"$": ["side-menu-item.scss"]
};
}
static get styleUrls() {
return {
"$": ["side-menu-item.css"]
};
}
static get properties() {
return {
"selected": {
"type": "boolean",
"mutable": false,
"complexType": {
"original": "boolean",
"resolved": "boolean",
"references": {}
},
"required": false,
"optional": false,
"docs": {
"tags": [],
"text": "If the item should appear selected."
},
"getter": false,
"setter": false,
"reflect": false,
"attribute": "selected",
"defaultValue": "false"
},
"active": {
"type": "boolean",
"mutable": false,
"complexType": {
"original": "boolean",
"resolved": "boolean",
"references": {}
},
"required": false,
"optional": false,
"docs": {
"tags": [],
"text": "If the item should appear active. Can be used when the item is\ntriggering a dropdown, and the dropdown is open, for example."
},
"getter": false,
"setter": false,
"reflect": false,
"attribute": "active",
"defaultValue": "false"
}
};
}
static get states() {
return {
"collapsed": {},
"hasUserComponent": {}
};
}
static get elementRef() { return "host"; }
static get listeners() {
return [{
"name": "internalTdsSideMenuPropChange",
"method": "collapseSideMenuEventHandler",
"target": "body",
"capture": false,
"passive": false
}];
}
}