Merge branch 'develop' into ICU-179-tab-component

This commit is contained in:
Randall Morey authored and GitHub committed 2020-06-04 13:17:21 -04:00
commit 591a476f5d
35 files changed
+593 -258

No files matched your search

@@ -0,0 +1,11 @@
import Component from '@ember/component';
import layout from '../../../templates/components/rose/nav/sidebar';
import ComponentAutoId from '../../../mixins/component-auto-id';
/**
* A simple navigation component intended for the sidebar layout region.
*/
export default Component.extend(ComponentAutoId, {
layout,
tagName: '',
});
@@ -0,0 +1,34 @@
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';
<Meta title="Rose|Nav/Sidebar" component="Nav/Sidebar" />
# Sidebar Navigation
A simple navigation component intended for use in the sidebar layout region.
<Preview>
<Story name="Basic Sidebar Nav" height="8rem">{{
template: hbs`
<Rose::Nav::Sidebar @title={{title}} as |nav|>
<nav.link @route="index" class="active">Item Name</nav.link>
<nav.link @route="index">Item Name</nav.link>
</Rose::Nav::Sidebar>
`,
context: {
title: text('title', 'Title'),
},
}}</Story>
</Preview>
_Note_: do not assign the `active` class directly. This is done by the link
component automatically. We use it in this story for illustrative purposes.
```htmlbars
<Rose::Nav::Sidebar @title="Title" as |nav|>
<nav.link @route="index">Item Name</nav.link>
<nav.link @route="about">Item Name</nav.link>
</Rose::Nav::Sidebar>
```
@@ -20,8 +20,9 @@ export default Component.extend({
get icon() {
let icon = 'info-circle-fill';
switch (this.style) {
case 'failure':
switch(this.style) {
case 'error':
icon = 'cancel-square-fill';
break;
case 'success':
@@ -8,7 +8,7 @@ import { text, boolean, select } from '@storybook/addon-knobs';
# Notification
Notifications come in four semantic styles: `info` (default), `success`,
`warning`, and `failure`. Heading text is required. Additional block content
`warning`, and `error`. Heading text is required. Additional block content
is optional.
Notifications may be made dismissible by passing a `@dismiss` function into
@@ -69,7 +69,7 @@ handler takes appropriate action and hides the notification.
Careful now.
</Rose::Notification>
<Rose::Notification
@style="failure"
@style="error"
@heading="Error"
@dismiss={{dismiss}}
@dismissText="Dismiss"
@@ -5,3 +5,4 @@
@import 'notification';
@import 'card';
@import 'tab';
@import 'nav';
@@ -82,7 +82,7 @@
color: var(--header-color);
}
&.is-failure {
&.is-error {
--icon-color: var(--failure);
--header-color: var(--failure);
--border-color: var(--failure-subtler-1);
@@ -24,8 +24,13 @@
}
&:hover {
$s: sizing.rems(s); // 12
$xs: sizing.rems(xs); // 8
$xxs: sizing.rems(xxs); // 4
border-color: var(--ui-gray);
background-color: var(--ui-gray-subtler-5);
box-shadow: 0 $xs $s rgba(var(--stark-components), var(--opacity-3)),
0 $xxs $xxs rgba(var(--stark-components), var(--opacity-4));
}
&:active {
@@ -2,7 +2,7 @@
@use '../../utilities/type';
.rose-form-input {
margin-bottom: sizing.rems(l);
margin-bottom: sizing.rems(m);
.rose-form-input-label {
@include type.type(s, semibold);
@@ -2,7 +2,7 @@
@use '../../utilities/type';
.rose-form-select {
margin-bottom: sizing.rems(l);
margin-bottom: sizing.rems(m);
.rose-form-select-label {
@include type.type(s, semibold);
@@ -20,6 +20,7 @@
.rose-header-brand-text {
@include type.type(m, normal);
margin: 0;
margin-left: sizing.rems(s);
white-space: nowrap;
position: absolute;
top: -1000px;
@@ -1,3 +1,4 @@
@use '../../variables/sizing';
@use '../../variables/media';
@import 'tabs';
@@ -8,7 +9,7 @@
'header header header header'
'sidebar main main main';
// Define static grid column for sidebar
grid-template-columns: 12rem auto 1fr;
grid-template-columns: 16rem auto 1fr;
grid-template-rows: auto 1fr;
height: 100vh;
}
@@ -23,6 +24,7 @@
.rose-layout-sidebar {
grid-area: sidebar;
border-right: sizing.rems(xxxxs) solid var(--ui-border-subtler-1);
}
@media (max-width: media.width(small)) {
@@ -0,0 +1 @@
@import "sidebar";
@@ -0,0 +1,40 @@
@use '../../variables/sizing';
@use '../../utilities/type';
.rose-nav-sidebar {
$threePX: sizing.rems(xxxs) + sizing.rems(xxxxs);
.rose-nav-title {
@include type.type(xs, semibold);
display: block;
color: var(--ui-gray);
text-transform: uppercase;
$lineHeight: 20 / 12;
line-height: $lineHeight;
padding: 0 sizing.rems(m);
margin-bottom: $threePX;
border-bottom: sizing.rems(xxxxs) solid var(--ui-gray-subtler-2);
}
.rose-nav-link {
@include type.type(s);
display: block;
color: var(--stark);
$lineHeight: 36 / 14;
line-height: $lineHeight;
text-decoration: none;
padding: 0 sizing.rems(m);
border-right: $threePX solid transparent;
&.active {
color: var(--action);
border-color: currentColor;
}
&:hover {
text-decoration: underline;
color: var(--action);
background-color: var(--action-subtler-1h);
}
}
}
@@ -56,6 +56,7 @@
--success-starker-1: #{color(green, 800)};
--action-subtler-2: #{color(blue, 010)};
--action-subtler-1h: #{color(blue, 050)};
--action-subtler-1: #{color(blue, 100)};
--action: #{color(blue)};
--action-starker-1: #{color(blue, 700)};
@@ -115,6 +116,7 @@
--success-starker-1: #{color(green, 200)};
--action-subtler-2: #{color(blue, 900)};
--action-subtler-1h: #{color(blue, 800)};
--action-subtler-1: #{color(blue, 800)};
--action: #{color(blue)};
--action-starker-1: #{color(blue, 300)};
@@ -0,0 +1,17 @@
<nav
...attributes
class="rose-nav-sidebar"
id={{this.id}}
aria-labelledby={{if @title (concat "title-" this.id)}}>
{{#if @title}}
<span class="rose-nav-title" id="title-{{this.id}}">
{{@title}}
</span>
{{/if}}
{{yield (hash
link=(component "link-to" class="rose-nav-link")
)}}
</nav>
@@ -0,0 +1 @@
export { default } from 'rose/components/rose/nav/sidebar';
+184 -172
View File
@@ -1,190 +1,202 @@
<Rose::Header as |header|>
<Rose::Layout::Page as |page|>
<page.header>
<Rose::Header as |header|>
<header.brand @logo="logo" @text="Product Name" />
<header.brand @logo="logo" @text="Product Name" />
<header.nav as |nav|>
<nav.dropdown @text="org-name" as |dropdown|>
<dropdown.link @route="index">Menu item</dropdown.link>
<dropdown.link @route="about">Menu item</dropdown.link>
<dropdown.button>Button menu item</dropdown.button>
</nav.dropdown>
<nav.link @route="index">Section</nav.link>
<nav.link @route="about">Section</nav.link>
</header.nav>
<header.nav as |nav|>
<nav.dropdown @text="org-name" as |dropdown|>
<dropdown.link @route="index">Menu item</dropdown.link>
<dropdown.link @route="about">Menu item</dropdown.link>
<dropdown.button>Button menu item</dropdown.button>
</nav.dropdown>
<nav.link @route="index">Section</nav.link>
<nav.link @route="about">Section</nav.link>
</header.nav>
<header.utilities as |utilities|>
<utilities.dropdown
@text="user@example.net"
@iconOnly={{true}}
@icon="user-square-fill" as |dropdown|
<header.utilities as |utilities|>
<utilities.dropdown
@text="user@example.net"
@iconOnly={{true}}
@icon="user-square-fill" as |dropdown|
>
<dropdown.link @route="index">Menu item</dropdown.link>
<dropdown.link @route="about">Menu item</dropdown.link>
<dropdown.button>Button menu item</dropdown.button>
</utilities.dropdown>
</header.utilities>
</Rose::Header>
</page.header>
<page.sidebar>
<Rose::Nav::Sidebar @title="Title" as |nav|>
<nav.link @route="index">Item Name</nav.link>
<nav.link @route="about">Item Name</nav.link>
<nav.link @route="about">Item Name</nav.link>
<nav.link @route="about">Item Name</nav.link>
</Rose::Nav::Sidebar>
</page.sidebar>
<page.main>
Dummy app index template
<Rose::Notification
@style="error"
@heading="Error"
@dismiss={{this.actionHandler}}
@dismissText="Dismiss"
>
<dropdown.link @route="index">Menu item</dropdown.link>
<dropdown.link @route="about">Menu item</dropdown.link>
<dropdown.button>Button menu item</dropdown.button>
</utilities.dropdown>
</header.utilities>
An error occurred.
</Rose::Notification>
</Rose::Header>
<h2>Icon</h2>
<Rose::Icon @name="alert-circle-fill" />
<Rose::Icon @name="alert-circle-fill" @size="medium" />
<Rose::Icon @name="alert-circle-fill" @size="small" />
Dummy app index template
<h2>Button</h2>
<Rose::Button @style="primary">Primary</Rose::Button>
<br>
<Rose::Button @style="primary" @disabled={{true}}>Primary</Rose::Button>
<br>
<Rose::Notification
@style="failure"
@heading="Error"
@dismiss={{this.actionHandler}}
@dismissText="Dismiss"
>
An error occurred.
</Rose::Notification>
<Rose::Button @style="secondary">Secondary</Rose::Button>
<br>
<Rose::Button @style="secondary" @disabled={{true}}>Secondary</Rose::Button>
<br>
<h2>Icon</h2>
<Rose::Icon @name="alert-circle-fill" />
<Rose::Icon @name="alert-circle-fill" @size="medium" />
<Rose::Icon @name="alert-circle-fill" @size="small" />
<h2>Form</h2>
<Rose::Form
@onSubmit={{this.actionHandler}}
@cancel={{this.actionHandler}}
@disabled={{false}}
as |form|
>
<h2>Button</h2>
<Rose::Button @style="primary">Primary</Rose::Button>
<br>
<Rose::Button @style="primary" @disabled={{true}}>Primary</Rose::Button>
<br>
<h3>Inputs</h3>
<form.input
@label="Label"
@value="Read only"
readonly={{true}}
/>
<form.input
@label="Label"
@helperText="Helper text"
@value="Text"
/>
<form.input
@label="Label"
@helperText="Helper text"
@value="Text"
@error={{true}}
/>
<form.input
@label="Label"
@helperText="Helper text"
@value="Text"
disabled={{true}}
/>
<Rose::Button @style="secondary">Secondary</Rose::Button>
<br>
<Rose::Button @style="secondary" @disabled={{true}}>Secondary</Rose::Button>
<br>
<h3>Textareas</h3>
<form.textarea
@label="Label"
@value="Read only"
readonly={{true}}
/>
<form.textarea
@label="Label"
@helperText="Helper text"
@value="Text"
/>
<form.textarea
@label="Label"
@helperText="Helper text"
@value="Text"
@error={{true}}
/>
<form.textarea
@label="Label"
@helperText="Helper text"
@value="Text"
disabled={{true}}
/>
<h2>Form</h2>
<Rose::Form
@onSubmit={{this.actionHandler}}
@cancel={{this.actionHandler}}
@disabled={{false}}
as |form|
>
<h3>Selects</h3>
<form.select
@label="Label"
@helperText="Helper text"
@onChange={{fn this.actionHandler}}
as |field|
>
<field.field as |select|>
<select.option>Choose an option</select.option>
<select.option @value="value-1">Value 1</select.option>
<select.option @value="value-2">Value 2</select.option>
<select.option @value="value-3">Value 3</select.option>
</field.field>
</form.select>
<form.select
<h3>Inputs</h3>
<form.input
@label="Label"
@value="Read only"
readonly={{true}}
/>
<form.input
@label="Label"
@helperText="Helper text"
@value="Text"
/>
<form.input
@label="Label"
@helperText="Helper text"
@value="Text"
@error={{true}}
/>
<form.input
@label="Label"
@helperText="Helper text"
@value="Text"
disabled={{true}}
/>
<h3>Textareas</h3>
<form.textarea
@label="Label"
@value="Read only"
readonly={{true}}
/>
<form.textarea
@label="Label"
@helperText="Helper text"
@value="Text"
/>
<form.textarea
@label="Label"
@helperText="Helper text"
@value="Text"
@error={{true}}
/>
<form.textarea
@label="Label"
@helperText="Helper text"
@value="Text"
disabled={{true}}
/>
<h3>Selects</h3>
<form.select
@label="Label"
@helperText="Helper text"
@onChange={{fn this.actionHandler}}
as |field|
>
<field.field as |select|>
<select.option>Choose an option</select.option>
<select.option @value="value-1">Value 1</select.option>
<select.option @value="value-2">Value 2</select.option>
<select.option @value="value-3">Value 3</select.option>
</field.field>
</form.select>
<form.select
@label="Label"
@helperText="Helper text"
@onChange={{fn this.actionHandler}}
as |field|
>
<field.field as |select|>
<select.option>Choose an option</select.option>
</field.field>
</form.select>
@label="Label"
@helperText="Helper text"
@onChange={{fn this.actionHandler}}
as |field|
>
<field.field as |select|>
<select.option>Choose an option</select.option>
</field.field>
</form.select>
<h3>Radio Group</h3>
<form.radioGroup @name="color" @selectedValue={{this.color}} as |radioGroup|>
<radioGroup.radio
@label="Red"
@value="red"
/>
<radioGroup.radio
@label="Green"
@value="green"
/>
<radioGroup.radio
@label="Blue"
@value="blue"
@disabled={{true}}
/>
</form.radioGroup>
<h3>Radio Group</h3>
<form.radioGroup @name="color" @selectedValue={{this.color}} as |radioGroup|>
<radioGroup.radio
@label="Red"
@value="red"
/>
<radioGroup.radio
@label="Green"
@value="green"
/>
<radioGroup.radio
@label="Blue"
@value="blue"
@disabled={{true}}
/>
</form.radioGroup>
<h3>Checkboxes</h3>
<form.checkbox
@label="Label"
/>
<form.checkbox
@error={{true}}
@label="Error"
/>
<form.checkbox
@checked={{true}}
@label="Checked"
/>
<form.checkbox
@label="Disabled"
disabled={{true}}
/>
<form.checkbox
@checked={{true}}
@label="Disabled + Checked"
disabled={{true}}
/>
<h3>Checkboxes</h3>
<form.checkbox
@label="Label"
/>
<form.checkbox
@error={{true}}
@label="Error"
/>
<form.checkbox
@checked={{true}}
@label="Checked"
/>
<form.checkbox
@label="Disabled"
disabled={{true}}
/>
<form.checkbox
@checked={{true}}
@label="Disabled + Checked"
disabled={{true}}
/>
<form.actions
@submitText="Save"
@cancelText="Cancel" />
</Rose::Form>
<form.actions
@submitText="Save"
@cancelText="Cancel" />
</Rose::Form>
<Rose::Card::Link @title="I'm a card" />
<Rose::Card::Link @title="I'm a card" @description="I'm a description" />
<Rose::Card::Link @title="I'm a card" @description="I'm a description" @subtitle="I'm a subtitle"/>
<Rose::Layout::Tabs>
<Rose::Tab @title="Text" @badge="3" @icon="info-circle-outline" />
</Rose::Layout::Tabs>
<Rose::Card::Link @title="I'm a card" />
<Rose::Card::Link @title="I'm a card" @description="I'm a description" />
<Rose::Card::Link @title="I'm a card" @description="I'm a description" @subtitle="I'm a subtitle"/>
</page.main>
</Rose::Layout::Page>
@@ -0,0 +1,33 @@
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/nav/sidebar', function(hooks) {
setupRenderingTest(hooks);
test('it renders', async function(assert) {
assert.expect(2)
await render(hbs`
<Rose::Nav::Sidebar @title="Title" as |nav|>
<nav.link @route="index">Item Name</nav.link>
</Rose::Nav::Sidebar>
`);
assert.equal(find('.rose-nav-title').textContent.trim(), 'Title');
assert.equal(find('.rose-nav-link').textContent.trim(), 'Item Name');
});
test('it associates title with nav via aria-labelledby', async function (assert) {
assert.expect(2)
await render(hbs`
<Rose::Nav::Sidebar @title="Title" as |nav|>
<nav.link @route="index">Item Name</nav.link>
</Rose::Nav::Sidebar>
`);
const el = find('.rose-nav-sidebar');
const id = el.id;
const titleId = `title-${id}`;
assert.equal(find('.rose-nav-title').id, titleId);
assert.equal(el.getAttribute('aria-labelledby').trim(), titleId);
});
});
+15 -29
View File
@@ -1,44 +1,30 @@
<form
...attributes
novalidate
method="post"
{{on "submit" @submit}}>
<Rose::Form
@onSubmit={{@submit}}
@cancel={{@cancel}}
@disabled={{@model.isSaving}}
as |form|
>
<Rose::Form::Input
<form.input
name="name"
@type="name"
@value={{@model.name}}
@label={{t "form.label.name"}}
@error={{false}}
disabled={{@model.isSaving}}
readonly={{false}}
/>
readonly={{false}} />
<Rose::Form::Textarea
<form.textarea
name="description"
@type="description"
@value={{@model.description}}
@label={{t "form.label.description"}}
@error={{false}}
disabled={{@model.isSaving}}
readonly={{false}}
/>
readonly={{false}} />
<section class="form-actions">
<Rose::Button
@disabled={{@model.cannotSave}}
@submit={{true}}
@style="primary"
>
{{t 'actions.save'}}
</Rose::Button>
<form.actions
@disabled={{if @model.cannotSave @model.cannotSave}}
@submitText={{t "actions.save"}}
@cancelText={{t "actions.cancel"}} />
<Rose::Button
@disabled={{@model.cannotSave}}
@style="secondary"
{{on "click" @cancel}}
>
{{t 'actions.cancel'}}
</Rose::Button>
</section>
</form>
</Rose::Form>
@@ -1,9 +1,3 @@
import Route from '@ember/routing/route';
import { action } from '@ember/object';
export default class OrgsOrgProjectsIndexRoute extends Route {
@action
new() {
this.transitionTo('orgs.org.projects.new');
}
}
export default class OrgsOrgProjectsIndexRoute extends Route {}
+10 -5
View File
@@ -1,7 +1,12 @@
import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';
import { action } from '@ember/object';
export default class OrgsOrgProjectsNewRoute extends Route {
// =services
@service notify;
// =methods
/**
@@ -31,15 +36,15 @@ export default class OrgsOrgProjectsNewRoute extends Route {
* @param {Event} e
*/
@action
async save(project, e) {
// Prevent default behavior, since this was trigger from a form submission.
e.preventDefault();
async save(project) {
try {
await project.save();
this.transitionTo('orgs.org.projects.project', project);
// TODO: replace with translated strings
this.notify.success('Project created.');
} catch (e) {
// TODO: error handling
throw e;
// TODO: replace with translated strings
this.notify.error('Project could not be created.', {closeAfter: null});
}
}
}
@@ -6,6 +6,7 @@ export default class OrgsOrgProjectsProjectRoute extends Route {
// =services
@service scope;
@service notify;
// =methods
@@ -44,14 +45,14 @@ export default class OrgsOrgProjectsProjectRoute extends Route {
* @param {Event} e
*/
@action
async save(project, e) {
// Prevent default behavior, since this was trigger from a form submission.
e.preventDefault();
async save(project) {
try {
await project.save();
// TODO: replace with translated strings
this.notify.success('Save succeeded.');
} catch (e) {
// TODO: error handling
throw e;
// TODO: replace with translated strings
this.notify.error('An error occurred.', {closeAfter: null});
}
}
@@ -64,9 +65,11 @@ export default class OrgsOrgProjectsProjectRoute extends Route {
try {
await project.destroyRecord();
this.transitionTo('orgs.org.projects');
// TODO: replace with translated strings
this.notify.success('Deleted project succesfully.');
} catch (e) {
// TODO: error handling
throw e;
// TODO: replace with translated strings
this.notify.error('An error occurred.', {closeAfter: null});
}
}
}
+89
View File
@@ -0,0 +1,89 @@
/**
* This file is essentially a rip of the default ember notify styles, with some
* minor tweaks for positioning.
*/
@-webkit-keyframes "ember-notify-show" {
from {
left: -310px;
}
to {
left: 0;
}
}
@keyframes "ember-notify-show" {
from {
left: -310px;
}
to {
left: 0;
}
}
@-webkit-keyframes "ember-notify-hide" {
from {
left: 0;
}
to {
left: -310px;
}
}
@keyframes "ember-notify-hide" {
from {
left: 0;
}
to {
left: -310px;
}
}
.ember-notify-cn {
position: fixed;
z-index: 5000;
bottom: 0px;
left: 0px;
}
.ember-notify {
display: block;
margin: 10px;
position: relative;
width: 300px;
box-sizing: border-box;
//border: 1px solid #ccc;
//padding: 10px;
.close {
float: right;
cursor: pointer;
}
}
.ember-notify-show {
-webkit-animation-duration: 500ms;
animation-duration: 500ms;
-webkit-animation-name: ember-notify-show;
animation-name: ember-notify-show;
-webkit-animation-timing-function: cubic-bezier(0.175, 0.885, 0.32, 1.275);
animation-timing-function: cubic-bezier(0.175, 0.885, 0.32, 1.275);
}
.ember-notify-hide {
-webkit-animation-duration: 250ms;
animation-duration: 250ms;
-webkit-animation-name: ember-notify-hide;
animation-name: ember-notify-hide;
-webkit-animation-timing-function: cubic-bezier(0.6, -0.28, 0.735, 0.045);
animation-timing-function: cubic-bezier(0.6, -0.28, 0.735, 0.045);
&:hover {
-webkit-animation-play-state: paused;
-moz-animation-play-state: paused;
-o-animation-play-state: paused;
animation-play-state: paused;
}
}
@media only screen and (max-width: 680px) {
.ember-notify-cn {
width: 100%;
padding-left: 20px;
box-sizing: border-box;
}
.ember-notify {
width: 100%;
float: right;
}
}
+22 -18
View File
@@ -1,7 +1,26 @@
@use 'rose/variables/sizing';
@import 'rose';
@import 'notify';
.rose-nav-sidebar {
margin-top: sizing.rems(xxl);
}
.rose-form {
width: 66%;
.rose-form-input {
width: 100%;
.rose-form-input-field {
width: 100%;
}
}
}
.projects-overview {
margin: 0 10px;
margin: sizing.rems(l);
.projects {
display: flex;
@@ -17,25 +36,10 @@
}
}
.project-new-link {
cursor: pointer;
text-decoration: none;
padding: 10px;
color: #ffffff;
text-shadow: 0px 1px 1px rgba(0, 0, 0, 0.25);
background: #1563ff;
border: 1px solid #082766;
box-sizing: border-box;
box-shadow: 0px 4px 4px rgba(0, 0, 0, 0.25);
border-radius: 2px;
position: relative;
float: right;
top: -50px;
}
.project-overview,
.project-new {
margin: 0 10px;
margin: sizing.rems(l);
.breadcrumbs,
.breadcrumbs a {
color: #6f7682;
+42 -3
View File
@@ -1,14 +1,53 @@
<HeadLayout />
{{title (app-name)}}
<Rose::Layout::Page as |page|>
<page.header>
<Rose::Header as |header|>
<header.brand @logo="logo" @text={{app-name}} />
<header.brand @logo="logo-hashi" @text={{app-name}} />
<header.nav as |nav|>
<nav.dropdown @text={{t 'dev.default-org'}} as |dropdown|>
<dropdown.link @route="index">{{t 'dev.menu-item'}}</dropdown.link>
<dropdown.link @route="orgs">{{t 'dev.menu-item'}}</dropdown.link>
<dropdown.button>{{t 'dev.button-menu-item'}}</dropdown.button>
</nav.dropdown>
<nav.link @route="index">{{t 'dev.section'}}</nav.link>
<nav.link @route="index">{{t 'dev.section'}}</nav.link>
</header.nav>
<header.utilities as |utilities|>
<utilities.dropdown
@text="user@example.net"
@iconOnly={{true}}
@icon="user-square-fill" as |dropdown|
>
<dropdown.link @route="index">{{t 'dev.menu-item'}}</dropdown.link>
<dropdown.button>{{t 'dev.button-menu-item'}}</dropdown.button>
</utilities.dropdown>
</header.utilities>
</Rose::Header>
</page.header>
<page.main>
{{title (app-name)}}
{{outlet}}
</page.main>
<page.sidebar />
<page.sidebar>
<Rose::Nav::Sidebar @title={{t 'dev.title'}} as |nav|>
<nav.link @route="orgs" class="active">{{t 'dev.item-name'}}</nav.link>
<nav.link @route="index">{{t 'dev.item-name'}}</nav.link>
</Rose::Nav::Sidebar>
</page.sidebar>
</Rose::Layout::Page>
<EmberNotify @closeAfter={{4000}} as |message close|>
<Rose::Notification
@style={{message.type}}
@heading={{t (concat 'states.' message.type)}}
@dismiss={{close}}
@dismissText={{t 'actions.dismiss'}}
>
{{message.text}}
</Rose::Notification>
</EmberNotify>
@@ -1 +1,3 @@
{{title (t "resources.projects")}}
{{outlet}}
@@ -1,13 +1,11 @@
<div class="projects-overview">
<h2>{{t "resources.projects"}}</h2>
<Rose::Button
class="project-new-link"
@style="primary"
@iconLeft="plus-plain"
{{on "click" (route-action "new")}}
>
{{t 'titles.new'}}
</Rose::Button>
<LinkTo @route="orgs.org.projects.new">
<Rose::Icon @name="plus-circle-outline" @size="medium" />
{{t "titles.new"}}
</LinkTo>
<ul class="projects">
{{#each @model as |project|}}
@@ -1,3 +1,5 @@
{{title (t "titles.new")}}
<div class="project-new">
<div class="breadcrumbs">
<LinkTo @route='orgs.org.projects'>{{t "resources.projects"}}</LinkTo>
@@ -1,3 +1,5 @@
{{title @model.name}}
<div class="project-overview">
<div class="breadcrumbs">
<LinkTo @route='orgs.org.projects'>{{t "resources.projects"}}</LinkTo>
+1 -1
View File
@@ -41,7 +41,7 @@ module.exports = function (environment) {
'frame-src': ["'self'"],
'font-src': ["'self'"],
'connect-src': ["'self'"],
'img-src': ["'self'"],
'img-src': ["'self'", "data:"],
'style-src': ["'self'"],
'media-src': ["'self'"],
'manifest-src': ["'self'"],
+3
View File
@@ -15,6 +15,9 @@ module.exports = function (defaults) {
onlyIncluded: true,
extension: 'scss',
},
emberNotify: {
importCss: false,
},
});
// Use `app.import` to add additional libraries to the generated
+2
View File
@@ -60,6 +60,8 @@
"ember-intl": "^5.1.1",
"ember-load-initializers": "^2.1.1",
"ember-maybe-import-regenerator": "^0.1.6",
"ember-modifier": "^1.0.3",
"ember-notify": "^6.0.0",
"ember-page-title": "^5.2.1",
"ember-qunit": "^4.6.0",
"ember-resolver": "^7.0.0",
+24
View File
@@ -0,0 +1,24 @@
<svg
width="30"
height="30"
viewBox="0 0 30 30"
fill="none"
xmlns="http://www.w3.org/2000/svg">
<g id="logomark">
<path
d="M0 7.19579L11.4553 0.58728V5.55192L4.30398 9.68052V25.5537L0 23.069V7.19579Z"
fill="currentColor">
</path>
<path
d="M16.0285 0.58728V13.2291H11.4553V8.51084L7.15165 10.9956V27.1919L11.4553 29.6829V17.0771H16.0285V21.7641L20.3321 19.2788V3.07229L16.0285 0.58728Z"
fill="currentColor">
</path>
<path
d="M27.4838 23.0789L16.0285 29.6875V24.7228L23.1798 20.5939V4.72074L27.4838 7.20576V23.0789Z"
fill="currentColor">
</path>
</g>
</svg>

After

Width:  |  Height:  |  Size: 633 B

+13
View File
@@ -1,12 +1,25 @@
actions:
cancel: Cancel
delete: Delete
dismiss: Dismiss
save: Save
resources:
projects: Projects
titles:
new: New
states:
info: Info
success: Success
warning: Warning
error: Error
form:
label:
name: Name
description: Description
dev:
default-org: Default Org
menu-item: Menu item
button-menu-item: Button menu item
section: Section
title: Title
item-name: Item Name
+8
View File
@@ -7815,6 +7815,14 @@ ember-modifier@^1.0.3:
ember-cli-string-utils "^1.1.0"
ember-modifier-manager-polyfill "^1.2.0"
ember-notify@^6.0.0:
version "6.0.0"
resolved "https://registry.yarnpkg.com/ember-notify/-/ember-notify-6.0.0.tgz#f92978e3452934f7c9b70d76ad2ec62bf072495a"
integrity sha512-2ewX5xwkGyZtkRRlgT/Tam5PaxGy78IoXltwt4s8roEam1esXNHfafzycvJwcuX7Hgrwr7LlTpmKP+81vWT3QQ==
dependencies:
ember-cli-babel "^7.7.3"
ember-cli-htmlbars "^3.0.1"
ember-page-title@^5.2.1:
version "5.2.1"
resolved "https://registry.yarnpkg.com/ember-page-title/-/ember-page-title-5.2.1.tgz#12261e010bec96af6200cd132fe4068e717ccbec"