From 534315badf1160a66c3aa045a7f0c1093e46e06a Mon Sep 17 00:00:00 2001 From: Rodrigo Pinto Date: Fri, 6 May 2022 11:15:45 -0400 Subject: [PATCH 1/3] Select chart components from a selection in the events table Select corresponding chart components from the events table. Clicking on a line in the events table will cause a chart like "Thread Status" to scroll vertically to the row which has the element that corresponds to the clicked event. For each line in the timegraph tree, parse the metadata in the TimeGraphEntry received from the server and try to find matches with the key / values pairs of the clicked event. It will select the entry which has the most matches. When extending the selection, only the last selected event will be used to broadcast the selection (multi-line selection). This PR requires the following pull requests: https://git.eclipse.org/r/c/tracecompass.incubator/org.eclipse.tracecompass.incubator/+/193246 https://github.com/eclipse-cdt-cloud/tsp-typescript-client/pull/63 https://github.com/eclipse-cdt-cloud/timeline-chart/pull/204 The corresponding Trace Server Protocol (TSP) update: https://github.com/eclipse-cdt-cloud/trace-server-protocol/pull/83 Signed-off-by: Rodrigo Pinto Signed-off-by: Bernd Hufmann --- .../src/components/table-output-component.tsx | 14 +-- .../components/timegraph-output-component.tsx | 101 +++++++++++++++++- .../components/utils/filter-tree/utils.tsx | 5 + 3 files changed, 112 insertions(+), 8 deletions(-) diff --git a/packages/react-components/src/components/table-output-component.tsx b/packages/react-components/src/components/table-output-component.tsx index 670dc5fa6..936d8ffba 100644 --- a/packages/react-components/src/components/table-output-component.tsx +++ b/packages/react-components/src/components/table-output-component.tsx @@ -103,7 +103,7 @@ export class TableOutputComponent extends AbstractOutputComponentthis.checkFocus(event)} + onFocus={event => this.checkFocus(event)} className={this.props.backgroundTheme === 'light' ? 'ag-theme-balham' : 'ag-theme-balham-dark'} style={{ height: this.props.style.height, width: this.props.outputWidth }}> { @@ -65,6 +66,7 @@ export class TimegraphOutputComponent extends AbstractTreeOutputComponent this.doHandleSelectionChangedSignal(payload); + private pendingSelection: TimeGraphEntry | undefined; constructor(props: TimegraphOutputProps) { super(props); @@ -76,7 +78,8 @@ export class TimegraphOutputComponent extends AbstractTreeOutputComponent { + this.pendingSelection = undefined; if (model) { this.selectedElement = this.chartLayer.getStateById(model.id); } else { @@ -285,6 +289,19 @@ export class TimegraphOutputComponent extends AbstractTreeOutputComponent { + if (el.metadata) { + let cnt = 0; + Object.entries(el.metadata).forEach(([key, values]) => { + if (typeof (payload.load) !== 'string') { + const val = payload.load[key]; + if (val !== undefined) { + const num = Number(val); + // at least one value in array needs to match + const result = values.find((value: string | number) => (num !== undefined && num === value) || (val === value)); + if (result !== undefined) { + cnt++; + } + } + } + }); + if (cnt > max) { + max = cnt; + element = el; + } + } + }); + + } + return element; + } + private getMarkersLayerHeight() { const rowHeight = 20; const scrollbarHeight = 10; @@ -533,6 +592,14 @@ export class TimegraphOutputComponent extends AbstractTreeOutputComponent node.id === entry?.id); + if (foundNode) { + let parentId: number | undefined = foundNode.parentId; + const ids: number[] = []; + while (parentId && parentId >= 0) { + ids.push(parentId); + foundNode = this.state.timegraphTree.find(node => node.id === parentId); + parentId = foundNode?.parentId; + } + + let newList = [...this.state.collapsedNodes]; + ids.forEach(parentIds => { + const exist = this.state.collapsedNodes.find(expandId => expandId === parentIds); + if (exist !== undefined) { + newList = newList.filter(collapsed => parentIds !== collapsed); + } + }); + const retVal = newList.length === this.state.collapsedNodes.length; + this.setState({ collapsedNodes: newList }, this.updateTotalHeight); + return retVal; + } + } + + private selectAndReveal(item: TimeGraphEntry) { + const rowIndex = getIndexOfNode(item.id, listToTree(this.state.timegraphTree, this.state.columns), this.state.collapsedNodes); + this.chartLayer.selectAndReveal(rowIndex); + } + } diff --git a/packages/react-components/src/components/utils/filter-tree/utils.tsx b/packages/react-components/src/components/utils/filter-tree/utils.tsx index 348c13fad..30afdcfa1 100644 --- a/packages/react-components/src/components/utils/filter-tree/utils.tsx +++ b/packages/react-components/src/components/utils/filter-tree/utils.tsx @@ -57,3 +57,8 @@ export const getAllExpandedNodeIds = (nodes: TreeNode[],collapsedNodes: number[] }); return visibleIds; }; + +export const getIndexOfNode = (id: number, nodes: TreeNode[], collapsedNodes: number[]): number => { + const ids = getAllExpandedNodeIds(nodes, collapsedNodes); + return ids.findIndex(eId => eId === id); +}; From 6e0775b1f71d2a09996475ae3f74e378cc065a2e Mon Sep 17 00:00:00 2001 From: Bernd Hufmann Date: Mon, 6 Jun 2022 14:35:55 -0400 Subject: [PATCH 2/3] Select chart components when finding a matched event in events table When selecting an event using the search capability in the events table broadcast the event details to other charts to select corresponding chart component. Signed-off-by: Bernd Hufmann --- .../src/components/table-output-component.tsx | 28 +++++++++++++++---- 1 file changed, 22 insertions(+), 6 deletions(-) diff --git a/packages/react-components/src/components/table-output-component.tsx b/packages/react-components/src/components/table-output-component.tsx index 936d8ffba..41a37f6e1 100644 --- a/packages/react-components/src/components/table-output-component.tsx +++ b/packages/react-components/src/components/table-output-component.tsx @@ -617,9 +617,16 @@ export class TableOutputComponent extends AbstractOutputComponent= 0) { const data = await this.findMatchIndex(currRowIndex, direction); if (data !== undefined) { @@ -635,14 +644,21 @@ export class TableOutputComponent extends AbstractOutputComponent { + allCols.map(item => { if (item.field === column.field) { item.hide = columnApi.getColumn(column).isVisible(); } @@ -695,7 +711,7 @@ export class TableOutputComponent extends AbstractOutputComponent - +
{columns.map((column, key) => From a91db65ddbee8f6f3b4a91ecf4634465932f4f9d Mon Sep 17 00:00:00 2001 From: Bernd Hufmann Date: Mon, 6 Jun 2022 14:40:47 -0400 Subject: [PATCH 3/3] Select chart components when selecting an event with keyboard in table When using the keyboard to select an event, broadcast the event details to other charts to select corresponding chart component. Add support for arrow up/down key selection of events in the events table. When extending the selection, only the last selected event will be used to broadcast the selection (multi-line selection). Make sure that the properties view is updated with the last event selection. Signed-off-by: Bernd Hufmann --- .../src/components/table-output-component.tsx | 37 ++++++++++++++++--- 1 file changed, 31 insertions(+), 6 deletions(-) diff --git a/packages/react-components/src/components/table-output-component.tsx b/packages/react-components/src/components/table-output-component.tsx index 41a37f6e1..c4b63dfb5 100644 --- a/packages/react-components/src/components/table-output-component.tsx +++ b/packages/react-components/src/components/table-output-component.tsx @@ -221,6 +221,7 @@ export class TableOutputComponent extends AbstractOutputComponent