Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Loading terrain takes exactly 30 seconds #625

Open
EliiasG opened this issue Jun 26, 2024 · 2 comments
Open

Loading terrain takes exactly 30 seconds #625

EliiasG opened this issue Jun 26, 2024 · 2 comments
Labels
bug Something isn't working triage Bug has not been confirmed as real issue yet

Comments

@EliiasG
Copy link

EliiasG commented Jun 26, 2024

Valence Version

valence#1331a790

Overview

When changing the layer of a client to be a layer with a different dimension, the client says "loading terrain..." for what seems like exactly 30 seconds, no matter how many chunks are in the new layer.

At first i thought it might be built into the client, but i tested both in singleplayer and with a vanilla 1.20.1 server, and in both cases it loaded pretty much instantly.

My theory

I do not know much about how minecraft for valence works under the hood, but to me it seems like the 30 seconds might be a maximum time for if the server never says its done loading.

Example code (sneaking changes dimension)
use valence::prelude::*;

const SPAWN_Y: i32 = 50;

#[derive(Component)]
struct Overworld;

#[derive(Resource)]
struct Overworld(Entity);

#[derive(Resource)]
struct End(Entity);

fn main() {
    App::new()
        .add_plugins(DefaultPlugins)
        .add_systems(Startup, setup)
        .add_systems(
            Update,
            (init_clients, despawn_disconnected_clients, change_on_sneak),
        )
        .run();
}

fn setup(
    mut commands: Commands,
    server: Res<Server>,
    dimensions: Res<DimensionTypeRegistry>,
    biomes: Res<BiomeRegistry>,
) {
    let mut overworld_layer = LayerBundle::new(ident!("overworld"), &dimensions, &biomes, &server);
    let mut end_layer = LayerBundle::new(ident!("the_end"), &dimensions, &biomes, &server);

    for z in -15..15 {
        for x in -15..15 {
            overworld_layer
                .chunk
                .insert_chunk([x, z], UnloadedChunk::new());
            end_layer.chunk.insert_chunk([x, z], UnloadedChunk::new());
        }
    }

    end_layer
        .chunk
        .set_block([0, SPAWN_Y, 0], BlockState::BEDROCK);
    overworld_layer
        .chunk
        .set_block([0, SPAWN_Y, 0], BlockState::BEDROCK);

    let overworld = commands.spawn((overworld_layer, OverworldId)).id();
    let end = commands.spawn(end_layer).id();
    commands.insert_resource(Overworld(overworld));
    commands.insert_resource(End(end));
}

fn init_clients(
    mut clients: Query<
        (
            &mut EntityLayerId,
            &mut VisibleChunkLayer,
            &mut VisibleEntityLayers,
            &mut Position,
            &mut GameMode,
        ),
        Added<Client>,
    >,
    layers: Query<Entity, (With<ChunkLayer>, With<EntityLayer>, With<OverworldId>)>,
) {
    for (
        mut layer_id,
        mut visible_chunk_layer,
        mut visible_entity_layers,
        mut pos,
        mut game_mode,
    ) in &mut clients
    {
        let layer = layers.single();

        layer_id.0 = layer;
        visible_chunk_layer.0 = layer;
        visible_entity_layers.0.insert(layer);
        pos.set([0.0, SPAWN_Y as f64 + 1.0, 0.0]);
        *game_mode = GameMode::Creative;
    }
}

fn change_on_sneak(
    mut events: EventReader<SneakEvent>,
    mut clients: Query<(
        &mut EntityLayerId,
        &mut VisibleChunkLayer,
        &mut VisibleEntityLayers,
        &mut Position,
    )>,
    layers: Query<Has<OverworldId>>,
    overworld: Res<Overworld>,
    end: Res<End>,
) {
    for event in events.read() {
        if event.state != SneakState::Start {
            continue;
        }
        let (mut cur_layer, mut chunk_layer, mut entity_layers, mut pos) =
            clients.get_mut(event.client).unwrap();
        entity_layers.0.remove(&cur_layer.0);
        let new_layer = if layers.get(cur_layer.0).unwrap() {
            end.0
        } else {
            overworld.0
        };
        cur_layer.0 = new_layer;
        chunk_layer.0 = new_layer;
        entity_layers.0.insert(new_layer);
        pos.set([0.0, SPAWN_Y as f64 + 50.0, 0.0]);
    }
}
@EliiasG EliiasG added bug Something isn't working triage Bug has not been confirmed as real issue yet labels Jun 26, 2024
@EliiasG
Copy link
Author

EliiasG commented Jun 26, 2024

Also the flying speed (set with the FlyingSpeed component) of the Client seems to reset when changing layers, even if dimensions do not change

@andrewgazelka
Copy link

andrewgazelka commented Oct 29, 2024

@EliiasG only one region file can be loaded at a time I'm pretty sure (or there is some limiting factor that is similar to this). I had to do modifications to fix this as it is was a perf concern.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working triage Bug has not been confirmed as real issue yet
Projects
None yet
Development

No branches or pull requests

2 participants