ランダムに配置された色付きの円を 5 つ表示したいと考えています。簡単な部分でした。次に、このコードをアニメーションになるように調整します。このアプリケーションは、無限にランダムな円を生成する必要がありますが、条件は、画面上に最後の 5 つの円のみを保持することです。ここで行き詰まりました。JavaFx は ListChangeListener を提供します。使うべきものだと思います。しかし、どのように?以下は私の未完成のコードです:
import java.util.Random;
import javafx.application.Application;
import javafx.collections.ListChangeListener;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.paint.Color;
import javafx.scene.shape.Circle;
import javafx.stage.Stage;
public class RandomColorTest extends Application {
int radius = 20;
int sceneWidth = 300;
int sceneHeight = 300;
private void init(Stage primaryStage) {
Group root = new Group();
primaryStage.setResizable(false);
primaryStage.setScene(new Scene(root, sceneWidth,sceneHeight));
for (int i = root.getChildren().size(); i < 5; i++) {
root.getChildren().add(createCircle());
// the following should convey the idea:
// if the collection holds 5 elements then keep least recently generated element for 1 second and then delete it
// add one new element
// if the collection holds 5 elements then keep least recently generated element for 1 second and then delete it
// add one new element
// and so on
root.getChildren().addListener(new ListChangeListener<E>() {
@Override
public void onChanged(
javafx.collections.ListChangeListener.Change<? extends E> arg0) {
// TODO Auto-generated method stub
}
});
}
}
// Create randomly positioned and colored circle
private Circle createCircle() {
final Circle circle = new Circle();
circle.setRadius(radius);
Random r = new Random();
int rCol1 = r.nextInt(256);
int rCol2 = r.nextInt(256);
int rCol3 = r.nextInt(256);
int rX = radius+r.nextInt(sceneWidth);
if (rX>sceneWidth-radius) {
rX=rX-2*radius;
}
int rY = radius+r.nextInt(sceneHeight);
if (rY>sceneHeight-radius) {
rY=rY-2*radius;
}
circle.setLayoutX(rX);
circle.setLayoutY(rY);
circle.setStroke(Color.BLACK);
circle.setFill(Color.rgb(rCol1,rCol2,rCol3));
System.out.println(rCol1+"-"+rCol2+"-"+rCol3+"-"+rX+"-"+rY);
return circle;
}
@Override public void start(Stage primaryStage) throws Exception {
init(primaryStage);
primaryStage.show();
}
public static void main(String[] args) { launch(args); }
}
ListChangeListener をエラーなしでコンパイルできた後でも、期待どおりに動作しません。for ループに加えられた変更:
for (int i = root.getChildren().size();;i++) {
final ObservableList<Node> ol = root.getChildren();
// the following should convey the idea:
// if the collection holds 5 elements then keep least recently generated element for 1 second and then delete it
// add one new element
// if the collection holds 5 elements then keep least recently generated element for 1 second and then delete it
// add one new element
// and so on
ol.add(createCircle());
ol.addListener( new ListChangeListener<Node>(){
@Override
public void onChanged(
javafx.collections.ListChangeListener.Change<? extends Node> arg0) {
// TODO Auto-generated method stub
System.out.println("one new element added, size:"+ol.size());
if (ol.size()==5) {
ol.remove(0);
}
}
});
}
for ループは無限にループするように定義されています (おそらく、この問題を解決する正しい方法でもありません)。コンソールから、プログラムの実行中に円が削除されたり追加されたりすることがわかります。残念ながら、GUI が表示されなくなりました。