forked from qt-creator/qt-creator
LanguageClient: save document version for semantic tokens
Change-Id: Icd17e7f140cd172b2515711a3562c479f0ad488d Reviewed-by: Christian Kandeler <christian.kandeler@qt.io>
This commit is contained in:
@@ -192,8 +192,9 @@ void SemanticTokenSupport::reloadSemanticTokens(TextDocument *textDocument)
|
|||||||
return;
|
return;
|
||||||
const Utils::FilePath filePath = textDocument->filePath();
|
const Utils::FilePath filePath = textDocument->filePath();
|
||||||
const TextDocumentIdentifier docId(DocumentUri::fromFilePath(filePath));
|
const TextDocumentIdentifier docId(DocumentUri::fromFilePath(filePath));
|
||||||
auto responseCallback = [this, filePath](const SemanticTokensFullRequest::Response &response){
|
auto responseCallback = [this, filePath, documentVersion = m_client->documentVersion(filePath)](
|
||||||
handleSemanticTokens(filePath, response.result().value_or(nullptr));
|
const SemanticTokensFullRequest::Response &response) {
|
||||||
|
handleSemanticTokens(filePath, response.result().value_or(nullptr), documentVersion);
|
||||||
};
|
};
|
||||||
/*if (supportedRequests.testFlag(SemanticRequestType::Range)) {
|
/*if (supportedRequests.testFlag(SemanticRequestType::Range)) {
|
||||||
const int start = widget->firstVisibleBlockNumber();
|
const int start = widget->firstVisibleBlockNumber();
|
||||||
@@ -223,15 +224,18 @@ void SemanticTokenSupport::updateSemanticTokens(TextDocument *textDocument)
|
|||||||
const SemanticRequestTypes supportedRequests = supportedSemanticRequests(textDocument);
|
const SemanticRequestTypes supportedRequests = supportedSemanticRequests(textDocument);
|
||||||
if (supportedRequests.testFlag(SemanticRequestType::FullDelta)) {
|
if (supportedRequests.testFlag(SemanticRequestType::FullDelta)) {
|
||||||
const Utils::FilePath filePath = textDocument->filePath();
|
const Utils::FilePath filePath = textDocument->filePath();
|
||||||
const QString &previousResultId = m_tokens.value(filePath).resultId().value_or(QString());
|
const QString &previousResultId = m_tokens.value(filePath).tokens.resultId().value_or(QString());
|
||||||
if (!previousResultId.isEmpty()) {
|
if (!previousResultId.isEmpty()) {
|
||||||
SemanticTokensDeltaParams params;
|
SemanticTokensDeltaParams params;
|
||||||
params.setTextDocument(TextDocumentIdentifier(DocumentUri::fromFilePath(filePath)));
|
params.setTextDocument(TextDocumentIdentifier(DocumentUri::fromFilePath(filePath)));
|
||||||
params.setPreviousResultId(previousResultId);
|
params.setPreviousResultId(previousResultId);
|
||||||
SemanticTokensFullDeltaRequest request(params);
|
SemanticTokensFullDeltaRequest request(params);
|
||||||
request.setResponseCallback(
|
request.setResponseCallback(
|
||||||
[this, filePath](const SemanticTokensFullDeltaRequest::Response &response) {
|
[this, filePath, documentVersion = m_client->documentVersion(filePath)](
|
||||||
handleSemanticTokensDelta(filePath, response.result().value_or(nullptr));
|
const SemanticTokensFullDeltaRequest::Response &response) {
|
||||||
|
handleSemanticTokensDelta(filePath,
|
||||||
|
response.result().value_or(nullptr),
|
||||||
|
documentVersion);
|
||||||
});
|
});
|
||||||
m_client->sendContent(request);
|
m_client->sendContent(request);
|
||||||
return;
|
return;
|
||||||
@@ -369,10 +373,11 @@ SemanticRequestTypes SemanticTokenSupport::supportedSemanticRequests(TextDocumen
|
|||||||
}
|
}
|
||||||
|
|
||||||
void SemanticTokenSupport::handleSemanticTokens(const Utils::FilePath &filePath,
|
void SemanticTokenSupport::handleSemanticTokens(const Utils::FilePath &filePath,
|
||||||
const SemanticTokensResult &result)
|
const SemanticTokensResult &result,
|
||||||
|
int documentVersion)
|
||||||
{
|
{
|
||||||
if (auto tokens = Utils::get_if<SemanticTokens>(&result)) {
|
if (auto tokens = Utils::get_if<SemanticTokens>(&result)) {
|
||||||
m_tokens[filePath] = *tokens;
|
m_tokens[filePath] = {*tokens, documentVersion};
|
||||||
highlight(filePath);
|
highlight(filePath);
|
||||||
} else {
|
} else {
|
||||||
m_tokens.remove(filePath);
|
m_tokens.remove(filePath);
|
||||||
@@ -380,10 +385,12 @@ void SemanticTokenSupport::handleSemanticTokens(const Utils::FilePath &filePath,
|
|||||||
}
|
}
|
||||||
|
|
||||||
void SemanticTokenSupport::handleSemanticTokensDelta(
|
void SemanticTokenSupport::handleSemanticTokensDelta(
|
||||||
const Utils::FilePath &filePath, const LanguageServerProtocol::SemanticTokensDeltaResult &result)
|
const Utils::FilePath &filePath,
|
||||||
|
const LanguageServerProtocol::SemanticTokensDeltaResult &result,
|
||||||
|
int documentVersion)
|
||||||
{
|
{
|
||||||
if (auto tokens = Utils::get_if<SemanticTokens>(&result)) {
|
if (auto tokens = Utils::get_if<SemanticTokens>(&result)) {
|
||||||
m_tokens[filePath] = *tokens;
|
m_tokens[filePath] = {*tokens, documentVersion};
|
||||||
} else if (auto tokensDelta = Utils::get_if<SemanticTokensDelta>(&result)) {
|
} else if (auto tokensDelta = Utils::get_if<SemanticTokensDelta>(&result)) {
|
||||||
QList<SemanticTokensEdit> edits = tokensDelta->edits();
|
QList<SemanticTokensEdit> edits = tokensDelta->edits();
|
||||||
if (edits.isEmpty()) {
|
if (edits.isEmpty()) {
|
||||||
@@ -393,7 +400,8 @@ void SemanticTokenSupport::handleSemanticTokensDelta(
|
|||||||
|
|
||||||
Utils::sort(edits, &SemanticTokensEdit::start);
|
Utils::sort(edits, &SemanticTokensEdit::start);
|
||||||
|
|
||||||
SemanticTokens &tokens = m_tokens[filePath];
|
m_tokens[filePath].version = documentVersion;
|
||||||
|
SemanticTokens &tokens = m_tokens[filePath].tokens;
|
||||||
const QList<int> &data = tokens.data();
|
const QList<int> &data = tokens.data();
|
||||||
|
|
||||||
int newDataSize = data.size();
|
int newDataSize = data.size();
|
||||||
@@ -443,7 +451,7 @@ void SemanticTokenSupport::highlight(const Utils::FilePath &filePath)
|
|||||||
SyntaxHighlighter *highlighter = doc->syntaxHighlighter();
|
SyntaxHighlighter *highlighter = doc->syntaxHighlighter();
|
||||||
if (!highlighter)
|
if (!highlighter)
|
||||||
return;
|
return;
|
||||||
const QList<SemanticToken> tokens = m_tokens.value(filePath).toTokens(m_tokenTypes,
|
const QList<SemanticToken> tokens = m_tokens.value(filePath).tokens.toTokens(m_tokenTypes,
|
||||||
m_tokenModifiers);
|
m_tokenModifiers);
|
||||||
if (m_tokensHandler) {
|
if (m_tokensHandler) {
|
||||||
int line = 1;
|
int line = 1;
|
||||||
|
@@ -86,16 +86,23 @@ private:
|
|||||||
LanguageServerProtocol::SemanticRequestTypes supportedSemanticRequests(
|
LanguageServerProtocol::SemanticRequestTypes supportedSemanticRequests(
|
||||||
TextEditor::TextDocument *document) const;
|
TextEditor::TextDocument *document) const;
|
||||||
void handleSemanticTokens(const Utils::FilePath &filePath,
|
void handleSemanticTokens(const Utils::FilePath &filePath,
|
||||||
const LanguageServerProtocol::SemanticTokensResult &result);
|
const LanguageServerProtocol::SemanticTokensResult &result,
|
||||||
|
int documentVersion);
|
||||||
void handleSemanticTokensDelta(const Utils::FilePath &filePath,
|
void handleSemanticTokensDelta(const Utils::FilePath &filePath,
|
||||||
const LanguageServerProtocol::SemanticTokensDeltaResult &result);
|
const LanguageServerProtocol::SemanticTokensDeltaResult &result,
|
||||||
|
int documentVersion);
|
||||||
void highlight(const Utils::FilePath &filePath);
|
void highlight(const Utils::FilePath &filePath);
|
||||||
void updateFormatHash();
|
void updateFormatHash();
|
||||||
void currentEditorChanged();
|
void currentEditorChanged();
|
||||||
|
|
||||||
Client *m_client = nullptr;
|
Client *m_client = nullptr;
|
||||||
|
|
||||||
QHash<Utils::FilePath, LanguageServerProtocol::SemanticTokens> m_tokens;
|
struct VersionedTokens
|
||||||
|
{
|
||||||
|
LanguageServerProtocol::SemanticTokens tokens;
|
||||||
|
int version;
|
||||||
|
};
|
||||||
|
QHash<Utils::FilePath, VersionedTokens> m_tokens;
|
||||||
QList<int> m_tokenTypes;
|
QList<int> m_tokenTypes;
|
||||||
QList<int> m_tokenModifiers;
|
QList<int> m_tokenModifiers;
|
||||||
QHash<int, QTextCharFormat> m_formatHash;
|
QHash<int, QTextCharFormat> m_formatHash;
|
||||||
|
Reference in New Issue
Block a user