From 91bc32b71f531de895cff4a07c95347fd3a44956 Mon Sep 17 00:00:00 2001 From: dismine Date: Thu, 4 Dec 2014 19:28:47 +0200 Subject: [PATCH] Use little trick for translation error strings from math parser. --HG-- branch : develop --- src/libs/qmuparser/qmuparser.pri | 6 +- src/libs/qmuparser/qmuparsererror.cpp | 197 +++++++++++++++++++------- src/libs/qmuparser/qmuparsererror.h | 5 +- src/libs/qmuparser/qmutranslation.cpp | 77 ++++++++++ src/libs/qmuparser/qmutranslation.h | 95 +++++++++++++ 5 files changed, 328 insertions(+), 52 deletions(-) create mode 100644 src/libs/qmuparser/qmutranslation.cpp create mode 100644 src/libs/qmuparser/qmutranslation.h diff --git a/src/libs/qmuparser/qmuparser.pri b/src/libs/qmuparser/qmuparser.pri index e4913de81..13a555b84 100644 --- a/src/libs/qmuparser/qmuparser.pri +++ b/src/libs/qmuparser/qmuparser.pri @@ -9,7 +9,8 @@ SOURCES += \ $$PWD/qmuparserbytecode.cpp \ $$PWD/qmuparserbase.cpp \ $$PWD/qmuparsertest.cpp \ - $$PWD/stable.cpp + $$PWD/stable.cpp \ + $$PWD/qmutranslation.cpp HEADERS += \ $$PWD/qmuparser.h\ @@ -23,4 +24,5 @@ HEADERS += \ $$PWD/qmuparserbytecode.h \ $$PWD/qmuparserbase.h \ $$PWD/qmuparsertest.h \ - $$PWD/stable.h + $$PWD/stable.h \ + $$PWD/qmutranslation.h diff --git a/src/libs/qmuparser/qmuparsererror.cpp b/src/libs/qmuparser/qmuparsererror.cpp index 1eac14d9b..824fd47be 100644 --- a/src/libs/qmuparser/qmuparsererror.cpp +++ b/src/libs/qmuparser/qmuparsererror.cpp @@ -38,56 +38,154 @@ QmuParserErrorMsg::~QmuParserErrorMsg() //--------------------------------------------------------------------------------------------------------------------- QmuParserErrorMsg::QmuParserErrorMsg() - : m_vErrMsg ( 0 ) + : m_vErrMsg () { - m_vErrMsg.resize ( ecCOUNT ); + m_vErrMsg.clear(); - m_vErrMsg[ecUNASSIGNABLE_TOKEN] = "Unexpected token \"$TOK$\" found at position $POS$."; - m_vErrMsg[ecINTERNAL_ERROR] = "Internal error"; - m_vErrMsg[ecINVALID_NAME] = "Invalid function-, variable- or constant name: \"$TOK$\"."; - m_vErrMsg[ecINVALID_BINOP_IDENT] = "Invalid binary operator identifier: \"$TOK$\"."; - m_vErrMsg[ecINVALID_INFIX_IDENT] = "Invalid infix operator identifier: \"$TOK$\"."; - m_vErrMsg[ecINVALID_POSTFIX_IDENT] = "Invalid postfix operator identifier: \"$TOK$\"."; - m_vErrMsg[ecINVALID_FUN_PTR] = "Invalid pointer to callback function."; - m_vErrMsg[ecEMPTY_EXPRESSION] = "Expression is empty."; - m_vErrMsg[ecINVALID_VAR_PTR] = "Invalid pointer to variable."; - m_vErrMsg[ecUNEXPECTED_OPERATOR] = "Unexpected operator \"$TOK$\" found at position $POS$"; - m_vErrMsg[ecUNEXPECTED_EOF] = "Unexpected end of expression at position $POS$"; - m_vErrMsg[ecUNEXPECTED_ARG_SEP] = "Unexpected argument separator at position $POS$"; - m_vErrMsg[ecUNEXPECTED_PARENS] = "Unexpected parenthesis \"$TOK$\" at position $POS$"; - m_vErrMsg[ecUNEXPECTED_FUN] = "Unexpected function \"$TOK$\" at position $POS$"; - m_vErrMsg[ecUNEXPECTED_VAL] = "Unexpected value \"$TOK$\" found at position $POS$"; - m_vErrMsg[ecUNEXPECTED_VAR] = "Unexpected variable \"$TOK$\" found at position $POS$"; - m_vErrMsg[ecUNEXPECTED_ARG] = "Function arguments used without a function (position: $POS$)"; - m_vErrMsg[ecMISSING_PARENS] = "Missing parenthesis"; - m_vErrMsg[ecTOO_MANY_PARAMS] = "Too many parameters for function \"$TOK$\" at expression position $POS$"; - m_vErrMsg[ecTOO_FEW_PARAMS] = "Too few parameters for function \"$TOK$\" at expression position $POS$"; - m_vErrMsg[ecDIV_BY_ZERO] = "Divide by zero"; - m_vErrMsg[ecDOMAIN_ERROR] = "Domain error"; - m_vErrMsg[ecNAME_CONFLICT] = "Name conflict"; - m_vErrMsg[ecOPT_PRI] = "Invalid value for operator priority (must be greater or equal to zero)."; - m_vErrMsg[ecBUILTIN_OVERLOAD] = "user defined binary operator \"$TOK$\" conflicts with a built in operator."; - m_vErrMsg[ecUNEXPECTED_STR] = "Unexpected string token found at position $POS$."; - m_vErrMsg[ecUNTERMINATED_STRING] = "Unterminated string starting at position $POS$."; - m_vErrMsg[ecSTRING_EXPECTED] = "String function called with a non string type of argument."; - m_vErrMsg[ecVAL_EXPECTED] = "String value used where a numerical argument is expected."; - m_vErrMsg[ecOPRT_TYPE_CONFLICT] = "No suitable overload for operator \"$TOK$\" at position $POS$."; - m_vErrMsg[ecSTR_RESULT] = "Function result is a string."; - m_vErrMsg[ecGENERIC] = "Parser error."; - m_vErrMsg[ecLOCALE] = "Decimal separator is identic to function argument separator."; - m_vErrMsg[ecUNEXPECTED_CONDITIONAL] = "The \"$TOK$\" operator must be preceeded by a closing bracket."; - m_vErrMsg[ecMISSING_ELSE_CLAUSE] = "If-then-else operator is missing an else clause"; - m_vErrMsg[ecMISPLACED_COLON] = "Misplaced colon at position $POS$"; - -#if defined(_DEBUG) - for ( int i = 0; i < ecCOUNT; ++i ) - { - if ( m_vErrMsg[i].length() == false) - { - assert ( false ); - } - } -#endif + m_vErrMsg.insert(ecUNASSIGNABLE_TOKEN, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected token \"$TOK$\" found at position $POS$.", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecINTERNAL_ERROR, + QmuTranslation::translate("QmuParserErrorMsg", + "Internal error", + "Math parser error messages.")); + m_vErrMsg.insert(ecINVALID_NAME, + QmuTranslation::translate("QmuParserErrorMsg", + "Invalid function-, variable- or constant name: \"$TOK$\".", + "Math parser error messages. Left untouched \"$TOK$\"")); + m_vErrMsg.insert(ecINVALID_BINOP_IDENT, + QmuTranslation::translate("QmuParserErrorMsg", + "Invalid binary operator identifier: \"$TOK$\".", + "Math parser error messages. Left untouched \"$TOK$\"")); + m_vErrMsg.insert(ecINVALID_INFIX_IDENT, + QmuTranslation::translate("QmuParserErrorMsg", + "Invalid infix operator identifier: \"$TOK$\".", + "Math parser error messages. Left untouched \"$TOK$\"")); + m_vErrMsg.insert(ecINVALID_POSTFIX_IDENT, + QmuTranslation::translate("QmuParserErrorMsg", + "Invalid postfix operator identifier: \"$TOK$\".", + "Math parser error messages. Left untouched \"$TOK$\"")); + m_vErrMsg.insert(ecINVALID_FUN_PTR, + QmuTranslation::translate("QmuParserErrorMsg", + "Invalid pointer to callback function.", + "Math parser error messages.")); + m_vErrMsg.insert(ecEMPTY_EXPRESSION, + QmuTranslation::translate("QmuParserErrorMsg", + "Expression is empty.", + "Math parser error messages.")); + m_vErrMsg.insert(ecINVALID_VAR_PTR, + QmuTranslation::translate("QmuParserErrorMsg", + "Invalid pointer to variable.", + "Math parser error messages.")); + m_vErrMsg.insert(ecUNEXPECTED_OPERATOR, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected operator \"$TOK$\" found at position $POS$", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecUNEXPECTED_EOF, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected end of expression at position $POS$", + "Math parser error messages. Left untouched $POS$")); + m_vErrMsg.insert(ecUNEXPECTED_ARG_SEP, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected argument separator at position $POS$", + "Math parser error messages. Left untouched $POS$")); + m_vErrMsg.insert(ecUNEXPECTED_PARENS, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected parenthesis \"$TOK$\" at position $POS$", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecUNEXPECTED_FUN, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected function \"$TOK$\" at position $POS$", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecUNEXPECTED_VAL, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected value \"$TOK$\" found at position $POS$", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecUNEXPECTED_VAR, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected variable \"$TOK$\" found at position $POS$", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecUNEXPECTED_ARG, + QmuTranslation::translate("QmuParserErrorMsg", + "Function arguments used without a function (position: $POS$)", + "Math parser error messages. Left untouched $POS$")); + m_vErrMsg.insert(ecMISSING_PARENS, + QmuTranslation::translate("QmuParserErrorMsg", + "Missing parenthesis", + "Math parser error messages.")); + m_vErrMsg.insert(ecTOO_MANY_PARAMS, + QmuTranslation::translate("QmuParserErrorMsg", + "Too many parameters for function \"$TOK$\" at expression position $POS$", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecTOO_FEW_PARAMS, + QmuTranslation::translate("QmuParserErrorMsg", + "Too few parameters for function \"$TOK$\" at expression position $POS$", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecDIV_BY_ZERO, + QmuTranslation::translate("QmuParserErrorMsg", + "Divide by zero", + "Math parser error messages.")); + m_vErrMsg.insert(ecDOMAIN_ERROR, + QmuTranslation::translate("QmuParserErrorMsg", + "Domain error", + "Math parser error messages.")); + m_vErrMsg.insert(ecNAME_CONFLICT, + QmuTranslation::translate("QmuParserErrorMsg", + "Name conflict", + "Math parser error messages.")); + m_vErrMsg.insert(ecOPT_PRI, + QmuTranslation::translate("QmuParserErrorMsg", + "Invalid value for operator priority (must be greater or equal to zero).", + "Math parser error messages.")); + m_vErrMsg.insert(ecBUILTIN_OVERLOAD, + QmuTranslation::translate("QmuParserErrorMsg", + "user defined binary operator \"$TOK$\" conflicts with a built in operator.", + "Math parser error messages. Left untouched \"$TOK$\"")); + m_vErrMsg.insert(ecUNEXPECTED_STR, + QmuTranslation::translate("QmuParserErrorMsg", + "Unexpected string token found at position $POS$.", + "Math parser error messages. Left untouched $POS$")); + m_vErrMsg.insert(ecUNTERMINATED_STRING, + QmuTranslation::translate("QmuParserErrorMsg", + "Unterminated string starting at position $POS$.", + "Math parser error messages. Left untouched $POS$")); + m_vErrMsg.insert(ecSTRING_EXPECTED, + QmuTranslation::translate("QmuParserErrorMsg", + "String function called with a non string type of argument.", + "Math parser error messages.")); + m_vErrMsg.insert(ecVAL_EXPECTED, + QmuTranslation::translate("QmuParserErrorMsg", + "String value used where a numerical argument is expected.", + "Math parser error messages.")); + m_vErrMsg.insert(ecOPRT_TYPE_CONFLICT, + QmuTranslation::translate("QmuParserErrorMsg", + "No suitable overload for operator \"$TOK$\" at position $POS$.", + "Math parser error messages. Left untouched \"$TOK$\" and $POS$")); + m_vErrMsg.insert(ecSTR_RESULT, + QmuTranslation::translate("QmuParserErrorMsg", + "Function result is a string.", + "Math parser error messages.")); + m_vErrMsg.insert(ecGENERIC, + QmuTranslation::translate("QmuParserErrorMsg", + "Parser error.", + "Math parser error messages.")); + m_vErrMsg.insert(ecLOCALE, + QmuTranslation::translate("QmuParserErrorMsg", + "Decimal separator is identic to function argument separator.", + "Math parser error messages.")); + m_vErrMsg.insert(ecUNEXPECTED_CONDITIONAL, + QmuTranslation::translate("QmuParserErrorMsg", + "The \"$TOK$\" operator must be preceeded by a closing bracket.", + "Math parser error messages. Left untouched $TOK$")); + m_vErrMsg.insert(ecMISSING_ELSE_CLAUSE, + QmuTranslation::translate("QmuParserErrorMsg", + "If-then-else operator is missing an else clause", + "Math parser error messages. Do not translate operator name.")); + m_vErrMsg.insert(ecMISPLACED_COLON, + QmuTranslation::translate("QmuParserErrorMsg", + "Misplaced colon at position $POS$", + "Math parser error messages. Left untouched $POS$")); } //--------------------------------------------------------------------------------------------------------------------- @@ -141,8 +239,11 @@ QmuParserError::QmuParserError ( EErrorCodes iErrc, const QString &sTok, const Q m_ErrMsg ( QmuParserErrorMsg::Instance() ) { m_sMsg = m_ErrMsg[m_iErrc]; + qDebug()< #include "qmuparserdef.h" +#include "qmutranslation.h" /** @file @brief This file defines the error class used by the parser. @@ -106,7 +107,7 @@ public: private: Q_DISABLE_COPY(QmuParserErrorMsg) - QVector m_vErrMsg; ///< A vector with the predefined error messages + QMap m_vErrMsg; ///< A map with the predefined error messages static const self_type m_Instance; ///< The instance pointer }; @@ -120,7 +121,7 @@ inline const QmuParserErrorMsg& QmuParserErrorMsg::Instance() //--------------------------------------------------------------------------------------------------------------------- inline QString QmuParserErrorMsg::operator[] ( int a_iIdx ) const { - return ( a_iIdx < m_vErrMsg.size() ) ? m_vErrMsg[a_iIdx] : QString(); + return m_vErrMsg.value(a_iIdx).translate(); } //--------------------------------------------------------------------------- diff --git a/src/libs/qmuparser/qmutranslation.cpp b/src/libs/qmuparser/qmutranslation.cpp new file mode 100644 index 000000000..a01b5cdf5 --- /dev/null +++ b/src/libs/qmuparser/qmutranslation.cpp @@ -0,0 +1,77 @@ +/*************************************************************************************************** + ** + ** Original work Copyright (C) 2014 Roman Telezhynskyi + ** + ** Permission is hereby granted, free of charge, to any person obtaining a copy of this + ** software and associated documentation files (the "Software"), to deal in the Software + ** without restriction, including without limitation the rights to use, copy, modify, + ** merge, publish, distribute, sublicense, and/or sell copies of the Software, and to + ** permit persons to whom the Software is furnished to do so, subject to the following conditions: + ** + ** The above copyright notice and this permission notice shall be included in all copies or + ** substantial portions of the Software. + ** + ** THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT + ** NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + ** NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, + ** DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + ** OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + ** + ******************************************************************************************************/ + +#include "qmutranslation.h" +#include + +namespace qmu +{ + +//--------------------------------------------------------------------------------------------------------------------- +QmuTranslation QmuTranslation::translate(const QString &context, const QString &sourceText, + const QString &disambiguation, int n) +{ + if (n < 0) + { + n = -1; + } + QmuTranslation t(context, sourceText, disambiguation, n); + return t; +} + +//--------------------------------------------------------------------------------------------------------------------- +QmuTranslation::QmuTranslation() + :mcontext(QString()), msourceText(QString()), mdisambiguation(QString()), mn(-1) +{} + +//--------------------------------------------------------------------------------------------------------------------- +QmuTranslation::QmuTranslation(const QString &context, const QString &sourceText, const QString &disambiguation, int n) + :mcontext(context), msourceText(sourceText), mdisambiguation(disambiguation), mn(n) +{} + +//--------------------------------------------------------------------------------------------------------------------- +QmuTranslation &QmuTranslation::operator=(const QmuTranslation &tr) +{ + if ( &tr == this ) + { + return *this; + } + this->mcontext = tr.getMcontext(); + this->msourceText = tr.getMsourceText(); + this->mdisambiguation = tr.getMdisambiguation(); + this->mn = tr.getN(); + return *this; +} + +//--------------------------------------------------------------------------------------------------------------------- +QmuTranslation::QmuTranslation(const QmuTranslation &tr) + :mcontext(tr.getMcontext()), msourceText(tr.getMsourceText()), mdisambiguation(tr.getMdisambiguation()), + mn(tr.getN()) +{} + +//--------------------------------------------------------------------------------------------------------------------- +QString QmuTranslation::translate() const +{ + return QCoreApplication::translate(mcontext.toUtf8().constData(), msourceText.toUtf8().constData(), + mdisambiguation.toUtf8().constData(), mn); +} + +} // namespace qmu diff --git a/src/libs/qmuparser/qmutranslation.h b/src/libs/qmuparser/qmutranslation.h new file mode 100644 index 000000000..688e8ecb5 --- /dev/null +++ b/src/libs/qmuparser/qmutranslation.h @@ -0,0 +1,95 @@ +/*************************************************************************************************** + ** + ** Original work Copyright (C) 2014 Roman Telezhynskyi + ** + ** Permission is hereby granted, free of charge, to any person obtaining a copy of this + ** software and associated documentation files (the "Software"), to deal in the Software + ** without restriction, including without limitation the rights to use, copy, modify, + ** merge, publish, distribute, sublicense, and/or sell copies of the Software, and to + ** permit persons to whom the Software is furnished to do so, subject to the following conditions: + ** + ** The above copyright notice and this permission notice shall be included in all copies or + ** substantial portions of the Software. + ** + ** THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT + ** NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + ** NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, + ** DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + ** OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + ** + ******************************************************************************************************/ + +#ifndef QMUTRANSLATION_H +#define QMUTRANSLATION_H + +#include "qmuparser_global.h" +#include + +namespace qmu +{ + +/** + * @file + * @brief The VTranslation class help store string for translation. + * + * I took idea from this article http://ololoepepe.blogspot.com/2013/08/qt.html. + * As you know, if wrap string to a function translate, it will be marked for translation. No matter what namespace + * contains this function. In class Translation used this circumstance. + * This mean never change name of method translate!!!!!. + * Instead of using QT_TRANSLATE_NOOP3 macros we can store strings in QMap. + * Example: + * create map and fill up its + * QMap map; + * map.insert("head_girth", VTranslation::translate("Measurements", "head_girth", "Around fullest part of Head.")); + * get translated string + * map.value(measurement).translate(); + */ +class QMUPARSERSHARED_EXPORT QmuTranslation +{ +public: + QmuTranslation(); + ~QmuTranslation(){} + QmuTranslation(const QString &context, const QString &sourceText, const QString &disambiguation = 0, int n = -1); + QmuTranslation &operator=(const QmuTranslation &tr); + QmuTranslation(const QmuTranslation &tr); + QString translate() const; + static QmuTranslation translate(const QString &context, const QString &sourceText, + const QString &disambiguation = 0, int n = -1); + QString getMcontext() const; + QString getMsourceText() const; + QString getMdisambiguation() const; + int getN() const; +private: + QString mcontext; + QString msourceText; + QString mdisambiguation; + int mn; +}; + +//--------------------------------------------------------------------------------------------------------------------- +inline QString QmuTranslation::getMcontext() const +{ + return mcontext; +} + +//--------------------------------------------------------------------------------------------------------------------- +inline QString QmuTranslation::getMsourceText() const +{ + return msourceText; +} + +//--------------------------------------------------------------------------------------------------------------------- +inline QString QmuTranslation::getMdisambiguation() const +{ + return mdisambiguation; +} + +//--------------------------------------------------------------------------------------------------------------------- +inline int QmuTranslation::getN() const +{ + return mn; +} + +} // namespace qmu + +#endif // QMUTRANSLATION_H