Add content / modification date changed as separate options

Previously this would require knowledge of regular expressions to match
any content.
This commit is contained in:
WarmUpTill 2022-09-11 01:44:14 +02:00 committed by WarmUpTill
parent 99ceb6a42a
commit 6d755ad570
6 changed files with 156 additions and 28 deletions

View File

@ -128,7 +128,10 @@ AdvSceneSwitcher.condition.window="Window"
AdvSceneSwitcher.condition.window.entry.line1="{{windows}} exist and ..."
AdvSceneSwitcher.condition.window.entry.line2="... is {{fullscreen}} fullscreen {{maximized}} maximized {{focused}} focused {{windowFocusChanged}} foreground window changed"
AdvSceneSwitcher.condition.file="File"
AdvSceneSwitcher.condition.file.entry.line1="Content of {{fileType}} {{filePath}} matches:"
AdvSceneSwitcher.condition.file.type.match="matches"
AdvSceneSwitcher.condition.file.type.contentChange="content changed"
AdvSceneSwitcher.condition.file.type.dateChange="modification date changed"
AdvSceneSwitcher.condition.file.entry.line1="Content of{{fileType}}{{filePath}}{{conditions}}"
AdvSceneSwitcher.condition.file.entry.line2="{{matchText}}"
AdvSceneSwitcher.condition.file.entry.line3="{{useRegex}} {{checkModificationDate}} {{checkFileContent}}"
AdvSceneSwitcher.condition.media="Media"

View File

@ -123,7 +123,7 @@ AdvSceneSwitcher.condition.window="Ventana"
AdvSceneSwitcher.condition.window.entry.line1="{{windows}} existen y ..."
AdvSceneSwitcher.condition.window.entry.line2="... es {{fullscreen}} pantalla completa {{maximized}} maximizada {{focused}} enfocada {{windowFocusChanged}} ventana de primer plano cambiada"
AdvSceneSwitcher.condition.file="Archivo"
AdvSceneSwitcher.condition.file.entry.line1="Contenido de {{fileType}} {{filePath}} coincidencias:"
AdvSceneSwitcher.condition.file.entry.line1="Contenido de{{fileType}}{{filePath}}{{conditions}}"
AdvSceneSwitcher.condition.file.entry.line2="{{matchText}}"
AdvSceneSwitcher.condition.file.entry.line3="{{useRegex}} {{checkModificationDate}} {{checkFileContent}}"
AdvSceneSwitcher.condition.media="Medios"

View File

@ -111,7 +111,7 @@ AdvSceneSwitcher.condition.window="Pencere"
AdvSceneSwitcher.condition.window.entry.line1="{{windows}} Varolan ve ..."
AdvSceneSwitcher.condition.window.entry.line2="... {{fullscreen}} Tam ekran {{maximized}} büyütüldü {{focused}} odaklanıldı {{windowFocusChanged}} ön plan penceresi değişikliği"
AdvSceneSwitcher.condition.file="Dosya"
AdvSceneSwitcher.condition.file.entry.line1="İçerik {{fileType}} {{filePath}} eşleştirmeler:"
AdvSceneSwitcher.condition.file.entry.line1="İçerik{{fileType}}{{filePath}}{{conditions}}"
AdvSceneSwitcher.condition.file.entry.line2="{{matchText}}"
AdvSceneSwitcher.condition.file.entry.line3="{{useRegex}} {{checkModificationDate}} {{checkFileContent}}"
AdvSceneSwitcher.condition.media="Medya"

View File

@ -116,7 +116,6 @@ AdvSceneSwitcher.condition.window="窗口"
AdvSceneSwitcher.condition.window.entry.line1="{{windows}} 存在..."
AdvSceneSwitcher.condition.window.entry.line2="... 并且是 {{fullscreen}} 全屏 {{maximized}} 最大化 {{focused}} 获得焦点 {{windowFocusChanged}} 焦点窗口已更改"
AdvSceneSwitcher.condition.file="文件"
AdvSceneSwitcher.condition.file.entry.line1="内容 {{fileType}} {{filePath}} (本地是文本,网络是获取的网页)完全匹配:"
AdvSceneSwitcher.condition.file.entry.line2="{{matchText}}"
AdvSceneSwitcher.condition.file.entry.line3="{{useRegex}} {{checkModificationDate}} {{checkFileContent}}"
AdvSceneSwitcher.condition.media="媒体"

View File

