use vst3::{
ComRef,
Steinberg::{IBStream, IBStream_::IStreamSeekMode_::kIBSeekSet, IBStreamTrait},
};
use crate::enum_to_i32;
pub struct StreamWrite<'a> {
buffer: ComRef<'a, IBStream>,
}
impl<'a> StreamWrite<'a> {
pub fn new(buffer: ComRef<'a, IBStream>) -> Self {
Self { buffer }
}
}
impl std::io::Write for StreamWrite<'_> {
fn write(&mut self, buf: &[u8]) -> std::io::Result<usize> {
unsafe {
let mut num_written = 0;
match self.buffer.write(
buf.as_ptr() as *mut std::ffi::c_void,
buf.len().try_into().unwrap(),
&raw mut num_written,
) {
vst3::Steinberg::kResultOk => Ok(num_written.try_into().unwrap()),
_ => Err(std::io::Error::other("VST3 write error")),
}
}
}
fn flush(&mut self) -> std::io::Result<()> {
std::io::Result::Ok(())
}
}
#[derive(Clone)]
pub struct StreamRead<'a> {
buffer: ComRef<'a, IBStream>,
}
impl<'a> StreamRead<'a> {
pub fn new(buffer: ComRef<'a, IBStream>) -> Self {
Self { buffer }
}
pub fn seek_to_start(&self) -> std::io::Result<()> {
unsafe {
let result =
self.buffer
.seek(0, enum_to_i32(kIBSeekSet).unwrap(), std::ptr::null_mut());
if result == vst3::Steinberg::kResultOk {
Ok(())
} else {
Err(std::io::Error::other("VST3 seek error"))
}
}
}
}
impl std::io::Read for StreamRead<'_> {
fn read(&mut self, buf: &mut [u8]) -> std::io::Result<usize> {
unsafe {
let mut num_read = 0;
match self.buffer.read(
buf.as_mut_ptr().cast::<std::ffi::c_void>(),
buf.len().try_into().unwrap(),
&raw mut num_read,
) {
vst3::Steinberg::kResultOk => Ok(num_read.try_into().unwrap()),
_ => Err(std::io::Error::other("VST3 read error")),
}
}
}
}