linux.ui: Add context menu to Control Flow View to follow a thread
authorMatthew Khouzam <matthew.khouzam@ericsson.com>
Tue, 16 Feb 2016 03:42:04 +0000 (22:42 -0500)
committerMatthew Khouzam <matthew.khouzam@ericsson.com>
Wed, 16 Mar 2016 01:50:38 +0000 (21:50 -0400)
The command to follow a thread generates a TmfThreadSelectedSignal. To
see the context menu, one must right click on a thread entry in the control
flow view. More follow action locations can be:

 * the events table
 * the resources view, on an event
 * the filters view
 * the critical flow view

Change-Id: Ib74eb67f98c514f29fde689c47c2cb42c90868db
Signed-off-by: Matthew Khouzam <matthew.khouzam@ericsson.com>
Reviewed-on: https://git.eclipse.org/r/66665
Reviewed-by: Hudson CI
Reviewed-by: Genevieve Bastien <gbastien+lttng@versatic.net>
Tested-by: Genevieve Bastien <gbastien+lttng@versatic.net>
analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/analysis/os/linux/ui/views/controlflow/ControlFlowView.java
analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/FollowThreadAction.java [new file with mode: 0644]
analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/Messages.java [new file with mode: 0644]
analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/messages.properties [new file with mode: 0644]

index 714f9b8871edafc83623a816749a0ce91a1c504f..4394f46052c7a625cf4a65e33aa982ae31ca352e 100644 (file)
@@ -25,12 +25,21 @@ import org.eclipse.jdt.annotation.NonNull;
 import org.eclipse.jdt.annotation.Nullable;
 import org.eclipse.jface.action.IAction;
 import org.eclipse.jface.action.IToolBarManager;
+import org.eclipse.jface.action.MenuManager;
 import org.eclipse.jface.dialogs.IDialogSettings;
+import org.eclipse.jface.viewers.TreeViewer;
+import org.eclipse.swt.events.MenuDetectEvent;
+import org.eclipse.swt.events.MenuDetectListener;
+import org.eclipse.swt.graphics.Point;
 import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.swt.widgets.Menu;
+import org.eclipse.swt.widgets.TreeItem;
 import org.eclipse.tracecompass.analysis.os.linux.core.kernelanalysis.Attributes;
 import org.eclipse.tracecompass.analysis.os.linux.core.kernelanalysis.KernelAnalysisModule;
 import org.eclipse.tracecompass.internal.analysis.os.linux.ui.Activator;
 import org.eclipse.tracecompass.internal.analysis.os.linux.ui.Messages;
+import org.eclipse.tracecompass.internal.analysis.os.linux.ui.actions.FollowThreadAction;
 import org.eclipse.tracecompass.internal.analysis.os.linux.ui.views.controlflow.ControlFlowColumnComparators;
 import org.eclipse.tracecompass.statesystem.core.ITmfStateSystem;
 import org.eclipse.tracecompass.statesystem.core.exceptions.AttributeNotFoundException;
@@ -43,6 +52,7 @@ import org.eclipse.tracecompass.tmf.core.statesystem.TmfStateSystemAnalysisModul
 import org.eclipse.tracecompass.tmf.core.trace.ITmfTrace;
 import org.eclipse.tracecompass.tmf.core.trace.TmfTraceManager;
 import org.eclipse.tracecompass.tmf.ui.views.timegraph.AbstractStateSystemTimeGraphView;
+import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.TimeGraphCombo;
 import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.model.ILinkEvent;
 import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.model.ITimeEvent;
 import org.eclipse.tracecompass.tmf.ui.widgets.timegraph.model.ITimeGraphEntry;
