-
-
Notifications
You must be signed in to change notification settings - Fork 31
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(design): create
DaffBreadcrumbComponent
(#3028)
- Loading branch information
Showing
20 changed files
with
387 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,52 @@ | ||
# Breadcrumb | ||
Breadcrumbs are a secondary navigation that displays a user's location within a website or application. | ||
|
||
## Overview | ||
Breadcrumbs are a visual representation of the site's navigational hierarchy. They indicate the current page's location and allows users to easily move up to a parent level. It's required for breadcrumbs to be used with the native HTML `<ol>` element, and for each item to be an `<li>`. This offers additional context for assistive technology. | ||
|
||
## Basic Breadcrumb | ||
<design-land-example-viewer-container example="basic-breadcrumb"></design-land-example-viewer-container> | ||
|
||
## Usage | ||
|
||
## Within a standalone component | ||
To use breadcrumb in a standalone component, import it directly into your custom component: | ||
|
||
```ts | ||
@Component({ | ||
selector: 'custom-component', | ||
templateUrl: './custom-component.component.html', | ||
standalone: true, | ||
imports: [ | ||
DAFF_BREADCRUMB_COMPONENTS, | ||
], | ||
}) | ||
export class CustomComponent {} | ||
``` | ||
|
||
## Within a module (deprecated) | ||
To use breadcrumb in a module, import `DaffBreadcrumbModule` into your custom module: | ||
|
||
```ts | ||
import { NgModule } from '@angular/core'; | ||
|
||
import { DaffBreadcrumbModule } from '@daffodil/design/breadcrumb'; | ||
|
||
@NgModule({ | ||
declarations: [ | ||
CustomComponent, | ||
], | ||
exports: [ | ||
CustomComponent, | ||
], | ||
imports: [ | ||
DaffBreadcrumbModule, | ||
], | ||
}) | ||
export class CustomComponentModule { } | ||
``` | ||
|
||
> This method is deprecated. It's recommended to update all custom components to standalone. | ||
## Accessibility | ||
Breadcrumbs should be wrapped in a native HTML `<nav>` element so that assistive technologies can present the breadcrumbs as a navigational element on the page. Use `aria-label="Breadcrumbs"` on the `nav` element to provide more context. `aria-current="page"` is added to a breadcrumb item when it's the current page, and `aria-current="false"` on all other items. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
{ | ||
"$schema": "../../../../node_modules/ng-packagr/ng-entrypoint.schema.json", | ||
"lib": { | ||
"entryFile": "src/index.ts", | ||
"styleIncludePaths": ["../../scss"] | ||
} | ||
} |
8 changes: 8 additions & 0 deletions
8
libs/design/breadcrumb/examples/src/basic-breadcrumb/basic-breadcrumb.component.html
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
<nav aria-label="Breadcrumb"> | ||
<ol daff-breadcrumb> | ||
<li daffBreadcrumbItem> | ||
<a routerLink="/link">Link</a> | ||
</li> | ||
<li daffBreadcrumbItem [active]="true">Active Link</li> | ||
</ol> | ||
</nav> |
18 changes: 18 additions & 0 deletions
18
libs/design/breadcrumb/examples/src/basic-breadcrumb/basic-breadcrumb.component.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
import { | ||
ChangeDetectionStrategy, | ||
Component, | ||
} from '@angular/core'; | ||
|
||
import { DAFF_BREADCRUMB_COMPONENTS } from '@daffodil/design/breadcrumb'; | ||
|
||
@Component({ | ||
// eslint-disable-next-line @angular-eslint/component-selector | ||
selector: 'basic-breadcrumb', | ||
templateUrl: './basic-breadcrumb.component.html', | ||
changeDetection: ChangeDetectionStrategy.OnPush, | ||
standalone: true, | ||
imports: [ | ||
DAFF_BREADCRUMB_COMPONENTS, | ||
], | ||
}) | ||
export class BasicBreadcrumbComponent {} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
export * from './public_api'; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
import { BasicBreadcrumbComponent } from './basic-breadcrumb/basic-breadcrumb.component'; | ||
|
||
export const BREADCRUMB_EXAMPLES = [ | ||
BasicBreadcrumbComponent, | ||
]; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
{ | ||
"$schema": "../../../node_modules/ng-packagr/ng-entrypoint.schema.json", | ||
"lib": { | ||
"entryFile": "src/index.ts", | ||
"styleIncludePaths": ["../src/scss"] | ||
} | ||
} |
73 changes: 73 additions & 0 deletions
73
libs/design/breadcrumb/src/breadcrumb-item/breadcrumb-item.directive.spec.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,73 @@ | ||
import { | ||
Component, | ||
DebugElement, | ||
} from '@angular/core'; | ||
import { | ||
waitForAsync, | ||
ComponentFixture, | ||
TestBed, | ||
} from '@angular/core/testing'; | ||
import { By } from '@angular/platform-browser'; | ||
|
||
import { DaffBreadcrumbItemDirective } from './breadcrumb-item.directive'; | ||
|
||
@Component({ | ||
template: `<li daffBreadcrumbItem [active]="active">Breadcrumb Item</li>`, | ||
standalone: true, | ||
imports: [ | ||
DaffBreadcrumbItemDirective, | ||
], | ||
}) | ||
class WrapperComponent { | ||
active = false; | ||
} | ||
|
||
describe('@daffodil/design/breadcrumb | DaffBreadcrumbItemDirective', () => { | ||
let wrapper: WrapperComponent; | ||
let de: DebugElement; | ||
let fixture: ComponentFixture<WrapperComponent>; | ||
let component: DaffBreadcrumbItemDirective; | ||
|
||
beforeEach(waitForAsync(() => { | ||
TestBed.configureTestingModule({ | ||
imports: [ | ||
WrapperComponent, | ||
], | ||
}) | ||
.compileComponents(); | ||
})); | ||
|
||
beforeEach(() => { | ||
fixture = TestBed.createComponent(WrapperComponent); | ||
wrapper = fixture.componentInstance; | ||
de = fixture.debugElement.query(By.css('[daffBreadcrumbItem]')); | ||
component = de.componentInstance; | ||
fixture.detectChanges(); | ||
}); | ||
|
||
it('should create', () => { | ||
expect(wrapper).toBeTruthy(); | ||
}); | ||
|
||
describe('li[daffBreadcrumbItem]', () => { | ||
it('should add a class of "daff-breadcrumb__item" to the host element', () => { | ||
expect(de.classes).toEqual(jasmine.objectContaining({ | ||
'daff-breadcrumb__item': true, | ||
})); | ||
}); | ||
}); | ||
|
||
it('should set the `aria-current` to page if it`s the active breadcrumb', () => { | ||
wrapper.active = true; | ||
fixture.detectChanges(); | ||
|
||
expect(de.nativeElement.ariaCurrent).toEqual('page'); | ||
}); | ||
|
||
it('should set the `aria-current` to false if it`s not the active breadcrumb', () => { | ||
wrapper.active = false; | ||
fixture.detectChanges(); | ||
|
||
expect(de.nativeElement.ariaCurrent).toEqual('false'); | ||
}); | ||
}); |
21 changes: 21 additions & 0 deletions
21
libs/design/breadcrumb/src/breadcrumb-item/breadcrumb-item.directive.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
import { | ||
Directive, | ||
HostBinding, | ||
Input, | ||
} from '@angular/core'; | ||
|
||
@Directive({ | ||
selector: 'li[daffBreadcrumbItem]', | ||
standalone: true, | ||
}) | ||
export class DaffBreadcrumbItemDirective { | ||
@HostBinding('class.daff-breadcrumb__item') class = true; | ||
|
||
@HostBinding('attr.aria-current') get ariaCurrent() { | ||
return this.active ? 'page' : 'false'; | ||
} | ||
|
||
/** Whether or not the breadcrumb item is active */ | ||
@Input() @HostBinding('class.active') active = false; | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
@use 'sass:map'; | ||
@use '../../scss/core'; | ||
@use '../../scss/theming'; | ||
|
||
@mixin daff-breadcrumb-theme($theme) { | ||
$base: core.daff-map-deep-get($theme, 'core.base'); | ||
$base-contrast: core.daff-map-deep-get($theme, 'core.base-contrast'); | ||
$neutral: core.daff-map-deep-get($theme, 'core.neutral'); | ||
|
||
.daff-breadcrumb__item { | ||
color: theming.daff-illuminate($base-contrast, $neutral, 4); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
import { NgModule } from '@angular/core'; | ||
|
||
import { DaffBreadcrumbComponent } from './breadcrumb/breadcrumb.component'; | ||
import { DaffBreadcrumbItemDirective } from './breadcrumb-item/breadcrumb-item.directive'; | ||
|
||
/** @deprecated in favor of {@link DAFF_BREADCRUMB_COMPONENTS} */ | ||
@NgModule({ | ||
imports: [ | ||
DaffBreadcrumbComponent, | ||
DaffBreadcrumbItemDirective, | ||
], | ||
exports: [ | ||
DaffBreadcrumbComponent, | ||
DaffBreadcrumbItemDirective, | ||
], | ||
}) | ||
export class DaffBreadcrumbModule { } |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
import { DaffBreadcrumbComponent } from './breadcrumb/breadcrumb.component'; | ||
import { DaffBreadcrumbItemDirective } from './breadcrumb-item/breadcrumb-item.directive'; | ||
|
||
export const DAFF_BREADCRUMB_COMPONENTS = <const> [ | ||
DaffBreadcrumbComponent, | ||
DaffBreadcrumbItemDirective, | ||
]; |
1 change: 1 addition & 0 deletions
1
libs/design/breadcrumb/src/breadcrumb/breadcrumb.component.html
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
<ng-content select="[daffBreadcrumbItem]"></ng-content> |
50 changes: 50 additions & 0 deletions
50
libs/design/breadcrumb/src/breadcrumb/breadcrumb.component.scss
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
@use '../../../scss/typography' as t; | ||
@use '../../../scss/state'; | ||
|
||
.daff-breadcrumb { | ||
$root: &; | ||
display: flex; | ||
flex-wrap: wrap; | ||
list-style: none; | ||
margin: 0; | ||
padding: 0; | ||
|
||
&__item { | ||
font-size: 1rem; | ||
|
||
a { | ||
text-decoration: none; | ||
|
||
&:hover { | ||
text-decoration: underline; | ||
} | ||
} | ||
|
||
&.active { | ||
font-weight: 500; | ||
} | ||
|
||
&:not(:last-child) { | ||
&::after { | ||
content: '/'; | ||
color: currentColor; | ||
font-weight: normal; | ||
margin: 0 0.5rem; | ||
} | ||
} | ||
} | ||
|
||
&.daff-skeleton { | ||
@include state.skeleton-screen(100%, 24px); | ||
max-width: 290px; | ||
width: 100%; | ||
|
||
#{$root}__item { | ||
visibility: hidden; | ||
|
||
&::before { | ||
content: unset; | ||
} | ||
} | ||
} | ||
} |
66 changes: 66 additions & 0 deletions
66
libs/design/breadcrumb/src/breadcrumb/breadcrumb.component.spec.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,66 @@ | ||
import { | ||
Component, | ||
DebugElement, | ||
} from '@angular/core'; | ||
import { | ||
waitForAsync, | ||
ComponentFixture, | ||
TestBed, | ||
} from '@angular/core/testing'; | ||
import { By } from '@angular/platform-browser'; | ||
|
||
import { DaffBreadcrumbComponent } from './breadcrumb.component'; | ||
|
||
@Component({ | ||
template: `<ol daff-breadcrumb [skeleton]="skeleton"></ol>`, | ||
standalone: true, | ||
imports: [ | ||
DaffBreadcrumbComponent, | ||
], | ||
}) | ||
|
||
class WrapperComponent { | ||
skeleton: boolean; | ||
} | ||
|
||
describe('@daffodil/design/breadcrumb | DaffBreadcrumbComponent', () => { | ||
let wrapper: WrapperComponent; | ||
let component: DaffBreadcrumbComponent; | ||
let de: DebugElement; | ||
let fixture: ComponentFixture<WrapperComponent>; | ||
|
||
beforeEach(waitForAsync(() => { | ||
TestBed.configureTestingModule({ | ||
imports: [ | ||
WrapperComponent, | ||
], | ||
}) | ||
.compileComponents(); | ||
})); | ||
|
||
beforeEach(() => { | ||
fixture = TestBed.createComponent(WrapperComponent); | ||
wrapper = fixture.componentInstance; | ||
de = fixture.debugElement.query(By.css('ol[daff-breadcrumb]')); | ||
component = de.componentInstance; | ||
|
||
fixture.detectChanges(); | ||
}); | ||
|
||
it('should create', () => { | ||
expect(component).toBeTruthy(); | ||
}); | ||
|
||
it('should add a class of "daff-breadcrumb" to the host element', () => { | ||
expect(de.classes).toEqual(jasmine.objectContaining({ | ||
'daff-breadcrumb': true, | ||
})); | ||
}); | ||
|
||
it('should take skeleton as an input', () => { | ||
wrapper.skeleton = true; | ||
fixture.detectChanges(); | ||
|
||
expect(de.nativeElement.classList.contains('daff-skeleton')).toEqual(true); | ||
}); | ||
}); |
Oops, something went wrong.