From d53e78a2605b19b4c8fbbb28e710146303821b0d Mon Sep 17 00:00:00 2001 From: nik Date: Tue, 15 Feb 2011 15:16:03 +0300 Subject: [PATCH 01/13] collect statistics about custom libraries --- .../libraries/impl/LibraryUsageCollector.java | 70 +++++++++++++++++++ resources/src/META-INF/IdeaPlugin.xml | 2 + 2 files changed, 72 insertions(+) create mode 100644 java/idea-ui/src/com/intellij/openapi/roots/ui/configuration/libraries/impl/LibraryUsageCollector.java diff --git a/java/idea-ui/src/com/intellij/openapi/roots/ui/configuration/libraries/impl/LibraryUsageCollector.java b/java/idea-ui/src/com/intellij/openapi/roots/ui/configuration/libraries/impl/LibraryUsageCollector.java new file mode 100644 index 000000000000..fdff8b12dd91 --- /dev/null +++ b/java/idea-ui/src/com/intellij/openapi/roots/ui/configuration/libraries/impl/LibraryUsageCollector.java @@ -0,0 +1,70 @@ +/* + * Copyright 2000-2011 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.roots.ui.configuration.libraries.impl; + +import com.intellij.internal.statistic.UsagesCollector; +import com.intellij.internal.statistic.beans.GroupDescriptor; +import com.intellij.internal.statistic.beans.UsageDescriptor; +import com.intellij.openapi.module.Module; +import com.intellij.openapi.module.ModuleManager; +import com.intellij.openapi.project.Project; +import com.intellij.openapi.roots.ModuleRootManager; +import com.intellij.openapi.roots.libraries.Library; +import com.intellij.openapi.roots.libraries.LibraryKind; +import com.intellij.util.Processor; +import org.jetbrains.annotations.NonNls; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import java.util.*; + +/** + * @author nik + */ +public class LibraryUsageCollector extends UsagesCollector { + @NonNls private static final String GROUP_ID = "libraries"; + + @NotNull + @Override + public Set getUsages(@Nullable Project project) { + if (project == null) return Collections.emptySet(); + + final Set> usedKinds = new HashSet>(); + final Processor processor = new Processor() { + @Override + public boolean process(Library library) { + usedKinds.addAll(LibraryPresentationManagerImpl.getLibraryKinds(library, null)); + return true; + } + }; + for (Module module : ModuleManager.getInstance(project).getModules()) { + ModuleRootManager.getInstance(module).orderEntries().librariesOnly().forEachLibrary(processor); + } + + final HashSet usageDescriptors = new HashSet(); + for (LibraryKind kind : usedKinds) { + final GroupDescriptor group = GroupDescriptor.create(GROUP_ID); + usageDescriptors.add(new UsageDescriptor(group, kind.getKindId(), 1)); + } + return usageDescriptors; + } + + @NotNull + @Override + public String getGroupId() { + return GROUP_ID; + } +} diff --git a/resources/src/META-INF/IdeaPlugin.xml b/resources/src/META-INF/IdeaPlugin.xml index ee8f6311b4bc..868c3ae07341 100644 --- a/resources/src/META-INF/IdeaPlugin.xml +++ b/resources/src/META-INF/IdeaPlugin.xml @@ -868,6 +868,8 @@ implementationClass="com.intellij.openapi.roots.ui.configuration.libraryEditor.SourcesOrderRootTypeUIFactory"/> + + From 6248a6265cb0decf240463ca839e9c6fb69e4b57 Mon Sep 17 00:00:00 2001 From: andrey zaytsev Date: Tue, 15 Feb 2011 15:43:28 +0300 Subject: [PATCH 02/13] find action in console fixed --- .../intellij/find/EditorSearchComponent.java | 22 ++++-- .../com/intellij/find/impl/LivePreview.java | 75 ++++++++----------- .../find/impl/LivePreviewController.java | 39 ++++++++++ .../find/impl/LivePreviewControllerBase.java | 6 ++ 4 files changed, 92 insertions(+), 50 deletions(-) diff --git a/platform/lang-impl/src/com/intellij/find/EditorSearchComponent.java b/platform/lang-impl/src/com/intellij/find/EditorSearchComponent.java index d6c3c215ef7b..18a2526b381d 100644 --- a/platform/lang-impl/src/com/intellij/find/EditorSearchComponent.java +++ b/platform/lang-impl/src/com/intellij/find/EditorSearchComponent.java @@ -41,6 +41,7 @@ import com.intellij.openapi.ui.popup.JBPopup; import com.intellij.openapi.ui.popup.JBPopupFactory; import com.intellij.openapi.ui.popup.PopupChooserBuilder; import com.intellij.openapi.util.IconLoader; +import com.intellij.openapi.util.Ref; import com.intellij.openapi.util.SystemInfo; import com.intellij.openapi.util.TextRange; import com.intellij.openapi.util.text.StringUtil; @@ -104,6 +105,12 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP mySearchField.requestFocus(); } + @Override + public Editor getEditor(Ref needToUpdate) { + needToUpdate.set(true); + return myEditor; + } + public void notFound() { setNotFoundBackground(); } @@ -136,12 +143,17 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP myIsReplace = isReplace; + GRADIENT_C1 = getBackground(); GRADIENT_C2 = new Color(Math.max(0, GRADIENT_C1.getRed() - 0x18), Math.max(0, GRADIENT_C1.getGreen() - 0x18), Math.max(0, GRADIENT_C1.getBlue() - 0x18)); - + myProject = project; myEditor = editor; + myLivePreview = new LivePreview(myEditor.getProject()); + myLivePreview.addCursorListener(this); + myLivePreview.setDelegate(myLivePreviewController); + JPanel leadPanel = createLeadPane(); add(leadPanel, BorderLayout.WEST); @@ -306,9 +318,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP new VariantsCompletionAction(); // It registers a shortcut set automatically on construction - myLivePreview = new LivePreview(myEditor.getProject()); - myLivePreview.addCursorListener(this); - myLivePreview.setDelegate(myLivePreviewController); + } private void configureReplacementPane() { @@ -551,7 +561,9 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP setRegularBackground(); myMatchInfoLabel.setText(""); myClickToHighlightLabel.setVisible(false); - myLivePreview.cleanUp(); + if (myLivePreview != null) { + myLivePreview.cleanUp(); + } } else { final FindModel model = new FindModel(); diff --git a/platform/lang-impl/src/com/intellij/find/impl/LivePreview.java b/platform/lang-impl/src/com/intellij/find/impl/LivePreview.java index 265a88fca371..0d9fa319333c 100644 --- a/platform/lang-impl/src/com/intellij/find/impl/LivePreview.java +++ b/platform/lang-impl/src/com/intellij/find/impl/LivePreview.java @@ -29,15 +29,12 @@ import com.intellij.openapi.editor.event.VisibleAreaListener; import com.intellij.openapi.editor.markup.CustomHighlighterRenderer; import com.intellij.openapi.editor.markup.RangeHighlighter; import com.intellij.openapi.editor.markup.TextAttributes; -import com.intellij.openapi.fileEditor.FileEditor; -import com.intellij.openapi.fileEditor.TextEditor; -import com.intellij.openapi.fileEditor.ex.FileEditorManagerEx; import com.intellij.openapi.project.Project; import com.intellij.openapi.ui.popup.Balloon; import com.intellij.openapi.ui.popup.BalloonBuilder; import com.intellij.openapi.ui.popup.JBPopupFactory; +import com.intellij.openapi.util.Ref; import com.intellij.openapi.util.TextRange; -import com.intellij.openapi.vfs.VirtualFile; import com.intellij.ui.awt.RelativePoint; import com.intellij.util.Alarm; import com.intellij.util.containers.HashSet; @@ -105,6 +102,14 @@ public class LivePreview extends DocumentAdapter implements ReplacementView.Dele return myCursor; } + public Project getProject() { + return myProject; + } + + public Editor getEditor() { + return myEditor; + } + public interface CursorListener { void cursorMoved(); } @@ -131,6 +136,8 @@ public class LivePreview extends DocumentAdapter implements ReplacementView.Dele void performReplaceAll(Editor e); void getFocusBack(); + + Editor getEditor(Ref needToUpdate); } private static final int USER_ACTIVITY_TRIGGERING_DELAY = 300; @@ -167,7 +174,7 @@ public class LivePreview extends DocumentAdapter implements ReplacementView.Dele public LivePreview(Project project) { myProject = project; - updateEditorReference(); +// updateEditorReference(); } public Delegate getDelegate() { @@ -179,51 +186,29 @@ public class LivePreview extends DocumentAdapter implements ReplacementView.Dele } @Nullable - public Editor updateEditorReference() { + private Editor updateEditorReference() { if (myProject == null) return null; - FileEditorManagerEx instanceEx = FileEditorManagerEx.getInstanceEx(myProject); - if (instanceEx != null) { - VirtualFile currentFile = instanceEx.getCurrentFile(); - if (currentFile != null) { - FileEditor[] editors = instanceEx.getEditors(currentFile); - if (editors.length > 0) { - FileEditor fileEditor = editors[0]; - boolean focusedFound = false; - for (FileEditor e : editors) { - if (e instanceof TextEditor && ((TextEditor)e).getEditor().getContentComponent().hasFocus()) { - fileEditor = e; - focusedFound = true; - } - } - boolean needToUpdate = true; - if (!focusedFound) { - for (FileEditor e : editors) { - if (e instanceof TextEditor && ((TextEditor)e).getEditor() == myEditor) { - needToUpdate = false; - } - } - } - if (needToUpdate && fileEditor instanceof TextEditor) { - Editor editor1 = ((TextEditor) fileEditor).getEditor(); - if (editor1 != myEditor) { - doInternalCleanUp(); - } - if (myEditor != null) { - myEditor.getDocument().removeDocumentListener(this); - } - myEditor = editor1; - myEditor.getDocument().addDocumentListener(this); - } - } else { - myEditor = null; - } - } else { - myEditor = null; - } + Ref needToUpdate = new Ref(); + Editor result = myDelegate.getEditor(needToUpdate); + if (!needToUpdate.isNull() && needToUpdate.get()) { + setEditor(result); } return myEditor; } + private void setEditor(Editor editor) { + if (editor != myEditor) { + doInternalCleanUp(); + } + if (myEditor != null) { + myEditor.getDocument().removeDocumentListener(this); + } + myEditor = editor; + if (myEditor != null) { + myEditor.getDocument().addDocumentListener(this); + } + } + @Override public void documentChanged(DocumentEvent e) { doInternalCleanUp(); diff --git a/platform/lang-impl/src/com/intellij/find/impl/LivePreviewController.java b/platform/lang-impl/src/com/intellij/find/impl/LivePreviewController.java index 2c241bb93301..0cd76024bbc9 100644 --- a/platform/lang-impl/src/com/intellij/find/impl/LivePreviewController.java +++ b/platform/lang-impl/src/com/intellij/find/impl/LivePreviewController.java @@ -4,7 +4,12 @@ import com.intellij.find.FindModel; import com.intellij.openapi.actionSystem.AnAction; import com.intellij.openapi.actionSystem.AnActionEvent; import com.intellij.openapi.editor.Editor; +import com.intellij.openapi.fileEditor.FileEditor; +import com.intellij.openapi.fileEditor.TextEditor; +import com.intellij.openapi.fileEditor.ex.FileEditorManagerEx; +import com.intellij.openapi.util.Ref; import com.intellij.openapi.util.TextRange; +import com.intellij.openapi.vfs.VirtualFile; import com.intellij.ui.UserActivityListener; import com.intellij.ui.UserActivityWatcher; import org.jetbrains.annotations.NotNull; @@ -88,6 +93,40 @@ public class LivePreviewController implements LivePreview.Delegate, UserActivity myFindDialog.getContentPane().requestFocus(); } + @Override + public Editor getEditor(Ref needToUpdate) { + Editor result = null; + FileEditorManagerEx instanceEx = FileEditorManagerEx.getInstanceEx(myLivePreview.getProject()); + if (instanceEx != null) { + VirtualFile currentFile = instanceEx.getCurrentFile(); + if (currentFile != null) { + FileEditor[] editors = instanceEx.getEditors(currentFile); + if (editors.length > 0) { + FileEditor fileEditor = editors[0]; + boolean focusedFound = false; + for (FileEditor e : editors) { + if (e instanceof TextEditor && ((TextEditor)e).getEditor().getContentComponent().hasFocus()) { + fileEditor = e; + focusedFound = true; + } + } + needToUpdate.set(true); + if (!focusedFound) { + for (FileEditor e : editors) { + if (e instanceof TextEditor && ((TextEditor)e).getEditor() == myLivePreview.getEditor()) { + needToUpdate.set(false); + } + } + } + if(needToUpdate.get() && fileEditor instanceof TextEditor) { + result = ((TextEditor)fileEditor).getEditor(); + } + } + } + } + return result; + } + @Override public TextRange performReplace(final LiveOccurrence occurrence, final String replacement, final Editor editor) { updateDelegatesFindModel(); diff --git a/platform/lang-impl/src/com/intellij/find/impl/LivePreviewControllerBase.java b/platform/lang-impl/src/com/intellij/find/impl/LivePreviewControllerBase.java index fdbdf8255b87..7ffd7c191764 100644 --- a/platform/lang-impl/src/com/intellij/find/impl/LivePreviewControllerBase.java +++ b/platform/lang-impl/src/com/intellij/find/impl/LivePreviewControllerBase.java @@ -8,6 +8,7 @@ import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.editor.Editor; import com.intellij.openapi.fileEditor.FileDocumentManager; import com.intellij.openapi.util.Pair; +import com.intellij.openapi.util.Ref; import com.intellij.openapi.util.TextRange; import com.intellij.openapi.vfs.VirtualFile; import org.jetbrains.annotations.NotNull; @@ -145,5 +146,10 @@ public class LivePreviewControllerBase implements LivePreview.Delegate { @Override public void getFocusBack() {} + @Override + public Editor getEditor(Ref needToUpdate) { + return null; //To change body of implemented methods use File | Settings | File Templates. + } + public void notFound() {} } From 9d6ce50537269b34413dda03cdaeed9af4672497 Mon Sep 17 00:00:00 2001 From: Oleg Shpynov Date: Tue, 15 Feb 2011 16:18:13 +0300 Subject: [PATCH 03/13] IDEA-64628: Better error message when there are no repositories to clone --- .../org/jetbrains/plugins/github/GithubCheckoutProvider.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/github/src/org/jetbrains/plugins/github/GithubCheckoutProvider.java b/plugins/github/src/org/jetbrains/plugins/github/GithubCheckoutProvider.java index 8c976b00de21..db926545b20b 100644 --- a/plugins/github/src/org/jetbrains/plugins/github/GithubCheckoutProvider.java +++ b/plugins/github/src/org/jetbrains/plugins/github/GithubCheckoutProvider.java @@ -32,7 +32,7 @@ public class GithubCheckoutProvider implements CheckoutProvider { return; } if (availableRepos.isEmpty()){ - Messages.showErrorDialog(project, "You don't have any repository available on GitHub.", "Cannot clone"); + Messages.showErrorDialog(project, "You don't have any repository available on GitHub.\nOnly your own or watched repositories can be cloned.", "Cannot clone"); return; } Collections.sort(availableRepos, new Comparator() { From 5b0765bb14c5ce64a587aff8ffbe678a39962bfa Mon Sep 17 00:00:00 2001 From: Konstantin Bulenkov Date: Tue, 15 Feb 2011 17:14:27 +0300 Subject: [PATCH 04/13] open file using FileManager instead of navigate (IDEA-65392 NPE) --- .../codeInsight/daemon/impl/IconLineMarkerProvider.java | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/IconLineMarkerProvider.java b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/IconLineMarkerProvider.java index 909cae8bb465..a76a1b283bff 100644 --- a/java/java-impl/src/com/intellij/codeInsight/daemon/impl/IconLineMarkerProvider.java +++ b/java/java-impl/src/com/intellij/codeInsight/daemon/impl/IconLineMarkerProvider.java @@ -21,7 +21,10 @@ import com.intellij.codeInsight.daemon.GutterIconNavigationHandler; import com.intellij.codeInsight.daemon.LineMarkerInfo; import com.intellij.codeInsight.daemon.LineMarkerProvider; import com.intellij.openapi.editor.markup.GutterIconRenderer; +import com.intellij.openapi.fileEditor.FileEditorManager; +import com.intellij.openapi.project.Project; import com.intellij.openapi.util.Pair; +import com.intellij.openapi.util.Ref; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.*; import com.intellij.psi.impl.source.resolve.reference.impl.providers.FileReference; @@ -107,7 +110,7 @@ public class IconLineMarkerProvider implements LineMarkerProvider { @Nullable private LineMarkerInfo resolveIconInfo(PsiType type, PsiExpression initializer, PsiElement bindingElement) { if (initializer != null && initializer.isValid() && isIconClassType(type)) { - + final Project project = initializer.getProject(); final List refs = new ArrayList(); initializer.accept(new JavaRecursiveElementWalkingVisitor() { @Override @@ -146,9 +149,10 @@ public class IconLineMarkerProvider implements LineMarkerProvider { final Icon icon = getIcon(file); if (icon != null) { + final Ref f = Ref.create(file); final GutterIconNavigationHandler navHandler = new GutterIconNavigationHandler() { public void navigate(MouseEvent e, PsiElement elt) { - psiFileSystemItem.navigate(true); + FileEditorManager.getInstance(project).openFile(f.get(), true); } }; return new LineMarkerInfo(bindingElement, bindingElement.getTextRange(), icon, From bcbb92f6e73dee0a4915db639daf05431bb478fd Mon Sep 17 00:00:00 2001 From: nik Date: Tue, 15 Feb 2011 17:29:15 +0300 Subject: [PATCH 05/13] trove4j.jar is used in module 'util' so it need to be added to bootstrap classpath --- plugins/devkit/src/run/PluginRunConfiguration.java | 1 + 1 file changed, 1 insertion(+) diff --git a/plugins/devkit/src/run/PluginRunConfiguration.java b/plugins/devkit/src/run/PluginRunConfiguration.java index 34b0ab3e92c9..9dff21bb8474 100644 --- a/plugins/devkit/src/run/PluginRunConfiguration.java +++ b/plugins/devkit/src/run/PluginRunConfiguration.java @@ -129,6 +129,7 @@ public class PluginRunConfiguration extends RunConfigurationBase implements Modu params.getClassPath().addFirst(libPath + File.separator + "log4j.jar"); params.getClassPath().addFirst(libPath + File.separator + "jdom.jar"); + params.getClassPath().addFirst(libPath + File.separator + "trove4j.jar"); params.getClassPath().addFirst(libPath + File.separator + "openapi.jar"); params.getClassPath().addFirst(libPath + File.separator + "util.jar"); params.getClassPath().addFirst(libPath + File.separator + "extensions.jar"); From c27effc1277934df3c90cdfd49b34689fc1b151b Mon Sep 17 00:00:00 2001 From: Kirill Kalishev Date: Tue, 15 Feb 2011 17:37:35 +0300 Subject: [PATCH 06/13] IDEA-65534 Optimizazion Hint shows up on every restart --- .../com/intellij/ide/startup/impl/StartupManagerImpl.java | 5 +++-- platform/util/src/com/intellij/openapi/util/SystemInfo.java | 2 ++ 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/platform/platform-impl/src/com/intellij/ide/startup/impl/StartupManagerImpl.java b/platform/platform-impl/src/com/intellij/ide/startup/impl/StartupManagerImpl.java index 46d1db1c6713..668a3a60548a 100644 --- a/platform/platform-impl/src/com/intellij/ide/startup/impl/StartupManagerImpl.java +++ b/platform/platform-impl/src/com/intellij/ide/startup/impl/StartupManagerImpl.java @@ -151,7 +151,7 @@ public class StartupManagerImpl extends StartupManagerEx { VirtualFileManager.getInstance().refresh(!app.isHeadlessEnvironment()); } - if (SystemInfo.isMac && SystemInfo.is64Bit && "10.6".compareTo(SystemInfo.OS_VERSION) <= 0) { + if (SystemInfo.isMac && SystemInfo.isMacIntel64 && "10.6".compareTo(SystemInfo.OS_VERSION) <= 0) { if (Registry.is("ide.firstStartup")) { String productName = ApplicationNamesInfo.getInstance().getProductName(); Notification n = @@ -164,9 +164,10 @@ public class StartupManagerImpl extends StartupManagerEx { } }); Notifications.Bus.notify(n, NotificationDisplayType.STICKY_BALLOON, null); - Registry.get("ide.firstStartup").setValue(false); } } + + Registry.get("ide.firstStartup").setValue(false); } private void startCacheUpdate() { diff --git a/platform/util/src/com/intellij/openapi/util/SystemInfo.java b/platform/util/src/com/intellij/openapi/util/SystemInfo.java index cffa51e2fcb4..00fda6c7b079 100644 --- a/platform/util/src/com/intellij/openapi/util/SystemInfo.java +++ b/platform/util/src/com/intellij/openapi/util/SystemInfo.java @@ -53,6 +53,8 @@ public class SystemInfo { public static final boolean is64Bit = !is32Bit; public static final boolean isAMD64 = "amd64".equals(OS_ARCH); + public static final boolean isMacIntel64 = isMac && "x86_64".equals(OS_ARCH); + /** * Whether IDEA is running under MacOS X version 10.4 or later. * From e820f5af2af35dc01a86d2c1001cb065dbd165fb Mon Sep 17 00:00:00 2001 From: Alexey Kudravtsev Date: Tue, 15 Feb 2011 12:59:02 +0300 Subject: [PATCH 07/13] notnull --- .../openapi/util/ShutDownTracker.java | 20 +++++++++---------- .../intellij/util/messages/impl/Message.java | 5 +++-- .../messages/impl/MessageListenerList.java | 9 +++++---- 3 files changed, 17 insertions(+), 17 deletions(-) diff --git a/platform/util/src/com/intellij/openapi/util/ShutDownTracker.java b/platform/util/src/com/intellij/openapi/util/ShutDownTracker.java index 42674fd28dc2..12f0e5b58973 100644 --- a/platform/util/src/com/intellij/openapi/util/ShutDownTracker.java +++ b/platform/util/src/com/intellij/openapi/util/ShutDownTracker.java @@ -16,6 +16,7 @@ package com.intellij.openapi.util; import com.intellij.openapi.diagnostic.Logger; +import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import java.util.ArrayList; @@ -89,35 +90,36 @@ public class ShutDownTracker implements Runnable { } } - private synchronized boolean isRegistered(Thread thread) { + private synchronized boolean isRegistered(@NotNull Thread thread) { return myThreads.contains(thread); } + @NotNull private synchronized Thread[] getStopperThreads() { return myThreads.toArray(new Thread[myThreads.size()]); } - public synchronized void registerStopperThread(Thread thread) { + public synchronized void registerStopperThread(@NotNull Thread thread) { myThreads.add(thread); } - public synchronized void unregisterStopperThread(Thread thread) { + public synchronized void unregisterStopperThread(@NotNull Thread thread) { myThreads.remove(thread); } - public synchronized void registerShutdownThread(final Thread thread) { + public synchronized void registerShutdownThread(@NotNull Thread thread) { myShutdownThreads.addLast(thread); } - public synchronized void registerShutdownThread(int index, final Thread thread) { + public synchronized void registerShutdownThread(int index, @NotNull Thread thread) { myShutdownThreads.add(index, thread); } - public synchronized void registerShutdownTask(Runnable task) { + public synchronized void registerShutdownTask(@NotNull Runnable task) { myShutdownTasks.addLast(task); } - public synchronized void unregisterShutdownTask(Runnable task) { + public synchronized void unregisterShutdownTask(@NotNull Runnable task) { myShutdownTasks.remove(task); } @@ -125,8 +127,4 @@ public class ShutDownTracker implements Runnable { private synchronized T removeLast(LinkedList list) { return list.isEmpty()? null : list.removeLast(); } - - private synchronized boolean isEmpty(LinkedList list) { - return list.isEmpty(); - } } diff --git a/platform/util/src/com/intellij/util/messages/impl/Message.java b/platform/util/src/com/intellij/util/messages/impl/Message.java index 2de6dc88011d..c4d0038aa515 100644 --- a/platform/util/src/com/intellij/util/messages/impl/Message.java +++ b/platform/util/src/com/intellij/util/messages/impl/Message.java @@ -20,6 +20,7 @@ package com.intellij.util.messages.impl; import com.intellij.util.messages.Topic; +import org.jetbrains.annotations.NotNull; import java.lang.reflect.Method; @@ -28,7 +29,7 @@ public final class Message { private final Method myListenerMethod; private final Object[] myArgs; - public Message(final Topic topic, final Method listenerMethod, final Object[] args) { + public Message(@NotNull Topic topic, @NotNull Method listenerMethod, Object[] args) { myTopic = topic; myListenerMethod = listenerMethod; myArgs = args; @@ -49,4 +50,4 @@ public final class Message { public String toString() { return myTopic.toString() + ":" + myListenerMethod.getName(); } -} \ No newline at end of file +} diff --git a/platform/util/src/com/intellij/util/messages/impl/MessageListenerList.java b/platform/util/src/com/intellij/util/messages/impl/MessageListenerList.java index 7448f444d853..fa0fc73b1680 100644 --- a/platform/util/src/com/intellij/util/messages/impl/MessageListenerList.java +++ b/platform/util/src/com/intellij/util/messages/impl/MessageListenerList.java @@ -20,6 +20,7 @@ import com.intellij.util.messages.MessageBusConnection; import com.intellij.util.messages.Topic; import com.intellij.openapi.Disposable; import com.intellij.openapi.util.Disposer; +import org.jetbrains.annotations.NotNull; import java.util.HashMap; import java.util.Map; @@ -32,18 +33,18 @@ public class MessageListenerList { private final Topic myTopic; private final Map myListenerToConnectionMap = new HashMap(); - public MessageListenerList(MessageBus messageBus, Topic topic) { + public MessageListenerList(@NotNull MessageBus messageBus, @NotNull Topic topic) { myTopic = topic; myMessageBus = messageBus; } - public void add(T listener) { + public void add(@NotNull T listener) { final MessageBusConnection connection = myMessageBus.connect(); connection.subscribe(myTopic, listener); myListenerToConnectionMap.put(listener, connection); } - public void add(final T listener, Disposable parentDisposable) { + public void add(@NotNull final T listener, @NotNull Disposable parentDisposable) { Disposer.register(parentDisposable, new Disposable() { public void dispose() { myListenerToConnectionMap.remove(listener); @@ -54,7 +55,7 @@ public class MessageListenerList { myListenerToConnectionMap.put(listener, connection); } - public void remove(T listener) { + public void remove(@NotNull T listener) { final MessageBusConnection connection = myListenerToConnectionMap.remove(listener); if (connection != null) { connection.disconnect(); From 598ebd6fa1909a1ab9f95736ad8ec86a5f0a1ac7 Mon Sep 17 00:00:00 2001 From: Alexey Kudravtsev Date: Tue, 15 Feb 2011 13:02:35 +0300 Subject: [PATCH 08/13] cleanup --- .../intellij/psi/impl/source/PsiFileImpl.java | 17 ++++++----------- 1 file changed, 6 insertions(+), 11 deletions(-) diff --git a/platform/lang-impl/src/com/intellij/psi/impl/source/PsiFileImpl.java b/platform/lang-impl/src/com/intellij/psi/impl/source/PsiFileImpl.java index 141ede0c5a57..8424ea6566e1 100644 --- a/platform/lang-impl/src/com/intellij/psi/impl/source/PsiFileImpl.java +++ b/platform/lang-impl/src/com/intellij/psi/impl/source/PsiFileImpl.java @@ -619,20 +619,11 @@ public abstract class PsiFileImpl extends ElementBase implements PsiFileEx, PsiF final StubTree derefdOnLock = derefStub(); if (derefdOnLock != null) return derefdOnLock; - setStubTree(stubHolder); - - return derefStub(); - } - } - - public void setStubTree(StubTree stubHolder) { - synchronized (myStubLock) { - assert getTreeElementNoLock() == null; myStub = new SoftReference(stubHolder); StubBase base = (StubBase)stubHolder.getRoot(); base.setPsi(this); - base.putUserData(STUB_TREE_IN_PARSED_TREE, stubHolder); // This will prevent soft reference myStub to be collected before all of the stubs are collected. + return stubHolder; } } @@ -890,7 +881,11 @@ public abstract class PsiFileImpl extends ElementBase implements PsiFileEx, PsiF final FileElement fileElement = calcTreeElement(); StubTree tree = fileElement.getUserData(STUB_TREE_IN_PARSED_TREE); if (tree == null) { - final StubElement currentStubTree = ((IStubFileElementType)getContentElementType()).getBuilder().buildStubTree(this); + IElementType contentElementType = getContentElementType(); + if (!(contentElementType instanceof IStubFileElementType)) { + LOG.error("ContentElementType: "+contentElementType+"; file: "+this); + } + final StubElement currentStubTree = ((IStubFileElementType)contentElementType).getBuilder().buildStubTree(this); tree = new StubTree((PsiFileStub)currentStubTree); bindFakeStubsToTree(tree); fileElement.putUserData(STUB_TREE_IN_PARSED_TREE, tree); From a3a4b88752d15fea105090462e14c66a803f742b Mon Sep 17 00:00:00 2001 From: Alexey Kudravtsev Date: Tue, 15 Feb 2011 13:05:42 +0300 Subject: [PATCH 09/13] leaks in tests --- .../psi/impl/PsiDocumentManagerImpl.java | 22 +++++++++++-------- 1 file changed, 13 insertions(+), 9 deletions(-) diff --git a/platform/lang-impl/src/com/intellij/psi/impl/PsiDocumentManagerImpl.java b/platform/lang-impl/src/com/intellij/psi/impl/PsiDocumentManagerImpl.java index 5c9281c59b7c..9b854eae16fd 100644 --- a/platform/lang-impl/src/com/intellij/psi/impl/PsiDocumentManagerImpl.java +++ b/platform/lang-impl/src/com/intellij/psi/impl/PsiDocumentManagerImpl.java @@ -155,7 +155,7 @@ public class PsiDocumentManagerImpl extends PsiDocumentManager implements Projec } @Nullable - public FileViewProvider getCachedViewProvider(Document document) { + public FileViewProvider getCachedViewProvider(@NotNull Document document) { final VirtualFile virtualFile = FileDocumentManager.getInstance().getFile(document); if (virtualFile == null || !virtualFile.isValid()) return null; return ((PsiManagerEx)myPsiManager).getFileManager().findCachedViewProvider(virtualFile); @@ -521,13 +521,14 @@ public class PsiDocumentManagerImpl extends PsiDocumentManager implements Projec public void beforeDocumentChange(DocumentEvent event) { final Document document = event.getDocument(); - final FileViewProvider provider = getCachedViewProvider(document); - if (provider == null) return; + final FileViewProvider viewProvider = getCachedViewProvider(document); + if (viewProvider == null) return; + if (!isRelevant(viewProvider)) return; - VirtualFile virtualFile = provider.getVirtualFile(); + VirtualFile virtualFile = viewProvider.getVirtualFile(); if (virtualFile.getFileType().isBinary()) return; - final List files = provider.getAllFiles(); + final List files = viewProvider.getAllFiles(); boolean hasLockedBlocks = false; for (PsiFile file : files) { if (file == null) continue; @@ -556,7 +557,7 @@ public class PsiDocumentManagerImpl extends PsiDocumentManager implements Projec } if (!hasLockedBlocks) { - ((SingleRootFileViewProvider)provider).beforeDocumentChanged(); + ((SingleRootFileViewProvider)viewProvider).beforeDocumentChanged(); } } @@ -564,9 +565,7 @@ public class PsiDocumentManagerImpl extends PsiDocumentManager implements Projec final Document document = event.getDocument(); final FileViewProvider viewProvider = getCachedViewProvider(document); if (viewProvider == null) return; - VirtualFile virtualFile = viewProvider.getVirtualFile(); - if (virtualFile.getFileType().isBinary()) return; - if (viewProvider.getManager() != myPsiManager) return; + if (!isRelevant(viewProvider)) return; final List files = viewProvider.getAllFiles(); boolean commitNecessary = false; @@ -597,6 +596,11 @@ public class PsiDocumentManagerImpl extends PsiDocumentManager implements Projec } } + private boolean isRelevant(FileViewProvider viewProvider) { + VirtualFile virtualFile = viewProvider.getVirtualFile(); + return !virtualFile.getFileType().isBinary() && viewProvider.getManager() == myPsiManager && !myPsiManager.getProject().isDisposed(); + } + public TextBlock getTextBlock(Document document, PsiFile file) { TextBlock textBlock = file.getUserData(KEY_TEXT_BLOCK); if (textBlock == null){ From e5540883a28280f1f1586e0b712502fcb652619e Mon Sep 17 00:00:00 2001 From: Alexey Kudravtsev Date: Tue, 15 Feb 2011 15:40:04 +0300 Subject: [PATCH 10/13] cleanup --- .../lang/java/parser/StatementParser.java | 2 +- .../tree/events/impl/TreeChangeEventImpl.java | 18 ++++++++++-------- .../impl/source/text/BlockSupportImpl.java | 4 ++-- .../src/com/intellij/util/diff/DiffTree.java | 19 +++++++++---------- 4 files changed, 22 insertions(+), 21 deletions(-) diff --git a/java/java-impl/src/com/intellij/lang/java/parser/StatementParser.java b/java/java-impl/src/com/intellij/lang/java/parser/StatementParser.java index e14dd6ea895f..a4ba10e2e8b0 100644 --- a/java/java-impl/src/com/intellij/lang/java/parser/StatementParser.java +++ b/java/java-impl/src/com/intellij/lang/java/parser/StatementParser.java @@ -117,7 +117,7 @@ public class StatementParser { final PsiBuilder.Marker codeBlock = builder.mark(); builder.advanceLexer(); - parseStatements(builder, (parseUntilEof ? BraceMode.TILL_LAST : BraceMode.TILL_FIRST)); + parseStatements(builder, parseUntilEof ? BraceMode.TILL_LAST : BraceMode.TILL_FIRST); final boolean greedyBlock = !expectOrError(builder, JavaTokenType.RBRACE, JavaErrorMessages.message("expected.rbrace")); builder.getTokenType(); // eat spaces diff --git a/platform/lang-impl/src/com/intellij/pom/tree/events/impl/TreeChangeEventImpl.java b/platform/lang-impl/src/com/intellij/pom/tree/events/impl/TreeChangeEventImpl.java index e36accb9a054..73f7a5e1f71b 100644 --- a/platform/lang-impl/src/com/intellij/pom/tree/events/impl/TreeChangeEventImpl.java +++ b/platform/lang-impl/src/com/intellij/pom/tree/events/impl/TreeChangeEventImpl.java @@ -186,14 +186,16 @@ public class TreeChangeEventImpl implements TreeChangeEvent{ } private void insertAtList(ASTNode node){ - final int[] nodeRoute = getRoute(node); - int index = 0; - while(index < myChangedInOrder.size()){ - final ASTNode current = myChangedInOrder.get(index++); - final int[] route = getRoute(current); - if(compareRouts(nodeRoute, route) < 0) { - myChangedInOrder.add(index, node); - return; + if (!myChangedInOrder.isEmpty()) { + final int[] nodeRoute = getRoute(node); + int index = 0; + while(index < myChangedInOrder.size()){ + final ASTNode current = myChangedInOrder.get(index++); + final int[] route = getRoute(current); + if(compareRouts(nodeRoute, route) < 0) { + myChangedInOrder.add(index, node); + return; + } } } myChangedInOrder.add(node); diff --git a/platform/lang-impl/src/com/intellij/psi/impl/source/text/BlockSupportImpl.java b/platform/lang-impl/src/com/intellij/psi/impl/source/text/BlockSupportImpl.java index 8c49683d476b..be89f30f561b 100644 --- a/platform/lang-impl/src/com/intellij/psi/impl/source/text/BlockSupportImpl.java +++ b/platform/lang-impl/src/com/intellij/psi/impl/source/text/BlockSupportImpl.java @@ -87,11 +87,11 @@ public class BlockSupportImpl extends BlockSupport { file.getViewProvider().beforeContentsSynchronized(); final PsiFileImpl fileImpl = (PsiFileImpl)file; Project project = fileImpl.getProject(); - final CharTable charTable = fileImpl.getTreeElement().getCharTable(); + final FileElement treeFileElement = fileImpl.getTreeElement(); + final CharTable charTable = treeFileElement.getCharTable(); // hack final int textLength = file.getTextLength() + lengthShift; - final FileElement treeFileElement = fileImpl.getTreeElement(); if (treeFileElement.getElementType() instanceof ITemplateDataElementType || isTooDeep(file)) { // unable to perform incremental reparse for template data in JSP, or in exceptionally deep trees diff --git a/platform/util/src/com/intellij/util/diff/DiffTree.java b/platform/util/src/com/intellij/util/diff/DiffTree.java index a658306b0e94..0bab60dc87da 100644 --- a/platform/util/src/com/intellij/util/diff/DiffTree.java +++ b/platform/util/src/com/intellij/util/diff/DiffTree.java @@ -120,7 +120,6 @@ public class DiffTree { NT newChild2 = newIndex < newSize-1 ? newChildren[newIndex+1] : null; CompareResult c11 = looksEqual(comparator, oldChild1, newChild1); - if (c11 == CompareResult.EQUAL || c11 == CompareResult.DRILL_DOWN_NEEDED) { if (c11 == CompareResult.DRILL_DOWN_NEEDED) { build(oldChild1, newChild1, level+1); @@ -129,32 +128,32 @@ public class DiffTree { newIndex++; continue; } - CompareResult c12 = looksEqual(comparator, oldChild1, newChild2); - CompareResult c21 = looksEqual(comparator, oldChild2, newChild1); if (c11 == CompareResult.TYPE_ONLY) { + CompareResult c21 = looksEqual(comparator, oldChild2, newChild1); if (c21 == CompareResult.EQUAL || c21 == CompareResult.DRILL_DOWN_NEEDED) { myConsumer.nodeDeleted(oldNode, oldChild1); oldIndex++; continue; } - else if (c12 == CompareResult.EQUAL || c12 == CompareResult.DRILL_DOWN_NEEDED) { + CompareResult c12 = looksEqual(comparator, oldChild1, newChild2); + if (c12 == CompareResult.EQUAL || c12 == CompareResult.DRILL_DOWN_NEEDED) { myConsumer.nodeInserted(oldNode, newChild1, newIndex); newIndex++; continue; } - else { - myConsumer.nodeReplaced(oldChild1, newChild1); - oldIndex++; - newIndex++; - continue; - } + myConsumer.nodeReplaced(oldChild1, newChild1); + oldIndex++; + newIndex++; + continue; } + CompareResult c12 = looksEqual(comparator, oldChild1, newChild2); if (c12 == CompareResult.EQUAL || c12 == CompareResult.DRILL_DOWN_NEEDED || c12 == CompareResult.TYPE_ONLY) { myConsumer.nodeInserted(oldNode, newChild1, newIndex); newIndex++; continue; } + CompareResult c21 = looksEqual(comparator, oldChild2, newChild1); if (c21 == CompareResult.EQUAL || c21 == CompareResult.DRILL_DOWN_NEEDED || c21 == CompareResult.TYPE_ONLY) { myConsumer.nodeDeleted(oldNode, oldChild1); oldIndex++; From b64809b4f3968c6656be699638eb29704a7b6308 Mon Sep 17 00:00:00 2001 From: Alexey Kudravtsev Date: Tue, 15 Feb 2011 18:14:09 +0300 Subject: [PATCH 11/13] error --- .../src/git4idea/checkin/GitPushActiveBranchesDialog.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/plugins/git4idea/src/git4idea/checkin/GitPushActiveBranchesDialog.java b/plugins/git4idea/src/git4idea/checkin/GitPushActiveBranchesDialog.java index cc8cfd115c7b..76a37d7ab60b 100644 --- a/plugins/git4idea/src/git4idea/checkin/GitPushActiveBranchesDialog.java +++ b/plugins/git4idea/src/git4idea/checkin/GitPushActiveBranchesDialog.java @@ -759,12 +759,12 @@ public class GitPushActiveBranchesDialog extends DialogWrapper { } if (postUiTask != null) { - ApplicationManager.getApplication().invokeAndWait(new Runnable() { + UIUtil.invokeAndWaitIfNeeded(new Runnable() { @Override public void run() { postUiTask.run(roots); } - }, ModalityState.stateForComponent(getRootPane())); + }); } } }; From 0756ccc40ac17ed25712b9eb3f9a7f2e1f4e0d55 Mon Sep 17 00:00:00 2001 From: Anton Makeev Date: Tue, 15 Feb 2011 16:21:50 +0100 Subject: [PATCH 12/13] CIDR: 'clean' action + 'build/clean' actions' progress + refactored references VFS: additional 'refreshIoFiles' methods --- .../src/com/intellij/execution/ExecutionHelper.java | 4 ++-- .../src/com/intellij/execution/ExecutionMode.java | 4 ++-- .../com/intellij/openapi/vfs/LocalFileSystem.java | 3 +++ .../openapi/vfs/impl/local/LocalFileSystemBase.java | 13 +++++++++---- .../openapi/vfs/impl/local/LocalFileSystemImpl.java | 2 +- .../src/com/intellij/mock/MockLocalFileSystem.java | 9 +++++++++ 6 files changed, 26 insertions(+), 9 deletions(-) diff --git a/platform/lang-impl/src/com/intellij/execution/ExecutionHelper.java b/platform/lang-impl/src/com/intellij/execution/ExecutionHelper.java index 3c56bc8f36e0..284c0f06c0f2 100644 --- a/platform/lang-impl/src/com/intellij/execution/ExecutionHelper.java +++ b/platform/lang-impl/src/com/intellij/execution/ExecutionHelper.java @@ -185,7 +185,7 @@ public class ExecutionHelper { public static void executeExternalProcess(@Nullable final Project myProject, @NotNull final OSProcessHandler processHandler, @NotNull final ExecutionMode mode) { - final String title = mode.getTitle() != null ? mode.getTitle() : "Running. Please wait..."; + final String title = mode.getTitle() != null ? mode.getTitle() : "Please wait..."; assert title != null; final Runnable process; @@ -275,7 +275,7 @@ public class ExecutionHelper { public void run() { myProgressIndicator = ProgressManager.getInstance().getProgressIndicator(); if (myProgressIndicator != null && StringUtil.isEmpty(myProgressIndicator.getText())) { - myProgressIndicator.setText("Please wait"); + myProgressIndicator.setText("Please wait..."); } LOG.assertTrue(myProgressIndicator != null || cancelableFun != null, diff --git a/platform/lang-impl/src/com/intellij/execution/ExecutionMode.java b/platform/lang-impl/src/com/intellij/execution/ExecutionMode.java index 656101855044..63104e65d732 100644 --- a/platform/lang-impl/src/com/intellij/execution/ExecutionMode.java +++ b/platform/lang-impl/src/com/intellij/execution/ExecutionMode.java @@ -27,7 +27,7 @@ import java.util.List; /** * @author Roman.Chernyatchik */ -public abstract class ExecutionMode { +public class ExecutionMode { private final boolean myCancelable; private final String myTitle; private final String myTitle2; @@ -107,4 +107,4 @@ public abstract class ExecutionMode { public List getProcessListeners() { return myListeners; } -} \ No newline at end of file +} diff --git a/platform/platform-api/src/com/intellij/openapi/vfs/LocalFileSystem.java b/platform/platform-api/src/com/intellij/openapi/vfs/LocalFileSystem.java index 40626132fa4b..75d6d682e521 100644 --- a/platform/platform-api/src/com/intellij/openapi/vfs/LocalFileSystem.java +++ b/platform/platform-api/src/com/intellij/openapi/vfs/LocalFileSystem.java @@ -59,6 +59,8 @@ public abstract class LocalFileSystem extends NewVirtualFileSystem { */ public abstract void refreshIoFiles(Iterable files); + public abstract void refreshIoFiles(Iterable files, boolean async, boolean recursive, @Nullable Runnable onFinish); + /** * Performs a nonrecursive synchronous refresh of specified files * @param files files to refresh @@ -66,6 +68,7 @@ public abstract class LocalFileSystem extends NewVirtualFileSystem { */ public abstract void refreshFiles(Iterable files); + public abstract void refreshFiles(Iterable files, boolean async, boolean recursive, @Nullable Runnable onFinish); public abstract byte[] physicalContentsToByteArray(final VirtualFile virtualFile) throws IOException; public abstract long physicalLength(final VirtualFile virtualFile) throws IOException; diff --git a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemBase.java b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemBase.java index 000b276a218b..18b7c7c6296f 100644 --- a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemBase.java +++ b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemBase.java @@ -192,7 +192,12 @@ public abstract class LocalFileSystemBase extends LocalFileSystem { return refreshAndFindFileByPath(path.replace(File.separatorChar, '/')); } + @Override public void refreshIoFiles(Iterable files) { + refreshIoFiles(files, false, false, null); + } + + public void refreshIoFiles(Iterable files, boolean async, boolean recursive, @Nullable Runnable onFinish) { final VirtualFileManagerEx manager = (VirtualFileManagerEx)VirtualFileManager.getInstance(); Application app = ApplicationManager.getApplication(); @@ -209,7 +214,7 @@ public abstract class LocalFileSystemBase extends LocalFileSystem { } } - RefreshQueue.getInstance().refresh(false, false, null, VfsUtil.toVirtualFileArray(filesToRefresh)); + RefreshQueue.getInstance().refresh(async, recursive, onFinish, VfsUtil.toVirtualFileArray(filesToRefresh)); } finally { if (fireCommonRefreshSession) manager.fireAfterRefreshFinish(false); @@ -217,16 +222,16 @@ public abstract class LocalFileSystemBase extends LocalFileSystem { } public void refreshFiles(Iterable files) { - refreshFiles(files, false, false); + refreshFiles(files, false, false, null); } - protected static void refreshFiles(final Iterable files, final boolean recursive, final boolean async) { + public void refreshFiles(Iterable files, boolean async, boolean recursive, @Nullable Runnable onFinish) { List list = new ArrayList(); for (VirtualFile file : files) { list.add(file); } - RefreshQueue.getInstance().refresh(async, recursive, null, VfsUtil.toVirtualFileArray(list)); + RefreshQueue.getInstance().refresh(async, recursive, onFinish, VfsUtil.toVirtualFileArray(list)); } public byte[] physicalContentsToByteArray(final VirtualFile virtualFile) throws IOException { diff --git a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemImpl.java b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemImpl.java index a3b6a47d239d..dfdb178a1204 100644 --- a/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemImpl.java +++ b/platform/platform-impl/src/com/intellij/openapi/vfs/impl/local/LocalFileSystemImpl.java @@ -388,7 +388,7 @@ public final class LocalFileSystemImpl extends LocalFileSystemBase implements Ap ((NewVirtualFile)file).markDirtyRecursively(); } } - refreshFiles(filesToSynchronize, toWatchRecursively, true); + refreshFiles(filesToSynchronize, true, toWatchRecursively, null); } return result; diff --git a/platform/testFramework/src/com/intellij/mock/MockLocalFileSystem.java b/platform/testFramework/src/com/intellij/mock/MockLocalFileSystem.java index 0f4c7e850a84..d669d3259e65 100644 --- a/platform/testFramework/src/com/intellij/mock/MockLocalFileSystem.java +++ b/platform/testFramework/src/com/intellij/mock/MockLocalFileSystem.java @@ -72,6 +72,14 @@ public class MockLocalFileSystem extends LocalFileSystem { public void refreshFiles(final Iterable files) { } + @Override + public void refreshIoFiles(Iterable files, boolean async, boolean recursive, @Nullable Runnable onFinish) { + } + + @Override + public void refreshFiles(Iterable files, boolean async, boolean recursive, @Nullable Runnable onFinish) { + } + @Override public byte[] physicalContentsToByteArray(final VirtualFile virtualFile) throws IOException { throw new UnsupportedOperationException("'physicalContentsToByteArray' not implemented in " + getClass().getName()); @@ -110,6 +118,7 @@ public class MockLocalFileSystem extends LocalFileSystem { public void unregisterAuxiliaryFileOperationsHandler(final LocalFileOperationsHandler handler) { } + @Override public boolean processCachedFilesInSubtree(final VirtualFile file, final Processor processor) { throw new UnsupportedOperationException("'processCachedFilesInSubtree' not implemented in " + getClass().getName()); From dbf393814c1c4d1ec9c5893f40925cc1a6bd29db Mon Sep 17 00:00:00 2001 From: andrey zaytsev Date: Tue, 15 Feb 2011 18:43:11 +0300 Subject: [PATCH 13/13] IDEA-65490 --- .../intellij/find/EditorSearchComponent.java | 98 ++++++++----------- .../intellij/find/impl/LiveOccurrence.java | 10 ++ .../com/intellij/find/impl/LivePreview.java | 42 ++++---- .../find/impl/LivePreviewControllerBase.java | 33 +++---- .../util/src/com/intellij/util/ui/UIUtil.java | 8 +- 5 files changed, 93 insertions(+), 98 deletions(-) diff --git a/platform/lang-impl/src/com/intellij/find/EditorSearchComponent.java b/platform/lang-impl/src/com/intellij/find/EditorSearchComponent.java index 18a2526b381d..1d0d9bd67dd9 100644 --- a/platform/lang-impl/src/com/intellij/find/EditorSearchComponent.java +++ b/platform/lang-impl/src/com/intellij/find/EditorSearchComponent.java @@ -19,8 +19,6 @@ */ package com.intellij.find; -import com.intellij.codeInsight.highlighting.HighlightManager; -import com.intellij.codeInsight.highlighting.HighlightManagerImpl; import com.intellij.featureStatistics.FeatureUsageTracker; import com.intellij.find.impl.FindManagerImpl; import com.intellij.find.impl.LiveOccurrence; @@ -34,7 +32,6 @@ import com.intellij.openapi.editor.ScrollType; import com.intellij.openapi.editor.colors.EditorFontType; import com.intellij.openapi.editor.event.SelectionEvent; import com.intellij.openapi.editor.event.SelectionListener; -import com.intellij.openapi.editor.markup.RangeHighlighter; import com.intellij.openapi.project.DumbAware; import com.intellij.openapi.project.Project; import com.intellij.openapi.ui.popup.JBPopup; @@ -73,6 +70,7 @@ import java.util.Set; import java.util.regex.Pattern; public class EditorSearchComponent extends JPanel implements DataProvider, LivePreview.CursorListener, SelectionListener { + private static final int MATCHES_LIMIT = 100; private final JLabel myMatchInfoLabel; private final LinkLabel myClickToHighlightLabel; private final Project myProject; @@ -91,9 +89,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP private static final Color FOCUS_CATCHER_COLOR = new Color(0x9999ff); private final JComponent myToolbarComponent; private com.intellij.openapi.editor.event.DocumentAdapter myDocumentListener; - private ArrayList myHighlighters = new ArrayList(); - private int myMatchesLimit = 100; private final JCheckBox myCbRegexp; private final JCheckBox myCbWholeWords; private final JCheckBox myCbInComments; @@ -111,13 +107,31 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP return myEditor; } - public void notFound() { - setNotFoundBackground(); - } - @Override - protected void tooManyMatches() { - myMatchInfoLabel.setText("More than " + myMatchesLimit + " matches"); + public void searchEndsWith(int count) { + if (count <= getMatchesLimit()) { + myClickToHighlightLabel.setVisible(false); + + if (count > 0) { + setRegularBackground(); + if (count > 1) { + myMatchInfoLabel.setText(count + " matches"); + } + else { + myMatchInfoLabel.setText("1 match"); + } + } + else { + setNotFoundBackground(); + myMatchInfoLabel.setText("No matches"); + } + } + else { + setRegularBackground(); + myMatchInfoLabel.setText("More than 100 matches"); + myClickToHighlightLabel.setVisible(true); + boldMatchInfo(); + } } }; private final LivePreview myLivePreview; @@ -125,6 +139,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP private boolean myIsReplace; private boolean myListeningSelection = false; + private boolean myToChangeSelection = true; @Nullable public Object getData(@NonNls final String dataId) { @@ -143,6 +158,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP myIsReplace = isReplace; + setMatchesLimit(MATCHES_LIMIT); GRADIENT_C1 = getBackground(); GRADIENT_C2 = new Color(Math.max(0, GRADIENT_C1.getRed() - 0x18), Math.max(0, GRADIENT_C1.getGreen() - 0x18), Math.max(0, GRADIENT_C1.getBlue() - 0x18)); @@ -270,7 +286,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP myClickToHighlightLabel = new LinkLabel("Click to highlight", null, new LinkListener() { @Override public void linkSelected(LinkLabel aSource, Object aLinkData) { - myMatchesLimit = Integer.MAX_VALUE; + setMatchesLimit(Integer.MAX_VALUE); updateResults(true); } }); @@ -321,6 +337,10 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP } + private void setMatchesLimit(int value) { + myLivePreviewController.setMatchesLimit(value); + } + private void configureReplacementPane() { JPanel replacement = createLeadPane(); myReplaceField = createTextField(); @@ -409,7 +429,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP searchField.getDocument().addDocumentListener(new DocumentAdapter() { protected void textChanged(final DocumentEvent e) { - myMatchesLimit = 100; + setMatchesLimit(MATCHES_LIMIT); updateResults(true); } }); @@ -447,13 +467,13 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP } private void searchBackward() { - myLivePreview.prevOccurrence(); + moveCursor(false); addCurrentTextToRecents(); } private void searchForward() { - myLivePreview.nextOccurrence(); + moveCursor(true); addCurrentTextToRecents(); } @@ -467,7 +487,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP @Override public void cursorMoved() { - if (mySelectionOnly == null || !mySelectionOnly.isSelected()) { + if (myToChangeSelection && (mySelectionOnly == null || !mySelectionOnly.isSelected())) { LiveOccurrence cursor = myLivePreview.getCursor(); if (cursor != null) { TextRange range = cursor.getPrimaryRange(); @@ -479,6 +499,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP myEditor.getCaretModel().moveToOffset(range.getStartOffset()); myEditor.getScrollingModel().scrollToCaret(ScrollType.RELATIVE); } + myToChangeSelection = false; } } @@ -488,6 +509,7 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP } public void moveCursor(boolean forwardOrBackward) { + myToChangeSelection = true; if (forwardOrBackward) { myLivePreview.nextOccurrence(); } else { @@ -512,13 +534,12 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP } private void close() { - removeCurrentHighlights(); if (myEditor.getSelectionModel().hasSelection()) { myEditor.getCaretModel().moveToOffset(myEditor.getSelectionModel().getSelectionStart()); myEditor.getSelectionModel().removeSelection(); } IdeFocusManager.getInstance(myProject).requestFocus(myEditor.getContentComponent(), false); - + myLivePreview.cleanUp(); myEditor.setHeaderComponent(null); addCurrentTextToRecents(); } @@ -554,7 +575,6 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP } private void updateResults(final boolean allowedToChangedEditorSelection) { - removeCurrentHighlights(); myMatchInfoLabel.setFont(myMatchInfoLabel.getFont().deriveFont(Font.PLAIN)); final String text = mySearchField.getText(); if (text.length() == 0) { @@ -609,41 +629,10 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP model.setGlobal(!mySelectionOnly.isSelected()); model.setPreserveCase(myPreserveCase.isEnabled() && myPreserveCase.isSelected()); } - - + myToChangeSelection = allowedToChangedEditorSelection; myLivePreviewController.setFindModel(model); myLivePreview.update(); - myLivePreview.setContinuation(new Runnable() { - @Override - public void run() { - final int count = myLivePreview.getSearchResults().size(); - if (count <= myMatchesLimit) { - myClickToHighlightLabel.setVisible(false); - - if (count > 0) { - setRegularBackground(); - if (count > 1) { - myMatchInfoLabel.setText(count + " matches"); - } - else { - myMatchInfoLabel.setText("1 match"); - } - } - else { - setNotFoundBackground(); - myMatchInfoLabel.setText("No matches"); - } - } - else { - setRegularBackground(); - myMatchInfoLabel.setText("More than 100 matches"); - myClickToHighlightLabel.setVisible(true); - boldMatchInfo(); - } - } - - }); } } @@ -689,13 +678,6 @@ public class EditorSearchComponent extends JPanel implements DataProvider, LiveP updateResults(false); } - private void removeCurrentHighlights() { - final HighlightManagerImpl highlightManager = (HighlightManagerImpl)HighlightManager.getInstance(myProject); - for (RangeHighlighter highlighter : myHighlighters) { - highlightManager.removeSegmentHighlighter(myEditor, highlighter); - } - } - public void setTextInField(final String text) { mySearchField.setText(text); updateResults(true); diff --git a/platform/lang-impl/src/com/intellij/find/impl/LiveOccurrence.java b/platform/lang-impl/src/com/intellij/find/impl/LiveOccurrence.java index 9297f07ecaeb..bef2f3c6536c 100644 --- a/platform/lang-impl/src/com/intellij/find/impl/LiveOccurrence.java +++ b/platform/lang-impl/src/com/intellij/find/impl/LiveOccurrence.java @@ -24,4 +24,14 @@ public class LiveOccurrence { public void setSecondaryRanges(Collection secondaryRanges) { this.mySecondaryRanges = secondaryRanges; } + + @Override + public boolean equals(Object o) { + if (o instanceof LiveOccurrence) { + if (myPrimaryRange.equals(((LiveOccurrence)o).getPrimaryRange())) { + return true; + } + } + return false; + } } diff --git a/platform/lang-impl/src/com/intellij/find/impl/LivePreview.java b/platform/lang-impl/src/com/intellij/find/impl/LivePreview.java index 0d9fa319333c..810b058cd234 100644 --- a/platform/lang-impl/src/com/intellij/find/impl/LivePreview.java +++ b/platform/lang-impl/src/com/intellij/find/impl/LivePreview.java @@ -384,16 +384,9 @@ public class LivePreview extends DocumentAdapter implements ReplacementView.Dele } } - private static void drawMatch(Graphics2D g2d, Point start, Point end, int lineHeight, int horizontalGap, int verticalGap) { - g2d.setColor(new Color(50, 50, 50)); - g2d.translate(0, start.y-verticalGap); - UIUtil.drawSearchMatch(g2d, start.x-horizontalGap, end.x+horizontalGap, lineHeight+2*verticalGap); - g2d.translate(0, -start.y+verticalGap); - } - private void setCursor(LiveOccurrence liveOccurrence) { hideBalloon(); - boolean toNotify = myCursor != null && !myCursor.equals(liveOccurrence); + boolean toNotify = myCursor == null || !myCursor.equals(liveOccurrence); myCursor = liveOccurrence; @@ -406,17 +399,7 @@ public class LivePreview extends DocumentAdapter implements ReplacementView.Dele highlightRange(myCursor.getPrimaryRange(), new TextAttributes(null, null, null, null, 0), dummy); if (!dummy.isEmpty()) { myCursorHighlighter = dummy.get(0); - myCursorHighlighter.setCustomRenderer(new CustomHighlighterRenderer() { - @Override - public void paint(Editor editor, RangeHighlighter highlighter, Graphics g) { - Graphics2D g2d = (Graphics2D)g; - VisualPosition startVp = editor.offsetToVisualPosition(highlighter.getStartOffset()); - VisualPosition endVp = editor.offsetToVisualPosition(highlighter.getEndOffset()); - Point start = editor.visualPositionToXY(startVp); - Point end = editor.visualPositionToXY(endVp); - drawMatch(g2d, start, end, editor.getLineHeight(), 1, 4); - } - }); + myCursorHighlighter.setCustomRenderer(new MyCustomCursorRenderer()); } if (!insideVisibleArea(myEditor, myCursor.getPrimaryRange())) { @@ -434,7 +417,9 @@ public class LivePreview extends DocumentAdapter implements ReplacementView.Dele } if (toNotify) { for (CursorListener l : myListeners) { - l.cursorMoved(); + if (l!= null) { + l.cursorMoved(); + } } } } @@ -521,4 +506,21 @@ public class LivePreview extends DocumentAdapter implements ReplacementView.Dele return visibleArea.contains(point); } + + private static class MyCustomCursorRenderer implements CustomHighlighterRenderer { + @Override + public void paint(Editor editor, RangeHighlighter highlighter, Graphics g) { + Graphics2D g2d = (Graphics2D)g; + VisualPosition startVp = editor.offsetToVisualPosition(highlighter.getStartOffset()); + VisualPosition endVp = editor.offsetToVisualPosition(highlighter.getEndOffset()); + Point start = editor.visualPositionToXY(startVp); + Point end = editor.visualPositionToXY(endVp); + g2d.setColor(new Color(50, 50, 50)); + g2d.translate(0, start.y - 4); + Color c1 = new Color(220, 200, 130); + Color c2 = new Color(220, 170, 30); + UIUtil.drawSearchMatch(g2d, start.x- 1, end.x+ 1, editor.getLineHeight() +2* 4, c1, c2); + g2d.translate(0, -start.y + 4); + } + } } diff --git a/platform/lang-impl/src/com/intellij/find/impl/LivePreviewControllerBase.java b/platform/lang-impl/src/com/intellij/find/impl/LivePreviewControllerBase.java index 7ffd7c191764..82c93f288eec 100644 --- a/platform/lang-impl/src/com/intellij/find/impl/LivePreviewControllerBase.java +++ b/platform/lang-impl/src/com/intellij/find/impl/LivePreviewControllerBase.java @@ -63,7 +63,7 @@ public class LivePreviewControllerBase implements LivePreview.Delegate { } int offset = r.getStartOffset(); VirtualFile virtualFile = FileDocumentManager.getInstance().getFile(editor.getDocument()); - ArrayList results = new ArrayList(); + final ArrayList results = new ArrayList(); while (true) { FindManager findManager = FindManager.getInstance(editor.getProject()); @@ -77,28 +77,24 @@ public class LivePreviewControllerBase implements LivePreview.Delegate { if (results.size() > myMatchesLimit) break; } if (results.size() < myMatchesLimit) { - if (results.isEmpty()) { - ApplicationManager.getApplication().invokeLater(new Runnable() { - @Override - public void run() { - notFound(); - } - }); - } + findResultsToOccurrences(results, occurrences); - } else { - ApplicationManager.getApplication().invokeLater(new Runnable() { - @Override - public void run() { - tooManyMatches(); - } - }); } + + ApplicationManager.getApplication().invokeLater(new Runnable() { + @Override + public void run() { + searchEndsWith(results.size()); + } + }); } return occurrences; } - protected void tooManyMatches() { } + protected void searchEndsWith(int size) { + + } + @Override public String getReplacementPreviewText(Editor editor, LiveOccurrence liveOccurrence) { @@ -148,8 +144,7 @@ public class LivePreviewControllerBase implements LivePreview.Delegate { @Override public Editor getEditor(Ref needToUpdate) { - return null; //To change body of implemented methods use File | Settings | File Templates. + return null; } - public void notFound() {} } diff --git a/platform/util/src/com/intellij/util/ui/UIUtil.java b/platform/util/src/com/intellij/util/ui/UIUtil.java index 0f5590c3a49b..934adf54bbe8 100644 --- a/platform/util/src/com/intellij/util/ui/UIUtil.java +++ b/platform/util/src/com/intellij/util/ui/UIUtil.java @@ -761,9 +761,15 @@ public class UIUtil { final int startX, final int endX, final int height) { + Color c1 = new Color(255, 234, 162); + Color c2 = new Color(255, 208, 66); + drawSearchMatch(g, startX, endX, height, c1, c2); + } + + public static void drawSearchMatch(Graphics2D g, int startX, int endX, int height, Color c1, Color c2) { final boolean drawRound = endX - startX > 4; - g.setPaint(new GradientPaint(startX, 2, new Color(255, 234, 162), startX, height - 5, new Color(255, 208, 66))); + g.setPaint(new GradientPaint(startX, 2, c1, startX, height - 5, c2)); g.fillRect(startX, 3, endX - startX, height - 5); if (drawRound) {