}
dataset.add(overlapsTaskSeries);
dataset.add(gapsTaskSeries);
dataset.add(completeDurationTaskSeries);
final SlidingGanttCategoryDataset slidingDataset = new SlidingGanttCategoryDataset(dataset, 0, GROUPS_VISIBLE);
final JFreeChart chart = ChartFactory.createGanttChart("Date gaps and overlaps in " + result.getFromColumnName()
+ " / " + result.getToColumnName(), result.getGroupColumnName(), "Time", slidingDataset, true, true, false);
ChartUtils.applyStyles(chart);
// make sure the 3 timeline types have correct coloring
{
final CategoryPlot plot = (CategoryPlot) chart.getPlot();
plot.setDrawingSupplier(new DCDrawingSupplier(WidgetUtils.ADDITIONAL_COLOR_GREEN_BRIGHT,
WidgetUtils.ADDITIONAL_COLOR_RED_BRIGHT, WidgetUtils.BG_COLOR_BLUE_BRIGHT));
}
final ChartPanel chartPanel = new ChartPanel(chart);
chartPanel.addChartMouseListener(new ChartMouseListener() {
@Override
public void chartMouseMoved(ChartMouseEvent event) {
Cursor cursor = Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR);
ChartEntity entity = event.getEntity();
if (entity instanceof PlotEntity) {
cursor = Cursor.getPredefinedCursor(Cursor.E_RESIZE_CURSOR);
}
chartPanel.setCursor(cursor);
}
@Override
public void chartMouseClicked(ChartMouseEvent event) {
// do nothing
}
});
final int visibleLines = Math.min(GROUPS_VISIBLE, groupNames.size());
chartPanel.setPreferredSize(new Dimension(0, visibleLines * 50 + 200));
final JComponent decoratedChartPanel;
StringBuilder chartDescription = new StringBuilder();
chartDescription.append("<html><p>The chart displays the recorded timeline based on FROM and TO dates.<br/><br/>");
chartDescription
.append("The <b>red items</b> represent gaps in the timeline and the <b>green items</b> represent points in the timeline where more than one record show activity.<br/><br/>");
chartDescription
.append("You can <b>zoom in</b> by clicking and dragging the area that you want to examine in further detail.");
if (groupNames.size() > GROUPS_VISIBLE) {
final JScrollBar scroll = new JScrollBar(JScrollBar.VERTICAL);
scroll.setMinimum(0);
scroll.setMaximum(groupNames.size());
scroll.addAdjustmentListener(new AdjustmentListener() {
@Override
public void adjustmentValueChanged(AdjustmentEvent e) {
int value = e.getAdjustable().getValue();
slidingDataset.setFirstCategoryIndex(value);
}
});
chartPanel.addMouseWheelListener(new MouseWheelListener() {