mirror of
https://github.com/cookiengineer/audacity
synced 2025-07-31 07:59:27 +02:00
Line breaks allowed in strings (or lists) in $ lines; \n means n ...
... because we must match how xgettext parses strings, and unlike XLisp, it does it strictly according to this reference: http://www.lispworks.com/documentation/lw70/CLHS/Body/02_de.htm
This commit is contained in:
parent
ad4843621b
commit
ff3a869e83
@ -1471,26 +1471,27 @@ wxString NyquistEffect::EscapeString(const wxString & inStr)
|
||||
|
||||
wxArrayString NyquistEffect::ParseChoice(const wxString & text)
|
||||
{
|
||||
wxArrayString choices;
|
||||
if (text[0] == wxT('(')) {
|
||||
// New style: expecting a Lisp-like list of strings
|
||||
Tokenize(text, choices, 1, 1);
|
||||
Tokenizer tzer;
|
||||
tzer.Tokenize(text, true, 1, 1);
|
||||
auto &choices = tzer.tokens;
|
||||
for (auto &choice : choices)
|
||||
choice = UnQuote(choice);
|
||||
return choices;
|
||||
}
|
||||
else {
|
||||
// Old style: expecting a comma-separated list of
|
||||
// un-internationalized names, ignoring leading and trailing spaces
|
||||
// on each; and the whole may be quoted
|
||||
choices = wxStringTokenize(
|
||||
auto choices = wxStringTokenize(
|
||||
text[0] == wxT('"') ? text.Mid(1, text.Length() - 2) : text,
|
||||
wxT(",")
|
||||
);
|
||||
for (auto &choice : choices)
|
||||
choice = choice.Trim(true).Trim(false);
|
||||
return choices;
|
||||
}
|
||||
|
||||
return choices;
|
||||
}
|
||||
|
||||
void NyquistEffect::RedirectOutput()
|
||||
@ -1530,8 +1531,9 @@ wxString NyquistEffect::UnQuote(
|
||||
}
|
||||
else if (allowParens &&
|
||||
len >= 2 && s[0] == wxT('(') && s[len - 1] == wxT(')')) {
|
||||
wxArrayString tokens;
|
||||
Tokenize(s, tokens, 1, 1);
|
||||
Tokenizer tzer;
|
||||
tzer.Tokenize(s, true, 1, 1);
|
||||
auto &tokens = tzer.tokens;
|
||||
if (tokens.size() > 1)
|
||||
// Assume the first token was _ -- we don't check that
|
||||
// And the second is the string, which is internationalized
|
||||
@ -1564,15 +1566,10 @@ double NyquistEffect::GetCtrlValue(const wxString &s)
|
||||
return Internat::CompatibleToDouble(s);
|
||||
}
|
||||
|
||||
void NyquistEffect::Tokenize(
|
||||
const wxString &line, wxArrayString &tokens,
|
||||
bool NyquistEffect::Tokenizer::Tokenize(
|
||||
const wxString &line, bool eof,
|
||||
size_t trimStart, size_t trimEnd)
|
||||
{
|
||||
bool sl = false;
|
||||
bool q = false;
|
||||
wxString tok = wxT("");
|
||||
int paren = 0;
|
||||
|
||||
auto endToken = [&]{
|
||||
if (!tok.empty()) {
|
||||
tokens.push_back(tok);
|
||||
@ -1587,8 +1584,6 @@ void NyquistEffect::Tokenize(
|
||||
sl = true;
|
||||
continue;
|
||||
}
|
||||
else if (sl && c == wxT('n'))
|
||||
c = wxT('\n');
|
||||
|
||||
if (!sl && !paren && c == wxT('"')) {
|
||||
if (!q)
|
||||
@ -1626,18 +1621,29 @@ void NyquistEffect::Tokenize(
|
||||
sl = false;
|
||||
}
|
||||
|
||||
// Finish -- this just forgives unbalanced open quotes or left parens
|
||||
endToken();
|
||||
if (eof || (!q && !paren)) {
|
||||
endToken();
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
// End of line but not of file, and a string or list is yet unclosed
|
||||
// If a string, accumulate a newline character
|
||||
if (q)
|
||||
tok += wxT('\n');
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
void NyquistEffect::Parse(const wxString &line)
|
||||
bool NyquistEffect::Parse(
|
||||
Tokenizer &tzer, const wxString &line, bool eof, bool first)
|
||||
{
|
||||
wxArrayString tokens;
|
||||
Tokenize(line, tokens, 1, 0);
|
||||
if ( !tzer.Tokenize(line, eof, first ? 1 : 0, 0) )
|
||||
return false;
|
||||
|
||||
const auto &tokens = tzer.tokens;
|
||||
int len = tokens.size();
|
||||
if (len < 1) {
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Consistency decision is for "plug-in" as the correct spelling
|
||||
@ -1645,7 +1651,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
if (len == 2 && tokens[0] == wxT("nyquist") &&
|
||||
(tokens[1] == wxT("plug-in") || tokens[1] == wxT("plugin"))) {
|
||||
mOK = true;
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (len >= 2 && tokens[0] == wxT("type")) {
|
||||
@ -1661,7 +1667,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
if (len >= 3 && tokens[2] == wxT("spectral")) {;
|
||||
mIsSpectral = true;
|
||||
}
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (len == 2 && tokens[0] == wxT("codetype")) {
|
||||
@ -1674,7 +1680,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
mIsSal = true;
|
||||
mFoundType = true;
|
||||
}
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
// TODO: Update documentation.
|
||||
@ -1696,7 +1702,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
mCompiler = false;
|
||||
}
|
||||
}
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
// We support versions 1, 2 and 3
|
||||
@ -1713,7 +1719,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
_("This version of Audacity does not support Nyquist plug-in version %ld"),
|
||||
v
|
||||
);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
mVersion = (int) v;
|
||||
}
|
||||
@ -1722,17 +1728,17 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
mName = UnQuote(tokens[1]);
|
||||
if (mName.EndsWith(wxT("...")))
|
||||
mName = mName.RemoveLast(3);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (len >= 2 && tokens[0] == wxT("action")) {
|
||||
mAction = UnQuote(tokens[1]);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (len >= 2 && tokens[0] == wxT("info")) {
|
||||
mInfo = UnQuote(tokens[1]);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (len >= 2 && tokens[0] == wxT("preview")) {
|
||||
@ -1751,7 +1757,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
else if (tokens[1] == wxT("disabled") || tokens[1] == wxT("false")) {
|
||||
mEnablePreview = false;
|
||||
}
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Maximum number of samples to be processed. This can help the
|
||||
@ -1768,7 +1774,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
// -1 = auto (default), 0 = don't merge clips, 1 = do merge clips
|
||||
tokens[1].ToLong(&v);
|
||||
mMergeClips = v;
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (len >= 2 && tokens[0] == wxT("restoresplits")) {
|
||||
@ -1776,18 +1782,18 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
// Splits are restored by default. Set to 0 to prevent.
|
||||
tokens[1].ToLong(&v);
|
||||
mRestoreSplits = !!v;
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (len >= 2 && tokens[0] == wxT("author")) {
|
||||
mAuthor = UnQuote(tokens[1]);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (len >= 2 && tokens[0] == wxT("copyright")) {
|
||||
mCopyright = UnQuote(tokens[1]);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
// TODO: Document.
|
||||
@ -1795,7 +1801,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
if (len >= 2 && tokens[0] == wxT("manpage")) {
|
||||
// do not translate
|
||||
mManPage = UnQuote(tokens[1], false, false);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
// TODO: Document.
|
||||
@ -1803,7 +1809,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
if (len >= 2 && tokens[0] == wxT("helpfile")) {
|
||||
// do not translate
|
||||
mHelpFile = UnQuote(tokens[1], false, false);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
// TODO: Document.
|
||||
@ -1812,7 +1818,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
if (tokens[1] == wxT("disabled") || tokens[1] == wxT("false")) {
|
||||
mDebugButton = false;
|
||||
}
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (len >= 6 && tokens[0] == wxT("control")) {
|
||||
@ -1845,7 +1851,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
ctrl.label = UnQuote( ctrl.label );
|
||||
|
||||
if (len < 8) {
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
if ((tokens[3] == wxT("float")) ||
|
||||
@ -1869,7 +1875,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
// Note that the AudacityApp's mLogger has not yet been created,
|
||||
// so this brings up an alert box, but after the Audacity frame is up.
|
||||
wxLogWarning(str);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
ctrl.lowStr = tokens[6];
|
||||
@ -1924,6 +1930,7 @@ void NyquistEffect::Parse(const wxString &line)
|
||||
mCategories.Add(tokens[i]);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool NyquistEffect::ParseProgram(wxInputStream & stream)
|
||||
@ -1952,18 +1959,29 @@ bool NyquistEffect::ParseProgram(wxInputStream & stream)
|
||||
mFoundType = false;
|
||||
while (!stream.Eof() && stream.IsOk())
|
||||
{
|
||||
bool dollar = false;
|
||||
wxString line = pgm.ReadLine().Trim(false);
|
||||
if (line.Length() > 1 &&
|
||||
// New in 2.3.0: allow magic comment lines to start with $
|
||||
// The trick is that xgettext will not consider such lines comments
|
||||
// and will extract the strings they contain
|
||||
(line[0] == wxT(';') || line[0] == wxT('$')))
|
||||
(line[0] == wxT(';') ||
|
||||
(dollar = (line[0] == wxT('$')))))
|
||||
{
|
||||
Parse(line);
|
||||
// Don't pass this line to the interpreter, so it doesn't get confused
|
||||
// by $, but pass a blank,
|
||||
Tokenizer tzer;
|
||||
unsigned nLines = 1;
|
||||
bool done;
|
||||
do
|
||||
// Allow run-ons only for new $ format header lines
|
||||
done = Parse(tzer, line, !dollar || stream.Eof(), nLines == 1);
|
||||
while(!done &&
|
||||
(line = pgm.ReadLine().Trim(false), ++nLines, true));
|
||||
|
||||
// Don't pass these lines to the interpreter, so it doesn't get confused
|
||||
// by $, but pass blanks,
|
||||
// so that SAL effects compile with proper line numbers
|
||||
mCmd += wxT('\n');
|
||||
while (nLines --)
|
||||
mCmd += wxT('\n');
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -163,10 +163,18 @@ private:
|
||||
void ParseFile();
|
||||
bool ParseCommand(const wxString & cmd);
|
||||
bool ParseProgram(wxInputStream & stream);
|
||||
static void Tokenize(
|
||||
const wxString &line, wxArrayString &tokens,
|
||||
size_t trimStart, size_t trimEnd);
|
||||
void Parse(const wxString &line);
|
||||
struct Tokenizer {
|
||||
bool sl { false };
|
||||
bool q { false };
|
||||
int paren{ 0 };
|
||||
wxString tok;
|
||||
wxArrayString tokens;
|
||||
|
||||
bool Tokenize(
|
||||
const wxString &line, bool eof,
|
||||
size_t trimStart, size_t trimEnd);
|
||||
};
|
||||
bool Parse(Tokenizer &tokenizer, const wxString &line, bool eof, bool first);
|
||||
|
||||
static wxString UnQuote(const wxString &s,
|
||||
bool allowParens = true, bool translate = true);
|
||||
|
Loading…
x
Reference in New Issue
Block a user