obs/source: Refactor old deprecated classes

This commit is contained in:
Michael Fabian 'Xaymar' Dirks 2022-05-14 06:29:41 +02:00
parent 6dd661a41c
commit 9bbc35b293
13 changed files with 1052 additions and 908 deletions

View file

@ -1313,18 +1313,32 @@ list(APPEND PROJECT_PRIVATE_SOURCE
"source/obs/gs/gs-vertex.cpp"
"source/obs/gs/gs-vertexbuffer.hpp"
"source/obs/gs/gs-vertexbuffer.cpp"
"source/obs/obs-encoder-factory.hpp"
"source/obs/obs-encoder-factory.cpp"
"source/obs/obs-signal-handler.hpp"
"source/obs/obs-signal-handler.cpp"
"source/obs/obs-source.hpp"
"source/obs/obs-source.cpp"
"source/obs/obs-source-factory.hpp"
"source/obs/obs-source-factory.cpp"
"source/obs/obs-source-tracker.hpp"
"source/obs/obs-source-tracker.cpp"
"source/obs/obs-tools.hpp"
"source/obs/obs-tools.cpp"
# obs_encoder_info_t, obs_encoder_t, obs_weak_encoder_t
"source/obs/obs-encoder-factory.hpp"
"source/obs/obs-encoder-factory.cpp"
# obs_source_info_t, obs_source_t, obs_weak_source_t
"source/obs/obs-source-factory.hpp"
"source/obs/obs-source-factory.cpp"
"source/obs/obs-source-info.hpp"
"source/obs/obs-source-info.cpp"
"source/obs/obs-source.hpp"
"source/obs/obs-source.cpp"
"source/obs/obs-source-active-child.hpp"
"source/obs/obs-source-active-child.cpp"
"source/obs/obs-source-active-reference.hpp"
"source/obs/obs-source-active-reference.cpp"
"source/obs/obs-source-showing-reference.hpp"
"source/obs/obs-source-showing-reference.cpp"
"source/obs/obs-weak-source.hpp"
"source/obs/obs-weak-source.cpp"
)
list(APPEND PROJECT_DATA
"data/effects/color_conversion_rgb_hsl.effect"

View file

@ -0,0 +1,19 @@
/*
* Copyright (C) 2022 Michael Fabian Dirks
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "obs-source-active-child.hpp"

View file

@ -0,0 +1,49 @@
/*
* Copyright (C) 2022 Michael Fabian Dirks
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#pragma once
#include "common.hpp"
#include "obs-source.hpp"
#include "obs-tools.hpp"
#include "obs-weak-source.hpp"
namespace streamfx::obs {
class source_active_child {
::streamfx::obs::weak_source _parent;
::streamfx::obs::weak_source _child;
public:
~source_active_child()
{
auto parent = _parent.lock();
auto child = _child.lock();
if (parent && child) {
obs_source_remove_active_child(parent, child);
}
}
source_active_child(::streamfx::obs::source const& parent, ::streamfx::obs::source const& child)
: _parent(parent), _child(child)
{
if (::streamfx::obs::tools::source_find_source(child, parent)) {
throw std::runtime_error("Child contains Parent");
} else if (!obs_source_add_active_child(parent, child)) {
throw std::runtime_error("Child contains Parent");
}
}
};
} // namespace streamfx::obs

View file

@ -0,0 +1,19 @@
/*
* Copyright (C) 2022 Michael Fabian Dirks
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "obs-source-active-reference.hpp"

View file

@ -0,0 +1,48 @@
/*
* Copyright (C) 2022 Michael Fabian Dirks
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#pragma once
#include "common.hpp"
#include "obs-source.hpp"
#include "obs-weak-source.hpp"
namespace streamfx::obs {
class source_active_reference {
::streamfx::obs::weak_source _target;
public:
~source_active_reference()
{
auto v = _target.lock();
if (v) {
v.decrement_active();
}
}
source_active_reference(::streamfx::obs::source& source) : _target(source)
{
source.increment_active();
}
public:
static FORCE_INLINE std::shared_ptr<source_active_reference>
add_active_reference(::streamfx::obs::source& source)
{
return std::make_shared<source_active_reference>(source);
}
};
} // namespace streamfx::obs

View file

View file

View file

@ -0,0 +1,19 @@
/*
* Copyright (C) 2022 Michael Fabian Dirks
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "obs-source-showing-reference.hpp"

View file

@ -0,0 +1,49 @@
/*
* Copyright (C) 2022 Michael Fabian Dirks
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#pragma once
#include "common.hpp"
#include "obs-source.hpp"
#include "obs-tools.hpp"
#include "obs-weak-source.hpp"
namespace streamfx::obs {
class source_showing_reference {
::streamfx::obs::weak_source _target;
public:
~source_showing_reference()
{
auto v = _target.lock();
if (v) {
v.decrement_showing();
}
}
source_showing_reference(::streamfx::obs::source& source) : _target(source)
{
source.increment_showing();
}
public:
static FORCE_INLINE std::shared_ptr<source_showing_reference>
add_showing_reference(::streamfx::obs::source& source)
{
return std::make_shared<source_showing_reference>(source);
}
};
} // namespace streamfx::obs

View file

@ -18,816 +18,3 @@
*/
#include "obs-source.hpp"
#include <stdexcept>
#include "plugin.hpp"
void streamfx::obs::deprecated_source::handle_destroy(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
obs_source_t* source;
if (!calldata_get_ptr(calldata, "source", &source)) {
return;
}
if (self->_self == source) {
self->_self = nullptr;
}
if (self->events.destroy) {
return;
}
self->events.destroy(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_remove(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.remove) {
return;
}
self->events.remove(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_save(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.save) {
return;
}
self->events.save(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_load(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.load) {
return;
}
self->events.load(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_activate(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.activate) {
return;
}
self->events.activate(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_deactivate(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.deactivate) {
return;
}
self->events.deactivate(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_show(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.show) {
return;
}
self->events.show(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_hide(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.hide) {
return;
}
self->events.hide(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_enable(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.enable) {
return;
}
bool enabled = false;
if (!calldata_get_bool(calldata, "enabled", &enabled)) {
return;
}
self->events.enable(self, enabled);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_push_to_mute_changed(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.push_to_mute_changed) {
return;
}
bool enabled = false;
if (!calldata_get_bool(calldata, "enabled", &enabled)) {
return;
}
self->events.push_to_mute_changed(self, enabled);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_push_to_mute_delay(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.push_to_mute_delay) {
return;
}
long long delay;
if (!calldata_get_int(calldata, "delay", &delay)) {
return;
}
self->events.push_to_mute_delay(self, delay);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_push_to_talk_changed(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.push_to_talk_changed) {
return;
}
bool enabled = false;
if (!calldata_get_bool(calldata, "enabled", &enabled)) {
return;
}
self->events.push_to_talk_changed(self, enabled);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_push_to_talk_delay(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.push_to_talk_delay) {
return;
}
long long delay;
if (!calldata_get_int(calldata, "delay", &delay)) {
return;
}
self->events.push_to_talk_delay(self, delay);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_rename(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.enable) {
return;
}
const char* new_name;
if (!calldata_get_string(calldata, "new_name", &new_name)) {
return;
}
const char* prev_name;
if (!calldata_get_string(calldata, "prev_name", &prev_name)) {
return;
}
self->events.rename(self, std::string(new_name ? new_name : ""), std::string(prev_name ? prev_name : ""));
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_update_properties(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.update_properties) {
return;
}
self->events.update_properties(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_update_flags(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.update_flags) {
return;
}
long long flags;
if (!calldata_get_int(calldata, "flags", &flags)) {
return;
}
self->events.update_flags(self, flags);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_mute(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.mute) {
return;
}
bool muted;
if (!calldata_get_bool(calldata, "muted", &muted)) {
return;
}
self->events.mute(self, muted);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_volume(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.volume) {
return;
}
double volume;
if (!calldata_get_float(calldata, "volume", &volume)) {
return;
}
self->events.volume(self, volume);
calldata_set_float(calldata, "volume", volume);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_audio_sync(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.audio_sync) {
return;
}
long long mixers;
if (!calldata_get_int(calldata, "offset", &mixers)) {
return;
}
self->events.audio_sync(self, mixers);
calldata_set_int(calldata, "offset", mixers);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_audio_mixers(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.audio_mixers) {
return;
}
long long mixers;
if (!calldata_get_int(calldata, "mixers", &mixers)) {
return;
}
self->events.audio_mixers(self, mixers);
calldata_set_int(calldata, "mixers", mixers);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_audio_data(void* p, obs_source_t*, const audio_data* audio,
bool muted) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.audio) {
return;
}
self->events.audio(self, audio, muted);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_filter_add(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.filter_add) {
return;
}
obs_source_t* filter;
if (!calldata_get_ptr(calldata, "filter", &filter)) {
return;
}
self->events.filter_add(self, filter);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_filter_remove(void* p, calldata_t* calldata) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.filter_remove) {
return;
}
obs_source_t* filter;
if (!calldata_get_ptr(calldata, "filter", &filter)) {
return;
}
self->events.filter_remove(self, filter);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_reorder_filters(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.reorder_filters) {
return;
}
self->events.reorder_filters(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_transition_start(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.transition_start) {
return;
}
self->events.transition_start(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_transition_video_stop(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.transition_video_stop) {
return;
}
self->events.transition_video_stop(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
void streamfx::obs::deprecated_source::handle_transition_stop(void* p, calldata_t*) noexcept
try {
streamfx::obs::deprecated_source* self = reinterpret_cast<streamfx::obs::deprecated_source*>(p);
if (!self->events.transition_stop) {
return;
}
self->events.transition_stop(self);
} catch (const std::exception& ex) {
DLOG_ERROR("Unexpected exception in function '%s': %s.", __FUNCTION_NAME__, ex.what());
} catch (...) {
DLOG_ERROR("Unexpected exception in function '%s'.", __FUNCTION_NAME__);
}
streamfx::obs::deprecated_source::~deprecated_source()
{
#ifdef auto_signal_d
#undef auto_signal_d
#endif
#define auto_signal_d(SIGNAL) this->events.SIGNAL.clear()
auto_signal_d(destroy);
auto_signal_d(remove);
auto_signal_d(save);
auto_signal_d(load);
auto_signal_d(activate);
auto_signal_d(deactivate);
auto_signal_d(show);
auto_signal_d(hide);
auto_signal_d(mute);
auto_signal_d(push_to_mute_changed);
auto_signal_d(push_to_mute_delay);
auto_signal_d(push_to_talk_changed);
auto_signal_d(push_to_talk_delay);
auto_signal_d(enable);
auto_signal_d(rename);
auto_signal_d(volume);
auto_signal_d(update_properties);
auto_signal_d(update_flags);
auto_signal_d(audio_sync);
auto_signal_d(audio_mixers);
auto_signal_d(audio);
auto_signal_d(filter_add);
auto_signal_d(filter_remove);
auto_signal_d(reorder_filters);
auto_signal_d(transition_start);
auto_signal_d(transition_video_stop);
auto_signal_d(transition_stop);
#undef auto_signal_d
if (this->_track_ownership && this->_self) {
obs_source_release(this->_self);
}
this->_self = nullptr;
}
streamfx::obs::deprecated_source::deprecated_source()
{
#ifdef auto_signal_c
#undef auto_signal_c
#endif
#define auto_signal_c(SIGNAL) \
{ \
this->events.SIGNAL.set_listen_callback([this]() noexcept { \
if (!this->_self) \
return; \
auto sh = obs_source_get_signal_handler(this->_self); \
if (sh) { \
signal_handler_connect(sh, "" #SIGNAL, obs::deprecated_source::handle_##SIGNAL, this); \
} \
}); \
this->events.SIGNAL.set_silence_callback([this]() noexcept { \
if (!this->_self) \
return; \
auto sh = obs_source_get_signal_handler(this->_self); \
if (sh) { \
signal_handler_disconnect(sh, "" #SIGNAL, obs::deprecated_source::handle_##SIGNAL, this); \
} \
}); \
}
auto_signal_c(destroy) auto_signal_c(remove) auto_signal_c(save) auto_signal_c(load) auto_signal_c(activate)
auto_signal_c(deactivate) auto_signal_c(show) auto_signal_c(hide) auto_signal_c(mute)
auto_signal_c(push_to_mute_changed) auto_signal_c(push_to_mute_delay) auto_signal_c(push_to_talk_changed)
auto_signal_c(push_to_talk_delay) auto_signal_c(enable) auto_signal_c(rename) auto_signal_c(volume)
auto_signal_c(update_properties) auto_signal_c(update_flags) auto_signal_c(audio_sync)
auto_signal_c(audio_mixers) auto_signal_c(filter_add) auto_signal_c(filter_remove)
auto_signal_c(reorder_filters) auto_signal_c(transition_start)
auto_signal_c(transition_video_stop) auto_signal_c(transition_stop)
#undef auto_signal_c
// libOBS unfortunately does not use the event system for audio data callbacks, which is kind of odd as most other
// things do. So instead we'll have to manually deal with it for now.
{
this->events.audio.set_listen_callback([this]() noexcept {
if (!this->_self)
return;
obs_source_add_audio_capture_callback(this->_self, streamfx::obs::deprecated_source::handle_audio_data,
this);
});
this->events.audio.set_silence_callback([this]() noexcept {
if (!this->_self)
return;
obs_source_remove_audio_capture_callback(this->_self, streamfx::obs::deprecated_source::handle_audio_data,
this);
});
}
}
streamfx::obs::deprecated_source::deprecated_source(std::string name, bool ptrack_ownership, bool add_reference)
: ::streamfx::obs::deprecated_source::deprecated_source()
{
this->_self = obs_get_source_by_name(name.c_str());
if (!this->_self) {
throw std::runtime_error("source with name not found");
}
this->_track_ownership = ptrack_ownership;
if (!add_reference) {
obs_source_release(this->_self);
}
}
streamfx::obs::deprecated_source::deprecated_source(obs_source_t* source, bool ptrack_ownership, bool add_reference)
: ::streamfx::obs::deprecated_source::deprecated_source()
{
this->_self = source;
if (!this->_self) {
throw std::invalid_argument("source must not be null");
}
this->_track_ownership = ptrack_ownership;
if (add_reference) {
obs_source_addref(this->_self);
}
}
/*
obs::deprecated_source::deprecated_source(deprecated_source const& other)
{
this->_self = other._self;
this->_track_ownership = other._track_ownership;
if (this->_track_ownership) {
obs_source_addref(this->_self);
}
#ifdef auto_signal_c
#undef auto_signal_c
#endif
#define auto_signal_c(SIGNAL) this->events.SIGNAL = other.events.SIGNAL
auto_signal_c(destroy);
auto_signal_c(remove);
auto_signal_c(save);
auto_signal_c(load);
auto_signal_c(activate);
auto_signal_c(deactivate);
auto_signal_c(show);
auto_signal_c(hide);
auto_signal_c(mute);
auto_signal_c(push_to_mute_changed);
auto_signal_c(push_to_mute_delay);
auto_signal_c(push_to_talk_changed);
auto_signal_c(push_to_talk_delay);
auto_signal_c(enable);
auto_signal_c(rename);
auto_signal_c(volume);
auto_signal_c(update_properties);
auto_signal_c(update_flags);
auto_signal_c(audio_sync);
auto_signal_c(audio_mixers);
auto_signal_c(audio);
auto_signal_c(filter_add);
auto_signal_c(filter_remove);
auto_signal_c(reorder_filters);
auto_signal_c(transition_start);
auto_signal_c(transition_video_stop);
auto_signal_c(transition_stop);
#undef auto_signal_c
}
obs::deprecated_source& obs::deprecated_source::operator=(deprecated_source const& other)
{
if (this == &other) {
return *this;
}
// Release previous source.
if (this->_self && this->_track_ownership) {
obs_source_release(this->_self);
}
this->_self = other._self;
this->_track_ownership = other._track_ownership;
if (this->_track_ownership) {
obs_source_addref(this->_self);
}
#ifdef auto_signal_c
#undef auto_signal_c
#endif
#define auto_signal_c(SIGNAL) this->events.SIGNAL = other.events.SIGNAL
auto_signal_c(destroy);
auto_signal_c(remove);
auto_signal_c(save);
auto_signal_c(load);
auto_signal_c(activate);
auto_signal_c(deactivate);
auto_signal_c(show);
auto_signal_c(hide);
auto_signal_c(mute);
auto_signal_c(push_to_mute_changed);
auto_signal_c(push_to_mute_delay);
auto_signal_c(push_to_talk_changed);
auto_signal_c(push_to_talk_delay);
auto_signal_c(enable);
auto_signal_c(rename);
auto_signal_c(volume);
auto_signal_c(update_properties);
auto_signal_c(update_flags);
auto_signal_c(audio_sync);
auto_signal_c(audio_mixers);
auto_signal_c(audio);
auto_signal_c(filter_add);
auto_signal_c(filter_remove);
auto_signal_c(reorder_filters);
auto_signal_c(transition_start);
auto_signal_c(transition_video_stop);
auto_signal_c(transition_stop);
#undef auto_signal_c
return *this;
}
*/
streamfx::obs::deprecated_source::deprecated_source(deprecated_source&& other)
: _self(std::move(other._self)), _track_ownership(std::move(other._track_ownership))
{
// Clean out other source
other._self = nullptr;
other._track_ownership = false;
#ifdef auto_signal_c
#undef auto_signal_c
#endif
#define auto_signal_c(SIGNAL) this->events.SIGNAL = std::move(other.events.SIGNAL)
auto_signal_c(destroy);
auto_signal_c(remove);
auto_signal_c(save);
auto_signal_c(load);
auto_signal_c(activate);
auto_signal_c(deactivate);
auto_signal_c(show);
auto_signal_c(hide);
auto_signal_c(mute);
auto_signal_c(push_to_mute_changed);
auto_signal_c(push_to_mute_delay);
auto_signal_c(push_to_talk_changed);
auto_signal_c(push_to_talk_delay);
auto_signal_c(enable);
auto_signal_c(rename);
auto_signal_c(volume);
auto_signal_c(update_properties);
auto_signal_c(update_flags);
auto_signal_c(audio_sync);
auto_signal_c(audio_mixers);
auto_signal_c(audio);
auto_signal_c(filter_add);
auto_signal_c(filter_remove);
auto_signal_c(reorder_filters);
auto_signal_c(transition_start);
auto_signal_c(transition_video_stop);
auto_signal_c(transition_stop);
#undef auto_signal_c
}
streamfx::obs::deprecated_source& streamfx::obs::deprecated_source::operator=(deprecated_source&& other)
{
if (this != &other) {
return *this;
}
// Release previous source.
if (this->_self && this->_track_ownership) {
obs_source_release(this->_self);
}
this->_self = std::move(other._self);
this->_track_ownership = std::move(other._track_ownership);
other._self = nullptr;
other._track_ownership = false;
#ifdef auto_signal_c
#undef auto_signal_c
#endif
#define auto_signal_c(SIGNAL) this->events.SIGNAL = std::move(other.events.SIGNAL)
auto_signal_c(destroy);
auto_signal_c(remove);
auto_signal_c(save);
auto_signal_c(load);
auto_signal_c(activate);
auto_signal_c(deactivate);
auto_signal_c(show);
auto_signal_c(hide);
auto_signal_c(mute);
auto_signal_c(push_to_mute_changed);
auto_signal_c(push_to_mute_delay);
auto_signal_c(push_to_talk_changed);
auto_signal_c(push_to_talk_delay);
auto_signal_c(enable);
auto_signal_c(rename);
auto_signal_c(volume);
auto_signal_c(update_properties);
auto_signal_c(update_flags);
auto_signal_c(audio_sync);
auto_signal_c(audio_mixers);
auto_signal_c(audio);
auto_signal_c(filter_add);
auto_signal_c(filter_remove);
auto_signal_c(reorder_filters);
auto_signal_c(transition_start);
auto_signal_c(transition_video_stop);
auto_signal_c(transition_stop);
#undef auto_signal_c
return *this;
}
obs_source_type streamfx::obs::deprecated_source::type()
{
if (!_self) {
return static_cast<obs_source_type>(-1);
}
return obs_source_get_type(_self);
}
void* streamfx::obs::deprecated_source::type_data()
{
if (!_self) {
return nullptr;
}
return obs_source_get_type_data(_self);
}
uint32_t streamfx::obs::deprecated_source::width()
{
if (!_self) {
return 0;
}
return obs_source_get_width(_self);
}
uint32_t streamfx::obs::deprecated_source::height()
{
if (!_self) {
return 0;
}
return obs_source_get_height(_self);
}
bool streamfx::obs::deprecated_source::destroyed()
{
return _self == nullptr;
}
void streamfx::obs::deprecated_source::clear()
{
_self = nullptr;
}
obs_source_t* streamfx::obs::deprecated_source::get()
{
return _self;
}

View file

@ -19,119 +19,649 @@
#pragma once
#include "common.hpp"
#include "util/util-event.hpp"
namespace streamfx::obs {
class deprecated_source {
obs_source_t* _self;
bool _track_ownership = false;
static void handle_destroy(void* p, calldata_t* calldata) noexcept;
static void handle_remove(void* p, calldata_t* calldata) noexcept;
static void handle_save(void* p, calldata_t* calldata) noexcept;
static void handle_load(void* p, calldata_t* calldata) noexcept;
static void handle_activate(void* p, calldata_t* calldata) noexcept;
static void handle_deactivate(void* p, calldata_t* calldata) noexcept;
static void handle_show(void* p, calldata_t* calldata) noexcept;
static void handle_hide(void* p, calldata_t* calldata) noexcept;
static void handle_enable(void* p, calldata_t* calldata) noexcept;
static void handle_push_to_mute_changed(void* p, calldata_t* calldata) noexcept;
static void handle_push_to_mute_delay(void* p, calldata_t* calldata) noexcept;
static void handle_push_to_talk_changed(void* p, calldata_t* calldata) noexcept;
static void handle_push_to_talk_delay(void* p, calldata_t* calldata) noexcept;
static void handle_rename(void* p, calldata_t* calldata) noexcept;
static void handle_update_properties(void* p, calldata_t* calldata) noexcept;
static void handle_update_flags(void* p, calldata_t* calldata) noexcept;
static void handle_mute(void* p, calldata_t* calldata) noexcept;
static void handle_volume(void* p, calldata_t* calldata) noexcept;
static void handle_audio_sync(void* p, calldata_t* calldata) noexcept;
static void handle_audio_mixers(void* p, calldata_t* calldata) noexcept;
static void handle_audio_data(void* p, obs_source_t* source, const audio_data* audio, bool muted) noexcept;
static void handle_filter_add(void* p, calldata_t* calldata) noexcept;
static void handle_filter_remove(void* p, calldata_t* calldata) noexcept;
static void handle_reorder_filters(void* p, calldata_t* calldata) noexcept;
static void handle_transition_start(void* p, calldata_t* calldata) noexcept;
static void handle_transition_video_stop(void* p, calldata_t* calldata) noexcept;
static void handle_transition_stop(void* p, calldata_t* calldata) noexcept;
class source {
obs_source_t* _ref;
bool _is_owner;
public:
virtual ~deprecated_source();
FORCE_INLINE ~source()
{
release();
};
deprecated_source();
/** Empty/Invalid hard reference.
*
*/
FORCE_INLINE source() : _ref(nullptr), _is_owner(false){};
deprecated_source(std::string name, bool track_ownership = true, bool add_reference = true);
/** Create a new hard reference from an existing pointer.
*
* @param source The source object to reference.
* @param add_reference Should we increment the reference counter (duplicate ownership) or leave as it is (transfer ownership)?
*/
FORCE_INLINE source(obs_source_t* source, bool duplicate_reference = false, bool take_ownership = true)
: _is_owner(take_ownership)
{
if (duplicate_reference) {
_ref = obs_source_get_ref(source);
} else {
_ref = source;
}
};
deprecated_source(obs_source_t* source, bool track_ownership = true, bool add_reference = false);
/** Create a new hard reference for a given source by name.
*
* Attention: May fail if the name does not exactly match.
*/
FORCE_INLINE source(std::string_view name) : _is_owner(true)
{
_ref = obs_get_source_by_name(name.data());
};
public /*copy*/:
deprecated_source(deprecated_source const& other) = delete;
deprecated_source& operator=(deprecated_source const& other) = delete;
/** Create a new hard reference for a new source.
*
* Attention: May fail.
*/
FORCE_INLINE source(std::string_view id, std::string_view name, obs_data_t* settings, obs_data_t* hotkeys)
: _is_owner(true)
{
_ref = obs_source_create(id.data(), name.data(), settings, hotkeys);
if (!_ref) {
throw std::runtime_error("Failed to create source with given parameters.");
}
};
public /*move*/:
deprecated_source(deprecated_source&& other);
deprecated_source& operator=(deprecated_source&& other);
/** Create a new hard reference for a new private source.
*
* Attention: May fail.
*/
FORCE_INLINE source(std::string_view id, std::string_view name, obs_data_t* settings) : _is_owner(true)
{
_ref = obs_source_create_private(id.data(), name.data(), settings);
if (!_ref) {
throw std::runtime_error("Failed to create source with given parameters.");
}
};
FORCE_INLINE source(source&& move) noexcept
{
_ref = move._ref;
_is_owner = move._is_owner;
move._ref = nullptr;
};
FORCE_INLINE ::streamfx::obs::source& operator=(source&& move) noexcept
{
release();
_ref = move._ref;
_is_owner = move._is_owner;
move._ref = nullptr;
return *this;
};
FORCE_INLINE source(const source& copy)
{
if (copy._is_owner) {
_ref = obs_source_get_ref(copy._ref);
} else {
_ref = copy._ref;
}
_is_owner = copy._is_owner;
};
FORCE_INLINE ::streamfx::obs::source& operator=(const source& copy)
{
release();
if (copy._is_owner) {
_ref = obs_source_get_ref(copy._ref);
} else {
_ref = copy._ref;
}
_is_owner = copy._is_owner;
return *this;
};
public:
obs_source_type type();
/** Retrieve the underlying pointer for manual manipulation.
*
* Attention: Ownership remains with the class instance.
*/
FORCE_INLINE obs_source_t* get() const
{
return _ref;
};
void* type_data();
/** Release the underlying pointer.
*
* Useful if you need to respond to the "source_remove" or "remove" signals.
*
* EXPORT void obs_source_release(obs_source_t *source);
*/
FORCE_INLINE void release()
{
if (_ref && _is_owner) {
obs_source_release(_ref);
_ref = nullptr;
_is_owner = false;
}
};
uint32_t width();
uint32_t height();
/** Duplicate the source if possible.
*
* Will create a duplicate the source entirely unless forbidden. If forbidden, will instead just return a reference.
*
* EXPORT obs_source_t *obs_source_duplicate(obs_source_t *source, const char *desired_name, bool create_private);
*/
FORCE_INLINE ::streamfx::obs::source duplicate(std::string_view name, bool is_private)
{
return obs_source_duplicate(_ref, name.data(), is_private);
};
bool destroyed();
public:
/** Get the source info identifier for this reference.
*
* May have a version appended to the end.
*
* EXPORT const char *obs_source_get_id(const obs_source_t *source);
*/
FORCE_INLINE std::string_view id() const
{
return obs_source_get_id(_ref);
};
public: // Unsafe Methods
void clear();
/** Get the source info identifier for this reference.
*
* EXPORT const char *obs_source_get_unversioned_id(const obs_source_t *source);
*/
FORCE_INLINE std::string_view unversioned_id() const
{
return obs_source_get_unversioned_id(_ref);
};
obs_source_t* get();
/** What type is this source?
*
*/
FORCE_INLINE obs_source_type type() const
{
return obs_source_get_type(_ref);
};
public: // Events
struct {
// Destroy and Remove
streamfx::util::event<streamfx::obs::deprecated_source*> destroy;
streamfx::util::event<streamfx::obs::deprecated_source*> remove;
/** Get the output flags.
*
* EXPORT uint32_t obs_source_get_output_flags(const obs_source_t *source);
*/
FORCE_INLINE uint32_t output_flags() const
{
return obs_source_get_output_flags(_ref);
};
// Saving, Loading and Update
streamfx::util::event<streamfx::obs::deprecated_source*> save;
streamfx::util::event<streamfx::obs::deprecated_source*> load;
streamfx::util::event<streamfx::obs::deprecated_source*> update_properties;
/** Get the flags
*
* EXPORT uint32_t obs_source_get_flags(const obs_source_t *source);
*/
FORCE_INLINE uint32_t flags() const
{
return obs_source_get_flags(_ref);
};
// Activate, Deactivate
streamfx::util::event<streamfx::obs::deprecated_source*> activate;
streamfx::util::event<streamfx::obs::deprecated_source*> deactivate;
/** Set the flags
*
* EXPORT void obs_source_set_default_flags(obs_source_t* source, uint32_t flags);
*/
FORCE_INLINE void default_flags(uint32_t flags)
{
obs_source_set_default_flags(_ref, flags);
};
// Show Hide
streamfx::util::event<streamfx::obs::deprecated_source*> show;
streamfx::util::event<streamfx::obs::deprecated_source*> hide;
/** Set the flags
*
* EXPORT void obs_source_set_flags(obs_source_t *source, uint32_t flags);
*/
FORCE_INLINE void flags(uint32_t flags)
{
obs_source_set_flags(_ref, flags);
};
// Other
streamfx::util::event<streamfx::obs::deprecated_source*, bool> enable;
streamfx::util::event<streamfx::obs::deprecated_source*, std::string, std::string> rename;
streamfx::util::event<streamfx::obs::deprecated_source*, long long> update_flags;
/** What is the source type called?
*
* EXPORT const char *obs_source_get_display_name(const char *id);
*/
FORCE_INLINE std::string_view display_name() const
{
return obs_source_get_display_name(id().data());
};
// Hotkeys (PtM, PtT)
streamfx::util::event<streamfx::obs::deprecated_source*, bool> push_to_mute_changed;
streamfx::util::event<streamfx::obs::deprecated_source*, long long> push_to_mute_delay;
streamfx::util::event<streamfx::obs::deprecated_source*, bool> push_to_talk_changed;
streamfx::util::event<streamfx::obs::deprecated_source*, long long> push_to_talk_delay;
/** What is this source called?
*
* EXPORT const char *obs_source_get_name(const obs_source_t *source);
*/
FORCE_INLINE std::string_view name() const
{
return obs_source_get_name(_ref);
};
// Audio
streamfx::util::event<streamfx::obs::deprecated_source*, bool> mute;
streamfx::util::event<streamfx::obs::deprecated_source*, double&> volume;
streamfx::util::event<streamfx::obs::deprecated_source*, long long&> audio_sync;
streamfx::util::event<streamfx::obs::deprecated_source*, long long&> audio_mixers;
streamfx::util::event<streamfx::obs::deprecated_source*, const audio_data*, bool> audio;
/** Change the name of the source.
*
* Triggers 'rename' on the source itself, as well as 'source_rename' globally if not private.
*
* EXPORT void obs_source_set_name(obs_source_t *source, const char *name);
*/
FORCE_INLINE void name(std::string_view new_name)
{
obs_source_set_name(_ref, new_name.data());
};
// Filters
streamfx::util::event<streamfx::obs::deprecated_source*, obs_source_t*> filter_add;
streamfx::util::event<streamfx::obs::deprecated_source*, obs_source_t*> filter_remove;
streamfx::util::event<streamfx::obs::deprecated_source*> reorder_filters;
/**
*
* EXPORT bool obs_source_enabled(const obs_source_t *source);
*/
FORCE_INLINE bool enabled() const
{
return obs_source_enabled(_ref);
};
// Transition
streamfx::util::event<streamfx::obs::deprecated_source*> transition_start;
streamfx::util::event<streamfx::obs::deprecated_source*> transition_video_stop;
streamfx::util::event<streamfx::obs::deprecated_source*> transition_stop;
} events;
/**
*
* EXPORT void obs_source_set_enabled(obs_source_t *source, bool enabled);
*/
FORCE_INLINE void enabled(bool enabled)
{
obs_source_set_enabled(_ref, enabled);
};
/**
*
* EXPORT bool obs_source_is_hidden(obs_source_t *source);
*/
FORCE_INLINE bool hidden() const
{
return obs_source_is_hidden(_ref);
};
/**
*
* EXPORT void obs_source_set_hidden(obs_source_t *source, bool hidden);
*/
FORCE_INLINE void hidden(bool v)
{
obs_source_set_hidden(_ref, v);
};
public /* Size */:
/** Get the base width of the source, if supported.
*
* This will be the size without any other scaling factors applied.
*
* EXPORT uint32_t obs_source_get_base_width(obs_source_t *source);
*/
FORCE_INLINE uint32_t base_width() const
{
return obs_source_get_base_width(_ref);
};
/** Get the base height of the source, if supported.
*
* This will be the size without any other scaling factors applied.
*
* EXPORT uint32_t obs_source_get_base_height(obs_source_t *source);
*/
FORCE_INLINE uint32_t base_height() const
{
return obs_source_get_base_height(_ref);
};
/** Get the reported width of the source, if supported.
*
* EXPORT uint32_t obs_source_get_width(obs_source_t *source);
*/
FORCE_INLINE uint32_t width() const
{
return obs_source_get_width(_ref);
};
/** Get the reported height of the source, if supported.
*
* EXPORT uint32_t obs_source_get_height(obs_source_t *source);
*/
FORCE_INLINE uint32_t height() const
{
return obs_source_get_height(_ref);
};
/** Get the reported size of the source, if supported.
*
* EXPORT uint32_t obs_source_get_width(obs_source_t *source);
* EXPORT uint32_t obs_source_get_height(obs_source_t *source);
*/
FORCE_INLINE std::pair<uint32_t, uint32_t> size() const
{
return {width(), height()};
};
public /* Configuration */:
/** Is the source configurable?
*
* EXPORT bool obs_source_configurable(const obs_source_t *source);
*/
FORCE_INLINE bool configurable()
{
return obs_source_configurable(_ref);
};
/** Retrieve the properties for the source.
*
* EXPORT obs_properties_t *obs_get_source_properties(const char *id);
*/
FORCE_INLINE obs_properties_t* properties()
{
return obs_source_properties(_ref);
};
/** Signal for properties to be updated.
*
* EXPORT void obs_source_update_properties(obs_source_t *source);
*/
FORCE_INLINE void update_properties()
{
obs_source_update_properties(_ref);
};
/** Retrieve the default values for the settings.
*
* EXPORT obs_data_t *obs_get_source_defaults(const char *id);
*/
FORCE_INLINE obs_data_t* defaults()
{
return obs_get_source_defaults(id().data());
};
/** Retrieve the private settings.
*
* EXPORT obs_data_t *obs_source_get_private_settings(obs_source_t *item);
*/
FORCE_INLINE obs_data_t* private_settings()
{
return obs_source_get_private_settings(_ref);
};
/** Retrieve the current settings.
*
* EXPORT obs_data_t *obs_source_get_settings(const obs_source_t *source);
*/
FORCE_INLINE obs_data_t* settings()
{
return obs_source_get_settings(_ref);
};
/** Update the settings with new ones.
*
* Does not remove previously existing entries.
*
* EXPORT void obs_source_update(obs_source_t *source, obs_data_t *settings);
*/
FORCE_INLINE void update(obs_data_t* settings)
{
obs_source_update(_ref, settings);
};
/** Reset the settings, then update with new settings.
*
* EXPORT void obs_source_reset_settings(obs_source_t *source, obs_data_t *settings);
*/
FORCE_INLINE void reset_settings(obs_data_t* settings = nullptr)
{
obs_source_reset_settings(_ref, settings);
};
/** Signal the source to load.
*
* EXPORT void obs_source_load(obs_source_t *source);
*/
FORCE_INLINE void load()
{
obs_source_load(_ref);
};
/** Signal the source and all its filters to load.
*
* EXPORT void obs_source_load2(obs_source_t *source);
*/
FORCE_INLINE void load2()
{
obs_source_load2(_ref);
};
/** Signal the source to save.
*
* EXPORT void obs_source_save(obs_source_t *source);
*/
FORCE_INLINE void save()
{
obs_source_save(_ref);
};
public /* Interaction */:
/**
*
* EXPORT void obs_source_send_mouse_click(obs_source_t *source, const struct obs_mouse_event *event, int32_t type, bool mouse_up, uint32_t click_count);
*/
FORCE_INLINE void send_mouse_press(const obs_mouse_event* event, int32_t type, bool released, uint32_t count)
{
return obs_source_send_mouse_click(_ref, event, type, released, count);
};
/**
*
* EXPORT void obs_source_send_mouse_move(obs_source_t *source, const struct obs_mouse_event *event, bool mouse_leave);
*/
FORCE_INLINE void send_mouse_move(const obs_mouse_event* event, bool leave)
{
return obs_source_send_mouse_move(_ref, event, leave);
};
/**
*
* EXPORT void obs_source_send_mouse_wheel(obs_source_t *source, const struct obs_mouse_event *event, int x_delta, int y_delta);
*/
FORCE_INLINE void send_mouse_wheel(const obs_mouse_event* event, int32_t x_delta, int32_t y_delta)
{
return obs_source_send_mouse_wheel(_ref, event, x_delta, y_delta);
};
/**
*
* EXPORT void obs_source_send_key_click(obs_source_t *source, const struct obs_key_event *event, bool key_up);
*/
FORCE_INLINE void send_key_press(const obs_key_event* event, bool released)
{
return obs_source_send_key_click(_ref, event, released);
};
/**
*
* EXPORT void obs_source_send_focus(obs_source_t *source, bool focus);
*/
FORCE_INLINE void send_focus(bool in_focus)
{
return obs_source_send_focus(_ref, in_focus);
};
public /* Filters */:
/**
*
* EXPORT void obs_source_filter_add(obs_source_t *source, obs_source_t *filter);
*/
FORCE_INLINE void add_filter(::streamfx::obs::source& filter)
{
return obs_source_filter_add(_ref, filter.get());
};
/**
*
* EXPORT void obs_source_filter_remove(obs_source_t *source, obs_source_t *filter);
*/
FORCE_INLINE void remove_filter(::streamfx::obs::source& filter)
{
return obs_source_filter_remove(_ref, filter.get());
};
/**
*
* EXPORT obs_source_t *obs_filter_get_parent(const obs_source_t *filter);
*/
FORCE_INLINE ::streamfx::obs::source get_filter_parent()
{
return obs_filter_get_parent(_ref);
};
/**
*
* EXPORT obs_source_t *obs_filter_get_target(const obs_source_t *filter);
*/
FORCE_INLINE ::streamfx::obs::source get_filter_target()
{
return obs_filter_get_target(_ref);
};
/**
*
* EXPORT void obs_source_skip_video_filter(obs_source_t *filter);
*/
FORCE_INLINE void skip_video_filter()
{
return obs_source_skip_video_filter(_ref);
};
/**
*
* EXPORT bool obs_source_process_filter_begin(obs_source_t *filter, enum gs_color_format format, enum obs_allow_direct_render allow_direct);
*/
FORCE_INLINE bool process_filter_begin(gs_color_format format, obs_allow_direct_render allow_direct)
{
return obs_source_process_filter_begin(_ref, format, allow_direct);
};
/**
*
* EXPORT void obs_source_process_filter_end(obs_source_t *filter, gs_effect_t *effect, uint32_t width, uint32_t height);
*/
FORCE_INLINE void process_filter_end(gs_effect_t* effect, uint32_t width, uint32_t height)
{
obs_source_process_filter_end(_ref, effect, width, height);
};
/**
*
* EXPORT void obs_source_process_filter_tech_end(obs_source_t *filter, gs_effect_t *effect, uint32_t width, uint32_t height, const char *tech_name);
*/
FORCE_INLINE void process_filter_tech_end(gs_effect_t* effect, uint32_t width, uint32_t height,
std::string_view tech_name)
{
obs_source_process_filter_tech_end(_ref, effect, width, height, tech_name.data());
};
public /* Active/Showing References */:
/** Is the source visible in main view?
*
* EXPORT bool obs_source_active(const obs_source_t *source);
*/
FORCE_INLINE bool active() const
{
return obs_source_active(_ref);
}
/** Add a active reference (visible in main view).
*
* EXPORT void obs_source_inc_active(obs_source_t *source);
*/
FORCE_INLINE void increment_active()
{
obs_source_inc_active(_ref);
}
/** Remove a active reference (visible in main view).
*
* EXPORT void obs_source_dec_active(obs_source_t *source);
*/
FORCE_INLINE void decrement_active()
{
obs_source_dec_active(_ref);
}
/** Is the source visible in auxiliary views?
*
* EXPORT bool obs_source_showing(const obs_source_t *source);
*/
FORCE_INLINE bool showing() const
{
return obs_source_showing(_ref);
}
/** Add a showing reference (visible in auxiliary view).
*
* EXPORT void obs_source_inc_showing(obs_source_t *source);
* EXPORT void obs_source_dec_showing(obs_source_t *source);
*/
FORCE_INLINE void increment_showing()
{
obs_source_inc_showing(_ref);
}
/** Add a showing reference (visible in auxiliary view).
*
* EXPORT void obs_source_inc_showing(obs_source_t *source);
* EXPORT void obs_source_dec_showing(obs_source_t *source);
*/
FORCE_INLINE void decrement_showing()
{
obs_source_dec_showing(_ref);
}
public /* ToDo */:
/**
*
* EXPORT obs_missing_files_t* obs_source_get_missing_files(const obs_source_t *source);
*/
obs_missing_files_t* get_missing_files();
/**
*
* EXPORT void obs_source_replace_missing_file(obs_missing_file_cb cb, obs_source_t *source, const char *new_path, void *data);
*/
void replace_missing_file(obs_missing_file_cb cb, std::string_view path, void* data);
public:
FORCE_INLINE operator obs_source_t*() const
{
return _ref;
}
FORCE_INLINE obs_source_t* operator*() const
{
return _ref;
}
FORCE_INLINE operator bool() const
{
return _ref != nullptr;
};
FORCE_INLINE bool operator==(source const& rhs) const
{
return _ref == rhs._ref;
};
FORCE_INLINE bool operator<(source const& rhs) const
{
return _ref < rhs._ref;
};
FORCE_INLINE bool operator==(obs_source_t* const& rhs) const
{
return _ref == rhs;
};
};
} // namespace streamfx::obs

View file

@ -0,0 +1,19 @@
/*
* Copyright (C) 2022 Michael Fabian Dirks
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "obs-weak-source.hpp"

View file

@ -0,0 +1,191 @@
/*
* Copyright (C) 2022 Michael Fabian Dirks
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#pragma once
#include "common.hpp"
#include "obs-source.hpp"
namespace streamfx::obs {
class source;
class weak_source {
obs_weak_source_t* _ref;
public:
~weak_source()
{
if (_ref) {
obs_weak_source_release(_ref);
}
};
/** Empty/Invalid weak reference.
*
*/
weak_source() : _ref(nullptr){};
/** Create a new weak reference from an existing pointer.
*
* Attention: Ownership of obs_weak_source_t is transferred to the class itself, and should not be released.
*/
weak_source(obs_weak_source_t* source) : _ref(source)
{
if (!_ref)
throw std::invalid_argument("Parameter 'source' does not define a valid source.");
};
/** Create a new weak reference from an existing hard reference.
*/
weak_source(obs_source_t* source)
{
_ref = obs_source_get_weak_source(source);
if (!_ref)
throw std::invalid_argument("Parameter 'source' does not define a valid source.");
};
/** Create a new weak reference from an existing hard reference.
*/
weak_source(::streamfx::obs::source& source)
{
_ref = obs_source_get_weak_source(source.get());
if (!_ref)
throw std::invalid_argument("Parameter 'source' does not define a valid source.");
};
/** Create a new weak reference for a given source by name.
*
* Attention: May fail if the name does not exactly match.
*/
weak_source(std::string_view name)
{
std::shared_ptr<obs_source_t> ref{obs_get_source_by_name(name.data()),
[](obs_source_t* v) { obs_source_release(v); }};
if (!ref) {
throw std::invalid_argument("Parameter 'name' does not define an valid source.");
}
_ref = obs_source_get_weak_source(ref.get());
};
weak_source(weak_source&& move) noexcept
{
_ref = move._ref;
move._ref = nullptr;
};
FORCE_INLINE ::streamfx::obs::weak_source& operator=(weak_source&& move) noexcept
{
if (_ref) {
obs_weak_source_release(_ref);
_ref = nullptr;
}
if (move._ref) {
_ref = move._ref;
move._ref = nullptr;
}
return *this;
};
weak_source(const weak_source& copy)
{
_ref = copy._ref;
obs_weak_source_addref(_ref);
};
FORCE_INLINE ::streamfx::obs::weak_source& operator=(const weak_source& copy)
{
if (_ref) {
obs_weak_source_release(_ref);
_ref = nullptr;
}
if (copy._ref) {
_ref = copy._ref;
obs_weak_source_addref(_ref);
}
return *this;
};
/** Retrieve the underlying pointer for manual manipulation.
*
* Attention: Ownership remains with the class instance.
*/
FORCE_INLINE obs_weak_source_t* get() const
{
return _ref;
};
/** Is the weak reference expired?
*
* A weak reference is expired when the original object it is pointing at no longer exists.
*/
FORCE_INLINE bool expired() const
{
return (!_ref) || (obs_weak_source_expired(_ref));
};
/** Try and acquire a hard reference to the source.
*
* May fail if the reference expired before we successfully acquire it.
*/
FORCE_INLINE ::streamfx::obs::source lock() const
{
return {obs_weak_source_get_source(_ref)};
};
public:
FORCE_INLINE operator obs_weak_source_t*() const
{
return _ref;
}
FORCE_INLINE obs_weak_source_t* operator*() const
{
return _ref;
}
FORCE_INLINE operator bool() const
{
return !expired();
};
FORCE_INLINE bool operator==(weak_source const& rhs) const
{
return _ref == rhs._ref;
};
FORCE_INLINE bool operator<(weak_source const& rhs) const
{
return _ref < rhs._ref;
};
FORCE_INLINE bool operator==(obs_weak_source_t* const& rhs) const
{
return _ref == rhs;
};
FORCE_INLINE bool operator==(source const& rhs) const
{
return obs_weak_source_references_source(_ref, rhs.get());
};
FORCE_INLINE bool operator==(obs_source_t* const& rhs) const
{
return obs_weak_source_references_source(_ref, rhs);
};
};
} // namespace streamfx::obs