-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(ɵcomponents): add toggle button component
Usage: ```html <sci-toggle-button [formControl]="..."></sci-toggle-button> ```
- Loading branch information
1 parent
b0d23c1
commit 9fed733
Showing
10 changed files
with
285 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
13 changes: 13 additions & 0 deletions
13
apps/components/src/app/sci-toggle-button-page/sci-toggle-button-page.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,13 @@ | ||
<h1>sci-toggle-button (ɵ)</h1> | ||
|
||
<form [formGroup]="form"> | ||
<section class="state"> | ||
<header>State</header> | ||
|
||
<sci-form-field label="Disabled"> | ||
<sci-checkbox [formControl]="form.controls.state.controls.disabled"></sci-checkbox> | ||
</sci-form-field> | ||
</section> | ||
</form> | ||
|
||
<sci-toggle-button [formControl]="form.controls.toggleButton"></sci-toggle-button> |
30 changes: 30 additions & 0 deletions
30
apps/components/src/app/sci-toggle-button-page/sci-toggle-button-page.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,30 @@ | ||
:host { | ||
display: flex; | ||
flex-direction: column; | ||
gap: 1em; | ||
|
||
> h1 { | ||
flex: none; | ||
} | ||
|
||
> form { | ||
flex: none; | ||
|
||
> section.state { | ||
display: flex; | ||
flex-direction: column; | ||
border: 1px solid var(--sci-color-border); | ||
border-radius: var(--sci-corner); | ||
padding: 1em; | ||
|
||
> header { | ||
font-weight: bold; | ||
margin-bottom: 1em; | ||
} | ||
} | ||
} | ||
|
||
> sci-toggle-button { | ||
flex: none; | ||
} | ||
} |
55 changes: 55 additions & 0 deletions
55
apps/components/src/app/sci-toggle-button-page/sci-toggle-button-page.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,55 @@ | ||
/* | ||
* Copyright (c) 2018-2023 Swiss Federal Railways | ||
* | ||
* This program and the accompanying materials are made | ||
* available under the terms of the Eclipse Public License 2.0 | ||
* which is available at https://www.eclipse.org/legal/epl-2.0/ | ||
* | ||
* SPDX-License-Identifier: EPL-2.0 | ||
*/ | ||
|
||
import {Component} from '@angular/core'; | ||
import {NonNullableFormBuilder, ReactiveFormsModule} from '@angular/forms'; | ||
import {SciFormFieldComponent} from '@scion/components.internal/form-field'; | ||
import {SciToggleButtonComponent} from '@scion/components.internal/toggle-button'; | ||
import {SciCheckboxComponent} from '@scion/components.internal/checkbox'; | ||
import {takeUntilDestroyed} from '@angular/core/rxjs-interop'; | ||
|
||
@Component({ | ||
selector: 'sci-toggle-button-page', | ||
templateUrl: './sci-toggle-button-page.component.html', | ||
styleUrls: ['./sci-toggle-button-page.component.scss'], | ||
standalone: true, | ||
imports: [ | ||
ReactiveFormsModule, | ||
SciFormFieldComponent, | ||
SciToggleButtonComponent, | ||
SciCheckboxComponent, | ||
], | ||
}) | ||
export default class SciToggleButtonPageComponent { | ||
|
||
public form = this._formBuilder.group({ | ||
toggleButton: this._formBuilder.control<boolean>(true), | ||
state: this._formBuilder.group({ | ||
disabled: this._formBuilder.control<boolean>(false), | ||
}), | ||
}); | ||
|
||
constructor(private _formBuilder: NonNullableFormBuilder) { | ||
this.installToggleButtonDisabler(); | ||
} | ||
|
||
private installToggleButtonDisabler(): void { | ||
this.form.controls.state.controls.disabled.valueChanges | ||
.pipe(takeUntilDestroyed()) | ||
.subscribe(disabled => { | ||
if (disabled) { | ||
this.form.controls.toggleButton.disable(); | ||
} | ||
else { | ||
this.form.controls.toggleButton.enable(); | ||
} | ||
}); | ||
} | ||
} |
3 changes: 3 additions & 0 deletions
3
projects/scion/components.internal/toggle-button/ng-package.json
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,3 @@ | ||
{ | ||
"$schema": "../../../../node_modules/ng-packagr/ng-package.schema.json" | ||
} |
16 changes: 16 additions & 0 deletions
16
projects/scion/components.internal/toggle-button/src/public_api.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,16 @@ | ||
/* | ||
* Copyright (c) 2018-2019 Swiss Federal Railways | ||
* | ||
* This program and the accompanying materials are made | ||
* available under the terms of the Eclipse Public License 2.0 | ||
* which is available at https://www.eclipse.org/legal/epl-2.0/ | ||
* | ||
* SPDX-License-Identifier: EPL-2.0 | ||
*/ | ||
|
||
/* | ||
* Secondary entrypoint: '@scion/components.internal/toggle-button' | ||
* | ||
* @see https://github.com/ng-packagr/ng-packagr/blob/master/docs/secondary-entrypoints.md | ||
*/ | ||
export {SciToggleButtonComponent} from './toggle-button.component'; |
2 changes: 2 additions & 0 deletions
2
projects/scion/components.internal/toggle-button/src/toggle-button.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,2 @@ | ||
<input type="checkbox" [id]="id" [formControl]="formControl"> | ||
<label [for]="id"></label> |
75 changes: 75 additions & 0 deletions
75
projects/scion/components.internal/toggle-button/src/toggle-button.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,75 @@ | ||
$size: 1.25rem; | ||
|
||
:host { | ||
display: inline-grid; | ||
border-radius: $size; | ||
padding: 1px; | ||
background-color: var(--sci-color-border); | ||
width: 2 * $size; | ||
height: $size; | ||
box-sizing: content-box; | ||
|
||
> input[type=checkbox] { | ||
all: unset; | ||
height: 0; | ||
width: 0; | ||
} | ||
|
||
> label { // checkbox label filling the entire component | ||
cursor: pointer; | ||
|
||
&:after { // on/off circle of the toggle button | ||
content: ''; | ||
display: block; | ||
height: $size; | ||
width: $size; | ||
border-radius: 50%; | ||
transition: transform 125ms ease-out; | ||
background-color: var(--sci-color-accent-inverse); | ||
border: 1px solid var(--sci-color-border); | ||
box-sizing: border-box; | ||
} | ||
} | ||
|
||
&:has(> input:disabled) { | ||
> label { | ||
cursor: unset; | ||
} | ||
} | ||
|
||
> input:checked + label:after { | ||
transform: translateX(100%); // "on" state | ||
} | ||
|
||
&:has(> input:checked:not(:disabled)) { | ||
background-color: var(--sci-color-accent); | ||
|
||
> label:after { // "on" state | ||
border-color: var(--sci-color-accent); | ||
} | ||
} | ||
|
||
&:has(> input:checked:disabled) { | ||
background-color: var(--sci-color-background-input-disabled); | ||
|
||
> label:after { // "on" state | ||
background-color: var(--sci-color-gray-100); | ||
border-color: var(--sci-color-gray-100); | ||
} | ||
} | ||
|
||
&:has(> input:not(:checked):disabled) { | ||
background-color: var(--sci-color-background-input-disabled); | ||
|
||
> label:after { // "off" state | ||
background-color: var(--sci-color-gray-100); | ||
border-color: var(--sci-color-background-input-disabled); | ||
} | ||
} | ||
|
||
&:has(> input:focus-visible:not(:disabled) ) { | ||
outline: 1px solid var(--sci-color-accent); | ||
border-color: transparent; | ||
background-clip: content-box; | ||
} | ||
} |
83 changes: 83 additions & 0 deletions
83
projects/scion/components.internal/toggle-button/src/toggle-button.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,83 @@ | ||
/* | ||
* Copyright (c) 2018-2023 Swiss Federal Railways | ||
* | ||
* This program and the accompanying materials are made | ||
* available under the terms of the Eclipse Public License 2.0 | ||
* which is available at https://www.eclipse.org/legal/epl-2.0/ | ||
* | ||
* SPDX-License-Identifier: EPL-2.0 | ||
*/ | ||
|
||
import {Component, forwardRef} from '@angular/core'; | ||
import {UUID} from '@scion/toolkit/uuid'; | ||
import {ControlValueAccessor, FormControl, NG_VALUE_ACCESSOR, ReactiveFormsModule} from '@angular/forms'; | ||
import {coerceBooleanProperty} from '@angular/cdk/coercion'; | ||
import {noop} from 'rxjs'; | ||
import {takeUntilDestroyed} from '@angular/core/rxjs-interop'; | ||
|
||
@Component({ | ||
selector: 'sci-toggle-button', | ||
templateUrl: './toggle-button.component.html', | ||
styleUrls: ['./toggle-button.component.scss'], | ||
standalone: true, | ||
imports: [ | ||
ReactiveFormsModule, | ||
], | ||
providers: [ | ||
{provide: NG_VALUE_ACCESSOR, multi: true, useExisting: forwardRef(() => SciToggleButtonComponent)}, | ||
], | ||
}) | ||
export class SciToggleButtonComponent implements ControlValueAccessor { | ||
|
||
private _cvaChangeFn: (value: any) => void = noop; | ||
private _cvaTouchedFn: () => void = noop; | ||
|
||
protected formControl = new FormControl<boolean>(false); | ||
protected id = UUID.randomUUID(); | ||
|
||
constructor() { | ||
this.formControl.valueChanges | ||
.pipe(takeUntilDestroyed()) | ||
.subscribe(value => { | ||
this._cvaChangeFn(value); | ||
this._cvaTouchedFn(); | ||
}); | ||
} | ||
|
||
/** | ||
* Method implemented as part of `ControlValueAccessor` to work with Angular forms API | ||
* @docs-private | ||
*/ | ||
public registerOnChange(fn: any): void { | ||
this._cvaChangeFn = fn; | ||
} | ||
|
||
/** | ||
* Method implemented as part of `ControlValueAccessor` to work with Angular forms API | ||
* @docs-private | ||
*/ | ||
public registerOnTouched(fn: any): void { | ||
this._cvaTouchedFn = fn; | ||
} | ||
|
||
/** | ||
* Method implemented as part of `ControlValueAccessor` to work with Angular forms API | ||
* @docs-private | ||
*/ | ||
public setDisabledState(isDisabled: boolean): void { | ||
if (isDisabled) { | ||
this.formControl.disable(); | ||
} | ||
else { | ||
this.formControl.enable(); | ||
} | ||
} | ||
|
||
/** | ||
* Method implemented as part of `ControlValueAccessor` to work with Angular forms API | ||
* @docs-private | ||
*/ | ||
public writeValue(value: any): void { | ||
this.formControl.setValue(coerceBooleanProperty(value), {emitEvent: 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