diff --git a/addons/rose/addon/components/rose/layout/main/header.stories.mdx b/addons/rose/addon/components/rose/layout/main/header.stories.mdx deleted file mode 100644 index 3d2dda848..000000000 --- a/addons/rose/addon/components/rose/layout/main/header.stories.mdx +++ /dev/null @@ -1,66 +0,0 @@ -import { Meta, Story, Preview } from '@storybook/addon-docs/blocks'; -import { hbs } from 'ember-cli-htmlbars'; -import { action } from '@storybook/addon-actions'; -import { text, boolean, select } from '@storybook/addon-knobs'; - - - -# Layout | Main Header - -A header component for main layout component with ability to configure title and action buttons. Title can be configured to be a either a dropdown component or a simple heading title. The title dropdown is `Rose::Header::Dropdown` component where as all header actions are `Rose::Button` components. - -```html - - - - Menu item - Menu item - Button menu item - - - Secondary - Primary - -``` - - - {{ - template: hbs` - - - - Menu item - Menu item - Button menu item - - - Secondary - Primary - - `, - context: { - pagetitle: text('page title', 'Page Section Title'), - dropdownIcon: select( - 'dropdown icon', - { - 'user-square-fill': 'user-square-fill', - 'check-circle-outline': 'check-circle-outline', - 'copy-action': 'copy-action', - 'unfold-more': 'unfold-more', - 'unfold-less': 'unfold-less', - }, - 'user-square-fill' - ), - }, - }} - - -Main page title can configured to be a basic title. - -```html - - - -``` diff --git a/addons/rose/addon/components/rose/layout/page-header.stories.mdx b/addons/rose/addon/components/rose/layout/page-header.stories.mdx index c771ba93a..218fa75c1 100644 --- a/addons/rose/addon/components/rose/layout/page-header.stories.mdx +++ b/addons/rose/addon/components/rose/layout/page-header.stories.mdx @@ -6,7 +6,7 @@ import { action } from '@storybook/addon-actions'; # Layout|Page Header -A page layout/positioning component that configures a single column grid for use as a header. +A page layout/positioning component that configures a two column grid with defined areas: title and utilities ```htmlbars @@ -15,8 +15,9 @@ A page layout/positioning component that configures a single column grid for use {{ template: hbs` - - Page Header + +
Grid area: title
+
Grid area: utilities
`, }}
diff --git a/addons/rose/addon/components/rose/layout/main/header.js b/addons/rose/addon/components/rose/page-header/title.js similarity index 57% rename from addons/rose/addon/components/rose/layout/main/header.js rename to addons/rose/addon/components/rose/page-header/title.js index 74d539127..9ac3c1431 100644 --- a/addons/rose/addon/components/rose/layout/main/header.js +++ b/addons/rose/addon/components/rose/page-header/title.js @@ -1,5 +1,5 @@ import Component from '@ember/component'; -import layout from '../../../../templates/components/rose/layout/main/header'; +import layout from '../../../templates/components/rose/page-header/title'; export default Component.extend({ layout, diff --git a/addons/rose/addon/components/rose/page-header/title.stories.mdx b/addons/rose/addon/components/rose/page-header/title.stories.mdx new file mode 100644 index 000000000..050c77192 --- /dev/null +++ b/addons/rose/addon/components/rose/page-header/title.stories.mdx @@ -0,0 +1,62 @@ +import { Meta, Story, Preview } from '@storybook/addon-docs/blocks'; +import { hbs } from 'ember-cli-htmlbars'; +import { action } from '@storybook/addon-actions'; +import { text, select } from '@storybook/addon-knobs'; + + + +# Title + +A header title component with ability to configure dropdown using `Rose::Header::Dropdown`. To be used with `Rose::Layout::PageHeader`. + +```html + + + + Menu item + Button menu item + + + +``` + + + {{ + template: hbs` + + + + Menu item + Button menu item + + + + `, + context: { + pageTitle: text('pageTitle', 'Page Section Title'), + dropdownIcon: select( + 'dropdownIcon', + { + 'user-square-fill': 'user-square-fill', + 'check-circle-outline': 'check-circle-outline', + 'copy-action': 'copy-action', + 'unfold-more': 'unfold-more', + 'unfold-less': 'unfold-less', + }, + 'user-square-fill' + ), + }, + }} + + +Title can be configured to be a level 1 heading with optional icon. + +```html + +``` diff --git a/addons/rose/addon/components/rose/layout/main/header/title.js b/addons/rose/addon/components/rose/page-header/utilities.js similarity index 54% rename from addons/rose/addon/components/rose/layout/main/header/title.js rename to addons/rose/addon/components/rose/page-header/utilities.js index 285af1ebb..71b82bc1c 100644 --- a/addons/rose/addon/components/rose/layout/main/header/title.js +++ b/addons/rose/addon/components/rose/page-header/utilities.js @@ -1,5 +1,5 @@ import Component from '@ember/component'; -import layout from '../../../../../templates/components/rose/layout/main/header/title'; +import layout from '../../../templates/components/rose/page-header/utilities'; export default Component.extend({ layout, diff --git a/addons/rose/addon/components/rose/page-header/utilities.stories.mdx b/addons/rose/addon/components/rose/page-header/utilities.stories.mdx new file mode 100644 index 000000000..e1077084e --- /dev/null +++ b/addons/rose/addon/components/rose/page-header/utilities.stories.mdx @@ -0,0 +1,31 @@ +import { Meta, Story, Preview } from '@storybook/addon-docs/blocks'; +import { hbs } from 'ember-cli-htmlbars'; +import { action } from '@storybook/addon-actions'; + + + +# Utilities + +An component comprised of `Rose::Button` as actions. To be used with `Rose::Layout::PageHeader`. + +```html + + + Secondary + Primary + + +``` + + + {{ + template: hbs` + + + Secondary + Primary + + + `, + }} + diff --git a/addons/rose/addon/styles/rose/components/_index.scss b/addons/rose/addon/styles/rose/components/_index.scss index ec7bd22af..fd25c4bf2 100644 --- a/addons/rose/addon/styles/rose/components/_index.scss +++ b/addons/rose/addon/styles/rose/components/_index.scss @@ -4,4 +4,4 @@ @import 'layout'; @import 'notification'; @import 'card'; -@import 'nav'; +@import 'page-header'; diff --git a/addons/rose/addon/styles/rose/components/layout/_index.scss b/addons/rose/addon/styles/rose/components/layout/_index.scss index 40c35ee12..9b927fb2c 100644 --- a/addons/rose/addon/styles/rose/components/layout/_index.scss +++ b/addons/rose/addon/styles/rose/components/layout/_index.scss @@ -1,7 +1,6 @@ @use '../../variables/sizing'; @use '../../variables/media'; -@import 'main'; @import 'page-header'; .rose-layout-page { diff --git a/addons/rose/addon/styles/rose/components/layout/_page-header.scss b/addons/rose/addon/styles/rose/components/layout/_page-header.scss index 0fb1fe8eb..ccd539138 100644 --- a/addons/rose/addon/styles/rose/components/layout/_page-header.scss +++ b/addons/rose/addon/styles/rose/components/layout/_page-header.scss @@ -2,16 +2,21 @@ .rose-layout-page-header { display: grid; - grid-template-areas: - 'title title utilities'; + grid-template-areas: 'title title utilities'; grid-template-columns: 1fr auto; grid-template-rows: auto 1fr; + + .rose-page-header-utilities { + display: flex; + align-items: center; + justify-content: flex-end; + flex-wrap: wrap; + } } @media (max-width: media.width(small)) { - .rose-layout-page { + .rose-layout-page-header { grid-template-columns: 1fr; - grid-template-rows: 0.1fr auto 1fr; grid-template-areas: 'title' 'utilities'; diff --git a/addons/rose/addon/styles/rose/components/layout/main/_index.scss b/addons/rose/addon/styles/rose/components/layout/main/_index.scss deleted file mode 100644 index 6053ec318..000000000 --- a/addons/rose/addon/styles/rose/components/layout/main/_index.scss +++ /dev/null @@ -1 +0,0 @@ -@import 'header'; diff --git a/addons/rose/addon/styles/rose/components/layout/main/header/_index.scss b/addons/rose/addon/styles/rose/components/layout/main/header/_index.scss deleted file mode 100644 index 6e4be91b6..000000000 --- a/addons/rose/addon/styles/rose/components/layout/main/header/_index.scss +++ /dev/null @@ -1,75 +0,0 @@ -@use '../../../../utilities/type' as typography; -@use '../../../../variables/sizing'; -@use '../../../../variables/media'; - -.rose-layout-main-header { - display: grid; - grid-template-areas: 'title title actions'; - grid-template-columns: 1fr auto; - - .rose-layout-main-header-title { - display: inline-block; - grid-area: title; - - .rose-layout-main-header-title-text { - display: inline-block; - color: var(--stark); - } - - .rose-layout-main-header-title-icon { - vertical-align: sub; - - svg { - width: sizing.rems(l); - width: sizing.rems(l); - } - } - } - - .rose-header-dropdown { - .rose-header-dropdown-trigger-text { - // Apply heading level 1 style to text to fit page section style spec - // Duplicate of h1 style defined in typography - @include typography.type(h1, bold); - margin-top: sizing.rems(m); - margin-bottom: sizing.rems(xs); - - margin-right: sizing.rems(xs); - } - - .rose-header-dropdown-trigger { - background-size: sizing.rems(l); - background-position: right (sizing.rems(m) + sizing.rems(s)); - } - - .rose-icon > svg { - vertical-align: sub; - } - } - - .rose-layout-main-header-actions { - grid-area: actions; - display: flex; - align-items: center; - justify-content: flex-end; - - // Remove margin to align action buttons with h1 text - button { - margin-bottom: 0; - } - } -} - -@media (max-width: media.width(small)) { - .rose-layout-main-header { - grid-template-columns: 1fr; - grid-template-rows: 1fr auto; - grid-template-areas: - 'title' - 'actions'; - - .rose-layout-main-header-actions { - flex-wrap: wrap; - } - } -} diff --git a/addons/rose/addon/styles/rose/components/page-header/_index.scss b/addons/rose/addon/styles/rose/components/page-header/_index.scss new file mode 100644 index 000000000..6cd272653 --- /dev/null +++ b/addons/rose/addon/styles/rose/components/page-header/_index.scss @@ -0,0 +1,2 @@ +@import 'title'; +@import 'utilities'; diff --git a/addons/rose/addon/styles/rose/components/page-header/_title.scss b/addons/rose/addon/styles/rose/components/page-header/_title.scss new file mode 100644 index 000000000..32fdb890d --- /dev/null +++ b/addons/rose/addon/styles/rose/components/page-header/_title.scss @@ -0,0 +1,35 @@ +@use '../../variables/sizing'; +@use '../../utilities/type' as typography; + +.rose-page-header-title { + display: inline-block; + grid-area: title; + + .rose-page-header-title-text { + display: inline-block; + color: var(--stark); + } + + .rose-page-header-title-icon { + vertical-align: sub; + + svg { + width: sizing.rems(l); + width: sizing.rems(l); + } + } + + .rose-header-dropdown { + .rose-header-dropdown-trigger-text { + @include typography.type(h1, bold); + margin-top: sizing.rems(xs); + margin-bottom: sizing.rems(xs); + + margin-right: sizing.rems(xs); + } + + .rose-header-dropdown-trigger { + background-size: sizing.rems(l); + } + } +} diff --git a/addons/rose/addon/styles/rose/components/page-header/_utilities.scss b/addons/rose/addon/styles/rose/components/page-header/_utilities.scss new file mode 100644 index 000000000..45a78dd82 --- /dev/null +++ b/addons/rose/addon/styles/rose/components/page-header/_utilities.scss @@ -0,0 +1,8 @@ +.rose-page-header-utilities { + grid-area: utilities; + + // Remove margin to align action buttons with h1 text + button { + margin-bottom: 0; + } +} diff --git a/addons/rose/addon/templates/components/rose/layout/main/header.hbs b/addons/rose/addon/templates/components/rose/layout/main/header.hbs deleted file mode 100644 index 9634fdb25..000000000 --- a/addons/rose/addon/templates/components/rose/layout/main/header.hbs +++ /dev/null @@ -1,11 +0,0 @@ -
- {{yield (hash - title=(component 'rose/layout/main/header/title') - )}} - -
- {{yield (hash - action=(component 'rose/button') - )}} -
-
diff --git a/addons/rose/addon/templates/components/rose/layout/main/header/title.hbs b/addons/rose/addon/templates/components/rose/layout/main/header/title.hbs deleted file mode 100644 index 1147d6c48..000000000 --- a/addons/rose/addon/templates/components/rose/layout/main/header/title.hbs +++ /dev/null @@ -1,19 +0,0 @@ -
- {{#if (has-block)}} - {{yield (hash - dropdown=(component 'rose/header/dropdown' style='dark') - )}} - {{else}} -
- {{#if @icon}} - {{inline-svg @icon}} - {{/if}} - - {{#if @text}} -

{{@text}}

- {{/if}} -
- {{/if}} -
diff --git a/addons/rose/addon/templates/components/rose/page-header/title.hbs b/addons/rose/addon/templates/components/rose/page-header/title.hbs new file mode 100644 index 000000000..388e53812 --- /dev/null +++ b/addons/rose/addon/templates/components/rose/page-header/title.hbs @@ -0,0 +1,17 @@ +
+ {{#if (has-block)}} + {{yield (hash + dropdown=(component 'rose/header/dropdown' style='dark') + )}} + {{else}} +
+ {{#if @icon}} + {{inline-svg @icon}} + {{/if}} + + {{#if @text}} +

{{@text}}

+ {{/if}} +
+ {{/if}} +
diff --git a/addons/rose/addon/templates/components/rose/page-header/utilities.hbs b/addons/rose/addon/templates/components/rose/page-header/utilities.hbs new file mode 100644 index 000000000..3203ea86e --- /dev/null +++ b/addons/rose/addon/templates/components/rose/page-header/utilities.hbs @@ -0,0 +1,5 @@ +
+ {{yield (hash + action=(component 'rose/button') + )}} +
diff --git a/addons/rose/app/components/rose/layout/main/header.js b/addons/rose/app/components/rose/layout/main/header.js deleted file mode 100644 index cc3ca8769..000000000 --- a/addons/rose/app/components/rose/layout/main/header.js +++ /dev/null @@ -1 +0,0 @@ -export { default } from 'rose/components/rose/layout/main/header'; diff --git a/addons/rose/app/components/rose/layout/main/header/title.js b/addons/rose/app/components/rose/layout/main/header/title.js deleted file mode 100644 index c189eb8d5..000000000 --- a/addons/rose/app/components/rose/layout/main/header/title.js +++ /dev/null @@ -1 +0,0 @@ -export { default } from 'rose/components/rose/layout/main/header/title'; diff --git a/addons/rose/app/components/rose/layout/page-header.js b/addons/rose/app/components/rose/layout/page-header.js index 0ee612631..5235f3c7b 100644 --- a/addons/rose/app/components/rose/layout/page-header.js +++ b/addons/rose/app/components/rose/layout/page-header.js @@ -1 +1 @@ -export { default } from 'rose/components/rose/layout/page-header'; \ No newline at end of file +export { default } from 'rose/components/rose/layout/page-header'; diff --git a/addons/rose/app/components/rose/page-header/title.js b/addons/rose/app/components/rose/page-header/title.js new file mode 100644 index 000000000..880f984d0 --- /dev/null +++ b/addons/rose/app/components/rose/page-header/title.js @@ -0,0 +1 @@ +export { default } from 'rose/components/rose/page-header/title'; diff --git a/addons/rose/app/components/rose/page-header/utilities.js b/addons/rose/app/components/rose/page-header/utilities.js new file mode 100644 index 000000000..69dd95a0c --- /dev/null +++ b/addons/rose/app/components/rose/page-header/utilities.js @@ -0,0 +1 @@ +export { default } from 'rose/components/rose/page-header/utilities'; diff --git a/addons/rose/tests/integration/components/rose/layout/main/header-test.js b/addons/rose/tests/integration/components/rose/layout/main/header-test.js deleted file mode 100644 index e2261a66d..000000000 --- a/addons/rose/tests/integration/components/rose/layout/main/header-test.js +++ /dev/null @@ -1,60 +0,0 @@ -import { module, test } from 'qunit'; -import { setupRenderingTest } from 'ember-qunit'; -import { render, find, findAll } from '@ember/test-helpers'; -import hbs from 'htmlbars-inline-precompile'; - -module('Integration | Component | rose/layout/main/header', function (hooks) { - setupRenderingTest(hooks); - - test('it renders', async function (assert) { - await render(hbs``); - assert.ok(find('.rose-layout-main-header')); - }); - - test('it renders with title', async function (assert) { - await render(hbs` - - `); - assert.ok(find('.rose-layout-main-header-title')); - assert.equal( - find('.rose-layout-main-header-title').textContent.trim(), - 'header title' - ); - }); - - test('it renders with dropdown title', async function (assert) { - await render(hbs` - - - - `); - assert.ok(find('.rose-header-dropdown')); - assert.equal( - find('.rose-layout-main-header-title').textContent.trim(), - 'Dropdown title' - ); - }); - - test('it renders with dropdown title menu', async function (assert) { - await render(hbs` - - - Menu item - Button menu item - - - `); - assert.ok(find('.rose-header-dropdown')); - assert.equal(findAll('a').length, 1); - assert.equal(findAll('button').length, 1); - }); - - test('it renders with actions', async function (assert) { - await render(hbs` - - - `); - assert.ok(find('.rose-layout-main-header-actions')); - assert.ok(findAll('button').length, 2); - }); -}); diff --git a/addons/rose/tests/integration/components/rose/layout/page-header-test.js b/addons/rose/tests/integration/components/rose/layout/page-header-test.js index a5f0be46b..723df72c1 100644 --- a/addons/rose/tests/integration/components/rose/layout/page-header-test.js +++ b/addons/rose/tests/integration/components/rose/layout/page-header-test.js @@ -3,21 +3,26 @@ import { setupRenderingTest } from 'ember-qunit'; import { render, find } from '@ember/test-helpers'; import hbs from 'htmlbars-inline-precompile'; -module('Integration | Component | rose/layout/page-header', function(hooks) { +module('Integration | Component | rose/layout/page-header', function (hooks) { setupRenderingTest(hooks); - test('it renders', async function(assert) { + test('it renders', async function (assert) { await render(hbs``); assert.ok(find('.rose-layout-page-header')); }); - test('it renders with html attributes', async function(assert) { + test('it renders with html attributes', async function (assert) { await render(hbs``); assert.ok(find('#page-header')); }); - test('it renders with content', async function(assert) { - await render(hbs`Page header content`); - assert.equal(find('.rose-layout-page-header').textContent.trim(), 'Page header content'); + test('it renders with content', async function (assert) { + await render( + hbs`Page header content` + ); + assert.equal( + find('.rose-layout-page-header').textContent.trim(), + 'Page header content' + ); }); }); diff --git a/addons/rose/tests/integration/components/rose/layout/main/header/title-test.js b/addons/rose/tests/integration/components/rose/page-header/title-test.js similarity index 73% rename from addons/rose/tests/integration/components/rose/layout/main/header/title-test.js rename to addons/rose/tests/integration/components/rose/page-header/title-test.js index 8d7fef6ac..b4e8d7e74 100644 --- a/addons/rose/tests/integration/components/rose/layout/main/header/title-test.js +++ b/addons/rose/tests/integration/components/rose/page-header/title-test.js @@ -3,28 +3,24 @@ import { setupRenderingTest } from 'ember-qunit'; import { render, click, find, findAll } from '@ember/test-helpers'; import hbs from 'htmlbars-inline-precompile'; -module('Integration | Component | rose/layout/main/header/title', function ( - hooks -) { +module('Integration | Component | rose/page-header/title', function (hooks) { setupRenderingTest(hooks); test('it renders', async function (assert) { - await render(hbs``); - assert.ok(find('.rose-layout-main-header-title')); + await render(hbs``); + assert.ok(find('.rose-page-header-title')); }); test('it renders with title', async function (assert) { - await render( - hbs`` - ); + await render(hbs``); assert.equal( - find('.rose-layout-main-header-title-text').textContent.trim(), + find('.rose-page-header-title-text').textContent.trim(), 'header title' ); }); test('it renders with title as dropdown', async function (assert) { - await render(hbs` + await render(hbs` Menu item Menu item @@ -32,7 +28,7 @@ module('Integration | Component | rose/layout/main/header/title', function ( Button menu item Button menu item - `); + `); assert.equal( find('.rose-header-dropdown-trigger').textContent.trim(), 'header title' @@ -42,7 +38,7 @@ module('Integration | Component | rose/layout/main/header/title', function ( }); test('it opens title dropdown on click', async function (assert) { - await render(hbs` + await render(hbs` Menu item Menu item @@ -50,7 +46,7 @@ module('Integration | Component | rose/layout/main/header/title', function ( Button menu item Button menu item - `); + `); await click('summary'); assert.ok(find('#dropdown').open); await click('#title'); diff --git a/addons/rose/tests/integration/components/rose/page-header/utilities-test.js b/addons/rose/tests/integration/components/rose/page-header/utilities-test.js new file mode 100644 index 000000000..5685c96d4 --- /dev/null +++ b/addons/rose/tests/integration/components/rose/page-header/utilities-test.js @@ -0,0 +1,38 @@ +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { render, find, findAll } from '@ember/test-helpers'; +import hbs from 'htmlbars-inline-precompile'; + +module('Integration | Component | rose/page-header/utilities', function ( + hooks +) { + setupRenderingTest(hooks); + + test('it renders', async function (assert) { + await render(hbs``); + assert.ok(find('.rose-page-header-utilities')); + }); + + test('it renders with attributes', async function (assert) { + await render(hbs``); + assert.ok(find('#utilities')); + }); + + test('it renders with content', async function (assert) { + await render( + hbs`Page header utilities` + ); + assert.equal( + find('.rose-page-header-utilities').textContent.trim(), + 'Page header utilities' + ); + }); + + test('it renders utility action buttons', async function (assert) { + await render(hbs` + + + `); + assert.equal(findAll('button').length, 2); + }); +});