forked from mia/Aegisub
Clean up SearchReplaceEngine a bit
This commit is contained in:
parent
f8b717e9ac
commit
6be8d32929
1 changed files with 26 additions and 25 deletions
|
@ -41,26 +41,28 @@ struct MatchState {
|
||||||
};
|
};
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
template<typename AssDialogue>
|
auto get_dialogue_field(SearchReplaceSettings::Field field) -> decltype(&AssDialogue::Text) {
|
||||||
auto get_dialogue_field(AssDialogue *cur, SearchReplaceSettings::Field field) -> decltype(&cur->Text) {
|
|
||||||
switch (field) {
|
switch (field) {
|
||||||
case SearchReplaceSettings::Field::TEXT: return &cur->Text;
|
case SearchReplaceSettings::Field::TEXT: return &AssDialogue::Text;
|
||||||
case SearchReplaceSettings::Field::STYLE: return &cur->Style;
|
case SearchReplaceSettings::Field::STYLE: return &AssDialogue::Style;
|
||||||
case SearchReplaceSettings::Field::ACTOR: return &cur->Actor;
|
case SearchReplaceSettings::Field::ACTOR: return &AssDialogue::Actor;
|
||||||
case SearchReplaceSettings::Field::EFFECT: return &cur->Effect;
|
case SearchReplaceSettings::Field::EFFECT: return &AssDialogue::Effect;
|
||||||
}
|
}
|
||||||
throw agi::InternalError("Bad field for search", 0);
|
throw agi::InternalError("Bad field for search", 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
typedef std::function<MatchState (const AssDialogue*, size_t)> matcher;
|
typedef std::function<MatchState (const AssDialogue*, size_t)> matcher;
|
||||||
|
|
||||||
struct noop_accessor {
|
class noop_accessor {
|
||||||
SearchReplaceSettings::Field field;
|
boost::flyweight<wxString> AssDialogue::*field;
|
||||||
size_t start;
|
size_t start;
|
||||||
|
|
||||||
|
public:
|
||||||
|
noop_accessor(SearchReplaceSettings::Field f) : field(get_dialogue_field(f)), start(0) { }
|
||||||
|
|
||||||
wxString get(const AssDialogue *d, size_t s) {
|
wxString get(const AssDialogue *d, size_t s) {
|
||||||
start = s;
|
start = s;
|
||||||
return get_dialogue_field(d, field)->get().substr(s);
|
return (d->*field).get().substr(s);
|
||||||
}
|
}
|
||||||
|
|
||||||
MatchState make_match_state(size_t s, size_t e, wxRegEx *r = nullptr) {
|
MatchState make_match_state(size_t s, size_t e, wxRegEx *r = nullptr) {
|
||||||
|
@ -68,8 +70,8 @@ struct noop_accessor {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
struct skip_tags_accessor {
|
class skip_tags_accessor {
|
||||||
SearchReplaceSettings::Field field;
|
boost::flyweight<wxString> AssDialogue::*field;
|
||||||
std::vector<std::pair<size_t, size_t>> blocks;
|
std::vector<std::pair<size_t, size_t>> blocks;
|
||||||
size_t start;
|
size_t start;
|
||||||
|
|
||||||
|
@ -89,8 +91,11 @@ struct skip_tags_accessor {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public:
|
||||||
|
skip_tags_accessor(SearchReplaceSettings::Field f) : field(get_dialogue_field(f)), start(0) { }
|
||||||
|
|
||||||
wxString get(const AssDialogue *d, size_t s) {
|
wxString get(const AssDialogue *d, size_t s) {
|
||||||
auto const& str = get_dialogue_field(d, field)->get();
|
auto const& str = (d->*field).get();
|
||||||
parse_str(str);
|
parse_str(str);
|
||||||
|
|
||||||
wxString out;
|
wxString out;
|
||||||
|
@ -181,13 +186,9 @@ matcher get_matcher(SearchReplaceSettings const& settings, wxRegEx *regex, Acces
|
||||||
}
|
}
|
||||||
|
|
||||||
matcher get_matcher(SearchReplaceSettings const& settings, wxRegEx *regex) {
|
matcher get_matcher(SearchReplaceSettings const& settings, wxRegEx *regex) {
|
||||||
if (!settings.skip_tags) {
|
if (settings.skip_tags)
|
||||||
noop_accessor a = { settings.field };
|
return get_matcher(settings, regex, skip_tags_accessor(settings.field));
|
||||||
return get_matcher(settings, regex, a);
|
return get_matcher(settings, regex, noop_accessor(settings.field));
|
||||||
}
|
|
||||||
|
|
||||||
skip_tags_accessor a = { settings.field };
|
|
||||||
return get_matcher(settings, regex, a);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename Iterator, typename Container>
|
template<typename Iterator, typename Container>
|
||||||
|
@ -207,8 +208,8 @@ SearchReplaceEngine::SearchReplaceEngine(agi::Context *c)
|
||||||
}
|
}
|
||||||
|
|
||||||
void SearchReplaceEngine::Replace(AssDialogue *diag, MatchState &ms) {
|
void SearchReplaceEngine::Replace(AssDialogue *diag, MatchState &ms) {
|
||||||
auto diag_field = get_dialogue_field(diag, settings.field);
|
auto& diag_field = diag->*get_dialogue_field(settings.field);
|
||||||
auto text = diag_field->get();
|
auto text = diag_field.get();
|
||||||
|
|
||||||
wxString replacement = settings.replace_with;
|
wxString replacement = settings.replace_with;
|
||||||
if (ms.re) {
|
if (ms.re) {
|
||||||
|
@ -217,7 +218,7 @@ void SearchReplaceEngine::Replace(AssDialogue *diag, MatchState &ms) {
|
||||||
replacement = to_replace;
|
replacement = to_replace;
|
||||||
}
|
}
|
||||||
|
|
||||||
*diag_field = text.substr(0, ms.start) + replacement + text.substr(ms.end);
|
diag_field = text.substr(0, ms.start) + replacement + text.substr(ms.end);
|
||||||
ms.end = ms.start + replacement.size();
|
ms.end = ms.start + replacement.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -316,13 +317,13 @@ bool SearchReplaceEngine::ReplaceAll() {
|
||||||
|
|
||||||
if (settings.use_regex) {
|
if (settings.use_regex) {
|
||||||
if (MatchState ms = matches(diag, 0)) {
|
if (MatchState ms = matches(diag, 0)) {
|
||||||
auto diag_field = get_dialogue_field(diag, settings.field);
|
auto& diag_field = diag->*get_dialogue_field(settings.field);
|
||||||
auto text = diag_field->get();
|
auto text = diag_field.get();
|
||||||
// A zero length match (such as '$') will always be replaced
|
// A zero length match (such as '$') will always be replaced
|
||||||
// maxMatches times, which is almost certainly not what the user
|
// maxMatches times, which is almost certainly not what the user
|
||||||
// wanted, so limit it to one replacement in that situation
|
// wanted, so limit it to one replacement in that situation
|
||||||
count += ms.re->Replace(&text, settings.replace_with, ms.start == ms.end);
|
count += ms.re->Replace(&text, settings.replace_with, ms.start == ms.end);
|
||||||
*diag_field = text;
|
diag_field = text;
|
||||||
}
|
}
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue