@angular/aria 21.0.0-rc.1 → 21.0.0-rc.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (41) hide show
  1. package/_adev_assets/aria-accordion.json +439 -55
  2. package/_adev_assets/aria-combobox.json +343 -35
  3. package/_adev_assets/aria-grid.json +345 -77
  4. package/_adev_assets/aria-listbox.json +113 -33
  5. package/_adev_assets/aria-menu.json +366 -141
  6. package/_adev_assets/aria-tabs.json +261 -77
  7. package/_adev_assets/aria-toolbar.json +72 -33
  8. package/_adev_assets/aria-tree.json +169 -26
  9. package/fesm2022/_widget-chunk.mjs +388 -57
  10. package/fesm2022/_widget-chunk.mjs.map +1 -1
  11. package/fesm2022/accordion.mjs +121 -68
  12. package/fesm2022/accordion.mjs.map +1 -1
  13. package/fesm2022/aria.mjs +1 -1
  14. package/fesm2022/aria.mjs.map +1 -1
  15. package/fesm2022/combobox.mjs +132 -21
  16. package/fesm2022/combobox.mjs.map +1 -1
  17. package/fesm2022/grid.mjs +198 -61
  18. package/fesm2022/grid.mjs.map +1 -1
  19. package/fesm2022/listbox.mjs +42 -31
  20. package/fesm2022/listbox.mjs.map +1 -1
  21. package/fesm2022/menu.mjs +173 -67
  22. package/fesm2022/menu.mjs.map +1 -1
  23. package/fesm2022/private.mjs +415 -439
  24. package/fesm2022/private.mjs.map +1 -1
  25. package/fesm2022/tabs.mjs +86 -55
  26. package/fesm2022/tabs.mjs.map +1 -1
  27. package/fesm2022/toolbar.mjs +13 -25
  28. package/fesm2022/toolbar.mjs.map +1 -1
  29. package/fesm2022/tree.mjs +86 -44
  30. package/fesm2022/tree.mjs.map +1 -1
  31. package/package.json +2 -2
  32. package/types/_grid-chunk.d.ts +216 -35
  33. package/types/accordion.d.ts +133 -34
  34. package/types/combobox.d.ts +145 -12
  35. package/types/grid.d.ts +149 -31
  36. package/types/listbox.d.ts +58 -26
  37. package/types/menu.d.ts +130 -46
  38. package/types/private.d.ts +210 -250
  39. package/types/tabs.d.ts +119 -39
  40. package/types/toolbar.d.ts +49 -29
  41. package/types/tree.d.ts +113 -41
@@ -1,4 +1,4 @@
1
- import { computed, signal, linkedSignal } from '@angular/core';
1
+ import { signal, computed, linkedSignal, untracked } from '@angular/core';
2
2
 
3
3
  var Modifier;
