aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChristian Kandeler <christian.kandeler@qt.io>2019-02-01 16:50:29 +0100
committerChristian Kandeler <christian.kandeler@qt.io>2019-02-05 11:31:52 +0000
commit69565d6c88ad66e11817bd661c20af8395b6000e (patch)
tree6bd7fd89e356cf3b810b85b22c6ba077625e35d9
parent719749103a17a6c89cec86bda943232f23e5ee86 (diff)
QmakePM: Respect editor settings when adding files to project
If the user wants to indent with tabs, then consider that when adding source files via the UI. But try not to mix: If the respective variable already uses a different indentation consistently, then keep using that one. Fixes: QTCREATORBUG-8016 Change-Id: I037c9ac4d4e7fbbe5753a846e57d938bbb440d6a Reviewed-by: David Schulz <david.schulz@qt.io>
-rw-r--r--src/plugins/qmakeprojectmanager/qmakeparsernodes.cpp25
-rw-r--r--src/plugins/qmakeprojectmanager/qmakeparsernodes.h2
-rw-r--r--src/shared/proparser/prowriter.cpp65
-rw-r--r--src/shared/proparser/prowriter.h5
-rw-r--r--tests/auto/profilewriter/tst_profilewriter.cpp88
5 files changed, 120 insertions, 65 deletions
diff --git a/src/plugins/qmakeprojectmanager/qmakeparsernodes.cpp b/src/plugins/qmakeprojectmanager/qmakeparsernodes.cpp
index 21d5627f0f..c0034972d6 100644
--- a/src/plugins/qmakeprojectmanager/qmakeparsernodes.cpp
+++ b/src/plugins/qmakeprojectmanager/qmakeparsernodes.cpp
@@ -36,10 +36,14 @@
#include <coreplugin/iversioncontrol.h>
#include <coreplugin/vcsmanager.h>
#include <cpptools/cpptoolsconstants.h>
+#include <projectexplorer/editorconfiguration.h>
#include <projectexplorer/projectexplorer.h>
#include <projectexplorer/projectexplorerconstants.h>
#include <projectexplorer/target.h>
#include <qtsupport/profilereader.h>
+#include <texteditor/icodestylepreferences.h>
+#include <texteditor/tabsettings.h>
+#include <texteditor/texteditorsettings.h>
#include <utils/algorithm.h>
#include <utils/filesystemwatcher.h>
@@ -378,6 +382,19 @@ void QmakePriFile::watchFolders(const QSet<FileName> &folders)
m_watchedFolders = folderStrings;
}
+QString QmakePriFile::continuationIndent() const
+{
+ const EditorConfiguration *editorConf = project()->editorConfiguration();
+ const TextEditor::TabSettings &tabSettings = editorConf->useGlobalSettings()
+ ? TextEditor::TextEditorSettings::codeStyle()->tabSettings()
+ : editorConf->codeStyle()->tabSettings();
+ if (tabSettings.m_continuationAlignBehavior == TextEditor::TabSettings::ContinuationAlignWithIndent
+ && tabSettings.m_tabPolicy == TextEditor::TabSettings::TabsOnlyTabPolicy) {
+ return QString("\t");
+ }
+ return QString(tabSettings.m_indentSize, ' ');
+}
+
bool QmakePriFile::knowsFile(const FileName &filePath) const
{
return m_recursiveEnumerateFiles.contains(filePath);
@@ -747,7 +764,8 @@ bool QmakePriFile::renameFile(const QString &oldName,
ProWriter::addFiles(includeFile, &lines,
QStringList(newName),
- varNameForAdding(mimeType));
+ varNameForAdding(mimeType),
+ continuationIndent());
if (mode == Change::Save)
save(lines);
includeFile->deref();
@@ -777,7 +795,8 @@ void QmakePriFile::changeFiles(const QString &mimeType,
if (change == AddToProFile) {
// Use the first variable for adding.
- ProWriter::addFiles(includeFile, &lines, filePaths, varNameForAdding(mimeType));
+ ProWriter::addFiles(includeFile, &lines, filePaths, varNameForAdding(mimeType),
+ continuationIndent());
notChanged->clear();
} else { // RemoveFromProFile
QDir priFileDir = QDir(m_qmakeProFile->directoryPath().toString());
@@ -818,7 +837,7 @@ bool QmakePriFile::setProVariable(const QString &var, const QStringList &values,
ProWriter::putVarValues(includeFile, &lines, values, var,
ProWriter::PutFlags(flags),
- scope);
+ scope, continuationIndent());
save(lines);
includeFile->deref();
diff --git a/src/plugins/qmakeprojectmanager/qmakeparsernodes.h b/src/plugins/qmakeprojectmanager/qmakeparsernodes.h
index f2bb612b7e..6f0e13a5c9 100644
--- a/src/plugins/qmakeprojectmanager/qmakeparsernodes.h
+++ b/src/plugins/qmakeprojectmanager/qmakeparsernodes.h
@@ -216,6 +216,8 @@ private:
static void processValues(Internal::QmakePriFileEvalResult &result);
void watchFolders(const QSet<Utils::FileName> &folders);
+ QString continuationIndent() const;
+
QmakeProject *m_project = nullptr;
QmakeProFile *m_qmakeProFile = nullptr;
QmakePriFile *m_parent = nullptr;
diff --git a/src/shared/proparser/prowriter.cpp b/src/shared/proparser/prowriter.cpp
index 98547f89ed..3ca7220621 100644
--- a/src/shared/proparser/prowriter.cpp
+++ b/src/shared/proparser/prowriter.cpp
@@ -246,6 +246,7 @@ bool ProWriter::locateVarValues(const ushort *tokPtr, const ushort *tokPtrEnd,
struct LineInfo
{
+ QString indent;
int continuationPos = 0;
bool hasComment = false;
};
@@ -260,14 +261,29 @@ static LineInfo lineInfo(const QString &line)
li.continuationPos = idx;
for (int i = idx - 1; i >= 0 && (line.at(i) == ' ' || line.at(i) == '\t'); --i)
--li.continuationPos;
+ for (int i = 0; i < line.length() && (line.at(i) == ' ' || line.at(i) == '\t'); ++i)
+ li.indent += line.at(i);
return li;
}
-static int skipContLines(QStringList *lines, int lineNo, bool addCont)
+struct ContinuationInfo {
+ QString indent; // Empty means use default
+ int lineNo;
+};
+
+static ContinuationInfo skipContLines(QStringList *lines, int lineNo, bool addCont)
{
+ bool hasConsistentIndent = true;
+ QString lastIndent;
for (; lineNo < lines->count(); lineNo++) {
const QString line = lines->at(lineNo);
LineInfo li = lineInfo(line);
+ if (hasConsistentIndent) {
+ if (lastIndent.isEmpty())
+ lastIndent = li.indent;
+ else if (lastIndent != li.indent)
+ hasConsistentIndent = false;
+ }
if (li.continuationPos == 0) {
if (li.hasComment)
continue;
@@ -280,34 +296,45 @@ static int skipContLines(QStringList *lines, int lineNo, bool addCont)
break;
}
}
- return lineNo;
+ ContinuationInfo ci;
+ if (hasConsistentIndent)
+ ci.indent = lastIndent;
+ ci.lineNo = lineNo;
+ return ci;
}
-void ProWriter::putVarValues(ProFile *profile, QStringList *lines,
- const QStringList &values, const QString &var, PutFlags flags, const QString &scope)
+void ProWriter::putVarValues(ProFile *profile, QStringList *lines, const QStringList &values,
+ const QString &var, PutFlags flags, const QString &scope,
+ const QString &continuationIndent)
{
- QString indent = scope.isEmpty() ? QString() : QLatin1String(" ");
+ QString indent = scope.isEmpty() ? QString() : continuationIndent;
+ const auto effectiveContIndent = [indent, continuationIndent](const ContinuationInfo &ci) {
+ return !ci.indent.isEmpty() ? ci.indent : continuationIndent + indent;
+ };
int scopeStart = -1, lineNo;
if (locateVarValues(profile->tokPtr(), profile->tokPtrEnd(), scope, var, &scopeStart, &lineNo)) {
if (flags & ReplaceValues) {
// remove continuation lines with old values
- int lNo = skipContLines(lines, lineNo, false);
- lines->erase(lines->begin() + lineNo + 1, lines->begin() + lNo);
+ const ContinuationInfo contInfo = skipContLines(lines, lineNo, false);
+ lines->erase(lines->begin() + lineNo + 1, lines->begin() + contInfo.lineNo);
// remove rest of the line
QString &line = (*lines)[lineNo];
int eqs = line.indexOf(QLatin1Char('='));
if (eqs >= 0) // If this is not true, we mess up the file a bit.
line.truncate(eqs + 1);
// put new values
- foreach (const QString &v, values)
- line += ((flags & MultiLine) ? QLatin1String(" \\\n ") + indent : QString::fromLatin1(" ")) + v;
+ foreach (const QString &v, values) {
+ line += ((flags & MultiLine) ? QLatin1String(" \\\n") + effectiveContIndent(contInfo)
+ : QString::fromLatin1(" ")) + v;
+ }
} else {
- int endLineNo = skipContLines(lines, lineNo, false);
+ const ContinuationInfo contInfo = skipContLines(lines, lineNo, false);
+ int endLineNo = contInfo.lineNo;
for (const QString &v : values) {
int curLineNo = lineNo + 1;
while (curLineNo < endLineNo && v >= lines->at(curLineNo).trimmed())
++curLineNo;
- QString newLine = " " + indent + v;
+ QString newLine = effectiveContIndent(contInfo) + v;
if (curLineNo == endLineNo) {
QString &oldLastLine = (*lines)[endLineNo - 1];
oldLastLine.insert(lineInfo(oldLastLine).continuationPos, " \\");
@@ -322,6 +349,7 @@ void ProWriter::putVarValues(ProFile *profile, QStringList *lines,
// Create & append new variable item
QString added;
int lNo = lines->count();
+ ContinuationInfo contInfo;
if (!scope.isEmpty()) {
if (scopeStart < 0) {
added = QLatin1Char('\n') + scope + QLatin1String(" {");
@@ -329,8 +357,10 @@ void ProWriter::putVarValues(ProFile *profile, QStringList *lines,
QRegExp rx(QLatin1String("(\\s*") + scope + QLatin1String("\\s*:\\s*)[^\\s{].*"));
if (rx.exactMatch(lines->at(scopeStart))) {
(*lines)[scopeStart].replace(0, rx.cap(1).length(),
- QString(scope + QLatin1String(" {\n ")));
- lNo = skipContLines(lines, scopeStart, false);
+ QString(scope + QLatin1String(" {\n")
+ + continuationIndent));
+ contInfo = skipContLines(lines, scopeStart, false);
+ lNo = contInfo.lineNo;
scopeStart = -1;
}
}
@@ -357,14 +387,16 @@ void ProWriter::putVarValues(ProFile *profile, QStringList *lines,
added += QLatin1Char('\n');
added += indent + var + QLatin1String((flags & AppendOperator) ? " +=" : " =");
foreach (const QString &v, values)
- added += ((flags & MultiLine) ? QLatin1String(" \\\n ") + indent : QString::fromLatin1(" ")) + v;
+ added += ((flags & MultiLine) ? QLatin1String(" \\\n") + effectiveContIndent(contInfo)
+ : QString::fromLatin1(" ")) + v;
if (!scope.isEmpty() && scopeStart < 0)
added += QLatin1String("\n}");
lines->insert(lNo, added);
}
}
-void ProWriter::addFiles(ProFile *profile, QStringList *lines, const QStringList &values, const QString &var)
+void ProWriter::addFiles(ProFile *profile, QStringList *lines, const QStringList &values,
+ const QString &var, const QString &continuationIndent)
{
QStringList valuesToWrite;
QString prefixPwd;
@@ -374,7 +406,8 @@ void ProWriter::addFiles(ProFile *profile, QStringList *lines, const QStringList
foreach (const QString &v, values)
valuesToWrite << (prefixPwd + baseDir.relativeFilePath(v));
- putVarValues(profile, lines, valuesToWrite, var, AppendValues | MultiLine | AppendOperator);
+ putVarValues(profile, lines, valuesToWrite, var, AppendValues | MultiLine | AppendOperator,
+ QString(), continuationIndent);
}
static void findProVariables(const ushort *tokPtr, const QStringList &vars,
diff --git a/src/shared/proparser/prowriter.h b/src/shared/proparser/prowriter.h
index 808884837b..7d3dca765d 100644
--- a/src/shared/proparser/prowriter.h
+++ b/src/shared/proparser/prowriter.h
@@ -51,11 +51,12 @@ public:
static void putVarValues(ProFile *profile, QStringList *lines,
const QStringList &values, const QString &var, PutFlags flags,
- const QString &scope = QString());
+ const QString &scope, const QString &continuationIndent);
static QList<int> removeVarValues(ProFile *profile, QStringList *lines,
const QStringList &values, const QStringList &vars);
- static void addFiles(ProFile *profile, QStringList *lines, const QStringList &filePaths, const QString &var);
+ static void addFiles(ProFile *profile, QStringList *lines, const QStringList &filePaths,
+ const QString &var, const QString &continuationIndent);
static QStringList removeFiles(ProFile *profile, QStringList *lines,
const QDir &proFileDir, const QStringList &filePaths, const QStringList &vars);
diff --git a/tests/auto/profilewriter/tst_profilewriter.cpp b/tests/auto/profilewriter/tst_profilewriter.cpp
index b820d6fdcf..2abc7ccaa2 100644
--- a/tests/auto/profilewriter/tst_profilewriter.cpp
+++ b/tests/auto/profilewriter/tst_profilewriter.cpp
@@ -102,7 +102,7 @@ void tst_ProFileWriter::adds_data()
"add new append multi", f_foo, 0,
"",
"SOURCES += \\\n"
- " foo"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
@@ -111,7 +111,7 @@ void tst_ProFileWriter::adds_data()
"# test file\n"
"\n"
"SOURCES += \\\n"
- " foo"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
@@ -120,7 +120,7 @@ void tst_ProFileWriter::adds_data()
"\n"
"\n",
"SOURCES += \\\n"
- " foo\n"
+ "\tfoo\n"
"\n"
"\n"
"\n"
@@ -135,7 +135,7 @@ void tst_ProFileWriter::adds_data()
"# test file\n"
"\n"
"SOURCES += \\\n"
- " foo\n"
+ "\tfoo\n"
"\n"
"\n"
"\n"
@@ -147,7 +147,7 @@ void tst_ProFileWriter::adds_data()
"# test file\n"
"\n"
"SOURCES = \\\n"
- " foo"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::OneLine,
@@ -184,43 +184,43 @@ void tst_ProFileWriter::adds_data()
"unix:SOURCES = some files\n"
"\n"
"SOURCES += \\\n"
- " foo"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
"add new after some scope", f_foo, 0,
"unix {\n"
- " SOMEVAR = foo\n"
+ "\tSOMEVAR = foo\n"
"}",
"unix {\n"
- " SOMEVAR = foo\n"
+ "\tSOMEVAR = foo\n"
"}\n"
"\n"
"SOURCES += \\\n"
- " foo"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
"add to existing (wrong operator)", f_foo, 0,
"SOURCES = some files",
"SOURCES = some files \\\n"
- " foo"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
"insert at end", f_foo_bar, 0,
"SOURCES = some files",
"SOURCES = some files \\\n"
- " bar \\\n"
- " foo"
+ "\tbar \\\n"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
"insert into empty", f_foo_bar, 0,
"SOURCES =",
"SOURCES = \\\n"
- " bar \\\n"
- " foo"
+ "\tbar \\\n"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
@@ -239,33 +239,33 @@ void tst_ProFileWriter::adds_data()
"add to existing after comment (wrong operator)", f_foo, 0,
"SOURCES = some files # comment",
"SOURCES = some files \\ # comment\n"
- " foo"
+ "\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
"add to existing after comment line (wrong operator)", f_foo, 0,
"SOURCES = some \\\n"
" # comment\n"
- " files",
+ "\tfiles",
"SOURCES = some \\\n"
" # comment\n"
- " files \\\n"
- " foo"
+ "\tfiles \\\n"
+ "\tfoo"
},
{
PW::AppendValues|PW::AssignOperator|PW::MultiLine,
"add to existing", f_foo, 0,
"SOURCES = some files",
"SOURCES = some files \\\n"
- " foo"
+ "\tfoo"
},
{
PW::ReplaceValues|PW::AssignOperator|PW::MultiLine,
"replace existing multi", f_foo_bar, 0,
"SOURCES = some files",
"SOURCES = \\\n"
- " foo \\\n"
- " bar"
+ "\tfoo \\\n"
+ "\tbar"
},
{
PW::ReplaceValues|PW::AssignOperator|PW::OneLine,
@@ -278,7 +278,7 @@ void tst_ProFileWriter::adds_data()
"replace existing complex last", f_foo_bar, 0,
"SOURCES = some \\\n"
" # comment\n"
- " files",
+ "\tfiles",
"SOURCES = foo bar"
},
{
@@ -286,7 +286,7 @@ void tst_ProFileWriter::adds_data()
"replace existing complex middle 1", f_foo_bar, 0,
"SOURCES = some \\\n"
" # comment\n"
- " files\n"
+ "\tfiles\n"
"HEADERS = blubb",
"SOURCES = foo bar\n"
"HEADERS = blubb"
@@ -296,7 +296,7 @@ void tst_ProFileWriter::adds_data()
"replace existing complex middle 2", f_foo_bar, 0,
"SOURCES = some \\\n"
" # comment\n"
- " files\n"
+ "\tfiles\n"
"\n"
"HEADERS = blubb",
"SOURCES = foo bar\n"
@@ -308,7 +308,7 @@ void tst_ProFileWriter::adds_data()
"replace existing complex middle 3", f_foo_bar, 0,
"SOURCES = some \\\n"
" # comment\n"
- " files \\\n"
+ "\tfiles \\\n"
"\n"
"HEADERS = blubb",
"SOURCES = foo bar\n"
@@ -324,7 +324,7 @@ void tst_ProFileWriter::adds_data()
"SOURCES = yo\n"
"\n"
"dog {\n"
- " SOURCES += foo\n"
+ "\tSOURCES += foo\n"
"}"
},
{
@@ -332,13 +332,13 @@ void tst_ProFileWriter::adds_data()
"scoped new / extend scope", f_foo, "dog",
"# test file\n"
"dog {\n"
- " HEADERS += yo\n"
+ "\tHEADERS += yo\n"
"}",
"# test file\n"
"dog {\n"
- " HEADERS += yo\n"
+ "\tHEADERS += yo\n"
"\n"
- " SOURCES += foo\n"
+ "\tSOURCES += foo\n"
"}"
},
{
@@ -356,7 +356,7 @@ void tst_ProFileWriter::adds_data()
" yo \\\n"
" blubb\n"
"\n"
- " SOURCES += foo\n"
+ "\tSOURCES += foo\n"
"}"
},
{
@@ -367,7 +367,7 @@ void tst_ProFileWriter::adds_data()
"}",
"# test file\n"
"dog {\n"
- " SOURCES += foo\n"
+ "\tSOURCES += foo\n"
"}"
},
{
@@ -377,9 +377,9 @@ void tst_ProFileWriter::adds_data()
"dog:HEADERS += yo",
"# test file\n"
"dog {\n"
- " HEADERS += yo\n"
+ "\tHEADERS += yo\n"
"\n"
- " SOURCES += foo\n"
+ "\tSOURCES += foo\n"
"}"
},
{
@@ -392,10 +392,10 @@ void tst_ProFileWriter::adds_data()
"blubb()",
"# test file\n"
"dog {\n"
- " HEADERS += yo \\\n"
+ "\tHEADERS += yo \\\n"
" you\n"
"\n"
- " SOURCES += foo\n"
+ "\tSOURCES += foo\n"
"}\n"
"\n"
"blubb()"
@@ -413,8 +413,8 @@ void tst_ProFileWriter::adds_data()
" SOMEVAR = foo\n"
" }\n"
"\n"
- " SOURCES += \\\n"
- " foo\n"
+ "\tSOURCES += \\\n"
+ "\t\tfoo\n"
"}"
},
{
@@ -425,7 +425,7 @@ void tst_ProFileWriter::adds_data()
"}",
"# test file\n"
"dog: {\n"
- " SOURCES += foo\n"
+ "\tSOURCES += foo\n"
"}"
},
{
@@ -435,7 +435,7 @@ void tst_ProFileWriter::adds_data()
"dog:SOURCES = yo",
"# test file\n"
"dog:SOURCES = yo \\\n"
- " foo"
+ "\t\tfoo"
},
{
PW::AppendValues|PW::AppendOperator|PW::MultiLine,
@@ -446,8 +446,8 @@ void tst_ProFileWriter::adds_data()
"animal:!dog:SOURCES = yo\n"
"\n"
"dog {\n"
- " SOURCES += \\\n"
- " foo\n"
+ "\tSOURCES += \\\n"
+ "\t\tfoo\n"
"}"
},
};
@@ -478,7 +478,7 @@ void tst_ProFileWriter::adds()
QMakeParser parser(0, &vfs, &parseHandler);
ProFile *proFile = parser.parsedProBlock(QStringRef(&input), 0, QLatin1String(BASE_DIR "/test.pro"), 1);
QVERIFY(proFile);
- PW::putVarValues(proFile, &lines, values, var, PW::PutFlags(flags), scope);
+ PW::putVarValues(proFile, &lines, values, var, PW::PutFlags(flags), scope, "\t");
proFile->deref();
QCOMPARE(lines.join(QLatin1Char('\n')), output);
@@ -692,7 +692,7 @@ void tst_ProFileWriter::addFiles()
QStringList lines = input.split(QLatin1Char('\n'));
QString output = QLatin1String(
"SOURCES = foo.cpp \\\n"
- " sub/bar.cpp"
+ "\tsub/bar.cpp"
);
QMakeVfs vfs;
@@ -701,7 +701,7 @@ void tst_ProFileWriter::addFiles()
QVERIFY(proFile);
QmakeProjectManager::Internal::ProWriter::addFiles(proFile, &lines,
QStringList() << QString::fromLatin1(BASE_DIR "/sub/bar.cpp"),
- QLatin1String("SOURCES"));
+ QLatin1String("SOURCES"), "\t");
proFile->deref();
QCOMPARE(lines.join(QLatin1Char('\n')), output);