aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/qmldom/qqmldomindentinglinewriter.cpp171
-rw-r--r--src/qmldom/qqmldomindentinglinewriter_p.h3
-rw-r--r--src/qmldom/qqmldomlinewriter_p.h2
3 files changed, 92 insertions, 84 deletions
diff --git a/src/qmldom/qqmldomindentinglinewriter.cpp b/src/qmldom/qqmldomindentinglinewriter.cpp
index 99f81c1717..65dcdfade8 100644
--- a/src/qmldom/qqmldomindentinglinewriter.cpp
+++ b/src/qmldom/qqmldomindentinglinewriter.cpp
@@ -2,6 +2,7 @@
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
#include "qqmldomindentinglinewriter_p.h"
+#include "qqmldomlinewriter_p.h"
#include <QtCore/QCoreApplication>
#include <QtCore/QRegularExpression>
@@ -10,6 +11,9 @@ QT_BEGIN_NAMESPACE
namespace QQmlJS {
namespace Dom {
+static QSet<int> splitSequence = { QQmlJSGrammar::T_COMMA, QQmlJSGrammar::T_AND_AND,
+ QQmlJSGrammar::T_OR_OR, QQmlJSGrammar::T_LPAREN };
+
FormatPartialStatus &IndentingLineWriter::fStatus()
{
if (!m_fStatusValid) {
@@ -26,99 +30,100 @@ void IndentingLineWriter::willCommit()
void IndentingLineWriter::reindentAndSplit(const QString &eol, bool eof)
{
- bool shouldReindent = m_reindent;
-indentAgain:
// maybe re-indent
- if (shouldReindent && m_columnNr == 0) {
+ if (m_reindent && m_columnNr == 0)
setLineIndent(fStatus().indentLine());
- }
- if (!eol.isEmpty() || eof) {
- LineWriterOptions::TrailingSpace trailingSpace;
- if (!m_currentLine.isEmpty() && m_currentLine.trimmed().isEmpty()) {
- // space only line
- const Scanner::State &oldState = m_preCachedStatus.lexerState;
- if (oldState.isMultilineComment())
- trailingSpace = m_options.commentTrailingSpace;
- else if (oldState.isMultiline())
- trailingSpace = m_options.stringTrailingSpace;
- else
- trailingSpace = m_options.codeTrailingSpace;
- // in the LSP we will probably want to treat is specially if it is the line with the
- // cursor, of if indentation of it is requested
+
+ if (!eol.isEmpty() || eof)
+ handleTrailingSpace();
+
+ // maybe split long line
+ if (m_options.maxLineLength > 0 && m_currentLine.size() > m_options.maxLineLength)
+ splitOnMaxLength(eol, eof);
+
+ // maybe write out
+ if (!eol.isEmpty() || eof)
+ commitLine(eol);
+}
+
+void IndentingLineWriter::handleTrailingSpace()
+{
+ LineWriterOptions::TrailingSpace trailingSpace;
+ if (!m_currentLine.isEmpty() && m_currentLine.trimmed().isEmpty()) {
+ // space only line
+ const Scanner::State &oldState = m_preCachedStatus.lexerState;
+ if (oldState.isMultilineComment())
+ trailingSpace = m_options.commentTrailingSpace;
+ else if (oldState.isMultiline())
+ trailingSpace = m_options.stringTrailingSpace;
+ else
+ trailingSpace = m_options.codeTrailingSpace;
+ // in the LSP we will probably want to treat is specially if it is the line with the
+ // cursor, of if indentation of it is requested
+ } else {
+ const Scanner::State &currentState = fStatus().currentStatus.lexerState;
+ if (currentState.isMultilineComment()) {
+ trailingSpace = m_options.commentTrailingSpace;
+ } else if (currentState.isMultiline()) {
+ trailingSpace = m_options.stringTrailingSpace;
} else {
- const Scanner::State &currentState = fStatus().currentStatus.lexerState;
- if (currentState.isMultilineComment()) {
+ const int kind =
+ (fStatus().lineTokens.isEmpty() ? Lexer::T_EOL
+ : fStatus().lineTokens.last().lexKind);
+ if (Token::lexKindIsComment(kind)) {
+ // a // comment...
trailingSpace = m_options.commentTrailingSpace;
- } else if (currentState.isMultiline()) {
- trailingSpace = m_options.stringTrailingSpace;
+ Q_ASSERT(fStatus().currentStatus.state().type
+ != FormatTextStatus::StateType::MultilineCommentCont
+ && fStatus().currentStatus.state().type
+ != FormatTextStatus::StateType::
+ MultilineCommentStart); // these should have been
+ // handled above
} else {
- const int kind =
- (fStatus().lineTokens.isEmpty() ? Lexer::T_EOL
- : fStatus().lineTokens.last().lexKind);
- if (Token::lexKindIsComment(kind)) {
- // a // comment...
- trailingSpace = m_options.commentTrailingSpace;
- Q_ASSERT(fStatus().currentStatus.state().type
- != FormatTextStatus::StateType::MultilineCommentCont
- && fStatus().currentStatus.state().type
- != FormatTextStatus::StateType::
- MultilineCommentStart); // these should have been
- // handled above
- } else {
- trailingSpace = m_options.codeTrailingSpace;
- }
+ trailingSpace = m_options.codeTrailingSpace;
}
}
- handleTrailingSpace(trailingSpace);
}
- // maybe split long line
- if (m_options.maxLineLength > 0 && m_currentLine.size() > m_options.maxLineLength) {
- int possibleSplit = -1;
- if (fStatus().lineTokens.size() > 1) {
- // {}[] should already be handled (handle also here?)
- int minLen = 0;
- while (minLen < m_currentLine.size() && m_currentLine.at(minLen).isSpace())
- ++minLen;
- minLen = column(minLen) + m_options.minContentLength;
- int maxLen = qMax(minLen + m_options.strongMaxLineExtra, m_options.maxLineLength);
- std::array<QSet<int>, 2> splitSequence(
- { QSet<int>({ // try split after ',','||','&&'
- QQmlJSGrammar::T_COMMA, QQmlJSGrammar::T_AND_AND,
- QQmlJSGrammar::T_OR_OR }),
- QSet<int>({ // try split after '('
- QQmlJSGrammar::T_LPAREN }) });
- // try split after other binary operators?
- int minSplit = m_currentLine.size();
- for (const QSet<int> &splitOnToken : splitSequence) {
- for (int iToken = 0; iToken < fStatus().tokenCount(); ++iToken) {
- const Token t = fStatus().tokenAt(iToken);
- int tCol = column(t.end());
- if (splitOnToken.contains(t.lexKind) && tCol > minLen) {
- if (tCol <= maxLen && possibleSplit < t.end())
- possibleSplit = t.end();
- if (t.end() < minSplit)
- minSplit = t.end();
- }
- }
- if (possibleSplit > 0)
- break;
- }
- if (possibleSplit == -1 && minSplit + 4 < m_currentLine.size())
- possibleSplit = minSplit;
- if (possibleSplit > 0) {
- lineChanged();
- quint32 oChange = eolToWrite().size();
- changeAtOffset(m_utf16Offset + possibleSplit, oChange, 0,
- 0); // line & col change updated in commitLine
- commitLine(eolToWrite(), TextAddType::NewlineSplit, possibleSplit);
- shouldReindent = true;
- goto indentAgain;
- }
+ LineWriter::handleTrailingSpace(trailingSpace);
+}
+
+void IndentingLineWriter::splitOnMaxLength(const QString &eol, bool eof)
+{
+ int possibleSplit = -1;
+ if (fStatus().lineTokens.size() <= 1)
+ return;
+ // {}[] should already be handled (handle also here?)
+ int minLen = 0;
+ while (minLen < m_currentLine.size() && m_currentLine.at(minLen).isSpace())
+ ++minLen;
+ minLen = column(minLen) + m_options.minContentLength;
+ int maxLen = qMax(minLen + m_options.strongMaxLineExtra, m_options.maxLineLength);
+
+ // try split after other binary operators?
+ int minSplit = m_currentLine.size();
+
+ for (int iToken = 0; iToken < fStatus().tokenCount(); ++iToken) {
+ const Token t = fStatus().tokenAt(iToken);
+ int tCol = column(t.end());
+ if (splitSequence.contains(t.lexKind) && tCol > minLen) {
+ if (tCol <= maxLen && possibleSplit < t.end())
+ possibleSplit = t.end();
+ if (t.end() < minSplit)
+ minSplit = t.end();
}
}
- // maybe write out
- if (!eol.isEmpty() || eof)
- commitLine(eol);
+
+ if (possibleSplit == -1 && minSplit + 4 < m_currentLine.size())
+ possibleSplit = minSplit;
+ if (possibleSplit > 0) {
+ lineChanged();
+ quint32 oChange = eolToWrite().size();
+ changeAtOffset(m_utf16Offset + possibleSplit, oChange, 0,
+ 0); // line & col change updated in commitLine
+ commitLine(eolToWrite(), TextAddType::NewlineSplit, possibleSplit);
+ setReindent(true);
+ reindentAndSplit(eol, eof);
+ }
}
} // namespace Dom
diff --git a/src/qmldom/qqmldomindentinglinewriter_p.h b/src/qmldom/qqmldomindentinglinewriter_p.h
index 63ec3fc432..21197e277a 100644
--- a/src/qmldom/qqmldomindentinglinewriter_p.h
+++ b/src/qmldom/qqmldomindentinglinewriter_p.h
@@ -41,6 +41,7 @@ public:
{
}
void reindentAndSplit(const QString &eol, bool eof = false) override;
+ void handleTrailingSpace();
FormatPartialStatus &fStatus();
void lineChanged() override { m_fStatusValid = false; }
@@ -48,6 +49,8 @@ public:
bool reindent() const { return m_reindent; }
void setReindent(bool v) { m_reindent = v; }
+ void splitOnMaxLength(const QString &eol, bool eof);
+
private:
Q_DISABLE_COPY_MOVE(IndentingLineWriter)
protected:
diff --git a/src/qmldom/qqmldomlinewriter_p.h b/src/qmldom/qqmldomlinewriter_p.h
index 0046e3e31a..05fa3a4399 100644
--- a/src/qmldom/qqmldomlinewriter_p.h
+++ b/src/qmldom/qqmldomlinewriter_p.h
@@ -82,7 +82,7 @@ public:
enum class AttributesSequence { Normalize, Preserve };
Q_ENUM(AttributesSequence)
- int maxLineLength = -1;
+ int maxLineLength = -1; // -1 means no limit
int strongMaxLineExtra = 20;
int minContentLength = 10;
#if defined (Q_OS_WIN)