lttng: Add arrows in Control Flow view
[deliverable/tracecompass.git] / org.eclipse.linuxtools.tmf.ui / src / org / eclipse / linuxtools / tmf / ui / views / timegraph / AbstractTimeGraphView.java
1 /*******************************************************************************
2 * Copyright (c) 2012, 2013 Ericsson, École Polytechnique de Montréal
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:
10 * Patrick Tasse - Initial API and implementation
11 * Bernd Hufmann - Updated signal handling
12 * Geneviève Bastien - Move code to provide base classes for time graph view
13 * Marc-Andre Laperle - Add time zone preference
14 * Geneviève Bastien - Add event links between entries
15 *******************************************************************************/
16
17 package org.eclipse.linuxtools.tmf.ui.views.timegraph;
18
19 import java.util.ArrayList;
20 import java.util.Arrays;
21 import java.util.Collections;
22 import java.util.Comparator;
23 import java.util.HashMap;
24 import java.util.List;
25 import java.util.Map;
26
27 import org.eclipse.core.runtime.IProgressMonitor;
28 import org.eclipse.core.runtime.NullProgressMonitor;
29 import org.eclipse.jface.action.Action;
30 import org.eclipse.jface.action.IStatusLineManager;
31 import org.eclipse.jface.action.IToolBarManager;
32 import org.eclipse.jface.action.Separator;
33 import org.eclipse.jface.viewers.ILabelProviderListener;
34 import org.eclipse.jface.viewers.ITableLabelProvider;
35 import org.eclipse.jface.viewers.ITreeContentProvider;
36 import org.eclipse.jface.viewers.Viewer;
37 import org.eclipse.linuxtools.tmf.core.signal.TmfRangeSynchSignal;
38 import org.eclipse.linuxtools.tmf.core.signal.TmfSignalHandler;
39 import org.eclipse.linuxtools.tmf.core.signal.TmfTimeSynchSignal;
40 import org.eclipse.linuxtools.tmf.core.signal.TmfTimestampFormatUpdateSignal;
41 import org.eclipse.linuxtools.tmf.core.signal.TmfTraceClosedSignal;
42 import org.eclipse.linuxtools.tmf.core.signal.TmfTraceOpenedSignal;
43 import org.eclipse.linuxtools.tmf.core.signal.TmfTraceSelectedSignal;
44 import org.eclipse.linuxtools.tmf.core.timestamp.ITmfTimestamp;
45 import org.eclipse.linuxtools.tmf.core.timestamp.TmfNanoTimestamp;
46 import org.eclipse.linuxtools.tmf.core.timestamp.TmfTimeRange;
47 import org.eclipse.linuxtools.tmf.core.trace.ITmfTrace;
48 import org.eclipse.linuxtools.tmf.ui.views.TmfView;
49 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.ITimeGraphRangeListener;
50 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.ITimeGraphSelectionListener;
51 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.ITimeGraphTimeListener;
52 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphCombo;
53 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphPresentationProvider;
54 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphRangeUpdateEvent;
55 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphSelectionEvent;
56 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.TimeGraphTimeEvent;
57 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.model.ILinkEvent;
58 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.model.ITimeEvent;
59 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.model.ITimeGraphEntry;
60 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.model.TimeGraphEntry;
61 import org.eclipse.linuxtools.tmf.ui.widgets.timegraph.widgets.Utils.TimeFormat;
62 import org.eclipse.swt.SWT;
63 import org.eclipse.swt.graphics.Image;
64 import org.eclipse.swt.widgets.Composite;
65 import org.eclipse.swt.widgets.Display;
66 import org.eclipse.swt.widgets.TreeColumn;
67 import org.eclipse.ui.IActionBars;
68
69 /**
70 * An abstract view all time graph views can inherit
71 *
72 * This view contains a time graph combo, divided between a treeview on the
73 * left, showing entries and a canvas on the right to draw something for these
74 * entries.
75 *
76 * @since 2.1
77 */
78 public abstract class AbstractTimeGraphView extends TmfView {
79
80 private final String[] fColumns;
81 private final String[] fFilterColumns;
82
83 /**
84 * Redraw state enum
85 */
86 private enum State {
87 IDLE, BUSY, PENDING
88 }
89
90 // ------------------------------------------------------------------------
91 // Fields
92 // ------------------------------------------------------------------------
93
94 /** The timegraph combo */
95 private TimeGraphCombo fTimeGraphCombo;
96
97 /** The selected trace */
98 private ITmfTrace fTrace;
99
100 /** The timegraph entry list */
101 private List<TimeGraphEntry> fEntryList;
102
103 /** The trace to entry list hash map */
104 private final Map<ITmfTrace, List<TimeGraphEntry>> fEntryListMap = new HashMap<ITmfTrace, List<TimeGraphEntry>>();
105
106 /* The trace to build thread hash map */
107 private final Map<ITmfTrace, BuildThread> fBuildThreadMap = new HashMap<ITmfTrace, BuildThread>();
108
109 /** The start time */
110 private long fStartTime;
111
112 /** The end time */
113 private long fEndTime;
114
115 /** The display width */
116 private final int fDisplayWidth;
117
118 /** The zoom thread */
119 private ZoomThread fZoomThread;
120
121 /** The next resource action */
122 private Action fNextResourceAction;
123
124 /** The previous resource action */
125 private Action fPreviousResourceAction;
126
127 /** The relative weight of the sash */
128 private int[] fWeight = { 1, 1 };
129
130 /** A comparator class */
131 private Comparator<ITimeGraphEntry> fEntryComparator = null;
132
133 /** The redraw state used to prevent unnecessary queuing of display runnables */
134 private State fRedrawState = State.IDLE;
135
136 /** The redraw synchronization object */
137 private final Object fSyncObj = new Object();
138
139 /** The presentation provider for this view */
140 private final TimeGraphPresentationProvider fPresentation;
141
142 private TreeLabelProvider fLabelProvider = new TreeLabelProvider();
143
144 // ------------------------------------------------------------------------
145 // Getters and setters
146 // ------------------------------------------------------------------------
147
148 /**
149 * Getter for the time graph combo
150 *
151 * @return The Time graph combo
152 */
153 protected TimeGraphCombo getTimeGraphCombo() {
154 return fTimeGraphCombo;
155 }
156
157 /**
158 * Sets the tree label provider
159 *
160 * @param tlp
161 * The tree label provider
162 */
163 protected void setTreeLabelProvider(final TreeLabelProvider tlp) {
164 fLabelProvider = tlp;
165 }
166
167 /**
168 * Sets the relative weight of each part of the time graph combo
169 *
170 * @param weights
171 * The array of relative weights of each part of the combo
172 */
173 protected void setWeight(final int[] weights) {
174 fWeight = weights;
175 }
176
177 /**
178 * Gets the display width
179 *
180 * @return the display width
181 */
182 protected int getDisplayWidth() {
183 return fDisplayWidth;
184 }
185
186 /**
187 * Gets the comparator for the entries
188 *
189 * @return The entry comparator
190 */
191 protected Comparator<ITimeGraphEntry> getEntryComparator() {
192 return fEntryComparator;
193 }
194
195 /**
196 * Sets the comparator class for the entries * Gets the display width
197 *
198 * @param comparator
199 * A comparator object
200 */
201 protected void setEntryComparator(final Comparator<ITimeGraphEntry> comparator) {
202 fEntryComparator = comparator;
203 }
204
205 /**
206 * Gets the trace displayed in the view
207 *
208 * @return The trace
209 */
210 protected ITmfTrace getTrace() {
211 return fTrace;
212 }
213
214 /**
215 * Sets the trace to display
216 *
217 * @param trace
218 * The trace
219 */
220 protected void setTrace(final ITmfTrace trace) {
221 fTrace = trace;
222 }
223
224 /**
225 * Gets the start time
226 *
227 * @return The start time
228 */
229 protected long getStartTime() {
230 return fStartTime;
231 }
232
233 /**
234 * Sets the start time
235 *
236 * @param time
237 * The start time
238 */
239 protected void setStartTime(long time) {
240 fStartTime = time;
241 }
242
243 /**
244 * Gets the end time
245 *
246 * @return The end time
247 */
248 protected long getEndTime() {
249 return fEndTime;
250 }
251
252 /**
253 * Sets the end time
254 *
255 * @param time
256 * The end time
257 */
258 protected void setEndTime(long time) {
259 fEndTime = time;
260 }
261
262 /**
263 * Gets the entry list map
264 *
265 * @return the entry list map
266 */
267 protected Map<ITmfTrace, List<TimeGraphEntry>> getEntryListMap() {
268 return Collections.unmodifiableMap(fEntryListMap);
269 }
270
271 /**
272 * Adds an entry to the entry list
273 *
274 * @param trace
275 * the trace to add
276 * @param list
277 * The list of time graph entries
278 * @since 2.1
279 */
280 protected void putEntryList(ITmfTrace trace, List<TimeGraphEntry> list) {
281 synchronized(fEntryListMap) {
282 fEntryListMap.put(trace, list);
283 }
284 }
285
286 /**
287 * Text for the "next" button
288 *
289 * @return The "next" button text
290 */
291 protected String getNextText() {
292 return Messages.AbstractTimeGraphtView_NextText;
293 }
294
295 /**
296 * Tooltip for the "next" button
297 *
298 * @return Tooltip for the "next" button
299 */
300 protected String getNextTooltip() {
301 return Messages.AbstractTimeGraphView_NextTooltip;
302 }
303
304 /**
305 * Text for the "Previous" button
306 *
307 * @return The "Previous" button text
308 */
309 protected String getPrevText() {
310 return Messages.AbstractTimeGraphView_PreviousText;
311 }
312
313 /**
314 * Tooltip for the "previous" button
315 *
316 * @return Tooltip for the "previous" button
317 */
318 protected String getPrevTooltip() {
319 return Messages.AbstractTimeGraphView_PreviousTooltip;
320 }
321
322 // ------------------------------------------------------------------------
323 // Classes
324 // ------------------------------------------------------------------------
325
326 private class TreeContentProvider implements ITreeContentProvider {
327
328 @Override
329 public void dispose() {
330 }
331
332 @Override
333 public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
334 }
335
336 @Override
337 public Object[] getElements(Object inputElement) {
338 return (ITimeGraphEntry[]) inputElement;
339 }
340
341 @Override
342 public Object[] getChildren(Object parentElement) {
343 ITimeGraphEntry entry = (ITimeGraphEntry) parentElement;
344 List<? extends ITimeGraphEntry> children = entry.getChildren();
345 return children.toArray(new ITimeGraphEntry[children.size()]);
346 }
347
348 @Override
349 public Object getParent(Object element) {
350 ITimeGraphEntry entry = (ITimeGraphEntry) element;
351 return entry.getParent();
352 }
353
354 @Override
355 public boolean hasChildren(Object element) {
356 ITimeGraphEntry entry = (ITimeGraphEntry) element;
357 return entry.hasChildren();
358 }
359
360 }
361
362 /**
363 * Base class to provide the labels for the left tree view entry. Views
364 * extending this class typically need to override the getColumnText method
365 * if they have more than one column to display
366 */
367 protected static class TreeLabelProvider implements ITableLabelProvider {
368
369 @Override
370 public void addListener(ILabelProviderListener listener) {
371 }
372
373 @Override
374 public void dispose() {
375 }
376
377 @Override
378 public boolean isLabelProperty(Object element, String property) {
379 return false;
380 }
381
382 @Override
383 public void removeListener(ILabelProviderListener listener) {
384 }
385
386 @Override
387 public Image getColumnImage(Object element, int columnIndex) {
388 return null;
389 }
390
391 @Override
392 public String getColumnText(Object element, int columnIndex) {
393 TimeGraphEntry entry = (TimeGraphEntry) element;
394 if (columnIndex == 0) {
395 return entry.getName();
396 }
397 return new String();
398 }
399
400 }
401
402 private class BuildThread extends Thread {
403 private final ITmfTrace fBuildTrace;
404 private final IProgressMonitor fMonitor;
405
406 public BuildThread(final ITmfTrace trace, final String name) {
407 super(name + " build"); //$NON-NLS-1$
408 fBuildTrace = trace;
409 fMonitor = new NullProgressMonitor();
410 }
411
412 @Override
413 public void run() {
414 buildEventList(fBuildTrace, fMonitor);
415 synchronized (fBuildThreadMap) {
416 fBuildThreadMap.remove(this);
417 }
418 }
419
420 public void cancel() {
421 fMonitor.setCanceled(true);
422 }
423 }
424
425 private class ZoomThread extends Thread {
426 private final List<TimeGraphEntry> fZoomEntryList;
427 private final long fZoomStartTime;
428 private final long fZoomEndTime;
429 private final long fResolution;
430 private final IProgressMonitor fMonitor;
431
432 public ZoomThread(List<TimeGraphEntry> entryList, long startTime, long endTime, String name) {
433 super(name + " zoom"); //$NON-NLS-1$
434 fZoomEntryList = entryList;
435 fZoomStartTime = startTime;
436 fZoomEndTime = endTime;
437 fResolution = Math.max(1, (fZoomEndTime - fZoomStartTime) / fDisplayWidth);
438 fMonitor = new NullProgressMonitor();
439 }
440
441 @Override
442 public void run() {
443 if (fZoomEntryList == null) {
444 return;
445 }
446 for (TimeGraphEntry entry : fZoomEntryList) {
447 if (fMonitor.isCanceled()) {
448 return;
449 }
450 zoom(entry, fMonitor);
451 }
452 /* Refresh the arrows when zooming */
453 List<ILinkEvent> events = getLinkList(fZoomStartTime, fZoomEndTime, fResolution, fMonitor);
454 if (events != null) {
455 fTimeGraphCombo.setLinks(events);
456 redraw();
457 }
458 }
459
460 private void zoom(TimeGraphEntry entry, IProgressMonitor monitor) {
461 if (fZoomStartTime <= fStartTime && fZoomEndTime >= fEndTime) {
462 entry.setZoomedEventList(null);
463 } else {
464 List<ITimeEvent> zoomedEventList = getEventList(entry, fZoomStartTime, fZoomEndTime, fResolution, monitor);
465 if (zoomedEventList != null) {
466 entry.setZoomedEventList(zoomedEventList);
467 }
468 }
469 redraw();
470 for (TimeGraphEntry child : entry.getChildren()) {
471 if (fMonitor.isCanceled()) {
472 return;
473 }
474 zoom(child, monitor);
475 }
476 }
477
478 public void cancel() {
479 fMonitor.setCanceled(true);
480 }
481 }
482
483 // ------------------------------------------------------------------------
484 // Constructors
485 // ------------------------------------------------------------------------
486
487 /**
488 * Constructor
489 *
490 * @param id
491 * The id of the view
492 * @param cols
493 * The columns to display in the tree view on the left
494 * @param filterCols
495 * The columns list to filter the view
496 * @param pres
497 * The presentation provider
498 */
499 public AbstractTimeGraphView(String id, String[] cols, String[] filterCols,
500 TimeGraphPresentationProvider pres) {
501 super(id);
502 fColumns = cols;
503 fFilterColumns = filterCols;
504 fPresentation = pres;
505 fDisplayWidth = Display.getDefault().getBounds().width;
506 }
507
508 // ------------------------------------------------------------------------
509 // ViewPart
510 // ------------------------------------------------------------------------
511
512 @Override
513 public void createPartControl(Composite parent) {
514 fTimeGraphCombo = new TimeGraphCombo(parent, SWT.NONE, fWeight);
515
516 fTimeGraphCombo.setTreeContentProvider(new TreeContentProvider());
517
518 fTimeGraphCombo.setTreeLabelProvider(fLabelProvider);
519
520 fTimeGraphCombo.setTimeGraphProvider(fPresentation);
521
522 fTimeGraphCombo.setTreeColumns(fColumns);
523
524 fTimeGraphCombo.setFilterContentProvider(new TreeContentProvider());
525
526 fTimeGraphCombo.setFilterLabelProvider(new TreeLabelProvider());
527
528 fTimeGraphCombo.setFilterColumns(fFilterColumns);
529
530 fTimeGraphCombo.getTimeGraphViewer().addRangeListener(new ITimeGraphRangeListener() {
531 @Override
532 public void timeRangeUpdated(TimeGraphRangeUpdateEvent event) {
533 final long startTime = event.getStartTime();
534 final long endTime = event.getEndTime();
535 TmfTimeRange range = new TmfTimeRange(new TmfNanoTimestamp(startTime), new TmfNanoTimestamp(endTime));
536 broadcast(new TmfRangeSynchSignal(AbstractTimeGraphView.this, range));
537 if (fZoomThread != null) {
538 fZoomThread.cancel();
539 }
540 startZoomThread(startTime, endTime);
541 }
542 });
543
544 fTimeGraphCombo.getTimeGraphViewer().addTimeListener(new ITimeGraphTimeListener() {
545 @Override
546 public void timeSelected(TimeGraphTimeEvent event) {
547 TmfNanoTimestamp startTime = new TmfNanoTimestamp(event.getBeginTime());
548 TmfNanoTimestamp endTime = new TmfNanoTimestamp(event.getEndTime());
549 broadcast(new TmfTimeSynchSignal(AbstractTimeGraphView.this, startTime, endTime));
550 }
551 });
552
553 fTimeGraphCombo.addSelectionListener(new ITimeGraphSelectionListener() {
554 @Override
555 public void selectionChanged(TimeGraphSelectionEvent event) {
556 // ITimeGraphEntry selection = event.getSelection();
557 }
558 });
559
560 fTimeGraphCombo.getTimeGraphViewer().setTimeFormat(TimeFormat.CALENDAR);
561
562 IStatusLineManager statusLineManager = getViewSite().getActionBars().getStatusLineManager();
563 fTimeGraphCombo.getTimeGraphViewer().getTimeGraphControl().setStatusLineManager(statusLineManager);
564
565 // View Action Handling
566 makeActions();
567 contributeToActionBars();
568
569 ITmfTrace trace = getActiveTrace();
570 if (trace != null) {
571 traceSelected(new TmfTraceSelectedSignal(this, trace));
572 }
573
574 // make selection available to other views
575 getSite().setSelectionProvider(fTimeGraphCombo.getTreeViewer());
576 }
577
578 @Override
579 public void setFocus() {
580 fTimeGraphCombo.setFocus();
581 }
582
583 // ------------------------------------------------------------------------
584 // Signal handlers
585 // ------------------------------------------------------------------------
586
587 /**
588 * Handler for the trace opened signal.
589 *
590 * @param signal
591 * The incoming signal
592 * @since 2.0
593 */
594 @TmfSignalHandler
595 public void traceOpened(TmfTraceOpenedSignal signal) {
596 fTrace = signal.getTrace();
597 loadTrace();
598 }
599
600 /**
601 * Handler for the trace selected signal
602 *
603 * @param signal
604 * The incoming signal
605 */
606 @TmfSignalHandler
607 public void traceSelected(final TmfTraceSelectedSignal signal) {
608 if (signal.getTrace() == fTrace) {
609 return;
610 }
611 fTrace = signal.getTrace();
612
613 loadTrace();
614 }
615
616 /**
617 * Trace is closed: clear the data structures and the view
618 *
619 * @param signal
620 * the signal received
621 */
622 @TmfSignalHandler
623 public void traceClosed(final TmfTraceClosedSignal signal) {
624 synchronized (fBuildThreadMap) {
625 BuildThread buildThread = fBuildThreadMap.remove(signal.getTrace());
626 if (buildThread != null) {
627 buildThread.cancel();
628 }
629 }
630 synchronized (fEntryListMap) {
631 fEntryListMap.remove(signal.getTrace());
632 }
633 if (signal.getTrace() == fTrace) {
634 fTrace = null;
635 fStartTime = 0;
636 fEndTime = 0;
637 if (fZoomThread != null) {
638 fZoomThread.cancel();
639 }
640 refresh();
641 }
642 }
643
644 /**
645 * Handler for the time synch signal
646 *
647 * @param signal
648 * The signal that's received
649 */
650 @TmfSignalHandler
651 public void synchToTime(final TmfTimeSynchSignal signal) {
652 if (signal.getSource() == this || fTrace == null) {
653 return;
654 }
655 final long beginTime = signal.getBeginTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
656 final long endTime = signal.getEndTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
657
658 Display.getDefault().asyncExec(new Runnable() {
659 @Override
660 public void run() {
661 if (fTimeGraphCombo.isDisposed()) {
662 return;
663 }
664 if (beginTime == endTime) {
665 fTimeGraphCombo.getTimeGraphViewer().setSelectedTime(beginTime, true);
666 } else {
667 fTimeGraphCombo.getTimeGraphViewer().setSelectionRange(beginTime, endTime);
668 }
669 startZoomThread(fTimeGraphCombo.getTimeGraphViewer().getTime0(), fTimeGraphCombo.getTimeGraphViewer().getTime1());
670
671 synchingToTime(beginTime);
672 }
673 });
674 }
675
676 /**
677 * Handler for the range synch signal
678 *
679 * @param signal
680 * The signal that's received
681 */
682 @TmfSignalHandler
683 public void synchToRange(final TmfRangeSynchSignal signal) {
684 if (signal.getSource() == this || fTrace == null) {
685 return;
686 }
687 if (signal.getCurrentRange().getIntersection(fTrace.getTimeRange()) == null) {
688 return;
689 }
690 final long startTime = signal.getCurrentRange().getStartTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
691 final long endTime = signal.getCurrentRange().getEndTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
692 Display.getDefault().asyncExec(new Runnable() {
693 @Override
694 public void run() {
695 if (fTimeGraphCombo.isDisposed()) {
696 return;
697 }
698 fTimeGraphCombo.getTimeGraphViewer().setStartFinishTime(startTime, endTime);
699 startZoomThread(startTime, endTime);
700 }
701 });
702 }
703
704 /**
705 * @param signal the format of the timestamps was updated.
706 * @since 2.1
707 */
708 @TmfSignalHandler
709 public void updateTimeFormat( final TmfTimestampFormatUpdateSignal signal){
710 this.fTimeGraphCombo.refresh();
711 }
712
713 // ------------------------------------------------------------------------
714 // Internal
715 // ------------------------------------------------------------------------
716
717 private void loadTrace() {
718 synchronized (fEntryListMap) {
719 fEntryList = fEntryListMap.get(fTrace);
720 if (fEntryList == null) {
721 synchronized (fBuildThreadMap) {
722 BuildThread buildThread = new BuildThread(fTrace, this.getName());
723 fBuildThreadMap.put(fTrace, buildThread);
724 buildThread.start();
725 }
726 } else {
727 fStartTime = fTrace.getStartTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
728 fEndTime = fTrace.getEndTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
729 refresh();
730 }
731 }
732 }
733
734 /**
735 * Method called when synching to a given timestamp. Inheriting classes can
736 * perform actions here to update the view at the given timestamp.
737 *
738 * @param time
739 * The currently selected time
740 */
741 protected void synchingToTime(long time) {
742
743 }
744
745 /**
746 * Build the entries list to show in this time graph
747 *
748 * Called from the BuildThread
749 *
750 * @param trace
751 * The trace being built
752 * @param monitor
753 * The progress monitor object
754 */
755 protected abstract void buildEventList(final ITmfTrace trace, IProgressMonitor monitor);
756
757 /**
758 * Gets the list of event for an entry in a given timerange
759 *
760 * @param entry
761 * The entry to get events for
762 * @param startTime
763 * Start of the time range
764 * @param endTime
765 * End of the time range
766 * @param resolution
767 * The resolution
768 * @param monitor
769 * The progress monitor object
770 * @return The list of events for the entry
771 */
772 protected abstract List<ITimeEvent> getEventList(TimeGraphEntry entry,
773 long startTime, long endTime, long resolution,
774 IProgressMonitor monitor);
775
776 /**
777 * Gets the list of links (displayed as arrows) for a trace in a given
778 * timerange. Default implementation returns an empty list.
779 *
780 * @param startTime
781 * Start of the time range
782 * @param endTime
783 * End of the time range
784 * @param resolution
785 * The resolution
786 * @param monitor
787 * The progress monitor object
788 * @return The list of link events
789 * @since 2.1
790 */
791 protected List<ILinkEvent> getLinkList(long startTime, long endTime,
792 long resolution, IProgressMonitor monitor) {
793 return new ArrayList<ILinkEvent>();
794 }
795
796
797 /**
798 * Refresh the display
799 */
800 protected void refresh() {
801 Display.getDefault().asyncExec(new Runnable() {
802 @Override
803 public void run() {
804 if (fTimeGraphCombo.isDisposed()) {
805 return;
806 }
807 ITimeGraphEntry[] entries = null;
808 synchronized (fEntryListMap) {
809 fEntryList = fEntryListMap.get(fTrace);
810 if (fEntryList == null) {
811 fEntryList = new ArrayList<TimeGraphEntry>();
812 }
813 entries = fEntryList.toArray(new ITimeGraphEntry[0]);
814 }
815 if (fEntryComparator != null) {
816 Arrays.sort(entries, fEntryComparator);
817 }
818 fTimeGraphCombo.setInput(entries);
819 fTimeGraphCombo.getTimeGraphViewer().setTimeBounds(fStartTime, fEndTime);
820
821 long selectionBeginTime = fTrace == null ? 0 : fTraceManager.getSelectionBeginTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
822 long selectionEndTime = fTrace == null ? 0 : fTraceManager.getSelectionEndTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
823 long startTime = fTrace == null ? 0 : fTraceManager.getCurrentRange().getStartTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
824 long endTime = fTrace == null ? 0 : fTraceManager.getCurrentRange().getEndTime().normalize(0, ITmfTimestamp.NANOSECOND_SCALE).getValue();
825 startTime = Math.max(startTime, fStartTime);
826 endTime = Math.min(endTime, fEndTime);
827 fTimeGraphCombo.getTimeGraphViewer().setSelectionRange(selectionBeginTime, selectionEndTime);
828 fTimeGraphCombo.getTimeGraphViewer().setStartFinishTime(startTime, endTime);
829
830 for (TreeColumn column : fTimeGraphCombo.getTreeViewer().getTree().getColumns()) {
831 column.pack();
832 }
833
834 startZoomThread(startTime, endTime);
835 }
836 });
837 }
838
839 /**
840 * Redraw the canvas
841 */
842 protected void redraw() {
843 synchronized (fSyncObj) {
844 if (fRedrawState == State.IDLE) {
845 fRedrawState = State.BUSY;
846 } else {
847 fRedrawState = State.PENDING;
848 return;
849 }
850 }
851 Display.getDefault().asyncExec(new Runnable() {
852 @Override
853 public void run() {
854 if (fTimeGraphCombo.isDisposed()) {
855 return;
856 }
857 fTimeGraphCombo.redraw();
858 fTimeGraphCombo.update();
859 synchronized (fSyncObj) {
860 if (fRedrawState == State.PENDING) {
861 fRedrawState = State.IDLE;
862 redraw();
863 } else {
864 fRedrawState = State.IDLE;
865 }
866 }
867 }
868 });
869 }
870
871 private void startZoomThread(long startTime, long endTime) {
872 if (fZoomThread != null) {
873 fZoomThread.cancel();
874 }
875 fZoomThread = new ZoomThread(fEntryList, startTime, endTime, getName());
876 fZoomThread.start();
877 }
878
879 private void makeActions() {
880 fPreviousResourceAction = fTimeGraphCombo.getTimeGraphViewer().getPreviousItemAction();
881 fPreviousResourceAction.setText(getPrevText());
882 fPreviousResourceAction.setToolTipText(getPrevTooltip());
883 fNextResourceAction = fTimeGraphCombo.getTimeGraphViewer().getNextItemAction();
884 fNextResourceAction.setText(getNextText());
885 fNextResourceAction.setToolTipText(getNextTooltip());
886 }
887
888 private void contributeToActionBars() {
889 IActionBars bars = getViewSite().getActionBars();
890 fillLocalToolBar(bars.getToolBarManager());
891 }
892
893 /**
894 * Add actions to local tool bar manager
895 *
896 * @param manager the tool bar manager
897 */
898 protected void fillLocalToolBar(IToolBarManager manager) {
899 if (fFilterColumns.length > 0) {
900 manager.add(fTimeGraphCombo.getShowFilterAction());
901 }
902 manager.add(fTimeGraphCombo.getTimeGraphViewer().getShowLegendAction());
903 manager.add(new Separator());
904 manager.add(fTimeGraphCombo.getTimeGraphViewer().getResetScaleAction());
905 manager.add(fTimeGraphCombo.getTimeGraphViewer().getPreviousEventAction());
906 manager.add(fTimeGraphCombo.getTimeGraphViewer().getNextEventAction());
907 manager.add(fPreviousResourceAction);
908 manager.add(fNextResourceAction);
909 manager.add(fTimeGraphCombo.getTimeGraphViewer().getZoomInAction());
910 manager.add(fTimeGraphCombo.getTimeGraphViewer().getZoomOutAction());
911 manager.add(new Separator());
912 }
913 }
This page took 0.053101 seconds and 6 git commands to generate.