HEAD - Add Builds Comparison View
diff --git a/bundles/org.eclipse.test.performance.ui/icons/compare_view.gif b/bundles/org.eclipse.test.performance.ui/icons/compare_view.gif
new file mode 100644
index 0000000..dc549bc
--- /dev/null
+++ b/bundles/org.eclipse.test.performance.ui/icons/compare_view.gif
Binary files differ
diff --git a/bundles/org.eclipse.test.performance.ui/performanceui.jar b/bundles/org.eclipse.test.performance.ui/performanceui.jar
index 82efe4f..bb3394a 100644
--- a/bundles/org.eclipse.test.performance.ui/performanceui.jar
+++ b/bundles/org.eclipse.test.performance.ui/performanceui.jar
Binary files differ
diff --git a/bundles/org.eclipse.test.performance.ui/plugin.xml b/bundles/org.eclipse.test.performance.ui/plugin.xml
index 491cb79..04d80d3 100644
--- a/bundles/org.eclipse.test.performance.ui/plugin.xml
+++ b/bundles/org.eclipse.test.performance.ui/plugin.xml
@@ -49,6 +49,14 @@
name="Component Results"
restorable="true">
</view>
+ <view
+ category="Performances"
+ class="org.eclipse.test.internal.performance.results.ui.BuildsComparisonView"
+ icon="icons/compare_view.gif"
+ id="org.eclipse.test.internal.performance.results.ui.BuildsComparisonView"
+ name="Builds comparison"
+ restorable="true">
+ </view>
</extension>
<extension
point="org.eclipse.core.runtime.preferences">
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/model/PerformanceResultsElement.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/model/PerformanceResultsElement.java
index e8bb640..d4c108c 100644
--- a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/model/PerformanceResultsElement.java
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/model/PerformanceResultsElement.java
@@ -20,7 +20,7 @@
import java.util.Arrays;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.test.internal.performance.results.db.*;
-import org.eclipse.test.internal.performance.results.ui.ScenariosComparisonTable;
+import org.eclipse.test.internal.performance.results.ui.BuildsComparisonTable;
import org.eclipse.test.internal.performance.results.utils.IPerformancesConstants;
import org.eclipse.test.internal.performance.results.utils.Util;
import org.eclipse.test.performance.ui.Utils;
@@ -363,7 +363,7 @@
try {
int length = this.children.length;
for (int i=0; i<length; i++) {
- ScenariosComparisonTable table = new ScenariosComparisonTable(this.children[i].getName(), stream, build, reference);
+ BuildsComparisonTable table = new BuildsComparisonTable(this.children[i].getName(), stream, build, reference);
table.print(getPerformanceResults());
}
}
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonTab.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonTab.java
new file mode 100644
index 0000000..abcbcb1
--- /dev/null
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonTab.java
@@ -0,0 +1,506 @@
+/*******************************************************************************
+ * Copyright (c) 2000, 2009 IBM Corporation and others.
+ * 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
+ *
+ * Contributors:
+ * IBM Corporation - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.test.internal.performance.results.ui;
+
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import org.eclipse.core.runtime.preferences.IEclipsePreferences;
+import org.eclipse.core.runtime.preferences.InstanceScope;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.MouseEvent;
+import org.eclipse.swt.events.MouseTrackListener;
+import org.eclipse.swt.graphics.Color;
+import org.eclipse.swt.graphics.Font;
+import org.eclipse.swt.graphics.FontData;
+import org.eclipse.swt.graphics.GC;
+import org.eclipse.swt.graphics.Point;
+import org.eclipse.swt.graphics.Rectangle;
+import org.eclipse.swt.layout.GridData;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Display;
+import org.eclipse.swt.widgets.Shell;
+import org.eclipse.swt.widgets.Table;
+import org.eclipse.swt.widgets.TableColumn;
+import org.eclipse.swt.widgets.TableItem;
+import org.eclipse.swt.widgets.ToolTip;
+import org.eclipse.test.internal.performance.results.db.AbstractResults;
+import org.eclipse.test.internal.performance.results.db.BuildResults;
+import org.eclipse.test.internal.performance.results.db.ConfigResults;
+import org.eclipse.test.internal.performance.results.db.PerformanceResults;
+import org.eclipse.test.internal.performance.results.db.ScenarioResults;
+import org.eclipse.test.internal.performance.results.model.BuildResultsElement;
+import org.eclipse.test.internal.performance.results.model.PerformanceResultsElement;
+import org.eclipse.test.internal.performance.results.model.ResultsElement;
+import org.eclipse.test.internal.performance.results.utils.IPerformancesConstants;
+import org.eclipse.test.internal.performance.results.utils.Util;
+
+
+/**
+ * Tab to display all performances results numbers for a configuration (i.e a performance machine).
+ */
+public class BuildsComparisonTab {
+
+ // Colors
+ static final Display DEFAULT_DISPLAY = Display.getDefault();
+ static final Color BLUE= DEFAULT_DISPLAY.getSystemColor(SWT.COLOR_BLUE);
+ static final Color DARK_GREEN= DEFAULT_DISPLAY.getSystemColor(SWT.COLOR_DARK_GREEN);
+ static final Color GRAY = DEFAULT_DISPLAY.getSystemColor(SWT.COLOR_GRAY);
+ static final Color MAGENTA = DEFAULT_DISPLAY.getSystemColor(SWT.COLOR_MAGENTA);
+ static final Color RED = DEFAULT_DISPLAY.getSystemColor(SWT.COLOR_RED);
+
+ // SWT resources
+ Shell shell;
+ Display display;
+ Table table;
+ private GC gc;
+ private Color lightred;
+ private Color lightyellow;
+ private Color darkyellow;
+ private Color blueref;
+ private Font boldFont;
+ private Font italicFont;
+ private Font boldItalicFont;
+ Map toolTips;
+
+ // Information
+ String componentName;
+ double[][] allValues;
+ double[][] allErrors;
+
+ // Cells management
+ Point tableOrigin, tableSize;
+ int columnsCount, rowsCount;
+ List firstLine;
+
+ // Eclipse preferences
+ private IEclipsePreferences preferences;
+
+/*
+ * Default constructor.
+ */
+public BuildsComparisonTab(String name) {
+ this.componentName = name;
+ this.preferences = new InstanceScope().getNode(IPerformancesConstants.PLUGIN_ID);
+}
+
+/**
+ * Creates the tab folder page.
+ *
+ * @param tabFolder org.eclipse.swt.widgets.TabFolder
+ * @param fullSelection Tells whether the table should have a full line selection or not
+ * @return the new page for the tab folder
+ */
+Composite createTabFolderPage (BuildsComparisonView view) {
+ // Cache the shell and display.
+ this.shell = view.tabFolder.getShell();
+ this.display = this.shell.getDisplay();
+
+ // Remove old table if present
+ boolean initResources = this.table == null;
+ if (this.table != null) {
+ disposeTable();
+ }
+
+ // Create the "children" table
+ int style = SWT.MULTI | SWT.BORDER | SWT.H_SCROLL | SWT.V_SCROLL | SWT.FULL_SELECTION;
+ this.table = new Table(view.tabFolder, style);
+ this.table.setLinesVisible (true);
+ this.table.setHeaderVisible (true);
+ GridData gridData = new GridData(SWT.FILL, SWT.FILL, true, true, 3, 1);
+ gridData.heightHint = 150;
+ this.table.setLayoutData (gridData);
+ this.gc = new GC(this.table);
+
+ // Init resources
+ if (initResources) initResources();
+
+ // Add columns to the table
+ TableColumn firstColumn = new TableColumn(this.table, SWT.CENTER);
+ firstColumn.setText("");
+ PerformanceResultsElement results = view.getResults();
+ String [] configDescriptions = results.getConfigDescriptions();
+ int length = configDescriptions.length;
+ for (int i = 0; i < length; i++) {
+ TableColumn column = new TableColumn(this.table, SWT.CENTER);
+ column.setText(configDescriptions[i]);
+ }
+
+ // Add lines to the table
+ this.toolTips = new HashMap();
+ boolean fingerprints = this.preferences.getBoolean(IPerformancesConstants.PRE_FILTER_ADVANCED_SCENARIOS, IPerformancesConstants.DEFAULT_FILTER_ADVANCED_SCENARIOS);
+ fillTable(results, view.currentBuild, view.referenceBuild, fingerprints);
+
+ // Updated columns
+ for (int i=0; i<=length; i++) {
+ TableColumn column = this.table.getColumn(i);
+ column.setWidth(i==0?120:100);
+ }
+
+ // Store table info
+ this.columnsCount = length;
+
+ // Listen to mouse track events to display the table cell corresponding tooltip.
+ MouseTrackListener mouseTrackListener = new MouseTrackListener() {
+ ToolTip currentTooltip;
+ public void mouseHover(MouseEvent e) {
+ if (this.currentTooltip != null) {
+ this.currentTooltip.setVisible(false);
+ this.currentTooltip = null;
+ }
+ Point cellPosition = currentCellPosition(e.x, e.y);
+ if (cellPosition != null) {
+ ToolTip tooltip = (ToolTip) BuildsComparisonTab.this.toolTips.get(cellPosition);
+ if (tooltip != null) {
+ Point location = BuildsComparisonTab.this.table.toDisplay(new Point(e.x, e.y));
+ tooltip.setLocation(location);
+ tooltip.setVisible(true);
+ this.currentTooltip = tooltip;
+ }
+ }
+ }
+ public void mouseEnter(MouseEvent e) {
+ }
+ public void mouseExit(MouseEvent e) {
+ }
+ };
+ this.table.addMouseTrackListener(mouseTrackListener);
+
+ // Select the first line by default (as this is the current build)
+ this.table.select(0);
+
+ // Return the built composite
+ return this.table;
+}
+
+/*
+ * Create and store a tooltip with the given information and at the given position.
+ */
+void createToolTip(String toolTipText, String toolTipMessage, int toolTipStyle, Point position) {
+ ToolTip toolTip = new ToolTip(this.table.getShell(), toolTipStyle);
+ toolTip.setAutoHide(true);
+ toolTip.setText(toolTipText);
+ toolTip.setMessage(/*"("+col+","+row+") "+*/toolTipMessage);
+ this.toolTips.put(position, toolTip);
+}
+
+/*
+ * Get the current cell position (column, row) from a point position.
+ */
+Point currentCellPosition(int x, int y) {
+
+ // Compute the origin of the visible area
+ if (this.tableOrigin == null) {
+ this.tableOrigin = new Point(0, this.table.getHeaderHeight());
+ }
+
+ // Increment width until over current y position
+ int height= this.tableOrigin.y;
+ int row = this.table.getTopIndex();
+ while (row<this.rowsCount && height<y) {
+ height += this.table.getItemHeight();
+ row++;
+ }
+ if (height < y) {
+ // return when position is over the last line
+ return null;
+ }
+ row--;
+
+ // Increment width until being over current x position
+ int col = 0;
+ TableItem tableItem = this.table.getItem(row);
+ Rectangle bounds = tableItem.getBounds(col);
+ while (col<this.columnsCount) {
+ int max = bounds.x + bounds.width + this.table.getGridLineWidth();
+ if (x <= max) break;
+ if (col == this.columnsCount) {
+ // return when position is over the last column
+ return null;
+ }
+ col++;
+ bounds = tableItem.getBounds(col);
+ }
+
+ // Return the found table cell position
+ return new Point(col, row);
+}
+
+/*
+ * Dispose all SWT resources.
+ */
+public void dispose() {
+ if (this.boldFont != null) {
+ this.boldFont.dispose();
+ }
+ if (this.italicFont != null) {
+ this.italicFont.dispose();
+ }
+ if (this.boldItalicFont != null) {
+ this.boldItalicFont.dispose();
+ }
+ if (this.darkyellow != null) {
+ this.darkyellow.dispose();
+ }
+ if (this.lightyellow != null) {
+ this.lightyellow.dispose();
+ }
+ if (this.lightred != null) {
+ this.lightred.dispose();
+ }
+ if (this.blueref != null) {
+ this.blueref.dispose();
+ }
+ disposeTable();
+}
+
+/*
+ * Dispose all SWT controls associated with the table.
+ */
+private void disposeTable() {
+ if (this.toolTips != null) {
+ Iterator cells = this.toolTips.keySet().iterator();
+ while (cells.hasNext()) {
+ ToolTip toolTip = (ToolTip) this.toolTips.get(cells.next());
+ toolTip.dispose();
+ }
+ }
+ this.table.dispose();
+ this.tableOrigin = null;
+ this.firstLine = null;
+}
+
+/*
+ * Fill the lines of the tables.
+ * Get all the information from the model which are returned in a list (lines) of lists (columns).
+ */
+private void fillTable(PerformanceResultsElement results, String currentBuild, String referenceBuild, boolean fingerprints) {
+
+ // Get all the scenario for the component
+ final PerformanceResults performanceResults = results.getPerformanceResults();
+ List scenarios = performanceResults.getComponentScenarios(this.componentName);
+ int size = scenarios.size();
+
+ // Get thresholds
+ int failurePref = this.preferences.getInt(IPerformancesConstants.PRE_COMPARISON_THRESHOLD_FAILURE, IPerformancesConstants.DEFAULT_COMPARISON_THRESHOLD_FAILURE);
+ int errorPref = this.preferences.getInt(IPerformancesConstants.PRE_COMPARISON_THRESHOLD_ERROR, IPerformancesConstants.DEFAULT_COMPARISON_THRESHOLD_ERROR);
+ int improvementPref = this.preferences.getInt(IPerformancesConstants.PRE_COMPARISON_THRESHOLD_IMPROVEMENT, IPerformancesConstants.DEFAULT_COMPARISON_THRESHOLD_IMPROVEMENT);
+ final double failureThreshold = -failurePref / 100.0;
+ final double errorThreshold = errorPref / 100.0;
+ final double improvementThreshold = improvementPref / 100.0;
+
+ // Build the map made of one line per scenario results
+ final String[] configs = performanceResults.getConfigNames(true/*sort*/);
+ for (int i=0; i<size; i++) {
+ ScenarioResults scenarioResults = (ScenarioResults) scenarios.get(i);
+ if (!scenarioResults.isValid()) continue;
+ final boolean fingerprint = scenarioResults.hasSummary();
+ if (!fingerprints || fingerprint) {
+
+ // The first column is the scenario name
+ String scenarioName = scenarioResults.getShortName();
+ TableItem item = new TableItem (this.table, SWT.NONE);
+ item.setText(scenarioName);
+
+ // Bold font and blue ref background color if this is a fingerprint test
+ Font italic;
+ if (fingerprint) {
+ item.setFont(0, this.boldFont);
+ item.setBackground(this.blueref);
+ italic = this.boldItalicFont;
+ } else {
+ italic = this.italicFont;
+ }
+
+ // Fill config columns
+ int length = configs.length;
+ for (int j=0; j<length; j++) {
+
+ // See whether there's available numbers
+ int col = j+1;
+ final ConfigResults configResults = scenarioResults.getConfigResults(configs[j]);
+ if (configResults == null || !configResults.isValid()) {
+ item.setText(col, "Invalid");
+ item.setForeground(col, GRAY);
+ item.setFont(col, italic);
+ continue;
+ }
+ final BuildResults buildResults = configResults.getBuildResults(currentBuild);
+ if (buildResults == null) {
+ item.setText(col, "Missing results");
+ item.setForeground(col, GRAY);
+ item.setFont(col, italic);
+ continue;
+ }
+ final BuildResults referenceResults = configResults.getBuildResults(referenceBuild);
+ if (referenceResults == null) {
+ item.setText(col, "Missing ref");
+ item.setForeground(col, GRAY);
+ item.setFont(col, italic);
+ continue;
+ }
+
+ // Get numbers and infos
+ double[] values = configResults.getNumbers(buildResults, referenceResults);
+
+ // Reset tooltip info
+ String toolTipText = null;
+ String toolTipMessage = null;
+ int toolTipStyle = SWT.BALLOON;
+
+ // Get values array
+ final double buildValue = values[AbstractResults.BUILD_VALUE_INDEX];
+ final double referenceValue = values[AbstractResults.BASELINE_VALUE_INDEX];
+ final double delta = values[AbstractResults.DELTA_VALUE_INDEX];
+ final double error = values[AbstractResults.DELTA_ERROR_INDEX];
+
+ // Set text with delta value
+ item.setText(col, Util.PERCENTAGE_FORMAT.format(delta));
+
+ // Compute the tooltip to display on the cell
+ if (error > errorThreshold) {
+ // error is over the threshold
+ item.setForeground(col, this.darkyellow);
+ toolTipText = "May be not reliable";
+ toolTipMessage = "The error on this result is "+Util.PERCENTAGE_FORMAT.format(error)+", hence it may be not reliable";
+ toolTipStyle |= SWT.ICON_WARNING;
+ }
+ if (delta < -0.1) {
+ // delta < -10%: failure shown by an red-cross icon + text in red
+ item.setImage(col, ResultsElement.ERROR_IMAGE);
+ }
+ if (delta < failureThreshold) {
+ // negative delta over the threshold shown in red
+ item.setForeground(col, RED);
+ } else if (delta > improvementThreshold) {
+ // positive delta over the threshold are shown in green
+ item.setForeground(col, DARK_GREEN);
+ }
+
+ // Moderate the status if the build value or the difference is small
+ if (buildValue < 100 || referenceValue < 100) {
+ if (toolTipText == null) {
+ toolTipText = "";
+ } else {
+ toolTipText += ", ";
+ }
+ toolTipText += "Small value";
+ if (toolTipMessage == null) {
+ toolTipMessage = "";
+ } else {
+ toolTipMessage += ".\n";
+ }
+ toolTipMessage += "This test has a small value ("+buildValue+"ms)";
+ toolTipStyle |= SWT.ICON_WARNING;
+ item.setImage(col, ResultsElement.WARN_IMAGE);
+ }
+
+ // Add information in tooltip when history shows big variation
+ double deviation = configResults.getStatistics(Util.BASELINE_BUILD_PREFIXES)[3];
+ if (deviation > 0.2) {
+ // deviation is over 20% over the entire history
+ if (toolTipText == null) {
+ toolTipText = "";
+ } else {
+ toolTipText += ", ";
+ }
+ toolTipText += "History shows erratic values";
+ if (toolTipMessage == null) {
+ toolTipMessage = "";
+ } else {
+ toolTipMessage += ".\n";
+ }
+ toolTipMessage += "The results history shows that the variation of its delta is over 20% ("+Util.PERCENTAGE_FORMAT.format(deviation)+"), hence its result is surely not reliable";
+ // set the text in italic
+ item.setFont(col, italic);
+ toolTipStyle |= SWT.ICON_INFORMATION;
+ } else if (deviation > 0.1) { // moderate the status when the test
+ // deviation is between 10% and 20% over the entire history
+ if (toolTipText == null) {
+ toolTipText = "";
+ } else {
+ toolTipText += ", ";
+ }
+ toolTipText += "History shows unstable values";
+ if (toolTipMessage == null) {
+ toolTipMessage = "";
+ } else {
+ toolTipMessage += ".\n";
+ }
+ toolTipMessage += "The results history shows that the variation of its delta is between 10% and 20% ("+Util.PERCENTAGE_FORMAT.format(deviation)+"), hence its result may not be really reliable";
+ // set the text in italic
+ item.setFont(col, italic);
+ if (toolTipStyle == SWT.BALLOON && delta >= -0.1) {
+ toolTipStyle |= SWT.ICON_INFORMATION;
+ } else {
+ // reduce icon severity from error to warning
+ toolTipStyle |= SWT.ICON_WARNING;
+ }
+ }
+
+ // Set tooltip
+ if (toolTipText != null) {
+ createToolTip(toolTipText, toolTipMessage, toolTipStyle, new Point(col, i));
+ }
+ }
+ }
+ }
+ this.rowsCount = size;
+}
+
+/*
+ * The tab text is the full machine name.
+ */
+public String getTabText() {
+ return Util.componentDisplayName(this.componentName);
+}
+
+/*
+ * Init the SWT resources
+ */
+private void initResources() {
+ // Fonts
+ String fontDataName = this.gc.getFont().getFontData()[0].toString();
+ FontData fdItalic = new FontData(fontDataName);
+ fdItalic.setStyle(SWT.ITALIC);
+ this.italicFont = new Font(this.display, fdItalic);
+ FontData fdBold = new FontData(fontDataName);
+ fdBold.setStyle(SWT.BOLD);
+ this.boldFont = new Font(this.display, fdBold);
+ FontData fdBoldItalic = new FontData(fontDataName);
+ fdBoldItalic.setStyle(SWT.BOLD | SWT.ITALIC);
+ this.boldItalicFont = new Font(this.display, fdBoldItalic);
+
+ // Colors
+ this.lightred = new Color(DEFAULT_DISPLAY, 220, 50, 50);
+ this.lightyellow = new Color(DEFAULT_DISPLAY, 255, 255, 160);
+ this.darkyellow = new Color(DEFAULT_DISPLAY, 160, 160, 0);
+ this.blueref = new Color(DEFAULT_DISPLAY, 200, 200, 255);
+}
+
+/*
+ * Select the line corresponding to the given build.
+ */
+void select(BuildResultsElement buildResultsElement) {
+ int count = this.table.getItemCount();
+ String buildName = buildResultsElement.getName();
+ TableItem[] items = this.table.getItems();
+ for (int i=0; i<count; i++) {
+ if (items[i].getText().endsWith(buildName)) {
+ this.table.deselect(this.table.getSelectionIndex());
+ this.table.select(i);
+ return;
+ }
+ }
+}
+}
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/ScenariosComparisonTable.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonTable.java
similarity index 97%
rename from bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/ScenariosComparisonTable.java
rename to bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonTable.java
index fcfb69c..440c052 100644
--- a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/ScenariosComparisonTable.java
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonTable.java
@@ -25,14 +25,14 @@
* This class is responsible to print html table with the difference between two
* builds for all the scenarios and the configuration of a specific component.
*/
-public class ScenariosComparisonTable {
+public class BuildsComparisonTable {
private static final double DEFAULT_FAILURE_THRESHOLD = PerformanceResults.DEFAULT_FAILURE_THRESHOLD / 100.0 / 2;
private String component;
private PrintStream stream;
String buildName, referenceName;
-public ScenariosComparisonTable(String name, PrintStream stream, String build, String reference) {
+public BuildsComparisonTable(String name, PrintStream stream, String build, String reference) {
this.component = name;
this.stream = stream;
this.buildName = build;
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonView.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonView.java
new file mode 100644
index 0000000..d27eaca
--- /dev/null
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsComparisonView.java
@@ -0,0 +1,345 @@
+/*******************************************************************************
+ * Copyright (c) 2000, 2009 IBM Corporation and others.
+ * 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
+ *
+ * Contributors:
+ * IBM Corporation - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.test.internal.performance.results.ui;
+
+import org.eclipse.core.runtime.preferences.IEclipsePreferences;
+import org.eclipse.core.runtime.preferences.IEclipsePreferences.IPreferenceChangeListener;
+import org.eclipse.core.runtime.preferences.IEclipsePreferences.PreferenceChangeEvent;
+import org.eclipse.core.runtime.preferences.InstanceScope;
+import org.eclipse.jface.action.Action;
+import org.eclipse.jface.action.IAction;
+import org.eclipse.jface.action.IMenuManager;
+import org.eclipse.jface.action.IToolBarManager;
+import org.eclipse.jface.action.MenuManager;
+import org.eclipse.jface.viewers.ISelectionChangedListener;
+import org.eclipse.jface.viewers.SelectionChangedEvent;
+import org.eclipse.jface.viewers.TreeSelection;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.custom.CTabFolder;
+import org.eclipse.swt.custom.CTabItem;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Display;
+import org.eclipse.swt.widgets.Table;
+import org.eclipse.test.internal.performance.results.model.BuildResultsElement;
+import org.eclipse.test.internal.performance.results.model.PerformanceResultsElement;
+import org.eclipse.test.internal.performance.results.utils.IPerformancesConstants;
+import org.eclipse.test.internal.performance.results.utils.Util;
+import org.eclipse.ui.IActionBars;
+import org.eclipse.ui.IMemento;
+import org.eclipse.ui.IViewSite;
+import org.eclipse.ui.PartInitException;
+import org.eclipse.ui.PlatformUI;
+import org.eclipse.ui.part.ViewPart;
+
+
+/**
+ * This view shows the difference between two selected builds.
+ * <p>
+ * Each component are shown in a separate tab.
+ * </p><p>
+ * The displayed results can be written in a file, either all component or only
+ * the current one.
+ * </p><p>
+ * It's also possible to filter the scenario to display only the fingerprint ones.
+ * <br>
+ * Note that this filter is synchronized with the one applied in the
+ * {@link ComponentsView Components view}.
+ * </p>
+ *
+ * @see ConfigTab Folder tab containing all the results for a configuration.
+ */
+public class BuildsComparisonView extends ViewPart implements ISelectionChangedListener, IPreferenceChangeListener {
+
+ // SWT resources
+ CTabFolder tabFolder;
+
+ // Model information
+ BuildsComparisonTab[] tabs;
+ PerformanceResultsElement results;
+
+ // Action
+ Action filterAdvancedScenarios;
+
+ // Views
+ BuildsView buildsView;
+ IMemento viewState;
+
+ // Eclipse preferences
+ IEclipsePreferences preferences;
+
+ // Comparison
+ String currentBuild;
+ String referenceBuild;
+
+/*
+ * Default constructor:
+ * - create the image descriptor
+ * - register the view as a properties listener
+ */
+public BuildsComparisonView() {
+ this.preferences = new InstanceScope().getNode(IPerformancesConstants.PLUGIN_ID);
+ this.preferences.addPreferenceChangeListener(this);
+ // TODO should be done only once!
+ Util.initMilestones(this.preferences);
+}
+
+/*
+ * Contribute the local tools bar and the pull-down menu to the action bars.
+ */
+void contributeToActionBars() {
+ IActionBars bars = getViewSite().getActionBars();
+ fillLocalPullDown(bars.getMenuManager());
+ fillLocalToolBar(bars.getToolBarManager());
+}
+
+/*
+ * (non-Javadoc)
+ * @see org.eclipse.ui.part.WorkbenchPart#createPartControl(org.eclipse.swt.widgets.Composite)
+ */
+public void createPartControl(Composite parent) {
+
+ // Create the tab folder
+ this.tabFolder = new CTabFolder(parent, SWT.BORDER);
+
+ // Add results view as listener to viewer selection changes
+ Display.getDefault().asyncExec(new Runnable() {
+ public void run() {
+ PerformancesView performancesView = (PerformancesView) PerformancesView.getWorkbenchView("org.eclipse.test.internal.performance.results.ui.ComponentsView");
+ if (performancesView != null) {
+ performancesView.viewer.addSelectionChangedListener(BuildsComparisonView.this);
+ }
+ }
+ });
+
+ // Set actions
+ PlatformUI.getWorkbench().getHelpSystem().setHelp(this.tabFolder, "org.eclipse.test.performance.ui.results");
+ makeActions();
+ contributeToActionBars();
+
+ // Restore state
+ restoreState();
+
+ // Create tabs
+ createTabs();
+
+ // Set selections (tab and line)
+ this.tabFolder.setSimple(false);
+}
+
+/*
+ * Create the tab folder pages. There's one tab per performance machine.
+ * The list of these machines is got from the DB_Results contants.
+ */
+void createTabs() {
+ if (this.currentBuild == null || this.referenceBuild == null) return;
+ PerformanceResultsElement performanceResultsElement = getBuildsView().results;
+ String[] components = performanceResultsElement.getComponents();
+ int length = components.length;
+ this.tabs = new BuildsComparisonTab[length];
+ for (int i=0; i<length; i++) {
+ this.tabs[i] = new BuildsComparisonTab(components[i]);
+ }
+ for (int i=0; i<this.tabs.length; i++) {
+ CTabItem item = new CTabItem (this.tabFolder, SWT.NONE);
+ item.setText (this.tabs[i].getTabText ());
+ item.setControl (this.tabs[i].createTabFolderPage(this));
+ item.setData (this.tabs[i]);
+ }
+ this.tabFolder.setSelection(0);
+}
+
+/*
+ * (non-Javadoc)
+ * @see org.eclipse.ui.part.WorkbenchPart#dispose()
+ */
+public void dispose() {
+ this.tabFolder.dispose();
+ int length = this.tabs==null ? 0 : this.tabs.length;
+ for (int i=0; i<length; i++) {
+ this.tabs[i].dispose();
+ }
+ super.dispose();
+}
+
+/*
+ * Fill the filters drop-down menu with:
+ * - filter nightly builds
+ * - filter non-milestone builds
+ * - filter non-fingerprint scenarios
+ */
+void fillFiltersDropDown(IMenuManager manager) {
+ manager.add(this.filterAdvancedScenarios);
+}
+
+/*
+ * Fill the local pull down menu.
+ */
+void fillLocalPullDown(IMenuManager manager) {
+ MenuManager filtersManager= new MenuManager("Filters");
+ fillFiltersDropDown(filtersManager);
+ manager.add(filtersManager);
+}
+
+/*
+ * Fill the local tool bar with:
+ * - change line selection display
+ */
+void fillLocalToolBar(IToolBarManager manager) {
+ //manager.add(this.fullLineSelection);
+}
+
+/*
+ * Return the components results view.
+ */
+PerformanceResultsElement getResults() {
+ if (this.results == null) {
+ this.results = getBuildsView().results;
+ }
+ return this.results;
+}
+
+/*
+ * Return the components results view.
+ */
+BuildsView getBuildsView() {
+ if (this.buildsView == null) {
+ this.buildsView = (BuildsView) PerformancesView.getWorkbenchView("org.eclipse.test.internal.performance.results.ui.BuildsView");
+ }
+ return this.buildsView;
+}
+
+/*
+ * (non-Javadoc)
+ * @see org.eclipse.ui.part.ViewPart#init(org.eclipse.ui.IViewSite, org.eclipse.ui.IMemento)
+ */
+public void init(IViewSite site, IMemento memento) throws PartInitException {
+ super.init(site, memento);
+ this.viewState = memento;
+}
+
+/*
+ * Make the actions of the view:
+ * - change table line selection display
+ * - filter nightly builds
+ * - filter non-milestone builds
+ * - filter non-fingerprint scenarios
+ */
+void makeActions() {
+
+ // Filter non-fingerprints action
+ this.filterAdvancedScenarios = new Action("Advanced &Scenarios", IAction.AS_CHECK_BOX) {
+ public void run() {
+ BuildsComparisonView.this.preferences.putBoolean(IPerformancesConstants.PRE_FILTER_ADVANCED_SCENARIOS, isChecked());
+ resetTabFolders(false/*refresh*/);
+ }
+ };
+ this.filterAdvancedScenarios.setChecked(true);
+ this.filterAdvancedScenarios.setToolTipText("Filter advanced scenarios (i.e. not fingerprint ones)");
+}
+
+/* (non-Javadoc)
+ * @see org.eclipse.core.runtime.preferences.IEclipsePreferences.IPreferenceChangeListener#preferenceChange(org.eclipse.core.runtime.preferences.IEclipsePreferences.PreferenceChangeEvent)
+ */
+public void preferenceChange(PreferenceChangeEvent event) {
+ String propertyName = event.getKey();
+ Object newValue = event.getNewValue();
+
+ // Filter non-fingerprints change
+ if (propertyName.equals(IPerformancesConstants.PRE_FILTER_ADVANCED_SCENARIOS)) {
+ boolean checked = newValue == null ? IPerformancesConstants.DEFAULT_FILTER_ADVANCED_SCENARIOS : "true".equals(newValue);
+ this.filterAdvancedScenarios.setChecked(checked);
+ resetTabFolders(false/*refresh*/);
+ }
+}
+
+/*
+ * Reset the table tab folders by re-create all the pages.
+ * Selections are set onto the first found error if this is the first tab creation (typically on a component change event from the ComponentsView)
+ * or to the previous one if this is just a refresh.
+ */
+void resetTabFolders(boolean init) {
+
+ // Store current indexes
+ int tabIndex = this.tabFolder.getSelectionIndex();
+ int lineIndex = tabIndex<0 ? -1 : this.tabs[tabIndex].table.getSelectionIndex();
+
+ // Create tab folders
+ CTabItem[] tabItems = this.tabFolder.getItems();
+ int length = tabItems.length;
+ if (length == 0) {
+ createTabs();
+ } else {
+ for (int i=0; i<length; i++) {
+ tabItems[i].setControl(this.tabs [i].createTabFolderPage(this));
+ }
+ }
+
+ // Set part name
+ setPartName(this.currentBuild+" vs. "+this.referenceBuild);
+
+ // Set the selection
+ if (tabIndex >= 0 && lineIndex >= 0) {
+ this.tabFolder.setSelection(tabIndex);
+ Table table = this.tabs[tabIndex].table;
+ table.setSelection(lineIndex);
+ }
+}
+
+/*
+ * Restore the view state from the memento information.
+ */
+void restoreState() {
+
+ // Filter non fingerprints action state
+ boolean checked = this.preferences.getBoolean(IPerformancesConstants.PRE_FILTER_ADVANCED_SCENARIOS, IPerformancesConstants.DEFAULT_FILTER_ADVANCED_SCENARIOS);
+ this.filterAdvancedScenarios.setChecked(checked);
+}
+
+/*
+ * (non-Javadoc)
+ * @see org.eclipse.ui.part.ViewPart#saveState(org.eclipse.ui.IMemento)
+ */
+public void saveState(IMemento memento) {
+ super.saveState(memento);
+}
+
+/*
+ * (non-Javadoc)
+ * @see org.eclipse.jface.viewers.ISelectionChangedListener#selectionChanged(org.eclipse.jface.viewers.SelectionChangedEvent)
+ */
+public void selectionChanged(SelectionChangedEvent event) {
+ final Object[] selection = ((TreeSelection) event.getSelection()).toArray();
+ String firstBuildResults = null;
+ String secondBuildResults = null;
+ if (selection.length == 2) {
+ if (selection[0] instanceof BuildResultsElement) {
+ firstBuildResults = ((BuildResultsElement) selection[0]).getName();
+ }
+ if (selection[1] instanceof BuildResultsElement) {
+ secondBuildResults = ((BuildResultsElement) selection[1]).getName();
+ }
+ if (!firstBuildResults.equals(this.currentBuild) || !secondBuildResults.equals(this.referenceBuild)) {
+ this.currentBuild = firstBuildResults;
+ this.referenceBuild = secondBuildResults;
+ resetTabFolders(true);
+ }
+ }
+}
+
+/*
+ * (non-Javadoc)
+ * @see org.eclipse.ui.part.WorkbenchPart#setFocus()
+ */
+public void setFocus() {
+ // do nothing
+}
+
+}
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsView.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsView.java
index d703105..f6b9a99 100644
--- a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsView.java
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/BuildsView.java
@@ -27,6 +27,7 @@
import org.eclipse.jface.dialogs.ProgressMonitorDialog;
import org.eclipse.jface.operation.IRunnableWithProgress;
import org.eclipse.jface.resource.JFaceResources;
+import org.eclipse.jface.viewers.ISelectionChangedListener;
import org.eclipse.jface.viewers.IStructuredSelection;
import org.eclipse.jface.viewers.LabelProvider;
import org.eclipse.jface.viewers.SelectionChangedEvent;
@@ -38,6 +39,7 @@
import org.eclipse.swt.graphics.Font;
import org.eclipse.swt.graphics.FontData;
import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Display;
import org.eclipse.test.internal.performance.results.db.DB_Results;
import org.eclipse.test.internal.performance.results.model.BuildResultsElement;
import org.eclipse.test.internal.performance.results.model.ResultsElement;
@@ -274,6 +276,7 @@
// Views
PerformancesView componentsView;
+ BuildsComparisonView buildsComparisonView = null;
// Results model
BuildResultsElement[] buildsResults;
@@ -382,6 +385,16 @@
};
this.viewer.setSorter(nameSorter);
+ // Add results view as listener to viewer selection changes
+ Display.getDefault().asyncExec(new Runnable() {
+ public void run() {
+ ISelectionChangedListener listener = getComparisonView();
+ if (listener != null) {
+ BuildsView.this.viewer.addSelectionChangedListener(listener);
+ }
+ }
+ });
+
// Finalize viewer initialization
PlatformUI.getWorkbench().getHelpSystem().setHelp(this.viewer.getControl(), "org.eclipse.test.performance.ui.builds");
finalizeViewerCreation();
@@ -440,6 +453,16 @@
}
/*
+ * Return the components results view.
+ */
+BuildsComparisonView getComparisonView() {
+ if (this.buildsComparisonView == null) {
+ this.buildsComparisonView = (BuildsComparisonView) getWorkbenchView("org.eclipse.test.internal.performance.results.ui.BuildsComparisonView");
+ }
+ return this.buildsComparisonView;
+}
+
+/*
* Return the components view.
*/
PerformancesView getSiblingView() {
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/ComponentResultsView.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/ComponentResultsView.java
index 158361d..d166c3d 100644
--- a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/ComponentResultsView.java
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/ComponentResultsView.java
@@ -10,8 +10,6 @@
*******************************************************************************/
package org.eclipse.test.internal.performance.results.ui;
-import java.util.StringTokenizer;
-
import org.eclipse.core.runtime.preferences.IEclipsePreferences;
import org.eclipse.core.runtime.preferences.InstanceScope;
import org.eclipse.core.runtime.preferences.IEclipsePreferences.IPreferenceChangeListener;
@@ -81,9 +79,6 @@
*/
public class ComponentResultsView extends ViewPart implements ISelectionChangedListener, IPreferenceChangeListener {
- // Constants
- private static final String ORG_ECLIPSE = "org.eclipse.";
-
// SWT resources
CTabFolder tabFolder;
@@ -337,7 +332,7 @@
// Set the part name when possible
if (this.componentResultsElement != null) {
- setPartName();
+ setPartName(Util.componentDisplayName(this.componentResultsElement.getName()));
}
// If this is the first display then look for the first error to set the selection on it
@@ -486,7 +481,7 @@
* - org.eclipse.jdt.ui -> "JDT/UI"
* - org.eclipse.jdt.core -> "JDT/Core"
* - org.eclipse.pde.api.tools -> "PDE/API Tools"
- */
+ *
protected void setPartName() {
String componentName = this.componentResultsElement.getName();
String partName;
@@ -527,5 +522,6 @@
buffer.append("' results");
setPartName(buffer.toString());
}
+*/
}
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/PerformanceResultsPreferenceInitializer.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/PerformanceResultsPreferenceInitializer.java
index 4f27bfe..d40edc3 100644
--- a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/PerformanceResultsPreferenceInitializer.java
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/PerformanceResultsPreferenceInitializer.java
@@ -43,6 +43,11 @@
// Status
defaultPreferences.putInt(PRE_WRITE_STATUS, IPerformancesConstants.DEFAULT_WRITE_STATUS);
+ // Comparison
+ defaultPreferences.putInt(PRE_COMPARISON_THRESHOLD_FAILURE, IPerformancesConstants.DEFAULT_COMPARISON_THRESHOLD_FAILURE);
+ defaultPreferences.putInt(PRE_COMPARISON_THRESHOLD_ERROR, IPerformancesConstants.DEFAULT_COMPARISON_THRESHOLD_ERROR);
+ defaultPreferences.putInt(PRE_COMPARISON_THRESHOLD_IMPROVEMENT, IPerformancesConstants.DEFAULT_COMPARISON_THRESHOLD_IMPROVEMENT);
+
// Config descriptors
String[][] configDescriptors = PerformanceTestPlugin.getConfigDescriptors();
int cdLength = configDescriptors.length;
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/PerformanceResultsPreferencePage.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/PerformanceResultsPreferencePage.java
index d5c4b6b..459d1ed 100644
--- a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/PerformanceResultsPreferencePage.java
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/ui/PerformanceResultsPreferencePage.java
@@ -82,6 +82,9 @@
private Button statusStatisticErraticRadioButton;
private Button statusStatisticUnstableRadioButton;
private Text statusBuildsToConfirm;
+ private Text comparisonThresholdFailure;
+ private Text comparisonThresholdError;
+ private Text comparisonThresholdImprovement;
// TODO See whether config descriptors need to be set as preferences or not...
// private Table configDescriptorsTable;
@@ -221,6 +224,21 @@
this.statusBuildsToConfirm = createTextField(statusGroup);
this.statusBuildsToConfirm.setToolTipText("The number of previous builds to take into account to confirm a regression");
+ // Comparison
+ Composite compositeComparison = createComposite(parent, 1, 3);
+ Group comparisonGroup = createGroup(compositeComparison, "Comparison", 1);
+ Group thresholdsGroup = createGroup(comparisonGroup, "Thresholds", 6);
+// Composite compositeFailureThreshold = createComposite(comparisonGroup, 2, 2);
+ createLabel(thresholdsGroup, "Failure:", false);
+ this.comparisonThresholdFailure = createTextField(thresholdsGroup);
+ this.comparisonThresholdFailure.setToolTipText("The threshold in percentage to report a failure");
+ createLabel(thresholdsGroup, "Error:", false);
+ this.comparisonThresholdError = createTextField(thresholdsGroup);
+ this.comparisonThresholdError.setToolTipText("The threshold in percentage to report an error");
+ createLabel(thresholdsGroup, "Improvement:", false);
+ this.comparisonThresholdImprovement = createTextField(thresholdsGroup);
+ this.comparisonThresholdImprovement.setToolTipText("The threshold in percentage to report an improvement");
+
// Milestones
Composite compositeMilestones = createComposite(parent, 3, 1);
createLabel(compositeMilestones, "Milestones", false);
@@ -526,6 +544,11 @@
int writeStatus = store.getDefaultInt(PRE_WRITE_STATUS);
initStatusValues(writeStatus);
+ // Init comparison thresholds
+ this.comparisonThresholdFailure.setText(String.valueOf(store.getDefaultInt(PRE_COMPARISON_THRESHOLD_FAILURE)));
+ this.comparisonThresholdError.setText(String.valueOf(store.getDefaultInt(PRE_COMPARISON_THRESHOLD_ERROR)));
+ this.comparisonThresholdImprovement.setText(String.valueOf(store.getDefaultInt(PRE_COMPARISON_THRESHOLD_IMPROVEMENT)));
+
// Init eclipse version
this.mVersionRadioButton.setSelection(false);
this.dVersionRadionButton.setSelection(false);
@@ -596,6 +619,11 @@
int writeStatus = store.getInt(PRE_WRITE_STATUS);
initStatusValues(writeStatus);
+ // Init comparison thresholds
+ this.comparisonThresholdFailure.setText(String.valueOf(store.getInt(PRE_COMPARISON_THRESHOLD_FAILURE)));
+ this.comparisonThresholdError.setText(String.valueOf(store.getInt(PRE_COMPARISON_THRESHOLD_ERROR)));
+ this.comparisonThresholdImprovement.setText(String.valueOf(store.getInt(PRE_COMPARISON_THRESHOLD_IMPROVEMENT)));
+
// Init eclipse version
int version = store.getInt(PRE_ECLIPSE_VERSION);
if (version == ECLIPSE_MAINTENANCE_VERSION) {
@@ -1004,6 +1032,11 @@
writeStatus += Integer.parseInt(this.statusBuildsToConfirm.getText());
store.setValue(PRE_WRITE_STATUS, writeStatus);
+ // Init comparison thresholds
+ store.setValue(PRE_COMPARISON_THRESHOLD_FAILURE, Integer.parseInt(this.comparisonThresholdFailure.getText()));
+ store.setValue(PRE_COMPARISON_THRESHOLD_ERROR, Integer.parseInt(this.comparisonThresholdError.getText()));
+ store.setValue(PRE_COMPARISON_THRESHOLD_IMPROVEMENT, Integer.parseInt(this.comparisonThresholdImprovement.getText()));
+
// Set milestones
String prefix = PRE_MILESTONE_BUILDS + "." + version;
count = this.milestonesCombo.getItemCount();
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/utils/IPerformancesConstants.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/utils/IPerformancesConstants.java
index 0dc421b..b1bd2b1 100644
--- a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/utils/IPerformancesConstants.java
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/utils/IPerformancesConstants.java
@@ -76,6 +76,14 @@
public static final int STATUS_STATISTICS_MASK = 0xC000;
public static final int DEFAULT_WRITE_STATUS = STATUS_ERROR_NONE | DEFAULT_BUILDS_NUMBER;
+ // Comparison
+ public static final String PRE_COMPARISON_THRESHOLD_FAILURE = PREFIX + "comparison.threshold.failure"; //$NON-NLS-1$
+ public static final int DEFAULT_COMPARISON_THRESHOLD_FAILURE = 10;
+ public static final String PRE_COMPARISON_THRESHOLD_ERROR = PREFIX + "comparison.threshold.error"; //$NON-NLS-1$
+ public static final int DEFAULT_COMPARISON_THRESHOLD_ERROR = 3;
+ public static final String PRE_COMPARISON_THRESHOLD_IMPROVEMENT = PREFIX + "comparison.threshold.imporvement"; //$NON-NLS-1$
+ public static final int DEFAULT_COMPARISON_THRESHOLD_IMPROVEMENT = 10;
+
// Default milestones nowadays
public static final String[] V37_MILESTONES = new String[] {
};
diff --git a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/utils/Util.java b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/utils/Util.java
index 185b4d7..4bddd41 100644
--- a/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/utils/Util.java
+++ b/bundles/org.eclipse.test.performance.ui/src/org/eclipse/test/internal/performance/results/utils/Util.java
@@ -78,6 +78,9 @@
private static String[] MILESTONES;
public static final BuildDateComparator BUILD_DATE_COMPARATOR = new BuildDateComparator();
+ // Components constants
+ public static final String ORG_ECLIPSE = "org.eclipse.";
+
static class BuildDateComparator implements Comparator {
public int compare(Object o1, Object o2) {
String s1 = (String) o1;
@@ -120,6 +123,84 @@
public static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("yyyyMMddHHmm"); //$NON-NLS-1$
/**
+ * Return the name to display for the given component.
+ * <p>
+ * This name is built from the name of the component selected in the Components view.
+ * The rules to build the name are:
+ * <ol>
+ * <li>If the component name does not start with "org.eclipse" then the part name is just
+ * "<b>component name</b>"</li>
+ * <li>Otherwise, remove "org.eclipse." form the component name and count
+ * the tokens separated by a dot ('.')
+ * <ul>
+ * <li>If there's only one remaining token, then the part name is "<b>Platform/</b>"
+ * followed by:
+ * <ul>
+ * <li>"<b><i>TOKEN</i></b>" if token is less than 3 characters,</li>
+ * <li>"<b><i>Token</i></b>" otherwise</li>
+ * </ul>
+ * </li>
+ * <li>Otherwise then the part name is "<b><i>FIRST_TOKEN</i></b>" followed by:
+ * <ul>
+ * <li>for each followed additional token:
+ * <ul>
+ * <li>"<b><i>TOKEN</i></b>" if token is less than 3 characters,</li>
+ * <li>"<b><i>Token</i></b>" otherwise</li>
+ * </ul>
+ * </li>
+ * </ul>
+ * </li>
+ * </ul>
+ * </ol>
+ * E.g.
+ * - org.eclipse.ui -> "Platform/UI"
+ * - org.eclipse.swt -> "Platform/SWT"
+ * - org.eclipse.team -> "Platform/Team"
+ * - org.eclipse.jdt.ui -> "JDT/UI"
+ * - org.eclipse.jdt.core -> "JDT/Core"
+ * - org.eclipse.pde.api.tools -> "PDE/API Tools"
+ */
+public static String componentDisplayName(String componentName) {
+ String partName;
+ StringBuffer buffer = null;
+ if (componentName.startsWith(ORG_ECLIPSE)) {
+ partName = componentName.substring(ORG_ECLIPSE.length());
+ StringTokenizer tokenizer = new StringTokenizer(partName, ".");
+ while (tokenizer.hasMoreTokens()) {
+ String token = tokenizer.nextToken();
+ if (buffer == null) {
+ if (tokenizer.hasMoreTokens()) {
+ buffer = new StringBuffer("'"+token.toUpperCase());
+ buffer.append('/');
+ } else {
+ buffer = new StringBuffer("'Platform/");
+ if (token.length() > 3) {
+ buffer.append(Character.toUpperCase(token.charAt(0)));
+ buffer.append(token.substring(1));
+ } else {
+ buffer.append(token.toUpperCase());
+ }
+ }
+ } else {
+ if (token.length() > 3) {
+ buffer.append(Character.toUpperCase(token.charAt(0)));
+ buffer.append(token.substring(1));
+ } else {
+ buffer.append(token.toUpperCase());
+ }
+ if (tokenizer.hasMoreTokens()) buffer.append(' ');
+ }
+ }
+ } else {
+ buffer = new StringBuffer("'");
+ buffer.append(componentName);
+ buffer.append("'");
+ }
+ buffer.append("' results");
+ return buffer.toString();
+}
+
+/**
* Compute the student t-test values.
*
* @see "http://en.wikipedia.org/wiki/Student's_t-test"