Skip to content
This repository has been archived by the owner on Dec 11, 2024. It is now read-only.

Commit

Permalink
apply output
Browse files Browse the repository at this point in the history
  • Loading branch information
clouds56 committed Apr 9, 2024
1 parent 6dc1878 commit 9f13699
Show file tree
Hide file tree
Showing 6 changed files with 40 additions and 57 deletions.
67 changes: 22 additions & 45 deletions src/output/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,38 +14,28 @@ use obs_sys::{

use crate::hotkey::HotkeyCallbacks;
use crate::media::{audio::AudioRef, video::VideoRef};
use crate::string::TryIntoObsString;
use crate::{hotkey::Hotkey, prelude::DataObj, string::ObsString, wrapper::PtrWrapper};
use crate::{Error, Result};

#[deprecated = "use `OutputRef` instead"]
pub type OutputContext = OutputRef;

/// Context wrapping an OBS output - video / audio elements which are displayed
/// to the screen.
///
/// See [OBS documentation](https://obsproject.com/docs/reference-outputs.html#c.obs_output_t)
pub struct OutputContext {
pub struct OutputRef {
pub(crate) inner: *mut obs_output_t,
}

impl OutputContext {
/// # Safety
///
/// Pointer must be valid.
pub unsafe fn from_raw(output: *mut obs_output_t) -> Self {
Self {
inner: obs_output_get_ref(output),
}
}
}

impl Clone for OutputContext {
fn clone(&self) -> Self {
unsafe { Self::from_raw(self.inner) }
}
}

impl Drop for OutputContext {
fn drop(&mut self) {
unsafe { obs_output_release(self.inner) }
}
}
impl_ptr_wrapper!(
@ptr: inner,
OutputRef,
obs_output_t,
obs_output_get_ref,
obs_output_release
);

extern "C" fn enum_proc(params: *mut std::ffi::c_void, output: *mut obs_output_t) -> bool {
let mut v = unsafe { Box::<Vec<*mut obs_output_t>>::from_raw(params as *mut _) };
Expand All @@ -54,8 +44,8 @@ extern "C" fn enum_proc(params: *mut std::ffi::c_void, output: *mut obs_output_t
true
}

impl OutputContext {
pub fn new(id: ObsString, name: ObsString, settings: Option<DataObj<'_>>) -> Self {
impl OutputRef {
pub fn new(id: ObsString, name: ObsString, settings: Option<DataObj<'_>>) -> Result<Self> {
let settings = match settings {
Some(data) => unsafe { data.as_ptr_mut() },
None => std::ptr::null_mut(),
Expand All @@ -64,18 +54,19 @@ impl OutputContext {
obs_output_create(id.as_ptr(), name.as_ptr(), settings, std::ptr::null_mut())
};

unsafe { Self::from_raw(output) }
unsafe { Self::from_raw_unchecked(output) }.ok_or(Error::NulPointer("obs_output_cretae"))
}
pub fn all_outputs() -> Vec<Self> {
let outputs = Vec::<*mut obs_output_t>::new();
let params = Box::into_raw(Box::new(outputs));
unsafe {
// `obs_enum_outputs` would return `weak_ref`, so `get_ref` needed
obs_enum_outputs(Some(enum_proc), params as *mut _);
}
let outputs = unsafe { Box::from_raw(params) };
outputs
.into_iter()
.map(|i| unsafe { OutputContext::from_raw(i) })
.filter_map(OutputRef::from_raw)
.collect()
}
pub fn all_types() -> Vec<String> {
Expand All @@ -96,26 +87,12 @@ impl OutputContext {
types
}

pub fn output_id(&self) -> Option<&str> {
unsafe {
let ptr = obs_output_get_id(self.inner);
if ptr.is_null() {
None
} else {
Some(CStr::from_ptr(ptr).to_str().unwrap())
}
}
pub fn output_id(&self) -> Result<ObsString> {
unsafe { obs_output_get_id(self.inner) }.try_into_obs_string()
}

pub fn name(&self) -> Option<&str> {
unsafe {
let ptr = obs_output_get_name(self.inner);
if ptr.is_null() {
None
} else {
Some(CStr::from_ptr(ptr).to_str().unwrap())
}
}
pub fn name(&self) -> Result<ObsString> {
unsafe { obs_output_get_name(self.inner) }.try_into_obs_string()
}

pub fn start(&mut self) -> bool {
Expand Down
13 changes: 8 additions & 5 deletions src/output/ffi.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use super::{traits::*, CreatableOutputContext, OutputContext};
use super::{traits::*, CreatableOutputContext, OutputRef};
use crate::hotkey::{Hotkey, HotkeyCallbacks};
use crate::{data::DataObj, wrapper::PtrWrapper};
use obs_sys::{
Expand Down Expand Up @@ -53,9 +53,10 @@ pub unsafe extern "C" fn create<D: Outputable>(
settings: *mut obs_data_t,
output: *mut obs_output_t,
) -> *mut c_void {
let settings = DataObj::from_raw(settings).unwrap();
// this is later forgotten
let settings = DataObj::from_raw_unchecked(settings).unwrap();
let mut context = CreatableOutputContext::from_raw(settings);
let output_context = OutputContext::from_raw(output);
let output_context = OutputRef::from_raw(output).expect("create");

let data = D::create(&mut context, output_context);
let wrapper = Box::new(DataWrapper::from(data));
Expand Down Expand Up @@ -129,13 +130,15 @@ pub unsafe extern "C" fn encoded_packet<D: EncodedPacketOutput>(

pub unsafe extern "C" fn update<D: UpdateOutput>(data: *mut c_void, settings: *mut obs_data_t) {
let data: &mut DataWrapper<D> = &mut *(data as *mut DataWrapper<D>);
let mut settings = DataObj::from_raw(settings).unwrap();
// this is later forgotten
let mut settings = DataObj::from_raw_unchecked(settings).unwrap();
D::update(&mut data.data, &mut settings);
forget(settings);
}

pub unsafe extern "C" fn get_defaults<D: GetDefaultsOutput>(settings: *mut obs_data_t) {
let mut settings = DataObj::from_raw(settings).unwrap();
// this is later forgotten
let mut settings = DataObj::from_raw_unchecked(settings).unwrap();
D::get_defaults(&mut settings);
forget(settings);
}
Expand Down
4 changes: 2 additions & 2 deletions src/output/traits.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,11 @@ use obs_sys::{audio_data, encoder_packet, video_data};

use crate::{prelude::DataObj, properties::Properties, string::ObsString};

use super::{CreatableOutputContext, OutputContext};
use super::{CreatableOutputContext, OutputRef};

pub trait Outputable: Sized {
fn get_id() -> ObsString;
fn create(context: &mut CreatableOutputContext<'_, Self>, output: OutputContext) -> Self;
fn create(context: &mut CreatableOutputContext<'_, Self>, output: OutputRef) -> Self;

fn start(&mut self) -> bool {
true
Expand Down
8 changes: 5 additions & 3 deletions src/source/ffi.rs
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,8 @@ pub unsafe extern "C" fn create<D: Sourceable>(
source: *mut obs_source_t,
) -> *mut c_void {
let mut global = GlobalContext;
let settings = DataObj::from_raw(settings).unwrap();
// this is later forgotten
let settings = DataObj::from_raw_unchecked(settings).unwrap();
let mut context = CreatableSourceContext::from_raw(settings, &mut global);
let source_context = SourceRef::from_raw(source).expect("create");

Expand Down Expand Up @@ -115,7 +116,7 @@ pub unsafe extern "C" fn destroy<D>(data: *mut c_void) {
pub unsafe extern "C" fn update<D: UpdateSource>(data: *mut c_void, settings: *mut obs_data_t) {
let mut global = GlobalContext;
let data: &mut DataWrapper<D> = &mut *(data as *mut DataWrapper<D>);
let mut settings = DataObj::from_raw(settings).unwrap();
let mut settings = DataObj::from_raw_unchecked(settings).unwrap();
D::update(&mut data.data, &mut settings, &mut global);
forget(settings);
}
Expand Down Expand Up @@ -252,7 +253,8 @@ impl_media!(
);

pub unsafe extern "C" fn get_defaults<D: GetDefaultsSource>(settings: *mut obs_data_t) {
let mut settings = DataObj::from_raw(settings).unwrap();
// this is later forgotten
let mut settings = DataObj::from_raw_unchecked(settings).unwrap();
D::get_defaults(&mut settings);
forget(settings);
}
Expand Down
1 change: 1 addition & 0 deletions src/source/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,7 @@ impl SourceRef {
pub fn do_with_target<F: FnOnce(&mut SourceRef)>(&mut self, func: F) {
unsafe {
if let Ok(SourceType::Filter) = SourceType::from_raw(obs_source_get_type(self.inner)) {
// doc says "Does not increment the reference."
let target = obs_filter_get_target(self.inner);
if let Some(mut context) = SourceRef::from_raw(target) {
func(&mut context);
Expand Down
4 changes: 2 additions & 2 deletions src/wrapper.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,8 @@ pub trait PtrWrapperInternal: PtrWrapper {
unsafe fn new_internal(ptr: *mut Self::Pointer) -> Self;
/// # Safety
///
/// This function should not be called directly, use `from_raw` and
/// `from_raw_unchecked` instead.
/// This function should not be called directly, use `as_ptr`,
/// `as_ptr_mut` and `into_raw` instead.
unsafe fn get_internal(&self) -> *mut Self::Pointer;
}

Expand Down

0 comments on commit 9f13699

Please sign in to comment.