UNPKG

@siberiaweb/components

Version:
459 lines (458 loc) 13.8 kB
import CSS from "./CSS"; import Icon from "../icon/Icon"; import WebComponent from "@siberiaweb/webcomponent/lib/WebComponent"; /** * Столбец. */ export default class Col extends WebComponent { /** * Конструктор. */ constructor() { super(); /** * Минимальная ширина. */ this._minWidth = 0; /** * Порядок сортировки. */ this._sortOrder = "none"; /** * Шаблон содержания ячейки. */ this.cellContentTemplate = document.createElement("template"); this.cell = this.createCell(); this.resizer = this.createResizer(); this.sortIndicator = this.createSortIndicator(); } /** * Наблюдаемые атрибуты. */ static get observedAttributes() { return WebComponent.observedAttributes.concat([ Col.ATTR_CONTENT_ALIGN, Col.ATTR_CLASS, Col.ATTR_MIN_WIDTH, Col.ATTR_RESIZE_DISABLED, Col.ATTR_SORT_DISABLED ]); } /** * Создание ячейки. */ createCell() { return document.createElement("td"); } /** * Создание элемента для изменения ширины столбца. */ createResizer() { let resizer = document.createElement("div"); resizer.classList.add(CSS.COL_RESIZER, CSS.COL_RESIZE_CURSOR); return resizer; } /** * Создание индикатора сортировки. */ createSortIndicator() { let icon = document.createElement(Icon.COMPONENT_NAME); icon.classList.add(CSS.SORT_INDICATOR); return icon; } /** * Обработка изменения атрибута "class". */ attrClassChange() { this.cell.removeAttribute(Col.ATTR_CLASS); for (let className of this.classList) { this.cell.classList.add(className); } } /** * Обработка изменения атрибута "content-align". */ attrContentAlignChange() { this.cell.classList.remove(CSS.CELL_CONTENT_ALIGN_CENTER, CSS.CELL_CONTENT_ALIGN_RIGHT); switch (this.contentAlign) { case "center": this.cell.classList.add(CSS.CELL_CONTENT_ALIGN_CENTER); break; case "right": this.cell.classList.add(CSS.CELL_CONTENT_ALIGN_RIGHT); break; } } /** * Обработка изменения атрибута "min-width". * * @param newValue Новое значение. */ attrMinWidthChange(newValue) { let value = newValue === null ? 0 : parseInt(newValue); if (isNaN(value) || (value < 0)) { value = 0; } this._minWidth = value; if (this.offsetWidth < this.minWidth) { this.setWidth(this.minWidth); } } /** * Обработка изменения атрибута "resize-disabled". */ attrResizeDisabledChange() { if (this.resizeDisabled) { this.resizer.remove(); } else if (!this.cell.contains(this.resizer)) { this.cell.appendChild(this.resizer); } } /** * Обработка изменения атрибута "sort-disabled". */ attrSortDisabledChange() { if (this.sortDisabled) { this.sortIndicator.remove(); } else if (!this.cell.contains(this.sortIndicator)) { this.cell.appendChild(this.sortIndicator); } } /** * @override */ attributeChangedCallback(name, oldValue, newValue) { super.attributeChangedCallback(name, oldValue, newValue); switch (name) { case Col.ATTR_CLASS: this.attrClassChange(); break; case Col.ATTR_CONTENT_ALIGN: this.attrContentAlignChange(); break; case Col.ATTR_MIN_WIDTH: this.attrMinWidthChange(newValue); break; case Col.ATTR_RESIZE_DISABLED: this.attrResizeDisabledChange(); break; case Col.ATTR_SORT_DISABLED: this.attrSortDisabledChange(); break; } } /** * @override */ firstConnectedCallback() { super.firstConnectedCallback(); let cellContentTemplate = this.querySelector("template"); if (cellContentTemplate !== null) { this.cellContentTemplate.content.appendChild(cellContentTemplate.content); } else if (this.textContent) { this.cellContentTemplate.content.append(this.textContent); } this.cell.appendChild(this.cellContentTemplate.content.cloneNode(true)); if (!this.resizeDisabled) { this.cell.appendChild(this.resizer); } if (!this.sortDisabled) { this.cell.appendChild(this.sortIndicator); } } /** * Получение заголовка. */ get caption() { return this.getAttributeOrDefault(Col.ATTR_CAPTION, ""); } /** * Установка заголовка. * * @param value Значение. */ set caption(value) { this.setAttribute(Col.ATTR_CAPTION, value); } /** * Получение выравнивания содержания. */ get contentAlign() { switch (this.getAttribute(Col.ATTR_CONTENT_ALIGN)) { case "center": return "center"; case "right": return "right"; default: return "left"; } } /** * Установка выравнивания. */ set contentAlign(value) { this.setAttribute(Col.ATTR_CONTENT_ALIGN, value); } /** * Получение наименования поля в наборе данных. */ get fieldName() { return this.getAttributeOrDefault(Col.ATTR_FIELD_NAME, ""); } /** * Установка наименования поля в наборе данных. * * @param value Значение. */ set fieldName(value) { this.setAttribute(Col.ATTR_FIELD_NAME, value); } /** * Получение типа данных поля в наборе данных. */ get fieldType() { switch (this.getAttribute(Col.ATTR_FIELD_TYPE)) { case "boolean": return "boolean"; case "date": return "date"; case "date-string": return "date-string"; case "number": return "number"; default: return "text"; } } /** * Установка типа данных поля в наборе данных. */ set fieldType(value) { this.setAttribute(Col.ATTR_FIELD_TYPE, value); } /** * Получение форматирования при выводе. */ get format() { return this.getAttributeOrDefault(Col.ATTR_FORMAT, ""); } /** * Установка форматирования при выводе. * * @param value Значение. */ set format(value) { this.setAttribute(Col.ATTR_FORMAT, value); } /** * Получение минимальной ширины. */ get minWidth() { return this._minWidth; } /** * Установка минимальной ширины. * * @param value Значение. */ set minWidth(value) { this.setAttribute(Col.ATTR_MIN_WIDTH, value.toString()); } /** * Получение наименования. */ get name() { return this.getAttributeOrDefault(Col.ATTR_NAME, ""); } /** * Установка наименования. * * @param value Значение. */ set name(value) { this.setAttribute(Col.ATTR_NAME, value); } /** * Получение шаблона, описывающего формат данных в наборе данных. */ get pattern() { return this.getAttributeOrDefault(Col.ATTR_PATTERN, ""); } /** * Установка шаблона, описывающего формат данных в наборе данных. * * @param value Значение. */ set pattern(value) { this.setAttribute(Col.ATTR_PATTERN, value); } /** * Получение признака отключения изменения ширины. */ get resizeDisabled() { return this.hasAttribute(Col.ATTR_RESIZE_DISABLED); } /** * Установка признака отключения изменения ширины. * * @param value Значение. */ set resizeDisabled(value) { this.toggleAttribute(Col.ATTR_RESIZE_DISABLED, value); } /** * Получение признака отключения сортировки. */ get sortDisabled() { return this.hasAttribute(Col.ATTR_SORT_DISABLED); } /** * Установка признака отключения сортировки. * * @param value Значение. */ set sortDisabled(value) { this.toggleAttribute(Col.ATTR_SORT_DISABLED, value); } /** * Получение порядка сортировки. */ get sortOrder() { return this._sortOrder; } /** * Установка порядка сортировки. * * @param value Значение. */ set sortOrder(value) { this._sortOrder = value; this.cell.classList.remove(CSS.SORT, CSS.SORT_ASC, CSS.SORT_DESC); if (this._sortOrder === "asc") { this.cell.classList.add(CSS.SORT, CSS.SORT_ASC); } else if (this._sortOrder === "desc") { this.cell.classList.add(CSS.SORT, CSS.SORT_DESC); } } /** * Установка следующего порядка сортировки. */ setNextSortOrder() { if (this.sortOrder === "asc") { this.sortOrder = "desc"; } else if (this.sortOrder === "desc") { this.sortOrder = "none"; } else { this.sortOrder = "asc"; } } /** * Получение ширины по умолчанию. */ getDefaultWidth() { let defaultWidth = parseInt(this.getAttributeOrDefault(Col.ATTR_DEFAULT_WIDTH, "0")); if (isNaN(defaultWidth) || (defaultWidth < 0)) { defaultWidth = 0; } return defaultWidth; } /** * Установка ширины столбца в пикселях. * * @param value Значение. */ setWidth(value) { if (value < this.minWidth) { value = this.minWidth; } this.cell.style.minWidth = value + "px"; this.cell.style.width = value + "px"; } /** * Получение шаблона содержания ячейки. */ getCellContentTemplate() { let template = document.createElement("template"); template.content.appendChild(this.cellContentTemplate.content.cloneNode(true)); return template; } /** * Получение ячейки. */ getCell() { return this.cell; } /** * Получение элемента для изменения размера столбца. */ getResizer() { return this.resizer; } } /** * Наименование компонента. */ Col.COMPONENT_NAME = "sw-grid-col"; /** * Заголовок. */ Col.ATTR_CAPTION = "caption"; /** * Класс CSS. */ Col.ATTR_CLASS = "class"; /** * Выравнивание содержания. */ Col.ATTR_CONTENT_ALIGN = "content-align"; /** * Ширина по умолчанию. */ Col.ATTR_DEFAULT_WIDTH = "default-width"; /** * Наименование поля в наборе данных. */ Col.ATTR_FIELD_NAME = "field-name"; /** * Тип данных поля в наборе данных. */ Col.ATTR_FIELD_TYPE = "field-type"; /** * Форматирование при выводе. */ Col.ATTR_FORMAT = "format"; /** * Скрытый столбец. */ Col.ATTR_HIDDEN = "hidden"; /** * Минимальная ширина. */ Col.ATTR_MIN_WIDTH = "min-width"; /** * Наименование. */ Col.ATTR_NAME = "name"; /** * Шаблон, описывающий формат данных в наборе данных. */ Col.ATTR_PATTERN = "pattern"; /** * Изменение размера отключено. */ Col.ATTR_RESIZE_DISABLED = "resize-disabled"; /** * Сортировка отключена. */ Col.ATTR_SORT_DISABLED = "sort-disabled"; /** * Тип данных поля по умолчанию. */ Col.DEFAULT_FIELD_TYPE = "text"; Col.define(Icon);