diff --git a/addons/rose/addon/components/rose/layout/body-content/index.hbs b/addons/rose/addon/components/rose/layout/body-content/index.hbs new file mode 100644 index 000000000..0e991d4a2 --- /dev/null +++ b/addons/rose/addon/components/rose/layout/body-content/index.hbs @@ -0,0 +1,15 @@ +{{! + Copyright (c) HashiCorp, Inc. + SPDX-License-Identifier: MPL-2.0 +}} + +
+ {{yield + (hash + Body=(component 'rose/anonymous' class='rose-layout-body-content-body') + Sidebar=(component + 'rose/anonymous' class='rose-layout-body-content-sidebar' + ) + ) + }} +
\ No newline at end of file diff --git a/addons/rose/addon/components/rose/layout/body-content/index.stories.mdx b/addons/rose/addon/components/rose/layout/body-content/index.stories.mdx new file mode 100644 index 000000000..61bdb18f0 --- /dev/null +++ b/addons/rose/addon/components/rose/layout/body-content/index.stories.mdx @@ -0,0 +1,28 @@ +import { Meta, Story, Preview } from '@storybook/addon-docs'; +import { hbs } from 'ember-cli-htmlbars'; + + + +# Layout|BodyContent + +A page layout/positioning component that allows two distinct sections to be configured: body and sidebar. + +```handlebars + + + + +``` + + + + {{ + template: hbs` + + Body + Sidebar + + `, + }} + + diff --git a/addons/rose/app/components/rose/layout/body-content.js b/addons/rose/app/components/rose/layout/body-content.js new file mode 100644 index 000000000..26e6aa668 --- /dev/null +++ b/addons/rose/app/components/rose/layout/body-content.js @@ -0,0 +1,6 @@ +/** + * Copyright (c) HashiCorp, Inc. + * SPDX-License-Identifier: MPL-2.0 + */ + +export { default } from 'rose/components/rose/layout/body-content'; diff --git a/addons/rose/app/styles/rose/components/layout/_body-content.scss b/addons/rose/app/styles/rose/components/layout/_body-content.scss new file mode 100644 index 000000000..0195535af --- /dev/null +++ b/addons/rose/app/styles/rose/components/layout/_body-content.scss @@ -0,0 +1,39 @@ +/** + * Copyright (c) HashiCorp, Inc. + * SPDX-License-Identifier: MPL-2.0 + */ + +@use '../../variables/media'; + +.rose-layout-body-content { + display: grid; + grid-template-areas: 'body body sidebar'; + grid-template-columns: 1fr 1fr 300px; + grid-template-rows: auto 1fr; + gap: 2rem; + + &-body { + grid-area: body; + } + + &-sidebar { + grid-area: sidebar; + } +} + +@media (max-width: media.width(xlarge)) { + .rose-layout-body-content { + grid-template-areas: + 'body' + 'sidebar'; + grid-template-columns: auto; + + &-body { + min-width: 0; + } + + &-sidebar { + max-width: 300px; + } + } +} diff --git a/addons/rose/app/styles/rose/components/layout/_index.scss b/addons/rose/app/styles/rose/components/layout/_index.scss index 90850feb2..da27bc743 100644 --- a/addons/rose/app/styles/rose/components/layout/_index.scss +++ b/addons/rose/app/styles/rose/components/layout/_index.scss @@ -9,6 +9,7 @@ @import 'sidebar'; @import 'page'; @import 'centered'; +@import 'body-content'; // TODO: this is prescriptive and can be removed if it becomes a problem, // but used here reflects the fact that the "main" element, of which there diff --git a/addons/rose/tests/integration/components/rose/layout/body-content-test.js b/addons/rose/tests/integration/components/rose/layout/body-content-test.js new file mode 100644 index 000000000..5a704bfb0 --- /dev/null +++ b/addons/rose/tests/integration/components/rose/layout/body-content-test.js @@ -0,0 +1,39 @@ +/** + * Copyright (c) HashiCorp, Inc. + * SPDX-License-Identifier: MPL-2.0 + */ + +import { module, test } from 'qunit'; +import { setupRenderingTest } from 'ember-qunit'; +import { render } from '@ember/test-helpers'; +import { hbs } from 'ember-cli-htmlbars'; + +module('Integration | Component | rose/layout/body-content', function (hooks) { + setupRenderingTest(hooks); + + test('it renders', async function (assert) { + await render(hbs``); + + assert.dom('div').exists(); + assert.dom('.rose-layout-body-content').isVisible(); + }); + + test('it renders with attributes', async function (assert) { + await render(hbs``); + + assert.dom('#body-content').isVisible(); + }); + + test('it renders with content', async function (assert) { + await render(hbs` +