Merge branch 'master' of git.labs.intellij.net:idea/community

This commit is contained in:
Aleksey Pivovarov
2013-06-27 15:12:21 +04:00
41 changed files with 465 additions and 280 deletions
+2 -2
View File
@@ -1,8 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<scheme name="Darcula" version="1" parent_scheme="Default">
<option name="LINE_SPACING" value="1.0" />
<option name="EDITOR_FONT_SIZE" value="12" />
<option name="EDITOR_FONT_NAME" value="Menlo" />
<option name="EDITOR_FONT_SIZE" value="12" linux="13"/>
<option name="EDITOR_FONT_NAME" value="Menlo" linux="DejaVu Sans Mono"/>
<colors>
<option name="ADDED_LINES_COLOR" value="295622" />
<option name="ANNOTATIONS_COLOR" value="8b999f" />
@@ -787,6 +787,7 @@ public class CompileDriver {
final NotificationListener hyperlinkHandler = new NotificationListener.Adapter() {
@Override
protected void hyperlinkActivated(@NotNull Notification notification, @NotNull HyperlinkEvent e) {
notification.expire();
if (!myProject.isDisposed()) {
ShowSettingsUtil.getInstance().editConfigurable(myProject, new CompilerConfigurable(myProject));
}
@@ -995,7 +995,7 @@ public class HighlightClassUtil {
if (classReference == null) return;
final PsiClass psiClass = (PsiClass)classReference.resolve();
if (psiClass == null) return;
final MemberChooser<PsiMethodMember> chooser = chooseMethodsToImplement(editor, startElement, psiClass);
final MemberChooser<PsiMethodMember> chooser = chooseMethodsToImplement(editor, startElement, psiClass, false);
if (chooser == null) return;
final List<PsiMethodMember> selectedElements = chooser.getSelectedElements();
@@ -30,16 +30,11 @@ import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.project.Project;
import com.intellij.psi.*;
import com.intellij.psi.infos.CandidateInfo;
import com.intellij.psi.util.PsiUtil;
import com.intellij.util.containers.ContainerUtil;
import net.sf.cglib.core.CollectionUtils;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Iterator;
import java.util.List;
import java.util.*;
public class ImplementMethodsFix extends LocalQuickFixAndIntentionActionOnPsiElement {
public ImplementMethodsFix(PsiElement aClass) {
@@ -77,7 +72,7 @@ public class ImplementMethodsFix extends LocalQuickFixAndIntentionActionOnPsiEle
if (editor == null || !FileModificationService.getInstance().prepareFileForWrite(myPsiElement.getContainingFile())) return;
if (myPsiElement instanceof PsiEnumConstant) {
final MemberChooser<PsiMethodMember> chooser = chooseMethodsToImplement(editor, startElement, ((PsiEnumConstant)myPsiElement).getContainingClass());
final MemberChooser<PsiMethodMember> chooser = chooseMethodsToImplement(editor, startElement, ((PsiEnumConstant)myPsiElement).getContainingClass(), true);
if (chooser == null) return;
final List<PsiMethodMember> selectedElements = chooser.getSelectedElements();
@@ -105,10 +100,14 @@ public class ImplementMethodsFix extends LocalQuickFixAndIntentionActionOnPsiEle
@Nullable
protected static MemberChooser<PsiMethodMember> chooseMethodsToImplement(Editor editor, PsiElement startElement, PsiClass aClass) {
protected static MemberChooser<PsiMethodMember> chooseMethodsToImplement(Editor editor,
PsiElement startElement,
PsiClass aClass,
boolean implemented) {
FeatureUsageTracker.getInstance().triggerFeatureUsed(ProductivityFeatureNames.CODEASSISTS_OVERRIDE_IMPLEMENT);
final Collection<CandidateInfo> overrideImplement = OverrideImplementExploreUtil.getMapToOverrideImplement(aClass, true, implemented).values();
return OverrideImplementUtil
.showOverrideImplementChooser(editor, startElement, true, OverrideImplementExploreUtil.getMethodsToOverrideImplement(aClass, true), ContainerUtil.<CandidateInfo>newArrayList());
.showOverrideImplementChooser(editor, startElement, true, overrideImplement, ContainerUtil.<CandidateInfo>newArrayList());
}
}
@@ -37,7 +37,7 @@ public class GenerateGetterHandler extends GenerateGetterSetterHandlerBase {
protected GenerationInfo[] generateMemberPrototypes(PsiClass aClass, ClassMember original) throws IncorrectOperationException {
if (original instanceof PropertyClassMember) {
final PropertyClassMember propertyClassMember = (PropertyClassMember)original;
final GenerationInfo[] getters = propertyClassMember.generateGetters();
final GenerationInfo[] getters = propertyClassMember.generateGetters(aClass);
if (getters != null) {
return getters;
}
@@ -29,7 +29,7 @@ public class GenerateSetterHandler extends GenerateGetterSetterHandlerBase {
protected GenerationInfo[] generateMemberPrototypes(PsiClass aClass, ClassMember original) throws IncorrectOperationException {
if (original instanceof PropertyClassMember) {
final PropertyClassMember propertyClassMember = (PropertyClassMember)original;
final GenerationInfo[] getters = propertyClassMember.generateSetters();
final GenerationInfo[] getters = propertyClassMember.generateSetters(aClass);
if (getters != null) {
return getters;
}
@@ -15,6 +15,7 @@
*/
package com.intellij.codeInsight.generation;
import com.intellij.psi.PsiClass;
import com.intellij.util.IncorrectOperationException;
import org.jetbrains.annotations.Nullable;
@@ -25,13 +26,15 @@ import org.jetbrains.annotations.Nullable;
public interface PropertyClassMember extends EncapsulatableClassMember {
/**
* @return PsiElement or TemplateGenerationInfo
* @param aClass
*/
@Nullable
GenerationInfo[] generateGetters() throws IncorrectOperationException;
GenerationInfo[] generateGetters(PsiClass aClass) throws IncorrectOperationException;
/**
* @return PsiElement or TemplateGenerationInfo
* @param aClass
*/
@Nullable
GenerationInfo[] generateSetters() throws IncorrectOperationException;
GenerationInfo[] generateSetters(PsiClass aClass) throws IncorrectOperationException;
}
@@ -42,38 +42,37 @@ public class PsiFieldMember extends PsiElementClassMember<PsiField> implements P
@Nullable
@Override
public GenerationInfo generateGetter() throws IncorrectOperationException {
final GenerationInfo[] infos = generateGetters();
final GenerationInfo[] infos = generateGetters(getElement().getContainingClass());
return infos != null && infos.length > 0 ? infos[0] : null;
}
@Nullable
@Override
public GenerationInfo[] generateGetters() throws IncorrectOperationException {
final PsiField field = getElement();
return createGenerateInfos(field, GetterSetterPrototypeProvider.generateGetterSetters(field, true));
public GenerationInfo[] generateGetters(PsiClass aClass) throws IncorrectOperationException {
return createGenerateInfos(aClass, GetterSetterPrototypeProvider.generateGetterSetters(getElement(), true));
}
@Nullable
@Override
public GenerationInfo generateSetter() throws IncorrectOperationException {
final GenerationInfo[] infos = generateSetters();
final GenerationInfo[] infos = generateSetters(getElement().getContainingClass());
return infos != null && infos.length > 0 ? infos[0] : null;
}
@Override
@Nullable
public GenerationInfo[] generateSetters() {
public GenerationInfo[] generateSetters(PsiClass aClass) {
final PsiField field = getElement();
if (GetterSetterPrototypeProvider.isReadOnlyProperty(field)) {
return null;
}
return createGenerateInfos(field, GetterSetterPrototypeProvider.generateGetterSetters(field, false));
return createGenerateInfos(aClass, GetterSetterPrototypeProvider.generateGetterSetters(field, false));
}
private static GenerationInfo[] createGenerateInfos(PsiField field, PsiMethod[] prototypes) {
private static GenerationInfo[] createGenerateInfos(PsiClass aClass, PsiMethod[] prototypes) {
final List<GenerationInfo> methods = new ArrayList<GenerationInfo>();
for (PsiMethod prototype : prototypes) {
final PsiMethod method = createMethodIfNotExists(field, prototype);
final PsiMethod method = createMethodIfNotExists(aClass, prototype);
if (method != null) {
methods.add(new PsiGenerationInfo(method));
}
@@ -82,8 +81,7 @@ public class PsiFieldMember extends PsiElementClassMember<PsiField> implements P
}
@Nullable
private static PsiMethod createMethodIfNotExists(final PsiField field, final PsiMethod template) {
final PsiClass aClass = field.getContainingClass();
private static PsiMethod createMethodIfNotExists(PsiClass aClass, final PsiMethod template) {
PsiMethod existing = aClass.findMethodBySignature(template, false);
if (existing == null) {
if (template != null) {
@@ -55,7 +55,7 @@ public class AnchorElementInfoFactory implements SmartPointerElementInfoFactory
@Nullable
static PsiElement getAnchor(PsiElement element) {
LOG.assertTrue(element.isValid());
LOG.assertTrue(element.isValid(), element);
PsiElement anchor = null;
if (element instanceof PsiClass) {
if (element instanceof PsiAnonymousClass) {
@@ -96,13 +96,12 @@ public class TypeMigrationLabeler {
final PsiElement element = p.getFirst().retrieve();
LOG.assertTrue(element != null);
final PsiType type = ((PsiExpression)element).getType();
report[j++] = "Cannot convert type of expression <b>" +
StringUtil.escapeXml(element.getText()) +
"</b>" +
" from <b>" +
StringUtil.escapeXml(type.getCanonicalText()) +
"</b> to <b>" + StringUtil.escapeXml(p.getSecond().getCanonicalText()) +
"</b><br>";
report[j++] = "Cannot convert type of expression <b>" + StringUtil.escapeXml(element.getText()) + "</b>" +
(type != null
? " from <b>" + StringUtil.escapeXml(type.getCanonicalText()) + "</b>" +
" to <b>" + StringUtil.escapeXml(p.getSecond().getCanonicalText()) + "</b>"
: "")
+ "<br>";
}
return report;
@@ -539,7 +538,6 @@ public class TypeMigrationLabeler {
}
void markFailedConversion(final Pair<PsiType, PsiType> typePair, final PsiExpression expression) {
LOG.assertTrue(expression.getType() != null);
LOG.assertTrue(typePair.getSecond() != null);
myFailedConversions.add(new Pair<PsiAnchor, PsiType>(PsiAnchor.create(expression), typePair.getSecond()));
}
@@ -35,7 +35,12 @@ public class OverrideImplementExploreUtil {
}
@NotNull
private static Map<MethodSignature, CandidateInfo> getMapToOverrideImplement(PsiClass aClass, boolean toImplement) {
public static Map<MethodSignature, CandidateInfo> getMapToOverrideImplement(PsiClass aClass, boolean toImplement) {
return getMapToOverrideImplement(aClass, toImplement, true);
}
@NotNull
public static Map<MethodSignature, CandidateInfo> getMapToOverrideImplement(PsiClass aClass, boolean toImplement, boolean skipImplemented) {
Map<MethodSignature, PsiMethod> abstracts = new LinkedHashMap<MethodSignature,PsiMethod>();
Map<MethodSignature, PsiMethod> finals = new LinkedHashMap<MethodSignature,PsiMethod>();
Map<MethodSignature, PsiMethod> concretes = new LinkedHashMap<MethodSignature,PsiMethod>();
@@ -55,7 +60,7 @@ public class OverrideImplementExploreUtil {
continue;
}
// filter already implemented
if (aClass != hisClass && MethodSignatureUtil.findMethodBySignature(aClass, signature, false) != null) {
if (skipImplemented && MethodSignatureUtil.findMethodBySignature(aClass, signature, false) != null) {
continue;
}
@@ -393,6 +393,7 @@ public class ExpressionParser {
else if (dotTokenType == JavaTokenType.SUPER_KEYWORD) {
dotPos.drop();
final PsiBuilder.Marker refExpr = expr.precede();
builder.mark().done(JavaElementType.REFERENCE_PARAMETER_LIST);
builder.advanceLexer();
refExpr.done(JavaElementType.REFERENCE_EXPRESSION);
expr = refExpr;
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2012 JetBrains s.r.o.
* Copyright 2000-2013 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,6 +15,7 @@
*/
package com.intellij.psi.impl.compiled;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.psi.*;
import com.intellij.psi.impl.source.SourceTreeToPsiMap;
import com.intellij.psi.impl.source.tree.TreeElement;
@@ -33,7 +34,10 @@ public class ClsAnnotationParameterListImpl extends ClsElementImpl implements Ps
for (int i = 0; i < myAttributes.length; i++) {
String name = psiAttributes[i].getName();
PsiAnnotationMemberValue value = psiAttributes[i].getValue();
assert value != null : "name=" + name + " value" + value;
if (value == null) {
Logger.getInstance(getClass()).error("name=" + name + " value=" + value + " anno=[" + parent.getText() + "]");
value = new ClsLiteralExpressionImpl(this, "null", PsiType.NULL, null);
}
myAttributes[i] = new ClsNameValuePairImpl(this, name, value);
}
}
@@ -58,6 +58,8 @@ PsiJavaFile:QualifiedSuperMethodCall.java
PsiJavaToken:LPARENTH('(')
PsiJavaToken:RPARENTH(')')
PsiJavaToken:DOT('.')
PsiReferenceParameterList
<empty list>
PsiKeyword:super('super')
PsiExpressionList
PsiJavaToken:LPARENTH('(')
@@ -14,6 +14,8 @@ PsiJavaFile:QualifiedSuperMethodCall0.java
PsiJavaToken:LPARENTH('(')
PsiJavaToken:RPARENTH(')')
PsiJavaToken:DOT('.')
PsiReferenceParameterList
<empty list>
PsiKeyword:super('super')
PsiExpressionList
PsiJavaToken:LPARENTH('(')
@@ -1,4 +1,6 @@
package com.intellij.navigation
import com.intellij.ide.util.gotoByName.ChooseByNameBase
import com.intellij.ide.util.gotoByName.ChooseByNameModel
import com.intellij.ide.util.gotoByName.ChooseByNamePopup
import com.intellij.ide.util.gotoByName.GotoClassModel2
@@ -14,12 +16,20 @@ import com.intellij.util.concurrency.Semaphore
*/
class ChooseByNameTest extends LightCodeInsightFixtureTestCase {
public void "test trivial goto class"() {
def xxClass = myFixture.addClass("class Xxxxx {}")
def fooXxClass = myFixture.addClass("class FooXxxxx {}")
List<Object> elements = createPopup(new GotoClassModel2(project), "Xxx")
assert elements[0] == xxClass
assert elements[2] == fooXxClass
public void "test goto class order by matching degree"() {
def startMatch = myFixture.addClass("class UiUtil {}")
def wordSkipMatch = myFixture.addClass("class UiAbstractUtil {}")
def camelMatch = myFixture.addClass("class UberInstructionUxTopicInterface {}")
def middleMatch = myFixture.addClass("class BaseUiUtil {}")
def elements = createPopup(new GotoClassModel2(project), "uiuti")
assert elements == [startMatch, wordSkipMatch, camelMatch, ChooseByNameBase.NON_PREFIX_SEPARATOR, middleMatch]
}
public void "test annotation syntax"() {
def match = myFixture.addClass("@interface Anno1 {}")
myFixture.addClass("class Anno2 {}")
def elements = createPopup(new GotoClassModel2(project), "@Anno")
assert elements == [match]
}
private List<Object> createPopup(ChooseByNameModel model, String text) {
@@ -1057,6 +1057,10 @@ public class IncProjectBuilder {
BUILDER_CATEGORY_LOOP:
for (BuilderCategory category : BuilderCategory.values()) {
final List<ModuleLevelBuilder> builders = myBuilderRegistry.getBuilders(category);
if (category == BuilderCategory.CLASS_POST_PROCESSOR) {
// ensure changes from instrumenters are visible to class post-processors
saveInstrumentedClasses(outputConsumer);
}
if (builders.isEmpty()) {
continue;
}
@@ -1114,11 +1118,7 @@ public class IncProjectBuilder {
while (nextPassRequired);
}
finally {
for (CompiledClass compiledClass : outputConsumer.getCompiledClasses().values()) {
if (compiledClass.isDirty()) {
compiledClass.save();
}
}
saveInstrumentedClasses(outputConsumer);
outputConsumer.fireFileGeneratedEvents();
outputConsumer.clear();
for (BuilderCategory category : BuilderCategory.values()) {
@@ -1131,6 +1131,14 @@ public class IncProjectBuilder {
return doneSomething;
}
private void saveInstrumentedClasses(ChunkBuildOutputConsumerImpl outputConsumer) throws IOException {
for (CompiledClass compiledClass : outputConsumer.getCompiledClasses().values()) {
if (compiledClass.isDirty()) {
compiledClass.save();
}
}
}
private static void onChunkBuildComplete(CompileContext context, @NotNull BuildTargetChunk chunk) throws IOException {
final ProjectDescriptor pd = context.getProjectDescriptor();
final BuildFSState fsState = pd.fsState;
@@ -268,6 +268,8 @@ public class JavaBuilder extends ModuleLevelBuilder {
final int filesCount = files.size();
boolean compiledOk = true;
int tempRootsErrorCount = 0;
int tempRootsWarningCount = 0;
if (filesCount > 0) {
LOG.info("Compiling " + filesCount + " java files; module: " + chunkName + (chunk.containsTests() ? " (tests)" : ""));
if (LOG.isDebugEnabled()) {
@@ -283,27 +285,41 @@ public class JavaBuilder extends ModuleLevelBuilder {
LOG.debug(" " + file.getAbsolutePath());
}
}
compiledOk = compileJava(context, chunk, files, classpath, platformCp, srcPath, diagnosticSink, outputSink);
if (compiledOk) {
final Collection<File> loadedTempFiles = diagnosticSink.getLoadedTempSources();
if (!loadedTempFiles.isEmpty()) {
// compile all implicitly loaded sources from temporary roots
compiledOk = compileJava(context, chunk, loadedTempFiles, classpath, platformCp, tempRoots, new DiagnosticSink(context, Collections.<File>emptySet()), outputSink);
try {
compiledOk = compileJava(context, chunk, files, classpath, platformCp, srcPath, diagnosticSink, outputSink);
if (compiledOk) {
final Collection<File> loadedTempFiles = diagnosticSink.getLoadedTempSources();
if (!loadedTempFiles.isEmpty()) {
// compile all implicitly loaded sources from temporary roots
final DiagnosticSink tempRootsSink = new DiagnosticSink(context, Collections.<File>emptySet());
compiledOk = compileJava(context, chunk, loadedTempFiles, classpath, platformCp, tempRoots, tempRootsSink, outputSink);
tempRootsErrorCount = tempRootsSink.getErrorCount();
tempRootsWarningCount = tempRootsSink.getWarningCount();
}
}
}
finally {
// heuristic: incorrect paths data recovery, so that the next make should not contain non-existing sources in 'recompile' list
for (File file : diagnosticSink.getFilesWithErrors()) {
if (!file.exists()) {
FSOperations.markDeleted(context, file);
}
}
}
}
context.checkCanceled();
if (!compiledOk && diagnosticSink.getErrorCount() == 0) {
if (!compiledOk && (diagnosticSink.getErrorCount() + tempRootsErrorCount) == 0) {
diagnosticSink.report(new PlainMessageDiagnostic(Diagnostic.Kind.ERROR, "Compilation failed: internal java compiler error"));
}
if (!Utils.PROCEED_ON_ERROR_KEY.get(context, Boolean.FALSE) && diagnosticSink.getErrorCount() > 0) {
final int totalErrorCount = diagnosticSink.getErrorCount() + tempRootsErrorCount;
if (!Utils.PROCEED_ON_ERROR_KEY.get(context, Boolean.FALSE) && totalErrorCount > 0) {
if (!compiledOk) {
diagnosticSink.report(new PlainMessageDiagnostic(Diagnostic.Kind.OTHER, "Errors occurred while compiling module '" + chunkName + "'"));
}
throw new StopBuildException(
"Compilation failed: errors: " + diagnosticSink.getErrorCount() + "; warnings: " + diagnosticSink.getWarningCount()
"Compilation failed: errors: " + totalErrorCount + "; warnings: " + (diagnosticSink.getWarningCount() + tempRootsWarningCount)
);
}
}
@@ -786,12 +802,13 @@ public class JavaBuilder extends ModuleLevelBuilder {
return map;
}
private class DiagnosticSink implements DiagnosticOutputConsumer {
private static class DiagnosticSink implements DiagnosticOutputConsumer {
private final CompileContext myContext;
private final Set<File> myTempRoots;
private volatile int myErrorCount = 0;
private volatile int myWarningCount = 0;
private final Set<File> myLoadedTempSources = new THashSet<File>(FileUtil.FILE_HASHING_STRATEGY);
private final Set<File> myFilesWithErrors = new HashSet<File>();
public DiagnosticSink(CompileContext context, Set<File> tempRoots) {
myContext = context;
@@ -839,7 +856,7 @@ public class JavaBuilder extends ModuleLevelBuilder {
}
}
private BuildMessage.Kind getKindByMessageText(String line) {
private static BuildMessage.Kind getKindByMessageText(String line) {
final String lowercasedLine = line.toLowerCase(Locale.US);
if (lowercasedLine.contains("error") || lowercasedLine.contains("requires target release")) {
return BuildMessage.Kind.ERROR;
@@ -873,15 +890,23 @@ public class JavaBuilder extends ModuleLevelBuilder {
catch (Exception e) {
LOG.info(e);
}
final String srcPath = sourceFile != null ? FileUtil.toSystemIndependentName(sourceFile.getPath()) : null;
final String srcPath;
if (sourceFile != null) {
myFilesWithErrors.add(sourceFile);
srcPath = FileUtil.toSystemIndependentName(sourceFile.getPath());
}
else {
srcPath = null;
}
String message = diagnostic.getMessage(Locale.US);
if (Utils.IS_TEST_MODE) {
LOG.info(message);
}
myContext.processMessage(
new CompilerMessage(BUILDER_NAME, kind, message, srcPath, diagnostic.getStartPosition(),
diagnostic.getEndPosition(), diagnostic.getPosition(), diagnostic.getLineNumber(),
diagnostic.getColumnNumber()));
myContext.processMessage(new CompilerMessage(
BUILDER_NAME, kind, message, srcPath, diagnostic.getStartPosition(),
diagnostic.getEndPosition(), diagnostic.getPosition(), diagnostic.getLineNumber(),
diagnostic.getColumnNumber()
));
}
public int getErrorCount() {
@@ -891,6 +916,10 @@ public class JavaBuilder extends ModuleLevelBuilder {
public int getWarningCount() {
return myWarningCount;
}
public Collection<File> getFilesWithErrors() {
return myFilesWithErrors;
}
}
private class ClassProcessingConsumer implements OutputFileConsumer {
@@ -184,7 +184,7 @@ public class ExternalSystemApiUtil {
*/
@NotNull
public static String toCanonicalPath(@NotNull String path) {
return PathUtil.getCanonicalPath(new File(path).getAbsolutePath());
return PathUtil.getCanonicalPath(normalizePath(new File(path).getAbsolutePath()));
}
@NotNull
@@ -215,6 +215,7 @@ public class ExternalSystemApiUtil {
@NotNull
public static <K, V> Map<DataNode<K>, List<DataNode<V>>> groupBy(@NotNull Collection<DataNode<V>> nodes, @NotNull final Key<K> key) {
return groupBy(nodes, new Function<DataNode<V>, DataNode<K>>() {
@Nullable
@Override
public DataNode<K> fun(DataNode<V> node) {
return node.getDataNode(key);
@@ -355,7 +356,10 @@ public class ExternalSystemApiUtil {
if (!pathToUse.startsWith("/")) {
pathToUse = '/' + pathToUse;
}
classPath.add(PathManager.getResourceRoot(contextClass, pathToUse));
String root = PathManager.getResourceRoot(contextClass, pathToUse);
if (root != null) {
classPath.add(root);
}
}
@SuppressWarnings("ConstantConditions")
@@ -24,7 +24,6 @@ import org.jetbrains.annotations.NotNull;
*/
public class ExternalSystemConstants {
@NonNls @NotNull public static final String NEWLY_IMPORTED_PROJECT = "external.system.newly.imported";
@NonNls @NotNull public static final String EXTERNAL_SYSTEM_ID_KEY = "external.system.id";
@NonNls @NotNull public static final String LINKED_PROJECT_PATH_KEY = "external.linked.project.path";
@@ -21,6 +21,7 @@ import com.intellij.openapi.externalSystem.model.execution.ExternalTaskPojo;
import com.intellij.openapi.externalSystem.model.project.ExternalProjectPojo;
import com.intellij.openapi.externalSystem.service.task.ui.ExternalSystemRecentTasksList;
import com.intellij.openapi.externalSystem.service.task.ui.ExternalSystemTasksTreeModel;
import com.intellij.openapi.util.Key;
import org.jetbrains.annotations.NotNull;
/**
@@ -38,6 +39,8 @@ public class ExternalSystemDataKeys {
@NotNull public static final DataKey<ExternalSystemRecentTasksList> RECENT_TASKS_LIST
= DataKey.create("external.system.recent.tasks.list");
@NotNull public static final Key<Boolean> NEWLY_IMPORTED_PROJECT = new Key<Boolean>("external.system.newly.imported");
private ExternalSystemDataKeys() {
}
}
@@ -16,15 +16,14 @@
package com.intellij.openapi.externalSystem.service;
import com.intellij.openapi.externalSystem.ExternalSystemManager;
import com.intellij.openapi.externalSystem.model.ExternalSystemDataKeys;
import com.intellij.openapi.externalSystem.service.project.autoimport.ExternalSystemAutoImporter;
import com.intellij.openapi.externalSystem.service.ui.ExternalToolWindowManager;
import com.intellij.openapi.externalSystem.util.ExternalSystemApiUtil;
import com.intellij.openapi.externalSystem.util.ExternalSystemConstants;
import com.intellij.openapi.externalSystem.util.ExternalSystemUtil;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.startup.StartupActivity;
import com.intellij.openapi.startup.StartupManager;
import com.intellij.util.SystemProperties;
/**
* @author Denis Zhdanov
@@ -43,7 +42,7 @@ public class ExternalSystemStartupActivity implements StartupActivity {
((StartupActivity)manager).runActivity(project);
}
}
if (!SystemProperties.getBooleanProperty(ExternalSystemConstants.NEWLY_IMPORTED_PROJECT, false)) {
if (project.getUserData(ExternalSystemDataKeys.NEWLY_IMPORTED_PROJECT) != Boolean.TRUE) {
for (ExternalSystemManager manager : ExternalSystemManager.EP_NAME.getExtensions()) {
ExternalSystemUtil.refreshProjects(project, manager.getSystemId(), false);
}
@@ -3,6 +3,7 @@ package com.intellij.openapi.externalSystem.service.project.wizard;
import com.intellij.ide.util.projectWizard.WizardContext;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.externalSystem.model.DataNode;
import com.intellij.openapi.externalSystem.model.ExternalSystemDataKeys;
import com.intellij.openapi.externalSystem.model.ProjectSystemId;
import com.intellij.openapi.externalSystem.model.project.ProjectData;
import com.intellij.openapi.externalSystem.service.internal.ExternalSystemResolveProjectTask;
@@ -14,7 +15,6 @@ import com.intellij.openapi.externalSystem.settings.ExternalProjectSettings;
import com.intellij.openapi.externalSystem.settings.ExternalSystemSettingsManager;
import com.intellij.openapi.externalSystem.util.ExternalSystemApiUtil;
import com.intellij.openapi.externalSystem.util.ExternalSystemBundle;
import com.intellij.openapi.externalSystem.util.ExternalSystemConstants;
import com.intellij.openapi.externalSystem.util.ExternalSystemUtil;
import com.intellij.openapi.module.ModifiableModuleModel;
import com.intellij.openapi.module.Module;
@@ -116,7 +116,7 @@ public abstract class AbstractExternalProjectImportBuilder<C extends AbstractImp
ModulesProvider modulesProvider,
ModifiableArtifactModel artifactModel)
{
System.setProperty(ExternalSystemConstants.NEWLY_IMPORTED_PROJECT, Boolean.TRUE.toString());
project.putUserData(ExternalSystemDataKeys.NEWLY_IMPORTED_PROJECT, Boolean.TRUE);
final DataNode<ProjectData> externalProjectNode = getExternalProjectNode();
if (externalProjectNode != null) {
beforeCommit(externalProjectNode, project);
@@ -266,6 +266,7 @@ public abstract class AbstractExternalProjectImportBuilder<C extends AbstractImp
@Override
public void onFailure(@NotNull String errorMessage, @Nullable String errorDetails) {
if (!StringUtil.isEmpty(errorDetails)) {
assert errorDetails != null;
LOG.warn(errorDetails);
}
error.set(new ConfigurationException(ExternalSystemBundle.message("error.resolve.with.reason", errorMessage),
@@ -16,13 +16,12 @@
package com.intellij.openapi.externalSystem.service.settings;
import com.intellij.openapi.externalSystem.ExternalSystemManager;
import com.intellij.openapi.externalSystem.model.ExternalSystemDataKeys;
import com.intellij.openapi.externalSystem.model.ProjectSystemId;
import com.intellij.openapi.externalSystem.settings.AbstractExternalSystemSettings;
import com.intellij.openapi.externalSystem.util.ExternalSystemApiUtil;
import com.intellij.openapi.externalSystem.util.ExternalSystemConstants;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.Condition;
import com.intellij.util.SystemProperties;
import org.jetbrains.annotations.NotNull;
/**
@@ -39,7 +38,7 @@ public abstract class AbstractExternalSystemToolWindowCondition implements Condi
@Override
public boolean value(Project project) {
if (SystemProperties.getBooleanProperty(ExternalSystemConstants.NEWLY_IMPORTED_PROJECT, false)) {
if (project.getUserData(ExternalSystemDataKeys.NEWLY_IMPORTED_PROJECT) == Boolean.TRUE) {
return true;
}
ExternalSystemManager<?,?,?,?,?> manager = ExternalSystemApiUtil.getManager(myExternalSystemId);
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2009 JetBrains s.r.o.
* Copyright 2000-2013 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.
@@ -16,45 +16,31 @@
package com.intellij.codeInsight.preview;
import com.intellij.openapi.components.AbstractProjectComponent;
import com.intellij.openapi.extensions.Extensions;
import com.intellij.openapi.fileEditor.*;
import com.intellij.openapi.project.DumbAware;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.startup.StartupActivity;
import com.intellij.openapi.util.Disposer;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.FileViewProvider;
import com.intellij.psi.PsiFile;
import com.intellij.psi.PsiManager;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
/**
* @author spleaner
*/
public class ImageOrColorPreviewProjectComponent extends AbstractProjectComponent {
public ImageOrColorPreviewProjectComponent(final Project project) {
super(project);
}
public class ImageOrColorPreviewProjectComponent implements StartupActivity, DumbAware {
@Override
public void projectOpened() {
myProject.getMessageBus().connect(myProject).subscribe(FileEditorManagerListener.FILE_EDITOR_MANAGER, new MyFileEditorManagerListener());
}
@Override
@NonNls
@NotNull
public String getComponentName() {
return "ImageOrColorPreviewComponent";
public void runActivity(Project project) {
if (!project.isDefault()) {
project.getMessageBus().connect(project).subscribe(FileEditorManagerListener.FILE_EDITOR_MANAGER, new MyFileEditorManagerListener());
}
}
private static class MyFileEditorManagerListener extends FileEditorManagerAdapter {
@Override
public void fileOpened(@NotNull final FileEditorManager source, @NotNull final VirtualFile file) {
if (isSuitable(source.getProject(), file)) {
final FileEditor[] fileEditors = source.getEditors(file);
for (final FileEditor each : fileEditors) {
for (final FileEditor each : source.getEditors(file)) {
if (each instanceof TextEditor) {
Disposer.register(each, new ImageOrColorPreviewManager((TextEditor)each, source.getProject()));
}
@@ -64,10 +50,12 @@ public class ImageOrColorPreviewProjectComponent extends AbstractProjectComponen
private static boolean isSuitable(final Project project, final VirtualFile file) {
final FileViewProvider provider = PsiManager.getInstance(project).findViewProvider(file);
if (provider == null) return false;
if (provider == null) {
return false;
}
for (final PsiFile psiFile : provider.getAllFiles()) {
for(PreviewHintProvider hintProvider: Extensions.getExtensions(PreviewHintProvider.EP_NAME)) {
for (PreviewHintProvider hintProvider : Extensions.getExtensions(PreviewHintProvider.EP_NAME)) {
if (hintProvider.isSupportedFile(psiFile)) {
return true;
}
@@ -77,6 +65,4 @@ public class ImageOrColorPreviewProjectComponent extends AbstractProjectComponen
return false;
}
}
}
}
@@ -661,6 +661,9 @@ public class LanguageConsoleImpl implements Disposable, TypeSafeDataProvider {
}
}
};
if (myProject.isDisposed()) {
return;
}
myProject.getMessageBus().connect(this).subscribe(FileEditorManagerListener.FILE_EDITOR_MANAGER, fileEditorListener);
FileEditorManager editorManager = FileEditorManager.getInstance(getProject());
if (editorManager.isFileOpen(myVirtualFile)) {
@@ -47,12 +47,6 @@ public class DefaultChooseByNameItemProvider implements ChooseByNameItemProvider
myContext = new WeakReference<PsiElement>(context);
}
private enum MatchingMode {
CASE_SENSITIVE,
CASE_INSENSITIVE,
STRICT_CASE_INSENSITIVE
}
@Override
public boolean filterElements(@NotNull ChooseByNameBase base,
@NotNull String pattern,
@@ -69,68 +63,36 @@ public class DefaultChooseByNameItemProvider implements ChooseByNameItemProvider
Set<String> names = new THashSet<String>(Arrays.asList(base.getNames(everywhere)));
if (base.isSearchInAnyPlace() && !namePattern.trim().isEmpty()) {
String middleMatchPattern = "*" + namePattern;
// consume elements matching by prefix case-sensitively
Integer elementsConsumed = consumeElements(base, everywhere, indicator, consumer, namePattern, qualifierPattern, names,
MatchingMode.CASE_SENSITIVE, false);
if (elementsConsumed == null) return false;
if (elementsConsumed == 0) {
// search for strict prefixes case-insensitively
elementsConsumed = consumeElements(base, everywhere, indicator, consumer, namePattern,
qualifierPattern, names, MatchingMode.STRICT_CASE_INSENSITIVE, false);
if (elementsConsumed == null) return false;
// search with original pattern without case sensitivity, don't add separator before found items
// result: items matched by prefix will always be above middle-matched items
Integer elementsConsumed2 = consumeElements(base, everywhere, indicator, consumer, namePattern,
qualifierPattern, names, MatchingMode.CASE_INSENSITIVE, false);
if (elementsConsumed2 == null) return false;
elementsConsumed += elementsConsumed2;
}
// search with broadest criteria - middle match pattern, without case sensitivity
elementsConsumed = consumeElements(base, everywhere, indicator, consumer, middleMatchPattern,
qualifierPattern, names, MatchingMode.CASE_INSENSITIVE, elementsConsumed > 0);
return elementsConsumed != null;
}
else {
Integer elementsConsumed = consumeElements(base, everywhere, indicator, consumer, namePattern, qualifierPattern, names,
MatchingMode.CASE_INSENSITIVE, false);
return elementsConsumed != null;
}
return consumeElements(base, everywhere, indicator, consumer, namePattern, qualifierPattern, names);
}
/**
* @return null if consumer returned false, number of consumed elements otherwise.
*/
@Nullable
private Integer consumeElements(@NotNull ChooseByNameBase base,
private boolean consumeElements(@NotNull ChooseByNameBase base,
boolean everywhere,
@NotNull ProgressIndicator indicator,
@NotNull Processor<Object> consumer,
@NotNull String namePattern,
@NotNull String qualifierPattern,
@NotNull Set<String> allNames,
@NotNull MatchingMode matchingMode,
boolean needSeparator) {
@NotNull Set<String> allNames) {
ChooseByNameModel model = base.getModel();
List<String> namesList = new ArrayList<String>();
getNamesByPattern(base, new ArrayList<String>(allNames), indicator, namesList, namePattern, matchingMode);
String matchingPattern = convertToMatchingPattern(base, namePattern);
List<String> namesList = getNamesByPattern(base, new ArrayList<String>(allNames), indicator, matchingPattern);
allNames.removeAll(namesList);
sortNamesList(namePattern, namesList);
sortNamesList(matchingPattern, namesList);
indicator.checkCanceled();
List<Object> sameNameElements = new SmartList<Object>();
List<Pair<String, MinusculeMatcher>> patternsAndMatchers = getPatternsAndMatchers(qualifierPattern, base);
int elementsConsumed = 0;
MinusculeMatcher matcher = buildPatternMatcher(matchingPattern, NameUtil.MatchingCaseSensitivity.NONE);
boolean sortedByMatchingDegree = !(base.getModel() instanceof CustomMatcherModel);
boolean afterStartMatch = false;
for (String name : namesList) {
indicator.checkCanceled();
boolean isStartMatch = matcher.isStartMatch(name);
boolean needSeparator = sortedByMatchingDegree && !isStartMatch && afterStartMatch;
// use interruptible call if possible
Object[] elements = model instanceof ContributorsBasedGotoByModel ?
@@ -146,25 +108,39 @@ public class DefaultChooseByNameItemProvider implements ChooseByNameItemProvider
}
sortByProximity(base, sameNameElements);
for (Object element : sameNameElements) {
if (needSeparator && !consumer.process(ChooseByNameBase.NON_PREFIX_SEPARATOR)) return null;
if (!consumer.process(element)) return null;
if (needSeparator && !consumer.process(ChooseByNameBase.NON_PREFIX_SEPARATOR)) return false;
if (!consumer.process(element)) return false;
needSeparator = false;
elementsConsumed++;
afterStartMatch = isStartMatch;
}
}
else if (elements.length == 1 && matchesQualifier(elements[0], base, patternsAndMatchers)) {
if (needSeparator && !consumer.process(ChooseByNameBase.NON_PREFIX_SEPARATOR)) return null;
if (!consumer.process(elements[0])) return null;
needSeparator = false;
elementsConsumed++;
if (needSeparator && !consumer.process(ChooseByNameBase.NON_PREFIX_SEPARATOR)) return false;
if (!consumer.process(elements[0])) return false;
afterStartMatch = isStartMatch;
}
}
return elementsConsumed;
return true;
}
protected void sortNamesList(@NotNull String namePattern, @NotNull List<String> namesList) {
final MinusculeMatcher matcher = buildPatternMatcher(namePattern, NameUtil.MatchingCaseSensitivity.NONE);
// Here we sort using namePattern to have similar logic with empty qualified patten case
Collections.sort(namesList, new MatchesComparator(namePattern));
Collections.sort(namesList, new Comparator<String>() {
@Override
public int compare(String o1, String o2) {
boolean start1 = matcher.isStartMatch(o1);
boolean start2 = matcher.isStartMatch(o2);
if (start1 != start2) return start1 ? -1 : 1;
int degree1 = matcher.matchingDegree(o2);
int degree2 = matcher.matchingDegree(o1);
if (degree1 < degree2) return -1;
if (degree1 > degree2) return 1;
return o1.compareToIgnoreCase(o2);
}
});
}
private void sortByProximity(@NotNull ChooseByNameBase base, @NotNull List<Object> sameNameElements) {
@@ -265,51 +241,21 @@ public class DefaultChooseByNameItemProvider implements ChooseByNameItemProvider
@NotNull
@Override
public List<String> filterNames(@NotNull ChooseByNameBase base, @NotNull String[] names, @NotNull String pattern) {
List<String> res = new ArrayList<String>();
getNamesByPattern(base, Arrays.asList(names), null, res, pattern, MatchingMode.CASE_INSENSITIVE);
return res;
return getNamesByPattern(base, Arrays.asList(names), null, convertToMatchingPattern(base, pattern));
}
private static void getNamesByPattern(@NotNull final ChooseByNameBase base,
@NotNull List<String> names,
@Nullable ProgressIndicator indicator,
@NotNull final List<String> outListFiltered, // matched items
@NotNull String pattern,
@NotNull MatchingMode matchingMode) throws ProcessCanceledException {
if (!base.canShowListForEmptyPattern()) {
LOG.assertTrue(!pattern.isEmpty(), base);
}
if (StringUtil.startsWithChar(pattern, '@') && base.getModel() instanceof GotoClassModel2) {
pattern = pattern.substring(1);
}
final String finalPattern = pattern;
final Matcher matcher;
switch (matchingMode) {
case CASE_SENSITIVE:
matcher = buildPatternMatcher(pattern, NameUtil.MatchingCaseSensitivity.ALL);
break;
case CASE_INSENSITIVE:
matcher = buildPatternMatcher(pattern, NameUtil.MatchingCaseSensitivity.NONE);
break;
case STRICT_CASE_INSENSITIVE:
matcher = new Matcher() {
@Override
public boolean matches(@NotNull String name) {
return StringUtil.startsWithIgnoreCase(name, finalPattern);
}
};
break;
default:
return;
}
private static List<String> getNamesByPattern(@NotNull final ChooseByNameBase base,
@NotNull List<String> names,
@Nullable ProgressIndicator indicator,
final String pattern)
throws ProcessCanceledException {
final Matcher matcher = buildPatternMatcher(pattern, NameUtil.MatchingCaseSensitivity.NONE);
@NotNull final List<String> outListFiltered = new ArrayList<String>();
JobLauncher.getInstance().invokeConcurrentlyUnderProgress(names, indicator, false, new Processor<String>() {
@Override
public boolean process(String name) {
if (matches(base, finalPattern, matcher, name)) {
if (matches(base, pattern, matcher, name)) {
synchronized (outListFiltered) {
outListFiltered.add(name);
}
@@ -317,6 +263,22 @@ public class DefaultChooseByNameItemProvider implements ChooseByNameItemProvider
return true;
}
});
return outListFiltered;
}
private static String convertToMatchingPattern(ChooseByNameBase base, String pattern) {
if (!base.canShowListForEmptyPattern()) {
LOG.assertTrue(!pattern.isEmpty(), base);
}
if (base.getModel() instanceof GotoClassModel2 && (pattern.startsWith("@"))) {
pattern = pattern.substring(1);
}
if (base.isSearchInAnyPlace() && !pattern.trim().isEmpty()) {
pattern = "*" + pattern;
}
return pattern;
}
private static boolean matches(@NotNull ChooseByNameBase base,
@@ -343,24 +305,6 @@ public class DefaultChooseByNameItemProvider implements ChooseByNameItemProvider
return NameUtil.buildMatcher(pattern, caseSensitivity);
}
private static class MatchesComparator implements Comparator<String> {
private final String myOriginalPattern;
private MatchesComparator(@NotNull final String originalPattern) {
myOriginalPattern = originalPattern.trim();
}
@Override
public int compare(@NotNull final String a, @NotNull final String b) {
boolean aStarts = a.startsWith(myOriginalPattern);
boolean bStarts = b.startsWith(myOriginalPattern);
if (aStarts && bStarts) return a.compareToIgnoreCase(b);
if (aStarts) return -1;
if (bStarts) return 1;
return a.compareToIgnoreCase(b);
}
}
private static class PathProximityComparator implements Comparator<Object> {
private final ChooseByNameModel myModel;
@NotNull private final PsiProximityComparator myProximityComparator;
@@ -31,21 +31,29 @@ import java.io.IOException;
public class SerializedStubTree {
private final byte[] myBytes;
private final int myLength;
private final long myByteContentLength;
private final int myCharContentLength;
private Stub myStubElement;
public SerializedStubTree(final byte[] bytes, int length, @Nullable Stub stubElement) {
public SerializedStubTree(final byte[] bytes, int length, @Nullable Stub stubElement, long byteContentLength, int charContentLength) {
myBytes = bytes;
myLength = length;
myByteContentLength = byteContentLength;
myCharContentLength = charContentLength;
myStubElement = stubElement;
}
public SerializedStubTree(DataInput in) throws IOException {
myBytes = CompressionUtil.readCompressed(in);
myLength = myBytes.length;
myByteContentLength = in.readLong();
myCharContentLength = in.readInt();
}
public void write(DataOutput out) throws IOException {
CompressionUtil.writeCompressed(out, myBytes, myLength);
out.writeLong(myByteContentLength);
out.writeInt(myCharContentLength);
}
// willIndexStub is one time optimization hint, once can safely pass false
@@ -61,6 +69,13 @@ public class SerializedStubTree {
return SerializationManagerEx.getInstanceEx().deserialize(new UnsyncByteArrayInputStream(myBytes));
}
public boolean contentLengthMatches(long byteContentLength, int charContentLength) {
if (myCharContentLength >= 0 && charContentLength >= 0) {
return myCharContentLength == charContentLength;
}
return myByteContentLength == byteContentLength;
}
public boolean equals(final Object that) {
if (this == that) {
return true;
@@ -24,6 +24,8 @@ import com.intellij.openapi.project.DumbService;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.PsiFile;
import com.intellij.psi.PsiManager;
import com.intellij.psi.impl.PsiManagerEx;
import com.intellij.psi.impl.source.PsiFileImpl;
import com.intellij.psi.search.GlobalSearchScope;
import com.intellij.util.indexing.*;
@@ -104,9 +106,19 @@ public class StubTreeLoaderImpl extends StubTreeLoader {
final int size = datas.size();
if (size == 1) {
SerializedStubTree stubTree = datas.get(0);
if (!stubTree.contentLengthMatches(vFile.getLength(), getCurrentTextContentLength(project, vFile, document))) {
return processError(vFile,
"Outdated stub in index: " + StubUpdatingIndex.getIndexingStampInfo(vFile) +
", docSaved=" + saved +
", queried at " + vFile.getTimeStamp(),
null);
}
Stub stub;
try {
stub = datas.get(0).getStub(false);
stub = stubTree.getStub(false);
}
catch (SerializerNotFoundException e) {
return processError(vFile, "No stub serializer: " + vFile.getPresentableUrl() + ": " + e.getMessage(), e);
@@ -126,6 +138,21 @@ public class StubTreeLoaderImpl extends StubTreeLoader {
return null;
}
private static int getCurrentTextContentLength(Project project, VirtualFile vFile, Document document) {
if (vFile.getFileType().isBinary()) {
return -1;
}
PsiFile psiFile = ((PsiManagerEx)PsiManager.getInstance(project)).getFileManager().getCachedPsiFile(vFile);
if (psiFile instanceof PsiFileImpl && ((PsiFileImpl)psiFile).isContentsLoaded()) {
return psiFile.getTextLength();
}
if (document != null) {
return document.getTextLength();
}
return -1;
}
private static ObjectStubTree processError(final VirtualFile vFile, String message, @Nullable Exception e) {
LOG.error(message, e);
@@ -50,7 +50,7 @@ public class StubUpdatingIndex extends CustomImplementationFileBasedIndexExtensi
public static final ID<Integer, SerializedStubTree> INDEX_ID = ID.create("Stubs");
private static final int VERSION = 24;
private static final int VERSION = 25;
private static final DataExternalizer<SerializedStubTree> KEY_EXTERNALIZER = new DataExternalizer<SerializedStubTree>() {
@Override
@@ -131,13 +131,15 @@ public class StubUpdatingIndex extends CustomImplementationFileBasedIndexExtensi
final Stub rootStub = StubTreeBuilder.buildStubTree(inputData);
if (rootStub == null) return;
rememberIndexingStamp(inputData.getFile());
VirtualFile file = inputData.getFile();
int contentLength = file.getFileType().isBinary() ? -1 : inputData.getContentAsText().length();
rememberIndexingStamp(file, contentLength);
final BufferExposingByteArrayOutputStream bytes = new BufferExposingByteArrayOutputStream();
SerializationManagerEx.getInstanceEx().serialize(rootStub, bytes);
final int key = Math.abs(FileBasedIndex.getFileId(inputData.getFile()));
result.put(key, new SerializedStubTree(bytes.getInternalBuffer(), bytes.size(), rootStub));
final int key = Math.abs(FileBasedIndex.getFileId(file));
result.put(key, new SerializedStubTree(bytes.getInternalBuffer(), bytes.size(), rootStub, file.getLength(), contentLength));
}
});
@@ -146,11 +148,11 @@ public class StubUpdatingIndex extends CustomImplementationFileBasedIndexExtensi
};
}
private static void rememberIndexingStamp(final VirtualFile file) {
private static void rememberIndexingStamp(final VirtualFile file, long contentLength) {
try {
DataOutputStream stream = INDEXED_STAMP.writeAttribute(file);
stream.writeLong(file.getTimeStamp());
stream.writeLong(file.getLength());
stream.writeLong(contentLength);
stream.close();
}
catch (IOException e) {
@@ -19,6 +19,7 @@ package com.intellij.refactoring.rename;
import com.intellij.featureStatistics.FeatureUsageTracker;
import com.intellij.openapi.actionSystem.DataContext;
import com.intellij.openapi.actionSystem.DataKey;
import com.intellij.openapi.actionSystem.LangDataKeys;
import com.intellij.openapi.actionSystem.PlatformDataKeys;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.diagnostic.Logger;
@@ -57,6 +58,10 @@ public class PsiElementRenameHandler implements RenameHandler {
@Override
public void invoke(@NotNull Project project, Editor editor, PsiFile file, DataContext dataContext) {
PsiElement element = getElement(dataContext);
if (element == null) {
element = BaseRefactoringAction.getElementAtCaret(editor, file);
}
editor.getScrollingModel().scrollToCaret(ScrollType.MAKE_VISIBLE);
final PsiElement nameSuggestionContext = InjectedLanguageUtil.findElementAtNoCommit(file, editor.getCaretModel().getOffset());
invoke(element, project, nameSuggestionContext, editor);
@@ -28,6 +28,7 @@ import sun.awt.AppContext;
import javax.swing.*;
import javax.swing.plaf.ColorUIResource;
import javax.swing.plaf.FontUIResource;
import javax.swing.plaf.IconUIResource;
import javax.swing.plaf.InsetsUIResource;
import javax.swing.plaf.basic.BasicLookAndFeel;
@@ -86,6 +87,16 @@ public final class DarculaLaf extends BasicLookAndFeel {
superMethod.setAccessible(true);
final UIDefaults metalDefaults = (UIDefaults)superMethod.invoke(new MetalLookAndFeel());
final UIDefaults defaults = (UIDefaults)superMethod.invoke(base);
if (SystemInfo.isLinux) {
Font font = findFont("DejaVu Sans");
if (font != null) {
for (Object key : defaults.keySet()) {
if (key instanceof String && ((String)key).endsWith(".font")) {
defaults.put(key, new FontUIResource(font.deriveFont(13f)));
}
}
}
}
LafManagerImpl.initInputMapDefaults(defaults);
initIdeaDefaults(defaults);
@@ -102,6 +113,15 @@ public final class DarculaLaf extends BasicLookAndFeel {
return super.getDefaults();
}
private static Font findFont(String name) {
for (Font font : GraphicsEnvironment.getLocalGraphicsEnvironment().getAllFonts()) {
if (font.getName().equals(name)) {
return font;
}
}
return null;
}
private static void patchComboBox(UIDefaults metalDefaults, UIDefaults defaults) {
defaults.remove("ComboBox.ancestorInputMap");
defaults.remove("ComboBox.actionMap");
@@ -28,6 +28,7 @@ import com.intellij.openapi.editor.markup.TextAttributes;
import com.intellij.openapi.options.FontSize;
import com.intellij.openapi.util.Comparing;
import com.intellij.openapi.util.InvalidDataException;
import com.intellij.openapi.util.SystemInfo;
import com.intellij.openapi.util.WriteExternalException;
import com.intellij.util.containers.ContainerUtilRt;
import com.intellij.util.containers.HashMap;
@@ -41,7 +42,7 @@ import java.util.*;
import java.util.List;
public abstract class AbstractColorsScheme implements EditorColorsScheme {
private static final String OS_VALUE_PREFIX = SystemInfo.isWindows ? "windows" : SystemInfo.isMac ? "mac" : "linux";
private static final int CURR_VERSION = 124;
private static final FontSize DEFAULT_FONT_SIZE = FontSize.SMALL;
@@ -373,7 +374,7 @@ public abstract class AbstractColorsScheme implements EditorColorsScheme {
}
private static Color readColorValue(final Element colorElement) {
String value = colorElement.getAttributeValue(VALUE_ELEMENT);
String value = getValue(colorElement);
Color valueColor = null;
if (value != null && value.trim().length() > 0) {
try {
@@ -387,7 +388,7 @@ public abstract class AbstractColorsScheme implements EditorColorsScheme {
private void readSettings(Element childNode) {
String name = childNode.getAttributeValue(NAME_ATTR);
String value = childNode.getAttributeValue(VALUE_ELEMENT);
String value = getValue(childNode);
if (LINE_SPACING.equals(name)) {
myLineSpacing = Float.parseFloat(value);
}
@@ -418,11 +419,11 @@ public abstract class AbstractColorsScheme implements EditorColorsScheme {
for (Object child : children) {
Element e = (Element)child;
if (EDITOR_FONT_NAME.equals(e.getAttributeValue(NAME_ATTR))) {
fontFamily = e.getAttributeValue(VALUE_ELEMENT);
fontFamily = getValue(e);
}
else if (EDITOR_FONT_SIZE.equals(e.getAttributeValue(NAME_ATTR))) {
try {
size = Integer.parseInt(e.getAttributeValue(VALUE_ELEMENT));
size = Integer.parseInt(getValue(e));
}
catch (NumberFormatException ex) {
// ignore
@@ -437,6 +438,11 @@ public abstract class AbstractColorsScheme implements EditorColorsScheme {
}
}
private static String getValue(Element e) {
final String value = e.getAttributeValue(OS_VALUE_PREFIX);
return value == null ? e.getAttributeValue(VALUE_ELEMENT) : value;
}
@Override
public void writeExternal(Element parentNode) throws WriteExternalException {
parentNode.setAttribute(NAME_ATTR, getName());
@@ -33,6 +33,7 @@ public class OpenFilesActivity implements StartupActivity, DumbAware {
final FileEditorManager fileEditorManager = FileEditorManager.getInstance(project);
if (fileEditorManager instanceof FileEditorManagerImpl) {
Runnable runnable = new Runnable() {
@Override
public void run() {
FileEditorManagerImpl manager = (FileEditorManagerImpl)fileEditorManager;
manager.getMainSplitters().openFiles();
@@ -57,6 +57,7 @@ public class Splash extends JDialog implements StartupProgress {
public Splash(String imageName, final Color textColor) {
super((Frame)null);
setUndecorated(true);
setResizable(false);
setModal(false);
@@ -837,6 +837,9 @@
serviceImplementation="com.intellij.codeInsight.CodeInsightUtilBase"/>
<applicationService serviceInterface="com.intellij.ide.util.treeView.TreeAnchorizer"
serviceImplementation="com.intellij.ide.projectView.impl.nodes.PsiTreeAnchorizer"/>
<!--todo approve set order="last" for OpenFilesActivity-->
<postStartupActivity implementation="com.intellij.codeInsight.preview.ImageOrColorPreviewProjectComponent" order="first"/>
</extensions>
</idea-plugin>
@@ -203,11 +203,6 @@
<implementation-class>com.intellij.openapi.vcs.changes.VcsEventWatcher</implementation-class>
</component>
<component>
<interface-class>com.intellij.codeInsight.preview.ImageOrColorPreviewProjectComponent</interface-class>
<implementation-class>com.intellij.codeInsight.preview.ImageOrColorPreviewProjectComponent</implementation-class>
</component>
<component>
<implementation-class>com.intellij.openapi.roots.impl.PushedFilePropertiesUpdater</implementation-class>
</component>
@@ -16,11 +16,13 @@
package com.siyeh.ig.bugs;
import com.intellij.codeInspection.ui.MultipleCheckboxOptionsPanel;
import com.intellij.openapi.util.WriteExternalException;
import com.intellij.psi.*;
import com.siyeh.InspectionGadgetsBundle;
import com.siyeh.ig.BaseInspection;
import com.siyeh.ig.BaseInspectionVisitor;
import com.siyeh.ig.psiutils.FileTypeUtils;
import org.jdom.Element;
import org.jetbrains.annotations.NotNull;
import javax.swing.*;
@@ -33,6 +35,14 @@ public class EmptyStatementBodyInspection extends BaseInspection {
@SuppressWarnings("PublicField")
public boolean commentsAreContent = false;
@Override
public void writeSettings(@NotNull Element node) throws WriteExternalException {
node.addContent(new Element("option").setAttribute("name", "m_reportEmptyBlocks").setAttribute("value", String.valueOf(m_reportEmptyBlocks)));
if (commentsAreContent) {
node.addContent(new Element("option").setAttribute("name", "commentsAreContent").setAttribute("value", "true"));
}
}
@Override
@NotNull
public String getID() {
@@ -4,6 +4,7 @@ import com.intellij.openapi.util.text.StringUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.idea.maven.dom.model.MavenDomDependency;
import org.jetbrains.idea.maven.model.MavenArtifact;
/**
* See org.apache.maven.artifact.Artifact#getDependencyConflictId()
@@ -35,8 +36,37 @@ public class DependencyConflictId {
return new DependencyConflictId(groupId, artifactId, dep.getType().getStringValue(), dep.getClassifier().getStringValue());
}
public boolean isValid() {
return StringUtil.isNotEmpty(groupId) && StringUtil.isNotEmpty(artifactId);
@Nullable
public static DependencyConflictId create(@NotNull MavenArtifact dep) {
return create(dep.getGroupId(), dep.getArtifactId(), dep.getType(), dep.getClassifier());
}
@Nullable
public static DependencyConflictId create(String groupId, String artifactId, String type, String classifier) {
if (StringUtil.isEmpty(groupId)) return null;
if (StringUtil.isEmpty(artifactId)) return null;
return new DependencyConflictId(groupId, artifactId, type, classifier);
}
@NotNull
public String getGroupId() {
return groupId;
}
@NotNull
public String getArtifactId() {
return artifactId;
}
@NotNull
public String getType() {
return type;
}
@Nullable
public String getClassifier() {
return classifier;
}
@Override
@@ -46,9 +76,9 @@ public class DependencyConflictId {
DependencyConflictId id = (DependencyConflictId)o;
if (artifactId != null ? !artifactId.equals(id.artifactId) : id.artifactId != null) return false;
if (!artifactId.equals(id.artifactId)) return false;
if (classifier != null ? !classifier.equals(id.classifier) : id.classifier != null) return false;
if (groupId != null ? !groupId.equals(id.groupId) : id.groupId != null) return false;
if (!groupId.equals(id.groupId)) return false;
if (!type.equals(id.type)) return false;
return true;
@@ -56,8 +86,8 @@ public class DependencyConflictId {
@Override
public int hashCode() {
int result = groupId != null ? groupId.hashCode() : 0;
result = 31 * result + (artifactId != null ? artifactId.hashCode() : 0);
int result = groupId.hashCode();
result = 31 * result + artifactId.hashCode();
result = 31 * result + type.hashCode();
result = 31 * result + (classifier != null ? classifier.hashCode() : 0);
return result;
@@ -33,12 +33,15 @@ import gnu.trove.THashSet;
import org.jetbrains.annotations.NonNls;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.idea.maven.dom.DependencyConflictId;
import org.jetbrains.idea.maven.dom.MavenDomBundle;
import org.jetbrains.idea.maven.dom.MavenDomProjectProcessorUtils;
import org.jetbrains.idea.maven.dom.MavenDomUtil;
import org.jetbrains.idea.maven.dom.model.*;
import org.jetbrains.idea.maven.indices.MavenProjectIndicesManager;
import org.jetbrains.idea.maven.model.MavenArtifact;
import org.jetbrains.idea.maven.model.MavenId;
import org.jetbrains.idea.maven.model.MavenPlugin;
import org.jetbrains.idea.maven.project.MavenProject;
import org.jetbrains.idea.maven.project.MavenProjectsManager;
import org.jetbrains.idea.maven.utils.MavenArtifactUtil;
@@ -52,7 +55,7 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
if (s == null) return null;
MavenId id = MavenArtifactCoordinatesHelper.getId(context);
MavenProjectIndicesManager manager = MavenProjectIndicesManager.getInstance(getProject(context));
MavenProjectIndicesManager manager = MavenProjectIndicesManager.getInstance(context.getProject());
return selectStrategy(context).isValid(id, manager, context) ? s : null;
}
@@ -65,7 +68,7 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
@NotNull
public Collection<String> getVariants(ConvertContext context) {
MavenProjectIndicesManager manager = MavenProjectIndicesManager.getInstance(getProject(context));
MavenProjectIndicesManager manager = MavenProjectIndicesManager.getInstance(context.getProject());
MavenId id = MavenArtifactCoordinatesHelper.getId(context);
MavenDomShortArtifactCoordinates coordinates = MavenArtifactCoordinatesHelper.getCoordinates(context);
@@ -77,17 +80,12 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
@Override
public PsiElement resolve(String o, ConvertContext context) {
Project p = getProject(context);
MavenId id = MavenArtifactCoordinatesHelper.getId(context);
PsiFile result = selectStrategy(context).resolve(p, id, context);
PsiFile result = selectStrategy(context).resolve(id, context);
return result != null ? result : super.resolve(o, context);
}
private static Project getProject(ConvertContext context) {
return context.getFile().getProject();
}
@Override
public String getErrorMessage(@Nullable String s, ConvertContext context) {
return selectStrategy(context).getContextName() + " '''" + MavenArtifactCoordinatesHelper.getId(context) + "''' not found";
@@ -179,9 +177,9 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
return doGetVariants(id, manager);
}
public PsiFile resolve(Project project, MavenId id, ConvertContext context) {
MavenProjectsManager projectsManager = MavenProjectsManager.getInstance(project);
PsiManager psiManager = PsiManager.getInstance(project);
public PsiFile resolve(MavenId id, ConvertContext context) {
PsiManager psiManager = context.getPsiManager();
MavenProjectsManager projectsManager = MavenProjectsManager.getInstance(psiManager.getProject());
PsiFile result = resolveBySpecifiedPath();
if (result != null) return result;
@@ -197,6 +195,15 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
return null;
}
@Nullable
protected MavenProject findMavenProject(ConvertContext context) {
PsiFile psiFile = context.getFile().getOriginalFile();
VirtualFile file = psiFile.getVirtualFile();
if (file == null) return null;
return MavenProjectsManager.getInstance(psiFile.getProject()).findProject(file);
}
private PsiFile resolveInProjects(MavenId id, MavenProjectsManager projectsManager, PsiManager psiManager) {
MavenProject project = projectsManager.findProject(id);
return project == null ? null : psiManager.findFile(project.getFile());
@@ -212,7 +219,7 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
return psiManager.findFile(virtualFile);
}
protected File makeLocalRepositoryFile(MavenId id, File localRepository) {
private File makeLocalRepositoryFile(MavenId id, File localRepository) {
String relPath = (StringUtil.notNullize(id.getGroupId(), "null")).replace(".", "/");
relPath += "/" + id.getArtifactId();
@@ -225,7 +232,7 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
private class ProjectStrategy extends ConverterStrategy {
@Override
public PsiFile resolve(Project project, MavenId id, ConvertContext context) {
public PsiFile resolve(MavenId id, ConvertContext context) {
return null;
}
@@ -266,28 +273,40 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
}
@Override
public PsiFile resolve(Project project, MavenId id, ConvertContext context) {
if (id.getVersion() == null && id.getGroupId() != null && id.getArtifactId() != null) {
DomElement parent = context.getInvocationElement().getParent();
if (parent instanceof MavenDomDependency) {
MavenDomDependency managedDependency = MavenDomProjectProcessorUtils.searchManagingDependency((MavenDomDependency)parent);
if (managedDependency != null && !"import".equals(managedDependency.getScope().getStringValue())) {
final GenericDomValue<String> managedDependencyArtifactId = managedDependency.getArtifactId();
PsiElement res = RecursionManager.doPreventingRecursion(managedDependencyArtifactId, false, new Computable<PsiElement>() {
@Override
public PsiElement compute() {
return new GenericDomValueReference(managedDependencyArtifactId).resolve();
}
});
public PsiFile resolve(MavenId id, ConvertContext context) {
PsiFile res = super.resolve(id, context);
if (res != null) return res;
if (res instanceof PsiFile) {
return (PsiFile)res;
}
DomElement parent = context.getInvocationElement().getParent();
if (!(parent instanceof MavenDomDependency)) return null;
DependencyConflictId dependencyId = DependencyConflictId.create((MavenDomDependency)parent);
if (dependencyId == null) return null;
MavenProject mavenProject = findMavenProject(context);
if (mavenProject != null) {
for (MavenArtifact artifact : mavenProject.getDependencies()) {
if (dependencyId.equals(DependencyConflictId.create(artifact))) {
return super.resolve(new MavenId(id.getGroupId(), id.getArtifactId(), artifact.getVersion()), context);
}
}
}
return super.resolve(project, id, context);
if (id.getVersion() == null) {
MavenDomDependency managedDependency = MavenDomProjectProcessorUtils.searchManagingDependency((MavenDomDependency)parent);
if (managedDependency != null) {
final GenericDomValue<String> managedDependencyArtifactId = managedDependency.getArtifactId();
return RecursionManager.doPreventingRecursion(managedDependencyArtifactId, false, new Computable<PsiFile>() {
@Override
public PsiFile compute() {
PsiElement res = new GenericDomValueReference(managedDependencyArtifactId).resolve();
return res instanceof PsiFile ? (PsiFile)res : null;
}
});
}
}
return null;
}
@Override
@@ -313,7 +332,7 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
private class ExclusionStrategy extends ConverterStrategy {
@Override
public PsiFile resolve(Project project, MavenId id, ConvertContext context) {
public PsiFile resolve(MavenId id, ConvertContext context) {
return null;
}
@@ -369,8 +388,33 @@ public abstract class MavenArtifactCoordinatesConverter extends ResolvingConvert
}
@Override
protected File makeLocalRepositoryFile(MavenId id, File localRepository) {
return MavenArtifactUtil.getArtifactFile(localRepository, id.getGroupId(), id.getArtifactId(), id.getVersion(), "pom");
public PsiFile resolve(MavenId id, ConvertContext context) {
PsiFile res = super.resolve(id, context);
if (res != null) return res;
// Try to resolve to imported plugin
MavenProject mavenProject = findMavenProject(context);
if (mavenProject != null) {
for (MavenPlugin plugin : mavenProject.getPlugins()) {
if (MavenArtifactUtil.isPluginIdEquals(id.getGroupId(), id.getArtifactId(), plugin.getGroupId(), plugin.getArtifactId())) {
return super.resolve(plugin.getMavenId(), context);
}
}
}
// Try to resolve to plugin with latest version
PsiManager psiManager = context.getPsiManager();
MavenProjectsManager projectsManager = MavenProjectsManager.getInstance(psiManager.getProject());
File artifactFile = MavenArtifactUtil
.getArtifactFile(projectsManager.getLocalRepository(), id.getGroupId(), id.getArtifactId(), id.getVersion(), "pom");
VirtualFile virtualFile = LocalFileSystem.getInstance().findFileByIoFile(artifactFile);
if (virtualFile != null) {
return psiManager.findFile(virtualFile);
}
return null;
}
}
}
@@ -15,6 +15,7 @@
*/
package org.jetbrains.idea.maven.utils;
import com.intellij.openapi.util.Comparing;
import com.intellij.openapi.util.io.FileUtil;
import com.intellij.openapi.util.text.StringUtil;
import gnu.trove.THashMap;
@@ -70,6 +71,33 @@ public class MavenArtifactUtil {
return getArtifactFile(localRepository, id.getGroupId(), id.getArtifactId(), id.getVersion(), "pom");
}
public static boolean isPluginIdEquals(@Nullable String groupId1, @Nullable String artifactId1,
@Nullable String groupId2, @Nullable String artifactId2) {
if (artifactId1 == null) return false;
if (!artifactId1.equals(artifactId2)) return false;
if (groupId1 != null) {
for (String group : DEFAULT_GROUPS) {
if (groupId1.equals(group)) {
groupId1 = null;
break;
}
}
}
if (groupId2 != null) {
for (String group : DEFAULT_GROUPS) {
if (groupId2.equals(group)) {
groupId2 = null;
break;
}
}
}
return Comparing.equal(groupId1, groupId2);
}
@NotNull
public static File getArtifactFile(File localRepository, String groupId, String artifactId, String version, String type) {
File dir = null;