diff --git a/addons/rose/addon/components/rose/message.js b/addons/rose/addon/components/rose/message.js new file mode 100644 index 000000000..89ac42ee5 --- /dev/null +++ b/addons/rose/addon/components/rose/message.js @@ -0,0 +1,7 @@ +import Component from '@ember/component'; +import layout from '../../templates/components/rose/message'; + +export default Component.extend({ + layout, + tagName: '', +}); diff --git a/addons/rose/addon/components/rose/message.stories.mdx b/addons/rose/addon/components/rose/message.stories.mdx new file mode 100644 index 000000000..2c3e062d9 --- /dev/null +++ b/addons/rose/addon/components/rose/message.stories.mdx @@ -0,0 +1,65 @@ +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'; + + + +# Message + +A message component containing a title, description, and nav links. Title can be configured with optional icon and subtitle. + +```html + + {{inline-svg "chevron-left"}} Go back + Need help? + +``` + + + {{ + template: hbs` + + {{inline-svg "chevron-left"}} Go back + Need help? + + `, + context: { + title: text('title', 'You are not authorized'), + subtitle: text('subtitle', 'Error 403'), + description: text('description', 'You must be granted permissions to view this data. Ask your administrator if you think you should have access.'), + icon: select( + 'icon', + { + 'alert-circle-outline': 'alert-circle-outline', + 'help-circle-outline': 'help-circle-outline', + 'disabled': 'disabled', + }, + 'disabled' + ), + }, + }} + + +Message can be configured without icons and navigation links. +```html + +``` + + {{ + template: hbs` + + `, + context: { + title: text('title', 'No logs received yet'), + description: text('description', 'Your logs will appear here when we start receiving them. If your server is currently outputting logs, check your configuration.'), + }, + }} + + +Message can be configured with a single left aligned link. +```html + + Add a namespace + +``` diff --git a/addons/rose/addon/components/rose/message/link.js b/addons/rose/addon/components/rose/message/link.js new file mode 100644 index 000000000..3291d255d --- /dev/null +++ b/addons/rose/addon/components/rose/message/link.js @@ -0,0 +1,7 @@ +import Component from '@ember/component'; +import layout from '../../../templates/components/rose/message/link'; + +export default Component.extend({ + layout, + tagName: '', +}); diff --git a/addons/rose/addon/styles/rose/components/_index.scss b/addons/rose/addon/styles/rose/components/_index.scss index f63f9bdf0..1c86e7a83 100644 --- a/addons/rose/addon/styles/rose/components/_index.scss +++ b/addons/rose/addon/styles/rose/components/_index.scss @@ -9,3 +9,4 @@ @import 'separator'; @import 'nav'; @import 'table'; +@import 'message'; diff --git a/addons/rose/addon/styles/rose/components/_message.scss b/addons/rose/addon/styles/rose/components/_message.scss new file mode 100644 index 000000000..c00e2e1fd --- /dev/null +++ b/addons/rose/addon/styles/rose/components/_message.scss @@ -0,0 +1,83 @@ +@use '../utilities/type'; +@use '../variables/sizing'; +@use '../variables/media'; + +.rose-message { + @include type.type(s, normal); + display: grid; + grid-template-areas: + 'title title title' + 'description description description' + 'left-link . right-link'; + grid-auto-columns: auto 1fr; + color: var(--ui-gray); + width: sizing.rems(m) * 16; //16 rems/320 px + + .rose-message-title { + @include type.type(m, semibold); + grid-area: title; + + .rose-message-title-text { + display: inline-block; + } + + .rose-message-icon { + display: inline; + svg { + vertical-align: top; + width: sizing.rems(m) * 2; // 40px + } + } + + .rose-message-subtitle { + @include type.type(xs, normal); + $lineHeight: 16 / 15; + line-height: $lineHeight; // 16px + vertical-align: bottom; + } + } + + .rose-message-description { + grid-area: description; + margin: sizing.rems(xs) 0; + } + + .rose-message-link { + @include type.type(xs, semibold); + text-decoration: none; + cursor: pointer; + --color: var(--ui-gray); + color: var(--color); + margin: sizing.rems(xs) 0; + + svg { + vertical-align: top; + width: sizing.rems(m); + height: sizing.rems(m); + } + + &.rose-message-link-left-align { + grid-area: left-link; + --color: var(--action); + } + + &.rose-message-link-right-align { + grid-area: right-link; + } + + &:hover { + --color: var(--action); + } + } +} + +@media (max-width: media.width(small)) { + .rose-message { + grid-template-areas: + 'title' + 'description' + 'right-link' + 'left-link'; + grid-auto-columns: auto 1fr; + } +} diff --git a/addons/rose/addon/templates/components/rose/message.hbs b/addons/rose/addon/templates/components/rose/message.hbs new file mode 100644 index 000000000..d15efb596 --- /dev/null +++ b/addons/rose/addon/templates/components/rose/message.hbs @@ -0,0 +1,25 @@ +
+ {{#if @title}} +
+ {{#if @icon}} +
{{inline-svg @icon}}
+ {{/if}} + +
+ {{@title}} + + {{#if @subtitle}} +
{{@subtitle}}
+ {{/if}} +
+
+ {{/if}} + + {{#if @description}} +
{{@description}}
+ {{/if}} + + {{yield (hash + link=(component 'rose/message/link') + )}} +
diff --git a/addons/rose/addon/templates/components/rose/message/link.hbs b/addons/rose/addon/templates/components/rose/message/link.hbs new file mode 100644 index 000000000..95337aaf2 --- /dev/null +++ b/addons/rose/addon/templates/components/rose/message/link.hbs @@ -0,0 +1,13 @@ +{{#if @leftAlign}} + + {{yield}} + +{{else}} + + {{yield}} + +{{/if}} diff --git a/addons/rose/app/components/rose/message.js b/addons/rose/app/components/rose/message.js new file mode 100644 index 000000000..914d08e41 --- /dev/null +++ b/addons/rose/app/components/rose/message.js @@ -0,0 +1 @@ +export { default } from 'rose/components/rose/message'; diff --git a/addons/rose/app/components/rose/message/link.js b/addons/rose/app/components/rose/message/link.js new file mode 100644 index 000000000..fe210dd3a --- /dev/null +++ b/addons/rose/app/components/rose/message/link.js @@ -0,0 +1 @@ +export { default } from 'rose/components/rose/message/link'; diff --git a/addons/rose/tests/dummy/app/templates/index.hbs b/addons/rose/tests/dummy/app/templates/index.hbs index bb8ae24db..bbcb98065 100644 --- a/addons/rose/tests/dummy/app/templates/index.hbs +++ b/addons/rose/tests/dummy/app/templates/index.hbs @@ -1,7 +1,22 @@ - - Level 1 - Level 2 - Level 3 - Level 4 - Level 5 - + + {{inline-svg "chevron-left"}} Go back + Need help? + +
+ + {{inline-svg "chevron-left"}} Go back + Need help? + +
+ + {{inline-svg "refresh-default"}} Try again + Need help? + +
+ + +
+ + Add a namespace + +
diff --git a/addons/rose/tests/dummy/app/templates/playground.hbs b/addons/rose/tests/dummy/app/templates/playground.hbs index 634ea800c..00b1c94cf 100644 --- a/addons/rose/tests/dummy/app/templates/playground.hbs +++ b/addons/rose/tests/dummy/app/templates/playground.hbs @@ -229,5 +229,13 @@ + + + Level 1 + Level 2 + Level 3 + Level 4 + Level 5 + diff --git a/addons/rose/tests/integration/components/rose/message-test.js b/addons/rose/tests/integration/components/rose/message-test.js new file mode 100644 index 000000000..497974080 --- /dev/null +++ b/addons/rose/tests/integration/components/rose/message-test.js @@ -0,0 +1,44 @@ +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/message', function (hooks) { + setupRenderingTest(hooks); + + test('it renders', async function (assert) { + await render(hbs``); + assert.ok(find('.rose-message')); + }); + + test('it renders with attributes', async function (assert) { + await render(hbs``); + assert.ok(find('#message')); + }); + + test('it renders with title', async function (assert) { + await render(hbs``); + assert.equal(find('.rose-message-title').textContent.trim(), 'Title'); + }); + + test('it renders with subtitle', async function (assert) { + await render(hbs``); + assert.equal(find('.rose-message-subtitle').textContent.trim(), 'Subtitle'); + }); + + test('it renders with description', async function (assert) { + await render(hbs``); + assert.equal( + find('.rose-message-description').textContent.trim(), + 'Description' + ); + }); + + test('it renders with link', async function (assert) { + await render(hbs` + + + `); + assert.equal(findAll('.rose-message-link').length, 2); + }); +}); diff --git a/addons/rose/tests/integration/components/rose/message/link-test.js b/addons/rose/tests/integration/components/rose/message/link-test.js new file mode 100644 index 000000000..b92f3004a --- /dev/null +++ b/addons/rose/tests/integration/components/rose/message/link-test.js @@ -0,0 +1,28 @@ +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { render, find } from '@ember/test-helpers'; +import hbs from 'htmlbars-inline-precompile'; + +module('Integration | Component | rose/message/link', function (hooks) { + setupRenderingTest(hooks); + + test('it renders', async function (assert) { + await render(hbs``); + assert.ok(find('.rose-message-link')); + assert.ok(find('.rose-message-link-right-align')); + }); + + test('it renders with content', async function (assert) { + await render(hbs`Link content`); + assert.equal(find('.rose-message-link').textContent.trim(), 'Link content'); + }); + + test('it renders left aligned', async function (assert) { + this.set('leftAlign', true); + await render(hbs``); + assert.ok(find('.rose-message-link-left-align')); + + this.set('leftAlign', false); + assert.notOk(find('.rose-message-link-left-align')); + }); +});