diff --git a/projects/common/src/lib/list/list-item.directive.ts b/projects/common/src/lib/list/list-item.directive.ts index 33f538823a..667e5d04aa 100644 --- a/projects/common/src/lib/list/list-item.directive.ts +++ b/projects/common/src/lib/list/list-item.directive.ts @@ -12,7 +12,9 @@ import { selector: '[igoListItem]' }) export class ListItemDirective { - static cls = 'igo-list-item-selected'; + + static selectedCls = 'igo-list-item-selected'; + static disabledCls = 'igo-list-item-disabled'; @Input() get color() { @@ -31,16 +33,14 @@ export class ListItemDirective { if (value === this._focused) { return; } + if (this.disabled) { + return; + } value ? this.beforeFocus.emit(this) : this.beforeUnfocus.emit(this); - if (value) { - this.renderer.addClass(this.el.nativeElement, ListItemDirective.cls); - } else { - this.renderer.removeClass(this.el.nativeElement, ListItemDirective.cls); - } - this._focused = value; + this.toggleSelectedClass(); value ? this.focus.emit(this) : this.unfocus.emit(this); } @@ -54,30 +54,55 @@ export class ListItemDirective { if (value === this._selected) { return; } + if (this.disabled) { + return; + } value ? this.beforeSelect.emit(this) : this.beforeUnselect.emit(this); - if (value) { - this.renderer.addClass(this.el.nativeElement, ListItemDirective.cls); - } else { - this.renderer.removeClass(this.el.nativeElement, ListItemDirective.cls); - } - this._selected = value; this._focused = value; + this.toggleSelectedClass(); value ? this.select.emit(this) : this.unselect.emit(this); } private _selected = false; + @Input() + get disabled() { + return this._disabled; + } + set disabled(value: boolean) { + if (value === this._disabled) { + return; + } + + if (value === true) { + this.selected = false; + } + + value ? this.beforeDisable.emit(this) : this.beforeEnable.emit(this); + + this._disabled = value; + this.toggleDisabledClass(); + + value ? this.disable.emit(this) : this.enable.emit(this); + } + private _disabled = false; + + @Output() beforeSelect = new EventEmitter(); @Output() beforeFocus = new EventEmitter(); @Output() beforeUnselect = new EventEmitter(); @Output() beforeUnfocus = new EventEmitter(); + @Output() beforeDisable = new EventEmitter(); + @Output() beforeEnable = new EventEmitter(); @Output() focus = new EventEmitter(); @Output() unfocus = new EventEmitter(); @Output() select = new EventEmitter(); @Output() unselect = new EventEmitter(); + @Output() disable = new EventEmitter(); + @Output() enable = new EventEmitter(); @HostListener('click') onClick() { @@ -91,4 +116,28 @@ export class ListItemDirective { return this.el.nativeElement.offsetTop - padding; } + + private toggleSelectedClass() { + if (this.focused || this.selected) { + this.addCls(ListItemDirective.selectedCls); + } else { + this.removeCls(ListItemDirective.selectedCls); + } + } + + private toggleDisabledClass() { + if (this.disabled) { + this.addCls(ListItemDirective.disabledCls); + } else { + this.removeCls(ListItemDirective.disabledCls); + } + } + + private addCls(cls: string) { + this.renderer.addClass(this.el.nativeElement, cls); + } + + private removeCls(cls: string) { + this.renderer.removeClass(this.el.nativeElement, cls); + } } diff --git a/projects/common/src/lib/list/list.component.scss b/projects/common/src/lib/list/list.component.scss index bda9559a58..b7fd02adcd 100644 --- a/projects/common/src/lib/list/list.component.scss +++ b/projects/common/src/lib/list/list.component.scss @@ -53,7 +53,7 @@ mat-list { width: 40px; } -:host mat-list.selectable >>> [igolistitem] mat-list-item:hover { +:host mat-list.selectable >>> [igolistitem]:not(.igo-list-item-disabled) mat-list-item:hover { cursor: pointer; } diff --git a/projects/common/src/lib/list/list.component.ts b/projects/common/src/lib/list/list.component.ts index 4e908d82e5..0530f846f0 100644 --- a/projects/common/src/lib/list/list.component.ts +++ b/projects/common/src/lib/list/list.component.ts @@ -19,6 +19,7 @@ import { ListItemDirective } from './list-item.directive'; styleUrls: ['./list.component.scss'] }) export class ListComponent implements AfterViewInit, OnInit, OnDestroy { + @Input() get navigation() { return this._navigation; @@ -122,22 +123,40 @@ export class ListComponent implements AfterViewInit, OnInit, OnDestroy { } focusNext() { + const items = this.listItems.toArray(); + let item; + let disabled = true; let index = this.getFocusedIndex(); if (index === undefined) { index = -1; } - const items = this.listItems.toArray(); - if (index !== items.length - 1) { - this.focus(items[index + 1]); + while (disabled && index < items.length) { + index += 1; + item = items[index]; + disabled = item.disabled; + } + + if (item !== undefined) { + this.focus(item); } + } focusPrevious() { - const index = this.getFocusedIndex(); const items = this.listItems.toArray(); - if (index !== 0) { - this.focus(items[index - 1]); + let item; + let disabled = true; + let index = this.getFocusedIndex(); + + while (disabled && index > 0) { + index -= 1; + item = items[index]; + disabled = item.disabled; + } + + if (item !== undefined) { + this.focus(item); } } diff --git a/projects/common/src/lib/list/list.theming.scss b/projects/common/src/lib/list/list.theming.scss index 342ddbfd11..84cc81f456 100644 --- a/projects/common/src/lib/list/list.theming.scss +++ b/projects/common/src/lib/list/list.theming.scss @@ -12,12 +12,16 @@ color: mat-color($accent, default-contrast); } - igo-list [igolistitem][color="primary"]:hover > mat-list-item { + igo-list [igolistitem].igo-list-item-disabled > mat-list-item { + color: rgba(0, 0, 0, 0.38); + } + + igo-list [igolistitem][color="primary"]:not(.igo-list-item-disabled):hover > mat-list-item { background-color: mat-color($primary, lighter); color: mat-color($primary, default-contrast); } - igo-list [igolistitem][color="accent"]:hover > mat-list-item { + igo-list [igolistitem][color="accent"]:not(.igo-list-item-disabled):hover > mat-list-item { background-color: mat-color($accent, lighter); color: mat-color($accent, default-contrast); }