mirror of
https://github.com/WarmUpTill/SceneSwitcher.git
synced 2026-03-21 17:34:57 -05:00
Cleanup screenshot helper
This commit is contained in:
parent
c39ea0854a
commit
55ab096e49
|
|
@ -105,7 +105,7 @@ void AdvSceneSwitcher::on_getScreenshot_clicked()
|
|||
}
|
||||
|
||||
auto source = obs_weak_source_get_source(s->videoSource);
|
||||
auto screenshotData = std::make_unique<ScreenshotHelper>(source);
|
||||
auto screenshotData = std::make_unique<Screenshot>(source);
|
||||
obs_source_release(source);
|
||||
|
||||
QString filePath = QFileDialog::getSaveFileName(this);
|
||||
|
|
@ -121,16 +121,16 @@ void AdvSceneSwitcher::on_getScreenshot_clicked()
|
|||
// During selection of the save path enough time should usually have
|
||||
// passed already
|
||||
// Add this just in case ...
|
||||
if (!screenshotData->done) {
|
||||
if (!screenshotData->IsDone()) {
|
||||
std::this_thread::sleep_for(std::chrono::seconds(1));
|
||||
}
|
||||
|
||||
if (!screenshotData->done) {
|
||||
if (!screenshotData->IsDone()) {
|
||||
DisplayMessage("Failed to get screenshot of source!");
|
||||
return;
|
||||
}
|
||||
|
||||
screenshotData->image.save(file.fileName());
|
||||
screenshotData->GetImage().save(file.fileName());
|
||||
sw->SetFilePath(file.fileName());
|
||||
}
|
||||
|
||||
|
|
@ -262,7 +262,7 @@ void VideoSwitch::load(obs_data_t *obj)
|
|||
void VideoSwitch::getScreenshot()
|
||||
{
|
||||
auto source = obs_weak_source_get_source(videoSource);
|
||||
screenshotData = std::make_unique<ScreenshotHelper>(source);
|
||||
screenshotData = std::make_unique<Screenshot>(source);
|
||||
obs_source_release(source);
|
||||
}
|
||||
|
||||
|
|
@ -293,56 +293,55 @@ bool VideoSwitch::checkMatch()
|
|||
|
||||
bool match = false;
|
||||
|
||||
if (screenshotData) {
|
||||
if (screenshotData->done) {
|
||||
bool conditionMatch = false;
|
||||
|
||||
switch (condition) {
|
||||
case videoSwitchType::MATCH:
|
||||
conditionMatch = screenshotData->image ==
|
||||
matchImage;
|
||||
break;
|
||||
case videoSwitchType::DIFFER:
|
||||
conditionMatch = screenshotData->image !=
|
||||
matchImage;
|
||||
break;
|
||||
case videoSwitchType::HAS_NOT_CHANGED:
|
||||
conditionMatch = screenshotData->image ==
|
||||
matchImage;
|
||||
break;
|
||||
case videoSwitchType::HAS_CHANGED:
|
||||
conditionMatch = screenshotData->image !=
|
||||
matchImage;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (conditionMatch) {
|
||||
currentMatchDuration +=
|
||||
std::chrono::duration_cast<
|
||||
std::chrono::milliseconds>(
|
||||
screenshotData->time -
|
||||
previousTime);
|
||||
} else {
|
||||
currentMatchDuration = {};
|
||||
}
|
||||
|
||||
bool durationMatch = currentMatchDuration.count() >=
|
||||
duration * 1000;
|
||||
|
||||
if (conditionMatch && durationMatch) {
|
||||
match = true;
|
||||
}
|
||||
|
||||
if (!requiresFileInput(condition)) {
|
||||
matchImage = std::move(screenshotData->image);
|
||||
}
|
||||
previousTime = std::move(screenshotData->time);
|
||||
|
||||
screenshotData.reset(nullptr);
|
||||
}
|
||||
if (!screenshotData) {
|
||||
getScreenshot();
|
||||
return match;
|
||||
}
|
||||
if (!screenshotData->IsDone()) {
|
||||
getScreenshot();
|
||||
return match;
|
||||
}
|
||||
|
||||
bool conditionMatch = false;
|
||||
|
||||
switch (condition) {
|
||||
case videoSwitchType::MATCH:
|
||||
conditionMatch = screenshotData->GetImage() == matchImage;
|
||||
break;
|
||||
case videoSwitchType::DIFFER:
|
||||
conditionMatch = screenshotData->GetImage() != matchImage;
|
||||
break;
|
||||
case videoSwitchType::HAS_NOT_CHANGED:
|
||||
conditionMatch = screenshotData->GetImage() == matchImage;
|
||||
break;
|
||||
case videoSwitchType::HAS_CHANGED:
|
||||
conditionMatch = screenshotData->GetImage() != matchImage;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (conditionMatch) {
|
||||
currentMatchDuration +=
|
||||
std::chrono::duration_cast<std::chrono::milliseconds>(
|
||||
screenshotData->GetScreenshotTime() -
|
||||
previousTime);
|
||||
} else {
|
||||
currentMatchDuration = {};
|
||||
}
|
||||
|
||||
bool durationMatch = currentMatchDuration.count() >= duration * 1000;
|
||||
|
||||
if (conditionMatch && durationMatch) {
|
||||
match = true;
|
||||
}
|
||||
|
||||
if (!requiresFileInput(condition)) {
|
||||
matchImage = screenshotData->GetImage();
|
||||
}
|
||||
previousTime = screenshotData->GetScreenshotTime();
|
||||
|
||||
screenshotData.reset(nullptr);
|
||||
|
||||
getScreenshot();
|
||||
return match;
|
||||
|
|
|
|||
|
|
@ -32,7 +32,7 @@ struct VideoSwitch : virtual SceneSwitcherEntry {
|
|||
double duration = 0;
|
||||
bool ignoreInactiveSource = false;
|
||||
|
||||
std::unique_ptr<ScreenshotHelper> screenshotData = nullptr;
|
||||
std::unique_ptr<Screenshot> screenshotData = nullptr;
|
||||
std::chrono::high_resolution_clock::time_point previousTime{};
|
||||
QImage matchImage;
|
||||
|
||||
|
|
|
|||
|
|
@ -5,12 +5,10 @@
|
|||
|
||||
namespace advss {
|
||||
|
||||
static void ScreenshotTick(void *param, float);
|
||||
|
||||
ScreenshotHelper::ScreenshotHelper(obs_source_t *source, const QRect &subarea,
|
||||
bool blocking, int timeout, bool saveToFile,
|
||||
std::string path)
|
||||
: weakSource(OBSGetWeakRef(source)),
|
||||
Screenshot::Screenshot(obs_source_t *source, const QRect &subarea,
|
||||
bool blocking, int timeout, bool saveToFile,
|
||||
std::string path)
|
||||
: _weakSource(OBSGetWeakRef(source)),
|
||||
_subarea(subarea),
|
||||
_blocking(blocking),
|
||||
_saveToFile(saveToFile),
|
||||
|
|
@ -35,12 +33,12 @@ ScreenshotHelper::ScreenshotHelper(obs_source_t *source, const QRect &subarea,
|
|||
}
|
||||
}
|
||||
|
||||
ScreenshotHelper::~ScreenshotHelper()
|
||||
Screenshot::~Screenshot()
|
||||
{
|
||||
if (_initDone) {
|
||||
obs_enter_graphics();
|
||||
gs_stagesurface_destroy(stagesurf);
|
||||
gs_texrender_destroy(texrender);
|
||||
gs_stagesurface_destroy(_stagesurf);
|
||||
gs_texrender_destroy(_texrender);
|
||||
obs_leave_graphics();
|
||||
}
|
||||
obs_remove_tick_callback(ScreenshotTick, this);
|
||||
|
|
@ -49,21 +47,21 @@ ScreenshotHelper::~ScreenshotHelper()
|
|||
}
|
||||
}
|
||||
|
||||
void ScreenshotHelper::Screenshot()
|
||||
void Screenshot::CreateScreenshot()
|
||||
{
|
||||
OBSSource source = OBSGetStrongRef(weakSource);
|
||||
OBSSource source = OBSGetStrongRef(_weakSource);
|
||||
|
||||
if (source) {
|
||||
cx = obs_source_get_base_width(source);
|
||||
cy = obs_source_get_base_height(source);
|
||||
_cx = obs_source_get_base_width(source);
|
||||
_cy = obs_source_get_base_height(source);
|
||||
} else {
|
||||
obs_video_info ovi;
|
||||
obs_get_video_info(&ovi);
|
||||
cx = ovi.base_width;
|
||||
cy = ovi.base_height;
|
||||
_cx = ovi.base_width;
|
||||
_cy = ovi.base_height;
|
||||
}
|
||||
|
||||
QRect renderArea(0, 0, cx, cy);
|
||||
QRect renderArea(0, 0, _cx, _cy);
|
||||
if (!_subarea.isEmpty()) {
|
||||
renderArea &= _subarea;
|
||||
}
|
||||
|
|
@ -73,19 +71,19 @@ void ScreenshotHelper::Screenshot()
|
|||
"Cannot screenshot \"%s\", invalid target size",
|
||||
obs_source_get_name(source));
|
||||
obs_remove_tick_callback(ScreenshotTick, this);
|
||||
done = true;
|
||||
_done = true;
|
||||
return;
|
||||
}
|
||||
|
||||
cx = renderArea.width();
|
||||
cy = renderArea.height();
|
||||
_cx = renderArea.width();
|
||||
_cy = renderArea.height();
|
||||
|
||||
texrender = gs_texrender_create(GS_RGBA, GS_ZS_NONE);
|
||||
stagesurf = gs_stagesurface_create(renderArea.width(),
|
||||
renderArea.height(), GS_RGBA);
|
||||
_texrender = gs_texrender_create(GS_RGBA, GS_ZS_NONE);
|
||||
_stagesurf = gs_stagesurface_create(renderArea.width(),
|
||||
renderArea.height(), GS_RGBA);
|
||||
|
||||
gs_texrender_reset(texrender);
|
||||
if (gs_texrender_begin(texrender, renderArea.width(),
|
||||
gs_texrender_reset(_texrender);
|
||||
if (gs_texrender_begin(_texrender, renderArea.width(),
|
||||
renderArea.height())) {
|
||||
vec4 zero;
|
||||
vec4_zero(&zero);
|
||||
|
|
@ -108,48 +106,48 @@ void ScreenshotHelper::Screenshot()
|
|||
}
|
||||
|
||||
gs_blend_state_pop();
|
||||
gs_texrender_end(texrender);
|
||||
gs_texrender_end(_texrender);
|
||||
}
|
||||
}
|
||||
|
||||
void ScreenshotHelper::Download()
|
||||
void Screenshot::Download()
|
||||
{
|
||||
gs_stage_texture(stagesurf, gs_texrender_get_texture(texrender));
|
||||
gs_stage_texture(_stagesurf, gs_texrender_get_texture(_texrender));
|
||||
}
|
||||
|
||||
void ScreenshotHelper::Copy()
|
||||
void Screenshot::Copy()
|
||||
{
|
||||
uint8_t *videoData = nullptr;
|
||||
uint32_t videoLinesize = 0;
|
||||
|
||||
image = QImage(cx, cy, QImage::Format::Format_RGBA8888);
|
||||
_image = QImage(_cx, _cy, QImage::Format::Format_RGBA8888);
|
||||
|
||||
if (gs_stagesurface_map(stagesurf, &videoData, &videoLinesize)) {
|
||||
int linesize = image.bytesPerLine();
|
||||
for (int y = 0; y < (int)cy; y++)
|
||||
memcpy(image.scanLine(y),
|
||||
if (gs_stagesurface_map(_stagesurf, &videoData, &videoLinesize)) {
|
||||
int linesize = _image.bytesPerLine();
|
||||
for (int y = 0; y < (int)_cy; y++)
|
||||
memcpy(_image.scanLine(y),
|
||||
videoData + (y * videoLinesize), linesize);
|
||||
|
||||
gs_stagesurface_unmap(stagesurf);
|
||||
gs_stagesurface_unmap(_stagesurf);
|
||||
}
|
||||
}
|
||||
|
||||
void ScreenshotHelper::MarkDone()
|
||||
void Screenshot::MarkDone()
|
||||
{
|
||||
time = std::chrono::high_resolution_clock::now();
|
||||
done = true;
|
||||
_time = std::chrono::high_resolution_clock::now();
|
||||
_done = true;
|
||||
std::unique_lock<std::mutex> lock(_mutex);
|
||||
_cv.notify_all();
|
||||
}
|
||||
|
||||
void ScreenshotHelper::WriteToFile()
|
||||
void Screenshot::WriteToFile()
|
||||
{
|
||||
if (!_saveToFile) {
|
||||
return;
|
||||
}
|
||||
|
||||
_saveThread = std::thread([this]() {
|
||||
if (image.save(QString::fromStdString(_path))) {
|
||||
if (_image.save(QString::fromStdString(_path))) {
|
||||
vblog(LOG_INFO, "Wrote screenshot to \"%s\"",
|
||||
_path.c_str());
|
||||
} else {
|
||||
|
|
@ -165,19 +163,19 @@ void ScreenshotHelper::WriteToFile()
|
|||
#define STAGE_COPY_AND_SAVE 2
|
||||
#define STAGE_FINISH 3
|
||||
|
||||
static void ScreenshotTick(void *param, float)
|
||||
void Screenshot::ScreenshotTick(void *param, float)
|
||||
{
|
||||
ScreenshotHelper *data = reinterpret_cast<ScreenshotHelper *>(param);
|
||||
Screenshot *data = reinterpret_cast<Screenshot *>(param);
|
||||
|
||||
if (data->stage == STAGE_FINISH) {
|
||||
if (data->_stage == STAGE_FINISH) {
|
||||
return;
|
||||
}
|
||||
|
||||
obs_enter_graphics();
|
||||
|
||||
switch (data->stage) {
|
||||
switch (data->_stage) {
|
||||
case STAGE_SCREENSHOT:
|
||||
data->Screenshot();
|
||||
data->CreateScreenshot();
|
||||
break;
|
||||
case STAGE_DOWNLOAD:
|
||||
data->Download();
|
||||
|
|
@ -193,7 +191,7 @@ static void ScreenshotTick(void *param, float)
|
|||
|
||||
obs_leave_graphics();
|
||||
|
||||
data->stage++;
|
||||
data->_stage++;
|
||||
}
|
||||
|
||||
} // namespace advss
|
||||
|
|
|
|||
|
|
@ -9,36 +9,42 @@
|
|||
|
||||
namespace advss {
|
||||
|
||||
class ScreenshotHelper {
|
||||
public:
|
||||
EXPORT ScreenshotHelper() = default;
|
||||
EXPORT ScreenshotHelper(obs_source_t *source,
|
||||
const QRect &subarea = QRect(),
|
||||
bool blocking = false, int timeout = 1000,
|
||||
bool saveToFile = false, std::string path = "");
|
||||
EXPORT ScreenshotHelper &operator=(const ScreenshotHelper &) = delete;
|
||||
EXPORT ScreenshotHelper(const ScreenshotHelper &) = delete;
|
||||
EXPORT ~ScreenshotHelper();
|
||||
class Screenshot {
|
||||
using TimePoint = std::chrono::high_resolution_clock::time_point;
|
||||
|
||||
void Screenshot();
|
||||
public:
|
||||
EXPORT Screenshot() = default;
|
||||
EXPORT Screenshot(obs_source_t *source, const QRect &subarea = QRect(),
|
||||
bool blocking = false, int timeout = 1000,
|
||||
bool saveToFile = false, std::string path = "");
|
||||
EXPORT Screenshot &operator=(const Screenshot &) = delete;
|
||||
EXPORT Screenshot(const Screenshot &) = delete;
|
||||
EXPORT ~Screenshot();
|
||||
|
||||
EXPORT bool IsDone() const { return _done; }
|
||||
EXPORT QImage &GetImage() { return _image; }
|
||||
EXPORT TimePoint GetScreenshotTime() const { return _time; }
|
||||
|
||||
private:
|
||||
static void ScreenshotTick(void *param, float);
|
||||
void CreateScreenshot();
|
||||
void Download();
|
||||
void Copy();
|
||||
void MarkDone();
|
||||
void WriteToFile();
|
||||
|
||||
gs_texrender_t *texrender = nullptr;
|
||||
gs_stagesurf_t *stagesurf = nullptr;
|
||||
OBSWeakSource weakSource;
|
||||
QImage image;
|
||||
uint32_t cx = 0;
|
||||
uint32_t cy = 0;
|
||||
gs_texrender_t *_texrender = nullptr;
|
||||
gs_stagesurf_t *_stagesurf = nullptr;
|
||||
OBSWeakSource _weakSource;
|
||||
QImage _image;
|
||||
uint32_t _cx = 0;
|
||||
uint32_t _cy = 0;
|
||||
|
||||
int stage = 0;
|
||||
int _stage = 0;
|
||||
|
||||
bool done = false;
|
||||
std::chrono::high_resolution_clock::time_point time;
|
||||
bool _done = false;
|
||||
TimePoint _time;
|
||||
|
||||
private:
|
||||
std::atomic_bool _initDone = false;
|
||||
QRect _subarea = QRect();
|
||||
bool _blocking = false;
|
||||
|
|
|
|||
|
|
@ -32,8 +32,8 @@ void MacroActionScreenshot::CustomScreenshot(OBSWeakSource &source)
|
|||
return;
|
||||
}
|
||||
auto s = obs_weak_source_get_source(source);
|
||||
_screenshot.~ScreenshotHelper();
|
||||
new (&_screenshot) ScreenshotHelper(s, QRect(), false, 0, true, _path);
|
||||
_screenshot.~Screenshot();
|
||||
new (&_screenshot) Screenshot(s, QRect(), false, 0, true, _path);
|
||||
obs_source_release(s);
|
||||
}
|
||||
|
||||
|
|
@ -230,11 +230,7 @@ void MacroActionScreenshotEdit::UpdateEntryData()
|
|||
|
||||
void MacroActionScreenshotEdit::SceneChanged(const SceneSelection &s)
|
||||
{
|
||||
if (_loading || !_entryData) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto lock = LockContext();
|
||||
GUARD_LOADING_AND_LOCK();
|
||||
_entryData->_scene = s;
|
||||
emit HeaderInfoChanged(
|
||||
QString::fromStdString(_entryData->GetShortDesc()));
|
||||
|
|
|
|||
|
|
@ -42,7 +42,7 @@ private:
|
|||
void FrontendScreenshot(OBSWeakSource &);
|
||||
void CustomScreenshot(OBSWeakSource &);
|
||||
|
||||
ScreenshotHelper _screenshot;
|
||||
Screenshot _screenshot;
|
||||
|
||||
static bool _registered;
|
||||
static const std::string id;
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
#include "macro-condition-video.hpp"
|
||||
#include "screenshot-dialog.hpp"
|
||||
|
||||
#include <layout-helpers.hpp>
|
||||
#include <macro-condition-edit.hpp>
|
||||
|
|
@ -147,12 +148,12 @@ bool MacroConditionVideo::CheckCondition()
|
|||
GetScreenshot(true);
|
||||
}
|
||||
|
||||
if (_screenshotData.done) {
|
||||
if (_screenshotData.IsDone()) {
|
||||
match = Compare();
|
||||
_lastMatchResult = match;
|
||||
|
||||
if (!requiresFileInput(_condition)) {
|
||||
_matchImage = std::move(_screenshotData.image);
|
||||
_matchImage = std::move(_screenshotData.GetImage());
|
||||
}
|
||||
_getNextScreenshot = true;
|
||||
} else {
|
||||
|
|
@ -225,7 +226,7 @@ std::string MacroConditionVideo::GetShortDesc() const
|
|||
void MacroConditionVideo::GetScreenshot(bool blocking)
|
||||
{
|
||||
auto source = obs_weak_source_get_source(_video.GetVideo());
|
||||
_screenshotData.~ScreenshotHelper();
|
||||
_screenshotData.~Screenshot();
|
||||
QRect screenshotArea;
|
||||
if (_areaParameters.enable && _condition != VideoCondition::NO_IMAGE) {
|
||||
screenshotArea.setRect(_areaParameters.area.x,
|
||||
|
|
@ -233,8 +234,8 @@ void MacroConditionVideo::GetScreenshot(bool blocking)
|
|||
_areaParameters.area.width,
|
||||
_areaParameters.area.height);
|
||||
}
|
||||
new (&_screenshotData) ScreenshotHelper(source, screenshotArea,
|
||||
blocking, GetIntervalValue());
|
||||
new (&_screenshotData) Screenshot(source, screenshotArea, blocking,
|
||||
GetIntervalValue());
|
||||
obs_source_release(source);
|
||||
_getNextScreenshot = false;
|
||||
}
|
||||
|
|
@ -293,7 +294,7 @@ void MacroConditionVideo::SetCondition(VideoCondition condition)
|
|||
bool MacroConditionVideo::ScreenshotContainsPattern()
|
||||
{
|
||||
cv::Mat result;
|
||||
MatchPattern(_screenshotData.image, _patternImageData,
|
||||
MatchPattern(_screenshotData.GetImage(), _patternImageData,
|
||||
_patternMatchParameters.threshold, result, nullptr,
|
||||
_patternMatchParameters.useAlphaAsMask,
|
||||
_patternMatchParameters.matchMode);
|
||||
|
|
@ -319,12 +320,12 @@ bool MacroConditionVideo::FileInputIsUpToDate() const
|
|||
bool MacroConditionVideo::OutputChanged()
|
||||
{
|
||||
if (!_patternMatchParameters.useForChangedCheck) {
|
||||
return _screenshotData.image != _matchImage;
|
||||
return _screenshotData.GetImage() != _matchImage;
|
||||
}
|
||||
|
||||
cv::Mat result;
|
||||
_patternImageData = CreatePatternData(_matchImage);
|
||||
MatchPattern(_screenshotData.image, _patternImageData,
|
||||
MatchPattern(_screenshotData.GetImage(), _patternImageData,
|
||||
_patternMatchParameters.threshold, result, nullptr,
|
||||
_patternMatchParameters.useAlphaAsMask,
|
||||
_patternMatchParameters.matchMode);
|
||||
|
|
@ -336,7 +337,7 @@ bool MacroConditionVideo::OutputChanged()
|
|||
|
||||
bool MacroConditionVideo::ScreenshotContainsObject()
|
||||
{
|
||||
auto objects = MatchObject(_screenshotData.image,
|
||||
auto objects = MatchObject(_screenshotData.GetImage(),
|
||||
_objMatchParameters.cascade,
|
||||
_objMatchParameters.scaleFactor,
|
||||
_objMatchParameters.minNeighbors,
|
||||
|
|
@ -349,7 +350,8 @@ bool MacroConditionVideo::ScreenshotContainsObject()
|
|||
|
||||
bool MacroConditionVideo::CheckBrightnessThreshold()
|
||||
{
|
||||
_currentBrightness = GetAvgBrightness(_screenshotData.image) / 255.;
|
||||
_currentBrightness =
|
||||
GetAvgBrightness(_screenshotData.GetImage()) / 255.;
|
||||
SetTempVarValue("brightness", std::to_string(_currentBrightness));
|
||||
return _currentBrightness > _brightnessThreshold;
|
||||
}
|
||||
|
|
@ -360,7 +362,7 @@ bool MacroConditionVideo::CheckOCR()
|
|||
return false;
|
||||
}
|
||||
|
||||
auto text = RunOCR(_ocrParameters.GetOCR(), _screenshotData.image,
|
||||
auto text = RunOCR(_ocrParameters.GetOCR(), _screenshotData.GetImage(),
|
||||
_ocrParameters.color, _ocrParameters.colorThreshold);
|
||||
SetVariableValue(text);
|
||||
SetTempVarValue("text", text);
|
||||
|
|
@ -373,14 +375,14 @@ bool MacroConditionVideo::CheckOCR()
|
|||
bool MacroConditionVideo::CheckColor()
|
||||
{
|
||||
const bool ret = ContainsPixelsInColorRange(
|
||||
_screenshotData.image, _colorParameters.color,
|
||||
_screenshotData.GetImage(), _colorParameters.color,
|
||||
_colorParameters.colorThreshold,
|
||||
_colorParameters.matchThreshold);
|
||||
// Way too slow for now
|
||||
//SetTempVarValue("dominantColor", GetDominantColor(_screenshotData.image, 3)
|
||||
// .name(QColor::HexArgb)
|
||||
// .toStdString());
|
||||
SetTempVarValue("color", GetAverageColor(_screenshotData.image)
|
||||
SetTempVarValue("color", GetAverageColor(_screenshotData.GetImage())
|
||||
.name(QColor::HexArgb)
|
||||
.toStdString());
|
||||
return ret;
|
||||
|
|
@ -394,15 +396,15 @@ bool MacroConditionVideo::Compare()
|
|||
|
||||
switch (_condition) {
|
||||
case VideoCondition::MATCH:
|
||||
return _screenshotData.image == _matchImage;
|
||||
return _screenshotData.GetImage() == _matchImage;
|
||||
case VideoCondition::DIFFER:
|
||||
return _screenshotData.image != _matchImage;
|
||||
return _screenshotData.GetImage() != _matchImage;
|
||||
case VideoCondition::HAS_CHANGED:
|
||||
return OutputChanged();
|
||||
case VideoCondition::HAS_NOT_CHANGED:
|
||||
return !OutputChanged();
|
||||
case VideoCondition::NO_IMAGE:
|
||||
return _screenshotData.image.isNull();
|
||||
return _screenshotData.GetImage().isNull();
|
||||
case VideoCondition::PATTERN:
|
||||
return ScreenshotContainsPattern();
|
||||
case VideoCondition::OBJECT:
|
||||
|
|
@ -1418,11 +1420,6 @@ void MacroConditionVideoEdit::ImageBrowseButtonClicked()
|
|||
}
|
||||
|
||||
} else {
|
||||
auto source = obs_weak_source_get_source(
|
||||
_entryData->_video.GetVideo());
|
||||
ScreenshotHelper screenshot(source);
|
||||
obs_source_release(source);
|
||||
|
||||
path = QFileDialog::getSaveFileName(
|
||||
this, "",
|
||||
FileSelection::ValidPathOrDesktop(
|
||||
|
|
@ -1435,22 +1432,13 @@ void MacroConditionVideoEdit::ImageBrowseButtonClicked()
|
|||
if (!file.open(QIODevice::WriteOnly | QIODevice::Text)) {
|
||||
return;
|
||||
}
|
||||
if (!screenshot.done) { // Screenshot usually completed by now
|
||||
std::this_thread::sleep_for(std::chrono::seconds(1));
|
||||
}
|
||||
if (!screenshot.done) {
|
||||
DisplayMessage(obs_module_text(
|
||||
"AdvSceneSwitcher.condition.video.screenshotFail"));
|
||||
|
||||
auto source = OBSGetStrongRef(_entryData->_video.GetVideo());
|
||||
auto screenshot = ScreenshotDialog::AskForScreenshot(source);
|
||||
if (!screenshot) {
|
||||
return;
|
||||
}
|
||||
if (_entryData->_areaParameters.enable) {
|
||||
screenshot.image = screenshot.image.copy(
|
||||
_entryData->_areaParameters.area.x,
|
||||
_entryData->_areaParameters.area.y,
|
||||
_entryData->_areaParameters.area.width,
|
||||
_entryData->_areaParameters.area.height);
|
||||
}
|
||||
screenshot.image.save(path);
|
||||
screenshot->save(path);
|
||||
}
|
||||
_imagePath->SetPath(path);
|
||||
ImagePathChanged(path);
|
||||
|
|
@ -1458,11 +1446,7 @@ void MacroConditionVideoEdit::ImageBrowseButtonClicked()
|
|||
|
||||
void MacroConditionVideoEdit::UsePatternForChangedCheckChanged(int value)
|
||||
{
|
||||
if (_loading || !_entryData) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto lock = LockContext();
|
||||
GUARD_LOADING_AND_LOCK();
|
||||
_entryData->_patternMatchParameters.useForChangedCheck = value;
|
||||
SetWidgetVisibility();
|
||||
}
|
||||
|
|
@ -1470,11 +1454,7 @@ void MacroConditionVideoEdit::UsePatternForChangedCheckChanged(int value)
|
|||
void MacroConditionVideoEdit::PatternThresholdChanged(
|
||||
const DoubleVariable &value)
|
||||
{
|
||||
if (_loading || !_entryData) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto lock = LockContext();
|
||||
GUARD_LOADING_AND_LOCK();
|
||||
_entryData->_patternMatchParameters.threshold = value;
|
||||
_previewDialog.PatternMatchParametersChanged(
|
||||
_entryData->_patternMatchParameters);
|
||||
|
|
@ -1482,21 +1462,13 @@ void MacroConditionVideoEdit::PatternThresholdChanged(
|
|||
|
||||
void MacroConditionVideoEdit::ReduceLatencyChanged(int value)
|
||||
{
|
||||
if (_loading || !_entryData) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto lock = LockContext();
|
||||
GUARD_LOADING_AND_LOCK();
|
||||
_entryData->_blockUntilScreenshotDone = value;
|
||||
}
|
||||
|
||||
void MacroConditionVideoEdit::UseAlphaAsMaskChanged(int value)
|
||||
{
|
||||
if (_loading || !_entryData) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto lock = LockContext();
|
||||
GUARD_LOADING_AND_LOCK();
|
||||
_entryData->_patternMatchParameters.useAlphaAsMask = value;
|
||||
_entryData->LoadImageFromFile();
|
||||
_previewDialog.PatternMatchParametersChanged(
|
||||
|
|
@ -1505,11 +1477,7 @@ void MacroConditionVideoEdit::UseAlphaAsMaskChanged(int value)
|
|||
|
||||
void MacroConditionVideoEdit::PatternMatchModeChanged(int idx)
|
||||
{
|
||||
if (_loading || !_entryData) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto lock = LockContext();
|
||||
GUARD_LOADING_AND_LOCK();
|
||||
_entryData->_patternMatchParameters.matchMode =
|
||||
static_cast<cv::TemplateMatchModes>(
|
||||
_patternMatchMode->itemData(idx).toInt());
|
||||
|
|
@ -1519,22 +1487,14 @@ void MacroConditionVideoEdit::PatternMatchModeChanged(int idx)
|
|||
|
||||
void MacroConditionVideoEdit::ThrottleEnableChanged(int value)
|
||||
{
|
||||
if (_loading || !_entryData) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto lock = LockContext();
|
||||
GUARD_LOADING_AND_LOCK();
|
||||
_entryData->_throttleEnabled = value;
|
||||
_throttleCount->setEnabled(value);
|
||||
}
|
||||
|
||||
void MacroConditionVideoEdit::ThrottleCountChanged(int value)
|
||||
{
|
||||
if (_loading || !_entryData) {
|
||||
return;
|
||||
}
|
||||
|
||||
auto lock = LockContext();
|
||||
GUARD_LOADING_AND_LOCK();
|
||||
_entryData->_throttleCount = value / GetIntervalValue();
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -90,7 +90,7 @@ private:
|
|||
VideoCondition _condition = VideoCondition::MATCH;
|
||||
|
||||
bool _getNextScreenshot = true;
|
||||
ScreenshotHelper _screenshotData;
|
||||
Screenshot _screenshotData;
|
||||
QImage _matchImage;
|
||||
PatternImageData _patternImageData;
|
||||
|
||||
|
|
|
|||
|
|
@ -277,17 +277,18 @@ void PreviewImage::CreateImage(const VideoInput &video, PreviewType type,
|
|||
areaParams.area.width,
|
||||
areaParams.area.height);
|
||||
}
|
||||
ScreenshotHelper screenshot(source, screenshotArea, true);
|
||||
Screenshot screenshot(source, screenshotArea, true);
|
||||
obs_source_release(source);
|
||||
|
||||
if (!video.ValidSelection() || !screenshot.done) {
|
||||
if (!video.ValidSelection() || !screenshot.IsDone()) {
|
||||
emit StatusUpdate(obs_module_text(
|
||||
"AdvSceneSwitcher.condition.video.screenshotFail"));
|
||||
emit ImageReady(QPixmap());
|
||||
return;
|
||||
}
|
||||
|
||||
if (screenshot.image.width() == 0 || screenshot.image.height() == 0) {
|
||||
if (screenshot.GetImage().width() == 0 ||
|
||||
screenshot.GetImage().height() == 0) {
|
||||
emit StatusUpdate(obs_module_text(
|
||||
"AdvSceneSwitcher.condition.video.screenshotEmpty"));
|
||||
emit ImageReady(QPixmap());
|
||||
|
|
@ -297,14 +298,14 @@ void PreviewImage::CreateImage(const VideoInput &video, PreviewType type,
|
|||
if (type == PreviewType::SHOW_MATCH) {
|
||||
std::unique_lock<std::mutex> lock(_mtx);
|
||||
// Will emit status label update
|
||||
MarkMatch(screenshot.image, patternMatchParams,
|
||||
MarkMatch(screenshot.GetImage(), patternMatchParams,
|
||||
patternImageData, objDetectParams, ocrParams,
|
||||
condition);
|
||||
} else {
|
||||
emit StatusUpdate(obs_module_text(
|
||||
"AdvSceneSwitcher.condition.video.selectArea.status"));
|
||||
}
|
||||
emit ImageReady(QPixmap::fromImage(screenshot.image));
|
||||
emit ImageReady(QPixmap::fromImage(screenshot.GetImage()));
|
||||
}
|
||||
|
||||
void PreviewImage::MarkMatch(QImage &screenshot,
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user