Skip to content

Commit eef3526

Browse files
jelbournwagnermaciel
authored andcommitted
refactor(cdk-experimental/ui-patterns): remove controllers & lazy-loading
1 parent 6b857e0 commit eef3526

File tree

11 files changed

+366
-560
lines changed

11 files changed

+366
-560
lines changed

src/cdk-experimental/listbox/listbox.ts

+1-2
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,6 @@ import {toSignal} from '@angular/core/rxjs-interop';
4747
'[attr.aria-orientation]': 'pattern.orientation()',
4848
'[attr.aria-multiselectable]': 'pattern.multiselectable()',
4949
'[attr.aria-activedescendant]': 'pattern.activedescendant()',
50-
'(focusin)': 'pattern.onFocus()',
5150
'(keydown)': 'pattern.onKeydown($event)',
5251
'(mousedown)': 'pattern.onMousedown($event)',
5352
},
@@ -61,7 +60,7 @@ export class CdkListbox {
6160

6261
/** A signal wrapper for directionality. */
6362
protected directionality = toSignal(this._dir.change, {
64-
initialValue: 'ltr',
63+
initialValue: this._dir.value,
6564
});
6665

6766
/** The Option UIPatterns of the child CdkOptions. */

src/cdk-experimental/ui-patterns/behaviors/event-manager/event-manager.ts

+5-5
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ export interface EventHandlerOptions {
3232
* A config that specifies how to handle a particular event.
3333
*/
3434
export interface EventHandlerConfig<T extends Event> extends EventHandlerOptions {
35-
handler: (event: T) => Promise<boolean | void>;
35+
handler: (event: T) => boolean | void;
3636
}
3737

3838
/**
@@ -89,18 +89,18 @@ export abstract class EventManager<T extends Event> {
8989
* Note: the use of `undefined` instead of `false` in the unhandled case is necessary to avoid
9090
* accidentally preventing the default behavior on an unhandled event.
9191
*/
92-
async handle(event: T): Promise<true | undefined> {
92+
handle(event: T): true | undefined {
9393
if (!this.isHandled(event)) {
9494
return undefined;
9595
}
9696
for (const fn of this.beforeFns) {
9797
fn(event);
9898
}
9999
for (const submanager of this._submanagers) {
100-
await submanager.handle(event);
100+
submanager.handle(event);
101101
}
102102
for (const config of this.getHandlersForKey(event)) {
103-
await config.handler(event);
103+
config.handler(event);
104104
if (config.stopPropagation) {
105105
event.stopPropagation();
106106
}
@@ -158,7 +158,7 @@ export class GenericEventManager<T extends Event> extends EventManager<T> {
158158
/**
159159
* Configures this event manager to handle all events with the given handler.
160160
*/
161-
on(handler: (event: T) => Promise<boolean | void>): this {
161+
on(handler: (event: T) => boolean | void): this {
162162
this.configs.push({
163163
...this.defaultHandlerOptions,
164164
handler,

src/cdk-experimental/ui-patterns/behaviors/list-focus/controller.ts

-24
This file was deleted.

src/cdk-experimental/ui-patterns/behaviors/list-focus/list-focus.ts

+7-19
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88

99
import {computed, Signal} from '@angular/core';
1010
import {ListNavigation, ListNavigationItem} from '../list-navigation/list-navigation';
11-
import type {ListFocusController} from './controller';
1211

1312
/** The required properties for focus items. */
1413
export interface ListFocusItem extends ListNavigationItem {
@@ -30,26 +29,10 @@ export class ListFocus<T extends ListFocusItem> {
3029
/** The navigation controller of the parent list. */
3130
navigation: ListNavigation<ListFocusItem>;
3231

33-
get controller(): Promise<ListFocusController<T>> {
34-
if (this._controller === null) {
35-
return this.loadController();
36-
}
37-
return Promise.resolve(this._controller);
38-
}
39-
private _controller: ListFocusController<T> | null = null;
40-
4132
constructor(readonly inputs: ListFocusInputs<T> & {navigation: ListNavigation<T>}) {
4233
this.navigation = inputs.navigation;
4334
}
4435

45-
/** Loads the controller for list focus. */
46-
async loadController(): Promise<ListFocusController<T>> {
47-
return import('./controller').then(m => {
48-
this._controller = new m.ListFocusController(this);
49-
return this._controller;
50-
});
51-
}
52-
5336
/** Returns the id of the current active item. */
5437
getActiveDescendant(): Signal<string | null> {
5538
return computed(() => {
@@ -77,7 +60,12 @@ export class ListFocus<T extends ListFocusItem> {
7760
}
7861

7962
/** Focuses the current active item. */
80-
async focus() {
81-
(await this.controller).focus();
63+
focus() {
64+
if (this.inputs.focusMode() === 'activedescendant') {
65+
return;
66+
}
67+
68+
const item = this.navigation.inputs.items()[this.navigation.inputs.activeIndex()];
69+
item.element().focus();
8270
}
8371
}

src/cdk-experimental/ui-patterns/behaviors/list-navigation/controller.ts

-72
This file was deleted.

src/cdk-experimental/ui-patterns/behaviors/list-navigation/list-navigation.ts

+40-29
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@
77
*/
88

99
import {signal, Signal, WritableSignal} from '@angular/core';
10-
import type {ListNavigationController} from './controller';
1110

1211
/** The required properties for navigation items. */
1312
export interface ListNavigationItem {
@@ -41,53 +40,65 @@ export class ListNavigation<T extends ListNavigationItem> {
4140
/** The last index that was active. */
4241
prevActiveIndex = signal(0);
4342

44-
get controller(): Promise<ListNavigationController<T>> {
45-
if (this._controller === null) {
46-
return this.loadController();
47-
}
48-
return Promise.resolve(this._controller);
49-
}
50-
private _controller: ListNavigationController<T> | null = null;
51-
5243
constructor(readonly inputs: ListNavigationInputs<T>) {
5344
this.prevActiveIndex.set(inputs.activeIndex());
5445
}
5546

56-
/** Loads the controller for list navigation. */
57-
async loadController(): Promise<ListNavigationController<T>> {
58-
return import('./controller').then(m => {
59-
this._controller = new m.ListNavigationController(this);
60-
return this._controller;
61-
});
62-
}
63-
6447
/** Navigates to the given item. */
65-
async goto(item: T) {
66-
return (await this.controller).goto(item);
48+
goto(item: T) {
49+
if (this.isFocusable(item)) {
50+
this.prevActiveIndex.set(this.inputs.activeIndex());
51+
const index = this.inputs.items().indexOf(item);
52+
this.inputs.activeIndex.set(index);
53+
}
6754
}
6855

6956
/** Navigates to the next item in the list. */
70-
async next() {
71-
return (await this.controller).next();
57+
next() {
58+
const items = this.inputs.items();
59+
const after = items.slice(this.inputs.activeIndex() + 1);
60+
const before = items.slice(0, this.inputs.activeIndex());
61+
const array = this.inputs.wrap() ? after.concat(before) : after;
62+
const item = array.find(i => this.isFocusable(i));
63+
64+
if (item) {
65+
this.goto(item);
66+
}
7267
}
7368

7469
/** Navigates to the previous item in the list. */
75-
async prev() {
76-
return (await this.controller).prev();
70+
prev() {
71+
const items = this.inputs.items();
72+
const after = items.slice(this.inputs.activeIndex() + 1).reverse();
73+
const before = items.slice(0, this.inputs.activeIndex()).reverse();
74+
const array = this.inputs.wrap() ? before.concat(after) : before;
75+
const item = array.find(i => this.isFocusable(i));
76+
77+
if (item) {
78+
this.goto(item);
79+
}
7780
}
7881

7982
/** Navigates to the first item in the list. */
80-
async first() {
81-
return (await this.controller).first();
83+
first() {
84+
const item = this.inputs.items().find(i => this.isFocusable(i));
85+
86+
if (item) {
87+
this.goto(item);
88+
}
8289
}
8390

8491
/** Navigates to the last item in the list. */
85-
async last() {
86-
return (await this.controller).last();
92+
last() {
93+
const item = [...this.inputs.items()].reverse().find(i => this.isFocusable(i));
94+
95+
if (item) {
96+
this.goto(item);
97+
}
8798
}
8899

89100
/** Returns true if the given item can be navigated to. */
90-
async isFocusable(item: T) {
91-
return (await this.controller).isFocusable(item);
101+
isFocusable(item: T): boolean {
102+
return !item.disabled() || !this.inputs.skipDisabled();
92103
}
93104
}

0 commit comments

Comments
 (0)