UNPKG

@hashicorp/design-system-components

Version:
143 lines (139 loc) 5.81 kB
import Component from '@glimmer/component'; import { assert } from '@ember/debug'; import { element } from 'ember-element-helper'; import { hash } from '@ember/helper'; import style from 'ember-style-modifier'; import { HdsLayoutGridGapValues, HdsLayoutGridAlignValues } from './types.js'; import HdsLayoutGridItem from './item.js'; import { precompileTemplate } from '@ember/template-compilation'; import { setComponentTemplate } from '@ember/component'; /** * Copyright IBM Corp. 2021, 2025 * SPDX-License-Identifier: MPL-2.0 */ const ALIGNS = Object.values(HdsLayoutGridAlignValues); const DEFAULT_GAP = HdsLayoutGridGapValues.Zero; const GAPS = Object.values(HdsLayoutGridGapValues); class HdsLayoutGrid extends Component { get componentTag() { return this.args.tag ?? 'div'; } get align() { const { align } = this.args; if (align) { assert(`@align for "Hds::Layout::Grid" must be one of the following: ${ALIGNS.join(', ')}; received: ${align}`, ALIGNS.includes(align)); } return align; } get gap() { const { gap = DEFAULT_GAP } = this.args; if (gap) { assert(`@gap for "Hds::Layout::Grid" must be a single value or an array of two values of one of the following: ${GAPS.join(', ')}; received: ${gap}`, !Array.isArray(gap) && GAPS.includes(gap) || Array.isArray(gap) && gap.length === 2 && GAPS.includes(gap[0]) && GAPS.includes(gap[1])); return Array.isArray(gap) ? gap : [gap]; } else { return undefined; } } /* LOGIC: Default layout behavior: --hds-layout-grid-column-fill-type is set to auto-fit (fluid layout) If neither columnMinWidth nor columnWidth are passed in: - We do not set --hds-layout-grid-column-min-width (defaults to 0px) If columnMinWidth is passed in: - We set --hds-layout-grid-column-min-width to the passed in value If a columnWidth value is passed in: 1) we set --hds-layout-grid-column-min-width to the passed in value for the view 2) In the CSS, we use "auto-fill" for --hds-layout-grid-column-fill-type for the view (fixed layout) If both columnMinWidth & columnWidth are passed in: - We throw an error, as it doesn't make sense in the context of a CSS grid layout (too complex to determine which to use & desired behavior) */ get inlineStyles() { const inlineStyles = {}; // if both columnMinWidth and columnWidth are passed in, we throw an error assert(`@columnMinWidth and @columnWidth for "Hds::Layout::Grid" cannot be used together`, !(this.args.columnMinWidth && this.args.columnWidth)); if (this.args.columnMinWidth) { inlineStyles['--hds-layout-grid-column-min-width'] = this.args.columnMinWidth; } else if (this.args.columnWidth) { if (typeof this.args.columnWidth === 'string') { inlineStyles['--hds-layout-grid-column-min-width'] = this.args.columnWidth; } else if (typeof this.args.columnWidth === 'object') { // Responsive column widths if (this.args.columnWidth.sm) { inlineStyles['--hds-layout-grid-column-width-sm'] = this.args.columnWidth.sm; } if (this.args.columnWidth.md) { inlineStyles['--hds-layout-grid-column-width-md'] = this.args.columnWidth.md; } if (this.args.columnWidth.lg) { inlineStyles['--hds-layout-grid-column-width-lg'] = this.args.columnWidth.lg; } if (this.args.columnWidth.xl) { inlineStyles['--hds-layout-grid-column-width-xl'] = this.args.columnWidth.xl; } if (this.args.columnWidth.xxl) { inlineStyles['--hds-layout-grid-column-width-xxl'] = this.args.columnWidth.xxl; } } } return inlineStyles; } get classNames() { const classes = ['hds-layout-grid']; // add a class based on the @align argument if (this.align) { classes.push(`hds-layout-grid--align-items-${this.align}`); } // add a class based on the @gap argument if (this.gap) { if (this.gap.length === 2) { classes.push(`hds-layout-grid--row-gap-${this.gap[0]}`); classes.push(`hds-layout-grid--column-gap-${this.gap[1]}`); } else if (this.gap.length === 1) { classes.push(`hds-layout-grid--row-gap-${this.gap[0]}`); classes.push(`hds-layout-grid--column-gap-${this.gap[0]}`); } } // If a single columnWidth string is passed in, set the respective CSS class (non-responsive view case) if (typeof this.args.columnWidth === 'string') { classes.push('hds-layout-grid--column-width-non-responsive'); } // add classes based on responsive width arguments // If an object is passed in for the columnWidth arg, set the respective CSS classes if (typeof this.args.columnWidth === 'object') { if (this.args.columnWidth.sm) { classes.push('hds-layout-grid--column-width-sm'); } if (this.args.columnWidth.md) { classes.push('hds-layout-grid--column-width-md'); } if (this.args.columnWidth.lg) { classes.push('hds-layout-grid--column-width-lg'); } if (this.args.columnWidth.xl) { classes.push('hds-layout-grid--column-width-xl'); } if (this.args.columnWidth.xxl) { classes.push('hds-layout-grid--column-width-xxl'); } } return classes.join(' '); } static { setComponentTemplate(precompileTemplate("{{#let (element this.componentTag) as |Tag|}}\n <Tag class={{this.classNames}} {{style this.inlineStyles}} ...attributes>{{yield (hash Item=HdsLayoutGridItem)}}</Tag>\n{{/let}}", { strictMode: true, scope: () => ({ element, style, hash, HdsLayoutGridItem }) }), this); } } export { ALIGNS, DEFAULT_GAP, GAPS, HdsLayoutGrid as default }; //# sourceMappingURL=index.js.map