@ -72,7 +72,6 @@ bool MacroConditionFile::CheckRemoteFileContent()
bool MacroConditionFile::CheckLocalFileContent()
{
QString t = QString::fromStdString(_text);
QFile file(QString::fromStdString(_file));
if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
return false;
@ -93,13 +92,62 @@ bool MacroConditionFile::CheckLocalFileContent()
return match;
}
bool MacroConditionFile::CheckCondition()
bool MacroConditionFile::CheckChangeContent()
{
QString filedata;
switch (_fileType) {
case FileType::LOCAL: {
QFile file(QString::fromStdString(_file));
if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
return false;
}
filedata = QTextStream(&file).readAll();
file.close();
} break;
case FileType::REMOTE: {
std::string data = getRemoteData(_file);
QString filedata = QString::fromStdString(data);
} break;
default:
break;
}
size_t newHash = strHash(filedata.toUtf8().constData());
const bool contentChanged = newHash != _lastHash;
_lastHash = newHash;
return contentChanged;
}
bool MacroConditionFile::CheckChangeDate()
{
if (_fileType == FileType::REMOTE) {
return CheckRemoteFileContent();
} else {
return CheckLocalFileContent();
return false;
}
QFile file(QString::fromStdString(_file));
QDateTime newLastMod = QFileInfo(file).lastModified();
const bool dateChanged = _lastMod != newLastMod;
_lastMod = newLastMod;
return dateChanged;
}
bool MacroConditionFile::CheckCondition()
{
switch (_condition) {
case MacroConditionFile::ConditionType::MATCH:
if (_fileType == FileType::REMOTE) {
return CheckRemoteFileContent();
}
return CheckLocalFileContent();
case MacroConditionFile::ConditionType::CONTENT_CHANGE:
return CheckChangeContent();
case MacroConditionFile::ConditionType::DATE_CHANGE:
return CheckChangeDate();
default:
break;
}
return false;
}
bool MacroConditionFile::Save(obs_data_t *obj)
@ -109,6 +157,7 @@ bool MacroConditionFile::Save(obs_data_t *obj)
obs_data_set_string(obj, "file", _file.c_str());
obs_data_set_string(obj, "text", _text.c_str());
obs_data_set_int(obj, "fileType", static_cast<int>(_fileType));
obs_data_set_int(obj, "condition", static_cast<int>(_condition));
obs_data_set_bool(obj, "useTime", _useTime);
obs_data_set_bool(obj, "onlyMatchIfChanged", _onlyMatchIfChanged);
return true;
@ -126,6 +175,8 @@ bool MacroConditionFile::Load(obs_data_t *obj)
_file = obs_data_get_string(obj, "file");
_text = obs_data_get_string(obj, "text");
_fileType = static_cast<FileType>(obs_data_get_int(obj, "fileType"));
_condition =
static_cast<ConditionType>(obs_data_get_int(obj, "condition"));
_useTime = obs_data_get_bool(obj, "useTime");
_onlyMatchIfChanged = obs_data_get_bool(obj, "onlyMatchIfChanged");
return true;
@ -136,21 +187,42 @@ std::string MacroConditionFile::GetShortDesc()
return _file;
}
static void populateFileTypes(QComboBox *list)
{
list->addItem(obs_module_text("AdvSceneSwitcher.fileTab.local"));
list->addItem(obs_module_text("AdvSceneSwitcher.fileTab.remote"));
}
static void populateConditions(QComboBox *list)
{
list->addItem(
obs_module_text("AdvSceneSwitcher.condition.file.type.match"));
list->addItem(obs_module_text(
"AdvSceneSwitcher.condition.file.type.contentChange"));
list->addItem(obs_module_text(
"AdvSceneSwitcher.condition.file.type.dateChange"));
}
MacroConditionFileEdit::MacroConditionFileEdit(
QWidget *parent, std::shared_ptr<MacroConditionFile> entryData)
: QWidget(parent)
: QWidget(parent),
_fileTypes(new QComboBox()),
_conditions(new QComboBox()),
_filePath(new FileSelection()),
_matchText(new ResizingPlainTextEdit(this)),
_regex(new RegexConfigWidget(parent)),
_checkModificationDate(new QCheckBox(obs_module_text(
"AdvSceneSwitcher.fileTab.checkfileContentTime"))),
_checkFileContent(new QCheckBox(
obs_module_text("AdvSceneSwitcher.fileTab.checkfileContent")))
{
_fileType = new QComboBox();
_filePath = new FileSelection();
_matchText = new ResizingPlainTextEdit(this);
_regex = new RegexConfigWidget(parent);
_checkModificationDate = new QCheckBox(obs_module_text(
"AdvSceneSwitcher.fileTab.checkfileContentTime"));
_checkFileContent = new QCheckBox(
obs_module_text("AdvSceneSwitcher.fileTab.checkfileContent"));
populateFileTypes(_fileTypes);
populateConditions(_conditions);
QWidget::connect(_fileType, SIGNAL(currentIndexChanged(int)), this,
QWidget::connect(_fileTypes, SIGNAL(currentIndexChanged(int)), this,
SLOT(FileTypeChanged(int)));
QWidget::connect(_conditions, SIGNAL(currentIndexChanged(int)), this,
SLOT(ConditionChanged(int)));
QWidget::connect(_filePath, SIGNAL(PathChanged(const QString &)), this,
SLOT(PathChanged(const QString &)));
QWidget::connect(_matchText, SIGNAL(textChanged()), this,
@ -162,11 +234,9 @@ MacroConditionFileEdit::MacroConditionFileEdit(
QWidget::connect(_checkFileContent, SIGNAL(stateChanged(int)), this,
SLOT(OnlyMatchIfChangedChanged(int)));
_fileType->addItem(obs_module_text("AdvSceneSwitcher.fileTab.local"));
_fileType->addItem(obs_module_text("AdvSceneSwitcher.fileTab.remote"));
std::unordered_map<std::string, QWidget *> widgetPlaceholders = {
{"{{fileType}}", _fileType},
{"{{fileType}}", _fileTypes},
{"{{conditions}}", _conditions},
{"{{filePath}}", _filePath},
{"{{matchText}}", _matchText},
{"{{useRegex}}", _regex},
@ -204,16 +274,23 @@ void MacroConditionFileEdit::UpdateEntryData()
return;
}
_fileType->setCurrentIndex(static_cast<int>(_entryData->_fileType));
_fileTypes->setCurrentIndex(static_cast<int>(_entryData->_fileType));
_conditions->setCurrentIndex(static_cast<int>(_entryData->_condition));
_filePath->SetPath(QString::fromStdString(_entryData->_file));
_matchText->setPlainText(QString::fromStdString(_entryData->_text));
_regex->SetRegexConfig(_entryData->_regex);
_checkModificationDate->setChecked(_entryData->_useTime);
_checkFileContent->setChecked(_entryData->_onlyMatchIfChanged);
adjustSize();
updateGeometry();
// TODO: Remove in future version
if (!_entryData->_useTime) {
_checkModificationDate->hide();
}
if (!_entryData->_onlyMatchIfChanged) {
_checkFileContent->hide();
}
SetWidgetVisibility();
}
void MacroConditionFileEdit::FileTypeChanged(int index)
@ -237,6 +314,18 @@ void MacroConditionFileEdit::FileTypeChanged(int index)
_entryData->_fileType = type;
}
void MacroConditionFileEdit::ConditionChanged(int index)
{
if (_loading || !_entryData) {
return;
}
std::lock_guard<std::mutex> lock(switcher->m);
_entryData->_condition =
static_cast<MacroConditionFile::ConditionType>(index);
SetWidgetVisibility();
}
void MacroConditionFileEdit::PathChanged(const QString &text)
{
if (_loading || !_entryData) {
@ -293,3 +382,25 @@ void MacroConditionFileEdit::OnlyMatchIfChangedChanged(int state)
std::lock_guard<std::mutex> lock(switcher->m);
_entryData->_onlyMatchIfChanged = state;
}
void MacroConditionFileEdit::SetWidgetVisibility()
{
if (!_entryData) {
return;
}
_matchText->setVisible(_entryData->_condition ==
MacroConditionFile::ConditionType::MATCH);
_regex->setVisible(_entryData->_condition ==
MacroConditionFile::ConditionType::MATCH);
_checkModificationDate->setVisible(
_entryData->_useTime &&
_entryData->_condition ==
MacroConditionFile::ConditionType::MATCH);
_checkFileContent->setVisible(
_entryData->_onlyMatchIfChanged &&
_entryData->_condition ==
MacroConditionFile::ConditionType::MATCH);
adjustSize();
updateGeometry();
}

View File

@ -29,10 +29,19 @@ public:
REMOTE,
};
enum class ConditionType {
MATCH,
CONTENT_CHANGE,
DATE_CHANGE,
};
std::string _file = obs_module_text("AdvSceneSwitcher.enterPath");
std::string _text = obs_module_text("AdvSceneSwitcher.enterText");
FileType _fileType = FileType::LOCAL;
ConditionType _condition = ConditionType::MATCH;
RegexConfig _regex;
// TODO: Remove in future version
bool _useTime = false;
bool _onlyMatchIfChanged = false;
@ -40,6 +49,8 @@ private:
bool MatchFileContent(QString &filedata);
bool CheckRemoteFileContent();
bool CheckLocalFileContent();
bool CheckChangeContent();
bool CheckChangeDate();
QDateTime _lastMod;
size_t _lastHash = 0;
@ -65,6 +76,7 @@ public:
private slots:
void FileTypeChanged(int index);
void ConditionChanged(int index);
void PathChanged(const QString &text);
void MatchTextChanged();
void RegexChanged(RegexConfig);
@ -74,7 +86,8 @@ signals:
void HeaderInfoChanged(const QString &);
protected:
QComboBox *_fileType;
QComboBox *_fileTypes;
QComboBox *_conditions;
FileSelection *_filePath;
ResizingPlainTextEdit *_matchText;
RegexConfigWidget *_regex;
@ -83,5 +96,7 @@ protected:
std::shared_ptr<MacroConditionFile> _entryData;
private:
void SetWidgetVisibility();
bool _loading = true;
};