Skip to content

Commit b0e5ba0

Browse files
authored
feat(Table2) Row focus mode (#7037)
1 parent 8ee600b commit b0e5ba0

24 files changed

+906
-458
lines changed

packages/table-dev-app/src/mutableTable.tsx

Lines changed: 31 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@ import {
5656
TruncatedPopoverMode,
5757
Utils,
5858
} from "@blueprintjs/table";
59+
import { type FocusedRegion, FocusMode } from "@blueprintjs/table/src/common/cellTypes";
5960
import type { ColumnIndices, RowIndices } from "@blueprintjs/table/src/common/grid";
6061

6162
import { DenseGridMutableStore } from "./denseGridMutableStore";
@@ -94,6 +95,8 @@ const REGION_CARDINALITIES: RegionCardinality[] = [
9495
RegionCardinality.FULL_TABLE,
9596
];
9697

98+
const FOCUS_MODES: Array<FocusMode | undefined> = [undefined, FocusMode.CELL, FocusMode.ROW];
99+
97100
const RENDER_MODES: RenderMode[] = [RenderMode.BATCH_ON_UPDATE, RenderMode.BATCH, RenderMode.NONE];
98101

99102
const SELECTION_MODES: SelectedRegionTransformPreset[] = [
@@ -243,6 +246,7 @@ export interface MutableTableState {
243246
enableRowSelection?: boolean;
244247
enableSlowLayout?: boolean;
245248
enableScrollingApi?: boolean;
249+
focusMode?: FocusMode;
246250
numCols?: number;
247251
numFrozenCols?: number;
248252
numFrozenRows?: number;
@@ -259,7 +263,6 @@ export interface MutableTableState {
259263
showColumnHeadersLoading?: boolean;
260264
showColumnMenus?: boolean;
261265
showCustomRegions?: boolean;
262-
showFocusCell?: boolean;
263266
showGhostCells?: boolean;
264267
showInline?: boolean;
265268
showRowHeadersLoading?: boolean;
@@ -308,7 +311,6 @@ const DEFAULT_STATE: MutableTableState = {
308311
showColumnHeadersLoading: false,
309312
showColumnMenus: false,
310313
showCustomRegions: false,
311-
showFocusCell: false,
312314
showGhostCells: true,
313315
showInline: false,
314316
showRowHeadersLoading: false,
@@ -459,12 +461,12 @@ export class MutableTable extends React.Component<{}, MutableTableState> {
459461
enableColumnInteractionBar={this.state.showTableInteractionBar}
460462
enableColumnReordering={this.state.enableColumnReordering}
461463
enableColumnResizing={this.state.enableColumnResizing}
462-
enableFocusedCell={this.state.showFocusCell}
463464
enableGhostCells={this.state.showGhostCells}
464465
enableMultipleSelection={this.state.enableMultiSelection}
465466
enableRowHeader={this.state.enableRowHeader}
466467
enableRowReordering={this.state.enableRowReordering}
467468
enableRowResizing={this.state.enableRowResizing}
469+
focusMode={this.state.focusMode}
468470
getCellClipboardData={this.getCellValue}
469471
loadingOptions={this.getEnabledLoadingOptions()}
470472
numFrozenColumns={this.state.numFrozenCols}
@@ -475,6 +477,7 @@ export class MutableTable extends React.Component<{}, MutableTableState> {
475477
onCompleteRender={this.onCompleteRender}
476478
onCopy={this.onCopy}
477479
onFocusedCell={this.onFocus}
480+
onFocusedRegion={this.onFocusRegion}
478481
onRowHeightChanged={this.onRowHeightChanged}
479482
onRowsReordered={this.onRowsReordered}
480483
onSelection={this.onSelection}
@@ -679,6 +682,13 @@ export class MutableTable extends React.Component<{}, MutableTableState> {
679682
};
680683

681684
private renderSidebar() {
685+
const focusModeMenu = this.renderSelectMenu(
686+
"Focus mode",
687+
"focusMode",
688+
FOCUS_MODES,
689+
toFocusModeLabel,
690+
this.handleStringStateChange,
691+
);
682692
const renderModeMenu = this.renderSelectMenu(
683693
"Render mode",
684694
"renderMode",
@@ -732,7 +742,7 @@ export class MutableTable extends React.Component<{}, MutableTableState> {
732742
<H4>Table</H4>
733743
<H6>Display</H6>
734744
{this.renderSwitch("Inline", "showInline")}
735-
{this.renderSwitch("Focus cell", "showFocusCell")}
745+
{focusModeMenu}
736746
{this.renderSwitch("Ghost cells", "showGhostCells")}
737747
{renderModeMenu}
738748
{this.renderSwitch("Interaction bar", "showTableInteractionBar")}
@@ -903,10 +913,10 @@ export class MutableTable extends React.Component<{}, MutableTableState> {
903913
const isDisabled = !this.isPrereqStateKeySatisfied(prereqStateKey, prereqStateKeyValue);
904914

905915
// need to explicitly cast generic type T to string
906-
const selectedValue = this.state[stateKey].toString();
916+
const selectedValue = this.state[stateKey]?.toString();
907917
const options = values.map(value => {
908918
return (
909-
<option key={value.toString()} value={value.toString()}>
919+
<option key={value?.toString()} value={value?.toString()}>
910920
{generateValueLabel(value)}
911921
</option>
912922
);
@@ -984,6 +994,10 @@ export class MutableTable extends React.Component<{}, MutableTableState> {
984994
this.maybeLogCallback("[onFocusedCell] focusedCell =", focusedCell);
985995
};
986996

997+
private onFocusRegion = (focusedRegion: FocusedRegion) => {
998+
this.maybeLogCallback("[onFocusedRegion] focusedRegion =", focusedRegion);
999+
};
1000+
9871001
private onCopy = (success: boolean) => {
9881002
this.maybeLogCallback(`[onCopy] success = ${success}`);
9891003
};
@@ -1189,6 +1203,17 @@ export class MutableTable extends React.Component<{}, MutableTableState> {
11891203
// Select menu - label generators
11901204
// ==============================
11911205

1206+
function toFocusModeLabel(focusMode: FocusMode | undefined) {
1207+
switch (focusMode) {
1208+
case FocusMode.CELL:
1209+
return "Cells";
1210+
case FocusMode.ROW:
1211+
return "Rows";
1212+
case undefined:
1213+
return "None";
1214+
}
1215+
}
1216+
11921217
function toRenderModeLabel(renderMode: RenderMode) {
11931218
switch (renderMode) {
11941219
case RenderMode.BATCH:

packages/table/src/common/cellTypes.ts

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,3 +22,20 @@ export interface CellCoordinates {
2222
export interface FocusedCellCoordinates extends CellCoordinates {
2323
focusSelectionIndex: number;
2424
}
25+
26+
export enum FocusMode {
27+
CELL = "cell",
28+
ROW = "row",
29+
}
30+
31+
export interface FocusedCell extends FocusedCellCoordinates {
32+
type: FocusMode.CELL;
33+
}
34+
35+
export interface FocusedRow {
36+
type: FocusMode.ROW;
37+
row: number;
38+
focusSelectionIndex: number;
39+
}
40+
41+
export type FocusedRegion = FocusedCell | FocusedRow;

0 commit comments

Comments
 (0)