Refactor the Histogram View (Bug352885)
[deliverable/tracecompass.git] / org.eclipse.linuxtools.lttng.ui / src / org / eclipse / linuxtools / lttng / ui / views / histogram / HistogramView.java
CommitLineData
6e512b93 1/*******************************************************************************
c392540b 2 * Copyright (c) 2009, 2010, 2011 Ericsson
6e512b93
ASL
3 *
4 * All rights reserved. This program and the accompanying materials are
5 * made available under the terms of the Eclipse Public License v1.0 which
6 * accompanies this distribution, and is available at
7 * http://www.eclipse.org/legal/epl-v10.html
8 *
9 * Contributors:
b59134e1 10 * William Bourque - Initial API and implementation
c392540b
FC
11 * Yuriy Vashchuk - GUI reorganisation, simplification and some related code improvements.
12 * Yuriy Vashchuk - Histograms optimisation.
13 * Yuriy Vashchuk - Histogram Canvas Heritage correction
14 * Francois Chouinard - Cleanup and refactoring
6e512b93 15 *******************************************************************************/
3e9fdb8b 16
6e512b93
ASL
17package org.eclipse.linuxtools.lttng.ui.views.histogram;
18
b59134e1 19import org.eclipse.linuxtools.lttng.event.LttngEvent;
b59134e1 20import org.eclipse.linuxtools.tmf.event.TmfTimeRange;
833a21aa 21import org.eclipse.linuxtools.tmf.event.TmfTimestamp;
b59134e1 22import org.eclipse.linuxtools.tmf.experiment.TmfExperiment;
550d787e 23import org.eclipse.linuxtools.tmf.request.ITmfDataRequest.ExecutionType;
ff4ed569 24import org.eclipse.linuxtools.tmf.signal.TmfExperimentSelectedSignal;
ed4b3b9f 25import org.eclipse.linuxtools.tmf.signal.TmfRangeSynchSignal;
b59134e1 26import org.eclipse.linuxtools.tmf.signal.TmfSignalHandler;
c392540b 27import org.eclipse.linuxtools.tmf.signal.TmfSignalManager;
b59134e1 28import org.eclipse.linuxtools.tmf.signal.TmfTimeSynchSignal;
550d787e 29import org.eclipse.linuxtools.tmf.trace.ITmfTrace;
b59134e1
WB
30import org.eclipse.linuxtools.tmf.ui.views.TmfView;
31import org.eclipse.swt.SWT;
32import org.eclipse.swt.layout.GridData;
252ae4bd 33import org.eclipse.swt.layout.GridLayout;
6e512b93 34import org.eclipse.swt.widgets.Composite;
6e512b93 35
544fe9b7
WB
36/**
37 * <b><u>HistogramView</u></b>
38 * <p>
c392540b
FC
39 * The purpose of this view is to provide graphical time distribution statistics
40 * about the experiment/trace events.
544fe9b7 41 * <p>
c392540b
FC
42 * The view is composed of two histograms and two controls:
43 * <ul>
44 * <li>an event distribution histogram for the whole experiment;
45 * <li>an event distribution histogram for current time window (window span);
46 * <li>the timestamp of the currently selected event;
47 * <li>the window span (size of the time window of the smaller histogram).
48 * </ul>
49 * The histograms x-axis show their respective time range.
544fe9b7 50 */
c392540b
FC
51public class HistogramView extends TmfView {
52
53 // ------------------------------------------------------------------------
54 // Constants
55 // ------------------------------------------------------------------------
56
57 // The view ID as defined in plugin.xml
3b38ea61 58 public static final String ID = "org.eclipse.linuxtools.lttng.ui.views.histogram"; //$NON-NLS-1$
c392540b
FC
59
60 // The initial window span (in nanoseconds)
61 public static long INITIAL_WINDOW_SPAN = (1L * 100 * 1000 * 1000); // .1sec
62
63 // Time scale
64 private final byte TIME_SCALE = Histogram.TIME_SCALE;
65
66 // ------------------------------------------------------------------------
67 // Attributes
68 // ------------------------------------------------------------------------
69
70 // Parent widget
71 private Composite fParent;
72
73 // The current experiment
74 private TmfExperiment<LttngEvent> fCurrentExperiment;
75
76 // Current timestamp/time window
77 private long fExperimentStartTime;
78 private long fExperimentEndTime;
79 private long fWindowStartTime;
80 private long fWindowEndTime;
81 private long fWindowSpan = INITIAL_WINDOW_SPAN;
82 private long fCurrentTimestamp;
83
84 // Time controls
85 private HistogramTextControl fCurrentEventTimeControl;
86 private HistogramTextControl fTimeSpanControl;
87
88 // Histogram/request for the full trace range
89 private static FullTraceHistogram fFullTraceHistogram;
90 private HistogramRequest fFullTraceRequest;
91
92 // Histogram/request for the selected time range
93 private static TimeRangeHistogram fTimeRangeHistogram;
94 private HistogramRequest fTimeRangeRequest;
95
96 // ------------------------------------------------------------------------
97 // Constructor
98 // ------------------------------------------------------------------------
99
100 public HistogramView() {
101 super(ID);
102 }
103
104 public void dispose() {
105 fFullTraceHistogram.dispose();
106 fTimeRangeHistogram.dispose();
107 }
108
109 // ------------------------------------------------------------------------
110 // TmfView
111 // ------------------------------------------------------------------------
112
113 @Override
b59134e1 114 @SuppressWarnings("unchecked")
c392540b
FC
115 public void createPartControl(Composite parent) {
116
117 fParent = parent;
118
119 // Control labels
120 final String currentEventLabel = Messages.HistogramView_currentEventLabel;
121 final String windowSpanLabel = Messages.HistogramView_windowSpanLabel;
122
123 // --------------------------------------------------------------------
124 // Set the HistogramView layout
125 // --------------------------------------------------------------------
126
127 Composite viewComposite = new Composite(fParent, SWT.FILL);
128 GridLayout gridLayout = new GridLayout();
129 gridLayout.numColumns = 2;
130 gridLayout.horizontalSpacing = 5;
131 gridLayout.verticalSpacing = 0;
132 gridLayout.marginHeight = 0;
133 gridLayout.marginWidth = 0;
134 viewComposite.setLayout(gridLayout);
135
136 // Use all available space
137 GridData gridData = new GridData();
138 gridData.horizontalAlignment = SWT.FILL;
139 gridData.verticalAlignment = SWT.FILL;
140 gridData.grabExcessHorizontalSpace = true;
141 viewComposite.setLayoutData(gridData);
142
143 // --------------------------------------------------------------------
144 // Time controls
145 // --------------------------------------------------------------------
146
147 Composite controlsComposite = new Composite(viewComposite, SWT.FILL);
148 gridLayout = new GridLayout();
149 gridLayout.numColumns = 2;
150 gridLayout.marginHeight = 0;
151 gridLayout.marginWidth = 0;
152 gridLayout.horizontalSpacing = 5;
153 gridLayout.verticalSpacing = 0;
154 gridLayout.makeColumnsEqualWidth = true;
155 gridLayout.marginLeft = 5;
156 gridLayout.marginRight = 5;
157 controlsComposite.setLayout(gridLayout);
158
159 // Current event time control
160 gridData = new GridData();
161 gridData.horizontalAlignment = SWT.CENTER;
162 gridData.verticalAlignment = SWT.CENTER;
163 fCurrentEventTimeControl = new HistogramCurrentTimeControl(this, controlsComposite, SWT.BORDER, SWT.BORDER, currentEventLabel,
164 HistogramUtils.nanosecondsToString(0L));
165 fCurrentEventTimeControl.setLayoutData(gridData);
166
167 // Window span time control
168 gridData = new GridData();
169 gridData.horizontalAlignment = SWT.CENTER;
170 gridData.verticalAlignment = SWT.CENTER;
171 fTimeSpanControl = new HistogramTimeRangeControl(this, controlsComposite, SWT.BORDER, SWT.BORDER, windowSpanLabel,
172 HistogramUtils.nanosecondsToString(0L));
173 fTimeSpanControl.setLayoutData(gridData);
174
175 // --------------------------------------------------------------------
176 // Time range histogram
177 // --------------------------------------------------------------------
178
179 Composite timeRangeComposite = new Composite(viewComposite, SWT.FILL);
180 gridLayout = new GridLayout();
181 gridLayout.numColumns = 1;
182 gridLayout.marginHeight = 0;
183 gridLayout.marginWidth = 0;
184 gridLayout.marginTop = 5;
185 gridLayout.horizontalSpacing = 0;
186 gridLayout.verticalSpacing = 0;
187 gridLayout.marginLeft = 5;
188 gridLayout.marginRight = 5;
189 timeRangeComposite.setLayout(gridLayout);
190
191 // Use remaining horizontal space
192 gridData = new GridData();
193 gridData.horizontalAlignment = SWT.FILL;
194 gridData.verticalAlignment = SWT.FILL;
195 gridData.grabExcessHorizontalSpace = true;
196 timeRangeComposite.setLayoutData(gridData);
197
198 // Histogram
199 fTimeRangeHistogram = new TimeRangeHistogram(this, timeRangeComposite);
200
201 // --------------------------------------------------------------------
202 // Full range histogram
203 // --------------------------------------------------------------------
204
205 Composite fullRangeComposite = new Composite(viewComposite, SWT.FILL);
206 gridLayout = new GridLayout();
207 gridLayout.numColumns = 1;
208 gridLayout.marginHeight = 0;
209 gridLayout.marginWidth = 0;
210 gridLayout.marginTop = 5;
211 gridLayout.horizontalSpacing = 0;
212 gridLayout.verticalSpacing = 0;
213 gridLayout.marginLeft = 5;
214 gridLayout.marginRight = 5;
215 fullRangeComposite.setLayout(gridLayout);
216
217 // Use remaining horizontal space
218 gridData = new GridData();
219 gridData.horizontalAlignment = SWT.FILL;
220 gridData.verticalAlignment = SWT.FILL;
221 gridData.horizontalSpan = 2;
222 gridData.grabExcessHorizontalSpace = true;
223 fullRangeComposite.setLayoutData(gridData);
224
225 // Histogram
226 fFullTraceHistogram = new FullTraceHistogram(this, fullRangeComposite);
227
228 // Load the experiment if present
229 fCurrentExperiment = (TmfExperiment<LttngEvent>) TmfExperiment.getCurrentExperiment();
230 if (fCurrentExperiment != null)
231 loadExperiment();
ecfd1d41 232 }
c392540b
FC
233
234 @Override
3e9fdb8b 235 @SuppressWarnings("unchecked")
c392540b
FC
236 public void setFocus() {
237 TmfExperiment<LttngEvent> experiment = (TmfExperiment<LttngEvent>) TmfExperiment.getCurrentExperiment();
238 if ((experiment != null) && (experiment != fCurrentExperiment)) {
239 fCurrentExperiment = experiment;
240 initializeHistograms();
241 }
242 fParent.redraw();
833a21aa 243 }
c392540b
FC
244
245 // ------------------------------------------------------------------------
246 // Accessors
247 // ------------------------------------------------------------------------
248
249 public TmfTimeRange getTimeRange() {
250 return new TmfTimeRange(new TmfTimestamp(fWindowStartTime, TIME_SCALE), new TmfTimestamp(fWindowEndTime, TIME_SCALE));
251 }
252
253 // ------------------------------------------------------------------------
254 // Operations
255 // ------------------------------------------------------------------------
256
257 public void updateCurrentEventTime(long newTime) {
258 if (fCurrentExperiment != null) {
259 TmfTimeRange timeRange = new TmfTimeRange(new TmfTimestamp(newTime, TIME_SCALE), TmfTimestamp.BigCrunch);
260 HistogramRequest request = new HistogramRequest(fTimeRangeHistogram, timeRange, 1, ExecutionType.FOREGROUND) {
261 @Override
262 public void handleData(LttngEvent event) {
263 if (event != null) {
264 TmfTimeSynchSignal signal = new TmfTimeSynchSignal(this, event.getTimestamp());
265 TmfSignalManager.dispatchSignal(signal);
266 }
267 }
268 };
269 fCurrentExperiment.sendRequest(request);
270 }
271 }
272
273 public void updateTimeRange(long startTime, long endTime) {
274 if (fCurrentExperiment != null) {
275 // Build the new time range; keep the current time
276 TmfTimeRange timeRange = new TmfTimeRange(new TmfTimestamp(startTime, TIME_SCALE), new TmfTimestamp(endTime, TIME_SCALE));
277 TmfTimestamp currentTime = new TmfTimestamp(fCurrentTimestamp, TIME_SCALE);
088c1d4e 278
c392540b
FC
279 fTimeSpanControl.setValue(endTime - startTime);
280
281 // Send the FW signal
282 TmfRangeSynchSignal signal = new TmfRangeSynchSignal(this, timeRange, currentTime);
283 TmfSignalManager.dispatchSignal(signal);
284 }
285 }
286
287 public synchronized void updateTimeRange(long newDuration) {
288 if (fCurrentExperiment != null) {
289 long delta = newDuration - fWindowSpan;
290 long newStartTime = fWindowStartTime + delta / 2;
291 setNewRange(newStartTime, newDuration);
292 }
293 }
294
295 private void setNewRange(long startTime, long duration) {
296 if (startTime < fExperimentStartTime)
297 startTime = fExperimentStartTime;
298
299 long endTime = startTime + duration;
300 if (endTime > fExperimentEndTime) {
301 endTime = fExperimentEndTime;
302 if (endTime - duration > fExperimentStartTime)
303 startTime = endTime - duration;
304 else {
305 startTime = fExperimentStartTime;
306 }
307 }
308 updateTimeRange(startTime, endTime);
833a21aa 309 }
c392540b
FC
310
311 // ------------------------------------------------------------------------
312 // Signal handlers
313 // ------------------------------------------------------------------------
314
1406f802 315 @TmfSignalHandler
c392540b
FC
316 @SuppressWarnings("unchecked")
317 public void experimentSelected(TmfExperimentSelectedSignal<LttngEvent> signal) {
318 assert (signal != null);
319 fCurrentExperiment = (TmfExperiment<LttngEvent>) signal.getExperiment();
320 loadExperiment();
ecfd1d41 321 }
550d787e 322
c392540b
FC
323 private void loadExperiment() {
324 fExperimentStartTime = fCurrentExperiment.getStartTime().getValue();
325 fExperimentEndTime = fCurrentExperiment.getEndTime().getValue();
326 fCurrentTimestamp = fExperimentStartTime;
327 initializeHistograms();
328 fParent.redraw();
550d787e
FC
329 }
330
c392540b
FC
331// @TmfSignalHandler
332// @SuppressWarnings("unchecked")
333// public void experimentUpdated(TmfExperimentUpdatedSignal signal) {
334// fCurrentExperiment = (TmfExperiment<LttngEvent>) signal.getExperiment();
335// fFullRangeHistogramCanvas.redraw();
336// fTimespanHistogramCanvas.redraw();
337// createCanvasAndRequests();
338// }
339
340 @TmfSignalHandler
341 public void currentTimeUpdated(TmfTimeSynchSignal signal) {
342 // Because this can't happen :-)
343 assert (signal != null);
344
345 // Update the selected event time
346 TmfTimestamp currentTime = signal.getCurrentTime();
347 fCurrentTimestamp = currentTime.getValue();
348
349 // Notify the relevant widgets
350 fFullTraceHistogram.setCurrentEvent(fCurrentTimestamp);
351 fTimeRangeHistogram.setCurrentEvent(fCurrentTimestamp);
352 fCurrentEventTimeControl.setValue(fCurrentTimestamp);
ecfd1d41 353 }
f05aabed 354
c392540b
FC
355 @TmfSignalHandler
356 public void timeRangeUpdated(TmfRangeSynchSignal signal) {
357 // Because this can't happen :-)
358 assert (signal != null);
359
360 if (fCurrentExperiment != null) {
361 // Update the time range
362 fWindowStartTime = signal.getCurrentRange().getStartTime().getValue();
363 fWindowEndTime = signal.getCurrentRange().getEndTime().getValue();
364 fWindowSpan = fWindowEndTime - fWindowStartTime;
365
366 // Notify the relevant widgets
367 sendTimeRangeRequest(fWindowStartTime, fWindowEndTime);
368 fFullTraceHistogram.setTimeRange(fWindowStartTime, fWindowSpan);
369 fTimeSpanControl.setValue(fWindowSpan);
370 }
b59134e1 371 }
c392540b
FC
372
373 // ------------------------------------------------------------------------
374 // Helper functions
375 // ------------------------------------------------------------------------
376
377 private void initializeHistograms() {
378 updateExperimentTimeRange(fCurrentExperiment);
379 fTimeRangeHistogram.setFullRange(fExperimentStartTime, fExperimentEndTime);
380 fTimeRangeHistogram.setTimeRange(fExperimentStartTime, INITIAL_WINDOW_SPAN);
381 fTimeRangeHistogram.setCurrentEvent(fExperimentStartTime);
382
383 fFullTraceHistogram.setTimeRange(fExperimentStartTime, INITIAL_WINDOW_SPAN);
384 fFullTraceHistogram.setCurrentEvent(fExperimentStartTime);
385
386 fWindowStartTime = fExperimentStartTime;
387 fWindowSpan = INITIAL_WINDOW_SPAN;
388 fWindowEndTime = fWindowStartTime + fWindowSpan;
544fe9b7 389
c392540b
FC
390 fCurrentEventTimeControl.setValue(fExperimentStartTime);
391 fTimeSpanControl.setValue(fWindowSpan);
b59134e1 392
c392540b
FC
393 sendTimeRangeRequest(fExperimentStartTime, fExperimentStartTime + fWindowSpan);
394 sendFullRangeRequest();
b59134e1 395 }
c392540b
FC
396
397 private void sendTimeRangeRequest(long startTime, long endTime) {
398 if (fTimeRangeRequest != null && !fTimeRangeRequest.isCompleted()) {
399 fTimeRangeRequest.cancel();
088c1d4e 400 }
c392540b
FC
401 TmfTimestamp startTS = new TmfTimestamp(startTime, TIME_SCALE);
402 TmfTimestamp endTS = new TmfTimestamp(endTime, TIME_SCALE);
403 TmfTimeRange timeRange = new TmfTimeRange(startTS, endTS);
404
405 fTimeRangeHistogram.clear();
406 fTimeRangeHistogram.setTimeRange(startTime, endTime - startTime);
407 fTimeRangeRequest = new HistogramRequest(fTimeRangeHistogram, timeRange, ExecutionType.FOREGROUND);
408 fCurrentExperiment.sendRequest(fTimeRangeRequest);
088c1d4e 409 }
c392540b
FC
410
411 private void sendFullRangeRequest() {
412 if (fFullTraceRequest != null && !fFullTraceRequest.isCompleted()) {
413 fFullTraceRequest.cancel();
414 }
415 fFullTraceHistogram.clear();
416 TmfTimeRange timeRange = updateExperimentTimeRange(fCurrentExperiment);
417 fFullTraceRequest = new HistogramRequest(fFullTraceHistogram, timeRange, ExecutionType.BACKGROUND);
418 fCurrentExperiment.sendRequest(fFullTraceRequest);
ed4b3b9f 419 }
c392540b
FC
420
421 private TmfTimeRange updateExperimentTimeRange(TmfExperiment<LttngEvent> experiment) {
422 TmfTimestamp startTime = TmfTimestamp.BigCrunch;
423 TmfTimestamp endTime = TmfTimestamp.BigBang;
424 for (ITmfTrace trace : experiment.getTraces()) {
425 TmfTimestamp traceStartTime = trace.getStartTime();
426 if (traceStartTime.compareTo(startTime, true) < 0)
427 startTime = traceStartTime;
428 TmfTimestamp traceEndTime = trace.getEndTime();
429 if (traceEndTime.compareTo(endTime, true) > 0)
430 endTime = traceEndTime;
431 }
432 fExperimentStartTime = startTime.getValue();
433 fExperimentEndTime = endTime.getValue();
434
435 return new TmfTimeRange(startTime, endTime);
088c1d4e 436 }
f05aabed 437
6e512b93 438}
This page took 0.056512 seconds and 5 git commands to generate.