Empresas
Empregos
  • Sobre nós
  • Soluções
    • Publicação de vagas
      Publique sua vaga e receba candidatos qualificados em 48h.
    • Avaliações de candidatos
      Mais de 500 testes técnicos e psicológicos, mais anti-fraude.
    • Headhunting
      Busca executiva personalizada do início ao fim.
    • Folha de Pagamento + EOR
      Dispersão de folha e EOR em mais de 15 países da LATAM.
  • Preços
  • Empregos

0

234
Visualizações
JavaFX AnimationTimer no se detiene correctamente

Entonces, estoy creando el juego de la serpiente usando JavaFX y parece que no puedo hacer que el juego se detenga correctamente, es decir, se detiene ocasionalmente y otras veces, el juego simplemente ignora la pausa. Entonces, básicamente tengo una clase Main donde inicializo todos los componentes de la GUI, y también actúa como controlador para la aplicación javafx.

Tengo un Button llamado gameControl que inicia/pausa el juego, una Boolean pause variable que realiza un seguimiento de los estados del juego (nuevo/en pausa/en ejecución) y los métodos startGame , pauseGame .

El manejador de EventHandler del botón gameControl es el siguiente:

 gameControl.setOnClicked(event->{ if(paused == null) startGame(); //new game else if(paused) continueGame(); //for paused game else pauseGame(); //for running game });

La función startGame se parece a esto:

 void startGame(){ paused = false; Snake snake = new Snake(); //the snake sprite //following gameLoop controls the animation of the snake gameLoop = new AnimationTimer(){ @Override public void handle(long now){ drawSnake(); //draws the snake on the game snake.move(); //move snake ahead //following code is for slowing down the gameLoop renders to make it easier to play Task<Void> sleeper = new Task<>(){ @Override protected Void call() throws Exception { gameLoop.stop(); Thread.sleep(30); gameLoop.start(); return null; } }; new Thread(sleeper).start(); //force garbage collection or else throws a bunch of exceptions after a while of running. //not sure of the cause... System.gc(); } }; gameLoop.start(); }

AnimationTimer gameLoop son variables de la clase para permitir llamar desde otras funciones.

Y la función pauseGame :

 void pauseGame() { paused = true; gameLoop.stop(); }

Entonces, como dije antes, el juego no se detiene cada vez que presiono el botón gameControl , y sospecho que se debe a Thread.sleep(30); línea dentro de la Task del gameLoop . Dicho esto, todavía no estoy completamente seguro y no tengo idea de cómo solucionarlo. Cualquier ayuda sería apreciada.

over 4 years ago · Santiago Trujillo
2 Respostas
Responde à pergunta

0

¿Qué tipo es 'en pausa'? Verifica que sea nulo, pero luego lo trata como un booleano. No puedo entender por qué sería un contenedor de objeto booleano 'B' grande en lugar del tipo booleano primitivo.

Este:

 //following code is for slowing down the gameLoop renders to make it easier to play Task<Void> sleeper = new Task<>(){ @Override protected Void call() throws Exception { gameLoop.stop(); Thread.sleep(30); gameLoop.start(); return null; } };

Es una manera absolutamente horrible de acelerar la velocidad. Deje que se ejecute el ciclo de su juego, verifique el tiempo en cada ciclo para ver si ha transcurrido suficiente tiempo como para actualizar las cosas. Su temporizador de animación impulsará el juego. No desea pausar el subproceso de la plataforma principal, no desea pausar ningún subproceso de trabajo que esté manejando tareas. Si está programando tareas, prográmelas para que se ejecuten en los intervalos que desee; no acelere el hilo en el método call().

Lo que realmente quieres es algo como esto:

 //following gameLoop controls the animation of the snake gameLoop = new AnimationTimer(){ @Override public void handle(long now){ if ((now - lastTime) > updateIterval) { drawSnake(); //draws the snake on the game snake.move(); //move snake ahead lastTime = now; }

Incluso podría hacer un bucle para "ponerse al día" en caso de que el temporizador de animación se retrase por algún motivo:

 while ((now - lastTime) > updateIterval) { drawSnake(); //draws the snake on the game snake.move(); //move snake ahead lastTime += updateIterval; }
over 4 years ago · Santiago Trujillo Relatório

0

Tu intuición de que Thread.sleep(30); puede estar causando un problema está en el camino correcto. Un usuario puede hacer clic en el botón que llama a pauseGame , establecer pausado en verdadero y decirle al bucle de juego que se detenga. Si el nuevo subproceso durmiente se inicia y está durmiendo en ese momento, llamará a start() en el bucle de juego cuando se despierte.

Una opción puede ser simplemente verificar el valor de paused en la tarea durmiente para determinar si debe iniciar el bucle de juego.

 Task<Void> sleeper = new Task<>(){ @Override protected Void call() throws Exception { gameLoop.stop(); Thread.sleep(30); if (!paused) { gameLoop.start(); } return null; } };

Dado que el valor en pausa se establece y se lee desde varios subprocesos, recomendaría agregar un mecanismo para asegurarse de que no obtenga un comportamiento no determinista. Cambiar el booleano por un AtomicBoolean es una opción sencilla para garantizar la coherencia.

over 4 years ago · Santiago Trujillo Relatório
Responde à pergunta
Encontrar trabalhos remotos

Descubra a nova forma de encontrar um emprego!

melhores empregos
Principais categorias de trabalho
Empresas
Postar vaga Preços Comercial
Jurídico
Termos e Condições Política de privacidade
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomende algumas ofertas para mim
Preciso de ajuda