1 Commits

Author SHA1 Message Date
luchak
348def0b2a Merge 1d89ef8613 into 0878aa3f02 2024-06-12 06:31:05 +00:00
8 changed files with 483 additions and 753 deletions

1151
Cargo.lock generated

File diff suppressed because it is too large Load Diff

View File

@@ -1,6 +1,6 @@
[package] [package]
name = "uw8" name = "uw8"
version = "0.3.1" version = "0.3.0"
edition = "2021" edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
@@ -11,7 +11,7 @@ native = ["wasmtime", "uw8-window", "cpal", "rubato" ]
browser = ["warp", "tokio", "tokio-stream", "webbrowser"] browser = ["warp", "tokio", "tokio-stream", "webbrowser"]
[dependencies] [dependencies]
wasmtime = { git = "https://github.com/bytecodealliance/wasmtime.git", rev = "0f48f939b9870036562ca02ff21253547a9f1a5c", optional = true } wasmtime = { version = "19.0.1", optional = true }
anyhow = "1" anyhow = "1"
env_logger = "0.11.3" env_logger = "0.11.3"
log = "0.4" log = "0.4"

View File

@@ -3,16 +3,14 @@ include "../include/microw8-api.cwa"
export fn upd() { export fn upd() {
let i: i32; let i: i32;
loop pixels { loop pixels {
let inline t = 16!56; let inline t = time() * 63 as f32;
let inline x = (i % 320 - 160) as f32; let lazy x = (i % 320 - 160) as f32;
let inline y = (i #/ 320 - 120) as f32; let lazy y = (i / 320 - 120) as f32;
let inline d = 0xa000 as f32 / sqrt(x * x + y * y); let inline d = 40000 as f32 / sqrt(x * x + y * y);
let inline a = atan2(x, y) * 163_f; // (512 / pi) let inline u = atan2(x, y) * (512.0 / 3.141);
let inline u = i32.trunc_sat_f32_s(a) + t; let inline c = ((i32.trunc_sat_f32_s(d + t * 2 as f32) ^ i32.trunc_sat_f32_s(u + t)) & 255) >> 4;
let inline v = i32.trunc_sat_f32_s(d) + t * 2;
let inline c = ((v ^ u) #/ 16) % 16;
i?FRAMEBUFFER = c; i?FRAMEBUFFER = c;
branch_if (i := i + 1) < 320*240: pixels; branch_if (i := i + 1) < 320*240: pixels;
} }
} }

View File

@@ -21,7 +21,7 @@ loaded.
00000-00040: user memory 00000-00040: user memory
00040-00044: time since module start in ms 00040-00044: time since module start in ms
00044-0004c: gamepad state 00044-0004c: gamepad state
0004c-00050: number of frames since module start 0004c-00050: reserved
00050-00070: sound data (synced to sound thread) 00050-00070: sound data (synced to sound thread)
00070-00078: reserved 00070-00078: reserved
00078-12c78: frame buffer 00078-12c78: frame buffer

File diff suppressed because one or more lines are too long

View File

@@ -27,7 +27,6 @@ struct UW8Instance {
end_frame: TypedFunc<(), ()>, end_frame: TypedFunc<(), ()>,
update: Option<TypedFunc<(), ()>>, update: Option<TypedFunc<(), ()>>,
start_time: Instant, start_time: Instant,
frame_counter: u32,
watchdog: Arc<Mutex<UW8WatchDog>>, watchdog: Arc<Mutex<UW8WatchDog>>,
sound_tx: Option<mpsc::SyncSender<RegisterUpdate>>, sound_tx: Option<mpsc::SyncSender<RegisterUpdate>>,
} }
@@ -160,7 +159,6 @@ impl super::Runtime for MicroW8 {
end_frame, end_frame,
update, update,
start_time: Instant::now(), start_time: Instant::now(),
frame_counter: 0,
watchdog, watchdog,
sound_tx, sound_tx,
}); });
@@ -193,11 +191,8 @@ impl super::Runtime for MicroW8 {
let mem = instance.memory.data_mut(&mut instance.store); let mem = instance.memory.data_mut(&mut instance.store);
mem[64..68].copy_from_slice(&time.to_le_bytes()); mem[64..68].copy_from_slice(&time.to_le_bytes());
mem[68..72].copy_from_slice(&input.gamepads); mem[68..72].copy_from_slice(&input.gamepads);
mem[72..76].copy_from_slice(&instance.frame_counter.to_le_bytes());
} }
instance.frame_counter = instance.frame_counter.wrapping_add(1);
instance.store.set_epoch_deadline(self.timeout as u64); instance.store.set_epoch_deadline(self.timeout as u64);
if let Some(ref update) = instance.update { if let Some(ref update) = instance.update {
if let Err(err) = update.call(&mut instance.store, ()) { if let Err(err) = update.call(&mut instance.store, ()) {
@@ -333,8 +328,9 @@ fn init_sound(
let mut configs: Vec<_> = device let mut configs: Vec<_> = device
.supported_output_configs()? .supported_output_configs()?
.filter(|config| { .filter(|config| {
config.sample_format() == cpal::SampleFormat::F32 config.channels() <= 2
|| config.sample_format() == cpal::SampleFormat::I16 && (config.sample_format() == cpal::SampleFormat::F32
|| config.sample_format() == cpal::SampleFormat::I16)
}) })
.collect(); .collect();
@@ -536,25 +532,6 @@ fn init_sound(
} }
} }
fn stereo_to_surround<F>(mut buffer: &mut [f32], num_channels: usize, callback: &mut F)
where
F: FnMut(&mut [f32]),
{
let mut in_buffer = [0f32; 256];
buffer.fill(0.);
while !buffer.is_empty() {
let step_size = (buffer.len() / num_channels).min(in_buffer.len() / 2);
let step_buffer = &mut in_buffer[..step_size * 2];
callback(step_buffer);
for index in 0..step_size {
buffer[index * num_channels + 0] = step_buffer[index * 2 + 0];
buffer[index * num_channels + 1] = step_buffer[index * 2 + 1];
}
buffer = &mut buffer[step_size * num_channels..];
}
}
let stream = if sample_format == cpal::SampleFormat::F32 { let stream = if sample_format == cpal::SampleFormat::F32 {
if num_channels == 2 { if num_channels == 2 {
device.build_output_stream( device.build_output_stream(
@@ -565,21 +542,10 @@ fn init_sound(
}, },
None, None,
)? )?
} else if num_channels == 1 {
device.build_output_stream(
&config,
move |buffer: &mut [f32], _| stereo_to_mono(buffer, &mut callback),
move |err| {
dbg!(err);
},
None,
)?
} else { } else {
device.build_output_stream( device.build_output_stream(
&config, &config,
move |buffer: &mut [f32], _| { move |buffer: &mut [f32], _| stereo_to_mono(buffer, &mut callback),
stereo_to_surround(buffer, num_channels as usize, &mut callback)
},
move |err| { move |err| {
dbg!(err); dbg!(err);
}, },
@@ -596,24 +562,11 @@ fn init_sound(
}, },
None, None,
)? )?
} else if num_channels == 1 {
device.build_output_stream(
&config,
move |buffer: &mut [i16], _| {
f32_to_i16(buffer, &mut |b| stereo_to_mono(b, &mut callback))
},
move |err| {
dbg!(err);
},
None,
)?
} else { } else {
device.build_output_stream( device.build_output_stream(
&config, &config,
move |buffer: &mut [i16], _| { move |buffer: &mut [i16], _| {
f32_to_i16(buffer, &mut |b| { f32_to_i16(buffer, &mut |b| stereo_to_mono(b, &mut callback))
stereo_to_surround(b, num_channels as usize, &mut callback)
})
}, },
move |err| { move |err| {
dbg!(err); dbg!(err);

View File

@@ -10,7 +10,7 @@
</head> </head>
<body> <body>
<div id="uw8"> <div id="uw8">
<a href="https://exoticorn.github.io/microw8">MicroW8</a> 0.3.1 <a href="https://exoticorn.github.io/microw8">MicroW8</a> 0.3.0
</div> </div>
<div id="centered"> <div id="centered">
<canvas class="screen" id="screen" width="320" height="240"> <canvas class="screen" id="screen" width="320" height="240">

View File

@@ -240,7 +240,6 @@ export default function MicroW8(screen, config = {}) {
await audioReadyPromise; await audioReadyPromise;
let startTime = Date.now(); let startTime = Date.now();
let frameCounter = 0;
const timePerFrame = 1000 / 60; const timePerFrame = 1000 / 60;
@@ -307,7 +306,6 @@ export default function MicroW8(screen, config = {}) {
let time = Date.now() - startTime; let time = Date.now() - startTime;
u32Mem[16] = time; u32Mem[16] = time;
u32Mem[17] = pad | gamepad; u32Mem[17] = pad | gamepad;
u32Mem[18] = frameCounter++;
if(instance.exports.upd) { if(instance.exports.upd) {
instance.exports.upd(); instance.exports.upd();
} }