don't recalculate gutter size on brace highlighting

This commit is contained in:
Dmitry Batrak
2018-09-26 11:38:38 +03:00
parent 9a2b142e88
commit d4943531a8
3 changed files with 68 additions and 64 deletions
@@ -20,7 +20,6 @@ import com.intellij.openapi.editor.colors.EditorColorsManager;
import com.intellij.openapi.editor.colors.EditorColorsScheme;
import com.intellij.openapi.editor.ex.DocumentEx;
import com.intellij.openapi.editor.ex.EditorEx;
import com.intellij.openapi.editor.ex.MarkupModelEx;
import com.intellij.openapi.editor.ex.util.HighlighterIteratorWrapper;
import com.intellij.openapi.editor.ex.util.LexerEditorHighlighter;
import com.intellij.openapi.editor.highlighter.EditorHighlighter;
@@ -71,19 +70,19 @@ public class BraceHighlightingHandler {
private static final Set<Editor> PROCESSED_EDITORS = ContainerUtil.createWeakSet();
@NotNull private final Project myProject;
@NotNull private final Editor myEditor;
@NotNull private final EditorEx myEditor;
private final Alarm myAlarm;
private final DocumentEx myDocument;
private final PsiFile myPsiFile;
private final CodeInsightSettings myCodeInsightSettings;
private BraceHighlightingHandler(@NotNull Project project, @NotNull Editor editor, @NotNull Alarm alarm, PsiFile psiFile) {
private BraceHighlightingHandler(@NotNull Project project, @NotNull EditorEx editor, @NotNull Alarm alarm, PsiFile psiFile) {
myProject = project;
myEditor = editor;
myAlarm = alarm;
myDocument = (DocumentEx)myEditor.getDocument();
myDocument = myEditor.getDocument();
myPsiFile = psiFile;
myCodeInsightSettings = CodeInsightSettings.getInstance();
@@ -123,7 +122,7 @@ public class BraceHighlightingHandler {
ApplicationManager.getApplication().invokeLater((DumbAwareRunnable)() -> {
try {
if (isValidEditor(editor) && isValidFile(injected)) {
Editor newEditor = InjectedLanguageUtil.getInjectedEditorForInjectedFile(editor, injected);
EditorEx newEditor = (EditorEx)InjectedLanguageUtil.getInjectedEditorForInjectedFile(editor, injected);
BraceHighlightingHandler handler = new BraceHighlightingHandler(project, newEditor, alarm, injected);
processor.process(handler);
}
@@ -535,15 +534,16 @@ public class BraceHighlightingHandler {
LineMarkerRenderer renderer = createLineMarkerRenderer(matched);
if (renderer == null) return;
RangeHighlighter highlighter = myEditor.getMarkupModel().addRangeHighlighter(startOffset, endOffset, 0, null, HighlighterTargetArea.LINES_IN_RANGE);
highlighter.setLineMarkerRenderer(renderer);
RangeHighlighter highlighter = myEditor.getMarkupModel()
.addRangeHighlighterAndChangeAttributes(startOffset, endOffset, 0, null, HighlighterTargetArea.LINES_IN_RANGE, false,
h -> h.setLineMarkerRenderer(renderer));
myEditor.putUserData(LINE_MARKER_IN_EDITOR_KEY, highlighter);
}
private void removeLineMarkers() {
ApplicationManager.getApplication().assertIsDispatchThread();
RangeHighlighter marker = myEditor.getUserData(LINE_MARKER_IN_EDITOR_KEY);
if (marker != null && ((MarkupModelEx)myEditor.getMarkupModel()).containsHighlighter(marker)) {
if (marker != null && myEditor.getMarkupModel().containsHighlighter(marker)) {
marker.dispose();
}
myEditor.putUserData(LINE_MARKER_IN_EDITOR_KEY, null);
@@ -140,8 +140,8 @@ class EditorGutterComponentImpl extends EditorGutterComponentEx implements Mouse
private boolean myPaintBackground = true;
private boolean myLeftFreePaintersAreaShown;
private boolean myRightFreePaintersAreaShown;
private boolean myForceLeftFreePaintersAreaShown;
private boolean myForceRightFreePaintersAreaShown;
boolean myForceLeftFreePaintersAreaShown;
boolean myForceRightFreePaintersAreaShown;
private int myLastNonDumbModeIconAreaWidth;
boolean myDnDInProgress;
@@ -1962,7 +1962,7 @@ class EditorGutterComponentImpl extends EditorGutterComponentEx implements Mouse
}
@NotNull
private static LineMarkerRendererEx.Position getLineMarkerPosition(@NotNull LineMarkerRenderer renderer) {
static LineMarkerRendererEx.Position getLineMarkerPosition(@NotNull LineMarkerRenderer renderer) {
if (renderer instanceof LineMarkerRendererEx) {
return ((LineMarkerRendererEx)renderer).getPosition();
}
@@ -36,10 +36,7 @@ import com.intellij.openapi.editor.highlighter.EditorHighlighter;
import com.intellij.openapi.editor.highlighter.HighlighterClient;
import com.intellij.openapi.editor.impl.event.MarkupModelListener;
import com.intellij.openapi.editor.impl.view.EditorView;
import com.intellij.openapi.editor.markup.GutterDraggableObject;
import com.intellij.openapi.editor.markup.GutterIconRenderer;
import com.intellij.openapi.editor.markup.RangeHighlighter;
import com.intellij.openapi.editor.markup.TextAttributes;
import com.intellij.openapi.editor.markup.*;
import com.intellij.openapi.fileEditor.FileDocumentManager;
import com.intellij.openapi.fileEditor.ex.IdeDocumentHistory;
import com.intellij.openapi.fileEditor.impl.EditorsSplitters;
@@ -377,65 +374,21 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
}
myMarkupModelListener = new MarkupModelListener() {
private boolean areRenderersInvolved(@NotNull RangeHighlighterEx highlighter) {
return highlighter.getCustomRenderer() != null ||
highlighter.getGutterIconRenderer() != null ||
highlighter.getLineMarkerRenderer() != null ||
highlighter.getLineSeparatorRenderer() != null;
}
@Override
public void afterAdded(@NotNull RangeHighlighterEx highlighter) {
attributesChanged(highlighter, areRenderersInvolved(highlighter),
EditorUtil.attributesImpactFontStyleOrColor(highlighter.getTextAttributes()));
onHighlighterChanged(highlighter, canImpactGutterSize(highlighter),
EditorUtil.attributesImpactFontStyleOrColor(highlighter.getTextAttributes()));
}
@Override
public void beforeRemoved(@NotNull RangeHighlighterEx highlighter) {
attributesChanged(highlighter, areRenderersInvolved(highlighter),
EditorUtil.attributesImpactFontStyleOrColor(highlighter.getTextAttributes()));
onHighlighterChanged(highlighter, canImpactGutterSize(highlighter),
EditorUtil.attributesImpactFontStyleOrColor(highlighter.getTextAttributes()));
}
@Override
public void attributesChanged(@NotNull RangeHighlighterEx highlighter, boolean renderersChanged, boolean fontStyleOrColorChanged) {
if (myDocument.isInBulkUpdate()) return; // bulkUpdateFinished() will repaint anything
if (renderersChanged) {
updateGutterSize();
}
boolean errorStripeNeedsRepaint = renderersChanged || highlighter.getErrorStripeMarkColor() != null;
if (myDocumentChangeInProgress) {
// postpone repaint request, as folding model can be in inconsistent state and so coordinate
// conversions might give incorrect results
myErrorStripeNeedsRepaint |= errorStripeNeedsRepaint;
return;
}
int textLength = myDocument.getTextLength();
int start = Math.min(Math.max(highlighter.getAffectedAreaStartOffset(), 0), textLength);
int end = Math.min(Math.max(highlighter.getAffectedAreaEndOffset(), 0), textLength);
int startLine = start == -1 ? 0 : myDocument.getLineNumber(start);
int endLine = end == -1 ? myDocument.getLineCount() : myDocument.getLineNumber(end);
if (start != end && fontStyleOrColorChanged) {
myView.invalidateRange(start, end);
}
if (!myFoldingModel.isInBatchFoldingOperation()) { // at the end of batch folding operation everything is repainted
repaintLines(Math.max(0, startLine - 1), Math.min(endLine + 1, getDocument().getLineCount()));
}
// optimization: there is no need to repaint error stripe if the highlighter is invisible on it
if (errorStripeNeedsRepaint) {
if (myFoldingModel.isInBatchFoldingOperation()) {
myErrorStripeNeedsRepaint = true;
}
else {
myMarkupModel.repaint(start, end);
}
}
updateCaretCursor();
onHighlighterChanged(highlighter, renderersChanged, fontStyleOrColorChanged);
}
};
@@ -589,6 +542,57 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
CodeStyleSettingsManager.getInstance(myProject).addListener(this);
}
private boolean canImpactGutterSize(@NotNull RangeHighlighterEx highlighter) {
if (highlighter.getGutterIconRenderer() != null) return true;
LineMarkerRenderer lineMarkerRenderer = highlighter.getLineMarkerRenderer();
if (lineMarkerRenderer == null) return false;
LineMarkerRendererEx.Position position = EditorGutterComponentImpl.getLineMarkerPosition(lineMarkerRenderer);
return position == LineMarkerRendererEx.Position.LEFT && !myGutterComponent.myForceLeftFreePaintersAreaShown ||
position == LineMarkerRendererEx.Position.RIGHT && !myGutterComponent.myForceRightFreePaintersAreaShown;
}
private void onHighlighterChanged(@NotNull RangeHighlighterEx highlighter, boolean canImpactGutterSize, boolean fontStyleOrColorChanged) {
if (myDocument.isInBulkUpdate()) return; // bulkUpdateFinished() will repaint anything
if (canImpactGutterSize) {
updateGutterSize();
}
boolean errorStripeNeedsRepaint = highlighter.getErrorStripeMarkColor() != null;
if (myDocumentChangeInProgress) {
// postpone repaint request, as folding model can be in inconsistent state and so coordinate
// conversions might give incorrect results
myErrorStripeNeedsRepaint |= errorStripeNeedsRepaint;
return;
}
int textLength = myDocument.getTextLength();
int start = Math.min(Math.max(highlighter.getAffectedAreaStartOffset(), 0), textLength);
int end = Math.min(Math.max(highlighter.getAffectedAreaEndOffset(), 0), textLength);
int startLine = start == -1 ? 0 : myDocument.getLineNumber(start);
int endLine = end == -1 ? myDocument.getLineCount() : myDocument.getLineNumber(end);
if (start != end && fontStyleOrColorChanged) {
myView.invalidateRange(start, end);
}
if (!myFoldingModel.isInBatchFoldingOperation()) { // at the end of batch folding operation everything is repainted
repaintLines(Math.max(0, startLine - 1), Math.min(endLine + 1, getDocument().getLineCount()));
}
// optimization: there is no need to repaint error stripe if the highlighter is invisible on it
if (errorStripeNeedsRepaint) {
if (myFoldingModel.isInBatchFoldingOperation()) {
myErrorStripeNeedsRepaint = true;
}
else {
myMarkupModel.repaint(start, end);
}
}
updateCaretCursor();
}
private void onInlayUpdated(@NotNull Inlay inlay) {
if (myDocument.isInEventsHandling() || myDocument.isInBulkUpdate()) return;
validateSize();