mirror of
https://github.com/WarmUpTill/SceneSwitcher.git
synced 2026-03-21 17:34:57 -05:00
197 lines
4.8 KiB
C++
197 lines
4.8 KiB
C++
#include "macro-condition-run.hpp"
|
|
#include "layout-helpers.hpp"
|
|
|
|
#include <QProcess>
|
|
|
|
namespace advss {
|
|
|
|
const std::string MacroConditionRun::id = "run";
|
|
|
|
bool MacroConditionRun::_registered = MacroConditionFactory::Register(
|
|
MacroConditionRun::id,
|
|
{MacroConditionRun::Create, MacroConditionRunEdit::Create,
|
|
"AdvSceneSwitcher.condition.run"});
|
|
|
|
MacroConditionRun::~MacroConditionRun()
|
|
{
|
|
if (_thread.joinable()) {
|
|
_thread.join();
|
|
}
|
|
}
|
|
|
|
bool MacroConditionRun::CheckCondition()
|
|
{
|
|
if (!_threadDone) {
|
|
return false;
|
|
}
|
|
|
|
bool ret = false;
|
|
|
|
switch (_error) {
|
|
case ProcessConfig::ProcStartError::FAILED_TO_START:
|
|
SetVariableValue("Failed to start process");
|
|
break;
|
|
case ProcessConfig::ProcStartError::TIMEOUT:
|
|
SetVariableValue("Timeout while running process");
|
|
break;
|
|
case ProcessConfig::ProcStartError::CRASH:
|
|
SetVariableValue("Timeout while running process");
|
|
break;
|
|
case ProcessConfig::ProcStartError::NONE:
|
|
ret = _checkExitCode ? _exitCodeToCheck == _procExitCode : true;
|
|
SetVariableValue(std::to_string(_procExitCode));
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
|
|
if (_thread.joinable()) {
|
|
_thread.join();
|
|
}
|
|
_threadDone = false;
|
|
_thread = std::thread(&MacroConditionRun::RunProcess, this);
|
|
|
|
return ret;
|
|
}
|
|
|
|
void MacroConditionRun::RunProcess()
|
|
{
|
|
auto result = _procConfig.StartProcessAndWait(_timeout.Milliseconds());
|
|
|
|
if (std::holds_alternative<ProcessConfig::ProcStartError>(result)) {
|
|
_error = std::get<ProcessConfig::ProcStartError>(result);
|
|
} else {
|
|
_error = ProcessConfig::ProcStartError::NONE;
|
|
_procExitCode = std::get<int>(result);
|
|
}
|
|
_threadDone = true;
|
|
}
|
|
|
|
bool MacroConditionRun::Save(obs_data_t *obj) const
|
|
{
|
|
MacroCondition::Save(obj);
|
|
_procConfig.Save(obj);
|
|
obs_data_set_bool(obj, "checkExitCode", _checkExitCode);
|
|
obs_data_set_int(obj, "exitCode", _exitCodeToCheck);
|
|
_timeout.Save(obj, "timeout");
|
|
return true;
|
|
}
|
|
|
|
bool MacroConditionRun::Load(obs_data_t *obj)
|
|
{
|
|
MacroCondition::Load(obj);
|
|
_procConfig.Load(obj);
|
|
_checkExitCode = obs_data_get_bool(obj, "checkExitCode");
|
|
_exitCodeToCheck = obs_data_get_int(obj, "exitCode");
|
|
_timeout.Load(obj, "timeout");
|
|
return true;
|
|
}
|
|
|
|
std::string MacroConditionRun::GetShortDesc() const
|
|
{
|
|
return _procConfig.UnresolvedPath();
|
|
}
|
|
|
|
MacroConditionRunEdit::MacroConditionRunEdit(
|
|
QWidget *parent, std::shared_ptr<MacroConditionRun> entryData)
|
|
: QWidget(parent),
|
|
_procConfig(new ProcessConfigEdit(this)),
|
|
_checkExitCode(new QCheckBox()),
|
|
_exitCode(new QSpinBox()),
|
|
_timeout(new DurationSelection(this, false, 0.1))
|
|
{
|
|
_exitCode->setMinimum(-99999);
|
|
_exitCode->setMaximum(999999);
|
|
|
|
QWidget::connect(_procConfig,
|
|
SIGNAL(ConfigChanged(const ProcessConfig &)), this,
|
|
SLOT(ProcessConfigChanged(const ProcessConfig &)));
|
|
QWidget::connect(_timeout, SIGNAL(DurationChanged(const Duration &)),
|
|
this, SLOT(TimeoutChanged(const Duration &)));
|
|
QWidget::connect(_checkExitCode, SIGNAL(stateChanged(int)), this,
|
|
SLOT(CheckExitCodeChanged(int)));
|
|
QWidget::connect(_exitCode, SIGNAL(valueChanged(int)), this,
|
|
SLOT(ExitCodeChanged(int)));
|
|
|
|
std::unordered_map<std::string, QWidget *> widgetPlaceholders = {
|
|
{"{{checkExitCode}}", _checkExitCode},
|
|
{"{{exitCode}}", _exitCode},
|
|
{"{{timeout}}", _timeout},
|
|
};
|
|
|
|
auto exitLayout = new QHBoxLayout();
|
|
PlaceWidgets(
|
|
obs_module_text("AdvSceneSwitcher.condition.run.entry.exit"),
|
|
exitLayout, widgetPlaceholders);
|
|
auto timeoutLayout = new QHBoxLayout();
|
|
PlaceWidgets(obs_module_text("AdvSceneSwitcher.condition.run.entry"),
|
|
timeoutLayout, widgetPlaceholders);
|
|
|
|
auto *layout = new QVBoxLayout;
|
|
layout->addLayout(timeoutLayout);
|
|
layout->addWidget(_procConfig);
|
|
layout->addLayout(exitLayout);
|
|
setLayout(layout);
|
|
|
|
_entryData = entryData;
|
|
UpdateEntryData();
|
|
_loading = false;
|
|
}
|
|
|
|
void MacroConditionRunEdit::UpdateEntryData()
|
|
{
|
|
if (!_entryData) {
|
|
return;
|
|
}
|
|
_procConfig->SetProcessConfig(_entryData->_procConfig);
|
|
_timeout->SetDuration(_entryData->_timeout);
|
|
_checkExitCode->setChecked(_entryData->_checkExitCode);
|
|
_exitCode->setValue(_entryData->_exitCodeToCheck);
|
|
}
|
|
|
|
void MacroConditionRunEdit::TimeoutChanged(const Duration &dur)
|
|
{
|
|
if (_loading || !_entryData) {
|
|
return;
|
|
}
|
|
|
|
auto lock = LockContext();
|
|
_entryData->_timeout = dur;
|
|
}
|
|
|
|
void MacroConditionRunEdit::CheckExitCodeChanged(int state)
|
|
{
|
|
if (_loading || !_entryData) {
|
|
return;
|
|
}
|
|
|
|
auto lock = LockContext();
|
|
_entryData->_checkExitCode = state;
|
|
}
|
|
|
|
void MacroConditionRunEdit::ExitCodeChanged(int exitCode)
|
|
{
|
|
if (_loading || !_entryData) {
|
|
return;
|
|
}
|
|
|
|
auto lock = LockContext();
|
|
_entryData->_exitCodeToCheck = exitCode;
|
|
}
|
|
|
|
void MacroConditionRunEdit::ProcessConfigChanged(const ProcessConfig &conf)
|
|
{
|
|
if (_loading || !_entryData) {
|
|
return;
|
|
}
|
|
|
|
auto lock = LockContext();
|
|
_entryData->_procConfig = conf;
|
|
adjustSize();
|
|
updateGeometry();
|
|
emit HeaderInfoChanged(
|
|
QString::fromStdString(_entryData->GetShortDesc()));
|
|
}
|
|
|
|
} // namespace advss
|