I'm working on a 2048 game using the Bevy game engine (version 0.10.1), and I've encountered an intermittent issue when rendering the game board. In my code, I have a function display_game_board that iterates through the game board and spawns entities representing each tile. For each tile with a value, I also want to spawn a text entity displaying that value.
To achieve this, I originally used commands.spawn to create the tile entity and then with_children to spawn the text entity as a child of the tile entity. However, I noticed that the text entities were sometimes not rendered properly or were not displayed at all.
Works:
Doesn't work:
In a try too fix this, I attempted to use bevy::ecs::schedule::ShouldRun to insert a delay and spawn the text entities at the end of the frame, however, I learned that bevy::ecs::schedule::ShouldRun is deprecated in Bevy version 0.10.1 and no longer available. This approach doesn't work as expected, and the intermittent issue with rendering of text entities persists.
Given that ShouldRun is deprecated, I'm looking for an alternative method to properly handle the delayed spawning of child entities in Bevy. I suspect that the intermittent rendering issue might be related to the timing of entity construction and how the ECS system processes entities.
fn display_game_board(commands: &mut Commands, game_board: GameBoard, fonts: GameFonts) {
// Calculate the total width and height of the board based on the size of each tile and the number of tiles in a row/column
let tile_size = 100.0; // Adjust the size of each tile as needed
let gap_size = 5.0; // Adjust the size of the gap between tiles as needed
let board_width = (tile_size + gap_size) * game_board.size as f32 - gap_size;
let board_height = (tile_size + gap_size) * game_board.size as f32 - gap_size;
// Calculate the translation vector that centers the board on the screen
let translation = Vec3::new(
(-board_width / 2.0) + (tile_size / 2.0),
(-board_height / 2.0) + (tile_size / 2.0),
0.0,
);
for row in 0..game_board.size {
for col in 0..game_board.size {
// Calculate the translation vector to position each tile in the center of the board
let tile_translation = translation
+ Vec3::new(
col as f32 * (tile_size + gap_size),
row as f32 * (tile_size + gap_size),
0.0,
);
// For each tile, create a sprite representing the tile
commands.spawn(SpriteBundle {
sprite: Sprite {
color: Color::rgba_u8(200, 200, 200, 6).into(), // Default color for empty tiles
custom_size: Some(Vec2::new(tile_size, tile_size)),
..default()
},
transform: Transform::from_translation(tile_translation),
..default()
});
if let Some(value) = game_board.board[row][col] {
// If the tile has a value, create the text to display the value of the tile
let text = value.to_string();
// Calculate the brightness based on the value
let brightness = (value as f32 / 2048.0).min(1.0); // Divide by the maximum value (2048) to get a value between 0 and 1
// For each tile with a value, create a sprite representing the tile with grayscale color
commands
.spawn(SpriteBundle {
sprite: Sprite {
color: Color::rgba(brightness, brightness, brightness, 1.0).into(),
custom_size: Some(Vec2::new(tile_size, tile_size)),
..default()
},
transform: Transform::from_translation(tile_translation),
..default()
})
.with_children(|tile_parent| {
tile_parent.spawn(Text2dBundle {
text: Text::from_section(
text,
TextStyle {
font: fonts.main_font.clone(),
font_size: 40.0,
color: Color::WHITE,
},
),
transform: Transform::from_translation(Vec3 {
x: 0.0,
y: 0.0,
z: 0.0,
}),
visibility: Visibility::Visible,
..default()
});
});
}
}
}
}
Can someone guide me on how to implement a delay for spawning child entities in Bevy version 0.10.1, or suggest another approach to handle this situation?