diff --git a/build/scripts/utils.gant b/build/scripts/utils.gant index a1e04fd29841..fca3be9c9fbb 100644 --- a/build/scripts/utils.gant +++ b/build/scripts/utils.gant @@ -14,6 +14,7 @@ * limitations under the License. */ + import org.jetbrains.jps.gant.JpsGantTool import org.jetbrains.jps.gant.TeamCityBuildInfoPrinter import org.jetbrains.jps.model.java.JavaSourceRootType @@ -627,6 +628,23 @@ binding.setVariable("zipSources", { String home, String targetDir -> notifyArtifactBuilt(sources) }) +binding.setVariable("zipSourcesOfModules", { String home, String targetFilePath, Collection modules -> + projectBuilder.stage("zip sources of ${modules.size()} modules to $targetFilePath") + + ant.mkdir(dir: new File(targetFilePath).getParent()) + ant.delete(file: targetFilePath) + ant.zip(destfile: targetFilePath) { + modules.each { + JpsModule module = findModule(it) + module.getSourceRoots(JavaSourceRootType.SOURCE).flatten().collect {it.file}.each { File srcRoot -> + zipfileset(prefix: module.name, dir: srcRoot.absolutePath) + } + } + } + + notifyArtifactBuilt(targetFilePath) +}) + /** * E.g. * diff --git a/images/src/org/intellij/images/thumbnail/actions/EnterAction.java b/images/src/org/intellij/images/thumbnail/actions/EnterAction.java index b608b82f97c7..d0cb098f33a4 100644 --- a/images/src/org/intellij/images/thumbnail/actions/EnterAction.java +++ b/images/src/org/intellij/images/thumbnail/actions/EnterAction.java @@ -57,7 +57,7 @@ public final class EnterAction extends AnAction { if (selection.length > 0) { if (selection.length == 1 && selection[0].isDirectory()) { presentation.setVisible(true); - } else if (selection.length > 0) { + } else { boolean notImages = false; ImageFileTypeManager typeManager = ImageFileTypeManager.getInstance(); for (VirtualFile file : selection) { @@ -65,9 +65,6 @@ public final class EnterAction extends AnAction { } presentation.setEnabled(!notImages); presentation.setVisible(false); - } else { - presentation.setVisible(false); - presentation.setEnabled(false); } } else { presentation.setVisible(false); diff --git a/java/idea-ui/src/com/intellij/framework/FrameworkGroup.java b/java/idea-ui/src/com/intellij/framework/FrameworkGroup.java index a3705c263cbd..ac8d6b63c475 100644 --- a/java/idea-ui/src/com/intellij/framework/FrameworkGroup.java +++ b/java/idea-ui/src/com/intellij/framework/FrameworkGroup.java @@ -8,6 +8,10 @@ import java.util.Collections; import java.util.List; /** + * Represents a group of frameworks. in the frameworks tree ("Additional Libraries and Frameworks" + * in the New Project dialog or the tree displayed in the "Add Framework Support" dialog). + * Frameworks in a group can have a common version number. + * * @author nik */ public abstract class FrameworkGroup implements FrameworkOrGroup { @@ -26,6 +30,10 @@ public abstract class FrameworkGroup implements Fram @NotNull public abstract Icon getIcon(); + /** + * Returns the list of known versions of the framework group. The list is shown to the user + * and allows them to choose the version used in their project. + */ @NotNull public List getGroupVersions() { return Collections.emptyList(); diff --git a/java/idea-ui/src/com/intellij/framework/FrameworkOrGroup.java b/java/idea-ui/src/com/intellij/framework/FrameworkOrGroup.java index 8265b71d4658..9b491f602a84 100644 --- a/java/idea-ui/src/com/intellij/framework/FrameworkOrGroup.java +++ b/java/idea-ui/src/com/intellij/framework/FrameworkOrGroup.java @@ -20,8 +20,11 @@ import org.jetbrains.annotations.NotNull; import javax.swing.*; /** + * Represents a single node (framework or group) in the frameworks tree ("Additional Libraries and Frameworks" + * in the New Project dialog or the tree displayed in the "Add Framework Support" dialog). + * * @author Dmitry Avdeev - * Date: 09.10.13 + * @since 09.10.13 */ public interface FrameworkOrGroup { @NotNull diff --git a/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/ContractInference.java b/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/ContractInference.java index 1fc3ea176503..7dcf36afb4ee 100644 --- a/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/ContractInference.java +++ b/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/ContractInference.java @@ -17,17 +17,12 @@ package com.intellij.codeInspection.dataFlow; import com.intellij.codeInsight.NullableNotNullManager; import com.intellij.codeInspection.dataFlow.MethodContract.ValueConstraint; -import com.intellij.openapi.roots.FileIndexFacade; import com.intellij.openapi.util.Computable; import com.intellij.openapi.util.Condition; import com.intellij.openapi.util.RecursionManager; -import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.*; import com.intellij.psi.tree.IElementType; -import com.intellij.psi.util.CachedValueProvider; -import com.intellij.psi.util.CachedValuesManager; -import com.intellij.psi.util.PsiModificationTracker; -import com.intellij.psi.util.PsiUtilCore; +import com.intellij.psi.util.*; import com.intellij.util.Function; import com.intellij.util.NullableFunction; import com.intellij.util.containers.ContainerUtil; @@ -47,10 +42,10 @@ public class ContractInference { @NotNull public static List inferContracts(@NotNull final PsiMethod method) { - if (isLibraryCode(method)) { + if (!InferenceFromSourceUtil.shouldInferFromSource(method)) { return Collections.emptyList(); } - + return CachedValuesManager.getCachedValue(method, new CachedValueProvider>() { @Nullable @Override @@ -66,12 +61,6 @@ public class ContractInference { } }); } - - static boolean isLibraryCode(@NotNull PsiMethod method) { - if (method instanceof PsiCompiledElement) return true; - VirtualFile virtualFile = PsiUtilCore.getVirtualFile(method); - return virtualFile != null && FileIndexFacade.getInstance(method.getProject()).isInLibrarySource(virtualFile); - } } class ContractInferenceInterpreter { diff --git a/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/InferenceFromSourceUtil.java b/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/InferenceFromSourceUtil.java new file mode 100644 index 000000000000..408277627937 --- /dev/null +++ b/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/InferenceFromSourceUtil.java @@ -0,0 +1,55 @@ +/* + * 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.codeInspection.dataFlow; + +import com.intellij.openapi.roots.FileIndexFacade; +import com.intellij.openapi.vfs.VirtualFile; +import com.intellij.psi.*; +import com.intellij.psi.search.LocalSearchScope; +import com.intellij.psi.search.searches.MethodReferencesSearch; +import com.intellij.psi.util.PsiUtil; +import com.intellij.psi.util.PsiUtilCore; +import org.jetbrains.annotations.NotNull; + +/** + * @author peter + */ +public class InferenceFromSourceUtil { + static boolean shouldInferFromSource(@NotNull PsiMethod method) { + if (isLibraryCode(method) || + method.hasModifierProperty(PsiModifier.ABSTRACT) || + PsiUtil.canBeOverriden(method) || + method.getBody() == null) { + return false; + } + + if (method.hasModifierProperty(PsiModifier.STATIC)) return true; + + return !isUnusedInAnonymousClass(method); + } + + private static boolean isUnusedInAnonymousClass(@NotNull PsiMethod method) { + PsiClass containingClass = method.getContainingClass(); + return containingClass instanceof PsiAnonymousClass && + MethodReferencesSearch.search(method, new LocalSearchScope(containingClass), false).findFirst() == null; + } + + private static boolean isLibraryCode(@NotNull PsiMethod method) { + if (method instanceof PsiCompiledElement) return true; + VirtualFile virtualFile = PsiUtilCore.getVirtualFile(method); + return virtualFile != null && FileIndexFacade.getInstance(method.getProject()).isInLibrarySource(virtualFile); + } +} diff --git a/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/NullityInference.java b/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/NullityInference.java index 5b79e8637678..ab02b5bf7648 100644 --- a/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/NullityInference.java +++ b/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/NullityInference.java @@ -35,7 +35,7 @@ import java.util.concurrent.atomic.AtomicBoolean; public class NullityInference { public static Nullness inferNullity(final PsiMethod method) { - if (ContractInference.isLibraryCode(method)) { + if (!InferenceFromSourceUtil.shouldInferFromSource(method)) { return Nullness.UNKNOWN; } diff --git a/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/PurityInference.java b/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/PurityInference.java index 6ceaeec72ae5..ee81e7c09fd3 100644 --- a/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/PurityInference.java +++ b/java/java-analysis-impl/src/com/intellij/codeInspection/dataFlow/PurityInference.java @@ -34,7 +34,10 @@ import java.util.List; public class PurityInference { public static boolean inferPurity(@NotNull final PsiMethod method) { - if (ContractInference.isLibraryCode(method) || method.getReturnType() == PsiType.VOID || method.getBody() == null || method.isConstructor()) { + if (!InferenceFromSourceUtil.shouldInferFromSource(method) || + method.getReturnType() == PsiType.VOID || + method.getBody() == null || + method.isConstructor()) { return false; } diff --git a/java/java-impl/src/com/intellij/codeInsight/ExternalAnnotationsLineMarkerProvider.java b/java/java-impl/src/com/intellij/codeInsight/ExternalAnnotationsLineMarkerProvider.java index b4f318de8e4b..33ca812d78d2 100644 --- a/java/java-impl/src/com/intellij/codeInsight/ExternalAnnotationsLineMarkerProvider.java +++ b/java/java-impl/src/com/intellij/codeInsight/ExternalAnnotationsLineMarkerProvider.java @@ -38,6 +38,7 @@ import com.intellij.psi.*; import com.intellij.psi.util.PsiUtilCore; import com.intellij.ui.awt.RelativePoint; import com.intellij.util.Function; +import com.intellij.util.containers.ContainerUtil; import com.intellij.xml.util.XmlStringUtil; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -50,7 +51,24 @@ public class ExternalAnnotationsLineMarkerProvider implements LineMarkerProvider private static final Function ourTooltipProvider = new Function() { @Override public String fun(PsiElement nameIdentifier) { - return XmlStringUtil.wrapInHtml(JavaDocInfoGenerator.generateSignature(nameIdentifier.getParent())); + PsiModifierListOwner owner = (PsiModifierListOwner)nameIdentifier.getParent(); + + boolean hasInferred = false; + boolean hasExternal = false; + for (PsiAnnotation annotation : findSignatureNonCodeAnnotations(owner)) { + hasExternal |= AnnotationUtil.isExternalAnnotation(annotation); + hasInferred |= AnnotationUtil.isInferredAnnotation(annotation); + } + + String header; + if (hasInferred && hasExternal) { + header = "External and inferred"; + } else if (hasInferred) { + header = "Inferred"; + } else { + header = "External"; + } + return XmlStringUtil.wrapInHtml(header + " annotations available. Full signature:

\n" + JavaDocInfoGenerator.generateSignature(owner)); } }; @@ -65,7 +83,7 @@ public class ExternalAnnotationsLineMarkerProvider implements LineMarkerProvider PsiElement nameIdentifier = ((PsiNameIdentifierOwner)owner).getNameIdentifier(); if (nameIdentifier == null || !nameIdentifier.getTextRange().equals(element.getTextRange())) return null; - if (!shouldShowSignature((PsiModifierListOwner)owner)) { + if (findSignatureNonCodeAnnotations((PsiModifierListOwner)owner).isEmpty()) { return null; } @@ -76,38 +94,35 @@ public class ExternalAnnotationsLineMarkerProvider implements LineMarkerProvider GutterIconRenderer.Alignment.RIGHT); } - private static boolean shouldShowSignature(PsiModifierListOwner owner) { - if (hasNonCodeAnnotations(owner)) { - return true; - } + private static List findSignatureNonCodeAnnotations(PsiModifierListOwner owner) { + List result = ContainerUtil.newArrayList(findOwnNonCodeAnnotations(owner)); if (owner instanceof PsiMethod) { for (PsiParameter parameter : ((PsiMethod)owner).getParameterList().getParameters()) { - if (hasNonCodeAnnotations(parameter)) { - return true; - } + result.addAll(findOwnNonCodeAnnotations(parameter)); } } - return false; + return result; } - private static boolean hasNonCodeAnnotations(@NotNull PsiModifierListOwner element) { + private static List findOwnNonCodeAnnotations(@NotNull PsiModifierListOwner element) { + List result = ContainerUtil.newArrayList(); Project project = element.getProject(); PsiAnnotation[] externalAnnotations = ExternalAnnotationsManager.getInstance(project).findExternalAnnotations(element); if (externalAnnotations != null) { for (PsiAnnotation annotation : externalAnnotations) { if (isVisibleAnnotation(annotation)) { - return true; + result.add(annotation); } } } for (PsiAnnotation annotation : InferredAnnotationsManager.getInstance(project).findInferredAnnotations(element)) { if (isVisibleAnnotation(annotation)) { - return true; + result.add(annotation); } } - return false; + return result; } private static boolean isVisibleAnnotation(@NotNull PsiAnnotation annotation) { diff --git a/java/java-impl/src/com/intellij/refactoring/convertToInstanceMethod/ConvertToInstanceMethodDialog.java b/java/java-impl/src/com/intellij/refactoring/convertToInstanceMethod/ConvertToInstanceMethodDialog.java index be2b088dd6b4..d054943e6a7f 100644 --- a/java/java-impl/src/com/intellij/refactoring/convertToInstanceMethod/ConvertToInstanceMethodDialog.java +++ b/java/java-impl/src/com/intellij/refactoring/convertToInstanceMethod/ConvertToInstanceMethodDialog.java @@ -78,4 +78,14 @@ public class ConvertToInstanceMethodDialog extends MoveInstanceMethodDialogBase }.installOn(variableChooser); return variableChooser; } + + @Override + protected String getMovePropertySuffix() { + return null; + } + + @Override + protected String getCbTitle() { + return null; + } } diff --git a/java/java-impl/src/com/intellij/refactoring/convertToInstanceMethod/ConvertToInstanceMethodProcessor.java b/java/java-impl/src/com/intellij/refactoring/convertToInstanceMethod/ConvertToInstanceMethodProcessor.java index 5804445d7141..ff362fbf3fe4 100644 --- a/java/java-impl/src/com/intellij/refactoring/convertToInstanceMethod/ConvertToInstanceMethodProcessor.java +++ b/java/java-impl/src/com/intellij/refactoring/convertToInstanceMethod/ConvertToInstanceMethodProcessor.java @@ -18,6 +18,7 @@ package com.intellij.refactoring.convertToInstanceMethod; import com.intellij.codeInsight.ChangeContextUtil; import com.intellij.history.LocalHistory; import com.intellij.history.LocalHistoryAction; +import com.intellij.ide.util.EditorHelper; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.Key; @@ -231,6 +232,7 @@ public class ConvertToInstanceMethodProcessor extends BaseRefactoringProcessor { if (!myTargetClass.isInterface()) { PsiMethod method = addMethodToClass(myTargetClass); fixVisibility(method, usages); + EditorHelper.openInEditor(method); } else { final PsiMethod interfaceMethod = addMethodToClass(myTargetClass); @@ -240,6 +242,8 @@ public class ConvertToInstanceMethodProcessor extends BaseRefactoringProcessor { modifierList.setModifierProperty(PsiModifier.PROTECTED, false); RefactoringUtil.makeMethodAbstract(myTargetClass, interfaceMethod); + EditorHelper.openInEditor(interfaceMethod); + for (final PsiClass psiClass : inheritors) { final PsiMethod newMethod = addMethodToClass(psiClass); PsiUtil.setModifierProperty(newMethod, myNewVisibility != null && !myNewVisibility.equals(VisibilityUtil.ESCALATE_VISIBILITY) ? myNewVisibility diff --git a/java/java-impl/src/com/intellij/refactoring/move/MoveDialogBase.java b/java/java-impl/src/com/intellij/refactoring/move/MoveDialogBase.java new file mode 100644 index 000000000000..256aacb6876f --- /dev/null +++ b/java/java-impl/src/com/intellij/refactoring/move/MoveDialogBase.java @@ -0,0 +1,55 @@ +/* + * 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.refactoring.move; + +import com.intellij.ide.util.PropertiesComponent; +import com.intellij.openapi.project.Project; +import com.intellij.refactoring.ui.RefactoringDialog; +import org.jetbrains.annotations.NotNull; + +import javax.swing.*; + +public abstract class MoveDialogBase extends RefactoringDialog { + + private JCheckBox myOpenEditorCb; + + protected abstract String getMovePropertySuffix(); + protected abstract String getCbTitle(); + + protected JCheckBox initOpenInEditorCb() { + myOpenEditorCb = new JCheckBox(getCbTitle(), PropertiesComponent.getInstance().getBoolean("Move" + getMovePropertySuffix() +".OpenInEditor", + isEnabledByDefault())); + return myOpenEditorCb; + } + + protected boolean isEnabledByDefault() { + return true; + } + + protected void saveOpenInEditorOption() { + if (myOpenEditorCb != null) { + PropertiesComponent.getInstance().setValue("Move" + getMovePropertySuffix() +".OpenInEditor", String.valueOf(myOpenEditorCb.isSelected())); + } + } + + protected boolean isOpenInEditor() { + return myOpenEditorCb != null && myOpenEditorCb.isSelected(); + } + + protected MoveDialogBase(@NotNull Project project, boolean canBeParent) { + super(project, canBeParent); + } +} diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassToInnerProcessor.java b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassToInnerProcessor.java index 48ab4c42887a..03739a7ab5d1 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassToInnerProcessor.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassToInnerProcessor.java @@ -15,6 +15,7 @@ */ package com.intellij.refactoring.move.moveClassesOrPackages; +import com.intellij.ide.util.EditorHelper; import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.project.Project; @@ -39,6 +40,7 @@ import com.intellij.util.Function; import com.intellij.util.IncorrectOperationException; import com.intellij.util.Processor; import com.intellij.util.VisibilityUtil; +import com.intellij.util.containers.ContainerUtil; import com.intellij.util.containers.MultiMap; import org.jetbrains.annotations.NotNull; @@ -60,6 +62,7 @@ public class MoveClassToInnerProcessor extends BaseRefactoringProcessor { private final boolean mySearchInNonJavaFiles; private NonCodeUsageInfo[] myNonCodeUsages; private final MoveCallback myMoveCallback; + private boolean myOpenInEditor; public MoveClassToInnerProcessor(Project project, final PsiClass[] classesToMove, @@ -167,6 +170,13 @@ public class MoveClassToInnerProcessor extends BaseRefactoringProcessor { element.delete(); } } + + if (myOpenInEditor && !oldToNewElementsMapping.isEmpty()) { + final PsiElement item = ContainerUtil.getFirstItem(oldToNewElementsMapping.values()); + if (item != null) { + EditorHelper.openInEditor(item); + } + } } catch (IncorrectOperationException e) { LOG.error(e); @@ -324,6 +334,10 @@ public class MoveClassToInnerProcessor extends BaseRefactoringProcessor { }); } + public void setOpenInEditor(boolean openInEditor) { + myOpenInEditor = openInEditor; + } + private static class ConflictsCollector { private final PsiClass myClassToMove; private final MultiMap myConflicts; diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesDialog.form b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesDialog.form index a69d2e872668..60a7d8d5e2a8 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesDialog.form +++ b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesDialog.form @@ -112,7 +112,7 @@ - + @@ -135,6 +135,14 @@ + + + + + + + + diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesDialog.java b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesDialog.java index 3bbcf743506c..e0d206e733c1 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesDialog.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesDialog.java @@ -39,6 +39,7 @@ import com.intellij.psi.util.PsiUtilCore; import com.intellij.refactoring.*; import com.intellij.refactoring.move.MoveCallback; import com.intellij.refactoring.move.MoveClassesOrPackagesCallback; +import com.intellij.refactoring.move.MoveDialogBase; import com.intellij.refactoring.move.MoveHandler; import com.intellij.refactoring.move.moveFilesOrDirectories.MoveFilesOrDirectoriesUtil; import com.intellij.refactoring.ui.ClassNameReferenceEditor; @@ -64,7 +65,7 @@ import java.awt.event.ActionListener; import java.util.List; import java.util.Set; -public class MoveClassesOrPackagesDialog extends RefactoringDialog { +public class MoveClassesOrPackagesDialog extends MoveDialogBase { @NonNls private static final String RECENTS_KEY = "MoveClassesOrPackagesDialog.RECENTS_KEY"; private final PsiElement[] myElementsToMove; private final MoveCallback myMoveCallback; @@ -90,6 +91,7 @@ public class MoveClassesOrPackagesDialog extends RefactoringDialog { private ComboboxWithBrowseButton myDestinationFolderCB; private JPanel myTargetPanel; private JLabel myTargetDestinationLabel; + private JPanel myOpenInEditorPanel; private boolean myHavePackages; private boolean myTargetDirectoryFixed; private boolean mySuggestToMoveToAnotherRoot; @@ -138,6 +140,13 @@ public class MoveClassesOrPackagesDialog extends RefactoringDialog { myInnerClassChooser.requestFocus(); } }); + + for (PsiElement element : elementsToMove) { + if (element.getContainingFile() != null) { + myOpenInEditorPanel.add(initOpenInEditorCb(), BorderLayout.EAST); + break; + } + } } private void updateControlsEnabled() { @@ -376,6 +385,7 @@ public class MoveClassesOrPackagesDialog extends RefactoringDialog { } protected void doAction() { + saveOpenInEditorOption(); if (isMoveToPackage()) { invokeMoveToPackage(); } @@ -419,6 +429,7 @@ public class MoveClassesOrPackagesDialog extends RefactoringDialog { MoveClassesOrPackagesProcessor processor = createMoveToPackageProcessor(destination, myElementsToMove, myMoveCallback); if (processor.verifyValidPackageName()) { + processor.setOpenInEditor(isOpenInEditor()); invokeRefactoring(processor); } } @@ -476,7 +487,9 @@ public class MoveClassesOrPackagesDialog extends RefactoringDialog { for (int i = 0; i < myElementsToMove.length; i++) { classesToMove[i] = (PsiClass)myElementsToMove[i]; } - invokeRefactoring(createMoveToInnerProcessor(targetClass, classesToMove, myMoveCallback)); + final MoveClassToInnerProcessor processor = createMoveToInnerProcessor(targetClass, classesToMove, myMoveCallback); + processor.setOpenInEditor(isOpenInEditor()); + invokeRefactoring(processor); } //for scala plugin @@ -510,4 +523,14 @@ public class MoveClassesOrPackagesDialog extends RefactoringDialog { private List getSourceRoots() { return JavaProjectRootsUtil.getSuitableDestinationSourceRoots(myProject); } + + @Override + protected String getMovePropertySuffix() { + return "Class"; + } + + @Override + protected String getCbTitle() { + return "Open moved in editor"; + } } diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesProcessor.java b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesProcessor.java index 54ddf03a5c57..1d4548b23abf 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesProcessor.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesProcessor.java @@ -15,6 +15,7 @@ */ package com.intellij.refactoring.move.moveClassesOrPackages; +import com.intellij.ide.util.EditorHelper; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.extensions.Extensions; import com.intellij.openapi.project.Project; @@ -71,6 +72,7 @@ public class MoveClassesOrPackagesProcessor extends BaseRefactoringProcessor { private final MoveCallback myMoveCallback; protected @NotNull final MoveDestination myMoveDestination; protected NonCodeUsageInfo[] myNonCodeUsages; + private boolean myOpenInEditor; public MoveClassesOrPackagesProcessor(Project project, PsiElement[] elements, @@ -203,6 +205,10 @@ public class MoveClassesOrPackagesProcessor extends BaseRefactoringProcessor { return myMoveDestination.getTargetPackage(); } + public void setOpenInEditor(boolean openInEditor) { + myOpenInEditor = openInEditor; + } + protected static class ConflictsUsageInfo extends UsageInfo { private final Collection myConflicts; @@ -540,6 +546,15 @@ public class MoveClassesOrPackagesProcessor extends BaseRefactoringProcessor { } myNonCodeUsages = CommonMoveUtil.retargetUsages(usages, oldToNewElementsMapping); + + if (myOpenInEditor) { + for (PsiElement element : myElementsToMove) { + if (element.getContainingFile() != null) { + EditorHelper.openInEditor(element); + break; + } + } + } } catch (IncorrectOperationException e) { myNonCodeUsages = new NonCodeUsageInfo[0]; diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesToNewDirectoryDialog.java b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesToNewDirectoryDialog.java index 2640b2492a34..b70564343ac1 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesToNewDirectoryDialog.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesToNewDirectoryDialog.java @@ -33,6 +33,7 @@ import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.*; import com.intellij.refactoring.*; import com.intellij.refactoring.move.MoveCallback; +import com.intellij.refactoring.move.MoveDialogBase; import com.intellij.refactoring.move.MoveHandler; import com.intellij.refactoring.ui.RefactoringDialog; import com.intellij.ui.DocumentAdapter; @@ -43,6 +44,7 @@ import org.jetbrains.annotations.Nullable; import javax.swing.*; import javax.swing.event.DocumentEvent; +import java.awt.*; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.util.HashSet; @@ -51,7 +53,7 @@ import java.util.Set; /** * @author ven */ -public class MoveClassesOrPackagesToNewDirectoryDialog extends RefactoringDialog { +public class MoveClassesOrPackagesToNewDirectoryDialog extends MoveDialogBase { private static final Logger LOG = Logger.getInstance("com.intellij.refactoring.move.moveClassesOrPackages.MoveClassesToNewDirectoryDialog"); private final PsiDirectory myDirectory; @@ -124,6 +126,12 @@ public class MoveClassesOrPackagesToNewDirectoryDialog extends RefactoringDialog myPreserveSourceRoot.setSelected(sameModule); } init(); + for (PsiElement element : elementsToMove) { + if (element.getContainingFile() != null) { + myOpenInEditor.add(initOpenInEditorCb(), BorderLayout.WEST); + break; + } + } } private TextFieldWithBrowseButton myDestDirectoryField; @@ -132,6 +140,7 @@ public class MoveClassesOrPackagesToNewDirectoryDialog extends RefactoringDialog private JPanel myRootPanel; private JLabel myNameLabel; private JCheckBox myPreserveSourceRoot; + private JPanel myOpenInEditor; private boolean isSearchInNonJavaFiles() { return mySearchForTextOccurrencesCheckBox.isSelected(); @@ -179,6 +188,7 @@ public class MoveClassesOrPackagesToNewDirectoryDialog extends RefactoringDialog final boolean searchForTextOccurences = isSearchInNonJavaFiles(); refactoringSettings.MOVE_SEARCH_IN_COMMENTS = searchInComments; refactoringSettings.MOVE_SEARCH_FOR_TEXT = searchForTextOccurences; + saveOpenInEditorOption(); invokeRefactoring(createRefactoringProcessor(project, directory, aPackage, searchInComments, searchForTextOccurences)); } @@ -218,12 +228,28 @@ public class MoveClassesOrPackagesToNewDirectoryDialog extends RefactoringDialog MoveClassesOrPackagesProcessor processor = createMoveClassesOrPackagesProcessor(myDirectory.getProject(), myElementsToMove, destination, searchInComments, searchForTextOccurences, myMoveCallback); - + + processor.setOpenInEditor(isOpenInEditor()); if (processor.verifyValidPackageName()) { return processor; } return null; } + + @Override + protected String getMovePropertySuffix() { + return "ClassWithTarget"; + } + + @Override + protected String getCbTitle() { + return "Open moved classes in editor"; + } + + @Override + protected boolean isEnabledByDefault() { + return false; + } } diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesToNewDirectoryForm.form b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesToNewDirectoryForm.form index 75f157521894..069ddf6153db 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesToNewDirectoryForm.form +++ b/java/java-impl/src/com/intellij/refactoring/move/moveClassesOrPackages/MoveClassesOrPackagesToNewDirectoryForm.form @@ -1,9 +1,9 @@

- + - + @@ -69,9 +69,17 @@ - + + + + + + + + + diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerDialog.form b/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerDialog.form index 7e30dc6901cc..8fb954645c7b 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerDialog.form +++ b/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerDialog.form @@ -1,6 +1,6 @@ - + @@ -23,7 +23,7 @@ - + @@ -89,6 +89,14 @@ + + + + + + + + diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerDialog.java b/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerDialog.java index cb502377f83b..71539abd98c0 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerDialog.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerDialog.java @@ -20,6 +20,7 @@ */ package com.intellij.refactoring.move.moveInner; +import com.intellij.ide.util.PropertiesComponent; import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.help.HelpManager; import com.intellij.openapi.project.Project; @@ -37,6 +38,7 @@ import com.intellij.refactoring.HelpID; import com.intellij.refactoring.JavaRefactoringSettings; import com.intellij.refactoring.PackageWrapper; import com.intellij.refactoring.RefactoringBundle; +import com.intellij.refactoring.move.MoveDialogBase; import com.intellij.refactoring.move.MoveInstanceMembersUtil; import com.intellij.refactoring.move.moveClassesOrPackages.MoveClassesOrPackagesUtil; import com.intellij.refactoring.ui.NameSuggestionsField; @@ -52,13 +54,14 @@ import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import javax.swing.*; +import java.awt.*; import java.awt.event.ItemEvent; import java.awt.event.ItemListener; import java.util.List; import java.util.Map; import java.util.Set; -public class MoveInnerDialog extends RefactoringDialog { +public class MoveInnerDialog extends MoveDialogBase { private final Project myProject; private final PsiClass myInnerClass; private final PsiElement myTargetContainer; @@ -74,11 +77,22 @@ public class MoveInnerDialog extends RefactoringDialog { private JLabel myPackageNameLabel; private JLabel myClassNameLabel; private JLabel myParameterNameLabel; + private JPanel myOpenInEditorPanel; private SuggestedNameInfo mySuggestedNameInfo; private final PsiClass myOuterClass; @NonNls private static final String RECENTS_KEY = "MoveInnerDialog.RECENTS_KEY"; + @Override + protected String getMovePropertySuffix() { + return "Inner"; + } + + @Override + protected String getCbTitle() { + return "Open moved member in editor"; + } + public MoveInnerDialog(Project project, PsiClass innerClass, MoveInnerProcessor processor, final PsiElement targetContainer) { super(project, true); myProject = project; @@ -91,6 +105,7 @@ public class MoveInnerDialog extends RefactoringDialog { myPackageNameLabel.setLabelFor(myPackageNameField.getChildComponent()); myClassNameLabel.setLabelFor(myClassNameField); myParameterNameLabel.setLabelFor(myParameterField); + myOpenInEditorPanel.add(initOpenInEditorCb(), BorderLayout.EAST); } public boolean isSearchInComments() { @@ -297,6 +312,10 @@ public class MoveInnerDialog extends RefactoringDialog { if (target == null) return; myProcessor.setup(getInnerClass(), className, isPassOuterClass(), parameterName, isSearchInComments(), isSearchInNonJavaFiles(), target); + + final boolean openInEditor = isOpenInEditor(); + saveOpenInEditorOption(); + myProcessor.setOpenInEditor(openInEditor); invokeRefactoring(myProcessor); } diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerProcessor.java b/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerProcessor.java index d56b8c02844e..a95d6ef78a7f 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerProcessor.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveInner/MoveInnerProcessor.java @@ -17,6 +17,7 @@ package com.intellij.refactoring.move.moveInner; import com.intellij.codeInsight.ChangeContextUtil; import com.intellij.codeInsight.CodeInsightUtilCore; +import com.intellij.ide.util.EditorHelper; import com.intellij.lang.findUsages.DescriptiveNameUtil; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.fileEditor.FileEditorManager; @@ -70,6 +71,7 @@ public class MoveInnerProcessor extends BaseRefactoringProcessor { private boolean mySearchInComments; private boolean mySearchInNonJavaFiles; private NonCodeUsageInfo[] myNonCodeUsages; + private boolean myOpenInEditor; public MoveInnerProcessor(Project project, MoveCallback moveCallback) { super(project); @@ -267,9 +269,9 @@ public class MoveInnerProcessor extends BaseRefactoringProcessor { ChangeContextUtil.decodeContextInfo(newClass, null, null); } - PsiFile targetFile = newClass.getContainingFile(); - OpenFileDescriptor descriptor = new OpenFileDescriptor(myProject, targetFile.getVirtualFile(), newClass.getTextOffset()); - FileEditorManager.getInstance(myProject).openTextEditor(descriptor, true); + if (myOpenInEditor) { + EditorHelper.openInEditor(newClass); + } if (myMoveCallback != null) { myMoveCallback.refactoringCompleted(); @@ -530,4 +532,8 @@ public class MoveInnerProcessor extends BaseRefactoringProcessor { public String getParameterName() { return myParameterNameOuterClass; } + + public void setOpenInEditor(boolean openInEditor) { + myOpenInEditor = openInEditor; + } } \ No newline at end of file diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodDialog.java b/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodDialog.java index 1c058d2fe855..7a82ff79d60f 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodDialog.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodDialog.java @@ -85,6 +85,8 @@ public class MoveInstanceMethodDialog extends MoveInstanceMethodDialogBase { mainPanel.add(parametersPanel, new GridBagConstraints(0, GridBagConstraints.RELATIVE, 1, 1, 1.0, 0.0, GridBagConstraints.WEST, GridBagConstraints.HORIZONTAL, new Insets(0,0,0,0), 0,0)); } + mainPanel.add(initOpenInEditorCb(), new GridBagConstraints(0, GridBagConstraints.RELATIVE, 1, 1, 1, 0, GridBagConstraints.EAST, GridBagConstraints.HORIZONTAL, new Insets(0,0,0,0), 0,0)); + separator.setLabelFor(myList); validateTextFields(myList.getSelectedIndex()); @@ -148,8 +150,10 @@ public class MoveInstanceMethodDialog extends MoveInstanceMethodDialogBase { final MoveInstanceMethodProcessor processor = new MoveInstanceMethodProcessor(myMethod.getProject(), myMethod, targetVariable, myVisibilityPanel.getVisibility(), + isOpenInEditor(), parameterNames); if (!verifyTargetClass(processor.getTargetClass())) return; + saveOpenInEditorOption(); invokeRefactoring(processor); } @@ -167,4 +171,14 @@ public class MoveInstanceMethodDialog extends MoveInstanceMethodDialogBase { protected void doHelpAction() { HelpManager.getInstance().invokeHelp(HelpID.MOVE_INSTANCE_METHOD); } + + @Override + protected String getMovePropertySuffix() { + return "Instance"; + } + + @Override + protected String getCbTitle() { + return "Open moved method in editor"; + } } diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodDialogBase.java b/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodDialogBase.java index b839f3bdfe0d..a02fceb859d2 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodDialogBase.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodDialogBase.java @@ -25,6 +25,7 @@ import com.intellij.psi.PsiVariable; import com.intellij.psi.search.searches.ClassInheritorsSearch; import com.intellij.psi.util.PsiFormatUtil; import com.intellij.refactoring.RefactoringBundle; +import com.intellij.refactoring.move.MoveDialogBase; import com.intellij.refactoring.ui.JavaVisibilityPanel; import com.intellij.refactoring.ui.RefactoringDialog; import com.intellij.ui.ScrollPaneFactory; @@ -38,7 +39,7 @@ import java.awt.*; /** * @author dsl */ -public abstract class MoveInstanceMethodDialogBase extends RefactoringDialog { +public abstract class MoveInstanceMethodDialogBase extends MoveDialogBase { protected final PsiMethod myMethod; protected final PsiVariable[] myVariables; diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodProcessor.java b/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodProcessor.java index ca844f0a5bb9..3aa806ed98f8 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodProcessor.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveInstanceMethod/MoveInstanceMethodProcessor.java @@ -17,6 +17,7 @@ package com.intellij.refactoring.move.moveInstanceMethod; import com.intellij.codeInsight.ChangeContextUtil; import com.intellij.codeInsight.generation.OverrideImplementUtil; +import com.intellij.ide.util.EditorHelper; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.Comparing; @@ -62,16 +63,27 @@ public class MoveInstanceMethodProcessor extends BaseRefactoringProcessor{ private PsiVariable myTargetVariable; private PsiClass myTargetClass; private final String myNewVisibility; + private final boolean myOpenInEditor; private final Map myOldClassParameterNames; + public MoveInstanceMethodProcessor(final Project project, + final PsiMethod method, + final PsiVariable targetVariable, + final String newVisibility, + final Map oldClassParameterNames) { + this(project, method, targetVariable, newVisibility, false, oldClassParameterNames); + } + public MoveInstanceMethodProcessor(final Project project, final PsiMethod method, final PsiVariable targetVariable, final String newVisibility, + boolean openInEditor, final Map oldClassParameterNames) { super(project); myMethod = method; myTargetVariable = targetVariable; + myOpenInEditor = openInEditor; myOldClassParameterNames = oldClassParameterNames; LOG.assertTrue(myTargetVariable instanceof PsiParameter || myTargetVariable instanceof PsiField); LOG.assertTrue(myTargetVariable.getType() instanceof PsiClassType); @@ -247,6 +259,10 @@ public class MoveInstanceMethodProcessor extends BaseRefactoringProcessor{ reference.bindToElement(method); } VisibilityUtil.fixVisibility(UsageViewUtil.toElements(usages), method, myNewVisibility); + + if (myOpenInEditor) { + EditorHelper.openInEditor(method); + } } catch (IncorrectOperationException e) { LOG.error(e); diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveMembers/MoveMembersDialog.java b/java/java-impl/src/com/intellij/refactoring/move/moveMembers/MoveMembersDialog.java index a8daa9e733fe..f5eb13ce7376 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveMembers/MoveMembersDialog.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveMembers/MoveMembersDialog.java @@ -15,10 +15,7 @@ */ package com.intellij.refactoring.move.moveMembers; -import com.intellij.ide.util.ClassFilter; -import com.intellij.ide.util.PackageUtil; -import com.intellij.ide.util.TreeClassChooser; -import com.intellij.ide.util.TreeClassChooserFactory; +import com.intellij.ide.util.*; import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.command.CommandProcessor; import com.intellij.openapi.editor.event.DocumentAdapter; @@ -38,6 +35,7 @@ import com.intellij.refactoring.JavaRefactoringSettings; import com.intellij.refactoring.RefactoringBundle; import com.intellij.refactoring.classMembers.MemberInfoChange; import com.intellij.refactoring.move.MoveCallback; +import com.intellij.refactoring.move.MoveDialogBase; import com.intellij.refactoring.ui.JavaVisibilityPanel; import com.intellij.refactoring.ui.MemberSelectionPanel; import com.intellij.refactoring.ui.MemberSelectionTable; @@ -61,7 +59,7 @@ import java.util.Collection; import java.util.List; import java.util.Set; -public class MoveMembersDialog extends RefactoringDialog implements MoveMembersOptions { +public class MoveMembersDialog extends MoveDialogBase implements MoveMembersOptions { @NonNls private static final String RECENTS_KEY = "MoveMembersDialog.RECENTS_KEY"; private MyMemberInfoModel myMemberInfoModel; @@ -76,6 +74,16 @@ public class MoveMembersDialog extends RefactoringDialog implements MoveMembersO JavaVisibilityPanel myVisibilityPanel; private final JCheckBox myIntroduceEnumConstants = new JCheckBox(RefactoringBundle.message("move.enum.constant.cb"), true); + @Override + protected String getMovePropertySuffix() { + return "Member"; + } + + @Override + protected String getCbTitle() { + return "Open moved members in editor"; + } + public MoveMembersDialog(Project project, PsiClass sourceClass, final PsiClass initialTargetClass, @@ -195,6 +203,7 @@ public class MoveMembersDialog extends RefactoringDialog implements MoveMembersO myVisibilityPanel = new JavaVisibilityPanel(true, true); myVisibilityPanel.setVisibility(null); panel.add(myVisibilityPanel, BorderLayout.EAST); + panel.add(initOpenInEditorCb(), BorderLayout.SOUTH); return panel; } @@ -246,8 +255,9 @@ public class MoveMembersDialog extends RefactoringDialog implements MoveMembersO public String getTargetClassName() { return MoveMembersDialog.this.getTargetClassName(); } - })); + }, isOpenInEditor())); + saveOpenInEditorOption(); JavaRefactoringSettings.getInstance().MOVE_PREVIEW_USAGES = isPreviewUsages(); } diff --git a/java/java-impl/src/com/intellij/refactoring/move/moveMembers/MoveMembersProcessor.java b/java/java-impl/src/com/intellij/refactoring/move/moveMembers/MoveMembersProcessor.java index cc594a37c107..3e7dba171d64 100644 --- a/java/java-impl/src/com/intellij/refactoring/move/moveMembers/MoveMembersProcessor.java +++ b/java/java-impl/src/com/intellij/refactoring/move/moveMembers/MoveMembersProcessor.java @@ -15,6 +15,7 @@ */ package com.intellij.refactoring.move.moveMembers; +import com.intellij.ide.util.EditorHelper; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.Ref; @@ -56,6 +57,7 @@ public class MoveMembersProcessor extends BaseRefactoringProcessor { private PsiClass myTargetClass; private final Set myMembersToMove = new LinkedHashSet(); private final MoveCallback myMoveCallback; + private final boolean myOpenInEditor; private String myNewVisibility; // "null" means "as is" private String myCommandName = MoveMembersImpl.REFACTORING_NAME; private MoveMembersOptions myOptions; @@ -65,8 +67,13 @@ public class MoveMembersProcessor extends BaseRefactoringProcessor { } public MoveMembersProcessor(Project project, @Nullable MoveCallback moveCallback, MoveMembersOptions options) { + this(project, moveCallback, options, false); + } + + public MoveMembersProcessor(Project project, @Nullable MoveCallback moveCallback, MoveMembersOptions options, boolean openInEditor) { super(project); myMoveCallback = moveCallback; + myOpenInEditor = openInEditor; setOptions(options); } @@ -231,6 +238,13 @@ public class MoveMembersProcessor extends BaseRefactoringProcessor { if (myMoveCallback != null) { myMoveCallback.refactoringCompleted(); } + + if (myOpenInEditor && !movedMembers.isEmpty()) { + final PsiMember item = ContainerUtil.getFirstItem(movedMembers.values()); + if (item != null) { + EditorHelper.openInEditor(item); + } + } } catch (IncorrectOperationException e) { LOG.error(e); diff --git a/java/java-psi-api/src/com/intellij/psi/augment/PsiAugmentProvider.java b/java/java-psi-api/src/com/intellij/psi/augment/PsiAugmentProvider.java index b404c94b83d2..98df2e44e4c7 100644 --- a/java/java-psi-api/src/com/intellij/psi/augment/PsiAugmentProvider.java +++ b/java/java-psi-api/src/com/intellij/psi/augment/PsiAugmentProvider.java @@ -15,6 +15,7 @@ */ package com.intellij.psi.augment; +import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.extensions.ExtensionPointName; import com.intellij.openapi.extensions.Extensions; import com.intellij.psi.PsiElement; @@ -29,6 +30,7 @@ import java.util.List; public abstract class PsiAugmentProvider { + private static final Logger LOG = Logger.getInstance("#" + PsiAugmentProvider.class.getName()); public static final ExtensionPointName EP_NAME = ExtensionPointName.create("com.intellij.lang.psiAugmentProvider"); @NotNull @@ -64,9 +66,14 @@ public abstract class PsiAugmentProvider { @Nullable public static PsiType getInferredType(PsiTypeElement typeElement) { for (PsiAugmentProvider provider : Extensions.getExtensions(EP_NAME)) { - final PsiType type = provider.inferType(typeElement); - if (type != null) { - return type; + try { + final PsiType type = provider.inferType(typeElement); + if (type != null) { + return type; + } + } + catch (Exception e) { + LOG.error("provider: " + provider, e); } } return null; diff --git a/java/java-psi-impl/src/com/intellij/psi/impl/JavaPsiFacadeImpl.java b/java/java-psi-impl/src/com/intellij/psi/impl/JavaPsiFacadeImpl.java index bf75430563ed..e623f0714deb 100644 --- a/java/java-psi-impl/src/com/intellij/psi/impl/JavaPsiFacadeImpl.java +++ b/java/java-psi-impl/src/com/intellij/psi/impl/JavaPsiFacadeImpl.java @@ -16,16 +16,11 @@ package com.intellij.psi.impl; import com.intellij.openapi.Disposable; -import com.intellij.openapi.application.ReadActionProcessor; import com.intellij.openapi.progress.ProgressIndicatorProvider; -import com.intellij.openapi.project.DumbAware; import com.intellij.openapi.project.DumbService; import com.intellij.openapi.project.Project; -import com.intellij.openapi.roots.FileIndexFacade; -import com.intellij.openapi.roots.PackageIndex; import com.intellij.openapi.util.Comparing; import com.intellij.openapi.util.text.StringUtil; -import com.intellij.openapi.vfs.VirtualFile; import com.intellij.openapi.vfs.VirtualFileFilter; import com.intellij.psi.*; import com.intellij.psi.impl.file.impl.JavaFileManager; @@ -34,19 +29,15 @@ import com.intellij.psi.impl.source.JavaDummyHolder; import com.intellij.psi.impl.source.JavaDummyHolderFactory; import com.intellij.psi.impl.source.resolve.FileContextUtil; import com.intellij.psi.search.GlobalSearchScope; -import com.intellij.psi.stubs.StubTreeLoader; import com.intellij.psi.util.PsiModificationTracker; -import com.intellij.psi.util.PsiUtilCore; import com.intellij.reference.SoftReference; import com.intellij.util.ConcurrencyUtil; import com.intellij.util.Processor; import com.intellij.util.SmartList; import com.intellij.util.containers.ContainerUtil; -import com.intellij.util.containers.HashMap; import com.intellij.util.messages.MessageBus; import gnu.trove.THashSet; import org.jetbrains.annotations.NotNull; -import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.TestOnly; import java.util.*; @@ -94,7 +85,7 @@ public class JavaPsiFacadeImpl extends JavaPsiFacadeEx { public PsiClass findClass(@NotNull final String qualifiedName, @NotNull GlobalSearchScope scope) { ProgressIndicatorProvider.checkCanceled(); // We hope this method is being called often enough to cancel daemon processes smoothly - if (DumbService.getInstance(getProject()).isDumb()) { + if (shouldUseSlowResolve()) { PsiClass[] classes = findClassesInDumbMode(qualifiedName, scope); if (classes.length != 0) { return classes[0]; @@ -134,7 +125,7 @@ public class JavaPsiFacadeImpl extends JavaPsiFacadeEx { @Override @NotNull public PsiClass[] findClasses(@NotNull String qualifiedName, @NotNull GlobalSearchScope scope) { - if (DumbService.getInstance(getProject()).isDumb()) { + if (shouldUseSlowResolve()) { return findClassesInDumbMode(qualifiedName, scope); } @@ -147,6 +138,11 @@ public class JavaPsiFacadeImpl extends JavaPsiFacadeEx { return classes.toArray(new PsiClass[classes.size()]); } + private boolean shouldUseSlowResolve() { + DumbService dumbService = DumbService.getInstance(getProject()); + return dumbService.isDumb() && dumbService.isAlternativeResolveEnabled(); + } + @NotNull private PsiElementFinder[] finders() { PsiElementFinder[] answer = myElementFinders; @@ -161,7 +157,6 @@ public class JavaPsiFacadeImpl extends JavaPsiFacadeEx { @NotNull private PsiElementFinder[] calcFinders() { List elementFinders = new ArrayList(); - elementFinders.add(new PsiElementFinderImpl()); ContainerUtil.addAll(elementFinders, myProject.getExtensions(PsiElementFinder.EP_NAME)); return elementFinders.toArray(new PsiElementFinder[elementFinders.size()]); } @@ -274,146 +269,6 @@ public class JavaPsiFacadeImpl extends JavaPsiFacadeEx { return result.values().toArray(new PsiPackage[result.size()]); } - public PsiClass[] findClassByShortName(String name, PsiPackage psiPackage, GlobalSearchScope scope) { - List result = null; - for (PsiElementFinder finder : filteredFinders()) { - PsiClass[] classes = finder.getClasses(name, psiPackage, scope); - if (classes.length == 0) continue; - if (result == null) result = new ArrayList(); - ContainerUtil.addAll(result, classes); - } - - return result == null ? PsiClass.EMPTY_ARRAY : result.toArray(new PsiClass[result.size()]); - } - - private class PsiElementFinderImpl extends PsiElementFinder implements DumbAware { - @Override - public PsiClass findClass(@NotNull String qualifiedName, @NotNull GlobalSearchScope scope) { - return myFileManager.findClass(qualifiedName, scope); - } - - @Override - @NotNull - public PsiClass[] findClasses(@NotNull String qualifiedName, @NotNull GlobalSearchScope scope) { - return myFileManager.findClasses(qualifiedName, scope); - } - - @Override - public PsiPackage findPackage(@NotNull String qualifiedName) { - return myFileManager.findPackage(qualifiedName); - } - - @Override - @NotNull - public PsiPackage[] getSubPackages(@NotNull PsiPackage psiPackage, @NotNull GlobalSearchScope scope) { - final Map packagesMap = new HashMap(); - final String qualifiedName = psiPackage.getQualifiedName(); - for (PsiDirectory dir : psiPackage.getDirectories(scope)) { - PsiDirectory[] subDirs = dir.getSubdirectories(); - for (PsiDirectory subDir : subDirs) { - final PsiPackage aPackage = JavaDirectoryService.getInstance().getPackage(subDir); - if (aPackage != null) { - final String subQualifiedName = aPackage.getQualifiedName(); - if (subQualifiedName.startsWith(qualifiedName) && !packagesMap.containsKey(subQualifiedName)) { - packagesMap.put(aPackage.getQualifiedName(), aPackage); - } - } - } - } - - packagesMap.remove(qualifiedName); // avoid SOE caused by returning a package as a subpackage of itself - return packagesMap.values().toArray(new PsiPackage[packagesMap.size()]); - } - - @Override - @NotNull - public PsiClass[] getClasses(@NotNull PsiPackage psiPackage, @NotNull final GlobalSearchScope scope) { - return getClasses(null, psiPackage, scope); - } - - @Override - @NotNull - public PsiClass[] getClasses(@Nullable String shortName, @NotNull PsiPackage psiPackage, @NotNull final GlobalSearchScope scope) { - List list = null; - String packageName = psiPackage.getQualifiedName(); - for (PsiDirectory dir : psiPackage.getDirectories(scope)) { - PsiClass[] classes = JavaDirectoryService.getInstance().getClasses(dir); - if (classes.length == 0) continue; - if (list == null) list = new ArrayList(); - for (PsiClass aClass : classes) { - // class file can be located in wrong place inside file system - String qualifiedName = aClass.getQualifiedName(); - if (qualifiedName != null) qualifiedName = StringUtil.getPackageName(qualifiedName); - if (Comparing.strEqual(qualifiedName, packageName)) { - if (shortName == null || shortName.equals(aClass.getName())) list.add(aClass); - } - } - } - if (list == null) { - return PsiClass.EMPTY_ARRAY; - } - - if (list.size() > 1) { - ContainerUtil.quickSort(list, new Comparator() { - @Override - public int compare(PsiClass o1, PsiClass o2) { - VirtualFile file1 = PsiUtilCore.getVirtualFile(o1); - VirtualFile file2 = PsiUtilCore.getVirtualFile(o2); - return file1 == null ? file2 == null ? 0 : -1 : file2 == null ? 1 : scope.compare(file2, file1); - } - }); - } - - return list.toArray(new PsiClass[list.size()]); - } - - @NotNull - @Override - public Set getClassNames(@NotNull PsiPackage psiPackage, @NotNull GlobalSearchScope scope) { - Set names = null; - FileIndexFacade facade = FileIndexFacade.getInstance(myProject); - for (PsiDirectory dir : psiPackage.getDirectories(scope)) { - for (PsiFile file : dir.getFiles()) { - if (file instanceof PsiClassOwner && file.getViewProvider().getLanguages().size() == 1) { - VirtualFile vFile = file.getVirtualFile(); - if (vFile != null && - !(file instanceof PsiCompiledElement) && - !facade.isInSourceContent(vFile) && - (!scope.isForceSearchingInLibrarySources() || - !StubTreeLoader.getInstance().canHaveStub(vFile))) { - continue; - } - - Set inFile = file instanceof PsiClassOwnerEx ? ((PsiClassOwnerEx)file).getClassNames() : getClassNames(((PsiClassOwner)file).getClasses()); - - if (inFile.isEmpty()) continue; - if (names == null) names = new HashSet(); - names.addAll(inFile); - } - } - - } - return names == null ? Collections.emptySet() : names; - } - - @Override - public boolean processPackageDirectories(@NotNull PsiPackage psiPackage, - @NotNull final GlobalSearchScope scope, - @NotNull final Processor consumer, - boolean includeLibrarySources) { - final PsiManager psiManager = PsiManager.getInstance(getProject()); - return PackageIndex.getInstance(getProject()).getDirsByPackageName(psiPackage.getQualifiedName(), includeLibrarySources) - .forEach(new ReadActionProcessor() { - @Override - public boolean processInReadAction(final VirtualFile dir) { - if (!scope.contains(dir)) return true; - PsiDirectory psiDir = psiManager.findDirectory(dir); - return psiDir == null || consumer.process(psiDir); - } - }); - } - } - @Override public boolean isPartOfPackagePrefix(@NotNull String packageName) { final Collection packagePrefixes = myFileManager.getNonTrivialPackagePrefixes(); diff --git a/java/java-psi-impl/src/com/intellij/psi/impl/PsiElementFinderImpl.java b/java/java-psi-impl/src/com/intellij/psi/impl/PsiElementFinderImpl.java new file mode 100644 index 000000000000..2c482367abd6 --- /dev/null +++ b/java/java-psi-impl/src/com/intellij/psi/impl/PsiElementFinderImpl.java @@ -0,0 +1,177 @@ +/* + * 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.psi.impl; + +import com.intellij.openapi.application.ReadActionProcessor; +import com.intellij.openapi.project.DumbAware; +import com.intellij.openapi.project.Project; +import com.intellij.openapi.roots.FileIndexFacade; +import com.intellij.openapi.roots.PackageIndex; +import com.intellij.openapi.util.Comparing; +import com.intellij.openapi.util.text.StringUtil; +import com.intellij.openapi.vfs.VirtualFile; +import com.intellij.psi.*; +import com.intellij.psi.impl.file.impl.JavaFileManager; +import com.intellij.psi.search.GlobalSearchScope; +import com.intellij.psi.stubs.StubTreeLoader; +import com.intellij.psi.util.PsiUtilCore; +import com.intellij.util.Processor; +import com.intellij.util.containers.ContainerUtil; +import com.intellij.util.containers.HashMap; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import java.util.*; + +/** + * Created by kosyakov on 05.12.14. + */ +public class PsiElementFinderImpl extends PsiElementFinder implements DumbAware { + + private final Project myProject; + private final JavaFileManager myFileManager; + + public PsiElementFinderImpl(Project project, JavaFileManager javaFileManager) { + this.myProject = project; + this.myFileManager = javaFileManager; + } + + @Override + public PsiClass findClass(@NotNull String qualifiedName, @NotNull GlobalSearchScope scope) { + return myFileManager.findClass(qualifiedName, scope); + } + + @Override + @NotNull + public PsiClass[] findClasses(@NotNull String qualifiedName, @NotNull GlobalSearchScope scope) { + return myFileManager.findClasses(qualifiedName, scope); + } + + @Override + public PsiPackage findPackage(@NotNull String qualifiedName) { + return myFileManager.findPackage(qualifiedName); + } + + @Override + @NotNull + public PsiPackage[] getSubPackages(@NotNull PsiPackage psiPackage, @NotNull GlobalSearchScope scope) { + final Map packagesMap = new HashMap(); + final String qualifiedName = psiPackage.getQualifiedName(); + for (PsiDirectory dir : psiPackage.getDirectories(scope)) { + PsiDirectory[] subDirs = dir.getSubdirectories(); + for (PsiDirectory subDir : subDirs) { + final PsiPackage aPackage = JavaDirectoryService.getInstance().getPackage(subDir); + if (aPackage != null) { + final String subQualifiedName = aPackage.getQualifiedName(); + if (subQualifiedName.startsWith(qualifiedName) && !packagesMap.containsKey(subQualifiedName)) { + packagesMap.put(aPackage.getQualifiedName(), aPackage); + } + } + } + } + + packagesMap.remove(qualifiedName); // avoid SOE caused by returning a package as a subpackage of itself + return packagesMap.values().toArray(new PsiPackage[packagesMap.size()]); + } + + @Override + @NotNull + public PsiClass[] getClasses(@NotNull PsiPackage psiPackage, @NotNull final GlobalSearchScope scope) { + return getClasses(null, psiPackage, scope); + } + + @Override + @NotNull + public PsiClass[] getClasses(@Nullable String shortName, @NotNull PsiPackage psiPackage, @NotNull final GlobalSearchScope scope) { + List list = null; + String packageName = psiPackage.getQualifiedName(); + for (PsiDirectory dir : psiPackage.getDirectories(scope)) { + PsiClass[] classes = JavaDirectoryService.getInstance().getClasses(dir); + if (classes.length == 0) continue; + if (list == null) list = new ArrayList(); + for (PsiClass aClass : classes) { + // class file can be located in wrong place inside file system + String qualifiedName = aClass.getQualifiedName(); + if (qualifiedName != null) qualifiedName = StringUtil.getPackageName(qualifiedName); + if (Comparing.strEqual(qualifiedName, packageName)) { + if (shortName == null || shortName.equals(aClass.getName())) list.add(aClass); + } + } + } + if (list == null) { + return PsiClass.EMPTY_ARRAY; + } + + if (list.size() > 1) { + ContainerUtil.quickSort(list, new Comparator() { + @Override + public int compare(PsiClass o1, PsiClass o2) { + VirtualFile file1 = PsiUtilCore.getVirtualFile(o1); + VirtualFile file2 = PsiUtilCore.getVirtualFile(o2); + return file1 == null ? file2 == null ? 0 : -1 : file2 == null ? 1 : scope.compare(file2, file1); + } + }); + } + + return list.toArray(new PsiClass[list.size()]); + } + + @NotNull + @Override + public Set getClassNames(@NotNull PsiPackage psiPackage, @NotNull GlobalSearchScope scope) { + Set names = null; + FileIndexFacade facade = FileIndexFacade.getInstance(myProject); + for (PsiDirectory dir : psiPackage.getDirectories(scope)) { + for (PsiFile file : dir.getFiles()) { + if (file instanceof PsiClassOwner && file.getViewProvider().getLanguages().size() == 1) { + VirtualFile vFile = file.getVirtualFile(); + if (vFile != null && + !(file instanceof PsiCompiledElement) && + !facade.isInSourceContent(vFile) && + (!scope.isForceSearchingInLibrarySources() || !StubTreeLoader.getInstance().canHaveStub(vFile))) { + continue; + } + + Set inFile = + file instanceof PsiClassOwnerEx ? ((PsiClassOwnerEx)file).getClassNames() : getClassNames(((PsiClassOwner)file).getClasses()); + + if (inFile.isEmpty()) continue; + if (names == null) names = new HashSet(); + names.addAll(inFile); + } + } + + } + return names == null ? Collections.emptySet() : names; + } + + @Override + public boolean processPackageDirectories(@NotNull PsiPackage psiPackage, + @NotNull final GlobalSearchScope scope, + @NotNull final Processor consumer, + boolean includeLibrarySources) { + final PsiManager psiManager = PsiManager.getInstance(myProject); + return PackageIndex.getInstance(myProject).getDirsByPackageName(psiPackage.getQualifiedName(), includeLibrarySources) + .forEach(new ReadActionProcessor() { + @Override + public boolean processInReadAction(final VirtualFile dir) { + if (!scope.contains(dir)) return true; + PsiDirectory psiDir = psiManager.findDirectory(dir); + return psiDir == null || consumer.process(psiDir); + } + }); + } +} diff --git a/java/java-psi-impl/src/com/intellij/psi/impl/source/javadoc/PsiDocTokenImpl.java b/java/java-psi-impl/src/com/intellij/psi/impl/source/javadoc/PsiDocTokenImpl.java index 85301458d047..4225844fe754 100644 --- a/java/java-psi-impl/src/com/intellij/psi/impl/source/javadoc/PsiDocTokenImpl.java +++ b/java/java-psi-impl/src/com/intellij/psi/impl/source/javadoc/PsiDocTokenImpl.java @@ -15,8 +15,11 @@ */ package com.intellij.psi.impl.source.javadoc; +import com.intellij.psi.JavaDocTokenType; import com.intellij.psi.JavaElementVisitor; import com.intellij.psi.PsiElementVisitor; +import com.intellij.psi.PsiReference; +import com.intellij.psi.impl.source.resolve.reference.ReferenceProvidersRegistry; import com.intellij.psi.impl.source.tree.LeafPsiElement; import com.intellij.psi.javadoc.PsiDocToken; import com.intellij.psi.tree.IElementType; @@ -42,6 +45,15 @@ public class PsiDocTokenImpl extends LeafPsiElement implements PsiDocToken{ } } + @NotNull + @Override + public PsiReference[] getReferences() { + if (getTokenType() == JavaDocTokenType.DOC_COMMENT_DATA) { + return ReferenceProvidersRegistry.getReferencesFromProviders(this, PsiDocToken.class); + } + return super.getReferences(); + } + public String toString(){ return "PsiDocToken:" + getTokenType().toString(); } diff --git a/java/java-psi-impl/src/com/intellij/psi/impl/source/tree/JavaTreeGenerator.java b/java/java-psi-impl/src/com/intellij/psi/impl/source/tree/JavaTreeGenerator.java index c310f5effc08..b5ca2ea117c3 100644 --- a/java/java-psi-impl/src/com/intellij/psi/impl/source/tree/JavaTreeGenerator.java +++ b/java/java-psi-impl/src/com/intellij/psi/impl/source/tree/JavaTreeGenerator.java @@ -61,6 +61,9 @@ public class JavaTreeGenerator implements TreeGenerator { final LanguageLevel level = PsiUtil.getLanguageLevel(original); final DummyHolder holder = DummyHolderFactory.createHolder(original.getManager(), new JavaDummyElement(text, MOD_LIST, level), null); final TreeElement modifierListElement = holder.getTreeElement().getFirstChildNode(); + if (modifierListElement == null) { + throw new AssertionError("No modifier list for \"" + text + '\"'); + } return markGeneratedIfNeeded(original, modifierListElement); } @@ -148,7 +151,7 @@ public class JavaTreeGenerator implements TreeGenerator { return Factory.createSingleLeafElement(type, text, 0, text.length(), table, manager, CodeEditUtil.isNodeGenerated(original.getNode())); } - private static TreeElement markGeneratedIfNeeded(PsiElement original, TreeElement copy) { + private static TreeElement markGeneratedIfNeeded(@NotNull PsiElement original, @NotNull TreeElement copy) { if (CodeEditUtil.isNodeGenerated(original.getNode())) { copy.acceptTree(new GeneratedMarkerVisitor()); } diff --git a/java/java-psi-impl/src/com/intellij/psi/impl/source/tree/java/PsiMethodCallExpressionImpl.java b/java/java-psi-impl/src/com/intellij/psi/impl/source/tree/java/PsiMethodCallExpressionImpl.java index 9bbb90a677cd..f8dbb9d2c1f3 100644 --- a/java/java-psi-impl/src/com/intellij/psi/impl/source/tree/java/PsiMethodCallExpressionImpl.java +++ b/java/java-psi-impl/src/com/intellij/psi/impl/source/tree/java/PsiMethodCallExpressionImpl.java @@ -1,5 +1,5 @@ /* - * Copyright 2000-2009 JetBrains s.r.o. + * 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. @@ -97,8 +97,9 @@ public class PsiMethodCallExpressionImpl extends ExpressionPsiElement implements @NotNull public PsiExpressionList getArgumentList() { PsiExpressionList list = (PsiExpressionList)findChildByRoleAsPsiElement(ChildRole.ARGUMENT_LIST); - if (list != null) return list; - LOG.error("Invalid PSI. Children:" + DebugUtil.psiToString(this, false)); + if (list == null) { + LOG.error("Invalid PSI for'" + getText() + ". Parent:" + DebugUtil.psiToString(getParent(), false)); + } return list; } diff --git a/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/javaDoc/LinksInJavaDoc.java b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/javaDoc/LinksInJavaDoc.java new file mode 100644 index 000000000000..f4d84f9ab982 --- /dev/null +++ b/java/java-tests/testData/codeInsight/daemonCodeAnalyzer/javaDoc/LinksInJavaDoc.java @@ -0,0 +1,9 @@ +/** + * + * The Unicode Standard + */ +class LinksInJavaDoc { + // Since Java 7 classloading is parallel on parallel capable classloader (http://docs.oracle.com/javase/7/docs/technotes/guides/lang/cl-mt.html) + // Parallel classloading avoids deadlocks like https://youtrack.jetbrains.com/issue/IDEA-131621, + // Use mailto:webmaster@jetbrains.com to report abuse +} \ No newline at end of file diff --git a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/JavadocHighlightingTest.java b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/JavadocHighlightingTest.java index 10d5bc064dcd..52c201d3cb54 100644 --- a/java/java-tests/testSrc/com/intellij/codeInsight/daemon/JavadocHighlightingTest.java +++ b/java/java-tests/testSrc/com/intellij/codeInsight/daemon/JavadocHighlightingTest.java @@ -4,10 +4,17 @@ import com.intellij.JavaTestUtil; import com.intellij.codeInspection.LocalInspectionTool; import com.intellij.codeInspection.javaDoc.JavaDocLocalInspection; import com.intellij.codeInspection.javaDoc.JavaDocReferenceInspection; +import com.intellij.openapi.paths.WebReference; import com.intellij.openapi.roots.LanguageLevelProjectExtension; import com.intellij.pom.java.LanguageLevel; +import com.intellij.psi.PsiElement; +import com.intellij.psi.PsiRecursiveElementWalkingVisitor; +import com.intellij.psi.PsiReference; import org.jetbrains.annotations.NotNull; +import java.util.ArrayList; +import java.util.List; + public class JavadocHighlightingTest extends LightDaemonAnalyzerTestCase { private static final String BASE_PATH = "/codeInsight/daemonCodeAnalyzer/javaDoc"; @@ -107,6 +114,35 @@ public class JavadocHighlightingTest extends LightDaemonAnalyzerTestCase { doTest(); } + public void testLinksInJavaDoc() throws Exception { + configureByFile(BASE_PATH + "/" + getTestName(false) + ".java"); + final List refs = new ArrayList(); + myFile.accept(new PsiRecursiveElementWalkingVisitor() { + @Override + public void visitElement(PsiElement element) { + for(PsiReference ref:element.getReferences()) { + if (ref instanceof WebReference) refs.add((WebReference)ref); + } + + super.visitElement(element); + } + }); + + String[] targets = {"http://www.unicode.org/unicode/standard/standard.html", + "http://docs.oracle.com/javase/7/docs/technotes/guides/lang/cl-mt.html", + "https://youtrack.jetbrains.com/issue/IDEA-131621", + "mailto:webmaster@jetbrains.com" + }; + assertTrue(refs.size() == targets.length); + int i = 0; + + for(WebReference ref:refs) { + assertEquals(ref.getCanonicalText(), targets[i++]); + assertTrue(ref.isSoft()); + assertNotNull(ref.resolve()); + } + } + protected void doTest() throws Exception { super.doTest(BASE_PATH + "/" + getTestName(false) + ".java", true, false); } diff --git a/java/java-tests/testSrc/com/intellij/codeInspection/ContractInferenceFromSourceTest.groovy b/java/java-tests/testSrc/com/intellij/codeInspection/ContractInferenceFromSourceTest.groovy index 1ee47eccb835..2d2aeb7c92e5 100644 --- a/java/java-tests/testSrc/com/intellij/codeInspection/ContractInferenceFromSourceTest.groovy +++ b/java/java-tests/testSrc/com/intellij/codeInspection/ContractInferenceFromSourceTest.groovy @@ -16,6 +16,8 @@ package com.intellij.codeInspection import com.intellij.codeInspection.dataFlow.ContractInference +import com.intellij.psi.PsiAnonymousClass +import com.intellij.psi.util.PsiTreeUtil import com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase /** @@ -448,6 +450,27 @@ public static boolean isBlank(String s) { assert c == ['null -> true'] } + public void "test no inference for unused anonymous class methods where annotations won't be used anyway"() { + def method = PsiTreeUtil.findChildOfType(myFixture.addClass(""" +class Foo {{ + new Object() { + Object foo() { return null;} + }; +}}"""), PsiAnonymousClass).methods[0] + assert ContractInference.inferContracts(method).collect { it as String } == [] + } + + public void "test inference for used anonymous class methods"() { + def method = PsiTreeUtil.findChildOfType(myFixture.addClass(""" +class Foo {{ + new Object() { + Object foo() { return null;} + Object bar() { return foo();} + }; +}}"""), PsiAnonymousClass).methods[0] + assert ContractInference.inferContracts(method).collect { it as String } == [' -> null'] + } + private String inferContract(String method) { return assertOneElement(inferContracts(method)) } diff --git a/java/java-tests/testSrc/com/intellij/codeInspection/bytecodeAnalysis/BytecodeAnalysisIntegrationTest.java b/java/java-tests/testSrc/com/intellij/codeInspection/bytecodeAnalysis/BytecodeAnalysisIntegrationTest.java index 8a7340c76093..c3d5bc8cafd2 100644 --- a/java/java-tests/testSrc/com/intellij/codeInspection/bytecodeAnalysis/BytecodeAnalysisIntegrationTest.java +++ b/java/java-tests/testSrc/com/intellij/codeInspection/bytecodeAnalysis/BytecodeAnalysisIntegrationTest.java @@ -132,14 +132,16 @@ public class BytecodeAnalysisIntegrationTest extends JavaCodeInsightFixtureTestC public void testInferredAnnoGutter() { setUpLibraries(); openDecompiledClass("org.apache.velocity.util.ExceptionUtils"); - checkHasGutter("@Contract("null,_,_->null") \n" + + checkHasGutter("Inferred annotations available. Full signature:

\n" + + "@Contract("null,_,_->null") \n" + "public static Throwable createWithCause("); } public void testExternalAnnoGutter() { setUpExternalUpAnnotations(); openDecompiledClass("java.lang.Boolean"); - checkHasGutter("@org.jetbrains.annotations.Contract("null->false") \n" + + checkHasGutter("External and inferred annotations available. Full signature:

\n" + + "@org.jetbrains.annotations.Contract("null->false") \n" + "private static boolean toBoolean(@org.jetbrains.annotations.Nullable String var0)"); } diff --git a/jps/jps-builders/src/org/jetbrains/jps/javac/JavacMain.java b/jps/jps-builders/src/org/jetbrains/jps/javac/JavacMain.java index ed5bf0270f5f..c880924ea232 100644 --- a/jps/jps-builders/src/org/jetbrains/jps/javac/JavacMain.java +++ b/jps/jps-builders/src/org/jetbrains/jps/javac/JavacMain.java @@ -193,8 +193,7 @@ public class JavacMain { private static boolean canUseOptimizedFileManager(JavaCompilingTool compilingTool) { // since java 9 internal API's used by the optimizedFileManager have changed - return compilingTool instanceof JavacCompilerTool && - (JAVA_VERSION.contains("1.6") || JAVA_VERSION.contains("1.7") || JAVA_VERSION.contains("1.8")); + return compilingTool instanceof JavacCompilerTool && !SystemInfo.isJavaVersionAtLeast("1.9"); } private static void handleCancelException(DiagnosticOutputConsumer diagnosticConsumer) { diff --git a/platform/analysis-api/src/com/intellij/psi/search/GlobalSearchScopesCore.java b/platform/analysis-api/src/com/intellij/psi/search/GlobalSearchScopesCore.java index 76db4a7cc765..a45bc13625a7 100644 --- a/platform/analysis-api/src/com/intellij/psi/search/GlobalSearchScopesCore.java +++ b/platform/analysis-api/src/com/intellij/psi/search/GlobalSearchScopesCore.java @@ -19,6 +19,7 @@ import com.intellij.openapi.module.Module; import com.intellij.openapi.project.Project; import com.intellij.openapi.roots.ProjectFileIndex; import com.intellij.openapi.roots.ProjectRootManager; +import com.intellij.openapi.util.text.StringUtil; import com.intellij.openapi.vfs.VfsUtilCore; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.PsiBundle; @@ -27,6 +28,7 @@ import com.intellij.psi.PsiFile; import com.intellij.psi.PsiManager; import com.intellij.psi.search.scope.packageSet.*; import com.intellij.util.ArrayUtil; +import com.intellij.util.Function; import org.jetbrains.annotations.NotNull; import java.util.ArrayList; @@ -88,6 +90,12 @@ public class GlobalSearchScopesCore { return mySet.getName(); } + @NotNull + @Override + public Project getProject() { + return super.getProject(); + } + @Override public int compare(@NotNull VirtualFile file1, @NotNull VirtualFile file2) { return 0; @@ -255,6 +263,18 @@ public class GlobalSearchScopesCore { } return super.uniteWith(scope); } + + @NotNull + @Override + public Project getProject() { + return super.getProject(); + } + + @NotNull + @Override + public String getDisplayName() { + return "Directory '" + myDirectory.getName() + "'"; + } } static class DirectoriesScope extends GlobalSearchScope { @@ -265,6 +285,9 @@ public class GlobalSearchScopesCore { super(project); myWithSubdirectories = withSubdirectories; myDirectories = directories; + if (directories.length < 2) { + throw new IllegalArgumentException("Expected >1 directories, but got: " + Arrays.asList(directories)); + } } @Override @@ -353,5 +376,27 @@ public class GlobalSearchScopesCore { } return super.uniteWith(scope); } + + @NotNull + @Override + public Project getProject() { + return super.getProject(); + } + + @NotNull + @Override + public String getDisplayName() { + if (myDirectories.length == 1) { + VirtualFile root = myDirectories[0]; + return "Directory '" + root.getName() + "'"; + } + return "Directories " + StringUtil.join(myDirectories, new Function() { + @Override + public String fun(VirtualFile file) { + return "'" + file.getName() + "'"; + } + }, ", "); + } + } } diff --git a/platform/core-api/src/com/intellij/openapi/project/DumbService.java b/platform/core-api/src/com/intellij/openapi/project/DumbService.java index a0f5b43ce308..ac3edf55d890 100644 --- a/platform/core-api/src/com/intellij/openapi/project/DumbService.java +++ b/platform/core-api/src/com/intellij/openapi/project/DumbService.java @@ -34,7 +34,7 @@ import java.util.List; /** * A service managing IDEA's 'dumb' mode: when indices are updated in background and the functionality is very much limited. - * Only the explicitly allowed functionality is available. Usually it's allowed by implementing {@link com.intellij.openapi.project.DumbAware} interface. + * Only the explicitly allowed functionality is available. Usually it's allowed by implementing {@link DumbAware} interface. * * If you want to register a toolwindow, which will be enabled during the dumb mode, please use {@link com.intellij.openapi.wm.ToolWindowManager}'s * registration methods which have 'canWorkInDumMode' parameter. @@ -45,7 +45,7 @@ public abstract class DumbService { private static final Logger LOG = Logger.getInstance("#com.intellij.openapi.project.DumbService"); /** - * @see com.intellij.openapi.project.Project#getMessageBus() + * @see Project#getMessageBus() */ public static final Topic DUMB_MODE = new Topic("dumb mode", DumbModeListener.class); @@ -210,6 +210,26 @@ public abstract class DumbService { return o instanceof DumbAware; } + /** + * Enables or disables alternative resolve strategies for the current thread.

+ * + * Normally reference resolution uses index, and hence is not available in dumb mode. In some cases, alternative ways + * of performing resolve are available, although much slower. It's impractical to always use these ways because it'll + * lead to overloaded CPU (especially given there's also indexing in progress). But for some explicit user actions + * (e.g. explicit Goto Declaration) turning these slower methods is beneficial.

+ * + * A typical usage would involve try-finally, where the alternative resolution is first enabled, then an action is performed, + * and then alternative resolution is turned off in the finally block. + */ + public abstract void setAlternativeResolveEnabled(boolean enabled); + + /** + * @return whether alternative resolution is enabled for the current thread. + * + * @see #setAlternativeResolveEnabled(boolean) + */ + public abstract boolean isAlternativeResolveEnabled(); + /** * @see #DUMB_MODE */ diff --git a/platform/core-api/src/com/intellij/psi/search/NonClasspathDirectoriesScope.java b/platform/core-api/src/com/intellij/psi/search/NonClasspathDirectoriesScope.java index 0cf15e6970c2..921cddcf8cae 100644 --- a/platform/core-api/src/com/intellij/psi/search/NonClasspathDirectoriesScope.java +++ b/platform/core-api/src/com/intellij/psi/search/NonClasspathDirectoriesScope.java @@ -17,8 +17,10 @@ package com.intellij.psi.search; import com.intellij.openapi.module.Module; +import com.intellij.openapi.util.text.StringUtil; import com.intellij.openapi.vfs.VfsUtilCore; import com.intellij.openapi.vfs.VirtualFile; +import com.intellij.util.Function; import com.intellij.util.containers.ContainerUtil; import org.jetbrains.annotations.NotNull; @@ -42,7 +44,7 @@ public class NonClasspathDirectoriesScope extends GlobalSearchScope { } @NotNull - public static GlobalSearchScope compose(List roots) { + public static GlobalSearchScope compose(@NotNull List roots) { if (roots.isEmpty()) { return EMPTY_SCOPE; } @@ -88,4 +90,19 @@ public class NonClasspathDirectoriesScope extends GlobalSearchScope { result = 31 * result + myRoots.hashCode(); return result; } + + @NotNull + @Override + public String getDisplayName() { + if (myRoots.size() == 1) { + VirtualFile root = myRoots.iterator().next(); + return "Directory '" + root.getName() + "'"; + } + return "Directories " + StringUtil.join(myRoots, new Function() { + @Override + public String fun(VirtualFile file) { + return "'" + file.getName() + "'"; + } + }, ", "); + } } diff --git a/platform/core-impl/src/com/intellij/mock/MockDumbService.java b/platform/core-impl/src/com/intellij/mock/MockDumbService.java index 1e1179cc5ee8..b1fe7ae2a727 100644 --- a/platform/core-impl/src/com/intellij/mock/MockDumbService.java +++ b/platform/core-impl/src/com/intellij/mock/MockDumbService.java @@ -74,6 +74,15 @@ public class MockDumbService extends DumbService { return myProject; } + @Override + public void setAlternativeResolveEnabled(boolean enabled) { + } + + @Override + public boolean isAlternativeResolveEnabled() { + return false; + } + public void smartInvokeLater(@NotNull final Runnable runnable) { runnable.run(); } diff --git a/platform/core-impl/src/com/intellij/openapi/editor/ex/DocumentEx.java b/platform/core-impl/src/com/intellij/openapi/editor/ex/DocumentEx.java index 7e127598dab4..f0638c94e348 100644 --- a/platform/core-impl/src/com/intellij/openapi/editor/ex/DocumentEx.java +++ b/platform/core-impl/src/com/intellij/openapi/editor/ex/DocumentEx.java @@ -1,5 +1,5 @@ /* - * Copyright 2000-2012 JetBrains s.r.o. + * 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. @@ -83,7 +83,17 @@ public interface DocumentEx extends Document { @NotNull List getGuardedBlocks(); + + /** + * Get all range markers + * and hand them to the {@code processor} in their {@link RangeMarker#getStartOffset()} order + */ boolean processRangeMarkers(@NotNull Processor processor); + + /** + * Get range markers which {@link com.intellij.openapi.util.TextRange#intersects(int, int)} the specified range + * and hand them to the {@code processor} in their {@link RangeMarker#getStartOffset()} order + */ boolean processRangeMarkersOverlappingWith(int start, int end, @NotNull Processor processor); } diff --git a/platform/core-impl/src/com/intellij/openapi/editor/impl/DocumentImpl.java b/platform/core-impl/src/com/intellij/openapi/editor/impl/DocumentImpl.java index a9ac8c880521..d380056e8a47 100644 --- a/platform/core-impl/src/com/intellij/openapi/editor/impl/DocumentImpl.java +++ b/platform/core-impl/src/com/intellij/openapi/editor/impl/DocumentImpl.java @@ -332,11 +332,11 @@ public class DocumentImpl extends UserDataHolderBase implements DocumentEx { } } - public ReadonlyFragmentModificationHandler getReadonlyFragmentModificationHandler() { + ReadonlyFragmentModificationHandler getReadonlyFragmentModificationHandler() { return myReadonlyFragmentModificationHandler; } - public void setReadonlyFragmentModificationHandler(final ReadonlyFragmentModificationHandler readonlyFragmentModificationHandler) { + void setReadonlyFragmentModificationHandler(final ReadonlyFragmentModificationHandler readonlyFragmentModificationHandler) { myReadonlyFragmentModificationHandler = readonlyFragmentModificationHandler; } @@ -364,13 +364,13 @@ public class DocumentImpl extends UserDataHolderBase implements DocumentEx { } @TestOnly - public int getRangeMarkersSize() { + int getRangeMarkersSize() { return myRangeMarkers.size() + myPersistentRangeMarkers.size(); } @TestOnly - public int getRangeMarkersNodeSize() { - return myRangeMarkers.nodeSize()+myPersistentRangeMarkers.size(); + int getRangeMarkersNodeSize() { + return myRangeMarkers.nodeSize()+myPersistentRangeMarkers.nodeSize(); } @Override @@ -693,7 +693,7 @@ public class DocumentImpl extends UserDataHolderBase implements DocumentEx { getLineSet().clearModificationFlags(); } - public void clearLineModificationFlagsExcept(@NotNull int[] caretLines) { + void clearLineModificationFlagsExcept(@NotNull int[] caretLines) { IntArrayList modifiedLines = new IntArrayList(caretLines.length); LineSet lineSet = getLineSet(); for (int line : caretLines) { @@ -716,8 +716,8 @@ public class DocumentImpl extends UserDataHolderBase implements DocumentEx { assertNotNestedModification(); boolean enableRecursiveModifications = Registry.is("enable.recursive.document.changes"); // temporary property, to remove in IDEA 16 myChangeInProgress = true; - final DocumentEvent event; try { + final DocumentEvent event; try { event = doBeforeChangedUpdate(offset, oldString, newString, wholeTextReplaced); } @@ -742,11 +742,9 @@ public class DocumentImpl extends UserDataHolderBase implements DocumentEx { Application app = ApplicationManager.getApplication(); if (app != null) { FileDocumentManager manager = FileDocumentManager.getInstance(); - if (manager != null) { - VirtualFile file = manager.getFile(this); - if (file != null && !file.isValid()) { - LOG.error("File of this document has been deleted."); - } + VirtualFile file = manager.getFile(this); + if (file != null && !file.isValid()) { + LOG.error("File of this document has been deleted."); } } assertInsideCommand(); @@ -878,9 +876,9 @@ public class DocumentImpl extends UserDataHolderBase implements DocumentEx { private final Ref myCachedDocumentListenersRef; private final List myDocumentListeners; - public DocumentListenerDisposable(@NotNull DocumentListener listener, - @NotNull Ref cachedDocumentListenersRef, - @NotNull List documentListeners) { + private DocumentListenerDisposable(@NotNull DocumentListener listener, + @NotNull Ref cachedDocumentListenersRef, + @NotNull List documentListeners) { myListener = listener; myCachedDocumentListenersRef = cachedDocumentListenersRef; myDocumentListeners = documentListeners; @@ -1085,7 +1083,7 @@ public class DocumentImpl extends UserDataHolderBase implements DocumentEx { return "DocumentImpl[" + FileDocumentManager.getInstance().getFile(this) + "]"; } - public void requestTabTracking() { + void requestTabTracking() { ApplicationManager.getApplication().assertIsDispatchThread(); if (myTabTrackingRequestors++ == 0) { myMightContainTabs = false; @@ -1093,14 +1091,14 @@ public class DocumentImpl extends UserDataHolderBase implements DocumentEx { } } - public void giveUpTabTracking() { + void giveUpTabTracking() { ApplicationManager.getApplication().assertIsDispatchThread(); if (--myTabTrackingRequestors == 0) { myMightContainTabs = true; } } - public boolean mightContainTabs() { + boolean mightContainTabs() { return myMightContainTabs; } diff --git a/platform/core-impl/src/com/intellij/openapi/progress/util/TooManyUsagesStatus.java b/platform/core-impl/src/com/intellij/openapi/progress/util/TooManyUsagesStatus.java index f44d497edefa..a20d42d38bf8 100644 --- a/platform/core-impl/src/com/intellij/openapi/progress/util/TooManyUsagesStatus.java +++ b/platform/core-impl/src/com/intellij/openapi/progress/util/TooManyUsagesStatus.java @@ -15,6 +15,7 @@ */ package com.intellij.openapi.progress.util; +import com.intellij.openapi.progress.EmptyProgressIndicator; import com.intellij.openapi.progress.ProgressIndicator; import com.intellij.openapi.util.Key; import com.intellij.openapi.util.UserDataHolder; @@ -28,6 +29,11 @@ import java.util.concurrent.atomic.AtomicReference; public class TooManyUsagesStatus { private static final Key KEY = Key.create("TooManyUsagesStatus"); private static final NullStatus NULL_STATUS = new NullStatus(); + private final ProgressIndicator myIndicator; + + private TooManyUsagesStatus(@NotNull ProgressIndicator indicator) { + myIndicator = indicator; + } @NotNull public static TooManyUsagesStatus getFrom(@Nullable ProgressIndicator indicator) { @@ -38,7 +44,7 @@ public class TooManyUsagesStatus { public static TooManyUsagesStatus createFor(@NotNull ProgressIndicator indicator) { TooManyUsagesStatus data = null; if (indicator instanceof UserDataHolder) { - data = new TooManyUsagesStatus(); + data = new TooManyUsagesStatus(indicator); ((UserDataHolder)indicator).putUserData(KEY, data); } return data; @@ -65,8 +71,12 @@ public class TooManyUsagesStatus { public void pauseProcessingIfTooManyUsages() { if (tooManyUsagesStatus.get() == Status.WARNING_DIALOG_SHOWN) { //assert ApplicationManager.getApplication().isDispatchThread() || !ApplicationManager.getApplication().isReadAccessAllowed(); + long start = System.currentTimeMillis(); try { - waitWhileUserClick.await(1, TimeUnit.SECONDS); + while (System.currentTimeMillis() < start + 1000) { + if (waitWhileUserClick.await(10, TimeUnit.MILLISECONDS)) break; + if (myIndicator.isCanceled()) break; + } } catch (InterruptedException ignored) { } @@ -74,6 +84,10 @@ public class TooManyUsagesStatus { } private static class NullStatus extends TooManyUsagesStatus { + private NullStatus() { + super(new EmptyProgressIndicator()); + } + @Override public boolean switchTooManyUsagesStatus() { return false; diff --git a/platform/core-impl/src/com/intellij/psi/impl/smartPointers/SmartPointerManagerImpl.java b/platform/core-impl/src/com/intellij/psi/impl/smartPointers/SmartPointerManagerImpl.java index 4f0fa1b7dd1d..408a3656daac 100644 --- a/platform/core-impl/src/com/intellij/psi/impl/smartPointers/SmartPointerManagerImpl.java +++ b/platform/core-impl/src/com/intellij/psi/impl/smartPointers/SmartPointerManagerImpl.java @@ -30,6 +30,7 @@ import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.*; import com.intellij.psi.impl.PsiManagerEx; import com.intellij.psi.impl.source.tree.MarkersHolderFileViewProvider; +import com.intellij.psi.util.PsiUtilCore; import com.intellij.reference.SoftReference; import com.intellij.util.containers.UnsafeWeakList; import org.jetbrains.annotations.NotNull; @@ -143,6 +144,7 @@ public class SmartPointerManagerImpl extends SmartPointerManager { @NotNull public SmartPsiElementPointer createSmartPsiElementPointer(@NotNull E element, PsiFile containingFile) { if (containingFile != null && !containingFile.isValid() || containingFile == null && !element.isValid()) { + PsiUtilCore.ensureValid(element); LOG.error("Invalid element:" + element); } SmartPointerEx pointer = getCachedPointer(element); diff --git a/platform/icons/src/javaee/JavaeeAppModule.png b/platform/icons/src/javaee/JavaeeAppModule.png old mode 100644 new mode 100755 index 0a67d9245605..ba55aac029e7 Binary files a/platform/icons/src/javaee/JavaeeAppModule.png and b/platform/icons/src/javaee/JavaeeAppModule.png differ diff --git a/platform/icons/src/javaee/JavaeeAppModule@2x.png b/platform/icons/src/javaee/JavaeeAppModule@2x.png new file mode 100755 index 000000000000..92f2fb06bc93 Binary files /dev/null and b/platform/icons/src/javaee/JavaeeAppModule@2x.png differ diff --git a/platform/icons/src/javaee/JavaeeAppModule@2x_dark.png b/platform/icons/src/javaee/JavaeeAppModule@2x_dark.png new file mode 100755 index 000000000000..79201c60b52b Binary files /dev/null and b/platform/icons/src/javaee/JavaeeAppModule@2x_dark.png differ diff --git a/platform/icons/src/javaee/JavaeeAppModule_dark.png b/platform/icons/src/javaee/JavaeeAppModule_dark.png new file mode 100755 index 000000000000..d96b25349409 Binary files /dev/null and b/platform/icons/src/javaee/JavaeeAppModule_dark.png differ diff --git a/platform/icons/src/javaee/WebService.png b/platform/icons/src/javaee/WebService.png old mode 100644 new mode 100755 index 9961daa5c00f..6e6a16253bb9 Binary files a/platform/icons/src/javaee/WebService.png and b/platform/icons/src/javaee/WebService.png differ diff --git a/platform/icons/src/javaee/WebService2.png b/platform/icons/src/javaee/WebService2.png new file mode 100755 index 000000000000..590f3a50d1db Binary files /dev/null and b/platform/icons/src/javaee/WebService2.png differ diff --git a/platform/icons/src/javaee/WebService2@2x.png b/platform/icons/src/javaee/WebService2@2x.png new file mode 100755 index 000000000000..2e7a3bc9bd8e Binary files /dev/null and b/platform/icons/src/javaee/WebService2@2x.png differ diff --git a/platform/icons/src/javaee/WebService2@2x_dark.png b/platform/icons/src/javaee/WebService2@2x_dark.png new file mode 100755 index 000000000000..46daeb438595 Binary files /dev/null and b/platform/icons/src/javaee/WebService2@2x_dark.png differ diff --git a/platform/icons/src/javaee/WebService@2x.png b/platform/icons/src/javaee/WebService@2x.png new file mode 100755 index 000000000000..516a1b7d2927 Binary files /dev/null and b/platform/icons/src/javaee/WebService@2x.png differ diff --git a/platform/icons/src/javaee/WebServiceClient.png b/platform/icons/src/javaee/WebServiceClient.png old mode 100644 new mode 100755 index 63df7e02a0c7..a5a951aec840 Binary files a/platform/icons/src/javaee/WebServiceClient.png and b/platform/icons/src/javaee/WebServiceClient.png differ diff --git a/platform/icons/src/javaee/WebServiceClient2.png b/platform/icons/src/javaee/WebServiceClient2.png new file mode 100755 index 000000000000..114cddaa64d4 Binary files /dev/null and b/platform/icons/src/javaee/WebServiceClient2.png differ diff --git a/platform/icons/src/javaee/WebServiceClient2@2x.png b/platform/icons/src/javaee/WebServiceClient2@2x.png new file mode 100755 index 000000000000..839131bffa1b Binary files /dev/null and b/platform/icons/src/javaee/WebServiceClient2@2x.png differ diff --git a/platform/icons/src/javaee/WebServiceClient2@2x_dark.png b/platform/icons/src/javaee/WebServiceClient2@2x_dark.png new file mode 100755 index 000000000000..c4734599e65a Binary files /dev/null and b/platform/icons/src/javaee/WebServiceClient2@2x_dark.png differ diff --git a/platform/icons/src/javaee/WebServiceClient2_dark.png b/platform/icons/src/javaee/WebServiceClient2_dark.png new file mode 100755 index 000000000000..eaad4178f109 Binary files /dev/null and b/platform/icons/src/javaee/WebServiceClient2_dark.png differ diff --git a/platform/icons/src/javaee/WebServiceClient@2x.png b/platform/icons/src/javaee/WebServiceClient@2x.png new file mode 100755 index 000000000000..30a584a1ea72 Binary files /dev/null and b/platform/icons/src/javaee/WebServiceClient@2x.png differ diff --git a/platform/icons/src/javaee/WebService_dark.png b/platform/icons/src/javaee/WebService_dark.png new file mode 100755 index 000000000000..118fb9b0cd28 Binary files /dev/null and b/platform/icons/src/javaee/WebService_dark.png differ diff --git a/platform/icons/src/javaee/application_xml.png b/platform/icons/src/javaee/application_xml.png old mode 100644 new mode 100755 index 8bd86a3211ce..c7772fed3f1d Binary files a/platform/icons/src/javaee/application_xml.png and b/platform/icons/src/javaee/application_xml.png differ diff --git a/platform/icons/src/javaee/application_xml@2x.png b/platform/icons/src/javaee/application_xml@2x.png new file mode 100755 index 000000000000..d41ea772cffe Binary files /dev/null and b/platform/icons/src/javaee/application_xml@2x.png differ diff --git a/platform/icons/src/javaee/application_xml@2x_dark.png b/platform/icons/src/javaee/application_xml@2x_dark.png new file mode 100755 index 000000000000..f2c6e6159465 Binary files /dev/null and b/platform/icons/src/javaee/application_xml@2x_dark.png differ diff --git a/platform/icons/src/javaee/application_xml_dark.png b/platform/icons/src/javaee/application_xml_dark.png new file mode 100755 index 000000000000..0d20c5b29a1b Binary files /dev/null and b/platform/icons/src/javaee/application_xml_dark.png differ diff --git a/platform/icons/src/javaee/buildOnFrameDeactivation.png b/platform/icons/src/javaee/buildOnFrameDeactivation.png old mode 100644 new mode 100755 diff --git a/platform/icons/src/javaee/dataSourceImport.png b/platform/icons/src/javaee/dataSourceImport.png old mode 100644 new mode 100755 index 417055dba923..b882c72b9024 Binary files a/platform/icons/src/javaee/dataSourceImport.png and b/platform/icons/src/javaee/dataSourceImport.png differ diff --git a/platform/icons/src/javaee/dataSourceImport@2x.png b/platform/icons/src/javaee/dataSourceImport@2x.png new file mode 100755 index 000000000000..1e9697c8aaa5 Binary files /dev/null and b/platform/icons/src/javaee/dataSourceImport@2x.png differ diff --git a/platform/icons/src/javaee/databaseSchemaImportLegend.png b/platform/icons/src/javaee/databaseSchemaImportLegend.png old mode 100644 new mode 100755 diff --git a/platform/icons/src/javaee/dbSchemaImportBig.png b/platform/icons/src/javaee/dbSchemaImportBig.png old mode 100644 new mode 100755 index e7b85f70f6ce..1e9697c8aaa5 Binary files a/platform/icons/src/javaee/dbSchemaImportBig.png and b/platform/icons/src/javaee/dbSchemaImportBig.png differ diff --git a/platform/icons/src/javaee/dbSchemaImportBig@2x.png b/platform/icons/src/javaee/dbSchemaImportBig@2x.png new file mode 100755 index 000000000000..af5281303f1b Binary files /dev/null and b/platform/icons/src/javaee/dbSchemaImportBig@2x.png differ diff --git a/platform/icons/src/javaee/ejb-jar_xml.png b/platform/icons/src/javaee/ejb-jar_xml.png old mode 100644 new mode 100755 index 4fa3a36c91e6..a2761bf29bf8 Binary files a/platform/icons/src/javaee/ejb-jar_xml.png and b/platform/icons/src/javaee/ejb-jar_xml.png differ diff --git a/platform/icons/src/javaee/ejb-jar_xml@2x.png b/platform/icons/src/javaee/ejb-jar_xml@2x.png new file mode 100755 index 000000000000..471aa6c016ef Binary files /dev/null and b/platform/icons/src/javaee/ejb-jar_xml@2x.png differ diff --git a/platform/icons/src/javaee/ejbClass.png b/platform/icons/src/javaee/ejbClass.png old mode 100644 new mode 100755 index 5b3ab2957b50..c296e7b447da Binary files a/platform/icons/src/javaee/ejbClass.png and b/platform/icons/src/javaee/ejbClass.png differ diff --git a/platform/icons/src/javaee/ejbClass@2x.png b/platform/icons/src/javaee/ejbClass@2x.png new file mode 100755 index 000000000000..a7e22c53bf34 Binary files /dev/null and b/platform/icons/src/javaee/ejbClass@2x.png differ diff --git a/platform/icons/src/javaee/ejbModule.png b/platform/icons/src/javaee/ejbModule.png old mode 100644 new mode 100755 index 03ec8e1f06aa..95dc2bec229f Binary files a/platform/icons/src/javaee/ejbModule.png and b/platform/icons/src/javaee/ejbModule.png differ diff --git a/platform/icons/src/javaee/ejbModule@2x.png b/platform/icons/src/javaee/ejbModule@2x.png new file mode 100755 index 000000000000..da59cea45b75 Binary files /dev/null and b/platform/icons/src/javaee/ejbModule@2x.png differ diff --git a/platform/icons/src/javaee/embeddedAttributeOverlay.png b/platform/icons/src/javaee/embeddedAttributeOverlay.png old mode 100644 new mode 100755 index e2d0da45a470..475c2ed43d46 Binary files a/platform/icons/src/javaee/embeddedAttributeOverlay.png and b/platform/icons/src/javaee/embeddedAttributeOverlay.png differ diff --git a/platform/icons/src/javaee/embeddedAttributeOverlay@2x.png b/platform/icons/src/javaee/embeddedAttributeOverlay@2x.png new file mode 100755 index 000000000000..e7fb7f3da11c Binary files /dev/null and b/platform/icons/src/javaee/embeddedAttributeOverlay@2x.png differ diff --git a/platform/icons/src/javaee/embeddedAttributeOverlay@2x_dark.png b/platform/icons/src/javaee/embeddedAttributeOverlay@2x_dark.png new file mode 100755 index 000000000000..942f4cbddb5a Binary files /dev/null and b/platform/icons/src/javaee/embeddedAttributeOverlay@2x_dark.png differ diff --git a/platform/icons/src/javaee/embeddedAttributeOverlay_dark.png b/platform/icons/src/javaee/embeddedAttributeOverlay_dark.png new file mode 100755 index 000000000000..e59fa89a420b Binary files /dev/null and b/platform/icons/src/javaee/embeddedAttributeOverlay_dark.png differ diff --git a/platform/icons/src/javaee/entityBean.png b/platform/icons/src/javaee/entityBean.png old mode 100644 new mode 100755 index 6bd91f219a5e..fa15277c5576 Binary files a/platform/icons/src/javaee/entityBean.png and b/platform/icons/src/javaee/entityBean.png differ diff --git a/platform/icons/src/javaee/entityBean@2x.png b/platform/icons/src/javaee/entityBean@2x.png new file mode 100755 index 000000000000..3b527da79f30 Binary files /dev/null and b/platform/icons/src/javaee/entityBean@2x.png differ diff --git a/platform/icons/src/javaee/entityBean@2x_dark.png b/platform/icons/src/javaee/entityBean@2x_dark.png new file mode 100755 index 000000000000..0a946c280b2b Binary files /dev/null and b/platform/icons/src/javaee/entityBean@2x_dark.png differ diff --git a/platform/icons/src/javaee/entityBeanBig.png b/platform/icons/src/javaee/entityBeanBig.png old mode 100644 new mode 100755 index fa59d640d448..4d81661e0778 Binary files a/platform/icons/src/javaee/entityBeanBig.png and b/platform/icons/src/javaee/entityBeanBig.png differ diff --git a/platform/icons/src/javaee/entityBeanBig@2x.png b/platform/icons/src/javaee/entityBeanBig@2x.png new file mode 100755 index 000000000000..6f5a16f229e6 Binary files /dev/null and b/platform/icons/src/javaee/entityBeanBig@2x.png differ diff --git a/platform/icons/src/javaee/entityBeanBig@2x_dark.png b/platform/icons/src/javaee/entityBeanBig@2x_dark.png new file mode 100755 index 000000000000..67628940b6af Binary files /dev/null and b/platform/icons/src/javaee/entityBeanBig@2x_dark.png differ diff --git a/platform/icons/src/javaee/entityBeanBig_dark.png b/platform/icons/src/javaee/entityBeanBig_dark.png new file mode 100755 index 000000000000..5edeaaa54c37 Binary files /dev/null and b/platform/icons/src/javaee/entityBeanBig_dark.png differ diff --git a/platform/icons/src/javaee/entityBean_dark.png b/platform/icons/src/javaee/entityBean_dark.png new file mode 100755 index 000000000000..e62a2ecf5973 Binary files /dev/null and b/platform/icons/src/javaee/entityBean_dark.png differ diff --git a/platform/icons/src/javaee/home.png b/platform/icons/src/javaee/home.png old mode 100644 new mode 100755 index 5ab0f925cf2d..5d6e70ee7e0a Binary files a/platform/icons/src/javaee/home.png and b/platform/icons/src/javaee/home.png differ diff --git a/platform/icons/src/javaee/home@2x.png b/platform/icons/src/javaee/home@2x.png new file mode 100755 index 000000000000..bbdc01b56665 Binary files /dev/null and b/platform/icons/src/javaee/home@2x.png differ diff --git a/platform/icons/src/javaee/inheritedAttributeOverlay.png b/platform/icons/src/javaee/inheritedAttributeOverlay.png old mode 100644 new mode 100755 index dd829d5d4a0b..8e04255cd9d9 Binary files a/platform/icons/src/javaee/inheritedAttributeOverlay.png and b/platform/icons/src/javaee/inheritedAttributeOverlay.png differ diff --git a/platform/icons/src/javaee/inheritedAttributeOverlay@2x.png b/platform/icons/src/javaee/inheritedAttributeOverlay@2x.png new file mode 100755 index 000000000000..2cb2c2774d08 Binary files /dev/null and b/platform/icons/src/javaee/inheritedAttributeOverlay@2x.png differ diff --git a/platform/icons/src/javaee/inheritedAttributeOverlay@2x_dark.png b/platform/icons/src/javaee/inheritedAttributeOverlay@2x_dark.png new file mode 100755 index 000000000000..f61fe9571bd4 Binary files /dev/null and b/platform/icons/src/javaee/inheritedAttributeOverlay@2x_dark.png differ diff --git a/platform/icons/src/javaee/inheritedAttributeOverlay_dark.png b/platform/icons/src/javaee/inheritedAttributeOverlay_dark.png new file mode 100755 index 000000000000..398e25c21499 Binary files /dev/null and b/platform/icons/src/javaee/inheritedAttributeOverlay_dark.png differ diff --git a/platform/icons/src/javaee/interceptorClass.png b/platform/icons/src/javaee/interceptorClass.png old mode 100644 new mode 100755 index cee608187841..f543e2787238 Binary files a/platform/icons/src/javaee/interceptorClass.png and b/platform/icons/src/javaee/interceptorClass.png differ diff --git a/platform/icons/src/javaee/interceptorClass@2x.png b/platform/icons/src/javaee/interceptorClass@2x.png new file mode 100755 index 000000000000..01837fbc8746 Binary files /dev/null and b/platform/icons/src/javaee/interceptorClass@2x.png differ diff --git a/platform/icons/src/javaee/interceptorMethod.png b/platform/icons/src/javaee/interceptorMethod.png old mode 100644 new mode 100755 index 689653e68f49..146cefb39413 Binary files a/platform/icons/src/javaee/interceptorMethod.png and b/platform/icons/src/javaee/interceptorMethod.png differ diff --git a/platform/icons/src/javaee/interceptorMethod@2x.png b/platform/icons/src/javaee/interceptorMethod@2x.png new file mode 100755 index 000000000000..ca01ef3f5ba1 Binary files /dev/null and b/platform/icons/src/javaee/interceptorMethod@2x.png differ diff --git a/platform/icons/src/javaee/jpaFacet.png b/platform/icons/src/javaee/jpaFacet.png old mode 100644 new mode 100755 index 5bc6a74fc625..b96a2d29aae3 Binary files a/platform/icons/src/javaee/jpaFacet.png and b/platform/icons/src/javaee/jpaFacet.png differ diff --git a/platform/icons/src/javaee/jpaFacet@2x.png b/platform/icons/src/javaee/jpaFacet@2x.png new file mode 100755 index 000000000000..d317d01a1edd Binary files /dev/null and b/platform/icons/src/javaee/jpaFacet@2x.png differ diff --git a/platform/icons/src/javaee/local.png b/platform/icons/src/javaee/local.png old mode 100644 new mode 100755 index ed4ace42f02b..36754143ef8a Binary files a/platform/icons/src/javaee/local.png and b/platform/icons/src/javaee/local.png differ diff --git a/platform/icons/src/javaee/local@2x.png b/platform/icons/src/javaee/local@2x.png new file mode 100755 index 000000000000..477284ed3ef4 Binary files /dev/null and b/platform/icons/src/javaee/local@2x.png differ diff --git a/platform/icons/src/javaee/local@2x_dark.png b/platform/icons/src/javaee/local@2x_dark.png new file mode 100755 index 000000000000..d067e38282be Binary files /dev/null and b/platform/icons/src/javaee/local@2x_dark.png differ diff --git a/platform/icons/src/javaee/localHome.png b/platform/icons/src/javaee/localHome.png old mode 100644 new mode 100755 index 87c66c4721f7..9889c0aa2eb1 Binary files a/platform/icons/src/javaee/localHome.png and b/platform/icons/src/javaee/localHome.png differ diff --git a/platform/icons/src/javaee/localHome@2x.png b/platform/icons/src/javaee/localHome@2x.png new file mode 100755 index 000000000000..fe5706fe056b Binary files /dev/null and b/platform/icons/src/javaee/localHome@2x.png differ diff --git a/platform/icons/src/javaee/localHome@2x_dark.png b/platform/icons/src/javaee/localHome@2x_dark.png new file mode 100755 index 000000000000..44d95fe500c0 Binary files /dev/null and b/platform/icons/src/javaee/localHome@2x_dark.png differ diff --git a/platform/icons/src/javaee/localHome_dark.png b/platform/icons/src/javaee/localHome_dark.png new file mode 100755 index 000000000000..684bfdfdde2b Binary files /dev/null and b/platform/icons/src/javaee/localHome_dark.png differ diff --git a/platform/icons/src/javaee/local_dark.png b/platform/icons/src/javaee/local_dark.png new file mode 100755 index 000000000000..f42e1ed57917 Binary files /dev/null and b/platform/icons/src/javaee/local_dark.png differ diff --git a/platform/icons/src/javaee/messageBean.png b/platform/icons/src/javaee/messageBean.png old mode 100644 new mode 100755 index 37f84fc29e04..a249445a785a Binary files a/platform/icons/src/javaee/messageBean.png and b/platform/icons/src/javaee/messageBean.png differ diff --git a/platform/icons/src/javaee/messageBean@2x.png b/platform/icons/src/javaee/messageBean@2x.png new file mode 100755 index 000000000000..b5e73fec8ba8 Binary files /dev/null and b/platform/icons/src/javaee/messageBean@2x.png differ diff --git a/platform/icons/src/javaee/persistenceAttribute.png b/platform/icons/src/javaee/persistenceAttribute.png old mode 100644 new mode 100755 index d77b78007e6b..293f978d9422 Binary files a/platform/icons/src/javaee/persistenceAttribute.png and b/platform/icons/src/javaee/persistenceAttribute.png differ diff --git a/platform/icons/src/javaee/persistenceAttribute@2x.png b/platform/icons/src/javaee/persistenceAttribute@2x.png new file mode 100755 index 000000000000..58ffb227039b Binary files /dev/null and b/platform/icons/src/javaee/persistenceAttribute@2x.png differ diff --git a/platform/icons/src/javaee/persistenceEmbeddable.png b/platform/icons/src/javaee/persistenceEmbeddable.png old mode 100644 new mode 100755 index e8ada102599b..03f46d92bc53 Binary files a/platform/icons/src/javaee/persistenceEmbeddable.png and b/platform/icons/src/javaee/persistenceEmbeddable.png differ diff --git a/platform/icons/src/javaee/persistenceEmbeddable@2x.png b/platform/icons/src/javaee/persistenceEmbeddable@2x.png new file mode 100755 index 000000000000..0d4858bbc100 Binary files /dev/null and b/platform/icons/src/javaee/persistenceEmbeddable@2x.png differ diff --git a/platform/icons/src/javaee/persistenceEmbeddable@2x_dark.png b/platform/icons/src/javaee/persistenceEmbeddable@2x_dark.png new file mode 100755 index 000000000000..85dd10a3a5d8 Binary files /dev/null and b/platform/icons/src/javaee/persistenceEmbeddable@2x_dark.png differ diff --git a/platform/icons/src/javaee/persistenceEmbeddable_dark.png b/platform/icons/src/javaee/persistenceEmbeddable_dark.png new file mode 100755 index 000000000000..94a876d7aeb8 Binary files /dev/null and b/platform/icons/src/javaee/persistenceEmbeddable_dark.png differ diff --git a/platform/icons/src/javaee/persistenceEntity.png b/platform/icons/src/javaee/persistenceEntity.png old mode 100644 new mode 100755 index cf9264f27386..9f942f970782 Binary files a/platform/icons/src/javaee/persistenceEntity.png and b/platform/icons/src/javaee/persistenceEntity.png differ diff --git a/platform/icons/src/javaee/persistenceEntity@2x.png b/platform/icons/src/javaee/persistenceEntity@2x.png new file mode 100755 index 000000000000..8da8fa567716 Binary files /dev/null and b/platform/icons/src/javaee/persistenceEntity@2x.png differ diff --git a/platform/icons/src/javaee/persistenceEntity@2x_dark.png b/platform/icons/src/javaee/persistenceEntity@2x_dark.png new file mode 100755 index 000000000000..830e28ea190d Binary files /dev/null and b/platform/icons/src/javaee/persistenceEntity@2x_dark.png differ diff --git a/platform/icons/src/javaee/persistenceEntityListener.png b/platform/icons/src/javaee/persistenceEntityListener.png old mode 100644 new mode 100755 index cee608187841..f543e2787238 Binary files a/platform/icons/src/javaee/persistenceEntityListener.png and b/platform/icons/src/javaee/persistenceEntityListener.png differ diff --git a/platform/icons/src/javaee/persistenceEntityListener@2x.png b/platform/icons/src/javaee/persistenceEntityListener@2x.png new file mode 100755 index 000000000000..01837fbc8746 Binary files /dev/null and b/platform/icons/src/javaee/persistenceEntityListener@2x.png differ diff --git a/platform/icons/src/javaee/persistenceEntity_dark.png b/platform/icons/src/javaee/persistenceEntity_dark.png new file mode 100755 index 000000000000..10c8b599bd00 Binary files /dev/null and b/platform/icons/src/javaee/persistenceEntity_dark.png differ diff --git a/platform/icons/src/javaee/persistenceId.png b/platform/icons/src/javaee/persistenceId.png old mode 100644 new mode 100755 index b1e9983904d6..f4d960e10e90 Binary files a/platform/icons/src/javaee/persistenceId.png and b/platform/icons/src/javaee/persistenceId.png differ diff --git a/platform/icons/src/javaee/persistenceId@2x.png b/platform/icons/src/javaee/persistenceId@2x.png new file mode 100755 index 000000000000..a19c74f3f9a9 Binary files /dev/null and b/platform/icons/src/javaee/persistenceId@2x.png differ diff --git a/platform/icons/src/javaee/persistenceId@2x_dark.png b/platform/icons/src/javaee/persistenceId@2x_dark.png new file mode 100755 index 000000000000..21ada9090f86 Binary files /dev/null and b/platform/icons/src/javaee/persistenceId@2x_dark.png differ diff --git a/platform/icons/src/javaee/persistenceIdRelationship.png b/platform/icons/src/javaee/persistenceIdRelationship.png old mode 100644 new mode 100755 index 8889522ffbd6..565399d12b92 Binary files a/platform/icons/src/javaee/persistenceIdRelationship.png and b/platform/icons/src/javaee/persistenceIdRelationship.png differ diff --git a/platform/icons/src/javaee/persistenceIdRelationship@2x.png b/platform/icons/src/javaee/persistenceIdRelationship@2x.png new file mode 100755 index 000000000000..0b37bf06d49c Binary files /dev/null and b/platform/icons/src/javaee/persistenceIdRelationship@2x.png differ diff --git a/platform/icons/src/javaee/persistenceIdRelationship@2x_dark.png b/platform/icons/src/javaee/persistenceIdRelationship@2x_dark.png new file mode 100755 index 000000000000..9dd16bd357dc Binary files /dev/null and b/platform/icons/src/javaee/persistenceIdRelationship@2x_dark.png differ diff --git a/platform/icons/src/javaee/persistenceIdRelationship_dark.png b/platform/icons/src/javaee/persistenceIdRelationship_dark.png new file mode 100755 index 000000000000..2b0a5db7f0d9 Binary files /dev/null and b/platform/icons/src/javaee/persistenceIdRelationship_dark.png differ diff --git a/platform/icons/src/javaee/persistenceId_dark.png b/platform/icons/src/javaee/persistenceId_dark.png new file mode 100755 index 000000000000..1be9a7b226ba Binary files /dev/null and b/platform/icons/src/javaee/persistenceId_dark.png differ diff --git a/platform/icons/src/javaee/persistenceMappedSuperclass.png b/platform/icons/src/javaee/persistenceMappedSuperclass.png old mode 100644 new mode 100755 index f51d41d3c4f2..c65f565a1cf5 Binary files a/platform/icons/src/javaee/persistenceMappedSuperclass.png and b/platform/icons/src/javaee/persistenceMappedSuperclass.png differ diff --git a/platform/icons/src/javaee/persistenceMappedSuperclass@2x.png b/platform/icons/src/javaee/persistenceMappedSuperclass@2x.png new file mode 100755 index 000000000000..84231ab9ac4f Binary files /dev/null and b/platform/icons/src/javaee/persistenceMappedSuperclass@2x.png differ diff --git a/platform/icons/src/javaee/persistenceRelationship.png b/platform/icons/src/javaee/persistenceRelationship.png old mode 100644 new mode 100755 index 39537283d2e3..6ce6b653e2e3 Binary files a/platform/icons/src/javaee/persistenceRelationship.png and b/platform/icons/src/javaee/persistenceRelationship.png differ diff --git a/platform/icons/src/javaee/persistenceRelationship@2x.png b/platform/icons/src/javaee/persistenceRelationship@2x.png new file mode 100755 index 000000000000..71494e4ad1c4 Binary files /dev/null and b/platform/icons/src/javaee/persistenceRelationship@2x.png differ diff --git a/platform/icons/src/javaee/persistenceUnit.png b/platform/icons/src/javaee/persistenceUnit.png old mode 100644 new mode 100755 index 4198f3f2e53d..6e7c376533e5 Binary files a/platform/icons/src/javaee/persistenceUnit.png and b/platform/icons/src/javaee/persistenceUnit.png differ diff --git a/platform/icons/src/javaee/persistenceUnit@2x.png b/platform/icons/src/javaee/persistenceUnit@2x.png new file mode 100755 index 000000000000..b8fea6480ac9 Binary files /dev/null and b/platform/icons/src/javaee/persistenceUnit@2x.png differ diff --git a/platform/icons/src/javaee/remote.png b/platform/icons/src/javaee/remote.png old mode 100644 new mode 100755 index 7261ae432449..20a16df76c93 Binary files a/platform/icons/src/javaee/remote.png and b/platform/icons/src/javaee/remote.png differ diff --git a/platform/icons/src/javaee/remote@2x.png b/platform/icons/src/javaee/remote@2x.png new file mode 100755 index 000000000000..134bce3bc8b3 Binary files /dev/null and b/platform/icons/src/javaee/remote@2x.png differ diff --git a/platform/icons/src/javaee/remote@2x_dark.png b/platform/icons/src/javaee/remote@2x_dark.png new file mode 100755 index 000000000000..e697b4f1acf8 Binary files /dev/null and b/platform/icons/src/javaee/remote@2x_dark.png differ diff --git a/platform/icons/src/javaee/remote_dark.png b/platform/icons/src/javaee/remote_dark.png new file mode 100755 index 000000000000..520a42de5499 Binary files /dev/null and b/platform/icons/src/javaee/remote_dark.png differ diff --git a/platform/icons/src/javaee/sessionBean.png b/platform/icons/src/javaee/sessionBean.png old mode 100644 new mode 100755 index 2b3cc8d12366..61a450918959 Binary files a/platform/icons/src/javaee/sessionBean.png and b/platform/icons/src/javaee/sessionBean.png differ diff --git a/platform/icons/src/javaee/sessionBean@2x.png b/platform/icons/src/javaee/sessionBean@2x.png new file mode 100755 index 000000000000..a5a1fd22750b Binary files /dev/null and b/platform/icons/src/javaee/sessionBean@2x.png differ diff --git a/platform/icons/src/javaee/updateRunningApplication.png b/platform/icons/src/javaee/updateRunningApplication.png old mode 100644 new mode 100755 index b7f806f47818..92651293a5d5 Binary files a/platform/icons/src/javaee/updateRunningApplication.png and b/platform/icons/src/javaee/updateRunningApplication.png differ diff --git a/platform/icons/src/javaee/updateRunningApplication@2x.png b/platform/icons/src/javaee/updateRunningApplication@2x.png old mode 100644 new mode 100755 index 6c5e3f732f04..5acea70c114f Binary files a/platform/icons/src/javaee/updateRunningApplication@2x.png and b/platform/icons/src/javaee/updateRunningApplication@2x.png differ diff --git a/platform/icons/src/javaee/webModule.png b/platform/icons/src/javaee/webModule.png old mode 100644 new mode 100755 index 7e93bfff0f5e..0263085a2ab4 Binary files a/platform/icons/src/javaee/webModule.png and b/platform/icons/src/javaee/webModule.png differ diff --git a/platform/icons/src/javaee/webModule@2x.png b/platform/icons/src/javaee/webModule@2x.png new file mode 100755 index 000000000000..14a4980ebc26 Binary files /dev/null and b/platform/icons/src/javaee/webModule@2x.png differ diff --git a/platform/icons/src/javaee/webModuleGroup.png b/platform/icons/src/javaee/webModuleGroup.png old mode 100644 new mode 100755 index 6e81e1ec6dc3..61fa40474877 Binary files a/platform/icons/src/javaee/webModuleGroup.png and b/platform/icons/src/javaee/webModuleGroup.png differ diff --git a/platform/icons/src/javaee/webModuleGroup@2x.png b/platform/icons/src/javaee/webModuleGroup@2x.png new file mode 100755 index 000000000000..b204e4ebf10f Binary files /dev/null and b/platform/icons/src/javaee/webModuleGroup@2x.png differ diff --git a/platform/icons/src/javaee/web_xml.png b/platform/icons/src/javaee/web_xml.png old mode 100644 new mode 100755 index fc32397ca6fc..b750aaf45da9 Binary files a/platform/icons/src/javaee/web_xml.png and b/platform/icons/src/javaee/web_xml.png differ diff --git a/platform/icons/src/javaee/web_xml@2x.png b/platform/icons/src/javaee/web_xml@2x.png old mode 100644 new mode 100755 index 1b9d1582e236..2b2bf2d22daf Binary files a/platform/icons/src/javaee/web_xml@2x.png and b/platform/icons/src/javaee/web_xml@2x.png differ diff --git a/platform/lang-api/src/com/intellij/execution/filters/UrlFilter.java b/platform/lang-api/src/com/intellij/execution/filters/UrlFilter.java index cac68aa3a32a..c9bf47d6e435 100644 --- a/platform/lang-api/src/com/intellij/execution/filters/UrlFilter.java +++ b/platform/lang-api/src/com/intellij/execution/filters/UrlFilter.java @@ -27,7 +27,7 @@ import java.util.regex.Pattern; * @author yole */ public class UrlFilter implements Filter { - public static final Pattern URL_PATTERN = Pattern.compile("\\b(https?://|www\\.)[-A-Za-z0-9+&@#/%?=~_|!:,.;]*[-A-Za-z0-9+&@#/%=~_|]"); + public static final Pattern URL_PATTERN = Pattern.compile("\\b(mailto\\:|(news|(ht|f)tp(s?))\\://|www\\.)[-A-Za-z0-9+&@#/%?=~_|!:,.;]*[-A-Za-z0-9+&@#/%=~_|]"); @Nullable @Override diff --git a/platform/lang-api/src/com/intellij/execution/runners/ExecutionUtil.java b/platform/lang-api/src/com/intellij/execution/runners/ExecutionUtil.java index 1c3d265e4c86..cb2c3225e83f 100644 --- a/platform/lang-api/src/com/intellij/execution/runners/ExecutionUtil.java +++ b/platform/lang-api/src/com/intellij/execution/runners/ExecutionUtil.java @@ -23,6 +23,7 @@ import com.intellij.execution.process.ProcessNotCreatedException; import com.intellij.execution.ui.RunContentDescriptor; import com.intellij.ide.DataManager; import com.intellij.ide.util.PropertiesComponent; +import com.intellij.notification.Notification; import com.intellij.notification.NotificationGroup; import com.intellij.notification.NotificationListener; import com.intellij.notification.NotificationType; @@ -34,7 +35,6 @@ import com.intellij.openapi.ui.MessageType; import com.intellij.openapi.ui.Messages; import com.intellij.openapi.wm.ToolWindowManager; import com.intellij.ui.content.Content; -import com.intellij.util.ObjectUtils; import com.intellij.util.ui.UIUtil; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -124,7 +124,12 @@ public class ExecutionUtil { else { Messages.showErrorDialog(project, UIUtil.toHtml(fullMessage), ""); } - NotificationListener notificationListener = ObjectUtils.tryCast(finalListener, NotificationListener.class); + NotificationListener notificationListener = finalListener == null ? null : new NotificationListener() { + @Override + public void hyperlinkUpdate(@NotNull Notification notification, @NotNull HyperlinkEvent event) { + finalListener.hyperlinkUpdate(event); + } + }; ourNotificationGroup.createNotification(title, finalDescription, NotificationType.ERROR, notificationListener).notify(project); } }); diff --git a/platform/lang-impl/src/com/intellij/codeInsight/documentation/AbstractExternalFilter.java b/platform/lang-impl/src/com/intellij/codeInsight/documentation/AbstractExternalFilter.java index a64917f88e4e..d923262be097 100644 --- a/platform/lang-impl/src/com/intellij/codeInsight/documentation/AbstractExternalFilter.java +++ b/platform/lang-impl/src/com/intellij/codeInsight/documentation/AbstractExternalFilter.java @@ -37,7 +37,6 @@ import org.jetbrains.annotations.Nullable; import java.io.*; import java.net.URL; -import java.net.URLConnection; import java.util.Locale; import java.util.concurrent.Future; import java.util.jar.JarFile; @@ -243,34 +242,27 @@ public abstract class AbstractExternalFilter { }); } + @Nullable private static String guessEncoding(URL url) { - String result = null; - BufferedReader reader = null; - try { - URLConnection connection = url.openConnection(); - result = connection.getContentEncoding(); - if (result != null) return result; - //noinspection IOResourceOpenedButNotSafelyClosed - reader = new BufferedReader(new InputStreamReader(connection.getInputStream())); - for (String htmlLine = reader.readLine(); htmlLine != null; htmlLine = reader.readLine()) { - result = parseContentEncoding(htmlLine); - if (result != null) { - break; - } - } - } - catch (IOException ignored) { - } - finally { - if (reader != null) { + return HttpRequests.request(url.toExternalForm()).connect(new HttpRequests.RequestProcessor() { + @Override + public String process(@NotNull HttpRequests.Request request) throws IOException { + String result = request.getConnection().getContentEncoding(); + BufferedReader reader = new BufferedReader(new InputStreamReader(request.getInputStream())); try { + for (String htmlLine = reader.readLine(); htmlLine != null; htmlLine = reader.readLine()) { + result = parseContentEncoding(htmlLine); + if (result != null) { + break; + } + } + } + finally { reader.close(); } - catch (IOException ignored) { - } + return result; } - } - return result; + }, null, null); } @Nullable @@ -475,11 +467,9 @@ public abstract class AbstractExternalFilter { if (!htmlLine.contains("charset")) { return null; } - final Matcher matcher = CHARSET_META_PATTERN.matcher(htmlLine); - if (matcher.find()) { - return matcher.group(1); - } - return null; + + Matcher matcher = CHARSET_META_PATTERN.matcher(htmlLine); + return matcher.find() ? matcher.group(1) : null; } private static void appendLine(StringBuilder buffer, final String read) { diff --git a/platform/lang-impl/src/com/intellij/codeInsight/documentation/ArbitraryPlaceUrlReferenceProvider.java b/platform/lang-impl/src/com/intellij/codeInsight/documentation/ArbitraryPlaceUrlReferenceProvider.java new file mode 100644 index 000000000000..9bd3fe96b5cf --- /dev/null +++ b/platform/lang-impl/src/com/intellij/codeInsight/documentation/ArbitraryPlaceUrlReferenceProvider.java @@ -0,0 +1,82 @@ +/* + * 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.codeInsight.documentation; + +import com.intellij.execution.filters.UrlFilter; +import com.intellij.openapi.paths.GlobalPathReferenceProvider; +import com.intellij.openapi.paths.PathReferenceManager; +import com.intellij.openapi.util.TextRange; +import com.intellij.openapi.util.UserDataCache; +import com.intellij.psi.PsiElement; +import com.intellij.psi.PsiReference; +import com.intellij.psi.PsiReferenceProvider; +import com.intellij.psi.util.CachedValue; +import com.intellij.psi.util.CachedValueProvider; +import com.intellij.psi.util.CachedValuesManager; +import com.intellij.util.ProcessingContext; +import com.intellij.util.SmartList; +import org.jetbrains.annotations.NotNull; + +import java.util.List; +import java.util.concurrent.atomic.AtomicReference; +import java.util.regex.Matcher; + +/** +* Created by Maxim.Mossienko on 12/19/2014. +*/ +public class ArbitraryPlaceUrlReferenceProvider extends PsiReferenceProvider { + public static final ArbitraryPlaceUrlReferenceProvider INSTANCE = new ArbitraryPlaceUrlReferenceProvider(); + + private static final UserDataCache, PsiElement, Object> ourRefsCache = new UserDataCache, PsiElement, Object>("psielement.url.refs") { + private final AtomicReference myReferenceProvider = new AtomicReference(); + + @Override + protected CachedValue compute(final PsiElement element, Object p) { + return CachedValuesManager + .getManager(element.getProject()).createCachedValue(new CachedValueProvider() { + public Result compute() { + Matcher matcher = UrlFilter.URL_PATTERN.matcher(element.getText()); + + List refs = null; + GlobalPathReferenceProvider provider = myReferenceProvider.get(); + + while (matcher.find()) { + final int start = matcher.start(); + final int end = matcher.end(); + if (refs == null) refs = new SmartList(); + if (provider == null) { + provider = (GlobalPathReferenceProvider)PathReferenceManager.getInstance().getGlobalWebPathReferenceProvider(); + myReferenceProvider.lazySet(provider); + } + + provider.createUrlReference(element, matcher.group(0), new TextRange(start, end), refs); + } + + return new Result(refs != null ? refs.toArray(new PsiReference[refs.size()]) : PsiReference.EMPTY_ARRAY, + element); + } + }, false); + + } + }; + + + @NotNull + @Override + public PsiReference[] getReferencesByElement(@NotNull final PsiElement element, @NotNull ProcessingContext context) { + return ourRefsCache.get(element, null).getValue(); + } +} diff --git a/platform/lang-impl/src/com/intellij/codeInsight/navigation/actions/GotoDeclarationAction.java b/platform/lang-impl/src/com/intellij/codeInsight/navigation/actions/GotoDeclarationAction.java index d34cbf4cfa09..a633b302c969 100644 --- a/platform/lang-impl/src/com/intellij/codeInsight/navigation/actions/GotoDeclarationAction.java +++ b/platform/lang-impl/src/com/intellij/codeInsight/navigation/actions/GotoDeclarationAction.java @@ -76,6 +76,7 @@ public class GotoDeclarationAction extends BaseCodeInsightAction implements Code public void invoke(@NotNull final Project project, @NotNull Editor editor, @NotNull PsiFile file) { PsiDocumentManager.getInstance(project).commitAllDocuments(); + DumbService.getInstance(project).setAlternativeResolveEnabled(true); try { int offset = editor.getCaretModel().getOffset(); PsiElement[] elements = findAllTargetElements(project, editor, offset); @@ -105,6 +106,9 @@ public class GotoDeclarationAction extends BaseCodeInsightAction implements Code catch (IndexNotReadyException e) { DumbService.getInstance(project).showDumbModeNotification("Navigation is not available here during index update"); } + finally { + DumbService.getInstance(project).setAlternativeResolveEnabled(false); + } } public static PsiNameIdentifierOwner findElementToShowUsagesOf(@NotNull Editor editor, @NotNull PsiFile file, int offset) { diff --git a/platform/lang-impl/src/com/intellij/codeInsight/navigation/actions/GotoTypeDeclarationAction.java b/platform/lang-impl/src/com/intellij/codeInsight/navigation/actions/GotoTypeDeclarationAction.java index 190ce1d913bd..eb4861f733ff 100644 --- a/platform/lang-impl/src/com/intellij/codeInsight/navigation/actions/GotoTypeDeclarationAction.java +++ b/platform/lang-impl/src/com/intellij/codeInsight/navigation/actions/GotoTypeDeclarationAction.java @@ -27,6 +27,8 @@ import com.intellij.openapi.extensions.Extensions; import com.intellij.openapi.fileEditor.FileEditorManager; import com.intellij.openapi.fileEditor.OpenFileDescriptor; import com.intellij.openapi.project.DumbAware; +import com.intellij.openapi.project.DumbService; +import com.intellij.openapi.project.IndexNotReadyException; import com.intellij.openapi.project.Project; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.psi.*; @@ -64,14 +66,23 @@ public class GotoTypeDeclarationAction extends BaseCodeInsightAction implements public void invoke(@NotNull final Project project, @NotNull Editor editor, @NotNull PsiFile file) { PsiDocumentManager.getInstance(project).commitAllDocuments(); - int offset = editor.getCaretModel().getOffset(); - PsiElement[] symbolTypes = findSymbolTypes(editor, offset); - if (symbolTypes == null || symbolTypes.length == 0) return; - if (symbolTypes.length == 1) { - navigate(project, symbolTypes[0]); + DumbService.getInstance(project).setAlternativeResolveEnabled(true); + try { + int offset = editor.getCaretModel().getOffset(); + PsiElement[] symbolTypes = findSymbolTypes(editor, offset); + if (symbolTypes == null || symbolTypes.length == 0) return; + if (symbolTypes.length == 1) { + navigate(project, symbolTypes[0]); + } + else { + NavigationUtil.getPsiElementPopup(symbolTypes, CodeInsightBundle.message("choose.type.popup.title")).showInBestPositionFor(editor); + } } - else { - NavigationUtil.getPsiElementPopup(symbolTypes, CodeInsightBundle.message("choose.type.popup.title")).showInBestPositionFor(editor); + catch (IndexNotReadyException e) { + DumbService.getInstance(project).showDumbModeNotification("Navigation is not available here during index update"); + } + finally { + DumbService.getInstance(project).setAlternativeResolveEnabled(false); } } diff --git a/platform/lang-impl/src/com/intellij/execution/impl/RunManagerImpl.java b/platform/lang-impl/src/com/intellij/execution/impl/RunManagerImpl.java index 9172d7280cd8..769cd314585d 100644 --- a/platform/lang-impl/src/com/intellij/execution/impl/RunManagerImpl.java +++ b/platform/lang-impl/src/com/intellij/execution/impl/RunManagerImpl.java @@ -58,8 +58,7 @@ public class RunManagerImpl extends RunManagerEx implements PersistentStateCompo private final Map myTypesByName = new LinkedHashMap(); - private final Map myTemplateConfigurationsMap = - new THashMap(); + private final Map myTemplateConfigurationsMap = new TreeMap(); private final Map myConfigurations = new LinkedHashMap(); // template configurations are not included here private final Map mySharedConfigurations = new THashMap(); @@ -558,7 +557,6 @@ public class RunManagerImpl extends RunManagerEx implements PersistentStateCompo addConfigurationElement(parentNode, configuration); } - // temp && stable configurations, !unknown JDOMExternalizableStringList order = null; for (RunnerAndConfigurationSettings each : myConfigurations.values()) { if (each.getType() instanceof UnknownConfigurationType) { diff --git a/platform/lang-impl/src/com/intellij/find/impl/FindInProjectUtil.java b/platform/lang-impl/src/com/intellij/find/impl/FindInProjectUtil.java index 3bf96d0891af..3d064e69cc9e 100644 --- a/platform/lang-impl/src/com/intellij/find/impl/FindInProjectUtil.java +++ b/platform/lang-impl/src/com/intellij/find/impl/FindInProjectUtil.java @@ -42,10 +42,14 @@ import com.intellij.openapi.util.Computable; import com.intellij.openapi.util.Factory; import com.intellij.openapi.util.TextRange; import com.intellij.openapi.util.text.StringUtil; -import com.intellij.openapi.vfs.*; +import com.intellij.openapi.vfs.LocalFileProvider; +import com.intellij.openapi.vfs.LocalFileSystem; +import com.intellij.openapi.vfs.VirtualFile; +import com.intellij.openapi.vfs.VirtualFileManager; import com.intellij.openapi.vfs.ex.VirtualFileManagerEx; import com.intellij.psi.*; import com.intellij.psi.search.GlobalSearchScope; +import com.intellij.psi.search.GlobalSearchScopesCore; import com.intellij.psi.search.LocalSearchScope; import com.intellij.psi.search.SearchScope; import com.intellij.ui.content.Content; @@ -435,7 +439,6 @@ public class FindInProjectUtil { sink.put(UsageView.USAGE_SCOPE, scope); } } - } @NotNull @@ -445,44 +448,11 @@ public class FindInProjectUtil { VirtualFile directory = psiDir == null ? null : psiDir.getVirtualFile(); Module module = findModel.getModuleName() == null ? null : ModuleManager.getInstance(project).findModuleByName(findModel.getModuleName()); return findModel.isCustomScope() && customScope != null ? customScope : - directory != null ? new UnderDirectoryScope(directory) : - module != null ? GlobalSearchScope.moduleScope(module) : - findModel.isProjectScope() ? GlobalSearchScope.projectScope(project) : - GlobalSearchScope.allScope(project); - } - - private static class UnderDirectoryScope extends GlobalSearchScope { - @NotNull private final VirtualFile myRoot; - - private UnderDirectoryScope(@NotNull VirtualFile root) { - myRoot = root; - assert root.isDirectory(); - } - - @NotNull - @Override - public String getDisplayName() { - return "Directory '" + myRoot.getName() + "'"; - } - - @Override - public boolean contains(@NotNull VirtualFile file) { - return VfsUtilCore.isAncestor(myRoot, file, false); - } - - @Override - public int compare(@NotNull VirtualFile file1, @NotNull VirtualFile file2) { - return 0; - } - - @Override - public boolean isSearchInModuleContent(@NotNull Module aModule) { - return false; - } - - @Override - public boolean isSearchInLibraries() { - return false; - } + // we don't have to check for myProjectFileIndex.isExcluded(file) here like FindInProjectTask.collectFilesInScope() does + // because all found usages are guaranteed to be not in excluded dir + directory != null ? GlobalSearchScopesCore.directoryScope(project, directory, findModel.isWithSubdirectories()) : + module != null ? GlobalSearchScope.moduleScope(module) : + findModel.isProjectScope() ? GlobalSearchScope.projectScope(project) : + GlobalSearchScope.allScope(project); } } diff --git a/platform/lang-impl/src/com/intellij/ide/scratch/NewScratchFileAction.java b/platform/lang-impl/src/com/intellij/ide/scratch/NewScratchFileAction.java index 394e64050c71..d6cbd4e4cb17 100644 --- a/platform/lang-impl/src/com/intellij/ide/scratch/NewScratchFileAction.java +++ b/platform/lang-impl/src/com/intellij/ide/scratch/NewScratchFileAction.java @@ -20,12 +20,16 @@ import com.intellij.ide.util.PropertiesComponent; import com.intellij.lang.Language; import com.intellij.lang.LanguageUtil; import com.intellij.lang.StdLanguages; -import com.intellij.openapi.actionSystem.AnAction; +import com.intellij.lang.injection.InjectedLanguageManager; import com.intellij.openapi.actionSystem.AnActionEvent; import com.intellij.openapi.actionSystem.CommonDataKeys; +import com.intellij.openapi.application.ApplicationManager; +import com.intellij.openapi.editor.Caret; +import com.intellij.openapi.editor.Document; +import com.intellij.openapi.editor.Editor; import com.intellij.openapi.fileEditor.FileEditorManager; import com.intellij.openapi.fileTypes.LanguageFileType; -import com.intellij.openapi.project.DumbAware; +import com.intellij.openapi.project.DumbAwareAction; import com.intellij.openapi.project.Project; import com.intellij.openapi.ui.popup.JBPopupFactory; import com.intellij.openapi.ui.popup.ListPopup; @@ -35,8 +39,7 @@ import com.intellij.openapi.ui.popup.util.BaseListPopupStep; import com.intellij.openapi.util.registry.Registry; import com.intellij.openapi.util.text.StringUtil; import com.intellij.openapi.vfs.VirtualFile; -import com.intellij.psi.LanguageSubstitutors; -import com.intellij.psi.PsiFile; +import com.intellij.psi.*; import com.intellij.testFramework.LightVirtualFile; import com.intellij.util.Consumer; import com.intellij.util.containers.ContainerUtil; @@ -52,7 +55,7 @@ import java.util.List; /** * @author ignatov */ -public class NewScratchFileAction extends AnAction implements DumbAware { +public class NewScratchFileAction extends DumbAwareAction { public static final int MAX_VISIBLE_SIZE = 20; public NewScratchFileAction() { @@ -61,9 +64,14 @@ public class NewScratchFileAction extends AnAction implements DumbAware { @Override public void update(@NotNull AnActionEvent e) { - e.getPresentation().setEnabledAndVisible(e.getProject() != null && Registry.is("ide.scratch.enabled")); + e.getPresentation().setEnabledAndVisible(isEnabled(e)); } - + + public static boolean isEnabled(@NotNull AnActionEvent e) { + return e.getProject() != null && Registry.is("ide.scratch.enabled"); + } + + @NotNull public static List getLastUsedLanguagesIds(Project project) { String[] values = PropertiesComponent.getInstance(project).getValues(ScratchpadManager.class.getName()); return values == null ? ContainerUtil.emptyList() : ContainerUtil.list(values); @@ -75,26 +83,67 @@ public class NewScratchFileAction extends AnAction implements DumbAware { if (project == null) return; PsiFile file = e.getData(CommonDataKeys.PSI_FILE); - Language context = file != null ? file.getLanguage() : null; + Editor editor = e.getData(CommonDataKeys.EDITOR); + + Language language = getLanguageFromCaret(project, editor, file); + String text = getSelectionText(editor); + if (language != null && text != null) { + openNewFile(project, language, text); + return; + } - ListPopup popup = buildLanguagePopup(project, context, new Consumer() { + ListPopup popup = buildLanguagePopup(project, language, new Consumer() { @Override - public void consume(Language language) { - FeatureUsageTracker.getInstance().triggerFeatureUsed("scratch"); - VirtualFile file = ScratchpadManager.getInstance(project).createScratchFile(substitute(project, language)); - FileEditorManager.getInstance(project).openFile(file, true); + public void consume(@NotNull Language language) { + openNewFile(project, language, ""); } }); popup.showCenteredInCurrentWindow(project); } + @Nullable + public String getSelectionText(@Nullable Editor editor) { + if (editor == null) return null; + return editor.getSelectionModel().getSelectedText(); + } + + @Nullable + public Language getLanguageFromCaret(@NotNull Project project, + @Nullable Editor editor, + @Nullable PsiFile psiFile) { + if (editor == null) return null; + if (psiFile == null) return null; + Caret caret = editor.getCaretModel().getPrimaryCaret(); + int offset = caret.getOffset(); + PsiElement element = InjectedLanguageManager.getInstance(project).findInjectedElementAt(psiFile, offset); + element = element == null ? psiFile.findElementAt(offset) : element; + Language language = element != null ? element.getLanguage() : psiFile.getLanguage(); + return substitute(project, language); + } + + public static void openNewFile(@NotNull Project project, @NotNull Language language, @NotNull final String text) { + FeatureUsageTracker.getInstance().triggerFeatureUsed("scratch"); + VirtualFile file = ScratchpadManager.getInstance(project).createScratchFile(substitute(project, language)); + PsiFile psiFile = PsiManager.getInstance(project).findFile(file); + final Document document = psiFile == null ? null : PsiDocumentManager.getInstance(project).getDocument(psiFile); + if (document != null && StringUtil.isNotEmpty(text)) { + ApplicationManager.getApplication().runWriteAction(new Runnable() { + @Override + public void run() { + document.setText(text); + } + }); + } + FileEditorManager.getInstance(project).openFile(file, true); + } + @NotNull public static Language substitute(@NotNull Project project, @NotNull Language language) { return LanguageSubstitutors.INSTANCE.substituteLanguage(language, new LightVirtualFile(), project); } @NotNull - static ListPopup buildLanguagePopup(@NotNull Project project, @Nullable Language context, final Consumer onChoosen) { + static ListPopup buildLanguagePopup(@NotNull Project project, @Nullable Language context, @NotNull final Consumer onChoosen) { List languages = LanguageUtil.getFileLanguages(); final List ids = ContainerUtil.newArrayList(getLastUsedLanguagesIds(project)); if (context != null) { @@ -118,7 +167,7 @@ public class NewScratchFileAction extends AnAction implements DumbAware { new BaseListPopupStep("Choose Language", languages) { @NotNull @Override - public String getTextFor(Language value) { + public String getTextFor(@NotNull Language value) { return value.getDisplayName(); } @@ -134,7 +183,7 @@ public class NewScratchFileAction extends AnAction implements DumbAware { } @Override - public Icon getIconFor(Language language) { + public Icon getIconFor(@NotNull Language language) { LanguageFileType associatedLanguage = language.getAssociatedFileType(); return associatedLanguage != null ? associatedLanguage.getIcon() : null; } @@ -150,6 +199,7 @@ public class NewScratchFileAction extends AnAction implements DumbAware { ListPopupStep step = popup.getListStep(); List values = step.getValues(); for (Object v : values) { + //noinspection unchecked nameLen = Math.max(nameLen, step.getTextFor(v).length()); } if (values.size() > MAX_VISIBLE_SIZE) { diff --git a/platform/lang-impl/src/com/intellij/ide/util/gotoByName/ChooseByNameBase.java b/platform/lang-impl/src/com/intellij/ide/util/gotoByName/ChooseByNameBase.java index f5c06224f8c7..ff3ad83bcafe 100644 --- a/platform/lang-impl/src/com/intellij/ide/util/gotoByName/ChooseByNameBase.java +++ b/platform/lang-impl/src/com/intellij/ide/util/gotoByName/ChooseByNameBase.java @@ -48,6 +48,7 @@ import com.intellij.openapi.progress.Task; import com.intellij.openapi.progress.util.ProgressIndicatorBase; import com.intellij.openapi.progress.util.ProgressIndicatorUtils; import com.intellij.openapi.progress.util.ReadTask; +import com.intellij.openapi.progress.util.TooManyUsagesStatus; import com.intellij.openapi.project.Project; import com.intellij.openapi.ui.popup.*; import com.intellij.openapi.util.*; @@ -71,8 +72,8 @@ import com.intellij.ui.popup.PopupOwner; import com.intellij.ui.popup.PopupPositionManager; import com.intellij.ui.popup.PopupUpdateProcessor; import com.intellij.usageView.UsageInfo; -import com.intellij.usageView.UsageViewBundle; import com.intellij.usages.*; +import com.intellij.usages.impl.UsageViewManagerImpl; import com.intellij.util.Alarm; import com.intellij.util.Consumer; import com.intellij.util.Processor; @@ -102,7 +103,6 @@ import java.awt.*; import java.awt.event.*; import java.util.*; import java.util.List; -import java.util.concurrent.atomic.AtomicBoolean; public abstract class ChooseByNameBase { private static final Logger LOG = Logger.getInstance("#com.intellij.ide.util.gotoByName.ChooseByNameBase"); @@ -1541,18 +1541,18 @@ public abstract class ChooseByNameBase { new CalcElementsThread(myPattern, myCheckboxState, myCallback, myModalityState, myScopeExpanded).scheduleThread(); } - public void addElementsByPattern(@NotNull String pattern, + private void addElementsByPattern(@NotNull String pattern, @NotNull final Set elements, - @NotNull final ProgressIndicator cancelled, + @NotNull final ProgressIndicator indicator, boolean everywhere) { long start = System.currentTimeMillis(); myProvider.filterElements( ChooseByNameBase.this, pattern, everywhere, - cancelled, + indicator, new Processor() { @Override public boolean process(Object o) { - if (cancelled.isCanceled()) return false; + if (indicator.isCanceled()) return false; elements.add(o); if (isOverflow(elements)) { @@ -1653,8 +1653,9 @@ public abstract class ChooseByNameBase { cancelListUpdater(); final UsageViewPresentation presentation = new UsageViewPresentation(); - final String prefixPattern = myFindUsagesTitle + " \'" + myTextField.getText().trim() + "\'"; - final String nonPrefixPattern = myFindUsagesTitle + " \'*" + myTextField.getText().trim() + "*\'"; + final String text = myTextField.getText(); + final String prefixPattern = myFindUsagesTitle + " \'" + text.trim() + "\'"; + final String nonPrefixPattern = myFindUsagesTitle + " \'*" + text.trim() + "*\'"; presentation.setCodeUsagesString(prefixPattern); presentation.setUsagesInGeneratedCodeString(prefixPattern + " in generated code"); presentation.setDynamicUsagesString(nonPrefixPattern); @@ -1667,45 +1668,38 @@ public abstract class ChooseByNameBase { fillUsages(Arrays.asList(elements[0]), usages, targets, false); fillUsages(Arrays.asList(elements[1]), usages, targets, true); if (myListModel.contains(EXTRA_ELEM)) { //start searching for the rest - final String text = myTextField.getText(); final boolean everywhere = myCheckBox.isSelected(); - final LinkedHashSet prefixMatchElementsArray = new LinkedHashSet(); - final LinkedHashSet nonPrefixMatchElementsArray = new LinkedHashSet(); + final Set prefixMatchElementsArray = new LinkedHashSet(); + final Set nonPrefixMatchElementsArray = new LinkedHashSet(); hideHint(); ProgressManager.getInstance().run(new Task.Modal(myProject, prefixPattern, true) { private ChooseByNameBase.CalcElementsThread myCalcUsagesThread; - @Override public void run(@NotNull final ProgressIndicator indicator) { ensureNamesLoaded(everywhere); indicator.setIndeterminate(true); - ApplicationManager.getApplication().runReadAction(new Runnable() { + final TooManyUsagesStatus tooManyUsagesStatus = TooManyUsagesStatus.createFor(indicator); + myCalcUsagesThread = new CalcElementsThread(text, everywhere, null, ModalityState.NON_MODAL, false) { + @Override + protected boolean isOverflow(@NotNull Set elementsArray) { + tooManyUsagesStatus.pauseProcessingIfTooManyUsages(); + if (elementsArray.size() > UsageLimitUtil.USAGES_LIMIT - myMaximumListSizeLimit && tooManyUsagesStatus.switchTooManyUsagesStatus()) { + int usageCount = elementsArray.size() + myMaximumListSizeLimit; + UsageViewManagerImpl.showTooManyUsagesWarning(getProject(), tooManyUsagesStatus, indicator, presentation, usageCount, null); + } + return false; + } + }; + ApplicationManager.getApplication().runReadAction(new Runnable() { @Override public void run() { - final boolean[] overFlow = {false}; - myCalcUsagesThread = new CalcElementsThread(text, everywhere, null, ModalityState.NON_MODAL, false) { - private final AtomicBoolean userAskedToAbort = new AtomicBoolean(); - @Override - protected boolean isOverflow(@NotNull Set elementsArray) { - if (elementsArray.size() > UsageLimitUtil.USAGES_LIMIT - myMaximumListSizeLimit && !userAskedToAbort.getAndSet(true)) { - final UsageLimitUtil.Result ret = UsageLimitUtil.showTooManyUsagesWarning(myProject, UsageViewBundle - .message("find.excessive.usage.count.prompt", elementsArray.size() + myMaximumListSizeLimit, StringUtil.pluralize(presentation.getUsagesWord())), presentation); - if (ret == UsageLimitUtil.Result.ABORT) { - overFlow[0] = true; - return true; - } - } - return false; - } - }; - boolean anyPlace = isSearchInAnyPlace(); setSearchInAnyPlace(false); myCalcUsagesThread.addElementsByPattern(text, prefixMatchElementsArray, indicator, everywhere); setSearchInAnyPlace(anyPlace); - if (anyPlace && !overFlow[0]) { + if (anyPlace && !indicator.isCanceled()) { myCalcUsagesThread.addElementsByPattern(text, nonPrefixMatchElementsArray, indicator, everywhere); nonPrefixMatchElementsArray.removeAll(prefixMatchElementsArray); } diff --git a/platform/lang-impl/src/com/intellij/lang/javascript/boilerplate/GithubProjectGeneratorPeer.form b/platform/lang-impl/src/com/intellij/lang/javascript/boilerplate/GithubProjectGeneratorPeer.form index 1772de981680..2a2fa91b28b5 100644 --- a/platform/lang-impl/src/com/intellij/lang/javascript/boilerplate/GithubProjectGeneratorPeer.form +++ b/platform/lang-impl/src/com/intellij/lang/javascript/boilerplate/GithubProjectGeneratorPeer.form @@ -13,43 +13,20 @@ - + - - - - - - - - - - - - - - - - - - - - - - - + - diff --git a/platform/lang-impl/src/com/intellij/lang/javascript/boilerplate/GithubProjectGeneratorPeer.java b/platform/lang-impl/src/com/intellij/lang/javascript/boilerplate/GithubProjectGeneratorPeer.java index 2a94fdb52778..7c069b566d13 100644 --- a/platform/lang-impl/src/com/intellij/lang/javascript/boilerplate/GithubProjectGeneratorPeer.java +++ b/platform/lang-impl/src/com/intellij/lang/javascript/boilerplate/GithubProjectGeneratorPeer.java @@ -1,5 +1,5 @@ /* - * Copyright 2000-2012 JetBrains s.r.o. + * 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. @@ -15,59 +15,110 @@ */ package com.intellij.lang.javascript.boilerplate; -import com.google.common.collect.ImmutableCollection; import com.google.common.collect.ImmutableSet; import com.google.common.collect.Sets; -import com.intellij.icons.AllIcons; import com.intellij.ide.util.projectWizard.SettingsStep; -import com.intellij.openapi.actionSystem.ActionToolbar; -import com.intellij.openapi.actionSystem.AnAction; -import com.intellij.openapi.actionSystem.AnActionEvent; -import com.intellij.openapi.actionSystem.impl.ActionButton; import com.intellij.openapi.ui.ValidationInfo; import com.intellij.openapi.util.text.StringUtil; import com.intellij.platform.WebProjectGenerator; import com.intellij.platform.templates.github.GithubTagInfo; -import com.intellij.ui.JBColor; import com.intellij.ui.ListCellRendererWrapper; import com.intellij.util.ObjectUtils; import com.intellij.util.containers.ContainerUtil; -import com.intellij.util.ui.AsyncProcessIcon; -import com.intellij.util.ui.UIUtil; +import com.intellij.util.ui.ReloadableComboBoxPanel; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import javax.swing.*; -import java.awt.*; -import java.util.Collections; -import java.util.Comparator; -import java.util.List; -import java.util.Set; +import java.util.*; /** * @author Sergey Simonchik */ public class GithubProjectGeneratorPeer implements WebProjectGenerator.GeneratorPeer { + private void createUIComponents() { + myReloadableComboBoxPanel = new ReloadableComboBoxPanel() { - private static final String CONTROL_PLACE = "Github.Project.Generator.Reload"; + @SuppressWarnings("unchecked") + @Override + protected void doUpdateValues(@NotNull Set tags) { + if (!shouldUpdate(tags)) { + return; + } - private enum UpdateStatus { - UPDATING, IDLE + List sortedTags = createSortedTagList(tags); + GithubTagInfo selectedItem = getSelectedValue(); + if (selectedItem == null && sortedTags.size() > 0) { + selectedItem = sortedTags.get(0); + } + myComboBox.removeAllItems(); + myComboBox.addItem(myMasterTag); + for (GithubTagInfo tag : sortedTags) { + myComboBox.addItem(tag); + } + if (selectedItem != null) { + // restore previously selected item + for (int i = 0; i < myComboBox.getItemCount(); i++) { + GithubTagInfo item = GithubTagInfo.tryCast(myComboBox.getItemAt(i)); + if (item != null && item.getName().equals(selectedItem.getName())) { + myComboBox.setSelectedIndex(i); + break; + } + } + } + myComboBox.updateUI(); + fireStateChanged(); + } + + private boolean shouldUpdate(Set newTags) { + if (myComboBox.getItemCount() == 0) { + return true; + } + int count = myComboBox.getItemCount(); + Set oldTags = Sets.newHashSet(); + for (int i = 1; i < count; i++) { + GithubTagInfo item = ObjectUtils.tryCast(myComboBox.getItemAt(i), GithubTagInfo.class); + if (item != null) { + oldTags.add(item); + } + } + return !oldTags.equals(newTags); + } + + @SuppressWarnings("unchecked") + @NotNull + @Override + protected JComboBox createValuesComboBox() { + JComboBox box = super.createValuesComboBox(); + box.setRenderer(new ListCellRendererWrapper() { + @Override + public void customize(JList list, GithubTagInfo tag, int index, boolean selected, boolean hasFocus) { + final String text; + if (tag == null) { + text = isBackgroundJobRunning() ? "Loading..." : "Unavailable"; + } + else { + text = tag.getName(); + } + setText(text); + } + }); + + return box; + } + }; + + myVersionPanel = myReloadableComboBoxPanel.getMainPanel(); } private final List myListeners = ContainerUtil.newArrayList(); private final GithubTagInfo myMasterTag; private final GithubTagListProvider myTagListProvider; - private final AsyncProcessIcon myLoadingVersionIcon = new AsyncProcessIcon("Getting github tags"); - private final JLabel myErrorMessage = new JLabel(); - private JComboBox myComboBox; private JComponent myComponent; private JPanel myVersionPanel; - private JPanel myActionPanel; - private UpdateStatus myUpdateStatus; + private ReloadableComboBoxPanel myReloadableComboBoxPanel; public GithubProjectGeneratorPeer(@NotNull AbstractGithubTagDownloadedProjectGenerator generator) { - myErrorMessage.setForeground(JBColor.RED); String ghUserName = generator.getGithubUserName(); String ghRepoName = generator.getGithubRepositoryName(); myMasterTag = new GithubTagInfo( @@ -75,87 +126,33 @@ public class GithubProjectGeneratorPeer implements WebProjectGenerator.Generator String.format("https://github.com/%s/%s/zipball/master", ghUserName, ghRepoName) ); - myComboBox.setRenderer(new ListCellRendererWrapper() { + myTagListProvider = new GithubTagListProvider(ghUserName, ghRepoName); + + myReloadableComboBoxPanel.setDataProvider(new ReloadableComboBoxPanel.DataProvider() { @Override - public void customize(JList list, GithubTagInfo tag, int index, boolean selected, boolean hasFocus) { - final String text; - if (tag == null) { - text = isBackgroundJobRunning() ? "Loading..." : "Unavailable"; - } - else { - text = tag.getName(); - } - setText(text); + public Set getCachedValues() { + return myTagListProvider.getCachedTags(); + } + + @Override + public void updateValuesAsynchronously() { + myTagListProvider.updateTagListAsynchronously(GithubProjectGeneratorPeer.this); } }); - myTagListProvider = new GithubTagListProvider(ghUserName, ghRepoName); - fillActionPanel(); - ImmutableSet cachedTags = myTagListProvider.getCachedTags(); - if (cachedTags != null) { - onTagsUpdated(cachedTags); - } - reloadTagsInBackground(); + myReloadableComboBoxPanel.reloadValuesInBackground(); } void onTagsUpdated(@NotNull ImmutableSet tags) { - changeUpdateStatus(UpdateStatus.IDLE); - if (!shouldUpdate(tags)) { - return; - } - List sortedTags = createSortedTagList(tags); - GithubTagInfo selectedItem = getSelectedTag(); - if (selectedItem == null && sortedTags.size() > 0) { - selectedItem = sortedTags.get(0); - } - myComboBox.removeAllItems(); - myComboBox.addItem(myMasterTag); - for (GithubTagInfo tag : sortedTags) { - myComboBox.addItem(tag); - } - if (selectedItem != null) { - // restore previously selected item - for (int i = 0; i < myComboBox.getItemCount(); i++) { - GithubTagInfo item = GithubTagInfo.tryCast(myComboBox.getItemAt(i)); - if (item != null && item.getName().equals(selectedItem.getName())) { - myComboBox.setSelectedIndex(i); - break; - } - } - } - myComboBox.updateUI(); - fireStateChanged(); + myReloadableComboBoxPanel.onUpdateValues(tags); } void onTagsUpdateError(@NotNull final String errorMessage) { - UIUtil.invokeLaterIfNeeded(new Runnable() { - @Override - public void run() { - if (getSelectedTag() == null) { - myErrorMessage.setText(errorMessage); - } - changeUpdateStatus(UpdateStatus.IDLE); - } - }); - } - - private boolean shouldUpdate(@NotNull ImmutableSet newTags) { - if (myComboBox.getItemCount() == 0) { - return true; - } - int count = myComboBox.getItemCount(); - Set oldTags = Sets.newHashSet(); - for (int i = 1; i < count; i++) { - GithubTagInfo item = ObjectUtils.tryCast(myComboBox.getItemAt(i), GithubTagInfo.class); - if (item != null) { - oldTags.add(item); - } - } - return !oldTags.equals(newTags); + myReloadableComboBoxPanel.onValuesUpdateError(errorMessage); } @NotNull - private static List createSortedTagList(@NotNull ImmutableCollection tags) { + private static List createSortedTagList(@NotNull Collection tags) { List sortedTags = ContainerUtil.newArrayList(tags); Collections.sort(sortedTags, new Comparator() { @Override @@ -184,13 +181,13 @@ public class GithubProjectGeneratorPeer implements WebProjectGenerator.Generator @Override public void buildUI(@NotNull SettingsStep settingsStep) { settingsStep.addSettingsField("\u001BVersion:", myVersionPanel); - settingsStep.addSettingsComponent(myErrorMessage); + settingsStep.addSettingsComponent(myReloadableComboBoxPanel.getErrorComponent()); } @NotNull @Override public GithubTagInfo getSettings() { - GithubTagInfo tag = getSelectedTag(); + GithubTagInfo tag = myReloadableComboBoxPanel.getSelectedValue(); if (tag == null) { throw new RuntimeException("[internal error] No versions available."); } @@ -200,11 +197,11 @@ public class GithubProjectGeneratorPeer implements WebProjectGenerator.Generator @Override @Nullable public ValidationInfo validate() { - GithubTagInfo tag = getSelectedTag(); + GithubTagInfo tag = myReloadableComboBoxPanel.getSelectedValue(); if (tag != null) { return null; } - String errorMessage = StringUtil.notNullize(myErrorMessage.getText()); + String errorMessage = StringUtil.notNullize(myReloadableComboBoxPanel.getErrorComponent().getText()); if (errorMessage.isEmpty()) { errorMessage = "Versions have not been loaded yet."; } @@ -213,7 +210,7 @@ public class GithubProjectGeneratorPeer implements WebProjectGenerator.Generator @Override public boolean isBackgroundJobRunning() { - return myUpdateStatus == UpdateStatus.UPDATING; + return myReloadableComboBoxPanel.isBackgroundJobRunning(); } @Override @@ -221,78 +218,11 @@ public class GithubProjectGeneratorPeer implements WebProjectGenerator.Generator myListeners.add(listener); } - @Nullable - private GithubTagInfo getSelectedTag() { - return GithubTagInfo.tryCast(myComboBox.getSelectedItem()); - } private void fireStateChanged() { - GithubTagInfo tag = getSelectedTag(); + GithubTagInfo tag = myReloadableComboBoxPanel.getSelectedValue(); for (WebProjectGenerator.SettingsStateListener listener : myListeners) { listener.stateChanged(tag != null); } } - - private void reloadTagsInBackground() { - changeUpdateStatus(UpdateStatus.UPDATING); - myErrorMessage.setText(null); - myTagListProvider.updateTagListAsynchronously(this); - } - - private void changeUpdateStatus(@NotNull UpdateStatus status) { - CardLayout cardLayout = (CardLayout) myActionPanel.getLayout(); - cardLayout.show(myActionPanel, status.name()); - if (status == UpdateStatus.UPDATING) { - myLoadingVersionIcon.resume(); - } - else { - myLoadingVersionIcon.suspend(); - } - myUpdateStatus = status; - } - - private void fillActionPanel() { - myActionPanel.add(createReloadButtonPanel(), UpdateStatus.IDLE.name()); - myActionPanel.add(createReloadInProgressPanel(), UpdateStatus.UPDATING.name()); - changeUpdateStatus(UpdateStatus.IDLE); - } - - @NotNull - private JPanel createReloadButtonPanel() { - ReloadAction reloadAction = new ReloadAction(); - ActionButton reloadButton = new ActionButton( - reloadAction, - reloadAction.getTemplatePresentation().clone(), - CONTROL_PLACE, - ActionToolbar.DEFAULT_MINIMUM_BUTTON_SIZE - ); - JPanel panel = new JPanel(new BorderLayout(0, 0)); - panel.add(reloadButton, BorderLayout.WEST); - return panel; - } - - @NotNull - private JPanel createReloadInProgressPanel() { - JPanel panel = new JPanel(); - panel.add(myLoadingVersionIcon); - return panel; - } - - private class ReloadAction extends AnAction { - - private ReloadAction() { - super("Reload versions", null, AllIcons.Actions.Refresh); - } - - @Override - public void actionPerformed(AnActionEvent e) { - GithubProjectGeneratorPeer.this.reloadTagsInBackground(); - } - - @Override - public void update(AnActionEvent e) { - e.getPresentation().setEnabled(true); - } - } - } diff --git a/platform/lang-impl/src/com/intellij/openapi/paths/GlobalPathReferenceProvider.java b/platform/lang-impl/src/com/intellij/openapi/paths/GlobalPathReferenceProvider.java index bc4b97d781f5..bef8449529bd 100644 --- a/platform/lang-impl/src/com/intellij/openapi/paths/GlobalPathReferenceProvider.java +++ b/platform/lang-impl/src/com/intellij/openapi/paths/GlobalPathReferenceProvider.java @@ -31,7 +31,7 @@ import java.util.List; public class GlobalPathReferenceProvider implements PathReferenceProvider { @NonNls private static final String[] PREFIXES = { - "mailto:", "tel:", "sms:", "skype:", "data:", "xmpp:" + "tel:", "sms:", "skype:", "data:", "xmpp:" }; public static boolean startsWithAllowedPrefix(String s) { @@ -49,21 +49,30 @@ public class GlobalPathReferenceProvider implements PathReferenceProvider { if (manipulator == null) { return false; } - final TextRange range = manipulator.getRangeInElement(psiElement); - final String s = range.substring(psiElement.getText()); - if (isWebReferenceUrl(s)) { - references.add(new WebReference(psiElement, range)); + return createUrlReference( + psiElement, + manipulator.getRangeInElement(psiElement).substring(psiElement.getText()), + manipulator.getRangeInElement(psiElement), + references + ); + } + + public boolean createUrlReference(@NotNull PsiElement psiElement, + String url, + TextRange rangeInElement, @NotNull List references) { + if (isWebReferenceUrl(url)) { + references.add(new WebReference(psiElement, rangeInElement)); + return true; } - else if (s.contains("://") || s.startsWith("//") || startsWithAllowedPrefix(s)) { - final PsiReference reference = PsiReferenceBase.createSelfReference(psiElement, psiElement); - references.add(reference); + else if (url.contains("://") || url.startsWith("//") || startsWithAllowedPrefix(url)) { + references.add(PsiReferenceBase.createSelfReference(psiElement, psiElement)); return true; } return false; } public static boolean isWebReferenceUrl(String url) { - return url.startsWith("http://") || url.startsWith("https://") || url.startsWith("about:"); + return url.startsWith("http://") || url.startsWith("https://") || url.startsWith("about:") || url.startsWith("mailto:"); } @Override diff --git a/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesDialog.java b/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesDialog.java index 5a4e7ef70faa..76c07b93ffe9 100644 --- a/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesDialog.java +++ b/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesDialog.java @@ -17,6 +17,7 @@ package com.intellij.refactoring.move.moveFilesOrDirectories; import com.intellij.ide.util.DirectoryUtil; +import com.intellij.ide.util.PropertiesComponent; import com.intellij.openapi.actionSystem.ActionManager; import com.intellij.openapi.actionSystem.IdeActions; import com.intellij.openapi.application.ApplicationManager; @@ -56,6 +57,8 @@ import java.util.List; public class MoveFilesOrDirectoriesDialog extends DialogWrapper { @NonNls private static final String RECENT_KEYS = "MoveFile.RECENT_KEYS"; + @NonNls private static final String MOVE_FILES_OPEN_IN_EDITOR = "MoveFile.OpenInEditor"; + public interface Callback { void run(MoveFilesOrDirectoriesDialog dialog); @@ -68,6 +71,7 @@ public class MoveFilesOrDirectoriesDialog extends DialogWrapper { private final Callback myCallback; private PsiDirectory myTargetDirectory; private JCheckBox myCbSearchForReferences; + private JCheckBox myOpenInEditorCb; public MoveFilesOrDirectoriesDialog(Project project, Callback callback) { super(project, true); @@ -124,10 +128,15 @@ public class MoveFilesOrDirectoriesDialog extends DialogWrapper { myCbSearchForReferences = new NonFocusableCheckBox(RefactoringBundle.message("search.for.references")); myCbSearchForReferences.setSelected(RefactoringSettings.getInstance().MOVE_SEARCH_FOR_REFERENCES_FOR_FILE); + myOpenInEditorCb = new NonFocusableCheckBox("Open moved files in editor"); + myOpenInEditorCb.setSelected(isOpenInEditor()); + return FormBuilder.createFormBuilder().addComponent(myNameLabel) .addLabeledComponent(RefactoringBundle.message("move.files.to.directory.label"), myTargetDirectoryField, UIUtil.LARGE_VGAP) .addTooltip(RefactoringBundle.message("path.completion.shortcut", shortcutText)) - .addComponentToRightColumn(myCbSearchForReferences, UIUtil.LARGE_VGAP).getPanel(); + .addComponentToRightColumn(myCbSearchForReferences, UIUtil.LARGE_VGAP) + .addComponentToRightColumn(myOpenInEditorCb, UIUtil.LARGE_VGAP) + .getPanel(); } public void setData(PsiElement[] psiElements, PsiDirectory initialTargetDirectory, @NonNls String helpID) { @@ -169,12 +178,20 @@ public class MoveFilesOrDirectoriesDialog extends DialogWrapper { HelpManager.getInstance().invokeHelp(myHelpID); } + public static boolean isOpenInEditor() { + if (ApplicationManager.getApplication().isUnitTestMode()) { + return false; + } + return PropertiesComponent.getInstance().getBoolean(MOVE_FILES_OPEN_IN_EDITOR, true); + } + private void validateOKButton() { setOKActionEnabled(myTargetDirectoryField.getChildComponent().getText().length() > 0); } @Override protected void doOKAction() { + PropertiesComponent.getInstance().setValue(MOVE_FILES_OPEN_IN_EDITOR, String.valueOf(myOpenInEditorCb.isSelected())); //myTargetDirectoryField.getChildComponent().addCurrentTextToHistory(); RecentsManager.getInstance(myProject).registerRecentEntry(RECENT_KEYS, myTargetDirectoryField.getChildComponent().getText()); RefactoringSettings.getInstance().MOVE_SEARCH_FOR_REFERENCES_FOR_FILE = myCbSearchForReferences.isSelected(); diff --git a/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesProcessor.java b/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesProcessor.java index 5217b5795b7c..fe0a1bcd0ec0 100644 --- a/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesProcessor.java +++ b/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesProcessor.java @@ -16,6 +16,7 @@ package com.intellij.refactoring.move.moveFilesOrDirectories; +import com.intellij.ide.util.EditorHelper; import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.paths.PsiDynaReference; @@ -190,6 +191,10 @@ public class MoveFilesOrDirectoriesProcessor extends BaseRefactoringProcessor { retargetUsages(usages, oldToNewMap); + if (MoveFilesOrDirectoriesDialog.isOpenInEditor() && !movedFiles.isEmpty()) { + EditorHelper.openInEditor(movedFiles.get(0)); + } + // Perform CVS "add", "remove" commands on moved files. if (myMoveCallback != null) { diff --git a/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesUtil.java b/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesUtil.java index 885ce5b07214..286420d0c8e0 100644 --- a/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesUtil.java +++ b/platform/lang-impl/src/com/intellij/refactoring/move/moveFilesOrDirectories/MoveFilesOrDirectoriesUtil.java @@ -136,18 +136,16 @@ public class MoveFilesOrDirectoriesUtil { LOG.assertTrue(targetDirectory != null); targetElement[0] = targetDirectory; - PsiManager manager = PsiManager.getInstance(project); try { final int[] choice = elements.length > 1 || elements[0] instanceof PsiDirectory ? new int[]{-1} : null; final List els = new ArrayList(); - for (int i = 0, newElementsLength = newElements.length; i < newElementsLength; i++) { - final PsiElement psiElement = newElements[i]; + for (final PsiElement psiElement : newElements) { if (psiElement instanceof PsiFile) { final PsiFile file = (PsiFile)psiElement; final boolean fileExist = ApplicationManager.getApplication().runWriteAction(new Computable() { @Override public Boolean compute() { - return CopyFilesOrDirectoriesHandler.checkFileExist(targetDirectory, choice, file, file.getName(), "Move"); + return CopyFilesOrDirectoriesHandler.checkFileExist(targetDirectory, choice, file, file.getName(), "Move"); } }); if (fileExist) continue; diff --git a/platform/platform-api/src/com/intellij/ui/tabs/impl/singleRow/CompressibleSingleRowLayout.java b/platform/platform-api/src/com/intellij/ui/tabs/impl/singleRow/CompressibleSingleRowLayout.java index 7fe4b14af49d..f921d12c28d4 100644 --- a/platform/platform-api/src/com/intellij/ui/tabs/impl/singleRow/CompressibleSingleRowLayout.java +++ b/platform/platform-api/src/com/intellij/ui/tabs/impl/singleRow/CompressibleSingleRowLayout.java @@ -84,7 +84,7 @@ public class CompressibleSingleRowLayout extends SingleRowLayout { int length; if (needCompression) { length = iterator.hasNext() ? (int)(getStrategy().getLengthIncrement(label.getPreferredSize()) * (float)data.toFitLength / lengthEstimation) - : data.toFitLength - spentLength; + : data.toFitLength - spentLength - data.toLayout.size() / 2; spentLength += length; } else { diff --git a/platform/platform-api/src/com/intellij/util/io/HttpRequests.java b/platform/platform-api/src/com/intellij/util/io/HttpRequests.java index 08a5e6063d2d..bea10e9b625b 100644 --- a/platform/platform-api/src/com/intellij/util/io/HttpRequests.java +++ b/platform/platform-api/src/com/intellij/util/io/HttpRequests.java @@ -24,7 +24,9 @@ import com.intellij.openapi.util.SystemInfo; import com.intellij.openapi.util.io.BufferExposingByteArrayOutputStream; import com.intellij.openapi.util.io.FileUtilRt; import com.intellij.openapi.util.text.StringUtil; +import com.intellij.openapi.vfs.CharsetToolkit; import com.intellij.util.ArrayUtil; +import com.intellij.util.ReflectionUtil; import com.intellij.util.SystemProperties; import com.intellij.util.net.HttpConfigurable; import com.intellij.util.net.NetUtils; @@ -38,6 +40,7 @@ import java.net.HttpURLConnection; import java.net.URL; import java.net.URLClassLoader; import java.net.URLConnection; +import java.nio.charset.Charset; import java.util.zip.GZIPInputStream; /** @@ -194,10 +197,42 @@ public abstract class HttpRequests { } }); } + + @NotNull + public String getString(@Nullable final ProgressIndicator indicator) throws IOException { + return connect(new HttpRequests.RequestProcessor() { + @Override + public String process(@NotNull HttpRequests.Request request) throws IOException { + int contentLength = request.getConnection().getContentLength(); + BufferExposingByteArrayOutputStream out = new BufferExposingByteArrayOutputStream(contentLength > 0 ? contentLength : 16 * 1024); + NetUtils.copyStreamContent(indicator, request.getInputStream(), out, contentLength); + + Charset charset = CharsetToolkit.UTF8_CHARSET; + String contentEncoding = request.getConnection().getContentEncoding(); + if (contentEncoding != null) { + try { + charset = Charset.forName(contentEncoding); + } + catch (Exception ignored) { + charset = CharsetToolkit.UTF8_CHARSET; + } + } + return new String(out.getInternalBuffer(), 0, out.size(), charset); + } + }); + } } @NotNull public static RequestBuilder request(@NotNull String url) { + if (ApplicationManager.getApplication() == null) { + try { + return ((HttpRequests)ReflectionUtil.newInstance(Class.forName("com.intellij.util.io.HttpRequestsImpl"))).createRequestBuilder(url); + } + catch (ClassNotFoundException e) { + throw new RuntimeException(e); + } + } return ServiceManager.getService(HttpRequests.class).createRequestBuilder(url); } diff --git a/platform/platform-impl/src/com/intellij/ide/actions/ToggleDistractionFreeModeAction.java b/platform/platform-impl/src/com/intellij/ide/actions/ToggleDistractionFreeModeAction.java index 196d36ea5a6b..ba932e1d5d6a 100644 --- a/platform/platform-impl/src/com/intellij/ide/actions/ToggleDistractionFreeModeAction.java +++ b/platform/platform-impl/src/com/intellij/ide/actions/ToggleDistractionFreeModeAction.java @@ -20,12 +20,11 @@ import com.intellij.codeInsight.daemon.DaemonCodeAnalyzerSettings; import com.intellij.ide.ui.LafManager; import com.intellij.ide.ui.UISettings; import com.intellij.ide.util.PropertiesComponent; -import com.intellij.openapi.actionSystem.AnAction; import com.intellij.openapi.actionSystem.AnActionEvent; import com.intellij.openapi.editor.EditorFactory; import com.intellij.openapi.editor.ex.EditorSettingsExternalizable; import com.intellij.openapi.editor.ex.util.EditorUtil; -import com.intellij.openapi.project.DumbAware; +import com.intellij.openapi.project.DumbAwareAction; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.registry.Registry; import com.intellij.openapi.util.registry.RegistryValue; @@ -33,7 +32,9 @@ import org.jetbrains.annotations.NotNull; import javax.swing.*; -public class ToggleDistractionFreeModeAction extends AnAction implements DumbAware { +import static java.lang.String.valueOf; + +public class ToggleDistractionFreeModeAction extends DumbAwareAction { private static final String key = "editor.distraction.free.mode"; @Override @@ -51,49 +52,24 @@ public class ToggleDistractionFreeModeAction extends AnAction implements DumbAwa public void actionPerformed(@NotNull AnActionEvent e) { Project project = e.getProject(); RegistryValue value = Registry.get(key); - boolean v = !value.asBoolean(); - value.setValue(v); + boolean enter = !value.asBoolean(); + value.setValue(enter); if (project == null) return; - PropertiesComponent p = PropertiesComponent.getInstance(project); + PropertiesComponent p = PropertiesComponent.getInstance(); UISettings ui = UISettings.getInstance(); EditorSettingsExternalizable.OptionSet eo = EditorSettingsExternalizable.getInstance().getOptions(); DaemonCodeAnalyzerSettings ds = DaemonCodeAnalyzerSettings.getInstance(); String before = "BEFORE.DISTRACTION.MODE."; - if (v) { - p.setValue(before + "SHOW_STATUS_BAR", String.valueOf(ui.SHOW_STATUS_BAR)); ui.SHOW_STATUS_BAR = false; - p.setValue(before + "SHOW_MAIN_TOOLBAR", String.valueOf(ui.SHOW_MAIN_TOOLBAR)); ui.SHOW_MAIN_TOOLBAR = false; - p.setValue(before + "SHOW_NAVIGATION_BAR", String.valueOf(ui.SHOW_NAVIGATION_BAR)); ui.SHOW_NAVIGATION_BAR = false; - p.setValue(before + "HIDE_TOOL_STRIPES", String.valueOf(ui.HIDE_TOOL_STRIPES)); ui.HIDE_TOOL_STRIPES = true; - p.setValue(before + "EDITOR_TAB_PLACEMENT", String.valueOf(ui.EDITOR_TAB_PLACEMENT)); ui.EDITOR_TAB_PLACEMENT = UISettings.TABS_NONE; - - p.setValue(before + "IS_FOLDING_OUTLINE_SHOWN", String.valueOf(eo.IS_FOLDING_OUTLINE_SHOWN)); eo.IS_FOLDING_OUTLINE_SHOWN = false; - p.setValue(before + "IS_WHITESPACES_SHOWN", String.valueOf(eo.IS_WHITESPACES_SHOWN)); eo.IS_WHITESPACES_SHOWN = false; - p.setValue(before + "ARE_LINE_NUMBERS_SHOWN", String.valueOf(eo.ARE_LINE_NUMBERS_SHOWN)); eo.ARE_LINE_NUMBERS_SHOWN = false; - //p.setValue(before + "IS_RIGHT_MARGIN_SHOWN", String.valueOf(eo.IS_RIGHT_MARGIN_SHOWN)); eo.IS_RIGHT_MARGIN_SHOWN = false; - p.setValue(before + "IS_INDENT_GUIDES_SHOWN", String.valueOf(eo.IS_INDENT_GUIDES_SHOWN)); eo.IS_INDENT_GUIDES_SHOWN = false; - - p.setValue(before + "SHOW_METHOD_SEPARATORS", String.valueOf(ds.SHOW_METHOD_SEPARATORS)); ds.SHOW_METHOD_SEPARATORS = false; - + String after = "AFTER.DISTRACTION.MODE."; + if (enter) { + applyAndSave(p, ui, eo, ds, before, after, false); TogglePresentationModeAction.storeToolWindows(project); } else { - ui.SHOW_STATUS_BAR = p.getBoolean(before + "SHOW_STATUS_BAR", true); - ui.SHOW_MAIN_TOOLBAR = p.getBoolean(before + "SHOW_MAIN_TOOLBAR", true); - ui.SHOW_NAVIGATION_BAR = p.getBoolean(before + "SHOW_NAVIGATION_BAR", true); - ui.HIDE_TOOL_STRIPES = p.getBoolean(before + "HIDE_TOOL_STRIPES", true); - ui.EDITOR_TAB_PLACEMENT = p.getOrInitInt(before + "EDITOR_TAB_PLACEMENT", SwingConstants.TOP); - - eo.IS_FOLDING_OUTLINE_SHOWN = p.getBoolean(before + "IS_FOLDING_OUTLINE_SHOWN", true); - eo.IS_WHITESPACES_SHOWN = p.getBoolean(before + "IS_WHITESPACES_SHOWN", false); - eo.ARE_LINE_NUMBERS_SHOWN = p.getBoolean(before + "ARE_LINE_NUMBERS_SHOWN", false); - //eo.IS_RIGHT_MARGIN_SHOWN = p.getBoolean(before + "IS_RIGHT_MARGIN_SHOWN", true); - eo.IS_INDENT_GUIDES_SHOWN = p.getBoolean(before + "IS_INDENT_GUIDES_SHOWN", false); - - ds.SHOW_METHOD_SEPARATORS = p.getBoolean(before + "SHOW_METHOD_SEPARATORS", false); - + applyAndSave(p, ui, eo, ds, after, before, true); TogglePresentationModeAction.restoreToolWindows(project, true, false); } @@ -103,4 +79,27 @@ public class ToggleDistractionFreeModeAction extends AnAction implements DumbAwa DaemonCodeAnalyzer.getInstance(project).settingsChanged(); EditorFactory.getInstance().refreshAllEditors(); } + + public static void applyAndSave(@NotNull PropertiesComponent p, + @NotNull UISettings ui, + @NotNull EditorSettingsExternalizable.OptionSet eo, + @NotNull DaemonCodeAnalyzerSettings ds, + String before, String after, boolean value) { + // @formatter:off + p.setValue(before + "SHOW_STATUS_BAR", valueOf(ui.SHOW_STATUS_BAR)); ui.SHOW_STATUS_BAR = p.getBoolean(after + "SHOW_STATUS_BAR", value); + p.setValue(before + "SHOW_MAIN_TOOLBAR", valueOf(ui.SHOW_MAIN_TOOLBAR)); ui.SHOW_MAIN_TOOLBAR = p.getBoolean(after + "SHOW_MAIN_TOOLBAR", value); + p.setValue(before + "SHOW_NAVIGATION_BAR", valueOf(ui.SHOW_NAVIGATION_BAR)); ui.SHOW_NAVIGATION_BAR = p.getBoolean(after + "SHOW_NAVIGATION_BAR", value); + + p.setValue(before + "IS_FOLDING_OUTLINE_SHOWN", valueOf(eo.IS_FOLDING_OUTLINE_SHOWN)); eo.IS_FOLDING_OUTLINE_SHOWN = p.getBoolean(after + "IS_FOLDING_OUTLINE_SHOWN", value); + p.setValue(before + "IS_WHITESPACES_SHOWN", valueOf(eo.IS_WHITESPACES_SHOWN)); eo.IS_WHITESPACES_SHOWN = p.getBoolean(after + "IS_WHITESPACES_SHOWN", value); + p.setValue(before + "ARE_LINE_NUMBERS_SHOWN", valueOf(eo.ARE_LINE_NUMBERS_SHOWN)); eo.ARE_LINE_NUMBERS_SHOWN = p.getBoolean(after + "ARE_LINE_NUMBERS_SHOWN", value); + p.setValue(before + "IS_RIGHT_MARGIN_SHOWN", valueOf(eo.IS_RIGHT_MARGIN_SHOWN)); eo.IS_RIGHT_MARGIN_SHOWN = p.getBoolean(after + "IS_RIGHT_MARGIN_SHOWN", value); + p.setValue(before + "IS_INDENT_GUIDES_SHOWN", valueOf(eo.IS_INDENT_GUIDES_SHOWN)); eo.IS_INDENT_GUIDES_SHOWN = p.getBoolean(after + "IS_INDENT_GUIDES_SHOWN", value); + + p.setValue(before + "SHOW_METHOD_SEPARATORS", valueOf(ds.SHOW_METHOD_SEPARATORS)); ds.SHOW_METHOD_SEPARATORS = p.getBoolean(after + "SHOW_METHOD_SEPARATORS", value); + + p.setValue(before + "HIDE_TOOL_STRIPES", valueOf(ui.HIDE_TOOL_STRIPES)); ui.HIDE_TOOL_STRIPES = p.getBoolean(after + "HIDE_TOOL_STRIPES", !value); + p.setValue(before + "EDITOR_TAB_PLACEMENT", valueOf(ui.EDITOR_TAB_PLACEMENT)); ui.EDITOR_TAB_PLACEMENT = p.getOrInitInt(after + "EDITOR_TAB_PLACEMENT", value ? SwingConstants.TOP : UISettings.TABS_NONE); + // @formatter:on + } } diff --git a/platform/platform-impl/src/com/intellij/openapi/components/impl/ServiceManagerImpl.java b/platform/platform-impl/src/com/intellij/openapi/components/impl/ServiceManagerImpl.java index 017d9a08cbba..05ce99453036 100644 --- a/platform/platform-impl/src/com/intellij/openapi/components/impl/ServiceManagerImpl.java +++ b/platform/platform-impl/src/com/intellij/openapi/components/impl/ServiceManagerImpl.java @@ -25,10 +25,12 @@ import com.intellij.openapi.components.ServiceDescriptor; import com.intellij.openapi.components.ex.ComponentManagerEx; import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.extensions.*; +import com.intellij.openapi.extensions.impl.ExtensionComponentAdapter; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.Computable; import com.intellij.openapi.util.Disposer; import com.intellij.util.PairProcessor; +import com.intellij.util.PlatformUtils; import com.intellij.util.io.storage.HeavyProcessLatch; import com.intellij.util.pico.AssignableToComponentAdapter; import com.intellij.util.pico.ConstructorInjectionComponentAdapter; @@ -114,7 +116,13 @@ public class ServiceManagerImpl implements BaseComponent { } } catch (Throwable e) { - LOG.error(e); + if (PlatformUtils.isIdeaUltimate()) { + LOG.error(e); + } + else { + // well, component registered, but required jar is not added to classpath (community edition or junior IDE) + LOG.warn(e); + } continue; } @@ -122,7 +130,7 @@ public class ServiceManagerImpl implements BaseComponent { break; } } - else if (o instanceof ComponentAdapter) { + else if (o instanceof ComponentAdapter && !(o instanceof ExtensionComponentAdapter)) { try { aClass = ((ComponentAdapter)o).getComponentImplementation(); } diff --git a/platform/platform-impl/src/com/intellij/openapi/components/impl/stores/ComponentStoreImpl.java b/platform/platform-impl/src/com/intellij/openapi/components/impl/stores/ComponentStoreImpl.java index 2f8650670058..a1ec60a41c54 100644 --- a/platform/platform-impl/src/com/intellij/openapi/components/impl/stores/ComponentStoreImpl.java +++ b/platform/platform-impl/src/com/intellij/openapi/components/impl/stores/ComponentStoreImpl.java @@ -15,11 +15,7 @@ */ package com.intellij.openapi.components.impl.stores; -import com.intellij.openapi.application.AccessToken; -import com.intellij.openapi.application.ApplicationManager; -import com.intellij.openapi.application.ApplicationNamesInfo; -import com.intellij.openapi.application.WriteAction; -import com.intellij.openapi.application.ex.ApplicationManagerEx; +import com.intellij.openapi.application.*; import com.intellij.openapi.components.*; import com.intellij.openapi.components.StateStorage.SaveSession; import com.intellij.openapi.components.impl.ComponentManagerImpl; @@ -27,6 +23,7 @@ import com.intellij.openapi.components.impl.stores.StateStorageManager.Externali import com.intellij.openapi.components.store.ReadOnlyModificationException; import com.intellij.openapi.components.store.StateStorageBase; import com.intellij.openapi.diagnostic.Logger; +import com.intellij.openapi.progress.ProcessCanceledException; import com.intellij.openapi.project.Project; import com.intellij.openapi.project.ProjectBundle; import com.intellij.openapi.ui.Messages; @@ -59,7 +56,7 @@ public abstract class ComponentStoreImpl implements IComponentStore.Reloadable { protected abstract StateStorage getDefaultsStorage(); @Override - public void initComponent(@NotNull final Object component, boolean service) { + public void initComponent(@NotNull Object component, boolean service) { if (component instanceof SettingsSavingComponent) { mySettingsSavingComponents.add((SettingsSavingComponent)component); } @@ -68,25 +65,27 @@ public abstract class ComponentStoreImpl implements IComponentStore.Reloadable { return; } - ApplicationManagerEx.getApplicationEx().runReadAction(new Runnable() { - @Override - public void run() { - try { - if (component instanceof PersistentStateComponent) { - initPersistentComponent((PersistentStateComponent)component, null, false); - } - else { - initJdomExternalizable((JDOMExternalizable)component); - } - } - catch (StateStorageException e) { - throw e; - } - catch (Exception e) { - LOG.error(e); - } + AccessToken token = ReadAction.start(); + try { + if (component instanceof PersistentStateComponent) { + initPersistentComponent((PersistentStateComponent)component, null, false); } - }); + else { + initJdomExternalizable((JDOMExternalizable)component); + } + } + catch (StateStorageException e) { + throw e; + } + catch (ProcessCanceledException e) { + throw e; + } + catch (Exception e) { + LOG.error(e); + } + finally { + token.finish(); + } } @Override diff --git a/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/Change.java b/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/Change.java index 793d74002fdc..9b05f0ba3916 100644 --- a/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/Change.java +++ b/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/Change.java @@ -1,5 +1,5 @@ /* - * Copyright 2000-2009 JetBrains s.r.o. + * 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. @@ -70,13 +70,11 @@ public abstract class Change { RangeMarker originalRangeMarker = getRangeMarker(original); RangeMarker rangeMarker = getRangeMarker(targetSide); - if (originalRangeMarker != null && rangeMarker != null) { - TextRange textRange = modifyDocument(getProject(), originalRangeMarker, rangeMarker); - if (textRange != null && isValid()) { - updateTargetRangeMarker(targetSide, textRange); - } - onApplied(); + TextRange textRange = modifyDocument(getProject(), originalRangeMarker, rangeMarker); + if (textRange != null && isValid()) { + updateTargetRangeMarker(targetSide, textRange); } + onApplied(); } /** @@ -142,10 +140,12 @@ public abstract class Change { return getChangeList().getProject(); } + @NotNull private ChangeHighlighterHolder getHighlighterHolder(FragmentSide side) { return getChangeSide(side).getHighlighterHolder(); } + @NotNull private RangeMarker getRangeMarker(FragmentSide side) { ChangeSide changeSide = getChangeSide(side); LOG.assertTrue(changeSide != null); @@ -226,6 +226,7 @@ public abstract class Change { return myRange; } + @NotNull @Override public ChangeHighlighterHolder getHighlighterHolder() { return myHighlighterHolder; diff --git a/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/ChangeSide.java b/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/ChangeSide.java index 31b40d8fe913..885f82516b6d 100644 --- a/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/ChangeSide.java +++ b/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/ChangeSide.java @@ -1,5 +1,5 @@ /* - * Copyright 2000-2012 JetBrains s.r.o. + * 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. @@ -43,6 +43,7 @@ public abstract class ChangeSide { @NotNull public abstract DiffRangeMarker getRange(); + @NotNull public abstract ChangeHighlighterHolder getHighlighterHolder(); public boolean contains(int offset) { diff --git a/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/DiffRangeMarker.java b/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/DiffRangeMarker.java index 05b4a26f08e8..8890b2a3f37d 100644 --- a/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/DiffRangeMarker.java +++ b/platform/platform-impl/src/com/intellij/openapi/diff/impl/incrementalMerge/DiffRangeMarker.java @@ -15,48 +15,31 @@ */ package com.intellij.openapi.diff.impl.incrementalMerge; -import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.editor.Document; import com.intellij.openapi.editor.RangeMarker; import com.intellij.openapi.editor.event.DocumentAdapter; import com.intellij.openapi.editor.event.DocumentEvent; import com.intellij.openapi.util.Key; import com.intellij.openapi.util.TextRange; +import com.intellij.util.containers.ContainerUtil; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; -import java.util.ArrayList; +import java.util.Iterator; +import java.util.Map; class DiffRangeMarker implements RangeMarker { - private static final Logger LOG = Logger.getInstance("#com.intellij.openapi.diff.impl.incrementalMerge.DiffRangeMarker"); private final RangeMarker myRangeMarker; - private RangeInvalidListener myListener; DiffRangeMarker(@NotNull Document document, @NotNull TextRange range, RangeInvalidListener listener) { myRangeMarker = document.createRangeMarker(range.getStartOffset(), range.getEndOffset()); - myListener = listener; if (listener != null) { - final InvalidRangeDispatcher notifier = InvalidRangeDispatcher.addClient(document); - document.addDocumentListener(new DocumentAdapter() { - @Override - public void beforeDocumentChange(DocumentEvent e) { - if (myListener != null) { - notifier.notify(new RangeInvalidListener() { - @Override - public void onRangeInvalidated() { - if (!isValid() && myListener != null) myListener.onRangeInvalidated(); - } - }); - } - } - }); + InvalidRangeDispatcher.addClient(document, this, listener); } } - public void removeListener(RangeInvalidListener listener) { - LOG.assertTrue(myListener == listener || myListener == null); - myListener = null; - InvalidRangeDispatcher.removeClient(getDocument()); + public void removeListener(@NotNull RangeInvalidListener listener) { + InvalidRangeDispatcher.removeClient(getDocument(), this, listener); } interface RangeInvalidListener { @@ -65,43 +48,45 @@ class DiffRangeMarker implements RangeMarker { private static class InvalidRangeDispatcher extends DocumentAdapter { private static final Key KEY = Key.create("deferedNotifier"); - private final ArrayList myDeferedNotifications = new ArrayList(); - private int myClientCount = 0; + private final Map myDiffRangeMarkers = ContainerUtil.newConcurrentMap(); @Override public void documentChanged(DocumentEvent e) { - if (myDeferedNotifications.isEmpty()) return; - RangeInvalidListener[] notifications = myDeferedNotifications.toArray(new RangeInvalidListener[myDeferedNotifications.size()]); - myDeferedNotifications.clear(); - for (RangeInvalidListener notification : notifications) { - notification.onRangeInvalidated(); + for (Iterator> iterator = myDiffRangeMarkers.entrySet().iterator(); + iterator.hasNext(); ) { + Map.Entry entry = iterator.next(); + DiffRangeMarker diffRangeMarker = entry.getKey(); + RangeInvalidListener listener = entry.getValue(); + if (!diffRangeMarker.isValid() && listener != null) { + listener.onRangeInvalidated(); + iterator.remove(); + } } } - public void notify(@NotNull RangeInvalidListener listener) { - myDeferedNotifications.add(listener); - } - - private static InvalidRangeDispatcher addClient(@NotNull Document document) { + private static void addClient(@NotNull Document document, + @NotNull DiffRangeMarker marker, + @NotNull RangeInvalidListener listener) { InvalidRangeDispatcher notifier = document.getUserData(KEY); if (notifier == null) { notifier = new InvalidRangeDispatcher(); document.putUserData(KEY, notifier); document.addDocumentListener(notifier); } - notifier.myClientCount++; - return notifier; + assert !notifier.myDiffRangeMarkers.containsKey(marker); + notifier.myDiffRangeMarkers.put(marker, listener); } - private static void removeClient(Document document) { + private static void removeClient(@NotNull Document document, + @NotNull DiffRangeMarker marker, + @NotNull RangeInvalidListener listener) { InvalidRangeDispatcher notifier = document.getUserData(KEY); - notifier.onClientRemoved(document); + assert notifier != null; + notifier.onClientRemoved(document, marker, listener); } - private void onClientRemoved(Document document) { - myClientCount--; - LOG.assertTrue(myClientCount >= 0); - if (myClientCount == 0) { + private void onClientRemoved(@NotNull Document document, @NotNull DiffRangeMarker marker, @NotNull RangeInvalidListener listener) { + if (myDiffRangeMarkers.remove(marker) == listener && myDiffRangeMarkers.isEmpty()) { document.putUserData(KEY, null); document.removeDocumentListener(this); } diff --git a/platform/platform-impl/src/com/intellij/openapi/editor/impl/EditorImpl.java b/platform/platform-impl/src/com/intellij/openapi/editor/impl/EditorImpl.java index 0b54147990d0..52cdc8c558e2 100644 --- a/platform/platform-impl/src/com/intellij/openapi/editor/impl/EditorImpl.java +++ b/platform/platform-impl/src/com/intellij/openapi/editor/impl/EditorImpl.java @@ -130,10 +130,12 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi @NonNls public static final Object IGNORE_MOUSE_TRACKING = "ignore_mouse_tracking"; public static final Key PERMANENT_HEADER = Key.create("PERMANENT_HEADER"); public static final Key DO_DOCUMENT_UPDATE_TEST = Key.create("DoDocumentUpdateTest"); + public static final Key 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 BUFFER = Key.create("buffer"); - public static final JBColor CURSOR_FOREGROUND = new JBColor(Gray._255, Gray._0); + public static final Color CURSOR_FOREGROUND_LIGHT = Gray._255; + public static final Color CURSOR_FOREGROUND_DARK = Gray._0; @NotNull private final DocumentEx myDocument; private final JPanel myPanel; @@ -249,6 +251,7 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi private boolean myEmbeddedIntoDialogWrapper; @Nullable private CachedFontContent myLastCache; private int myDragOnGutterSelectionStartLine = -1; + private RangeMarker myDraggedRange; private boolean mySoftWrapsChanged; @@ -323,6 +326,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 +556,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) @@ -4328,10 +4346,12 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi if (caretShift != 0) { if (myMousePressedEvent != null) { if (mySettings.isDndEnabled()) { - boolean isCopy = UIUtil.isControlKeyDown(e) || isViewer() || !getDocument().isWritable(); - mySavedCaretOffsetForDNDUndoHack = oldCaretOffset; - getContentComponent().getTransferHandler() - .exportAsDrag(getContentComponent(), e, isCopy ? TransferHandler.COPY : TransferHandler.MOVE); + if (myDraggedRange == null) { + boolean isCopy = UIUtil.isControlKeyDown(e) || isViewer() || !getDocument().isWritable(); + mySavedCaretOffsetForDNDUndoHack = oldCaretOffset; + getContentComponent().getTransferHandler() + .exportAsDrag(getContentComponent(), e, isCopy ? TransferHandler.COPY : TransferHandler.MOVE); + } } else { selectionModel.removeSelection(); @@ -4348,6 +4368,13 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi } } + private void clearDraggedRange() { + if (myDraggedRange != null) { + myDraggedRange.dispose(); + myDraggedRange = null; + } + } + private void createSelectionTill(@NotNull LogicalPosition targetPosition) { List caretStates = new ArrayList(myCaretStateBeforeLastPress); if (myRectangularSelectionInProgress) { @@ -4721,7 +4748,7 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi //todo[kb] //in case of italic style we paint out of the cursor block. Painting the symbol to a dedicated buffered image //solves the problem, but still looks weird because it leaves colored pixels at right. - g.setColor(CURSOR_FOREGROUND); + g.setColor(ColorUtil.isDark(caretColor) ? CURSOR_FOREGROUND_LIGHT : CURSOR_FOREGROUND_DARK); g.drawChars(new char[]{ch}, 0, 1, x, y + getAscent()); } } @@ -5571,6 +5598,7 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi myLastMousePressedLocation = xyToLogicalPosition(e.getPoint()); myCaretStateBeforeLastPress = isToggleCaretEvent(e) ? myCaretModel.getCaretsAndSelections() : Collections.emptyList(); myCurrentDragIsSubstantial = false; + clearDraggedRange(); final int clickOffset = logicalPositionToOffset(myLastMousePressedLocation); putUserData(EditorActionUtil.EXPECTED_CARET_OFFSET, clickOffset); @@ -6224,16 +6252,14 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi } private static class MyTransferHandler extends TransferHandler { - private RangeMarker myDraggedRange = null; - - private static Editor getEditor(@NotNull JComponent comp) { + private static EditorImpl getEditor(@NotNull JComponent comp) { EditorComponentImpl editorComponent = (EditorComponentImpl)comp; return editorComponent.getEditor(); } @Override public boolean importData(@NotNull final JComponent comp, @NotNull final Transferable t) { - final EditorImpl editor = (EditorImpl)getEditor(comp); + final EditorImpl editor = getEditor(comp); final EditorDropHandler dropHandler = editor.getDropHandler(); if (dropHandler != null && dropHandler.canHandleDrop(t.getTransferDataFlavors())) { @@ -6242,11 +6268,12 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi } final int caretOffset = editor.getCaretModel().getOffset(); - if (myDraggedRange != null && myDraggedRange.getStartOffset() <= caretOffset && caretOffset < myDraggedRange.getEndOffset()) { + if (editor.myDraggedRange != null + && editor.myDraggedRange.getStartOffset() <= caretOffset && caretOffset < editor.myDraggedRange.getEndOffset()) { return false; } - if (myDraggedRange != null) { + if (editor.myDraggedRange != null) { editor.getCaretModel().moveToOffset(editor.mySavedCaretOffsetForDNDUndoHack); } @@ -6260,7 +6287,7 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi editor.getSelectionModel().removeSelection(); final int offset; - if (myDraggedRange != null) { + if (editor.myDraggedRange != null) { editor.getCaretModel().moveToOffset(caretOffset); offset = caretOffset; } @@ -6321,12 +6348,12 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi @Override @Nullable protected Transferable createTransferable(JComponent c) { - Editor editor = getEditor(c); + EditorImpl editor = getEditor(c); String s = editor.getSelectionModel().getSelectedText(); if (s == null) return null; int selectionStart = editor.getSelectionModel().getSelectionStart(); int selectionEnd = editor.getSelectionModel().getSelectionEnd(); - myDraggedRange = editor.getDocument().createRangeMarker(selectionStart, selectionEnd); + editor.myDraggedRange = editor.getDocument().createRangeMarker(selectionStart, selectionEnd); return new StringSelection(s); } @@ -6344,8 +6371,8 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi if (last != null && !(last instanceof EditorComponentImpl)) return; - final Editor editor = getEditor(source); - if (action == MOVE && !editor.isViewer() && myDraggedRange != null) { + final EditorImpl editor = getEditor(source); + if (action == MOVE && !editor.isViewer() && editor.myDraggedRange != null) { if (!FileDocumentManager.getInstance().requestWriting(editor.getDocument(), editor.getProject())) { return; } @@ -6358,7 +6385,7 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi Document doc = editor.getDocument(); doc.startGuardedBlockChecking(); try { - doc.deleteString(myDraggedRange.getStartOffset(), myDraggedRange.getEndOffset()); + doc.deleteString(editor.myDraggedRange.getStartOffset(), editor.myDraggedRange.getEndOffset()); } catch (ReadOnlyFragmentModificationException e) { EditorActionManager.getInstance().getReadonlyFragmentModificationHandler(doc).handle(e); @@ -6372,7 +6399,7 @@ public final class EditorImpl extends UserDataHolderBase implements EditorEx, Hi }, EditorBundle.message("move.selection.command.name"), DND_COMMAND_KEY, UndoConfirmationPolicy.DEFAULT, editor.getDocument()); } - myDraggedRange = null; + editor.clearDraggedRange(); } } diff --git a/platform/platform-impl/src/com/intellij/openapi/editor/impl/ForcedSoftWrapsNotificationProvider.java b/platform/platform-impl/src/com/intellij/openapi/editor/impl/ForcedSoftWrapsNotificationProvider.java new file mode 100644 index 000000000000..daec6275ec7c --- /dev/null +++ b/platform/platform-impl/src/com/intellij/openapi/editor/impl/ForcedSoftWrapsNotificationProvider.java @@ -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 { + private static final Key KEY = Key.create("forced.soft.wraps.notification.panel"); + private static final String NOTIFICATION_SETTINGS_KEY = "Forced soft wraps in editor"; + + @NotNull + @Override + public Key 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; + } +} diff --git a/platform/platform-impl/src/com/intellij/openapi/editor/impl/SettingsImpl.java b/platform/platform-impl/src/com/intellij/openapi/editor/impl/SettingsImpl.java index 560fec4fb8a0..6a7b3be213f2 100644 --- a/platform/platform-impl/src/com/intellij/openapi/editor/impl/SettingsImpl.java +++ b/platform/platform-impl/src/com/intellij/openapi/editor/impl/SettingsImpl.java @@ -545,6 +545,10 @@ public class SettingsImpl implements EditorSettings { myUseSoftWraps = newValue; fireEditorRefresh(); } + + public void setUseSoftWrapsQuiet() { + myUseSoftWraps = Boolean.TRUE; + } @Override public boolean isAllSoftWrapsShown() { diff --git a/platform/platform-impl/src/com/intellij/openapi/options/ex/ConfigurableCardPanel.java b/platform/platform-impl/src/com/intellij/openapi/options/ex/ConfigurableCardPanel.java index f851bda95b39..232bc62c7b3b 100644 --- a/platform/platform-impl/src/com/intellij/openapi/options/ex/ConfigurableCardPanel.java +++ b/platform/platform-impl/src/com/intellij/openapi/options/ex/ConfigurableCardPanel.java @@ -29,7 +29,13 @@ import java.awt.BorderLayout; /** * @author Sergey.Malenkov */ -public class ConfigurableCardPanel extends CardLayoutPanel { +public class ConfigurableCardPanel extends CardLayoutPanel { + @Override + protected Configurable prepare(Configurable key) { + ConfigurableWrapper.cast(Configurable.class, key); // create wrapped configurable on a pooled thread + return key; + } + @Override protected JComponent create(final Configurable configurable) { return configurable == null ? null : ApplicationManager.getApplication().runReadAction(new Computable() { diff --git a/platform/platform-impl/src/com/intellij/openapi/project/DumbServiceImpl.java b/platform/platform-impl/src/com/intellij/openapi/project/DumbServiceImpl.java index 7b3bd2198cf9..42d88cf5a4a0 100644 --- a/platform/platform-impl/src/com/intellij/openapi/project/DumbServiceImpl.java +++ b/platform/platform-impl/src/com/intellij/openapi/project/DumbServiceImpl.java @@ -63,6 +63,7 @@ public class DumbServiceImpl extends DumbService implements Disposable { private final Queue myRunWhenSmartQueue = new Queue(5); private final Project myProject; + private ThreadLocal myAlternativeResolution = new ThreadLocal(); public DumbServiceImpl(Project project) { myProject = project; @@ -104,6 +105,17 @@ public class DumbServiceImpl extends DumbService implements Disposable { return myProject; } + @Override + public boolean isAlternativeResolveEnabled() { + return Boolean.TRUE.equals(myAlternativeResolution.get()); + } + + @Override + public void setAlternativeResolveEnabled(boolean enabled) { + assert isAlternativeResolveEnabled() != enabled : "Nested alternative resolution mode is not supported"; + myAlternativeResolution.set(enabled); + } + @Override public boolean isDumb() { return myDumb; diff --git a/platform/platform-impl/src/com/intellij/ui/CardLayoutPanel.java b/platform/platform-impl/src/com/intellij/ui/CardLayoutPanel.java index 09b39042abce..ac4968903b20 100644 --- a/platform/platform-impl/src/com/intellij/ui/CardLayoutPanel.java +++ b/platform/platform-impl/src/com/intellij/ui/CardLayoutPanel.java @@ -26,13 +26,34 @@ import java.util.Iterator; import java.util.Map.Entry; /** + * @param the type of an object used as a key + * @param the type of an object used to create a component + * @param the type of a component to create + * * @author Sergey.Malenkov */ -public abstract class CardLayoutPanel extends JComponent { +public abstract class CardLayoutPanel extends JComponent { private final IdentityHashMap myContent = new IdentityHashMap(); private K myKey; - protected abstract V create(K key); + /** + * Prepares the specified key object to return the temporary object + * that can be used to create a component view. + * This method may be called on a pooled thread. + * + * @param key the key object + * @return the object used to create a component + */ + protected abstract UI prepare(K key); + + /** + * Creates a component view from the temporary object. + * This method is usually called on the EDT. + * + * @param ui + * @return + */ + protected abstract V create(UI ui); protected void dispose(K key) { } @@ -44,12 +65,12 @@ public abstract class CardLayoutPanel extends JComponent public V getValue(K key, boolean create) { V value = myContent.get(key); return create && value == null && !myContent.containsKey(key) - ? createValue(key) + ? createValue(key, prepare(key)) : value; } - private V createValue(K key) { - V value = create(key); + private V createValue(K key, UI ui) { + V value = create(ui); myContent.put(key, value); if (value != null) { value.setVisible(false); @@ -61,39 +82,44 @@ public abstract class CardLayoutPanel extends JComponent public ActionCallback select(K key, boolean now) { myKey = key; ActionCallback callback = new ActionCallback(); - select(callback, key, now); + if (now) { + select(callback, key, prepare(key)); + } + else { + selectLater(callback, key); + } return callback; } - private void select(ActionCallback callback, K key, boolean now) { + private void select(ActionCallback callback, K key, UI ui) { if (myKey != key) { callback.setRejected(); } else { V value = myContent.get(key); - boolean create = value == null && !myContent.containsKey(key); - if (create && !now) { - selectLater(callback, key, true); + if (value == null && !myContent.containsKey(key)) { + value = createValue(key, ui); } - else { - if (create) { - value = createValue(key); - } - for (Component component : getComponents()) { - component.setVisible(component == value); - } - callback.setDone(); + for (Component component : getComponents()) { + component.setVisible(component == value); } + callback.setDone(); } } - private void selectLater(final ActionCallback callback, final K key, final boolean create) { - ApplicationManager.getApplication().invokeLater(new Runnable() { + private void selectLater(final ActionCallback callback, final K key) { + ApplicationManager.getApplication().executeOnPooledThread(new Runnable() { @Override public void run() { - select(callback, key, create); + final UI ui = prepare(key); + ApplicationManager.getApplication().invokeLater(new Runnable() { + @Override + public void run() { + select(callback, key, ui); + } + }, ModalityState.any()); } - }, ModalityState.any()); + }); } @Override @@ -113,6 +139,9 @@ public abstract class CardLayoutPanel extends JComponent @Override public Dimension getPreferredSize() { + if (isPreferredSizeSet()) { + return super.getPreferredSize(); + } for (Component component : getComponents()) { if (component.isVisible()) { return component.getPreferredSize(); @@ -123,6 +152,9 @@ public abstract class CardLayoutPanel extends JComponent @Override public Dimension getMinimumSize() { + if (isMinimumSizeSet()) { + return super.getMinimumSize(); + } for (Component component : getComponents()) { if (component.isVisible()) { return component.getMinimumSize(); diff --git a/platform/platform-impl/src/com/intellij/util/ui/ReloadableComboBoxPanel.form b/platform/platform-impl/src/com/intellij/util/ui/ReloadableComboBoxPanel.form new file mode 100644 index 000000000000..3f7b56801418 --- /dev/null +++ b/platform/platform-impl/src/com/intellij/util/ui/ReloadableComboBoxPanel.form @@ -0,0 +1,34 @@ + +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
diff --git a/platform/platform-impl/src/com/intellij/util/ui/ReloadableComboBoxPanel.java b/platform/platform-impl/src/com/intellij/util/ui/ReloadableComboBoxPanel.java new file mode 100644 index 000000000000..fb6849aa1396 --- /dev/null +++ b/platform/platform-impl/src/com/intellij/util/ui/ReloadableComboBoxPanel.java @@ -0,0 +1,190 @@ +/* + * 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.util.ui; + +import com.intellij.icons.AllIcons; +import com.intellij.openapi.actionSystem.ActionToolbar; +import com.intellij.openapi.actionSystem.AnAction; +import com.intellij.openapi.actionSystem.AnActionEvent; +import com.intellij.openapi.actionSystem.impl.ActionButton; +import com.intellij.openapi.ui.ComboBox; +import com.intellij.ui.JBColor; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import javax.swing.*; +import java.awt.*; +import java.util.Set; + +public abstract class ReloadableComboBoxPanel { + public interface DataProvider { + + /** + * returns init cached values + */ + @Nullable + Set getCachedValues(); + + /** + * After getting values method must call #onUpdateValues or #onValuesUpdateError + */ + void updateValuesAsynchronously(); + } + + private static final String CONTROL_PLACE = "UI.Configuration.Component.Reload.Panel"; + + private final AsyncProcessIcon myLoadingVersionIcon = new AsyncProcessIcon("Getting possible values"); + + private final JLabel myErrorMessage = new JLabel(); + @Nullable + private volatile DataProvider myDataProvider; + @Nullable + private volatile UpdateStatus myUpdateStatus; + protected JComboBox myComboBox; + + protected JPanel myActionPanel; + protected JPanel myMainPanel; + public ReloadableComboBoxPanel() { + myErrorMessage.setForeground(JBColor.RED); + fillActionPanel(); + } + + public final void setDataProvider(@NotNull DataProvider dataProvider) { + myDataProvider = dataProvider; + + Set cachedValues = dataProvider.getCachedValues(); + if (cachedValues != null) { + onUpdateValues(cachedValues); + } + } + + protected abstract void doUpdateValues(@NotNull Set values); + + @SuppressWarnings("unchecked") + public T getSelectedValue() { + return (T)myComboBox.getSelectedItem(); + } + + @NotNull + public final JLabel getErrorComponent() { + return myErrorMessage; + } + + public final boolean isBackgroundJobRunning() { + return myUpdateStatus == UpdateStatus.UPDATING; + } + + public final void onUpdateValues(@NotNull Set values) { + changeUpdateStatus(UpdateStatus.IDLE); + doUpdateValues(values); + } + + public final void reloadValuesInBackground() { + if (myUpdateStatus == UpdateStatus.UPDATING) return; + changeUpdateStatus(UpdateStatus.UPDATING); + myErrorMessage.setText(null); + DataProvider provider = myDataProvider; + assert provider != null; + provider.updateValuesAsynchronously(); + } + + private void changeUpdateStatus(@NotNull UpdateStatus status) { + CardLayout cardLayout = (CardLayout)myActionPanel.getLayout(); + cardLayout.show(myActionPanel, status.name()); + if (status == UpdateStatus.UPDATING) { + myLoadingVersionIcon.resume(); + } + else { + myLoadingVersionIcon.suspend(); + } + myUpdateStatus = status; + } + + private void fillActionPanel() { + myActionPanel.add(createReloadButtonPanel(), UpdateStatus.IDLE.name()); + myActionPanel.add(createReloadInProgressPanel(), UpdateStatus.UPDATING.name()); + changeUpdateStatus(UpdateStatus.IDLE); + } + + public final void onValuesUpdateError(@NotNull final String errorMessage) { + UIUtil.invokeLaterIfNeeded(new Runnable() { + @Override + public void run() { + if (getSelectedValue() == null) { + myErrorMessage.setText(errorMessage); + } + changeUpdateStatus(UpdateStatus.IDLE); + } + }); + } + + + @NotNull + private JPanel createReloadButtonPanel() { + ReloadAction reloadAction = new ReloadAction(); + ActionButton reloadButton = new ActionButton( + reloadAction, + reloadAction.getTemplatePresentation().clone(), + CONTROL_PLACE, + ActionToolbar.DEFAULT_MINIMUM_BUTTON_SIZE + ); + JPanel panel = new JPanel(new BorderLayout(0, 0)); + panel.add(reloadButton, BorderLayout.WEST); + return panel; + } + + @NotNull + public final JPanel getMainPanel() { + return myMainPanel; + } + + @NotNull + private JPanel createReloadInProgressPanel() { + JPanel panel = new JPanel(); + panel.add(myLoadingVersionIcon); + return panel; + } + + private final class ReloadAction extends AnAction { + + private ReloadAction() { + super("Reload list", null, AllIcons.Actions.Refresh); + } + + @Override + public void actionPerformed(AnActionEvent e) { + reloadValuesInBackground(); + } + + @Override + public void update(AnActionEvent e) { + e.getPresentation().setEnabled(true); + } + } + + private enum UpdateStatus { + UPDATING, IDLE + } + + @NotNull + protected JComboBox createValuesComboBox() { + return new ComboBox(); + } + + private void createUIComponents() { + myComboBox = createValuesComboBox(); + } +} diff --git a/platform/platform-impl/src/org/jetbrains/io/PowerSupplyKit.java b/platform/platform-impl/src/org/jetbrains/io/PowerSupplyKit.java index 6464c6afb5c2..16c23e102155 100644 --- a/platform/platform-impl/src/org/jetbrains/io/PowerSupplyKit.java +++ b/platform/platform-impl/src/org/jetbrains/io/PowerSupplyKit.java @@ -15,11 +15,129 @@ */ package org.jetbrains.io; +import com.intellij.ide.PowerSaveMode; +import com.intellij.notification.*; +import com.intellij.openapi.application.ApplicationManager; +import com.intellij.openapi.util.SystemInfo; +import com.intellij.openapi.util.registry.Registry; +import com.intellij.util.lang.UrlClassLoader; +import org.jetbrains.annotations.NotNull; + +import javax.swing.event.HyperlinkEvent; + + public class PowerSupplyKit { - public static void checkPowerSupply() { + private static final String POWER_SUPPLY_GROUP_ID = "Power Supply Integration"; + private static boolean shouldCheckCordUnplug = Registry.is("check.power.supply.for.mbp") && SystemInfo.isMacIntel64; + //private static boolean shouldCheckDiscreteCard = + // Registry.is("check.power.supply.for.mbp") && SystemInfo.isMacIntel64 && hasDiscreteCard(); + static { + if (shouldCheckCordUnplug) { + UrlClassLoader.loadPlatformLibrary("MacNativeKit"); + } } + private static native void startListenPowerSupply (PowerSupplyKitCallback callback); + private static native boolean isPlugged(); + private static native String[] getInfo (); + private static boolean automaticallySwitchInPowerSaveModeOnUnpluggedCordEvent; + + // The first notification has been shown and + // power callback has been configurated + private static boolean powerSupplyKitHasBeenInitialized; + + private static boolean hasDiscreteCard() { + String [] models = getInfo(); + + if (models.length > 1) { + return true; + //for (String model : models) { + // if (model.contains("NVIDIA")) return true; + //} + } + + return false; + } + + public static void checkPowerSupply() { + + if (!shouldCheckCordUnplug) return; + + new Thread() { + @Override + public void run() { + startListenPowerSupply(new PowerSupplyKitCallback() { + @Override + public void call() { + initializeIfNeeded(); + PowerSaveMode.setEnabled(automaticallySwitchInPowerSaveModeOnUnpluggedCordEvent && isPlugged()); + } + }); + } + }.start(); + shouldCheckCordUnplug = false; + } + + private static void initializeIfNeeded() { + + if (powerSupplyKitHasBeenInitialized) return; + + NotificationsConfiguration.getNotificationsConfiguration().register( + POWER_SUPPLY_GROUP_ID, + NotificationDisplayType.STICKY_BALLOON, + false); + + final NotificationType type = NotificationType.INFORMATION; + + final NotificationListener listener = new NotificationListener() { + @Override + public void hyperlinkUpdate(@NotNull Notification notification, @NotNull HyperlinkEvent event) { + if (event.getEventType() == HyperlinkEvent.EventType.ACTIVATED) { + final String description = event.getDescription(); + if ("doNotShow".equals(description)) { + NotificationsConfiguration.getNotificationsConfiguration().changeSettings(POWER_SUPPLY_GROUP_ID, NotificationDisplayType.NONE, false, false); + notification.expire(); + } + if ("automatically".equals(description)) { + automaticallySwitchInPowerSaveModeOnUnpluggedCordEvent = true; + } + } + + } + }; + + //final String message = "We have noticed that your computer power cord is disconnected and you are using" + + // " a discrete video card on you MacBook Pro. You can switch " + + // " to the integrated video card. This significantly extend your battery life." + + // " Do no show this message anymore"; + + final String automaticPowerSafeModeSwitchMessage = "We have noticed that your computer power cord is disconnected. " + + "On unplugging your power cord we can automatically switch " + + "your Mac Book in a Power Save mode . This can extend your battery life." + + " Do no show this message anymore"; + + //final String powerSafeModeTurnedOnMesssage = "Power Save mode is turned on. Do no show this message anymore"; + + //final Notification notification = new Notification(POWER_SUPPLY_GROUP_ID, "Discrete video card warning", message, type, listener); + final Notification automaticPowerSafeModeSwitchNotification = + new Notification(POWER_SUPPLY_GROUP_ID, "Automatically enable Power Save mode", + automaticPowerSafeModeSwitchMessage, type, listener); + + + //final Notification powerSafeModeSwitchedNotification = + // new Notification(POWER_SUPPLY_GROUP_ID, "\"Power Save\" mode ", message, type, listener); + + ApplicationManager.getApplication().executeOnPooledThread(new Runnable() { + @Override + public void run() { + ApplicationManager.getApplication().getMessageBus(). + syncPublisher(Notifications.TOPIC).notify(automaticPowerSafeModeSwitchNotification); + } + }); + + powerSupplyKitHasBeenInitialized = true; + } } diff --git a/platform/platform-resources-en/src/messages/EditorBundle.properties b/platform/platform-resources-en/src/messages/EditorBundle.properties index 4cff2b744d91..575bd2d4b37b 100644 --- a/platform/platform-resources-en/src/messages/EditorBundle.properties +++ b/platform/platform-resources-en/src/messages/EditorBundle.properties @@ -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 \ No newline at end of file +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 \ No newline at end of file diff --git a/platform/platform-resources/src/META-INF/PlatformExtensions.xml b/platform/platform-resources/src/META-INF/PlatformExtensions.xml index b45e068f1afd..14ef0cd79cc2 100644 --- a/platform/platform-resources/src/META-INF/PlatformExtensions.xml +++ b/platform/platform-resources/src/META-INF/PlatformExtensions.xml @@ -335,6 +335,7 @@ + diff --git a/platform/platform-tests/testSrc/com/intellij/usages/impl/UsageViewManagerTest.java b/platform/platform-tests/testSrc/com/intellij/usages/impl/UsageViewManagerTest.java new file mode 100644 index 000000000000..3e38bd2bbb4a --- /dev/null +++ b/platform/platform-tests/testSrc/com/intellij/usages/impl/UsageViewManagerTest.java @@ -0,0 +1,39 @@ +/* + * 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.usages.impl; + +import com.intellij.find.FindModel; +import com.intellij.find.impl.FindInProjectUtil; +import com.intellij.openapi.vfs.VirtualFile; +import com.intellij.psi.search.GlobalSearchScopesCore; +import com.intellij.psi.search.SearchScope; +import com.intellij.testFramework.PlatformTestCase; +import com.intellij.usages.UsageTarget; +import com.intellij.usages.UsageViewManager; + +public class UsageViewManagerTest extends PlatformTestCase { + public void testScopeCreatedForFindInDirectory() { + VirtualFile dir = getProject().getBaseDir(); + FindModel findModel = new FindModel(); + findModel.setDirectoryName(dir.getPath()); + findModel.setWithSubdirectories(true); + findModel.setProjectScope(false); + UsageTarget target = new FindInProjectUtil.StringUsageTarget(getProject(), findModel); + UsageViewManagerImpl manager = (UsageViewManagerImpl)UsageViewManager.getInstance(getProject()); + SearchScope scope = manager.getMaxSearchScopeToWarnOfFallingOutOf(new UsageTarget[]{target}); + assertEquals(scope, GlobalSearchScopesCore.directoryScope(getProject(), dir, true)); + } +} diff --git a/platform/platform-tests/testSrc/com/intellij/util/io/HttpRequestsTest.java b/platform/platform-tests/testSrc/com/intellij/util/io/HttpRequestsTest.java index 682b646a53e8..b6549ab094c9 100644 --- a/platform/platform-tests/testSrc/com/intellij/util/io/HttpRequestsTest.java +++ b/platform/platform-tests/testSrc/com/intellij/util/io/HttpRequestsTest.java @@ -22,10 +22,10 @@ import org.junit.Test; import java.io.IOException; import java.net.SocketTimeoutException; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.fail; +import static org.hamcrest.CoreMatchers.containsString; +import static org.junit.Assert.*; -public class HttpRequestsTest { +public class HttpRequestsTest { private final HttpRequests.RequestProcessor myProcessor = new HttpRequests.RequestProcessor() { @SuppressWarnings("ResultOfMethodCallIgnored") @Override @@ -57,4 +57,9 @@ public class HttpRequestsTest { HttpRequests.request("http://openjdk.java.net").readTimeout(1).connect(myProcessor); fail(); } + + @Test(timeout = 5000) + public void testReadString() throws IOException { + assertThat(HttpRequests.request("http://openjdk.java.net").getString(null), containsString("Download")); + } } diff --git a/platform/projectModel-impl/src/com/intellij/openapi/components/impl/stores/DefaultStateSerializer.java b/platform/projectModel-impl/src/com/intellij/openapi/components/impl/stores/DefaultStateSerializer.java index 71fb2056386d..2b810028626a 100644 --- a/platform/projectModel-impl/src/com/intellij/openapi/components/impl/stores/DefaultStateSerializer.java +++ b/platform/projectModel-impl/src/com/intellij/openapi/components/impl/stores/DefaultStateSerializer.java @@ -1,5 +1,5 @@ /* - * Copyright 2000-2012 JetBrains s.r.o. + * 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. @@ -26,6 +26,7 @@ import com.intellij.openapi.util.WriteExternalException; import com.intellij.util.ReflectionUtil; import com.intellij.util.xmlb.Accessor; import com.intellij.util.xmlb.SkipDefaultValuesSerializationFilters; +import com.intellij.util.xmlb.XmlSerializationException; import com.intellij.util.xmlb.XmlSerializer; import org.jdom.Element; import org.jetbrains.annotations.NotNull; @@ -71,7 +72,7 @@ public class DefaultStateSerializer { @SuppressWarnings({"unchecked"}) @Nullable - public static T deserializeState(@Nullable Element stateElement, Class stateClass, @Nullable T mergeInto) throws StateStorageException { + public static T deserializeState(@Nullable Element stateElement, Class stateClass, @Nullable T mergeInto) throws StateStorageException,XmlSerializationException { if (stateElement == null) return mergeInto; if (stateClass.equals(Element.class)) { diff --git a/platform/testFramework/testSrc/com/intellij/testFramework/vcs/AbstractVcsTestCase.java b/platform/testFramework/testSrc/com/intellij/testFramework/vcs/AbstractVcsTestCase.java index b64e222e7792..bc20186244dd 100644 --- a/platform/testFramework/testSrc/com/intellij/testFramework/vcs/AbstractVcsTestCase.java +++ b/platform/testFramework/testSrc/com/intellij/testFramework/vcs/AbstractVcsTestCase.java @@ -59,8 +59,6 @@ public abstract class AbstractVcsTestCase { protected IdeaProjectTestFixture myProjectFixture; protected boolean myInitChangeListManager = true; - protected abstract String getPluginName(); - protected TestClientRunner createClientRunner() { return createClientRunner(null); } @@ -90,42 +88,26 @@ public abstract class AbstractVcsTestCase { } protected void initProject(final File clientRoot, String testName) throws Exception { - final String key = "idea.load.plugins.id"; - final String was = System.getProperty(key); - try { - final String pluginName = getPluginName(); - if (pluginName != null) { - System.setProperty(key, pluginName); - } - String name = testName; - final TestFixtureBuilder testFixtureBuilder = IdeaTestFixtureFactory.getFixtureFactory().createFixtureBuilder(name); - myProjectFixture = testFixtureBuilder.getFixture(); - testFixtureBuilder.addModule(EmptyModuleFixtureBuilder.class).addContentRoot(clientRoot.toString()); - myProjectFixture.setUp(); - myProject = myProjectFixture.getProject(); + final TestFixtureBuilder testFixtureBuilder = IdeaTestFixtureFactory.getFixtureFactory().createFixtureBuilder(testName); + myProjectFixture = testFixtureBuilder.getFixture(); + testFixtureBuilder.addModule(EmptyModuleFixtureBuilder.class).addContentRoot(clientRoot.toString()); + myProjectFixture.setUp(); + myProject = myProjectFixture.getProject(); - projectCreated(); + projectCreated(); - if (myInitChangeListManager) { - ((ProjectComponent) ChangeListManager.getInstance(myProject)).projectOpened(); - } - ((ProjectComponent) VcsDirtyScopeManager.getInstance(myProject)).projectOpened(); - - ApplicationManager.getApplication().runWriteAction(new Runnable() { - @Override - public void run() { - myWorkingCopyDir = LocalFileSystem.getInstance().refreshAndFindFileByIoFile(clientRoot); - assert myWorkingCopyDir != null; - } - }); + if (myInitChangeListManager) { + ((ProjectComponent) ChangeListManager.getInstance(myProject)).projectOpened(); } - finally { - if (was != null) { - System.setProperty(key, was); - } else { - System.clearProperty(key); + ((ProjectComponent) VcsDirtyScopeManager.getInstance(myProject)).projectOpened(); + + ApplicationManager.getApplication().runWriteAction(new Runnable() { + @Override + public void run() { + myWorkingCopyDir = LocalFileSystem.getInstance().refreshAndFindFileByIoFile(clientRoot); + assert myWorkingCopyDir != null; } - } + }); ((ProjectLevelVcsManagerImpl)ProjectLevelVcsManager.getInstance(myProject)).waitForInitialized(); } diff --git a/platform/usageView/src/com/intellij/usages/UsageLimitUtil.java b/platform/usageView/src/com/intellij/usages/UsageLimitUtil.java index 61fd1d91abd7..fbee3a7b9316 100644 --- a/platform/usageView/src/com/intellij/usages/UsageLimitUtil.java +++ b/platform/usageView/src/com/intellij/usages/UsageLimitUtil.java @@ -48,13 +48,12 @@ public class UsageLimitUtil { public static Result showTooManyUsagesWarning(@NotNull final Project project, @NotNull final String message, @NotNull final UsageViewPresentation usageViewPresentation) { - final String[] buttons = {UsageViewBundle.message("button.text.continue"), UsageViewBundle.message("button.text.abort")}; int result = runOrInvokeAndWait(new Computable() { @Override public Integer compute() { String title = UsageViewBundle.message("find.excessive.usages.title", StringUtil.capitalize(StringUtil.pluralize(usageViewPresentation.getUsagesWord()))); return Messages.showOkCancelDialog(project, message, - title, buttons[0], buttons[1], + title, UsageViewBundle.message("button.text.continue"), UsageViewBundle.message("button.text.abort"), Messages.getWarningIcon()); } }); diff --git a/platform/usageView/src/com/intellij/usages/impl/SearchForUsagesRunnable.java b/platform/usageView/src/com/intellij/usages/impl/SearchForUsagesRunnable.java index 680e621a8f16..449c462d7668 100644 --- a/platform/usageView/src/com/intellij/usages/impl/SearchForUsagesRunnable.java +++ b/platform/usageView/src/com/intellij/usages/impl/SearchForUsagesRunnable.java @@ -277,7 +277,7 @@ class SearchForUsagesRunnable implements Runnable { rangeBlinker.startBlinking(); } - private UsageViewImpl getUsageView(ProgressIndicator indicator) { + private UsageViewImpl getUsageView(@NotNull ProgressIndicator indicator) { UsageViewImpl usageView = myUsageViewRef.get(); if (usageView != null) return usageView; int usageCount = myUsageCountWithoutDefinition.get(); diff --git a/platform/usageView/src/com/intellij/usages/impl/UsageViewImpl.java b/platform/usageView/src/com/intellij/usages/impl/UsageViewImpl.java index d981aac222a1..566acce9ca60 100644 --- a/platform/usageView/src/com/intellij/usages/impl/UsageViewImpl.java +++ b/platform/usageView/src/com/intellij/usages/impl/UsageViewImpl.java @@ -772,7 +772,7 @@ public class UsageViewImpl implements UsageView, UsageModelTracker.UsageModelTra return configurableTarget == null ? getShowUsagesWithSettingsShortcut() : configurableTarget.getShortcut(); } - void associateProgress(ProgressIndicator indicator) { + void associateProgress(@NotNull ProgressIndicator indicator) { associatedProgress = indicator; } diff --git a/platform/usageView/src/com/intellij/usages/impl/UsageViewManagerImpl.java b/platform/usageView/src/com/intellij/usages/impl/UsageViewManagerImpl.java index 2445bb2653d5..455718c1160d 100644 --- a/platform/usageView/src/com/intellij/usages/impl/UsageViewManagerImpl.java +++ b/platform/usageView/src/com/intellij/usages/impl/UsageViewManagerImpl.java @@ -122,16 +122,7 @@ public class UsageViewManagerImpl extends UsageViewManager { @NotNull final UsageViewPresentation presentation, @NotNull final FindUsagesProcessPresentation processPresentation, @Nullable final UsageViewStateListener listener) { - final SearchScope searchScope = getMaxSearchScopeToWarnOfFallingOutOf(searchFor); - return doSearchAndShow(searchFor, searcherFactory, presentation, processPresentation, listener, searchScope); - } - - private UsageView doSearchAndShow(@NotNull final UsageTarget[] searchFor, - @NotNull final Factory searcherFactory, - @NotNull final UsageViewPresentation presentation, - @NotNull final FindUsagesProcessPresentation processPresentation, - @Nullable final UsageViewStateListener listener, - @NotNull final SearchScope searchScopeToWarnOfFallingOutOf) { + final SearchScope searchScopeToWarnOfFallingOutOf = getMaxSearchScopeToWarnOfFallingOutOf(searchFor); final AtomicReference usageViewRef = new AtomicReference(); Task.Backgroundable task = new Task.Backgroundable(myProject, getProgressTitle(presentation), true, new SearchInBackgroundOption()) { @@ -159,7 +150,7 @@ public class UsageViewManagerImpl extends UsageViewManager { } @NotNull - private SearchScope getMaxSearchScopeToWarnOfFallingOutOf(@NotNull UsageTarget[] searchFor) { + SearchScope getMaxSearchScopeToWarnOfFallingOutOf(@NotNull UsageTarget[] searchFor) { UsageTarget target = searchFor[0]; if (target instanceof TypeSafeDataProvider) { final SearchScope[] scope = new SearchScope[1]; @@ -220,20 +211,22 @@ public class UsageViewManagerImpl extends UsageViewManager { } - static void showTooManyUsagesWarning(@NotNull final Project project, - @NotNull final TooManyUsagesStatus tooManyUsagesStatus, - @NotNull final ProgressIndicator indicator, - @NotNull final UsageViewPresentation presentation, - final int usageCount, - final UsageViewImpl usageView) { + public static void showTooManyUsagesWarning(@NotNull final Project project, + @NotNull final TooManyUsagesStatus tooManyUsagesStatus, + @NotNull final ProgressIndicator indicator, + @NotNull final UsageViewPresentation presentation, + final int usageCount, + @Nullable final UsageViewImpl usageView) { UIUtil.invokeLaterIfNeeded(new Runnable() { @Override public void run() { if (usageView != null && usageView.searchHasBeenCancelled() || indicator.isCanceled()) return; String message = UsageViewBundle.message("find.excessive.usage.count.prompt", usageCount, StringUtil.pluralize(presentation.getUsagesWord())); UsageLimitUtil.Result ret = UsageLimitUtil.showTooManyUsagesWarning(project, message, presentation); - if (ret == UsageLimitUtil.Result.ABORT && usageView != null) { - usageView.cancelCurrentSearch(); + if (ret == UsageLimitUtil.Result.ABORT) { + if (usageView != null) { + usageView.cancelCurrentSearch(); + } indicator.cancel(); } tooManyUsagesStatus.userResponded(); diff --git a/platform/util/resources/misc/registry.properties b/platform/util/resources/misc/registry.properties index aabe0235a7bf..0cefc572b11d 100644 --- a/platform/util/resources/misc/registry.properties +++ b/platform/util/resources/misc/registry.properties @@ -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 diff --git a/platform/util/src/com/intellij/icons/AllIcons.java b/platform/util/src/com/intellij/icons/AllIcons.java index b34b7bd4aeab..2e3233570e37 100644 --- a/platform/util/src/com/intellij/icons/AllIcons.java +++ b/platform/util/src/com/intellij/icons/AllIcons.java @@ -700,7 +700,9 @@ public class AllIcons { public static final Icon WebModule = IconLoader.getIcon("/javaee/webModule.png"); // 16x16 public static final Icon WebModuleGroup = IconLoader.getIcon("/javaee/webModuleGroup.png"); // 16x16 public static final Icon WebService = IconLoader.getIcon("/javaee/WebService.png"); // 16x16 + public static final Icon WebService2 = IconLoader.getIcon("/javaee/WebService2.png"); // 16x16 public static final Icon WebServiceClient = IconLoader.getIcon("/javaee/WebServiceClient.png"); // 16x16 + public static final Icon WebServiceClient2 = IconLoader.getIcon("/javaee/WebServiceClient2.png"); // 16x16 } diff --git a/platform/util/src/com/intellij/ui/Graphics2DDelegate.java b/platform/util/src/com/intellij/ui/Graphics2DDelegate.java index 1d13b77b367c..1e37bd7950f5 100644 --- a/platform/util/src/com/intellij/ui/Graphics2DDelegate.java +++ b/platform/util/src/com/intellij/ui/Graphics2DDelegate.java @@ -37,6 +37,10 @@ public class Graphics2DDelegate extends Graphics2D{ myDelegate=g2d; } + public Graphics2D getDelegate() { + return myDelegate; + } + @Override public void addRenderingHints(Map hints) { myDelegate.addRenderingHints(hints); diff --git a/platform/util/testSrc/com/intellij/util/containers/ConcurrentMapsTest.java b/platform/util/testSrc/com/intellij/util/containers/ConcurrentMapsTest.java index 7bb66066e24a..f97d78434835 100644 --- a/platform/util/testSrc/com/intellij/util/containers/ConcurrentMapsTest.java +++ b/platform/util/testSrc/com/intellij/util/containers/ConcurrentMapsTest.java @@ -47,8 +47,8 @@ public class ConcurrentMapsTest { @SuppressWarnings("unchecked") ConcurrentWeakHashMap map = new ConcurrentWeakHashMap(TObjectHashingStrategy.IDENTITY); map.put(new Object(), new Object()); - tryGcSoftlyReachableObjects(); // sometimes weak references are not collected under linux, try to stress gc to force them do { + tryGcSoftlyReachableObjects(); // sometimes weak references are not collected under linux, try to stress gc to force them System.gc(); } while (!map.processQueue()); @@ -85,8 +85,8 @@ public class ConcurrentMapsTest { ConcurrentWeakHashMap map = new ConcurrentWeakHashMap(); map.put(new Object(), new Object()); - tryGcSoftlyReachableObjects(); // sometimes weak references are not collected under linux, try to stress gc to force them do { + tryGcSoftlyReachableObjects(); // sometimes weak references are not collected under linux, try to stress gc to force them System.gc(); } while (!map.processQueue()); @@ -109,8 +109,8 @@ public class ConcurrentMapsTest { ConcurrentSoftHashMap map = new ConcurrentSoftHashMap(); map.put(new Object(), new Object()); - tryGcSoftlyReachableObjects(); do { + tryGcSoftlyReachableObjects(); System.gc(); } while (!map.processQueue()); @@ -125,8 +125,8 @@ public class ConcurrentMapsTest { (ConcurrentWeakValueHashMap)ContainerUtil.createConcurrentWeakValueMap(); map.put(new Object(), new Object()); - tryGcSoftlyReachableObjects(); // sometimes weak references are not collected under linux, try to stress gc to force them do { + tryGcSoftlyReachableObjects(); // sometimes weak references are not collected under linux, try to stress gc to force them System.gc(); } while (!map.processQueue()); @@ -140,8 +140,8 @@ public class ConcurrentMapsTest { ConcurrentSoftValueHashMap map = new ConcurrentSoftValueHashMap(); map.put(new Object(), new Object()); - tryGcSoftlyReachableObjects(); do { + tryGcSoftlyReachableObjects(); System.gc(); } while (!map.processQueue()); @@ -190,8 +190,8 @@ public class ConcurrentMapsTest { SoftKeySoftValueHashMap map = new SoftKeySoftValueHashMap(); map.put(new Object(), new Object()); - tryGcSoftlyReachableObjects(); do { + tryGcSoftlyReachableObjects(); System.gc(); } while (!map.processQueue()); @@ -203,8 +203,8 @@ public class ConcurrentMapsTest { WeakKeyWeakValueHashMap map = new WeakKeyWeakValueHashMap(); map.put(new Object(), new Object()); - tryGcSoftlyReachableObjects(); do { + tryGcSoftlyReachableObjects(); System.gc(); } while (!map.processQueue()); diff --git a/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/shelf/ImportIntoShelfAction.java b/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/shelf/ImportIntoShelfAction.java index 7e62df697a85..1b413dee79a4 100644 --- a/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/shelf/ImportIntoShelfAction.java +++ b/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/shelf/ImportIntoShelfAction.java @@ -40,7 +40,7 @@ import java.util.List; */ public class ImportIntoShelfAction extends DumbAwareAction { public ImportIntoShelfAction() { - super("Import patches...", "Copies patch file to shelf", null); + super("Import Patches...", "Copies a patch file to the shelf", null); } @Override diff --git a/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/ui/CommitChangeListDialog.java b/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/ui/CommitChangeListDialog.java index 779260b26f0d..73334983a268 100644 --- a/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/ui/CommitChangeListDialog.java +++ b/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/ui/CommitChangeListDialog.java @@ -142,9 +142,27 @@ public class CommitChangeListDialog extends DialogWrapper implements CheckinProj private final MyUpdateButtonsRunnable myUpdateButtonsRunnable = new MyUpdateButtonsRunnable(this); - public static boolean commitChanges(final Project project, final List changes, final LocalChangeList initialSelection, - final List executors, final boolean showVcsCommit, final String comment, - @Nullable CommitResultHandler customResultHandler, boolean cancelIfNoChanges) { + public static boolean commitChanges(final Project project, + final List changes, + final LocalChangeList initialSelection, + final List executors, + final boolean showVcsCommit, + final String comment, + @Nullable CommitResultHandler customResultHandler, + boolean cancelIfNoChanges) { + return commitChanges(project, changes, initialSelection, executors, showVcsCommit, null, comment, customResultHandler, + cancelIfNoChanges); + } + + public static boolean commitChanges(final Project project, + final List changes, + final LocalChangeList initialSelection, + final List executors, + final boolean showVcsCommit, + @Nullable final AbstractVcs singleVcs, + final String comment, + @Nullable CommitResultHandler customResultHandler, + boolean cancelIfNoChanges) { if (cancelIfNoChanges && changes.isEmpty() && !ApplicationManager.getApplication().isUnitTestMode()) { Messages.showInfoMessage(project, VcsBundle.message("commit.dialog.no.changes.detected.text"), VcsBundle.message("commit.dialog.no.changes.detected.title")); @@ -159,8 +177,10 @@ public class CommitChangeListDialog extends DialogWrapper implements CheckinProj } final ChangeListManager manager = ChangeListManager.getInstance(project); - CommitChangeListDialog dialog = new CommitChangeListDialog(project, changes, initialSelection, executors, showVcsCommit, manager.getDefaultChangeList(), manager.getChangeListsCopy(), null, - false, comment, customResultHandler); + CommitChangeListDialog dialog = + new CommitChangeListDialog(project, changes, initialSelection, executors, showVcsCommit, manager.getDefaultChangeList(), + manager.getChangeListsCopy(), singleVcs, + false, comment, customResultHandler); if (!ApplicationManager.getApplication().isUnitTestMode()) { dialog.show(); } @@ -990,7 +1010,7 @@ public class CommitChangeListDialog extends DialogWrapper implements CheckinProj if (myIsAlien) { helper.doAlienCommit(myVcs); } else { - helper.doCommit(); + helper.doCommit(myVcs); } } diff --git a/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/ui/CommitHelper.java b/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/ui/CommitHelper.java index 3f0747e80b30..b64d5ac1997c 100644 --- a/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/ui/CommitHelper.java +++ b/platform/vcs-impl/src/com/intellij/openapi/vcs/changes/ui/CommitHelper.java @@ -101,7 +101,11 @@ public class CommitHelper { } public boolean doCommit() { - return doCommit(new CommitProcessor()); + return doCommit((AbstractVcs)null); + } + + public boolean doCommit(@Nullable AbstractVcs vcs) { + return doCommit(new CommitProcessor(vcs)); } public boolean doAlienCommit(final AbstractVcs vcs) { @@ -374,8 +378,10 @@ public class CommitHelper { private LocalHistoryAction myAction; private ChangeListsModificationAfterCommit myAfterVcsRefreshModification; private boolean myCommitSuccess; + @Nullable private final AbstractVcs myVcs; - private CommitProcessor() { + private CommitProcessor(@Nullable AbstractVcs vcs) { + myVcs = vcs; myAfterVcsRefreshModification = ChangeListsModificationAfterCommit.NOTHING; if (myChangeList instanceof LocalChangeList) { final LocalChangeList localList = (LocalChangeList) myChangeList; @@ -391,6 +397,9 @@ public class CommitHelper { } public void callSelf() { + if (myVcs != null && myIncludedChanges.isEmpty()) { + process(myVcs, myIncludedChanges); + } ChangesUtil.processChangesByVcs(myProject, myIncludedChanges, this); } diff --git a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/actions/XFetchValueActionBase.java b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/actions/XFetchValueActionBase.java index eaa1d1aa1830..51ca1fa28b3a 100644 --- a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/actions/XFetchValueActionBase.java +++ b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/actions/XFetchValueActionBase.java @@ -75,7 +75,7 @@ public abstract class XFetchValueActionBase extends AnAction { if (node instanceof XValueNodeImpl) { XValueNodeImpl valueNode = (XValueNodeImpl)node; XFullValueEvaluator fullValueEvaluator = valueNode.getFullValueEvaluator(); - if (fullValueEvaluator == null) { + if (fullValueEvaluator == null || !fullValueEvaluator.isShowValuePopup()) { String rawValue; if (valueNode.getValueContainer() instanceof XValueTextProvider) { rawValue = ((XValueTextProvider)valueNode.getValueContainer()).getValueText(); diff --git a/plugins/gradle/src/org/jetbrains/plugins/gradle/settings/GradleProjectSettings.java b/plugins/gradle/src/org/jetbrains/plugins/gradle/settings/GradleProjectSettings.java index 7b25028b4b7d..54ab8818e9b8 100644 --- a/plugins/gradle/src/org/jetbrains/plugins/gradle/settings/GradleProjectSettings.java +++ b/plugins/gradle/src/org/jetbrains/plugins/gradle/settings/GradleProjectSettings.java @@ -27,7 +27,7 @@ import org.jetbrains.annotations.Nullable; public class GradleProjectSettings extends ExternalProjectSettings { @Nullable private String myGradleHome; - @Nullable private String myGradleJvm = ExternalSystemJdkUtil.USE_PROJECT_JDK; + @Nullable private String myGradleJvm; @Nullable private DistributionType distributionType; private boolean disableWrapperSourceDistributionNotification; diff --git a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit SetUp Method.groovy.html b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit SetUp Method.groovy.html index 02c3b66e19d7..59bf56df03e5 100644 --- a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit SetUp Method.groovy.html +++ b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit SetUp Method.groovy.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit TearDown Method.groovy.html b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit TearDown Method.groovy.html index 046d8efa5b4f..b31948642b23 100644 --- a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit TearDown Method.groovy.html +++ b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit TearDown Method.groovy.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit Test Case.groovy.html b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit Test Case.groovy.html index bfdc7bd7bbcb..d5fe228ec24e 100644 --- a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit Test Case.groovy.html +++ b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit Test Case.groovy.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created class. - ${BODY} + ${BODY}   generated class body. diff --git a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit Test Method.groovy.html b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit Test Method.groovy.html index 0278d7b08131..2f27795254f2 100644 --- a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit Test Method.groovy.html +++ b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy JUnit Test Method.groovy.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy New Method Body.groovy.html b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy New Method Body.groovy.html index 5a4cbfb7f3c7..a98243ef53ce 100644 --- a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy New Method Body.groovy.html +++ b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Groovy New Method Body.groovy.html @@ -14,27 +14,27 @@ Predefined variables will take the following values: - ${RETURN_TYPE} + ${RETURN_TYPE}   a return type of a created method - ${DEFAULT_RETURN_VALUE} + ${DEFAULT_RETURN_VALUE}   a value returned by the method by default - ${METHOD_NAME} + ${METHOD_NAME}   name of the created method - ${CLASS_NAME} + ${CLASS_NAME}   qualified name of the class where method is created - ${SIMPLE_CLASS_NAME} + ${SIMPLE_CLASS_NAME}   non-qualified name of the class where method is implemented diff --git a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock Test Method.groovy.html b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock Test Method.groovy.html index f9789fc6a2c4..8a162f4ad3a8 100644 --- a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock Test Method.groovy.html +++ b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock Test Method.groovy.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock cleanup Method.groovy.html b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock cleanup Method.groovy.html index 0517d8d4bc17..538317fa6376 100644 --- a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock cleanup Method.groovy.html +++ b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock cleanup Method.groovy.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock_SetUp_Method.groovy.html b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock_SetUp_Method.groovy.html index 379785f36c3f..0ae62ac4e8b8 100644 --- a/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock_SetUp_Method.groovy.html +++ b/plugins/groovy/groovy-psi/resources/fileTemplates/code/Spock_SetUp_Method.groovy.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/groovy/groovy-psi/src/org/jetbrains/plugins/groovy/lang/groovydoc/lexer/GroovyDocLexer.java b/plugins/groovy/groovy-psi/src/org/jetbrains/plugins/groovy/lang/groovydoc/lexer/GroovyDocLexer.java index 128e8498ea5a..1c86d5ab3589 100644 --- a/plugins/groovy/groovy-psi/src/org/jetbrains/plugins/groovy/lang/groovydoc/lexer/GroovyDocLexer.java +++ b/plugins/groovy/groovy-psi/src/org/jetbrains/plugins/groovy/lang/groovydoc/lexer/GroovyDocLexer.java @@ -16,10 +16,7 @@ package org.jetbrains.plugins.groovy.lang.groovydoc.lexer; -import com.intellij.lexer.Lexer; -import com.intellij.lexer.LexerBase; -import com.intellij.lexer.LookAheadLexer; -import com.intellij.lexer.MergingLexerAdapter; +import com.intellij.lexer.*; import com.intellij.psi.TokenType; import com.intellij.psi.tree.IElementType; import com.intellij.psi.tree.TokenSet; @@ -100,7 +97,7 @@ public class GroovyDocLexer extends MergingLexerAdapter { @Override public int getState() { - return myState; + return getTokenStart() == 0 ? 0 : myState; } @Override diff --git a/plugins/groovy/test/org/jetbrains/plugins/groovy/GroovyActionsTest.groovy b/plugins/groovy/test/org/jetbrains/plugins/groovy/GroovyActionsTest.groovy index dff034d87443..31b20cd633e3 100644 --- a/plugins/groovy/test/org/jetbrains/plugins/groovy/GroovyActionsTest.groovy +++ b/plugins/groovy/test/org/jetbrains/plugins/groovy/GroovyActionsTest.groovy @@ -13,17 +13,11 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -package org.jetbrains.plugins.groovy; +package org.jetbrains.plugins.groovy - -import com.intellij.ide.DataManager import com.intellij.openapi.actionSystem.IdeActions -import com.intellij.openapi.editor.Editor -import com.intellij.openapi.editor.actionSystem.EditorActionHandler -import com.intellij.openapi.editor.actionSystem.EditorActionManager import com.intellij.testFramework.fixtures.LightCodeInsightFixtureTestCase import org.jetbrains.plugins.groovy.util.TestUtils - /** * @author peter */ @@ -117,6 +111,22 @@ this.allOptions = [:]; ''') } + public void "test hippie completion in groovydoc"() { + myFixture.configureByText 'a.groovy', ''' +class A { + + /** long + */ + void longName() {} + void example() {} +} +''' + performEditorAction(IdeActions.ACTION_HIPPIE_COMPLETION) + assert myFixture.editor.document.text.contains('** longName\n') + performEditorAction(IdeActions.ACTION_HIPPIE_COMPLETION) + assert myFixture.editor.document.text.contains('** longName\n') + } + void testSWforMemberWithDoc() { doTestForSelectWord(4, '''\ class A { @@ -159,9 +169,7 @@ class A { } private void performEditorAction(final String actionId) { - final EditorActionHandler handler = EditorActionManager.instance.getActionHandler(actionId); - final Editor editor = myFixture.editor; - handler.execute(editor, DataManager.instance.getDataContext(editor.contentComponent)); + myFixture.performEditorAction(actionId) } } diff --git a/plugins/hg4idea/src/org/zmlx/hg4idea/HgVcs.java b/plugins/hg4idea/src/org/zmlx/hg4idea/HgVcs.java index 02655cffa3ae..9c496969a3bb 100644 --- a/plugins/hg4idea/src/org/zmlx/hg4idea/HgVcs.java +++ b/plugins/hg4idea/src/org/zmlx/hg4idea/HgVcs.java @@ -53,6 +53,7 @@ import org.jetbrains.annotations.Nullable; import org.zmlx.hg4idea.provider.*; import org.zmlx.hg4idea.provider.annotate.HgAnnotationProvider; import org.zmlx.hg4idea.provider.commit.HgCheckinEnvironment; +import org.zmlx.hg4idea.provider.commit.HgCloseBranchExecutor; import org.zmlx.hg4idea.provider.commit.HgCommitAndPushExecutor; import org.zmlx.hg4idea.provider.update.HgUpdateEnvironment; import org.zmlx.hg4idea.roots.HgIntegrationEnabler; @@ -104,7 +105,8 @@ public class HgVcs extends AbstractVcs { private HgExecutableValidator myExecutableValidator; private final Object myExecutableValidatorLock = new Object(); private File myPromptHooksExtensionFile; - private CommitExecutor myCommitAndPushExecutor; + private final CommitExecutor myCommitAndPushExecutor; + private final HgCloseBranchExecutor myCloseBranchExecutor; private HgRemoteStatusUpdater myHgRemoteStatusUpdater; private HgStatusWidget myStatusWidget; @@ -130,6 +132,7 @@ public class HgVcs extends AbstractVcs { committedChangesProvider = new HgCachingCommittedChangesProvider(project, this); myMergeProvider = new HgMergeProvider(myProject); myCommitAndPushExecutor = new HgCommitAndPushExecutor(checkinEnvironment); + myCloseBranchExecutor = new HgCloseBranchExecutor(checkinEnvironment); } public String getDisplayName() { @@ -396,6 +399,11 @@ public class HgVcs extends AbstractVcs { return Collections.singletonList(myCommitAndPushExecutor); } + @NotNull + public HgCloseBranchExecutor getCloseBranchExecutor() { + return myCloseBranchExecutor; + } + public static VcsKey getKey() { return ourKey; } @@ -468,13 +476,11 @@ public class HgVcs extends AbstractVcs { final String reason = (e.getCause() != null ? e.getCause() : e).getMessage(); String message = HgVcsMessages.message("hg4idea.unable.to.run.hg", executable); vcsNotifier.notifyError(message, - String.format( - reason + - "
Please check your hg executable path in settings " - ), - linkAdapter + reason + + "
Please check your hg executable path in settings ", + linkAdapter ); } } diff --git a/plugins/hg4idea/src/org/zmlx/hg4idea/branch/HgBranchPopup.java b/plugins/hg4idea/src/org/zmlx/hg4idea/branch/HgBranchPopup.java index 3dcaf6dee161..dc73c36ee503 100644 --- a/plugins/hg4idea/src/org/zmlx/hg4idea/branch/HgBranchPopup.java +++ b/plugins/hg4idea/src/org/zmlx/hg4idea/branch/HgBranchPopup.java @@ -81,6 +81,7 @@ public class HgBranchPopup extends DvcsBranchPopup { List allRepositories = repositoryManager.getRepositories(); popupGroup.add(new HgBranchPopupActions.HgNewBranchAction(myProject, allRepositories, myCurrentRepository)); popupGroup.addAction(new HgBranchPopupActions.HgNewBookmarkAction(allRepositories, myCurrentRepository)); + popupGroup.addAction(new HgBranchPopupActions.HgCloseBranchAction(allRepositories, myCurrentRepository)); popupGroup.addAction(new HgBranchPopupActions.HgShowUnnamedHeadsForCurrentBranchAction(myCurrentRepository)); popupGroup.addAll(createRepositoriesActions()); diff --git a/plugins/hg4idea/src/org/zmlx/hg4idea/branch/HgBranchPopupActions.java b/plugins/hg4idea/src/org/zmlx/hg4idea/branch/HgBranchPopupActions.java index 633fe1cf87d9..9de49d560b65 100644 --- a/plugins/hg4idea/src/org/zmlx/hg4idea/branch/HgBranchPopupActions.java +++ b/plugins/hg4idea/src/org/zmlx/hg4idea/branch/HgBranchPopupActions.java @@ -23,9 +23,15 @@ import com.intellij.openapi.actionSystem.ActionGroup; import com.intellij.openapi.actionSystem.AnAction; import com.intellij.openapi.actionSystem.AnActionEvent; import com.intellij.openapi.actionSystem.DefaultActionGroup; +import com.intellij.openapi.application.ApplicationManager; +import com.intellij.openapi.application.ModalityState; import com.intellij.openapi.project.DumbAwareAction; import com.intellij.openapi.project.Project; +import com.intellij.openapi.util.Condition; import com.intellij.openapi.util.text.StringUtil; +import com.intellij.openapi.vcs.VcsBundle; +import com.intellij.openapi.vcs.changes.*; +import com.intellij.openapi.vcs.changes.ui.CommitChangeListDialog; import com.intellij.util.ArrayUtil; import com.intellij.util.Function; import com.intellij.util.PlatformIcons; @@ -35,15 +41,19 @@ import com.intellij.vcs.log.impl.HashImpl; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; import org.zmlx.hg4idea.HgNameWithHashInfo; +import org.zmlx.hg4idea.HgVcs; import org.zmlx.hg4idea.action.HgCommandResultNotifier; import org.zmlx.hg4idea.command.HgBookmarkCommand; import org.zmlx.hg4idea.command.HgBranchCreateCommand; import org.zmlx.hg4idea.execution.HgCommandException; import org.zmlx.hg4idea.execution.HgCommandResult; import org.zmlx.hg4idea.execution.HgCommandResultHandler; +import org.zmlx.hg4idea.provider.commit.HgCloseBranchExecutor; import org.zmlx.hg4idea.repo.HgRepository; +import org.zmlx.hg4idea.repo.HgRepositoryManager; import org.zmlx.hg4idea.ui.HgBookmarkDialog; import org.zmlx.hg4idea.util.HgErrorUtil; +import org.zmlx.hg4idea.util.HgUtil; import java.util.*; @@ -64,6 +74,7 @@ public class HgBranchPopupActions { DefaultActionGroup popupGroup = new DefaultActionGroup(null, false); popupGroup.addAction(new HgNewBranchAction(myProject, Collections.singletonList(myRepository), myRepository)); popupGroup.addAction(new HgNewBookmarkAction(Collections.singletonList(myRepository), myRepository)); + popupGroup.addAction(new HgBranchPopupActions.HgCloseBranchAction(Collections.singletonList(myRepository), myRepository)); popupGroup.addAction(new HgShowUnnamedHeadsForCurrentBranchAction(myRepository)); if (toInsert != null) { popupGroup.addAll(toInsert); @@ -129,6 +140,60 @@ public class HgBranchPopupActions { } } + public static class HgCloseBranchAction extends DumbAwareAction { + @NotNull private final List myRepositories; + @NotNull final HgRepository myPreselectedRepo; + + HgCloseBranchAction(@NotNull List repositories, @NotNull HgRepository preselectedRepo) { + super("Close " + StringUtil.pluralize("branch", repositories.size()), + "Close current " + StringUtil.pluralize("branch", repositories.size()), AllIcons.Actions.Delete); + myRepositories = repositories; + myPreselectedRepo = preselectedRepo; + } + + @Override + public void actionPerformed(AnActionEvent e) { + final Project project = myPreselectedRepo.getProject(); + ApplicationManager.getApplication().saveAll(); + ChangeListManager.getInstance(project).invokeAfterUpdate(new Runnable() { + @Override + public void run() { + commitAndCloseBranch(project); + } + }, InvokeAfterUpdateMode.SYNCHRONOUS_CANCELLABLE, VcsBundle + .message("waiting.changelists.update.for.show.commit.dialog.message"), + ModalityState.current()); + } + + private void commitAndCloseBranch(@NotNull final Project project) { + final LocalChangeList activeChangeList = ChangeListManager.getInstance(project).getDefaultChangeList(); + HgVcs vcs = HgVcs.getInstance(project); + assert vcs != null; + final HgRepositoryManager repositoryManager = HgUtil.getRepositoryManager(project); + List changesForRepositories = ContainerUtil.filter(activeChangeList.getChanges(), new Condition() { + @Override + public boolean value(Change change) { + return myRepositories.contains(repositoryManager.getRepositoryForFile(ChangesUtil.getFilePath(change))); + } + }); + HgCloseBranchExecutor closeBranchExecutor = vcs.getCloseBranchExecutor(); + closeBranchExecutor.setRepositories(myRepositories); + CommitChangeListDialog.commitChanges(project, changesForRepositories, activeChangeList, + Collections.singletonList(closeBranchExecutor), + false, vcs, "Close Branch", null, false); + } + + @Override + public void update(AnActionEvent e) { + e.getPresentation().setEnabledAndVisible(ContainerUtil.and(myRepositories, new Condition() { + @Override + public boolean value(HgRepository repository) { + return repository.getOpenedBranches().contains(repository.getCurrentBranch()); + } + })); + } + } + public static class HgNewBookmarkAction extends DumbAwareAction { @NotNull protected final List myRepositories; @NotNull final HgRepository myPreselectedRepo; diff --git a/plugins/hg4idea/src/org/zmlx/hg4idea/command/HgCommitCommand.java b/plugins/hg4idea/src/org/zmlx/hg4idea/command/HgCommitCommand.java index 794c7096d207..4ba12ee4add0 100644 --- a/plugins/hg4idea/src/org/zmlx/hg4idea/command/HgCommitCommand.java +++ b/plugins/hg4idea/src/org/zmlx/hg4idea/command/HgCommitCommand.java @@ -12,6 +12,7 @@ // limitations under the License. package org.zmlx.hg4idea.command; +import com.intellij.dvcs.repo.Repository; import com.intellij.openapi.application.PathManager; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.io.FileUtil; @@ -28,6 +29,7 @@ import org.zmlx.hg4idea.HgVcs; import org.zmlx.hg4idea.HgVcsMessages; import org.zmlx.hg4idea.execution.HgCommandException; import org.zmlx.hg4idea.execution.HgCommandExecutor; +import org.zmlx.hg4idea.repo.HgRepository; import org.zmlx.hg4idea.repo.HgRepositoryManager; import org.zmlx.hg4idea.util.HgEncodingUtil; import org.zmlx.hg4idea.util.HgUtil; @@ -51,16 +53,22 @@ public class HgCommitCommand { private final String myMessage; @NotNull private final Charset myCharset; private final boolean myAmend; + private final boolean myCloseBranch; private Set myFiles = Collections.emptySet(); @NotNull private List mySubrepos = Collections.emptyList(); - public HgCommitCommand(Project project, @NotNull VirtualFile root, String message, boolean amend) { + public HgCommitCommand(@NotNull Project project, @NotNull VirtualFile root, String message, boolean amend, boolean closeBranch) { myProject = project; myRoot = root; myMessage = message; myCharset = HgEncodingUtil.getDefaultCharset(myProject); myAmend = amend; + myCloseBranch = closeBranch; + } + + public HgCommitCommand(@NotNull Project project, @NotNull VirtualFile root, String message, boolean amend) { + this(project, root, message, amend, false); } public HgCommitCommand(Project project, @NotNull VirtualFile root, String message) { @@ -80,9 +88,9 @@ public class HgCommitCommand { throw new HgCommandException(HgVcsMessages.message("hg4idea.commit.error.messageEmpty")); } //if it's merge commit, so myFiles is Empty. Need to commit all files in changeList. - // see HgCheckinEnviroment->commit() method + // see HgCheckinEnvironment->commit() method if (myFiles.isEmpty()) { - commitChunkFiles(Collections.emptyList(), myAmend); + commitChunkFiles(Collections.emptyList(), myAmend, myCloseBranch); } else { List relativePaths = ContainerUtil.map2List(myFiles, new Function() { @@ -94,12 +102,12 @@ public class HgCommitCommand { List> chunkedCommits = VcsFileUtil.chunkRelativePaths(relativePaths); int size = chunkedCommits.size(); // commit with subrepo should be first, because it's not possible to amend with --subrepos argument; - commitChunkFiles(chunkedCommits.get(0), myAmend, !mySubrepos.isEmpty()); + commitChunkFiles(chunkedCommits.get(0), myAmend, !mySubrepos.isEmpty(), myCloseBranch && size == 1); HgVcs vcs = HgVcs.getInstance(myProject); boolean amendCommit = vcs != null && vcs.getVersion().isAmendSupported(); for (int i = 1; i < size; i++) { List chunk = chunkedCommits.get(i); - commitChunkFiles(chunk, amendCommit); + commitChunkFiles(chunk, amendCommit, false, myCloseBranch && i == size - 1); } } if (!myProject.isDisposed()) { @@ -111,11 +119,14 @@ public class HgCommitCommand { messageBus.syncPublisher(HgVcs.BRANCH_TOPIC).update(myProject, null); } - private void commitChunkFiles(@NotNull List chunk, boolean amendCommit) throws VcsException { - commitChunkFiles(chunk, amendCommit, false); + private void commitChunkFiles(@NotNull List chunk, boolean amendCommit, boolean closeBranch) throws VcsException { + commitChunkFiles(chunk, amendCommit, false, closeBranch); } - private void commitChunkFiles(@NotNull List chunk, boolean amendCommit, boolean withSubrepos) throws VcsException { + private void commitChunkFiles(@NotNull List chunk, boolean amendCommit, boolean withSubrepos, boolean closeBranch) + throws VcsException { + HgRepository repository = HgUtil.getRepositoryForFile(myProject, myRoot); + assert repository != null; List parameters = new LinkedList(); parameters.add("--logfile"); parameters.add(saveCommitMessage().getAbsolutePath()); @@ -127,6 +138,14 @@ public class HgCommitCommand { else if (amendCommit) { parameters.add("--amend"); } + if (closeBranch) { + if (chunk.isEmpty() && repository.getState() != Repository.State.MERGING) { + //if there are changed files but nothing selected -> need to exclude all; if merge commit then nothing excluded + parameters.add("-X"); + parameters.add("\"**\""); + } + parameters.add("--close-branch"); + } parameters.addAll(chunk); HgCommandExecutor executor = new HgCommandExecutor(myProject); executor.setCharset(myCharset); diff --git a/plugins/hg4idea/src/org/zmlx/hg4idea/command/HgUpdateCommand.java b/plugins/hg4idea/src/org/zmlx/hg4idea/command/HgUpdateCommand.java index 4cfe72f121f9..f64b923959bb 100644 --- a/plugins/hg4idea/src/org/zmlx/hg4idea/command/HgUpdateCommand.java +++ b/plugins/hg4idea/src/org/zmlx/hg4idea/command/HgUpdateCommand.java @@ -103,7 +103,6 @@ public class HgUpdateCommand { DvcsUtil.workingTreeChangeFinished(project, token); } - project.getMessageBus().syncPublisher(HgVcs.BRANCH_TOPIC).update(project, null); VfsUtil.markDirtyAndRefresh(true, true, false, repo); return result; } @@ -120,28 +119,28 @@ public class HgUpdateCommand { return exitCode.get(); } - public static void updateTo(@NotNull final String taskName, @NotNull List repos, @Nullable final Runnable callInAwtLater) { + public static void updateTo(@NotNull final String targetRevision, @NotNull List repos, @Nullable final Runnable callInAwtLater) { FileDocumentManager.getInstance().saveAllDocuments(); for (HgRepository repo : repos) { final VirtualFile repository = repo.getRoot(); Project project = repo.getProject(); - updateRepoTo(project, repository, taskName, callInAwtLater); + updateRepoTo(project, repository, targetRevision, callInAwtLater); } } public static void updateRepoTo(@NotNull final Project project, @NotNull final VirtualFile repository, - @NotNull final String taskName, + @NotNull final String targetRevision, @Nullable final Runnable callInAwtLater) { - updateRepoTo(project, repository, taskName, false, callInAwtLater); + updateRepoTo(project, repository, targetRevision, false, callInAwtLater); } public static void updateRepoTo(@NotNull final Project project, @NotNull final VirtualFile repository, - @NotNull final String taskName, + @NotNull final String targetRevision, final boolean clean, @Nullable final Runnable callInAwtLater) { - new Task.Backgroundable(project, HgVcsMessages.message("action.hg4idea.updateTo.description", taskName)) { + new Task.Backgroundable(project, HgVcsMessages.message("action.hg4idea.updateTo.description", targetRevision)) { @Override public void onSuccess() { if (callInAwtLater != null) { @@ -151,17 +150,17 @@ public class HgUpdateCommand { @Override public void run(@NotNull ProgressIndicator indicator) { - updateRepoToInCurrentThread(project, repository, taskName, clean); + updateRepoToInCurrentThread(project, repository, targetRevision, clean); } }.queue(); } public static boolean updateRepoToInCurrentThread(@NotNull final Project project, @NotNull final VirtualFile repository, - @NotNull final String taskName, + @NotNull final String targetRevision, final boolean clean) { final HgUpdateCommand hgUpdateCommand = new HgUpdateCommand(project, repository); - hgUpdateCommand.setRevision(taskName); + hgUpdateCommand.setRevision(targetRevision); hgUpdateCommand.setClean(clean); HgCommandResult result = hgUpdateCommand.execute(); new HgConflictResolver(project).resolve(repository); diff --git a/plugins/hg4idea/src/org/zmlx/hg4idea/provider/commit/HgCheckinEnvironment.java b/plugins/hg4idea/src/org/zmlx/hg4idea/provider/commit/HgCheckinEnvironment.java index cd46452f96f1..fe13294ef8ab 100644 --- a/plugins/hg4idea/src/org/zmlx/hg4idea/provider/commit/HgCheckinEnvironment.java +++ b/plugins/hg4idea/src/org/zmlx/hg4idea/provider/commit/HgCheckinEnvironment.java @@ -60,6 +60,8 @@ public class HgCheckinEnvironment implements CheckinEnvironment { private boolean myNextCommitIsPushed; private boolean myNextCommitAmend; // If true, the next commit is amended private boolean myShouldCommitSubrepos; + private boolean myCloseBranch; + @Nullable private Collection myRepos; public HgCheckinEnvironment(Project project) { myProject = project; @@ -67,8 +69,15 @@ public class HgCheckinEnvironment implements CheckinEnvironment { public RefreshableOnComponent createAdditionalOptionsPanel(CheckinProjectPanel panel, PairConsumer additionalDataConsumer) { + reset(); + return new HgCommitAdditionalComponent(myProject, panel); + } + + public void reset() { myNextCommitIsPushed = false; - return new HgCommitAdditionalComponent(myProject,panel); + myShouldCommitSubrepos = false; + myCloseBranch = false; + myRepos = null; } public String getDefaultMessageFor(FilePath[] filesToCheckin) { @@ -83,19 +92,19 @@ public class HgCheckinEnvironment implements CheckinEnvironment { return HgVcsMessages.message("hg4idea.commit"); } - @SuppressWarnings({"ThrowableInstanceNeverThrown"}) public List commit(List changes, String preparedComment, @NotNull NullableFunction parametersHolder, Set feedback) { List exceptions = new LinkedList(); Map> repositoriesMap = getFilesByRepository(changes); + addRepositoriesWithoutChanges(repositoriesMap); for (Map.Entry> entry : repositoriesMap.entrySet()) { HgRepository repo = entry.getKey(); Set selectedFiles = entry.getValue(); HgCommitCommand command = - new HgCommitCommand(myProject, repo.getRoot(), preparedComment, myNextCommitAmend); + new HgCommitCommand(myProject, repo.getRoot(), preparedComment, myNextCommitAmend, myCloseBranch); if (isMergeCommit(repo.getRoot())) { //partial commits are not allowed during merges @@ -255,7 +264,7 @@ public class HgCheckinEnvironment implements CheckinEnvironment { private void addFile(Map> result, ContentRevision contentRevision) { FilePath filePath = contentRevision.getFile(); - // try to find repository from hgFile from change + // try to find repository from hgFile from change: to be able commit sub repositories as expected HgRepository repo = HgUtil.getRepositoryForFile(myProject, contentRevision instanceof HgCurrentBinaryContentRevision ? ((HgCurrentBinaryContentRevision)contentRevision).getRepositoryRoot() : ChangesUtil.findValidParentAccurately(filePath)); @@ -276,6 +285,23 @@ public class HgCheckinEnvironment implements CheckinEnvironment { myNextCommitIsPushed = true; } + public void setCloseBranch(boolean closeBranch) { + myCloseBranch = closeBranch; + } + + public void setRepos(@NotNull Collection repos) { + myRepos = repos; + } + + private void addRepositoriesWithoutChanges(@NotNull Map> repositoryMap) { + if (myRepos == null) return; + for (HgRepository repository : myRepos) { + if (!repositoryMap.keySet().contains(repository)) { + repositoryMap.put(repository, Collections.emptySet()); + } + } + } + /** * Commit options for hg */ diff --git a/plugins/hg4idea/src/org/zmlx/hg4idea/provider/commit/HgCloseBranchExecutor.java b/plugins/hg4idea/src/org/zmlx/hg4idea/provider/commit/HgCloseBranchExecutor.java new file mode 100644 index 000000000000..3aac41d2b394 --- /dev/null +++ b/plugins/hg4idea/src/org/zmlx/hg4idea/provider/commit/HgCloseBranchExecutor.java @@ -0,0 +1,57 @@ +/* + * 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 org.zmlx.hg4idea.provider.commit; + +import com.intellij.openapi.vcs.changes.CommitExecutorBase; +import com.intellij.openapi.vcs.changes.CommitSession; +import org.jetbrains.annotations.Nls; +import org.jetbrains.annotations.NotNull; +import org.zmlx.hg4idea.repo.HgRepository; + +import java.util.Collection; + +public class HgCloseBranchExecutor extends CommitExecutorBase { + + @NotNull private final HgCheckinEnvironment myCheckinEnvironment; + @NotNull private static final String CLOSE_BRANCH_TITLE = "Commit And &Close" ; + + + public HgCloseBranchExecutor(@NotNull HgCheckinEnvironment environment) { + myCheckinEnvironment = environment; + } + + @Override + public boolean areChangesRequired() { + return false; + } + + @Nls + @Override + public String getActionText() { + return CLOSE_BRANCH_TITLE; + } + + @NotNull + @Override + public CommitSession createCommitSession() { + myCheckinEnvironment.setCloseBranch(true); + return CommitSession.VCS_COMMIT; + } + + public void setRepositories(@NotNull Collection repositories) { + myCheckinEnvironment.setRepos(repositories); + } +} diff --git a/plugins/hg4idea/testSrc/org/zmlx/hg4idea/test/HgTest.java b/plugins/hg4idea/testSrc/org/zmlx/hg4idea/test/HgTest.java index 43bb2121a9c9..007bc9ad8bc4 100644 --- a/plugins/hg4idea/testSrc/org/zmlx/hg4idea/test/HgTest.java +++ b/plugins/hg4idea/testSrc/org/zmlx/hg4idea/test/HgTest.java @@ -111,11 +111,6 @@ public abstract class HgTest extends AbstractVcsTestCase { }); } - @Override - protected String getPluginName() { - return "hg4idea"; - } - protected abstract HgTestRepository initRepositories() throws Exception; protected abstract void tearDownRepositories() throws Exception; diff --git a/plugins/java-i18n/src/com/intellij/psi/impl/source/resolve/reference/impl/providers/JavaReferenceContributor.java b/plugins/java-i18n/src/com/intellij/psi/impl/source/resolve/reference/impl/providers/JavaReferenceContributor.java index b38f94079933..1a0fe723e3e5 100644 --- a/plugins/java-i18n/src/com/intellij/psi/impl/source/resolve/reference/impl/providers/JavaReferenceContributor.java +++ b/plugins/java-i18n/src/com/intellij/psi/impl/source/resolve/reference/impl/providers/JavaReferenceContributor.java @@ -16,11 +16,13 @@ package com.intellij.psi.impl.source.resolve.reference.impl.providers; import com.intellij.codeInsight.AnnotationUtil; +import com.intellij.codeInsight.documentation.ArbitraryPlaceUrlReferenceProvider; import com.intellij.codeInspection.i18n.JavaI18nUtil; import com.intellij.patterns.PlatformPatterns; import com.intellij.psi.*; import com.intellij.psi.filters.ElementFilter; import com.intellij.psi.filters.position.FilterPattern; +import com.intellij.psi.javadoc.PsiDocToken; import org.jetbrains.annotations.NotNull; import java.util.HashMap; @@ -52,5 +54,8 @@ public class JavaReferenceContributor extends PsiReferenceContributor{ return true; } })), filePathReferenceProvider); + registrar.registerReferenceProvider(PlatformPatterns.psiElement(PsiDocToken.class), ArbitraryPlaceUrlReferenceProvider.INSTANCE); + // todo register for all ? + registrar.registerReferenceProvider(PlatformPatterns.psiElement(PsiComment.class), ArbitraryPlaceUrlReferenceProvider.INSTANCE); } } diff --git a/plugins/junit/src/fileTemplates/code/JUnit3 SetUp Method.java.html b/plugins/junit/src/fileTemplates/code/JUnit3 SetUp Method.java.html index a22b80b884f3..d41bedc88e66 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit3 SetUp Method.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit3 SetUp Method.java.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/junit/src/fileTemplates/code/JUnit3 TearDown Method.java.html b/plugins/junit/src/fileTemplates/code/JUnit3 TearDown Method.java.html index da1d3ae9ce26..a20a8a351f81 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit3 TearDown Method.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit3 TearDown Method.java.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/junit/src/fileTemplates/code/JUnit3 Test Class.java.html b/plugins/junit/src/fileTemplates/code/JUnit3 Test Class.java.html index 845e8be9069f..a015267dedfd 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit3 Test Class.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit3 Test Class.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created class. - ${BODY} + ${BODY}   generated class body. diff --git a/plugins/junit/src/fileTemplates/code/JUnit3 Test Method.java.html b/plugins/junit/src/fileTemplates/code/JUnit3 Test Method.java.html index b718403b4417..738f32f0401f 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit3 Test Method.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit3 Test Method.java.html @@ -13,12 +13,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/junit/src/fileTemplates/code/JUnit4 Parameters Method.java.html b/plugins/junit/src/fileTemplates/code/JUnit4 Parameters Method.java.html index 51fd9c2f15ef..7844aa2260b0 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit4 Parameters Method.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit4 Parameters Method.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/junit/src/fileTemplates/code/JUnit4 SetUp Method.java.html b/plugins/junit/src/fileTemplates/code/JUnit4 SetUp Method.java.html index e700267e9aa3..b48a5a892f58 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit4 SetUp Method.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit4 SetUp Method.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/junit/src/fileTemplates/code/JUnit4 TearDown Method.java.html b/plugins/junit/src/fileTemplates/code/JUnit4 TearDown Method.java.html index 5a419263f69a..199a4ec1e722 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit4 TearDown Method.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit4 TearDown Method.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/junit/src/fileTemplates/code/JUnit4 Test Class.java.html b/plugins/junit/src/fileTemplates/code/JUnit4 Test Class.java.html index 7a1542436cf2..c2ff42e4777c 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit4 Test Class.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit4 Test Class.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created class. - ${BODY} + ${BODY}   generated class body. diff --git a/plugins/junit/src/fileTemplates/code/JUnit4 Test Method.java.html b/plugins/junit/src/fileTemplates/code/JUnit4 Test Method.java.html index 7a04a90e35cd..1b7bde93b677 100644 --- a/plugins/junit/src/fileTemplates/code/JUnit4 Test Method.java.html +++ b/plugins/junit/src/fileTemplates/code/JUnit4 Test Method.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/maven/src/test/java/org/jetbrains/idea/maven/MavenImportingTestCase.java b/plugins/maven/src/test/java/org/jetbrains/idea/maven/MavenImportingTestCase.java index abf2d4b9c243..0b769d2774b3 100644 --- a/plugins/maven/src/test/java/org/jetbrains/idea/maven/MavenImportingTestCase.java +++ b/plugins/maven/src/test/java/org/jetbrains/idea/maven/MavenImportingTestCase.java @@ -19,6 +19,7 @@ package org.jetbrains.idea.maven; import com.intellij.compiler.server.BuildManager; import com.intellij.openapi.application.AccessToken; import com.intellij.openapi.application.ApplicationManager; +import com.intellij.openapi.application.PathManager; import com.intellij.openapi.module.Module; import com.intellij.openapi.module.ModuleManager; import com.intellij.openapi.progress.EmptyProgressIndicator; @@ -69,6 +70,7 @@ public abstract class MavenImportingTestCase extends MavenTestCase { if (myGlobalSettingsFile != null) { VfsRootAccess.allowRootAccess(myGlobalSettingsFile.getAbsolutePath()); } + VfsRootAccess.allowRootAccess(PathManager.getOptionsPath()); } @Override @@ -84,6 +86,7 @@ public abstract class MavenImportingTestCase extends MavenTestCase { if (myGlobalSettingsFile != null) { VfsRootAccess.disallowRootAccess(myGlobalSettingsFile.getAbsolutePath()); } + VfsRootAccess.allowRootAccess(PathManager.getOptionsPath()); Messages.setTestDialog(TestDialog.DEFAULT); myProjectsManager.projectClosed(); removeFromLocalRepository("test"); diff --git a/plugins/svn4idea/testSource/org/jetbrains/idea/SvnTestCase.java b/plugins/svn4idea/testSource/org/jetbrains/idea/SvnTestCase.java index 393995a29da8..3ab15eb94e98 100644 --- a/plugins/svn4idea/testSource/org/jetbrains/idea/SvnTestCase.java +++ b/plugins/svn4idea/testSource/org/jetbrains/idea/SvnTestCase.java @@ -113,11 +113,6 @@ public abstract class SvnTestCase extends AbstractJunitVcsTestCase { listener.after(events); } - @Override - protected String getPluginName() { - return "Subversion"; - } - @Before public void setUp() throws Exception { System.out.println("Native client for status: " + isUseNativeAcceleration()); diff --git a/plugins/terminal/resources/icons/OpenTerminal_13x13@2x_dark.png b/plugins/terminal/resources/icons/OpenTerminal_13x13@2x_dark.png index 382b1e728685..3abc58e0740d 100644 Binary files a/plugins/terminal/resources/icons/OpenTerminal_13x13@2x_dark.png and b/plugins/terminal/resources/icons/OpenTerminal_13x13@2x_dark.png differ diff --git a/plugins/terminal/resources/icons/OpenTerminal_13x13_dark.png b/plugins/terminal/resources/icons/OpenTerminal_13x13_dark.png index d9ceedc74ae0..1a08ae5a7778 100644 Binary files a/plugins/terminal/resources/icons/OpenTerminal_13x13_dark.png and b/plugins/terminal/resources/icons/OpenTerminal_13x13_dark.png differ diff --git a/plugins/testng/src/fileTemplates/code/TestNG Parameters Method.java.html b/plugins/testng/src/fileTemplates/code/TestNG Parameters Method.java.html index f6084e6774bb..da1766197222 100644 --- a/plugins/testng/src/fileTemplates/code/TestNG Parameters Method.java.html +++ b/plugins/testng/src/fileTemplates/code/TestNG Parameters Method.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/testng/src/fileTemplates/code/TestNG SetUp Method.java.html b/plugins/testng/src/fileTemplates/code/TestNG SetUp Method.java.html index 7f8b8e648874..9736ca8b96e1 100644 --- a/plugins/testng/src/fileTemplates/code/TestNG SetUp Method.java.html +++ b/plugins/testng/src/fileTemplates/code/TestNG SetUp Method.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/testng/src/fileTemplates/code/TestNG TearDown Method.java.html b/plugins/testng/src/fileTemplates/code/TestNG TearDown Method.java.html index 8c6e6d6685d5..f7f3b58393d1 100644 --- a/plugins/testng/src/fileTemplates/code/TestNG TearDown Method.java.html +++ b/plugins/testng/src/fileTemplates/code/TestNG TearDown Method.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/plugins/testng/src/fileTemplates/code/TestNG Test Class.java.html b/plugins/testng/src/fileTemplates/code/TestNG Test Class.java.html index 972b59a13ae8..5b04f0197f7a 100644 --- a/plugins/testng/src/fileTemplates/code/TestNG Test Class.java.html +++ b/plugins/testng/src/fileTemplates/code/TestNG Test Class.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created class. - ${BODY} + ${BODY}   generated class body. diff --git a/plugins/testng/src/fileTemplates/code/TestNG Test Method.java.html b/plugins/testng/src/fileTemplates/code/TestNG Test Method.java.html index b86268203ed8..81b82b324de1 100644 --- a/plugins/testng/src/fileTemplates/code/TestNG Test Method.java.html +++ b/plugins/testng/src/fileTemplates/code/TestNG Test Method.java.html @@ -12,12 +12,12 @@ Predefined variables will take the following values: - ${NAME} + ${NAME}   name of the created method. - ${BODY} + ${BODY}   generated method body. diff --git a/python/edu/build/idea.nsi b/python/edu/build/idea.nsi index 688d9bc40aaf..ffdc1ead3a51 100644 --- a/python/edu/build/idea.nsi +++ b/python/edu/build/idea.nsi @@ -347,7 +347,7 @@ FunctionEnd !insertmacro MUI_PAGE_WELCOME Page custom uninstallOldVersionDialog - +Var productDir Var control_fields Var max_fields @@ -686,7 +686,25 @@ skip_default_instdir: FunctionEnd -Function DoAssociation +Function ProductRegistration + StrCmp "${PRODUCT_WITH_VER}" "${MUI_PRODUCT} ${VER_BUILD}" eapInfo releaseInfo +eapInfo: + StrCpy $3 "${PRODUCT_WITH_VER}(EAP)" + goto createRegistration +releaseInfo: + StrCpy $3 "${PRODUCT_WITH_VER}" +createRegistration: + StrCpy $0 "HKCR" + StrCpy $1 "Applications\${PRODUCT_EXE_FILE}\shell\open" + StrCpy $2 "FriendlyAppName" + call OMWriteRegStr + StrCpy $1 "Applications\${PRODUCT_EXE_FILE}\shell\open\command" + StrCpy $2 "" + StrCpy $3 '$INSTDIR\bin\${PRODUCT_EXE_FILE} "%1"' + call OMWriteRegStr +FunctionEnd + +Function ProductAssociation ; back up old value of an association ReadRegStr $1 HKCR $R4 "" StrCmp $1 "" skip_backup @@ -816,12 +834,16 @@ get_user_choice: !insertmacro INSTALLOPTIONS_READ $R3 "Desktop.ini" "Field $R2" "State" StrCmp $R3 1 "" next_association !insertmacro INSTALLOPTIONS_READ $R4 "Desktop.ini" "Field $R2" "Text" - call DoAssociation + call ProductAssociation next_association: IntOp $R2 $R2 + 1 IntCmp $R1 $R2 get_user_choice done get_user_choice -done: +done: + ;registration application to be presented in Open With list + call ProductRegistration + ;reset icon cache + System::Call 'shell32.dll::SHChangeNotify(i, i, i, i) v (0x08000000, 0, 0, 0)' !insertmacro MUI_STARTMENU_WRITE_BEGIN Application ; $STARTMENU_FOLDER stores name of IDEA folder in Start Menu, ; save it name in the "MenuFolder" RegValue @@ -852,8 +874,8 @@ done: StrCmp $0 "" 0 "${Index}-Skip" WriteRegStr HKCR "IntelliJIdeaProjectFile" "" "IntelliJ IDEA Project File" WriteRegStr HKCR "IntelliJIdeaProjectFile\shell" "" "open" - WriteRegStr HKCR "IntelliJIdeaProjectFile\DefaultIcon" "" "$INSTDIR\bin\idea.exe,0" "${Index}-Skip:" + WriteRegStr HKCR "IntelliJIdeaProjectFile\DefaultIcon" "" "$INSTDIR\bin\${PRODUCT_EXE_FILE},0" WriteRegStr HKCR "IntelliJIdeaProjectFile\shell\open\command" "" \ '$INSTDIR\bin\${PRODUCT_EXE_FILE} "%1"' !undef Index @@ -1004,6 +1026,7 @@ FunctionEnd ;------------------------------------------------------------------------------ Function un.onInit + StrCpy $baseRegKey "HKCU" ;admin perm. is required to uninstall? ${UnStrStr} $R0 $INSTDIR $PROGRAMFILES StrCmp $R0 $INSTDIR requred_admin_perm UAC_Done @@ -1046,33 +1069,6 @@ UAC_Done: !insertmacro INSTALLOPTIONS_EXTRACT "DeleteSettings.ini" FunctionEnd -Function OMEnumRegKey - StrCmp $0 "HKCU" hkcu - EnumRegKey $3 HKLM $1 $4 - goto done -hkcu: - EnumRegKey $3 HKCU $1 $4 -done: -FunctionEnd - -Function un.OMReadRegStr - StrCmp $0 "HKCU" hkcu - ReadRegStr $3 HKLM $1 $2 - goto done -hkcu: - ReadRegStr $3 HKCU $1 $2 -done: -FunctionEnd - -Function un.OMDeleteRegValue - StrCmp $0 "HKCU" hkcu - DeleteRegValue HKLM $1 $2 - goto done -hkcu: - DeleteRegValue HKCU $1 $2 -done: -FunctionEnd - Function un.ReturnBackupRegValue ;replace Default str with the backup value (if there is the one) and then delete backup ; $1 - key (for example ".java") @@ -1086,34 +1082,6 @@ noBackup: Pop $0 FunctionEnd -Function un.OMDeleteRegKeyIfEmpty - StrCmp $0 "HKCU" hkcu - DeleteRegKey /ifempty HKLM $1 - goto done -hkcu: - DeleteRegKey /ifempty HKCU $1 -done: -FunctionEnd - -Function un.OMDeleteRegKey - StrCmp $0 "HKCU" hkcu - DeleteRegKey /ifempty HKLM $1 - goto done -hkcu: - DeleteRegKey /ifempty HKCU $1 -done: -FunctionEnd - -Function un.OMWriteRegStr - StrCmp $0 "HKCU" hkcu - WriteRegStr HKLM $1 $2 $3 - goto done -hkcu: - WriteRegStr HKCU $1 $2 $3 -done: -FunctionEnd - - ;------------------------------------------------------------------------------ ; custom uninstall pages ;------------------------------------------------------------------------------ @@ -1198,6 +1166,7 @@ FunctionEnd Section "Uninstall" + StrCpy $productDir $INSTDIR StrCpy $baseRegKey "HKCU" ; Uninstaller is in the \bin directory, we need upper level dir StrCpy $INSTDIR $INSTDIR\.. @@ -1254,7 +1223,6 @@ skip_delete_settings: StrCmp $R9 "" "" clear_shortcuts ReadRegStr $R9 HKLM "Software\${MANUFACTURER}\${PRODUCT_REG_VER}" "MenuFolder" StrCmp $R9 "" clear_Registry - StrCpy $baseRegKey "HKLM" StrCpy $5 "Software\${MANUFACTURER}" ; call un.winVersion ; ${If} $0 == "1" @@ -1279,10 +1247,10 @@ keep_current_user: clear_Registry: StrCpy $5 "Software\${MANUFACTURER}" -; call un.winVersion -; ${If} $0 == "1" -; StrCpy $5 "Software\Wow6432Node\${MANUFACTURER}" -; ${EndIf} + call un.winVersion + ${If} $0 == "1" + StrCpy $5 "Software\Wow6432Node\${MANUFACTURER}" + ${EndIf} StrCpy $0 $baseRegKey StrCpy $1 "$5\${PRODUCT_REG_VER}" @@ -1300,14 +1268,13 @@ loop: Call un.ReturnBackupRegValue goto loop finish_uninstall: + StrCpy $0 $baseRegKey StrCpy $1 "$5\${PRODUCT_REG_VER}" StrCpy $2 "Build" - Call un.OMDeleteRegValue - StrCpy $2 "" - Call un.OMDeleteRegValue + Call un.OMReadRegStr StrCpy $1 "$5\${PRODUCT_REG_VER}" - Call un.OMDeleteRegKeyIfEmpty + Call un.OMDeleteRegKey StrCpy $1 "$5\${MUI_PRODUCT}" Call un.OMDeleteRegKeyIfEmpty @@ -1315,6 +1282,24 @@ finish_uninstall: StrCpy $1 "$5" Call un.OMDeleteRegKeyIfEmpty + StrCpy $0 "HKCR" + StrCpy $1 "Applications\${PRODUCT_EXE_FILE}" + StrCpy $2 "" + Call un.OMDeleteRegKey + StrCpy $0 "HKCR" + StrCpy $1 "${PRODUCT_PATHS_SELECTOR}" + StrCpy $2 "" + Call un.OMDeleteRegKey + + StrCpy $0 "HKCR" + StrCpy $1 "IntelliJIdeaProjectFile\DefaultIcon" + StrCpy $2 "" + call un.OMReadRegStr + StrCmp $3 "$productDir\${PRODUCT_EXE_FILE},0" remove_IntelliJIdeaProjectFile done +remove_IntelliJIdeaProjectFile: + StrCpy $1 "IntelliJIdeaProjectFile" + Call un.OMDeleteRegKey +done: DeleteRegKey SHCTX "Software\Microsoft\Windows\CurrentVersion\Uninstall\${PRODUCT_WITH_VER}" ; UNCOMMENT THIS IN RELEASE BUILD diff --git a/resources/src/META-INF/IdeaPlugin.xml b/resources/src/META-INF/IdeaPlugin.xml index e4ed2ce70673..d51427bbd001 100644 --- a/resources/src/META-INF/IdeaPlugin.xml +++ b/resources/src/META-INF/IdeaPlugin.xml @@ -1,3 +1,18 @@ + com.intellij IDEA CORE @@ -1506,6 +1521,7 @@ +