From 1462d9a1add5b44557562430b02eb93aee14ce53 Mon Sep 17 00:00:00 2001 From: Miles Malerba Date: Thu, 23 Apr 2020 19:10:24 -0700 Subject: [PATCH 1/5] feat(material-expeirmental/mdc-list): add support for focus/hover states and ripples --- src/material-experimental/mdc-list/action-list.ts | 4 +++- src/material-experimental/mdc-list/nav-list.ts | 4 +++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/src/material-experimental/mdc-list/action-list.ts b/src/material-experimental/mdc-list/action-list.ts index b7df2137b024..533c905dea15 100644 --- a/src/material-experimental/mdc-list/action-list.ts +++ b/src/material-experimental/mdc-list/action-list.ts @@ -23,4 +23,6 @@ import {MatListBase} from './list-base'; {provide: MatListBase, useExisting: MatActionList}, ] }) -export class MatActionList extends MatListBase {} +export class MatActionList extends MatListBase { + _hasRipple = true; +} diff --git a/src/material-experimental/mdc-list/nav-list.ts b/src/material-experimental/mdc-list/nav-list.ts index 28b4dd07cd19..6cd1f9890129 100644 --- a/src/material-experimental/mdc-list/nav-list.ts +++ b/src/material-experimental/mdc-list/nav-list.ts @@ -33,4 +33,6 @@ import {MatListBase} from './list-base'; {provide: MatList, useExisting: MatNavList}, ] }) -export class MatNavList extends MatListBase {} +export class MatNavList extends MatListBase { + _hasRipple = true; +} From 1068c470aee74b65a255c1b7ea9e07c446344bd4 Mon Sep 17 00:00:00 2001 From: Miles Malerba Date: Fri, 24 Apr 2020 12:52:58 -0700 Subject: [PATCH 2/5] add state styles --- src/material-experimental/mdc-list/action-list.ts | 4 +--- src/material-experimental/mdc-list/nav-list.ts | 4 +--- 2 files changed, 2 insertions(+), 6 deletions(-) diff --git a/src/material-experimental/mdc-list/action-list.ts b/src/material-experimental/mdc-list/action-list.ts index 533c905dea15..b7df2137b024 100644 --- a/src/material-experimental/mdc-list/action-list.ts +++ b/src/material-experimental/mdc-list/action-list.ts @@ -23,6 +23,4 @@ import {MatListBase} from './list-base'; {provide: MatListBase, useExisting: MatActionList}, ] }) -export class MatActionList extends MatListBase { - _hasRipple = true; -} +export class MatActionList extends MatListBase {} diff --git a/src/material-experimental/mdc-list/nav-list.ts b/src/material-experimental/mdc-list/nav-list.ts index 6cd1f9890129..28b4dd07cd19 100644 --- a/src/material-experimental/mdc-list/nav-list.ts +++ b/src/material-experimental/mdc-list/nav-list.ts @@ -33,6 +33,4 @@ import {MatListBase} from './list-base'; {provide: MatList, useExisting: MatNavList}, ] }) -export class MatNavList extends MatListBase { - _hasRipple = true; -} +export class MatNavList extends MatListBase {} From 362dc9f6ce356f536e5f07c4b63cb96c78b48c64 Mon Sep 17 00:00:00 2001 From: Miles Malerba Date: Thu, 7 May 2020 23:22:33 -0700 Subject: [PATCH 3/5] add demo and stub implementation for mdc-based selection-list --- src/dev-app/mdc-list/mdc-list-demo.html | 64 +++++++++++++++++- .../mdc-list/BUILD.bazel | 1 + .../mdc-list/list-base.ts | 1 + .../mdc-list/list-option.html | 17 ++++- .../mdc-list/selection-list.html | 1 - .../mdc-list/selection-list.ts | 65 +++++++++++++++++-- src/material/list/selection-list.ts | 7 +- 7 files changed, 140 insertions(+), 16 deletions(-) delete mode 100644 src/material-experimental/mdc-list/selection-list.html diff --git a/src/dev-app/mdc-list/mdc-list-demo.html b/src/dev-app/mdc-list/mdc-list-demo.html index 268f0c511118..4090f8c62aa0 100644 --- a/src/dev-app/mdc-list/mdc-list-demo.html +++ b/src/dev-app/mdc-list/mdc-list-demo.html @@ -116,6 +116,68 @@