4
4
  (function (Modifier) {
@@ -132,6 +132,118 @@ class PointerEventManager extends EventManager {
132
132
  }
133
133
  }
134
134
 
135
+ class ListFocus {
136
+ inputs;
137
+ prevActiveItem = signal(undefined);
138
+ prevActiveIndex = computed(() => {
139
+ return this.prevActiveItem() ? this.inputs.items().indexOf(this.prevActiveItem()) : -1;
140
+ });
141
+ activeIndex = computed(() => {
142
+ return this.inputs.activeItem() ? this.inputs.items().indexOf(this.inputs.activeItem()) : -1;
143
+ });
144
+ constructor(inputs) {
145
+ this.inputs = inputs;
146
+ }
147
+ isListDisabled() {
148
+ return this.inputs.disabled() || this.inputs.items().every(i => i.disabled());
149
+ }
150
+ getActiveDescendant() {
151
+ if (this.isListDisabled()) {
152
+ return undefined;
153
+ }
154
+ if (this.inputs.focusMode() === 'roving') {
155
+ return undefined;
156
+ }
157
+ return this.inputs.activeItem()?.id() ?? undefined;
158
+ }
159
+ getListTabIndex() {
160
+ if (this.isListDisabled()) {
161
+ return 0;
162
+ }
163
+ return this.inputs.focusMode() === 'activedescendant' ? 0 : -1;
164
+ }
165
+ getItemTabIndex(item) {
166
+ if (this.isListDisabled()) {
167
+ return -1;
168
+ }
169
+ if (this.inputs.focusMode() === 'activedescendant') {
170
+ return -1;
171
+ }
172
+ return this.inputs.activeItem() === item ? 0 : -1;
173
+ }
174
+ focus(item, opts) {
175
+ if (this.isListDisabled() || !this.isFocusable(item)) {
176
+ return false;
177
+ }
178
+ this.prevActiveItem.set(this.inputs.activeItem());
179
+ this.inputs.activeItem.set(item);
180
+ if (opts?.focusElement || opts?.focusElement === undefined) {
181
+ this.inputs.focusMode() === 'roving' ? item.element()?.focus() : this.inputs.element()?.focus();
182
+ }
183
+ return true;
184
+ }
185
+ isFocusable(item) {
186
+ return !item.disabled() || this.inputs.softDisabled();
187
+ }
188
+ }
189
+
190
+ class ListNavigation {
191
+ inputs;
192
+ constructor(inputs) {
193
+ this.inputs = inputs;
194
+ }
195
+ goto(item, opts) {
196
+ return item ? this.inputs.focusManager.focus(item, opts) : false;
197
+ }
198
+ next(opts) {
199
+ return this._advance(1, opts);
200
+ }
201
+ peekNext() {
202
+ return this._peek(1);
203
+ }
204
+ prev(opts) {
205
+ return this._advance(-1, opts);
206
+ }
207
+ peekPrev() {
208
+ return this._peek(-1);
209
+ }
210
+ first(opts) {
211
+ const item = this.peekFirst();
212
+ return item ? this.goto(item, opts) : false;
213
+ }
214
+ last(opts) {
215
+ const item = this.peekLast();
216
+ return item ? this.goto(item, opts) : false;
217
+ }
218
+ peekFirst(items = this.inputs.items()) {
219
+ return items.find(i => this.inputs.focusManager.isFocusable(i));
220
+ }
221
+ peekLast(items = this.inputs.items()) {
222
+ for (let i = items.length - 1; i >= 0; i--) {
223
+ if (this.inputs.focusManager.isFocusable(items[i])) {
224
+ return items[i];
225
+ }
226
+ }
227
+ return;
228
+ }
229
+ _advance(delta, opts) {
230
+ const item = this._peek(delta);
231
+ return item ? this.goto(item, opts) : false;
232
+ }
233
+ _peek(delta) {
234
+ const items = this.inputs.items();
235
+ const itemCount = items.length;
236
+ const startIndex = this.inputs.focusManager.activeIndex();
237
+ const step = i => this.inputs.wrap() ? (i + delta + itemCount) % itemCount : i + delta;
238
+ for (let i = step(startIndex); i !== startIndex && i < itemCount && i >= 0; i = step(i)) {
239
+ if (this.inputs.focusManager.isFocusable(items[i])) {
240
+ return items[i];
241
+ }
242
+ }
243
+ return;
244
+ }
245
+ }
246
+
135
247
  class GridData {
136
248
  inputs;
137
249
  cells;
@@ -224,6 +336,9 @@ class GridData {
224
336
  this.inputs = inputs;
225
337
  this.cells = this.inputs.cells;
226
338
  }
339
+ hasCell(cell) {
340
+ return this._coordsMap().has(cell);
341
+ }
227
342
  getCell(rowCol) {
228
343
  return this._cellMap().get(`${rowCol.row}:${rowCol.col}`);
229
344
  }
@@ -294,7 +409,7 @@ class GridFocus {
294
409
  return this.activeCell() === cell ? 0 : -1;
295
410
  }
296
411
  isFocusable(cell) {
297
- return !cell.disabled() || this.inputs.softDisabled();
412
+ return this.inputs.grid.hasCell(cell) && (!cell.disabled() || this.inputs.softDisabled());
298
413
  }
299
414
  focusCell(cell) {
300
415
  if (this.gridDisabled()) {
@@ -395,11 +510,13 @@ class GridNavigation {
395
510
  };
396
511
  for (let step = 0; step < this._maxSteps(); step++) {
397
512
  const isWrapping = nextCoords.col + colDelta < 0 || nextCoords.col + colDelta >= maxColCount || nextCoords.row + rowDelta < 0 || nextCoords.row + rowDelta >= maxRowCount;
398
- if (wrap === 'nowrap' && isWrapping) return;
513
+ if (wrap === 'nowrap' && isWrapping) return undefined;
399
514
  if (wrap === 'continuous') {
400
515
  const generalDelta = delta.row ?? delta.col;
401
516
  const rowStep = isWrapping ? generalDelta : rowDelta;
402
517
  const colStep = isWrapping ? generalDelta : colDelta;
518
+ const bothWrapping = nextCoords.row + rowStep >= maxRowCount && nextCoords.col + colStep >= maxColCount || nextCoords.row + rowStep < 0 && nextCoords.col + colStep < 0;
519
+ if (bothWrapping) return undefined;
403
520
  nextCoords = {
404
521
  row: (nextCoords.row + rowStep + maxRowCount) % maxRowCount,
405
522
  col: (nextCoords.col + colStep + maxColCount) % maxColCount
@@ -720,7 +837,7 @@ class GridPattern {
720
837
  activeDescendant = computed(() => this.gridBehavior.activeDescendant());
721
838
  activeCell = computed(() => this.gridBehavior.focusBehavior.activeCell());
722
839
  anchorCell = computed(() => this.inputs.enableSelection() && this.inputs.multi() ? this.gridBehavior.selectionAnchorCell() : undefined);
723
- pauseNavigation = computed(() => this.gridBehavior.data.cells().flat().reduce((res, c) => res || c.widgetActivated(), false));
840
+ pauseNavigation = computed(() => this.gridBehavior.data.cells().flat().reduce((res, c) => res || c.isActivated(), false));
724
841
  isFocused = signal(false);
725
842
  hasBeenFocused = signal(false);
726
843
  dragging = signal(false);
@@ -736,7 +853,7 @@ class GridPattern {
736
853
  };
737
854
  manager.on('ArrowUp', () => this.gridBehavior.up(opts)).on('ArrowDown', () => this.gridBehavior.down(opts)).on(this.prevColKey(), () => this.gridBehavior.left(opts)).on(this.nextColKey(), () => this.gridBehavior.right(opts)).on('Home', () => this.gridBehavior.firstInRow(opts)).on('End', () => this.gridBehavior.lastInRow(opts)).on([Modifier.Ctrl], 'Home', () => this.gridBehavior.first(opts)).on([Modifier.Ctrl], 'End', () => this.gridBehavior.last(opts));
738
855
  if (this.inputs.enableSelection() && this.inputs.selectionMode() === 'explicit') {
739
- manager.on('Enter', () => this.inputs.multi() ? this.gridBehavior.toggle() : this.gridBehavior.toggleOne()).on(' ', () => this.inputs.multi() ? this.gridBehavior.toggle() : this.gridBehavior.toggleOne());
856
+ manager.on(/Enter| /, () => this.inputs.multi() ? this.gridBehavior.toggle() : this.gridBehavior.toggleOne());
740
857
  }
741
858
  if (this.inputs.enableSelection() && this.inputs.enableRangeSelection()) {
742
859
  manager.on(Modifier.Shift, 'ArrowUp', () => this.gridBehavior.up({
@@ -823,6 +940,7 @@ class GridPattern {
823
940
  });
824
941
  _maybeDeletion = signal(false);
825
942
  _deletion = signal(false);
943
+ _stateStale = signal(false);
826
944
  constructor(inputs) {
827
945
  this.inputs = inputs;
828
946
  this.gridBehavior = new Grid({
@@ -831,42 +949,49 @@ class GridPattern {
831
949
  });
832
950
  }
833
951
  onKeydown(event) {
834
- if (!this.disabled()) {
835
- this.keydown().handle(event);
836
- }
952
+ if (this.disabled()) return;
953
+ this.activeCell()?.onKeydown(event);
954
+ this.keydown().handle(event);
837
955
  }
838
956
  onPointerdown(event) {
839
- if (!this.disabled()) {
840
- this.pointerdown().handle(event);
841
- }
957
+ if (this.disabled()) return;
958
+ this.pointerdown().handle(event);
842
959
  }
843
960
  onPointermove(event) {
844
- if (this.disabled()) return;
845
- if (!this.inputs.enableSelection()) return;
846
- if (!this.inputs.enableRangeSelection()) return;
847
- if (!this.dragging()) return;
961
+ if (this.disabled() || !this.inputs.enableSelection() || !this.inputs.enableRangeSelection() || !this.dragging()) {
962
+ return;
963
+ }
848
964
  const cell = this.inputs.getCell(event.target);
849
- if (!cell) return;
850
- this.gridBehavior.gotoCell(cell, {
851
- anchor: true
852
- });
965
+ if (cell !== undefined) {
966
+ this.gridBehavior.gotoCell(cell, {
967
+ anchor: true
968
+ });
969
+ }
853
970
  }
854
971
  onPointerup(event) {
855
- if (!this.disabled()) {
856
- this.pointerup().handle(event);
857
- }
972
+ if (this.disabled()) return;
973
+ this.pointerup().handle(event);
858
974
  }
859
- onFocusIn() {
975
+ onFocusIn(event) {
860
976
  this.isFocused.set(true);
861
977
  this.hasBeenFocused.set(true);
978
+ if (this.dragging()) return;
979
+ const cell = this.inputs.getCell(event.target);
980
+ if (!cell || !this.gridBehavior.focusBehavior.isFocusable(cell)) return;
981
+ cell.onFocusIn(event);
982
+ if (cell !== this.activeCell()) {
983
+ this.gridBehavior.gotoCell(cell);
984
+ }
862
985
  }
863
986
  onFocusOut(event) {
864
- const parentEl = this.inputs.element();
865
- const targetEl = event.relatedTarget;
866
- if (targetEl === null) {
987
+ const blurTarget = event.target;
988
+ const cell = this.inputs.getCell(blurTarget);
989
+ cell?.onFocusOut(event);
990
+ const focusTarget = event.relatedTarget;
991
+ if (this.inputs.element().contains(focusTarget)) return;
992
+ if (focusTarget === null) {
867
993
  this._maybeDeletion.set(true);
868
994
  }
869
- if (parentEl.contains(targetEl)) return;
870
995
  this.isFocused.set(false);
871
996
  }
872
997
  setDefaultStateEffect() {
@@ -875,22 +1000,49 @@ class GridPattern {
875
1000
  }
876
1001
  resetStateEffect() {
877
1002
  const hasReset = this.gridBehavior.resetState();
878
- if (hasReset && this._maybeDeletion()) {
879
- this._deletion.set(true);
1003
+ if (hasReset) {
1004
+ if (this._maybeDeletion()) {
1005
+ this._deletion.set(true);
1006
+ } else {
1007
+ this._stateStale.set(true);
1008
+ }
880
1009
  }
881
1010
  this._maybeDeletion.set(false);
882
1011
  }
883
- focusEffect() {
884
- const activeCell = this.activeCell();
885
- const hasFocus = this.isFocused();
1012
+ resetFocusEffect() {
1013
+ const stateStale = this._stateStale();
1014
+ if (!stateStale) return;
1015
+ const isFocused = untracked(() => this.isFocused());
1016
+ const isRoving = untracked(() => this.inputs.focusMode() === 'roving');
1017
+ const activeCell = untracked(() => this.activeCell());
1018
+ if (isRoving && activeCell !== undefined && isFocused) {
1019
+ if (!activeCell.isFocused()) {
1020
+ activeCell.focus();
1021
+ }
1022
+ }
1023
+ this._stateStale.set(false);
1024
+ }
1025
+ restoreFocusEffect() {
886
1026
  const deletion = this._deletion();
887
- const isRoving = this.inputs.focusMode() === 'roving';
888
- if (activeCell !== undefined && isRoving && (hasFocus || deletion)) {
889
- activeCell.element().focus();
890
- if (deletion) {
891
- this._deletion.set(false);
1027
+ if (!deletion) return;
1028
+ const isRoving = untracked(() => this.inputs.focusMode() === 'roving');
1029
+ const activeCell = untracked(() => this.activeCell());
1030
+ if (isRoving && activeCell !== undefined) {
1031
+ if (!activeCell.isFocused()) {
1032
+ activeCell.focus();
892
1033
  }
893
1034
  }
1035
+ this._deletion.set(false);
1036
+ }
1037
+ focusEffect() {
1038
+ const activeCell = this.activeCell();
1039
+ const gridFocused = untracked(() => this.isFocused());
1040
+ if (activeCell === undefined || !gridFocused) return;
1041
+ const isRoving = untracked(() => this.inputs.focusMode() === 'roving');
1042
+ const cellFocused = untracked(() => activeCell.isFocused());
1043
+ if (isRoving && !cellFocused) {
1044
+ activeCell.focus();
1045
+ }
894
1046
  }
895
1047
  }
896
1048
 
@@ -905,45 +1057,224 @@ class GridRowPattern {
905
1057
 
906
1058
  class GridCellPattern {
907
1059
  inputs;
908
- id;
909
- disabled;
1060
+ id = () => this.inputs.id();
1061
+ element = () => this.inputs.element();
1062
+ isFocused = signal(false);
910
1063
  selected;
911
- selectable;
912
- rowSpan;
913
- colSpan;
1064
+ selectable = () => this.inputs.selectable();
1065
+ disabled = () => this.inputs.disabled();
1066
+ rowSpan = () => this.inputs.rowSpan();
1067
+ colSpan = () => this.inputs.colSpan();
1068
+ active = computed(() => this.inputs.grid().activeCell() === this);
1069
+ anchor = computed(() => this.inputs.grid().anchorCell() === this ? true : undefined);
914
1070
  ariaSelected = computed(() => this.inputs.grid().inputs.enableSelection() && this.selectable() ? this.selected() : undefined);
915
1071
  ariaRowIndex = computed(() => this.inputs.row().rowIndex() ?? this.inputs.rowIndex() ?? this.inputs.grid().gridBehavior.rowIndex(this));
916
1072
  ariaColIndex = computed(() => this.inputs.colIndex() ?? this.inputs.grid().gridBehavior.colIndex(this));
917
- element = computed(() => this.inputs.widget()?.element() ?? this.inputs.element());
918
- active = computed(() => this.inputs.grid().activeCell() === this);
919
- anchor = computed(() => this.inputs.grid().anchorCell() === this ? true : undefined);
920
1073
  _tabIndex = computed(() => this.inputs.grid().gridBehavior.cellTabIndex(this));
921
- tabIndex = computed(() => this.inputs.widget() !== undefined ? -1 : this._tabIndex());
922
- widgetActivated = computed(() => this.inputs.widget()?.inputs.activate() ?? false);
1074
+ tabIndex = computed(() => {
1075
+ if (this.singleWidgetMode() || this.navigationActivated()) {
1076
+ return -1;
1077
+ }
1078
+ return this._tabIndex();
1079
+ });
1080
+ singleWidgetMode = computed(() => this.inputs.widgets().length === 1);
1081
+ multiWidgetMode = computed(() => this.inputs.widgets().length > 1);
1082
+ navigationDisabled = computed(() => !this.multiWidgetMode() || !this.active() || this.inputs.disabled());
1083
+ focusBehavior;
1084
+ navigationBehavior;
1085
+ activeWidget = linkedSignal(() => this.inputs.widgets().length > 0 ? this.inputs.widgets()[0] : undefined);
1086
+ navigationActivated = signal(false);
1087
+ widgetActivated = computed(() => this.inputs.widgets().some(w => w.isActivated()));
1088
+ isActivated = computed(() => this.navigationActivated() || this.widgetActivated());
1089
+ prevKey = computed(() => {
1090
+ if (this.inputs.orientation() === 'vertical') {
1091
+ return 'ArrowUp';
1092
+ }
1093
+ return this.inputs.textDirection() === 'rtl' ? 'ArrowRight' : 'ArrowLeft';
1094
+ });
1095
+ nextKey = computed(() => {
1096
+ if (this.inputs.orientation() === 'vertical') {
1097
+ return 'ArrowDown';
1098
+ }
1099
+ return this.inputs.textDirection() === 'rtl' ? 'ArrowLeft' : 'ArrowRight';
1100
+ });
1101
+ keydown = computed(() => {
1102
+ const manager = new KeyboardEventManager();
1103
+ if (!this.navigationActivated()) {
1104
+ manager.on('Enter', () => this.startNavigation());
1105
+ return manager;
1106
+ }
1107
+ manager.on('Escape', () => this.stopNavigation()).on(this.prevKey(), () => this._advance(() => this.navigationBehavior.prev({
1108
+ focusElement: false
1109
+ }))).on(this.nextKey(), () => this._advance(() => this.navigationBehavior.next({
1110
+ focusElement: false
1111
+ }))).on('Home', () => this._advance(() => this.navigationBehavior.next({
1112
+ focusElement: false
1113
+ }))).on('End', () => this._advance(() => this.navigationBehavior.next({
1114
+ focusElement: false
1115
+ })));
1116
+ return manager;
1117
+ });
923
1118
  constructor(inputs) {
924
1119
  this.inputs = inputs;
925
- this.id = inputs.id;
926
- this.disabled = inputs.disabled;
927
- this.rowSpan = inputs.rowSpan;
928
- this.colSpan = inputs.colSpan;
929
1120
  this.selected = inputs.selected;
930
- this.selectable = inputs.selectable;
1121
+ const listNavigationInputs = {
1122
+ ...inputs,
1123
+ items: inputs.widgets,
1124
+ activeItem: this.activeWidget,
1125
+ disabled: this.navigationDisabled,
1126
+ focusMode: () => 'roving',
1127
+ softDisabled: () => true
1128
+ };
1129
+ this.focusBehavior = new ListFocus(listNavigationInputs);
1130
+ this.navigationBehavior = new ListNavigation({
1131
+ ...listNavigationInputs,
1132
+ focusManager: this.focusBehavior
1133
+ });
1134
+ }
1135
+ onKeydown(event) {
1136
+ if (this.disabled() || this.inputs.widgets().length === 0) return;
1137
+ if (this.singleWidgetMode()) {
1138
+ this.activeWidget().onKeydown(event);
1139
+ return;
1140
+ }
1141
+ if (!this.navigationActivated()) {
1142
+ this.keydown().handle(event);
1143
+ return;
1144
+ }
1145
+ const widgetActivated = this.widgetActivated();
1146
+ this.activeWidget().onKeydown(event);
1147
+ if (!widgetActivated) {
1148
+ this.keydown().handle(event);
1149
+ }
1150
+ }
1151
+ onFocusIn(event) {
1152
+ this.isFocused.set(true);
1153
+ const focusTarget = event.target;
1154
+ const widget = this.inputs.getWidget(focusTarget);
1155
+ if (!widget) return;
1156
+ widget.onFocusIn(event);
1157
+ if (widget !== this.activeWidget()) {
1158
+ this.navigationBehavior.goto(widget, {
1159
+ focusElement: false
1160
+ });
1161
+ }
1162
+ if (this.multiWidgetMode()) {
1163
+ this.navigationActivated.set(true);
1164
+ }
1165
+ }
1166
+ onFocusOut(event) {
1167
+ const blurTarget = event.target;
1168
+ const widget = this.inputs.getWidget(blurTarget);
1169
+ widget?.onFocusOut(event);
1170
+ const focusTarget = event.relatedTarget;
1171
+ if (this.element().contains(focusTarget)) return;
1172
+ this.isFocused.set(false);
1173
+ this.navigationActivated.set(false);
1174
+ }
1175
+ focus() {
1176
+ if (this.singleWidgetMode()) {
1177
+ this.activeWidget()?.focus();
1178
+ } else {
1179
+ this.element().focus();
1180
+ }
931
1181
  }
932
1182
  widgetTabIndex() {
933
- return this._tabIndex();
1183
+ if (this.singleWidgetMode()) {
1184
+ return this._tabIndex();
1185
+ }
1186
+ return this.navigationActivated() ? 0 : -1;
1187
+ }
1188
+ startNavigation() {
1189
+ if (this.navigationActivated()) return;
1190
+ this.navigationActivated.set(true);
1191
+ this.navigationBehavior.first();
1192
+ }
1193
+ stopNavigation() {
1194
+ if (!this.navigationActivated()) return;
1195
+ this.navigationActivated.set(false);
1196
+ this.element().focus();
1197
+ }
1198
+ _advance(op) {
1199
+ const success = op();
1200
+ if (success) {
1201
+ this.activeWidget()?.focus();
1202
+ }
934
1203
  }
935
1204
  }
936
1205
 
937
1206
  class GridCellWidgetPattern {
938
1207
  inputs;
939
- element;
1208
+ id = () => this.inputs.id();
1209
+ element = () => this.inputs.element();
1210
+ widgetHost = computed(() => this.inputs.focusTarget() ?? this.element());
1211
+ index = computed(() => this.inputs.cell().inputs.widgets().indexOf(this));
1212
+ disabled = computed(() => this.inputs.disabled() || this.inputs.cell().disabled());
940
1213
  tabIndex = computed(() => this.inputs.cell().widgetTabIndex());
941
- active = computed(() => this.inputs.cell().active());
1214
+ active = computed(() => this.inputs.cell().activeWidget() === this);
1215
+ isActivated = signal(false);
1216
+ lastActivateEvent = signal(undefined);
1217
+ lastDeactivateEvent = signal(undefined);
1218
+ keydown = computed(() => {
1219
+ const manager = new KeyboardEventManager();
1220
+ if (this.inputs.widgetType() === 'simple') {
1221
+ return manager;
1222
+ }
1223
+ if (this.isActivated()) {
1224
+ manager.on('Escape', e => {
1225
+ this.deactivate(e);
1226
+ this.focus();
1227
+ });
1228
+ if (this.inputs.widgetType() === 'editable') {
1229
+ manager.on('Enter', e => {
1230
+ this.deactivate(e);
1231
+ this.focus();
1232
+ });
1233
+ }
1234
+ return manager;
1235
+ }
1236
+ manager.on('Enter', e => this.activate(e));
1237
+ if (this.inputs.widgetType() === 'editable') {
1238
+ manager.on([Modifier.Shift, Modifier.None], /^[a-zA-Z0-9]$/, e => this.activate(e), {
1239
+ preventDefault: false
1240
+ });
1241
+ }
1242
+ return manager;
1243
+ });
942
1244
  constructor(inputs) {
943
1245
  this.inputs = inputs;
944
- this.element = inputs.element;
1246
+ }
1247
+ onKeydown(event) {
1248
+ if (this.disabled()) return;
1249
+ this.keydown().handle(event);
1250
+ }
1251
+ onFocusIn(event) {
1252
+ if (this.inputs.widgetType() === 'simple') return;
1253
+ const focusTarget = event.target;
1254
+ if (this.widgetHost().contains(focusTarget) && this.widgetHost() !== focusTarget) {
1255
+ this.activate(event);
1256
+ }
1257
+ }
1258
+ onFocusOut(event) {
1259
+ const focusTarget = event.relatedTarget;
1260
+ if (this.widgetHost().contains(focusTarget)) return;
1261
+ this.deactivate(event);
1262
+ }
1263
+ focus() {
1264
+ this.widgetHost().focus();
1265
+ }
1266
+ activate(event) {
1267
+ if (this.isActivated()) return;
1268
+ if (this.inputs.widgetType() === 'simple') return;
1269
+ this.isActivated.set(true);
1270
+ this.lastActivateEvent.set(event);
1271
+ }
1272
+ deactivate(event) {
1273
+ if (!this.isActivated()) return;
1274
+ this.isActivated.set(false);
1275
+ this.lastDeactivateEvent.set(event);
945
1276
  }
946
1277
  }
947
1278
 
948
- export { GridCellPattern, GridCellWidgetPattern, GridPattern, GridRowPattern, KeyboardEventManager, Modifier, PointerEventManager };
1279
+ export { GridCellPattern, GridCellWidgetPattern, GridPattern, GridRowPattern, KeyboardEventManager, ListFocus, ListNavigation, Modifier, PointerEventManager };
949
1280
  //# sourceMappingURL=_widget-chunk.mjs.map