use crate::*;
use crate::d3d9::*;
use winapi::shared::d3d9::IDirect3DResource9;
use winapi::shared::guiddef::GUID;
use winapi::um::unknwnbase::IUnknown;
use std::convert::TryInto;
use std::ptr::null_mut;
#[derive(Clone)] #[repr(transparent)]
pub struct Resource(pub(crate) mcom::Rc<IDirect3DResource9>);
unsafe impl AsSafe<IUnknown > for Resource { fn as_safe(&self) -> &IUnknown { &**self.0 } }
unsafe impl AsSafe<IDirect3DResource9 > for Resource { fn as_safe(&self) -> &IDirect3DResource9 { &*self.0 } }
impl Resource {
pub fn check_compatible_with(&self, device: &impl IDirect3DDevice9Ext, method: &'static str) -> Result<(), MethodError> {
let my_device = self.get_device()?;
if my_device.as_raw() == device.as_winapi() as *const _ as *mut _ {
Ok(())
} else {
Err(MethodError(method, THINERR::DEVICE_MISMATCH))
}
}
}
pub trait IDirect3DResource9Ext : AsSafe<IDirect3DResource9> {
fn free_private_data(&self, guid: &GUID) -> Result<(), MethodError> {
let hr = unsafe { self.as_winapi().FreePrivateData(guid) };
MethodError::check("IDirect3DResource9::FreePrivateData", hr)
}
fn get_device(&self) -> Result<Device, MethodError> {
let mut device = null_mut();
let hr = unsafe { self.as_winapi().GetDevice(&mut device) };
MethodError::check("IDirect3DResource9::GetDevice", hr)?;
Ok(unsafe { Device::from_raw(device) })
}
fn get_priority(&self) -> u32 {
unsafe { self.as_winapi().GetPriority() }
}
fn get_private_data_inplace<'s>(&self, guid: &GUID, data: &'s mut [u8]) -> Result<&'s [u8], MethodError> {
let mut n : u32 = data.len().try_into().map_err(|_| MethodError("Resource::get_private_data_inplace", THINERR::SLICE_OVERFLOW))?;
let hr = unsafe { self.as_winapi().GetPrivateData(guid, data.as_mut_ptr().cast(), &mut n) };
MethodError::check("IDirect3DResource9::GetPrivateData", hr)?;
Ok(&data[..(n as usize)])
}
fn get_type(&self) -> ResourceType {
ResourceType::from_unchecked(unsafe { self.as_winapi().GetType() })
}
fn preload(&self) {
unsafe { self.as_winapi().PreLoad() }
}
fn set_priority(&self, priority: u32) -> u32 {
unsafe { self.as_winapi().SetPriority(priority) }
}
fn set_private_data(&self, guid: &GUID, data: &[u8]) -> Result<(), MethodError> {
let n : u32 = data.len().try_into().map_err(|_| MethodError("Resource::set_private_data", THINERR::SLICE_OVERFLOW))?;
let hr = unsafe { self.as_winapi().SetPrivateData(guid, data.as_ptr().cast(), n, 0) };
MethodError::check("IDirect3DResource9::SetPrivateData", hr)
}
}
impl<T: AsSafe<IDirect3DResource9>> IDirect3DResource9Ext for T {}