pausing and unpausing

This commit is contained in:
りき萌 2023-05-01 13:15:07 +02:00
parent 32f3c692b8
commit 015e3fb8d7
5 changed files with 77 additions and 3 deletions

View file

@ -0,0 +1,23 @@
package net.liquidev.dawd3.events;
import net.fabricmc.api.EnvType;
import net.fabricmc.api.Environment;
import net.fabricmc.fabric.api.event.Event;
import net.fabricmc.fabric.api.event.EventFactory;
@Environment(EnvType.CLIENT)
public class D3ClientEvents {
public static Event<Pause> PAUSE = EventFactory.createArrayBacked(
Pause.class,
context -> {},
callbacks -> paused -> {
for (Pause callback : callbacks) {
callback.pause(paused);
}
}
);
public interface Pause {
void pause(boolean paused);
}
}

View file

@ -0,0 +1,26 @@
package net.liquidev.dawd3.mixin;
import net.liquidev.dawd3.events.D3ClientEvents;
import net.minecraft.client.MinecraftClient;
import org.objectweb.asm.Opcodes;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
@Mixin(MinecraftClient.class)
public class PauseMixin {
@Inject(
method = "render(Z)V",
at = @At(
value = "FIELD",
target = "Lnet/minecraft/client/MinecraftClient;paused:Z",
opcode = Opcodes.PUTFIELD,
shift = At.Shift.AFTER
)
)
private void onPause(boolean tick, CallbackInfo ci) {
var client = (MinecraftClient) (Object) this;
D3ClientEvents.PAUSE.invoker().pause(client.isPaused());
}
}

View file

@ -4,7 +4,9 @@ import net.liquidev.d3r.D3r
import net.liquidev.dawd3.Mod
import net.liquidev.dawd3.audio.generator.GeneratorWithProcessingState
import net.liquidev.dawd3.audio.generator.MixGenerator
import net.liquidev.dawd3.audio.generator.PausableGenerator
import net.liquidev.dawd3.audio.unit.Frequency
import net.liquidev.dawd3.events.D3ClientEvents
/** Audio system and common settings. */
object Audio {
@ -23,19 +25,21 @@ object Audio {
val mixer = MixGenerator()
private val processingStateAdapter = GeneratorWithProcessingState(mixer)
val processingState get() = processingStateAdapter.processingState
private val pauseAdapter = PausableGenerator(processingStateAdapter)
init {
logger.info("initializing")
D3r.openDefaultHost()
outputDeviceId = D3r.openDefaultOutputDevice()
outputStreamId =
D3r.openOutputStream(outputDeviceId, sampleRate, 1, bufferSize, processingStateAdapter)
D3r.openOutputStream(outputDeviceId, sampleRate, 1, bufferSize, pauseAdapter)
D3r.startPlayback(outputStreamId)
}
fun initializeClient() {
// Stubbed out; this is called explicitly to force the otherwise lazy initialization
// of Audio.
D3ClientEvents.PAUSE.register { isPaused ->
pauseAdapter.playing = !isPaused
}
}
fun deinitialize() {

View file

@ -0,0 +1,20 @@
package net.liquidev.dawd3.audio.generator
import java.util.concurrent.atomic.AtomicBoolean
class PausableGenerator(val inner: AudioGenerator) : AudioGenerator() {
private val internalPlaying = AtomicBoolean(true)
var playing: Boolean
get() = internalPlaying.get()
set(value) = internalPlaying.set(value)
override fun generate(output: FloatArray, sampleCount: Int, channelCount: Int) {
if (playing) {
inner.generate(output, sampleCount, channelCount)
} else {
for (i in 0 until (sampleCount * channelCount)) {
output[i] = 0f
}
}
}
}

View file

@ -6,6 +6,7 @@
"defaultRequire": 1
},
"mixins": [
"PauseMixin",
"PlayerItemSwitchMixin"
]
}