我用JFreeChart创建了甘特图,在其中实现了作业调度问题(JSSP),其中机器为任务/作业执行某些子任务。因此,我希望属于特定任务/作业的每个子任务都具有相同的颜色。
问题是我需要为子任务制作自定义文本。
例如我希望当任务1具有n个子任务时,所有属于任务1的子任务都被标记为(1.1、1.2,...,1.n)。
我在这里查看了几个链接,例如以下内容,但无法使它起作用:Text labels inside jfree Gantt chart bars
我有一个想法,它与我试图在下面显示的setBaseItemLabelGenerator
有关,但是肯定不起作用。
有人可以帮助我吗?我将添加我的代码以供参考。预先感谢。
public class Draw extends ApplicationFrame {
//private int maxSpan = 20;
public static final TaskSeriesCollection model = new TaskSeriesCollection();
public Draw(final String title) {
super(title);
final IntervalCategoryDataset dataset = createSampleDataset();
// create the chart...
final JFreeChart chart = ChartFactory.createGanttChart(
"Gantt Chart", // chart title
"Machines", // domain axis label
"TimeLine", // range axis label
dataset, // data
true, // include legend
true, // tooltips
false // urls
);
final CategoryPlot plot = (CategoryPlot) chart.getPlot();
DateAxis axis = (DateAxis) plot.getRangeAxis();
axis.setDateFormatOverride(new SimpleDateFormat("S"));
axis.setMaximumDate(new Date(50));
// add the chart to a panel...
final ChartPanel chartPanel = new ChartPanel(chart);
chartPanel.setPreferredSize(new java.awt.Dimension(500, 270));
setContentPane(chartPanel);
MyRenderer renderer = new MyRenderer(model);
plot.setRenderer(renderer);
renderer.setBaseItemLabelGenerator( new CategoryItemLabelGenerator(){
@Override
public String generateRowLabel(CategoryDataset dataset, int row) {
return "Your Row Text " + row;
}
@Override
public String generateColumnLabel(CategoryDataset dataset, int column) {
return "Your Column Text " + column;
}
@Override
public String generateLabel(CategoryDataset dataset, int row, int column) {
return "Your Label Text " + row + "," + column;
}
});
renderer.setBaseItemLabelsVisible(true);
renderer.setBaseItemLabelPaint(Color.BLACK);
renderer.setBasePositiveItemLabelPosition(new ItemLabelPosition(
ItemLabelAnchor.INSIDE6, TextAnchor.BOTTOM_CENTER));
this.pack();
RefineryUtilities.centerFrameOnScreen(this);
this.setVisible(true);
}
/** @see https://stackoverflow.com/a/8949913/230513 */
private static class MyRenderer extends GanttRenderer {
private static final int PASS = 2; // assumes two passes
private final List<Color> clut = new ArrayList<>();
private final TaskSeriesCollection model;
private int row;
private int col;
private int index;
//NB FIX COLORS
static final List<Color> colors = new ArrayList<Color>() {{
add(Color.BLACK);
add(Color.BLUE);
add(Color.GREEN);
add(Color.RED);
add(Color.CYAN);
add(Color.YELLOW);
add(Color.ORANGE);
add(Color.PINK);
add(Color.DARK_GRAY);
add(Color.MAGENTA);
add(Color.GRAY);
add(Color.LIGHT_GRAY);
add(Color.ORANGE);
add(Color.CYAN);
add(Color.PINK);
add(Color.DARK_GRAY);
add(Color.MAGENTA);
add(Color.GRAY);
add(Color.LIGHT_GRAY);
add(Color.RED);
add(Color.CYAN);
add(Color.YELLOW);
add(Color.ORANGE);
}};
public MyRenderer(TaskSeriesCollection model) {
this.model = model;
}
@Override
public Paint getItemPaint(int row, int col) {
if (clut.isEmpty() || this.row != row || this.col != col) {
initClut(row, col);
this.row = row;
this.col = col;
index = 0;
}
int clutIndex = index++ / PASS;
return clut.get(clutIndex);
}
private void initClut(int row, int col) {
clut.clear();
TaskSeries series = (TaskSeries) model.getRowKeys().get(row);
//NB! amt of machines is amt of tasks
List<Task> amtMachines = series.getTasks(); // unchecked
//TASKCOUNT is amount of jobs --> subtasks
int noJobs = amtMachines.get(col).getSubtaskCount();
noJobs = Math.max(1, noJobs);
String description;
//loop over all jobs
for (int i = 0; i < noJobs; i++) {
//get this task, loop over all subtasks in this task
description = amtMachines.get(col).getSubtask(i).getDescription();
//check which color this task has
for(int j = 0; j < schedule[0].length;j++) {
String string = "subtask" + j;
if(description.equals(string)){
clut.add(this.colors.get(j));
}
}
}
}
}
private IntervalCategoryDataset createSampleDataset() {
Task tasks[]= new Task[schedule.length]; //Potentially increasing runtime
Random r = new Random();
List<Task> taskList = new ArrayList<>();
final TaskSeries s = new TaskSeries("Jobs scheduled");
//for all machines
for(int i = 0; i < schedule.length;i++) {
Task subtasks[]= new Task[schedule[0].length];
//machineString
String str = "M" + i;
//create Task
tasks[i] = new Task(str, new SimpleTimePeriod(schedule[i][0][0], schedule[i][schedule[1].length-1][0]+schedule[i][schedule[1].length-1][1]));
taskList.add(tasks[i]);
//create amt of jobs aka. subtasks
for(int j = 0; j < schedule[0].length;j++) {
String string = "subtask" + j;
subtasks[j] = new Task(string, new SimpleTimePeriod(schedule[i][j][0], schedule[i][j][0]+schedule[i][j][1]));
tasks[i].addSubtask(subtasks[j]);
}
}
for(Task t : taskList) {
s.add(t);
}
model.add(s);
return model;
}
}