@@ -99,14 +109,16 @@ public class ControlFlowView extends AbstractStateSystemTimeGraphView {
     static {
         ImmutableList.Builder<Comparator<ITimeGraphEntry>> builder = ImmutableList.builder();
         builder.add(ControlFlowColumnComparators.PROCESS_NAME_COLUMN_COMPARATOR)
-               .add(ControlFlowColumnComparators.TID_COLUMN_COMPARATOR)
-               .add(ControlFlowColumnComparators.PTID_COLUMN_COMPARATOR)
-               .add(ControlFlowColumnComparators.BIRTH_TIME_COLUMN_COMPARATOR)
-               .add(ControlFlowColumnComparators.TRACE_COLUMN_COMPARATOR);
+            .add(ControlFlowColumnComparators.TID_COLUMN_COMPARATOR)
+            .add(ControlFlowColumnComparators.PTID_COLUMN_COMPARATOR)
+            .add(ControlFlowColumnComparators.BIRTH_TIME_COLUMN_COMPARATOR)
+            .add(ControlFlowColumnComparators.TRACE_COLUMN_COMPARATOR);
         List<Comparator<ITimeGraphEntry>> l = builder.build();
         COLUMN_COMPARATORS = l.toArray(new Comparator[l.size()]);
     }
 
+    private MenuManager fMenuMgr;
+
     // ------------------------------------------------------------------------
     // Constructors
     // ------------------------------------------------------------------------
@@ -132,6 +144,32 @@ public class ControlFlowView extends AbstractStateSystemTimeGraphView {
         // add "Uncheck inactive" Button to TimeGraphFilterDialog
         super.getTimeGraphCombo().addTimeGraphFilterUncheckInactiveButton(
                 new ControlFlowCheckActiveProvider(Messages.ControlFlowView_uncheckInactiveLabel, Messages.ControlFlowView_uncheckInactiveToolTip));
+        createContextMenu();
+    }
+
+    private void createContextMenu() {
+        fMenuMgr = new MenuManager();
+        final TimeGraphCombo timeGraphCombo = getTimeGraphCombo();
+        TreeViewer treeViewer = timeGraphCombo.getTreeViewer();
+        Control control = treeViewer.getControl();
+        Menu menu = fMenuMgr.createContextMenu(control);
+        control.setMenu(menu);
+        control.addMenuDetectListener(new MenuDetectListener() {
+            @Override
+            public void menuDetected(MenuDetectEvent event) {
+                fMenuMgr.removeAll();
+                Point point = control.toControl(event.x, event.y);
+                // this is super important, it makes zoom still work. Do not try
+                // to extend to the time graph area.
+                TreeItem item = treeViewer.getTree().getItem(point);
+
+                if (item.getData() instanceof ControlFlowEntry) {
+                    ControlFlowEntry entry = (ControlFlowEntry) item.getData();
+                    fMenuMgr.add(new FollowThreadAction(ControlFlowView.this, entry.getName(), entry.getThreadId(), entry.getTrace()));
+                }
+            }
+        });
+
     }
 
     @Override
diff --git a/analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/FollowThreadAction.java b/analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/FollowThreadAction.java
new file mode 100644 (file)
index 0000000..692c242
--- /dev/null
@@ -0,0 +1,68 @@
+/*******************************************************************************
+ * Copyright (c) 2016 Ericsson
+ *
+ * All rights reserved. This program and the accompanying materials are
+ * made available under the terms of the Eclipse Public License v1.0 which
+ * accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *******************************************************************************/
+
+package org.eclipse.tracecompass.internal.analysis.os.linux.ui.actions;
+
+import org.eclipse.jdt.annotation.NonNullByDefault;
+import org.eclipse.jdt.annotation.Nullable;
+import org.eclipse.jface.action.Action;
+import org.eclipse.tracecompass.analysis.os.linux.core.signals.TmfThreadSelectedSignal;
+import org.eclipse.tracecompass.tmf.core.trace.ITmfTrace;
+import org.eclipse.tracecompass.tmf.ui.views.TmfView;
+
+/**
+ * Follow Thread Action, this action broadcasts a
+ * {@link TmfThreadSelectedSignal} when run, it sends a thread id and a trace to
+ * the signal.
+ *
+ * @author Matthew Khouzam
+ */
+@NonNullByDefault
+public class FollowThreadAction extends Action {
+
+    private final int fThreadId;
+    private final TmfView fView;
+    private final ITmfTrace fTrace;
+    private final @Nullable String fThreadName;
+
+    /**
+     * Constructor
+     *
+     * @param source
+     *            the view that is generating the signal, but also shall
+     *            broadcast it
+     * @param threadName
+     *            the thread name, can be null
+     * @param threadId
+     *            the thread id
+     * @param trace
+     *            the trace containing the thread
+     */
+    public FollowThreadAction(TmfView source, @Nullable String threadName, int threadId, ITmfTrace trace) {
+        fView = source;
+        fThreadName = threadName;
+        fThreadId = threadId;
+        fTrace = trace;
+    }
+
+    @Override
+    public String getText() {
+        if (fThreadName == null) {
+            return Messages.FollowThreadAction_follow + ' ' + fThreadId;
+        }
+        return Messages.FollowThreadAction_follow + ' ' + fThreadName + '/' + fThreadId;
+    }
+
+    @Override
+    public void run() {
+        fView.broadcast(new TmfThreadSelectedSignal(fView, fThreadId, fTrace));
+        super.run();
+    }
+
+}
diff --git a/analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/Messages.java b/analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/Messages.java
new file mode 100644 (file)
index 0000000..4a94972
--- /dev/null
@@ -0,0 +1,32 @@
+/*******************************************************************************
+ * Copyright (c) 2016 Ericsson
+ *
+ * All rights reserved. This program and the accompanying materials are
+ * made available under the terms of the Eclipse Public License v1.0 which
+ * accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *******************************************************************************/
+
+package org.eclipse.tracecompass.internal.analysis.os.linux.ui.actions;
+
+import org.eclipse.osgi.util.NLS;
+
+/**
+ * Action messages
+ *
+ * @author Matthew Khouzam
+ */
+public class Messages extends NLS {
+    private static final String BUNDLE_NAME = "org.eclipse.tracecompass.internal.analysis.os.linux.ui.actions.messages"; //$NON-NLS-1$
+    /**
+     * Follow message
+     */
+    public static String FollowThreadAction_follow;
+    static {
+        // initialize resource bundle
+        NLS.initializeMessages(BUNDLE_NAME, Messages.class);
+    }
+
+    private Messages() {
+    }
+}
diff --git a/analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/messages.properties b/analysis/org.eclipse.tracecompass.analysis.os.linux.ui/src/org/eclipse/tracecompass/internal/analysis/os/linux/ui/actions/messages.properties
new file mode 100644 (file)
index 0000000..be910b6
--- /dev/null
@@ -0,0 +1,10 @@
+###############################################################################
+# Copyright (c) 2016 Ericsson
+#
+# All rights reserved. This program and the accompanying materials
+# are made available under the terms of the Eclipse Public License v1.0
+# which accompanies this distribution, and is available at
+# http://www.eclipse.org/legal/epl-v10.html
+###############################################################################
+
+FollowThreadAction_follow=Follow
This page took 0.029238 seconds and 5 git commands to generate.