Add a context menu (right-click) that provides options for copying to clipboard, including, for trees, the ability to copy only the cell under the mouse pointer. Committer testing: $ python ~acme/libexec/perf-core/scripts/python/exported-sql-viewer.py ~/c/adrian.hunter/simple-retpoline.db Simply right click and pick "Copy selection", that at this point has just the first line, not expanded, then see what was copied by pressing shift+control+v on a terminal: Call Path,Object,Count,Time (ns),Time (%),Branch Count,Branch Count (%) ▶ simple-retpolin,,,,,, Ditto after expanding, i.e. the selection continues to be just one line: Call Path Object Count Time (ns) Time (%) Branch Count Branch Count (%) ▼ simple-retpolin Now select all the lines with the mouse and control+shift+v again: Call Path Object Count Time (ns) Time (%) Branch Count Branch Count (%) ▼ 14503:14503 ▼ _start ld-2.28.so 1 156267 100.0 10602 100.0 ▶ unknown unknown 1 2276 1.5 1 0.0 ▶ _dl_start ld-2.28.so 1 137047 87.7 10088 95.2 ▶ _dl_init ld-2.28.so 1 9142 5.9 326 3.1 ▼ _start simple-retpoline 1 7457 4.8 182 1.7 ▶ unknown unknown 1 805 10.8 1 0.5 ▶ __libc_start_main libc-2.28.so 1 6347 85.1 179 98.4
Showing the changes to tools/perf/scripts/python (1 of 1 file). Show all
Unified · Split
| @@ -887,6 +887,8 @@ class TreeWindowBase(QMdiSubWindow): · 886 unmodified lines | |||
| 887 | self.view.setSelectionMode(QAbstractItemView.ContiguousSelection) | 887 | self.view.setSelectionMode(QAbstractItemView.ContiguousSelection) |
| 888 | self.view.CopyCellsToClipboard = CopyTreeCellsToClipboard | 888 | self.view.CopyCellsToClipboard = CopyTreeCellsToClipboard |
| 889 | 889 | ||
| 890 | self.context_menu = TreeContextMenu(self.view) | ||
| 891 | |||
| 890 | def DisplayFound(self, ids): | 892 | def DisplayFound(self, ids): |
| 891 | if not len(ids): | 893 | if not len(ids): |
| 892 | return False | 894 | return False |
| @@ -1660,6 +1662,8 @@ class BranchWindow(QMdiSubWindow): · 767 unmodified lines | |||
| 1660 | 1662 | ||
| 1661 | self.ResizeColumnsToContents() | 1663 | self.ResizeColumnsToContents() |
| 1662 | 1664 | ||
| 1665 | self.context_menu = TreeContextMenu(self.view) | ||
| 1666 | |||
| 1663 | self.find_bar = FindBar(self, self, True) | 1667 | self.find_bar = FindBar(self, self, True) |
| 1664 | 1668 | ||
| 1665 | self.finder = ChildDataItemFinder(self.model.root) | 1669 | self.finder = ChildDataItemFinder(self.model.root) |
| @@ -2469,6 +2473,39 @@ def CopyCellsToClipboardHdr(view): · 803 unmodified lines | |||
| 2469 | def CopyCellsToClipboardCSV(view): | 2473 | def CopyCellsToClipboardCSV(view): |
| 2470 | CopyCellsToClipboard(view, True, True) | 2474 | CopyCellsToClipboard(view, True, True) |
| 2471 | 2475 | ||
| 2476 | # Context menu | ||
| 2477 | |||
| 2478 | class ContextMenu(object): | ||
| 2479 | |||
| 2480 | def __init__(self, view): | ||
| 2481 | self.view = view | ||
| 2482 | self.view.setContextMenuPolicy(Qt.CustomContextMenu) | ||
| 2483 | self.view.customContextMenuRequested.connect(self.ShowContextMenu) | ||
| 2484 | |||
| 2485 | def ShowContextMenu(self, pos): | ||
| 2486 | menu = QMenu(self.view) | ||
| 2487 | self.AddActions(menu) | ||
| 2488 | menu.exec_(self.view.mapToGlobal(pos)) | ||
| 2489 | |||
| 2490 | def AddCopy(self, menu): | ||
| 2491 | menu.addAction(CreateAction("&Copy selection", "Copy to clipboard", lambda: CopyCellsToClipboardHdr(self.view), self.view)) | ||
| 2492 | menu.addAction(CreateAction("Copy selection as CS&V", "Copy to clipboard as CSV", lambda: CopyCellsToClipboardCSV(self.view), self.view)) | ||
| 2493 | |||
| 2494 | def AddActions(self, menu): | ||
| 2495 | self.AddCopy(menu) | ||
| 2496 | |||
| 2497 | class TreeContextMenu(ContextMenu): | ||
| 2498 | |||
| 2499 | def __init__(self, view): | ||
| 2500 | super(TreeContextMenu, self).__init__(view) | ||
| 2501 | |||
| 2502 | def AddActions(self, menu): | ||
| 2503 | i = self.view.currentIndex() | ||
| 2504 | text = str(i.data()).strip() | ||
| 2505 | if len(text): | ||
| 2506 | menu.addAction(CreateAction('Copy "' + text + '"', "Copy to clipboard", lambda: QApplication.clipboard().setText(text), self.view)) | ||
| 2507 | self.AddCopy(menu) | ||
| 2508 | |||
| 2472 | # Table window | 2509 | # Table window |
| 2473 | 2510 | ||
| 2474 | class TableWindow(QMdiSubWindow, ResizeColumnsToContentsBase): | 2511 | class TableWindow(QMdiSubWindow, ResizeColumnsToContentsBase): |
| @@ -2492,6 +2529,8 @@ class TableWindow(QMdiSubWindow, ResizeColumnsToContentsBase): · 17 unmodified lines | |||
| 2492 | 2529 | ||
| 2493 | self.ResizeColumnsToContents() | 2530 | self.ResizeColumnsToContents() |
| 2494 | 2531 | ||
| 2532 | self.context_menu = ContextMenu(self.view) | ||
| 2533 | |||
| 2495 | self.find_bar = FindBar(self, self, True) | 2534 | self.find_bar = FindBar(self, self, True) |
| 2496 | 2535 | ||
| 2497 | self.finder = ChildDataItemFinder(self.data_model) | 2536 | self.finder = ChildDataItemFinder(self.data_model) |
| @@ -2608,6 +2647,8 @@ class TopCallsWindow(QMdiSubWindow, ResizeColumnsToContentsBase): · 110 unmodified lines | |||
| 2608 | self.view.setSelectionMode(QAbstractItemView.ContiguousSelection) | 2647 | self.view.setSelectionMode(QAbstractItemView.ContiguousSelection) |
| 2609 | self.view.CopyCellsToClipboard = CopyTableCellsToClipboard | 2648 | self.view.CopyCellsToClipboard = CopyTableCellsToClipboard |
| 2610 | 2649 | ||
| 2650 | self.context_menu = ContextMenu(self.view) | ||
| 2651 | |||
| 2611 | self.ResizeColumnsToContents() | 2652 | self.ResizeColumnsToContents() |
| 2612 | 2653 | ||
| 2613 | self.find_bar = FindBar(self, self, True) | 2654 | self.find_bar = FindBar(self, self, True) |