Skip to content

Commit

Permalink
deprecation: deprecated action button icon iconType input and check…
Browse files Browse the repository at this point in the history
…box and radio button `icon` inputs in favor of new `iconName` input which utilizes SVG icons (#3062)
  • Loading branch information
Blackbaud-TrevorBurch authored Jan 30, 2025
1 parent 1abcf12 commit 567f922
Show file tree
Hide file tree
Showing 19 changed files with 259 additions and 60 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -73,13 +73,23 @@
[(ngModel)]="activeView.id"
>
@for (view of views; track view.id) {
<sky-radio
[attr.aria-label]="view.name"
[icon]="view.icon"
[value]="view.id"
[label]="view.name"
(change)="onViewChange(view.id)"
/>
@if (view.iconName) {
<sky-radio
[attr.aria-label]="view.name"
[iconName]="view.iconName"
[value]="view.id"
[label]="view.name"
(change)="onViewChange(view.id)"
/>
} @else {
<sky-radio
[attr.aria-label]="view.name"
[icon]="view.icon"
[value]="view.id"
[label]="view.name"
(change)="onViewChange(view.id)"
/>
}
}
</sky-radio-group>
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,14 @@ export interface SkyDataViewConfig {
/**
* The Font Awesome icon name to use for this view in the view switcher.
* Required if you have more than one view. Do not include the `fa-` prefix.
* @deprecated Use `iconName` instead.
*/
icon?: string;
/**
* The name of the Blackbaud SVG icon to display for this view in the view switcher.
* Required if you have more than one view.
*/
iconName?: string;
/**
* The unique ID for this view.
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ <h5 [class]="headingClass">{{ headingText }}</h5>
{{ hintText }}
</div>
<span class="sky-checkbox-group-inline sky-switch-icon-group">
<ng-content select="sky-checkbox[icon]" />
<ng-content select="sky-checkbox[icon], sky-checkbox[iconName]" />
</span>
<span class="sky-checkbox-group-stacked">
<ng-content select="sky-checkbox" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,12 @@
'sky-switch-control-danger': checkboxType === 'danger'
}"
>
@if (icon) {
<sky-icon [fixedWidth]="true" [icon]="icon" />
@if (icon || iconName) {
@if (iconName) {
<sky-icon [fixedWidth]="true" [iconName]="iconName" />
} @else {
<sky-icon [fixedWidth]="true" [icon]="icon" />
}
} @else {
@if (indeterminate) {
<sky-icon
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,34 +35,60 @@ import { SkyCheckboxModule } from './checkbox.module';
/** Simple component for testing a single checkbox. */
@Component({
template: ` <div>
<sky-checkbox
[checkboxType]="checkboxType"
[checked]="isChecked"
[disabled]="isDisabled"
[icon]="icon"
[id]="id"
[helpKey]="helpKey"
[helpPopoverContent]="helpPopoverContent"
[helpPopoverTitle]="helpPopoverTitle"
[hintText]="hintText"
[labelText]="labelText"
[stacked]="stacked"
[(indeterminate)]="indeterminate"
(change)="checkboxChange($event)"
>
<sky-checkbox-label>
Simple checkbox
@if (showInlineHelp) {
<span>Help inline</span>
}
</sky-checkbox-label>
</sky-checkbox>
@if (iconName) {
<sky-checkbox
[checkboxType]="checkboxType"
[checked]="isChecked"
[disabled]="isDisabled"
[iconName]="iconName"
[id]="id"
[helpKey]="helpKey"
[helpPopoverContent]="helpPopoverContent"
[helpPopoverTitle]="helpPopoverTitle"
[hintText]="hintText"
[labelText]="labelText"
[stacked]="stacked"
[(indeterminate)]="indeterminate"
(change)="checkboxChange($event)"
>
<sky-checkbox-label>
Simple checkbox
@if (showInlineHelp) {
<span>Help inline</span>
}
</sky-checkbox-label>
</sky-checkbox>
} @else {
<sky-checkbox
[checkboxType]="checkboxType"
[checked]="isChecked"
[disabled]="isDisabled"
[icon]="icon"
[id]="id"
[helpKey]="helpKey"
[helpPopoverContent]="helpPopoverContent"
[helpPopoverTitle]="helpPopoverTitle"
[hintText]="hintText"
[labelText]="labelText"
[stacked]="stacked"
[(indeterminate)]="indeterminate"
(change)="checkboxChange($event)"
>
<sky-checkbox-label>
Simple checkbox
@if (showInlineHelp) {
<span>Help inline</span>
}
</sky-checkbox-label>
</sky-checkbox>
}
</div>`,
standalone: false,
})
class SingleCheckboxComponent implements AfterViewInit {
public checkboxType: string | undefined;
public icon = 'bold';
public icon = 'plus';
public iconName: string | undefined;
public id: string | undefined = 'simple-check';
public indeterminate = false;
public isChecked: boolean | undefined = false;
Expand Down Expand Up @@ -362,6 +388,7 @@ describe('Checkbox component', () => {
beforeEach(async () => {
fixture = TestBed.createComponent(SingleCheckboxComponent);

fixture.detectChanges();
await fixture.whenStable();
checkboxDebugElement = fixture.debugElement.query(
By.directive(SkyCheckboxComponent),
Expand Down Expand Up @@ -464,6 +491,23 @@ describe('Checkbox component', () => {
expect(inputElement?.indeterminate).toBeTrue();
});

it('should handle the indeterminate state being set on initialization', async () => {
fixture = TestBed.createComponent(SingleCheckboxComponent);
testComponent = fixture.componentInstance;
testComponent.indeterminate = true;

fixture.detectChanges();
await fixture.whenStable();
checkboxDebugElement = fixture.debugElement.query(
By.directive(SkyCheckboxComponent),
);
checkboxNativeElement = checkboxDebugElement.nativeElement;
fixture.detectChanges();
inputElement = checkboxNativeElement?.querySelector('input');

expect(inputElement?.indeterminate).toBeTrue();
});

it('should turn off the indeterminate state if the checkbox is clicked after it is set', () => {
testComponent.indeterminate = true;
fixture.detectChanges();
Expand Down Expand Up @@ -721,6 +765,7 @@ describe('Checkbox component', () => {

it('should not assign aria-labelledby if no labeledBy is provided', async () => {
fixture = TestBed.createComponent(SingleCheckboxComponent);
fixture.detectChanges();

checkboxDebugElement = fixture.debugElement.query(
By.directive(SkyCheckboxComponent),
Expand Down Expand Up @@ -1366,7 +1411,7 @@ describe('Checkbox component', () => {
fixture.detectChanges();

let checkboxIcon = debugElement.query(By.css('i')).nativeElement;
expect(checkboxIcon).toHaveCssClass('fa-bold');
expect(checkboxIcon).toHaveCssClass('fa-plus');

fixture.componentInstance.icon = 'umbrella';
fixture.detectChanges();
Expand All @@ -1375,6 +1420,26 @@ describe('Checkbox component', () => {
expect(checkboxIcon).toHaveCssClass('fa-umbrella');
});

it('should set icon based on input - iconName', () => {
fixture.componentInstance.iconName = 'add';
fixture.detectChanges();

let checkboxIcon: HTMLElement = debugElement.query(
By.css('svg'),
).nativeElement;
expect(checkboxIcon.attributes.getNamedItem('data-sky-icon')?.value).toBe(
'add',
);

fixture.componentInstance.iconName = 'book';
fixture.detectChanges();

checkboxIcon = debugElement.query(By.css('svg')).nativeElement;
expect(checkboxIcon.attributes.getNamedItem('data-sky-icon')?.value).toBe(
'book',
);
});

it('should set the switch control class based on the checkbox type input', () => {
fixture.detectChanges();

Expand Down Expand Up @@ -1436,6 +1501,13 @@ describe('Checkbox component', () => {
await fixture.whenStable();
await expectAsync(fixture.nativeElement).toBeAccessible();
});

it('should pass accessibility - iconName', async () => {
fixture.componentInstance.iconName = 'add';
fixture.detectChanges();
await fixture.whenStable();
await expectAsync(fixture.nativeElement).toBeAccessible();
});
});

describe('with a consumer using OnPush change detection', () => {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import {
AfterViewInit,
ChangeDetectorRef,
Component,
ElementRef,
Expand All @@ -23,7 +24,7 @@ import {
import { SkyIdService, SkyLogService } from '@skyux/core';
import { SkyThemeComponentClassDirective } from '@skyux/theme';

import { BehaviorSubject, Observable } from 'rxjs';
import { Observable, Subject } from 'rxjs';

import { SKY_FORM_ERRORS_ENABLED } from '../form-error/form-errors-enabled-token';

Expand Down Expand Up @@ -52,7 +53,9 @@ import { SkyCheckboxChange } from './checkbox-change';
],
standalone: false,
})
export class SkyCheckboxComponent implements ControlValueAccessor, Validator {
export class SkyCheckboxComponent
implements AfterViewInit, ControlValueAccessor, Validator
{
/**
* The ARIA label for the checkbox. This sets the checkbox's `aria-label` attribute
* [to support accessibility](https://developer.blackbaud.com/skyux/components/checkbox#accessibility)
Expand Down Expand Up @@ -179,10 +182,18 @@ export class SkyCheckboxComponent implements ControlValueAccessor, Validator {
/**
* The icon to display in place of the checkbox. To group icon checkboxes
* like in the demo, place the checkboxes within a `sky-checkbox-group`.
* @deprecated Use `iconName` instead.
*/
@Input()
public icon: string | undefined;

/**
* The SVG icon to display in place of the checkbox. To group icon checkboxes
* like in the demo, place the checkboxes within a `sky-checkbox-group`.
*/
@Input()
public iconName: string | undefined;

/**
* The background color type after users select a checkbox where the
* `icon` property displays an icon in place of the checkbox. The valid options correspond to
Expand Down Expand Up @@ -233,11 +244,13 @@ export class SkyCheckboxComponent implements ControlValueAccessor, Validator {
*/
@Input()
public set indeterminate(value: boolean | undefined) {
this.#_indeterminate = !!value;
this.#indeterminateChange.next(this.#_indeterminate);
if (this.inputEl) {
this.inputEl.nativeElement.indeterminate = this.#_indeterminate;
this.#changeDetector.markForCheck();
if (value !== this.#_indeterminate) {
this.#_indeterminate = !!value;
this.#indeterminateChange.next(this.#_indeterminate);
if (this.inputEl) {
this.inputEl.nativeElement.indeterminate = this.#_indeterminate;
this.#changeDetector.markForCheck();
}
}
}

Expand Down Expand Up @@ -340,11 +353,11 @@ export class SkyCheckboxComponent implements ControlValueAccessor, Validator {
protected control: AbstractControl | undefined;
protected inputId = '';

#checkedChange: BehaviorSubject<boolean>;
#checkedChange: Subject<boolean>;
#checkedChangeObs: Observable<boolean>;
#disabledChange: BehaviorSubject<boolean>;
#disabledChange: Subject<boolean>;
#disabledChangeObs: Observable<boolean>;
#indeterminateChange: BehaviorSubject<boolean>;
#indeterminateChange: Subject<boolean>;
#indeterminateChangeObs: Observable<boolean>;

#_checked = false;
Expand All @@ -364,18 +377,23 @@ export class SkyCheckboxComponent implements ControlValueAccessor, Validator {
protected readonly errorId = this.#idSvc.generateId();

constructor() {
this.#checkedChange = new BehaviorSubject<boolean>(this.checked);
this.#disabledChange = new BehaviorSubject<boolean>(this.disabled);
this.#indeterminateChange = new BehaviorSubject<boolean>(this.disabled);
this.#checkedChange = new Subject<boolean>();
this.#disabledChange = new Subject<boolean>();
this.#indeterminateChange = new Subject<boolean>();

this.#checkedChangeObs = this.#checkedChange.asObservable();
this.#disabledChangeObs = this.#disabledChange.asObservable();
this.#indeterminateChangeObs = this.#indeterminateChange.asObservable();

this.id = this.#defaultId;
this.name = this.#defaultId;
}

public ngAfterViewInit(): void {
this.#checkedChange.next(this.checked);
this.#disabledChange.next(this.disabled);
this.#indeterminateChange.next(this.indeterminate);
}

public validate(control: AbstractControl<boolean>): ValidationErrors | null {
this.control ||= control;

Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,17 @@
<div>
@if (iconName) {
<sky-radio
id="simple-check"
[iconName]="iconName"
[label]="'default label'"
[radioType]="radioType"
/>
} @else {
<sky-radio
id="simple-check"
[icon]="icon"
[label]="'default label'"
[radioType]="radioType"
/>
}
</div>
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import { SkyRadioType } from '../types/radio-type';
standalone: false,
})
export class SkySingleRadioComponent {
public icon = 'bold';
public icon = 'plus';
public iconName: string | undefined;
public radioType: SkyRadioType | undefined;
}
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,9 @@
'sky-switch-control-danger': icon && radioType === 'danger'
}"
>
@if (icon) {
@if (iconName) {
<sky-icon [fixedWidth]="true" [iconName]="iconName" />
} @else if (icon) {
<sky-icon [fixedWidth]="true" [icon]="icon" />
}
</span>
Expand Down
Loading

0 comments on commit 567f922

Please sign in to comment.