IDEA-58130 Improve editor performance during working with large files written in a single line

force soft wraps for document with very long lines (limit is configurable in registry)
This commit is contained in:
Dmitry Batrak
2014-12-22 14:18:17 +03:00
parent ab8676d59a
commit 5d738faa69
6 changed files with 99 additions and 1 deletions
@@ -130,6 +130,7 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
@NonNls public static final Object IGNORE_MOUSE_TRACKING = "ignore_mouse_tracking";
public static final Key<JComponent> PERMANENT_HEADER = Key.create("PERMANENT_HEADER");
public static final Key<Boolean> DO_DOCUMENT_UPDATE_TEST = Key.create("DoDocumentUpdateTest");
public static final Key<Boolean> FORCED_SOFT_WRAPS = Key.create("forced.soft.wraps");
private static final boolean HONOR_CAMEL_HUMPS_ON_TRIPLE_CLICK =
Boolean.parseBoolean(System.getProperty("idea.honor.camel.humps.on.triple.click"));
private static final Key<BufferedImage> BUFFER = Key.create("buffer");
@@ -323,6 +324,11 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
initTabPainter();
myIsViewer = viewer;
mySettings = new SettingsImpl(this, project);
boolean forceSoftWraps = !mySettings.isUseSoftWraps() && shouldSoftWrapsBeForced(myDocument);
if (forceSoftWraps) {
mySettings.setUseSoftWrapsQuiet();
putUserData(FORCED_SOFT_WRAPS, Boolean.TRUE);
}
mySelectionModel = new SelectionModelImpl(this);
myMarkupModel = new EditorMarkupModelImpl(this);
@@ -548,6 +554,16 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi
}
}
private static boolean shouldSoftWrapsBeForced(Document document) {
int lineWidthLimit = Registry.intValue("editor.soft.wrap.force.limit");
for (int i = 0; i < document.getLineCount(); i++) {
if (document.getLineEndOffset(i) - document.getLineStartOffset(i) > lineWidthLimit) {
return true;
}
}
return false;
}
@NotNull
static Color adjustThumbColor(@NotNull Color base, boolean dark) {
return dark ? ColorUtil.withAlpha(ColorUtil.shift(base, 1.35), 0.5)
@@ -0,0 +1,71 @@
/*
* Copyright 2000-2014 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.intellij.openapi.editor.impl;
import com.intellij.notification.NotificationDisplayType;
import com.intellij.notification.NotificationsConfiguration;
import com.intellij.notification.impl.NotificationsConfigurationImpl;
import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.editor.EditorBundle;
import com.intellij.openapi.fileEditor.FileEditor;
import com.intellij.openapi.fileEditor.TextEditor;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Key;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.ui.EditorNotificationPanel;
import com.intellij.ui.EditorNotifications;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
public class ForcedSoftWrapsNotificationProvider extends EditorNotifications.Provider<EditorNotificationPanel> {
private static final Key<EditorNotificationPanel> KEY = Key.create("forced.soft.wraps.notification.panel");
private static final String NOTIFICATION_SETTINGS_KEY = "Forced soft wraps in editor";
@NotNull
@Override
public Key<EditorNotificationPanel> getKey() {
return KEY;
}
@Nullable
@Override
public EditorNotificationPanel createNotificationPanel(@NotNull final VirtualFile file, @NotNull final FileEditor fileEditor) {
if (!(fileEditor instanceof TextEditor)) return null;
final Editor editor = ((TextEditor)fileEditor).getEditor();
final Project project = editor.getProject();
if (project == null
|| !Boolean.TRUE.equals(editor.getUserData(EditorImpl.FORCED_SOFT_WRAPS))
|| NotificationsConfigurationImpl.getSettings(NOTIFICATION_SETTINGS_KEY).getDisplayType() == NotificationDisplayType.NONE) return null;
final EditorNotificationPanel panel = new EditorNotificationPanel();
panel.setText(EditorBundle.message("forced.soft.wrap.message"));
panel.createActionLabel(EditorBundle.message("forced.soft.wrap.hide.message"), new Runnable() {
@Override
public void run() {
editor.putUserData(EditorImpl.FORCED_SOFT_WRAPS, null);
EditorNotifications.getInstance(project).updateNotifications(file);
}
});
panel.createActionLabel(EditorBundle.message("forced.soft.wrap.dont.show.again.message"), new Runnable() {
@Override
public void run() {
NotificationsConfiguration.getNotificationsConfiguration().changeSettings(NOTIFICATION_SETTINGS_KEY, NotificationDisplayType.NONE, false, false);
EditorNotifications.getInstance(project).updateAllNotifications();
}
});
return panel;
}
}
@@ -545,6 +545,10 @@ public class SettingsImpl implements EditorSettings {
myUseSoftWraps = newValue;
fireEditorRefresh();
}
public void setUseSoftWrapsQuiet() {
myUseSoftWraps = Boolean.TRUE;
}
@Override
public boolean isAllSoftWrapsShown() {
@@ -21,4 +21,7 @@ hector.inspections.slider.label=Inspections
action.duplicate.block=&Duplicate Block
action.duplicate.line=&Duplicate Line
increase.editor.font=Increase Font Size
decrease.editor.font=Decrease Font Size
decrease.editor.font=Decrease Font Size
forced.soft.wrap.message=This document contains very long line(s). Soft wraps were forcibly enabled to improve editor performance.
forced.soft.wrap.hide.message=Hide notification
forced.soft.wrap.dont.show.again.message=Don't show again
@@ -335,6 +335,7 @@
<httpRequestHandler implementation="com.intellij.platform.ProjectSetRequestHandler"/>
<postStartupActivity implementation="org.jetbrains.ide.BuiltInServerManagerImpl$MyPostStartupActivity"/>
<editorNotificationProvider implementation="com.intellij.openapi.editor.impl.ForcedSoftWrapsNotificationProvider"/>
<editorNotificationProvider implementation="com.intellij.ide.FileChangedNotificationProvider"/>
<editorNotificationProvider implementation="com.intellij.openapi.updateSettings.impl.pluginsAdvertisement.PluginAdvertiserEditorNotificationProvider"/>
@@ -138,6 +138,9 @@ editor.add.carets.on.double.control.arrows=true
editor.durable.folding.state=true
editor.durable.folding.state.description=If set, collapsed fold regions will preserve their state after a wider variety of document editing changes
editor.soft.wrap.force.limit=1000
editor.soft.wrap.force.limit.description=If document contains lines longer than this value, soft wraps will be forcibly enabled in editor due to performance reasons
ide.showIndexRebuildMessage=false
ide.tabbedPane.bufferedPaint=true