Action list

Selection list

- TODO: Implement MDC-based selection list. + +
Groceries
+ + Bananas + Oranges + Apples + Strawberries +
+ + +
Dogs
+ + + + Shiba Inu + + + + + Other Shiba Inu + +
+ +

Selected: {{selectedOptions | json}}

+

Change Event Count {{changeEventCount}}

+

Model Change Event Count {{modelChangeEventCount}}

+

+ + Disable Selection List + +

+

+ + Disable Selection List ripples + +

+

+ + +

+
+ +
+

Single Selection list

+ + +
Favorite Grocery
+ + Bananas + Oranges + Apples + Strawberries +
+ +

Selected: {{favoriteOptions | json}}

diff --git a/src/material-experimental/mdc-list/BUILD.bazel b/src/material-experimental/mdc-list/BUILD.bazel index 917252188cf8..2b5c10615889 100644 --- a/src/material-experimental/mdc-list/BUILD.bazel +++ b/src/material-experimental/mdc-list/BUILD.bazel @@ -22,6 +22,7 @@ ng_module( assets = [":list_scss"] + glob(["**/*.html"]), module_name = "@angular/material-experimental/mdc-list", deps = [ + "//src/cdk/collections", "//src/material/divider", "@npm//@angular/core", "@npm//@angular/forms", diff --git a/src/material-experimental/mdc-list/list-base.ts b/src/material-experimental/mdc-list/list-base.ts index 7aec2ac109b6..090043279999 100644 --- a/src/material-experimental/mdc-list/list-base.ts +++ b/src/material-experimental/mdc-list/list-base.ts @@ -46,6 +46,7 @@ export abstract class MatListItemBase implements AfterContentInit, OnDestroy, Ri rippleConfig: RippleConfig = {}; + // TODO(mmalerba): Add @Input for disabling ripple. rippleDisabled: boolean; private _subscriptions = new Subscription(); diff --git a/src/material-experimental/mdc-list/list-option.html b/src/material-experimental/mdc-list/list-option.html index 05ec09f3cd49..11056329ac8b 100644 --- a/src/material-experimental/mdc-list/list-option.html +++ b/src/material-experimental/mdc-list/list-option.html @@ -1 +1,16 @@ -TODO: Implement. + + + + + + + + + + + + + diff --git a/src/material-experimental/mdc-list/selection-list.html b/src/material-experimental/mdc-list/selection-list.html deleted file mode 100644 index 05ec09f3cd49..000000000000 --- a/src/material-experimental/mdc-list/selection-list.html +++ /dev/null @@ -1 +0,0 @@ -TODO: Implement. diff --git a/src/material-experimental/mdc-list/selection-list.ts b/src/material-experimental/mdc-list/selection-list.ts index bbeb71599fd0..fd31bc853f99 100644 --- a/src/material-experimental/mdc-list/selection-list.ts +++ b/src/material-experimental/mdc-list/selection-list.ts @@ -6,19 +6,24 @@ * found in the LICENSE file at https://angular.io/license */ +import {BooleanInput} from '@angular/cdk/coercion'; +import {SelectionModel} from '@angular/cdk/collections'; import {Platform} from '@angular/cdk/platform'; import { ChangeDetectionStrategy, Component, ContentChildren, ElementRef, + EventEmitter, forwardRef, + Input, NgZone, + Output, QueryList, ViewEncapsulation } from '@angular/core'; -import {NG_VALUE_ACCESSOR} from '@angular/forms'; -import {MatLine} from '@angular/material/core'; +import {ControlValueAccessor, NG_VALUE_ACCESSOR} from '@angular/forms'; +import {MatLine, ThemePalette} from '@angular/material/core'; import {MatListBase, MatListItemBase} from './list-base'; const MAT_SELECTION_LIST_VALUE_ACCESSOR: any = { @@ -40,9 +45,10 @@ export class MatSelectionListChange { selector: 'mat-selection-list', exportAs: 'matSelectionList', host: { - 'class': 'mat-mdc-selection-list mat-mdc-list-base' + 'class': 'mat-mdc-selection-list mat-mdc-list-base mdc-list', + 'role': 'listbox', }, - templateUrl: 'selection-list.html', + template: '', styleUrls: ['list.css'], encapsulation: ViewEncapsulation.None, providers: [ @@ -51,23 +57,68 @@ export class MatSelectionListChange { ], changeDetection: ChangeDetectionStrategy.OnPush, }) -export class MatSelectionList extends MatListBase {} +export class MatSelectionList extends MatListBase implements ControlValueAccessor { + // TODO: Implement these inputs. + @Input() disableRipple: boolean; + @Input() tabIndex: number; + @Input() color: ThemePalette; + @Input() compareWith: (o1: any, o2: any) => boolean; + @Input() disabled: boolean; + @Input() multiple: boolean; + + // TODO: Implement these inputs. + @Output() readonly selectionChange = new EventEmitter(); + + @ContentChildren(forwardRef(() => MatListOption), {descendants: true}) options: + QueryList; + + // TODO: Implement these properties. + selectedOptions: SelectionModel; + + // TODO: Implement these methods. + focus(options?: FocusOptions) {} + selectAll() {} + deselectAll() {} + registerOnChange(fn: any) {} + registerOnTouched(fn: any) {} + writeValue(obj: any) {} +} @Component({ selector: 'mat-list-option', exportAs: 'matListOption', host: { - 'class': 'mat-mdc-list-item mat-mdc-list-option', + 'class': 'mat-mdc-list-item mat-mdc-list-option mdc-list-item', + 'role': 'option', + 'tabindex': '-1', }, templateUrl: 'list-option.html', encapsulation: ViewEncapsulation.None, changeDetection: ChangeDetectionStrategy.OnPush, }) export class MatListOption extends MatListItemBase { + static ngAcceptInputType_disabled: BooleanInput; + static ngAcceptInputType_selected: BooleanInput; + static ngAcceptInputType_disableRipple: BooleanInput; + @ContentChildren(MatLine, {read: ElementRef, descendants: true}) lines: QueryList>; - constructor(element: ElementRef, ngZone: NgZone, listBase: MatListBase, platform: Platform) { + // TODO: Implement these inputs. + @Input() disableRipple: boolean; + @Input() checkboxPosition: 'before' | 'after'; + @Input() color: ThemePalette; + @Input() value: any; + @Input() disabled: boolean; + @Input() selected: boolean; + + constructor(element: ElementRef, ngZone: NgZone, listBase: MatListBase, platform: Platform, + public selectionList: MatSelectionList) { super(element, ngZone, listBase, platform); } + + // TODO: Implement these methods. + getLabel() { return ''; } + focus() {} + toggle() {} } diff --git a/src/material/list/selection-list.ts b/src/material/list/selection-list.ts index 9a42ca215b43..35179047f201 100644 --- a/src/material/list/selection-list.ts +++ b/src/material/list/selection-list.ts @@ -32,6 +32,7 @@ import { forwardRef, Inject, Input, + isDevMode, OnChanges, OnDestroy, OnInit, @@ -40,7 +41,6 @@ import { SimpleChanges, ViewChild, ViewEncapsulation, - isDevMode, } from '@angular/core'; import {ControlValueAccessor, NG_VALUE_ACCESSOR} from '@angular/forms'; import { @@ -51,19 +51,14 @@ import { setLines, ThemePalette, } from '@angular/material/core'; - import {Subject} from 'rxjs'; import {startWith, takeUntil} from 'rxjs/operators'; - import {MatListAvatarCssMatStyler, MatListIconCssMatStyler} from './list'; - -/** @docs-private */ class MatSelectionListBase {} const _MatSelectionListMixinBase: CanDisableRippleCtor & typeof MatSelectionListBase = mixinDisableRipple(MatSelectionListBase); -/** @docs-private */ class MatListOptionBase {} const _MatListOptionMixinBase: CanDisableRippleCtor & typeof MatListOptionBase = mixinDisableRipple(MatListOptionBase); From d80c59614905477aa4fc193515d4bde463328603 Mon Sep 17 00:00:00 2001 From: Miles Malerba Date: Wed, 3 Jun 2020 17:51:48 -0700 Subject: [PATCH 4/5] reduce the number of ng-template's needed in list-item and list-option --- .../mdc-list/list-option.html | 35 ++++++++++++------- src/material-experimental/mdc-list/list.scss | 5 +++ src/material-experimental/mdc-list/module.ts | 3 +- .../mdc-list/selection-list.ts | 2 +- 4 files changed, 30 insertions(+), 15 deletions(-) diff --git a/src/material-experimental/mdc-list/list-option.html b/src/material-experimental/mdc-list/list-option.html index 11056329ac8b..4f2e4681d015 100644 --- a/src/material-experimental/mdc-list/list-option.html +++ b/src/material-experimental/mdc-list/list-option.html @@ -1,16 +1,25 @@ - - - - - - - - - + + + + + - + + + + + + + + + + + + + + + + + diff --git a/src/material-experimental/mdc-list/list.scss b/src/material-experimental/mdc-list/list.scss index e3b20ede5751..b877265ec4e8 100644 --- a/src/material-experimental/mdc-list/list.scss +++ b/src/material-experimental/mdc-list/list.scss @@ -108,3 +108,8 @@ right: 0; opacity: 0; } + +.mat-mdc-list-option .mdc-list-item__meta .mdc-list-item__graphic { + margin-right: 0; + vertical-align: middle; +} diff --git a/src/material-experimental/mdc-list/module.ts b/src/material-experimental/mdc-list/module.ts index cc11d2eb53dc..bf2fda759dc2 100644 --- a/src/material-experimental/mdc-list/module.ts +++ b/src/material-experimental/mdc-list/module.ts @@ -8,7 +8,7 @@ import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; -import {MatLineModule, MatRippleModule} from '@angular/material/core'; +import {MatLineModule, MatPseudoCheckboxModule, MatRippleModule} from '@angular/material/core'; import {MatDividerModule} from '@angular/material/divider'; import {MatActionList} from './action-list'; import { @@ -26,6 +26,7 @@ import {MatListOption, MatSelectionList} from './selection-list'; CommonModule, MatLineModule, MatRippleModule, + MatPseudoCheckboxModule, ], exports: [ MatList, diff --git a/src/material-experimental/mdc-list/selection-list.ts b/src/material-experimental/mdc-list/selection-list.ts index fd31bc853f99..c6f464b8ecd7 100644 --- a/src/material-experimental/mdc-list/selection-list.ts +++ b/src/material-experimental/mdc-list/selection-list.ts @@ -106,7 +106,7 @@ export class MatListOption extends MatListItemBase { // TODO: Implement these inputs. @Input() disableRipple: boolean; - @Input() checkboxPosition: 'before' | 'after'; + @Input() checkboxPosition: 'before' | 'after' = 'before'; @Input() color: ThemePalette; @Input() value: any; @Input() disabled: boolean; From 54daf49cd7d0115029633acd75d4f737dfe79c3f Mon Sep 17 00:00:00 2001 From: Miles Malerba Date: Thu, 4 Jun 2020 21:31:29 -0700 Subject: [PATCH 5/5] address comments --- src/material-experimental/mdc-list/list-option.html | 2 +- src/material-experimental/mdc-list/list.scss | 3 +++ 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/src/material-experimental/mdc-list/list-option.html b/src/material-experimental/mdc-list/list-option.html index 4f2e4681d015..ada597f38597 100644 --- a/src/material-experimental/mdc-list/list-option.html +++ b/src/material-experimental/mdc-list/list-option.html @@ -1,4 +1,4 @@ - + diff --git a/src/material-experimental/mdc-list/list.scss b/src/material-experimental/mdc-list/list.scss index b877265ec4e8..8473180a79a9 100644 --- a/src/material-experimental/mdc-list/list.scss +++ b/src/material-experimental/mdc-list/list.scss @@ -109,6 +109,9 @@ opacity: 0; } +// Normally the `.mdc-list-item__meta` class would be applied to the icon or checkbox directly. +// However, we need to group multiple potential `ng-content` blocks inside the meta section, so we +// add them as children instead. These styles ensure that they are properly aligned. .mat-mdc-list-option .mdc-list-item__meta .mdc-list-item__graphic { margin-right: 0; vertical-align: middle;