我正在尝试制作类似于心电图或其他显示器工作方式的实时更新折线图。我画了一条很好的线。随着新数字的添加,它从左到右步进 3。
我现在遇到的问题是让它向右滚动。经过大量研究,我仍然处于死胡同。
我可以让画布滚动吗?我是否需要在某种点对列表中包含所有点?我尝试使用 XYChart.Series (点对),但无法循环通过它来更改和更新。
我真的不知道如何将我在每个图中创建的线条作为我可以移动或操纵的对象。我假设这将是最好的方法,而不是每次添加新数据时都重新绘制画布。
这是我的图表类。
public class Graph {
public Double accval;
public Double sndval;
public Double litval;
public boolean accAlive = false;
public boolean sndAlive = false;
public boolean litAlive = false;
public Canvas accCanvas;
public Canvas sndCanvas;
public Canvas litCanvas;
public GraphicsContext accGFXContext;
public GraphicsContext sndGFXContext;
public GraphicsContext litGFXContext;
public int accPrevX = 3;
public int sndPrevX = 3;
public int litPrevX = 3;
public Double accPrevY;
public Double sndPrevY;
public Double litPrevY;
public Group accgroup;
public Group sndgroup;
public Group litgroup;
public Canvas creategraph(Canvas canvas, String type){
if (type.contains("acc")){accAlive = true; accCanvas = canvas; accgroup = new Group(); accGFXContext = accCanvas.getGraphicsContext2D(); return accCanvas;}
if (type.contains("snd")){sndAlive = true; sndCanvas = canvas; sndgroup = new Group(); sndGFXContext = sndCanvas.getGraphicsContext2D(); return sndCanvas;}
if (type.contains("lit")){litAlive = true; litCanvas = canvas; litgroup = new Group(); litGFXContext = litCanvas.getGraphicsContext2D(); return litCanvas;}
return null;
}
public void addData(String type, Double data){
if (type.contains("acc")){this.accval = data; draw("acc");}
if (type.contains("snd")){this.sndval = data; draw("snd");}
if (type.contains("lit")){this.litval = data; draw("lit");}
}
public void draw(String type){
GraphicsContext gc = null;
Double val = null;
Double prevVal = null;
int x = 0;
if (type.contains("acc")){gc = accGFXContext; x = accPrevX; val = accval; if(accPrevY == null){accPrevY = accval;} prevVal = accPrevY;}
if (type.contains("snd")){gc = sndGFXContext; x = sndPrevX; val = sndval; if(sndPrevY == null){sndPrevY = sndval;} prevVal = sndPrevY;}
if (type.contains("lit")){gc = litGFXContext; x = litPrevX; val = litval; if(litPrevY == null){litPrevY = litval;} prevVal = litPrevY;}
if (gc != null && val != null){
gc.setLineWidth(1);
gc.beginPath();
gc.setStroke(Color.GREEN);
gc.moveTo(x, prevVal);
x+=2;
gc.lineTo(x, val);
gc.stroke();
if (type.contains("acc")){accPrevY = val; accPrevX = x;}
if (type.contains("snd")){sndPrevY = val; sndPrevX = x;}
if (type.contains("lit")){litPrevY = val; litPrevX = x;}
}
}
}
这是我的控制器。
public class GUI implements Initializable{
private int currentval = 0;
public Graph graph;
Random rand;
@FXML
Canvas accCanvas;
@FXML
Canvas sndCanvas;
@FXML
Canvas litCanvas;
@Override
public void initialize(URL location, ResourceBundle resources) {
rand = new Random();
creategraph();
}
public void creategraph(){
graph = new Graph();
accCanvas = graph.creategraph(accCanvas, "acc");
sndCanvas = graph.creategraph(sndCanvas, "snd");
litCanvas = graph.creategraph(litCanvas, "lit");
startgraphing();
}
public void updatenumber(){
currentval = rand.nextInt(50) + 1;
}
public void startgraphing(){
Runnable timerRunnable = new Runnable() {
public void run() {
updatenumber();
System.out.println("Current Value: " + currentval);
graph.addData("acc", (double) currentval);
graph.addData("snd", (double) currentval);
graph.addData("lit", (double) currentval);
}
};
ScheduledExecutorService executor = Executors.newScheduledThreadPool(1);
executor.scheduleAtFixedRate(timerRunnable, 0, 50, TimeUnit.MILLISECONDS);
timerRunnable.run();
}
}
不是真的在寻找讲义。只是寻找有关如何前进的想法。