From 57b9902778017872299e7c3167f860c4ccb64fca Mon Sep 17 00:00:00 2001 From: Karl Seamon Date: Wed, 5 Jun 2019 15:26:30 -0400 Subject: [PATCH] feat(popover-edit): Helper class to reduce form state preservation boilerplate (#15939) --- .../popover-edit/form-value-container.ts | 38 +++++++++++++++++++ .../popover-edit/popover-edit.spec.ts | 6 +-- .../popover-edit/public-api.ts | 1 + .../popover-edit-mat-table-example.html | 6 +-- .../popover-edit-mat-table-example.ts | 5 ++- .../popover-edit/popover-edit.spec.ts | 6 +-- 6 files changed, 50 insertions(+), 12 deletions(-) create mode 100644 src/cdk-experimental/popover-edit/form-value-container.ts diff --git a/src/cdk-experimental/popover-edit/form-value-container.ts b/src/cdk-experimental/popover-edit/form-value-container.ts new file mode 100644 index 00000000000..adfdc9a8698 --- /dev/null +++ b/src/cdk-experimental/popover-edit/form-value-container.ts @@ -0,0 +1,38 @@ +/** + * @license + * Copyright Google LLC All Rights Reserved. + * + * Use of this source code is governed by an MIT-style license that can be + * found in the LICENSE file at https://angular.io/license + */ + +export interface Entry { + value?: FormValue; +} + +/** + * A convenience class for preserving unsaved form state while an edit lens is closed. + * + * Example usage: + * class MyComponent { + * readonly nameEditValues = new FormValueContainer<Item, {name: string}>(); + * } + * + * <form cdkEditControl [(cdkEditControlPreservedFormValue)]="nameEditValues.for(item).value"> + */ +export class FormValueContainer { + private _formValues = new WeakMap>(); + + for(key: Key): Entry { + const _formValues = this._formValues; + + let entry = _formValues.get(key); + if (!entry) { + // Expose entry as an object so that we can [(two-way)] bind to its value member + entry = {}; + _formValues.set(key, entry); + } + + return entry; + } +} diff --git a/src/cdk-experimental/popover-edit/popover-edit.spec.ts b/src/cdk-experimental/popover-edit/popover-edit.spec.ts index 876a28381ce..2fcb27008d2 100644 --- a/src/cdk-experimental/popover-edit/popover-edit.spec.ts +++ b/src/cdk-experimental/popover-edit/popover-edit.spec.ts @@ -14,6 +14,7 @@ import { CdkPopoverEditColspan, CdkPopoverEditModule, HoverContentState, + FormValueContainer, PopoverEditClickOutBehavior, } from './index'; @@ -22,8 +23,7 @@ const NAME_EDIT_TEMPLATE = `
@@ -63,7 +63,7 @@ interface PeriodicElement { abstract class BaseTestComponent { @ViewChild('table', {static: false}) table: ElementRef; - preservedValues = new Map(); + preservedValues = new FormValueContainer(); ignoreSubmitUnlessValid = true; clickOutBehavior: PopoverEditClickOutBehavior = 'close'; diff --git a/src/cdk-experimental/popover-edit/public-api.ts b/src/cdk-experimental/popover-edit/public-api.ts index 492487e7229..cdcfaf6b162 100644 --- a/src/cdk-experimental/popover-edit/public-api.ts +++ b/src/cdk-experimental/popover-edit/public-api.ts @@ -9,6 +9,7 @@ export * from './edit-event-dispatcher'; export * from './edit-ref'; export * from './focus-dispatcher'; +export * from './form-value-container'; export * from './lens-directives'; export * from './popover-edit-module'; export * from './popover-edit-position-strategy-factory'; diff --git a/src/material-examples/popover-edit-mat-table/popover-edit-mat-table-example.html b/src/material-examples/popover-edit-mat-table/popover-edit-mat-table-example.html index 7e0aea445b5..9a92edc7b24 100644 --- a/src/material-examples/popover-edit-mat-table/popover-edit-mat-table-example.html +++ b/src/material-examples/popover-edit-mat-table/popover-edit-mat-table-example.html @@ -8,8 +8,7 @@ + [(matEditLensPreservedFormValue)]="weightValues.for(element).value">
@@ -50,8 +49,7 @@ + [(matEditLensPreservedFormValue)]="nameValues.for(element).value">

Name

diff --git a/src/material-examples/popover-edit-mat-table/popover-edit-mat-table-example.ts b/src/material-examples/popover-edit-mat-table/popover-edit-mat-table-example.ts index a198efff70f..4d1edc82ecc 100644 --- a/src/material-examples/popover-edit-mat-table/popover-edit-mat-table-example.ts +++ b/src/material-examples/popover-edit-mat-table/popover-edit-mat-table-example.ts @@ -1,5 +1,6 @@ import {Component} from '@angular/core'; import {DataSource} from '@angular/cdk/collections'; +import {FormValueContainer} from '@angular/cdk-experimental/popover-edit'; import {NgForm} from '@angular/forms'; import {MatSnackBar} from '@angular/material/snack-bar'; import {BehaviorSubject, Observable} from 'rxjs'; @@ -46,8 +47,8 @@ export class PopoverEditMatTableExample { displayedColumns: string[] = ['position', 'name', 'weight', 'symbol']; dataSource = new ExampleDataSource(); - readonly preservedNameValues = new WeakMap(); - readonly preservedWeightValues = new WeakMap(); + readonly nameValues = new FormValueContainer(); + readonly weightValues = new FormValueContainer(); constructor(private readonly _snackBar: MatSnackBar) {} diff --git a/src/material-experimental/popover-edit/popover-edit.spec.ts b/src/material-experimental/popover-edit/popover-edit.spec.ts index 8283dafc93f..50a455eca87 100644 --- a/src/material-experimental/popover-edit/popover-edit.spec.ts +++ b/src/material-experimental/popover-edit/popover-edit.spec.ts @@ -12,6 +12,7 @@ import {BehaviorSubject} from 'rxjs'; import { CdkPopoverEditColspan, HoverContentState, + FormValueContainer, PopoverEditClickOutBehavior, } from '@angular/cdk-experimental/popover-edit'; import {MatPopoverEditModule} from './index'; @@ -21,8 +22,7 @@ const NAME_EDIT_TEMPLATE = ` @@ -62,7 +62,7 @@ interface PeriodicElement { abstract class BaseTestComponent { @ViewChild('table', {static: false}) table: ElementRef; - preservedValues = new Map(); + preservedValues = new FormValueContainer(); ignoreSubmitUnlessValid = true; clickOutBehavior: PopoverEditClickOutBehavior = 'close';