diff --git a/src/Gui/QuantitySpinBox.cpp b/src/Gui/QuantitySpinBox.cpp index 6b60ed6a1d..5d9c570c7a 100644 --- a/src/Gui/QuantitySpinBox.cpp +++ b/src/Gui/QuantitySpinBox.cpp @@ -187,18 +187,31 @@ public: static const std::string regexConstants = "e|ip|lomm|lom"; static const std::string regexNumber = "\\d+\\s*\\.?\\s*\\d*|\\.\\s*\\d+"; - //Find units and replace 1/2mm -> 1/2*(1mm), 1^2mm -> 1^2*(1mm) - copyChunk.replace(QRegularExpression(QString::fromStdString("("+regexUnits+")(\\)|(?:\\*|(?:\\)(?:(?:\\s*(?:"+regexConstants+"|\\)(?:[^()]|(?R))*\\((?:"+regexUnitlessFunctions+")|"+regexNumber+"))|(?R))*\\(|(?:\\s*(?:"+regexConstants+"|\\)(?:[^()]|(?R))*\\((?:"+regexUnitlessFunctions+")|"+regexNumber+"))))+[\\/\\^](?!("+regexUnits+")))")), QString::fromUtf8(")\\11(*\\2")); + // If expression does not contain /*() or ^, this regex will not find anything + if (copy.contains(QLatin1Char('/')) || copy.contains(QLatin1Char('*')) || copy.contains(QLatin1Char('(')) || copy.contains(QLatin1Char(')')) || copy.contains(QLatin1Char('^'))){ + //Find units and replace 1/2mm -> 1/2*(1mm), 1^2mm -> 1^2*(1mm) + QRegularExpression fixUnits(QString::fromStdString("("+regexUnits+")(\\s*\\)|(?:\\*|(?:\\)(?:(?:\\s*(?:"+regexConstants+"|\\)(?:[^()]|(?R))*\\((?:"+regexUnitlessFunctions+")|"+regexNumber+"))|(?R))*\\(|(?:\\s*(?:"+regexConstants+"|\\)(?:[^()]|(?R))*\\((?:"+regexUnitlessFunctions+")|"+regexNumber+"))))+(?:[\\/\\^]|(.*$))(?!("+regexUnits+")))")); + QRegularExpressionMatch fixUnitsMatch = fixUnits.match(copyChunk); + + //3rd capture group being filled indicates regex bailed out; no match. + if (fixUnitsMatch.lastCapturedIndex() == 2 || (fixUnitsMatch.lastCapturedIndex() == 3 && fixUnitsMatch.captured(3).isEmpty())){ + QString matchUnits = fixUnitsMatch.captured(1); + QString matchNumbers = fixUnitsMatch.captured(2); + copyChunk.replace(matchUnits+matchNumbers, QString::fromUtf8(")")+matchUnits+QString::fromUtf8("1(*")+matchNumbers); + } + } //Add default units to string if none are present - QRegularExpression unitsRe(QString::fromStdString("(?<=\\b|[^a-zA-Z])("+regexUnits+")(?=\\b|[^a-zA-Z])|°|″|′|\"|'|\\p{L}\\.\\p{L}|\\[\\p{L}")); + if (!copyChunk.contains(unitStr)){ // Fast check + QRegularExpression unitsRe(QString::fromStdString("(?<=\\b|[^a-zA-Z])("+regexUnits+")(?=\\b|[^a-zA-Z])|°|″|′|\"|'|\\p{L}\\.\\p{L}|\\[\\p{L}")); - QRegularExpressionMatch match = unitsRe.match(copyChunk); - std::reverse(copyChunk.begin(), copyChunk.end()); - if (!match.hasMatch() && !copyChunk.isEmpty()){ //If no units are found, use default units - copyChunk.append(QString::fromUtf8("*(1")+unitStr+QString::fromUtf8(")")); // Add units to the end of chunk *(1unit) + QRegularExpressionMatch match = unitsRe.match(copyChunk); + if (!match.hasMatch() && !copyChunk.isEmpty()) //If no units are found, use default units + copyChunk.prepend(QString::fromUtf8(")")+unitStr+QString::fromUtf8("1(*")); // Add units to the end of chunk *(1unit) } + std::reverse(copyChunk.begin(), copyChunk.end()); + copy.replace(matchChunk.capturedStart() + lengthOffset, matchChunk.capturedEnd() - matchChunk.capturedStart(), copyChunk); lengthOffset += copyChunk.length() - origionalChunk.length();