Estoy trabajando en un nuevo proyecto en Phaser y, por alguna razón, la gravedad en el juego está desordenada, cuando intento saltar, salto como un centímetro. si cambio los valores, nada cambia, siempre falla. ¿Cómo puedo hacer para que salte y caiga normalmente?
He tenido algunos proyectos anteriores y la gravedad funciona bien, para este proyecto estoy usando la última versión estable de Phaser 3. Sinceramente, no puedo ver cuál es el error y he estado en eso por un tiempo.
había mucho código que no era relevante para el error, así que lo eliminé para que sea más fácil para alguien revisarlo.
juego.js
const socket = io(); var config = { type: Phaser.AUTO, width: 1000, height: 550, parent: 'master', physics: { default: 'arcade', arcade: { gravity: { y: 300 }, debug: true } }, scene: { preload: resources, create: mechanics, update: controls } }; const game = new Phaser.Game(config); function resources() { this.load.image("arena", "../resources/images/arena1.png"); this.load.image("floor", "../resources/images/floor.png"); this.load.atlas("warrior", "../resources/images/characters/warrior.png","../resources/images/characters/warrior.json"); } var warrior; function mechanics() { grasslands = this.add.image(500, 225, "arena").setScale(0.7); warrior = this.physics.add.sprite(100, 490, "warrior").setScale(2).setSize(15, 15); floor = this.physics.add.staticGroup(); floor.create(500, 545, "floor").setVisible(false); this.physics.add.collider(warrior, floor); warrior.body.collideWorldBounds = true; warrior.body.onWorldBounds = true; } function controls() { key = this.input.keyboard.addKeys("W,A,S,D"); if(key.A.isDown) { warrior.setVelocityX(-100); warrior.flipX = true; }else if (key.D.isDown) { warrior.setVelocityX(100); warrior.flipX = false; }else if (key.W.isDown && warrior.body.touching.down) { warrior.setVelocityY(-330); }else{ warrior.setVelocity(0); } }El problema ocurre por esta linea warrior.setVelocity(0); . Esta línea detiene la gravedad del trabajo, según lo previsto (y dificulta el salto) , ya que en las actualizaciones de escena, la velocidad se establece en 0 . Elimine esa línea y agregue warrior.setVelocityX(0) al comienzo de la función de controls y todo debería funcionar bien (si quiere/tiene que mantener el bloque if-else ) . O echa un vistazo a mi demostración de trabajo al final de esta respuesta.
function controls() { key = this.input.keyboard.addKeys("W,A,S,D"); warrior.setVelocityX(0); if(key.A.isDown) { warrior.setVelocityX(-100); warrior.flipX = true; }else if (key.D.isDown) { warrior.setVelocityX(100); warrior.flipX = false; }else if (key.W.isDown && warrior.body.touching.down) { warrior.setVelocityY(-330); } } Solo detendría el movimiento de izquierda/derecha , cuando el jugador deje de presionar las teclas (con setVelocityX(0) ) , y dejaría que la gravedad se encargue de detener el movimiento de salto/hacia arriba.
Aquí una demostración básica:
var config = { type: Phaser.AUTO, width: 400, height: 160, physics: { default: 'arcade', arcade: { gravity: { y: 200 }, } }, scene: { create, update } }; var cursors; var player; var playerStateText; const SPEED = 250; var isJumping = true; function create () { cursors = this.input.keyboard.createCursorKeys(); this.add.text(10, 10, 'Use arrow Keys to move!') let ground = this.add.rectangle(-40, 120, 480, 50, 0xBAF0FF).setOrigin(0); player = this.add.rectangle(20, 20, 30, 30, 0xcccccc).setOrigin(0); ground = this.physics.add.existing(ground); ground.body.setImmovable(true); ground.body.allowGravity = false; player = this.physics.add.existing(player); this.physics.add.collider(player, ground, _ => isJumping = false); } function update (){ if (cursors.left.isDown){ player.body.setVelocityX(-SPEED); } else if (cursors.right.isDown) { player.body.setVelocityX(SPEED); } else { player.body.setVelocityX(0); } if (!isJumping && cursors.up.isDown){ player.body.setVelocityY(-SPEED * .75); isJumping = true; } } new Phaser.Game(config); <script src="//cdn.jsdelivr.net/npm/phaser@3.55.2/dist/phaser.js"></script>