Skip to content

Commit 485bd99

Browse files
authored
fix(multiple): stop exposing internal ripple implementation (#29622)
Removes the code that exposes the ripple implementations of some components since they are internal details and they require some hacky workarounds to keep exposed. BREAKING CHANGE: * `MatButton.ripple` is no longer available. * `MatCheckbox.ripple` is no longer available. * `MatChip.ripple` is no longer available.
1 parent 0fbfc8a commit 485bd99

File tree

11 files changed

+6
-186
lines changed

11 files changed

+6
-186
lines changed

src/material/button/button-base.ts

Lines changed: 3 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ import {
2121
OnDestroy,
2222
OnInit,
2323
} from '@angular/core';
24-
import {MatRipple, MatRippleLoader, ThemePalette} from '@angular/material/core';
24+
import {MatRippleLoader, ThemePalette} from '@angular/material/core';
2525

2626
/** Object that can be used to configure the default options for the button component. */
2727
export interface MatButtonConfig {
@@ -93,22 +93,10 @@ export class MatButtonBase implements AfterViewInit, OnDestroy {
9393
* Handles the lazy creation of the MatButton ripple.
9494
* Used to improve initial load time of large applications.
9595
*/
96-
_rippleLoader: MatRippleLoader = inject(MatRippleLoader);
96+
protected _rippleLoader: MatRippleLoader = inject(MatRippleLoader);
9797

9898
/** Whether this button is a FAB. Used to apply the correct class on the ripple. */
99-
_isFab = false;
100-
101-
/**
102-
* Reference to the MatRipple instance of the button.
103-
* @deprecated Considered an implementation detail. To be removed.
104-
* @breaking-change 17.0.0
105-
*/
106-
get ripple(): MatRipple {
107-
return this._rippleLoader?.getRipple(this._elementRef.nativeElement)!;
108-
}
109-
set ripple(v: MatRipple) {
110-
this._rippleLoader?.attachRipple(this._elementRef.nativeElement, v);
111-
}
99+
protected _isFab = false;
112100

113101
/**
114102
* Theme color of the button. This API is supported in M2 themes only, it has

src/material/button/button.spec.ts

Lines changed: 2 additions & 91 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,11 @@
11
import {createMouseEvent, dispatchEvent} from '@angular/cdk/testing/private';
2-
import {ApplicationRef, Component, DebugElement} from '@angular/core';
2+
import {ApplicationRef, Component} from '@angular/core';
33
import {ComponentFixture, TestBed, waitForAsync} from '@angular/core/testing';
4-
import {MatRipple, ThemePalette} from '@angular/material/core';
4+
import {ThemePalette} from '@angular/material/core';
55
import {By} from '@angular/platform-browser';
66
import {
77
MAT_BUTTON_CONFIG,
88
MAT_FAB_DEFAULT_OPTIONS,
9-
MatButton,
109
MatButtonModule,
1110
MatFabDefaultOptions,
1211
} from './index';
@@ -62,14 +61,6 @@ describe('MatButton', () => {
6261
expect(anchor.classList).toContain('mat-mdc-button-disabled');
6362
});
6463

65-
it('should expose the ripple instance', () => {
66-
const fixture = TestBed.createComponent(TestApp);
67-
fixture.detectChanges();
68-
69-
const button = fixture.debugElement.query(By.directive(MatButton))!.componentInstance;
70-
expect(button.ripple).toBeTruthy();
71-
});
72-
7364
it('should not clear previous defined classes', () => {
7465
let fixture = TestBed.createComponent(TestApp);
7566
let testComponent = fixture.debugElement.componentInstance;
@@ -287,86 +278,6 @@ describe('MatButton', () => {
287278
});
288279
});
289280

290-
// Ripple tests.
291-
describe('button ripples', () => {
292-
let fixture: ComponentFixture<TestApp>;
293-
let testComponent: TestApp;
294-
let buttonDebugElement: DebugElement;
295-
let buttonRippleInstance: MatRipple;
296-
let anchorDebugElement: DebugElement;
297-
let anchorRippleInstance: MatRipple;
298-
299-
beforeEach(() => {
300-
fixture = TestBed.createComponent(TestApp);
301-
fixture.detectChanges();
302-
303-
testComponent = fixture.componentInstance;
304-
305-
buttonDebugElement = fixture.debugElement.query(By.css('button[mat-button]'))!;
306-
buttonRippleInstance = buttonDebugElement.componentInstance.ripple;
307-
308-
anchorDebugElement = fixture.debugElement.query(By.css('a[mat-button]'))!;
309-
anchorRippleInstance = anchorDebugElement.componentInstance.ripple;
310-
});
311-
312-
it('should disable the ripple if matRippleDisabled input is set', () => {
313-
expect(buttonRippleInstance.disabled).toBeFalsy();
314-
315-
testComponent.rippleDisabled = true;
316-
fixture.changeDetectorRef.markForCheck();
317-
fixture.detectChanges();
318-
319-
expect(buttonRippleInstance.disabled).toBeTruthy();
320-
});
321-
322-
it('should disable the ripple when the button is disabled', () => {
323-
expect(buttonRippleInstance.disabled).toBeFalsy(
324-
'Expected an enabled button[mat-button] to have an enabled ripple',
325-
);
326-
expect(anchorRippleInstance.disabled).toBeFalsy(
327-
'Expected an enabled a[mat-button] to have an enabled ripple',
328-
);
329-
330-
testComponent.isDisabled = true;
331-
fixture.changeDetectorRef.markForCheck();
332-
fixture.detectChanges();
333-
334-
expect(buttonRippleInstance.disabled).toBeTruthy(
335-
'Expected a disabled button[mat-button] not to have an enabled ripple',
336-
);
337-
expect(anchorRippleInstance.disabled).toBeTruthy(
338-
'Expected a disabled a[mat-button] not to have an enabled ripple',
339-
);
340-
});
341-
342-
it('should render the ripple once it is referenced', () => {
343-
const fab = fixture.debugElement.query(By.css('button[mat-fab]'))!;
344-
let ripple = fab.nativeElement.querySelector('.mat-mdc-button-ripple');
345-
expect(ripple).withContext('Expect ripple to be absent before user interaction').toBeNull();
346-
347-
// Referencing the ripple should instantiate the ripple.
348-
expect(fab.componentInstance.ripple).toBeDefined();
349-
350-
ripple = fab.nativeElement.querySelector('.mat-mdc-button-ripple');
351-
expect(ripple)
352-
.withContext('Expect ripple to be present after user interaction')
353-
.not.toBeNull();
354-
});
355-
356-
// Ensure each of these events triggers the initialization of the button ripple.
357-
for (const event of ['mousedown', 'touchstart', 'mouseenter', 'focus']) {
358-
it(`should render the ripple once a button has received a "${event}" event`, () => {
359-
const fab = fixture.debugElement.query(By.css('button[mat-fab]'))!;
360-
let ripple = fab.nativeElement.querySelector('.mat-mdc-button-ripple');
361-
expect(ripple).toBeNull();
362-
363-
dispatchEvent(fab.nativeElement, createMouseEvent(event));
364-
ripple = fab.nativeElement.querySelector('.mat-mdc-button-ripple');
365-
expect(ripple).not.toBeNull();
366-
});
367-
}
368-
});
369-
370281
it('should have a focus indicator', () => {
371282
const fixture = TestBed.createComponent(TestApp);
372283
const buttonNativeElements = [

src/material/checkbox/checkbox.spec.ts

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -67,10 +67,6 @@ describe('MatCheckbox', () => {
6767
expect(inputElement.checked).toBe(false);
6868
}));
6969

70-
it('should expose the ripple instance', () => {
71-
expect(checkboxInstance.ripple).toBeTruthy();
72-
});
73-
7470
it('should hide the internal SVG', () => {
7571
const svg = checkboxNativeElement.querySelector('svg')!;
7672
expect(svg.getAttribute('aria-hidden')).toBe('true');

src/material/checkbox/checkbox.ts

Lines changed: 0 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -216,13 +216,6 @@ export class MatCheckbox
216216
@Input({transform: booleanAttribute})
217217
disabledInteractive: boolean;
218218

219-
/**
220-
* Reference to the MatRipple instance of the checkbox.
221-
* @deprecated Considered an implementation detail. To be removed.
222-
* @breaking-change 17.0.0
223-
*/
224-
@ViewChild(MatRipple) ripple: MatRipple;
225-
226219
/**
227220
* Called when the checkbox is blurred. Needed to properly implement ControlValueAccessor.
228221
* @docs-private

src/material/chips/chip.spec.ts

Lines changed: 0 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -65,16 +65,6 @@ describe('MatChip', () => {
6565

6666
expect(chip.getAttribute('tabindex')).toBe('15');
6767
});
68-
69-
it('should have its ripple disabled', () => {
70-
fixture = TestBed.createComponent(BasicChip);
71-
fixture.detectChanges();
72-
chipDebugElement = fixture.debugElement.query(By.directive(MatChip))!;
73-
chipInstance = chipDebugElement.injector.get<MatChip>(MatChip);
74-
expect(chipInstance.ripple.disabled)
75-
.withContext('Expected basic chip ripples to be disabled.')
76-
.toBe(true);
77-
});
7868
});
7969

8070
describe('MatChip', () => {
@@ -131,34 +121,6 @@ describe('MatChip', () => {
131121
expect(testComponent.chipRemove).toHaveBeenCalledWith({chip: chipInstance});
132122
});
133123

134-
it('should be able to disable ripples with the `[rippleDisabled]` input', () => {
135-
expect(chipInstance.ripple.disabled)
136-
.withContext('Expected chip ripples to be enabled.')
137-
.toBe(false);
138-
139-
testComponent.rippleDisabled = true;
140-
fixture.changeDetectorRef.markForCheck();
141-
fixture.detectChanges();
142-
143-
expect(chipInstance.ripple.disabled)
144-
.withContext('Expected chip ripples to be disabled.')
145-
.toBe(true);
146-
});
147-
148-
it('should disable ripples when the chip is disabled', () => {
149-
expect(chipInstance.ripple.disabled)
150-
.withContext('Expected chip ripples to be enabled.')
151-
.toBe(false);
152-
153-
testComponent.disabled = true;
154-
fixture.changeDetectorRef.markForCheck();
155-
fixture.detectChanges();
156-
157-
expect(chipInstance.ripple.disabled)
158-
.withContext('Expected chip ripples to be disabled.')
159-
.toBe(true);
160-
});
161-
162124
it('should make disabled chips non-focusable', () => {
163125
testComponent.disabled = true;
164126
fixture.changeDetectorRef.markForCheck();

src/material/chips/chip.ts

Lines changed: 1 addition & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,6 @@ import {
3838
} from '@angular/core';
3939
import {
4040
MAT_RIPPLE_GLOBAL_OPTIONS,
41-
MatRipple,
4241
MatRippleLoader,
4342
RippleGlobalOptions,
4443
} from '@angular/material/core';
@@ -216,26 +215,14 @@ export class MatChip implements OnInit, AfterViewInit, AfterContentInit, DoCheck
216215
/** The chip's trailing remove icon. */
217216
@ContentChild(MAT_CHIP_REMOVE) removeIcon: MatChipRemove;
218217

219-
/**
220-
* Reference to the MatRipple instance of the chip.
221-
* @deprecated Considered an implementation detail. To be removed.
222-
* @breaking-change 17.0.0
223-
*/
224-
get ripple(): MatRipple {
225-
return this._rippleLoader?.getRipple(this._elementRef.nativeElement)!;
226-
}
227-
set ripple(v: MatRipple) {
228-
this._rippleLoader?.attachRipple(this._elementRef.nativeElement, v);
229-
}
230-
231218
/** Action receiving the primary set of user interactions. */
232219
@ViewChild(MatChipAction) primaryAction: MatChipAction;
233220

234221
/**
235222
* Handles the lazy creation of the MatChip ripple.
236223
* Used to improve initial load time of large applications.
237224
*/
238-
_rippleLoader: MatRippleLoader = inject(MatRippleLoader);
225+
private _rippleLoader: MatRippleLoader = inject(MatRippleLoader);
239226

240227
protected _injector = inject(Injector);
241228

src/material/core/private/ripple-loader.ts

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -109,12 +109,6 @@ export class MatRippleLoader implements OnDestroy {
109109
}
110110
}
111111

112-
/** Returns the ripple instance for the given host element. */
113-
getRipple(host: HTMLElement): MatRipple | undefined {
114-
const ripple = this._hosts.get(host);
115-
return ripple || this._createRipple(host);
116-
}
117-
118112
/** Sets the disabled state on the ripple instance corresponding to the given host element. */
119113
setDisabled(host: HTMLElement, disabled: boolean): void {
120114
const ripple = this._hosts.get(host);

tools/public_api_guard/material/button.md

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,6 @@ import { FocusOrigin } from '@angular/cdk/a11y';
1010
import * as i0 from '@angular/core';
1111
import * as i1 from '@angular/material/core';
1212
import { InjectionToken } from '@angular/core';
13-
import { MatRipple } from '@angular/material/core';
1413
import { MatRippleLoader } from '@angular/material/core';
1514
import { NgZone } from '@angular/core';
1615
import { OnDestroy } from '@angular/core';

tools/public_api_guard/material/checkbox.md

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,6 @@ import { FocusableOption } from '@angular/cdk/a11y';
1515
import * as i0 from '@angular/core';
1616
import * as i3 from '@angular/material/core';
1717
import { InjectionToken } from '@angular/core';
18-
import { MatRipple } from '@angular/material/core';
1918
import { NgZone } from '@angular/core';
2019
import { OnChanges } from '@angular/core';
2120
import { Provider } from '@angular/core';
@@ -114,8 +113,6 @@ export class MatCheckbox implements AfterViewInit, OnChanges, ControlValueAccess
114113
// (undocumented)
115114
registerOnValidatorChange(fn: () => void): void;
116115
required: boolean;
117-
// @deprecated
118-
ripple: MatRipple;
119116
// (undocumented)
120117
setDisabledState(isDisabled: boolean): void;
121118
tabIndex: number;

tools/public_api_guard/material/chips.md

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,6 @@ import { InjectionToken } from '@angular/core';
2222
import { Injector } from '@angular/core';
2323
import { MatFormField } from '@angular/material/form-field';
2424
import { MatFormFieldControl } from '@angular/material/form-field';
25-
import { MatRipple } from '@angular/material/core';
26-
import { MatRippleLoader } from '@angular/material/core';
2725
import { NgControl } from '@angular/forms';
2826
import { NgForm } from '@angular/forms';
2927
import { NgZone } from '@angular/core';
@@ -116,10 +114,6 @@ export class MatChip implements OnInit, AfterViewInit, AfterContentInit, DoCheck
116114
remove(): void;
117115
readonly removed: EventEmitter<MatChipEvent>;
118116
removeIcon: MatChipRemove;
119-
// @deprecated
120-
get ripple(): MatRipple;
121-
set ripple(v: MatRipple);
122-
_rippleLoader: MatRippleLoader;
123117
role: string | null;
124118
trailingIcon: MatChipTrailingIcon;
125119
get value(): any;

tools/public_api_guard/material/core.md

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -411,7 +411,6 @@ export class MatRippleLoader implements OnDestroy {
411411
}): void;
412412
// (undocumented)
413413
destroyRipple(host: HTMLElement): void;
414-
getRipple(host: HTMLElement): MatRipple | undefined;
415414
// (undocumented)
416415
ngOnDestroy(): void;
417416
setDisabled(host: HTMLElement, disabled: boolean): void;

0 commit comments

Comments
 (0)