mirror of
https://github.com/Jozufozu/Flywheel.git
synced 2025-01-13 07:46:07 +01:00
DeDelleetete
- Process instancer deletions in parallel - Give DrawManagers a frame plan
This commit is contained in:
parent
7bd59f7b14
commit
48fdcdb751
7 changed files with 16 additions and 19 deletions
|
@ -160,7 +160,7 @@ public abstract class AbstractInstancer<I extends Instance> implements Instancer
|
||||||
deleted.set(index);
|
deleted.set(index);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void removeDeletedInstances() {
|
public void removeDeletedInstances() {
|
||||||
if (deleted.isEmpty()) {
|
if (deleted.isEmpty()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,14 +10,17 @@ import java.util.concurrent.ConcurrentLinkedQueue;
|
||||||
|
|
||||||
import com.mojang.datafixers.util.Pair;
|
import com.mojang.datafixers.util.Pair;
|
||||||
|
|
||||||
|
import dev.engine_room.flywheel.api.RenderContext;
|
||||||
import dev.engine_room.flywheel.api.backend.Engine;
|
import dev.engine_room.flywheel.api.backend.Engine;
|
||||||
import dev.engine_room.flywheel.api.instance.Instance;
|
import dev.engine_room.flywheel.api.instance.Instance;
|
||||||
import dev.engine_room.flywheel.api.instance.InstanceType;
|
import dev.engine_room.flywheel.api.instance.InstanceType;
|
||||||
import dev.engine_room.flywheel.api.model.Model;
|
import dev.engine_room.flywheel.api.model.Model;
|
||||||
|
import dev.engine_room.flywheel.api.task.Plan;
|
||||||
import dev.engine_room.flywheel.api.visualization.VisualType;
|
import dev.engine_room.flywheel.api.visualization.VisualType;
|
||||||
import dev.engine_room.flywheel.backend.FlwBackend;
|
import dev.engine_room.flywheel.backend.FlwBackend;
|
||||||
import dev.engine_room.flywheel.backend.engine.embed.Environment;
|
import dev.engine_room.flywheel.backend.engine.embed.Environment;
|
||||||
import dev.engine_room.flywheel.backend.engine.embed.EnvironmentStorage;
|
import dev.engine_room.flywheel.backend.engine.embed.EnvironmentStorage;
|
||||||
|
import dev.engine_room.flywheel.lib.task.ForEachPlan;
|
||||||
import it.unimi.dsi.fastutil.ints.Int2ObjectArrayMap;
|
import it.unimi.dsi.fastutil.ints.Int2ObjectArrayMap;
|
||||||
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
|
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
|
||||||
import net.minecraft.client.resources.model.ModelBakery;
|
import net.minecraft.client.resources.model.ModelBakery;
|
||||||
|
@ -45,6 +48,11 @@ public abstract class DrawManager<N extends AbstractInstancer<?>> {
|
||||||
return (AbstractInstancer<I>) instancers.computeIfAbsent(key, this::createAndDeferInit);
|
return (AbstractInstancer<I>) instancers.computeIfAbsent(key, this::createAndDeferInit);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Plan<RenderContext> createFramePlan() {
|
||||||
|
// Go wide on instancers to process deletions in parallel.
|
||||||
|
return ForEachPlan.of(() -> new ArrayList<>(instancers.values()), AbstractInstancer::removeDeletedInstances);
|
||||||
|
}
|
||||||
|
|
||||||
public void flush(LightStorage lightStorage, EnvironmentStorage environmentStorage) {
|
public void flush(LightStorage lightStorage, EnvironmentStorage environmentStorage) {
|
||||||
// Thread safety: flush is called from the render thread after all visual updates have been made,
|
// Thread safety: flush is called from the render thread after all visual updates have been made,
|
||||||
// so there are no:tm: threads we could be racing with.
|
// so there are no:tm: threads we could be racing with.
|
||||||
|
|
|
@ -50,7 +50,8 @@ public class EngineImpl implements Engine {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Plan<RenderContext> createFramePlan() {
|
public Plan<RenderContext> createFramePlan() {
|
||||||
return lightStorage.createFramePlan();
|
return drawManager.createFramePlan()
|
||||||
|
.and(lightStorage.createFramePlan());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -64,7 +64,6 @@ public class IndirectCullingGroup<I extends Instance> {
|
||||||
int modelIndex = 0;
|
int modelIndex = 0;
|
||||||
for (var iterator = instancers.iterator(); iterator.hasNext(); ) {
|
for (var iterator = instancers.iterator(); iterator.hasNext(); ) {
|
||||||
var instancer = iterator.next();
|
var instancer = iterator.next();
|
||||||
instancer.update();
|
|
||||||
var instanceCount = instancer.instanceCount();
|
var instanceCount = instancer.instanceCount();
|
||||||
|
|
||||||
if (instanceCount == 0) {
|
if (instanceCount == 0) {
|
||||||
|
@ -73,7 +72,7 @@ public class IndirectCullingGroup<I extends Instance> {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
instancer.postUpdate(modelIndex, instanceCountThisFrame);
|
instancer.update(modelIndex, instanceCountThisFrame);
|
||||||
instanceCountThisFrame += instanceCount;
|
instanceCountThisFrame += instanceCount;
|
||||||
|
|
||||||
modelIndex++;
|
modelIndex++;
|
||||||
|
@ -172,7 +171,7 @@ public class IndirectCullingGroup<I extends Instance> {
|
||||||
|
|
||||||
public void add(IndirectInstancer<I> instancer, InstancerKey<I> key, MeshPool meshPool) {
|
public void add(IndirectInstancer<I> instancer, InstancerKey<I> key, MeshPool meshPool) {
|
||||||
instancer.mapping = buffers.objectStorage.createMapping();
|
instancer.mapping = buffers.objectStorage.createMapping();
|
||||||
instancer.postUpdate(instancers.size(), -1);
|
instancer.update(instancers.size(), -1);
|
||||||
|
|
||||||
instancers.add(instancer);
|
instancers.add(instancer);
|
||||||
|
|
||||||
|
|
|
@ -55,11 +55,7 @@ public class IndirectInstancer<I extends Instance> extends AbstractInstancer<I>
|
||||||
return associatedDraws;
|
return associatedDraws;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void update() {
|
public void update(int modelIndex, int baseInstance) {
|
||||||
removeDeletedInstances();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void postUpdate(int modelIndex, int baseInstance) {
|
|
||||||
this.modelIndex = modelIndex;
|
this.modelIndex = modelIndex;
|
||||||
this.baseInstance = baseInstance;
|
this.baseInstance = baseInstance;
|
||||||
mapping.update(modelIndex, instanceCount());
|
mapping.update(modelIndex, instanceCount());
|
||||||
|
|
|
@ -65,13 +65,11 @@ public class InstancedDrawManager extends DrawManager<InstancedInstancer<?>> {
|
||||||
|
|
||||||
this.instancers.values()
|
this.instancers.values()
|
||||||
.removeIf(instancer -> {
|
.removeIf(instancer -> {
|
||||||
// Update the instancers and remove any that are empty.
|
|
||||||
instancer.update();
|
|
||||||
|
|
||||||
if (instancer.instanceCount() == 0) {
|
if (instancer.instanceCount() == 0) {
|
||||||
instancer.delete();
|
instancer.delete();
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
|
instancer.updateBuffer();
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
|
@ -44,12 +44,7 @@ public class InstancedInstancer<I extends Instance> extends AbstractInstancer<I>
|
||||||
vbo = new GlBuffer(GlBufferUsage.DYNAMIC_DRAW);
|
vbo = new GlBuffer(GlBufferUsage.DYNAMIC_DRAW);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void update() {
|
public void updateBuffer() {
|
||||||
removeDeletedInstances();
|
|
||||||
updateBuffer();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void updateBuffer() {
|
|
||||||
if (changed.isEmpty() || vbo == null) {
|
if (changed.isEmpty() || vbo == null) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue