mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
Merge remote-tracking branch 'origin/master'
This commit is contained in:
@@ -23,6 +23,7 @@ import com.intellij.openapi.vfs.VirtualFile;
|
||||
import gnu.trove.THashSet;
|
||||
import org.intellij.images.ImagesBundle;
|
||||
import org.intellij.images.fileTypes.ImageFileTypeManager;
|
||||
import org.intellij.images.vfs.IfsUtil;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
@@ -76,15 +77,16 @@ final class ImageFileTypeManagerImpl extends ImageFileTypeManager implements App
|
||||
}
|
||||
|
||||
public void createFileTypes(final @NotNull FileTypeConsumer consumer) {
|
||||
final String[] readerFormatNames = ImageIO.getReaderFormatNames();
|
||||
final Set<String> processed = new THashSet<String>();
|
||||
|
||||
final String[] readerFormatNames = ImageIO.getReaderFormatNames();
|
||||
for (String format : readerFormatNames) {
|
||||
final String s = format.toLowerCase();
|
||||
if (processed.contains(s)) continue;
|
||||
processed.add(s);
|
||||
final String ext = format.toLowerCase();
|
||||
processed.add(ext);
|
||||
}
|
||||
|
||||
processed.add(IfsUtil.ICO_FORMAT.toLowerCase());
|
||||
|
||||
consumer.consume(imageFileType, StringUtil.join(processed, FileTypeConsumer.EXTENSION_DELIMITER));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2009 JetBrains s.r.o.
|
||||
* Copyright 2000-2012 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.
|
||||
@@ -27,6 +27,9 @@ import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.reference.SoftReference;
|
||||
import com.intellij.util.LogicalRoot;
|
||||
import com.intellij.util.LogicalRootsManager;
|
||||
import org.apache.sanselan.ImageReadException;
|
||||
import org.apache.sanselan.common.byteSources.ByteSourceArray;
|
||||
import org.apache.sanselan.formats.ico.IcoImageParser;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@@ -46,9 +49,12 @@ import java.util.Iterator;
|
||||
* @author <a href="mailto:aefimov.box@gmail.com">Alexey Efimov</a>
|
||||
*/
|
||||
public final class IfsUtil {
|
||||
public static final String ICO_FORMAT = "ico";
|
||||
|
||||
private static final Key<Long> TIMESTAMP_KEY = Key.create("Image.timeStamp");
|
||||
private static final Key<String> FORMAT_KEY = Key.create("Image.format");
|
||||
private static final Key<SoftReference<BufferedImage>> BUFFERED_IMAGE_REF_KEY = Key.create("Image.bufferedImage");
|
||||
private static final IcoImageParser ICO_IMAGE_PARSER = new IcoImageParser();
|
||||
|
||||
/**
|
||||
* Load image data for file and put user data attributes into file.
|
||||
@@ -63,6 +69,17 @@ public final class IfsUtil {
|
||||
if (loadedTimeStamp == null || loadedTimeStamp.longValue() != file.getTimeStamp() || imageRef == null || imageRef.get() == null) {
|
||||
try {
|
||||
final byte[] content = file.contentsToByteArray();
|
||||
|
||||
if (ICO_FORMAT.equalsIgnoreCase(file.getExtension())) {
|
||||
try {
|
||||
final BufferedImage image = ICO_IMAGE_PARSER.getBufferedImage(new ByteSourceArray(content), null);
|
||||
file.putUserData(FORMAT_KEY, ICO_FORMAT);
|
||||
file.putUserData(BUFFERED_IMAGE_REF_KEY, new SoftReference<BufferedImage>(image));
|
||||
return true;
|
||||
}
|
||||
catch (ImageReadException ignore) { }
|
||||
}
|
||||
|
||||
InputStream inputStream = new ByteArrayInputStream(content, 0, content.length);
|
||||
ImageInputStream imageInputStream = ImageIO.createImageInputStream(inputStream);
|
||||
try {
|
||||
|
||||
@@ -500,7 +500,7 @@ public class ConsoleViewImpl extends JPanel implements ConsoleView, ObservableCo
|
||||
}
|
||||
|
||||
private ModalityState getStateForUpdate() {
|
||||
return null;//myStateForUpdate != null ? myStateForUpdate.compute() : ModalityState.stateForComponent(this);
|
||||
return myStateForUpdate != null ? myStateForUpdate.compute() : ModalityState.stateForComponent(this);
|
||||
}
|
||||
|
||||
private void requestFlushImmediately() {
|
||||
|
||||
@@ -1873,7 +1873,7 @@ public final class ToolWindowManagerImpl extends ToolWindowManagerEx implements
|
||||
|
||||
@Override
|
||||
public void hyperlinkUpdate(HyperlinkEvent e) {
|
||||
if (myBalloon != null) {
|
||||
if (myBalloon != null && e.getEventType() == HyperlinkEvent.EventType.ACTIVATED) {
|
||||
myBalloon.hide();
|
||||
}
|
||||
if (myListener != null) {
|
||||
|
||||
@@ -208,20 +208,8 @@ public class PopupFactoryImpl extends JBPopupFactory {
|
||||
builder.buildGroup(actionGroup);
|
||||
final List<ActionItem> items = builder.getItems();
|
||||
|
||||
int defaultOptionIndex = 0;
|
||||
if (preselectActionCondition != null) {
|
||||
for (int i = 0; i < items.size(); i++) {
|
||||
final AnAction action = items.get(i).getAction();
|
||||
if (preselectActionCondition.value(action)) {
|
||||
defaultOptionIndex = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return new ActionPopupStep(items, title, component, showNumbers || honorActionMnemonics && itemsHaveMnemonics(items),
|
||||
defaultOptionIndex,
|
||||
false, showDisabledActions);
|
||||
preselectActionCondition, false, showDisabledActions);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -300,14 +288,42 @@ public class PopupFactoryImpl extends JBPopupFactory {
|
||||
return createActionsStep(actionGroup, dataContext, showNumbers, showDisabledActions, title, component, honorActionMnemonics, 0, false);
|
||||
}
|
||||
|
||||
private static ListPopupStep createActionsStep(ActionGroup actionGroup, @NotNull DataContext dataContext, boolean showNumbers, boolean useAlphaAsNumbers, boolean showDisabledActions,
|
||||
String title, Component component, boolean honorActionMnemonics, int defaultOptionIndex,
|
||||
final boolean autoSelectionEnabled) {
|
||||
final ActionStepBuilder builder = new ActionStepBuilder(dataContext, showNumbers, useAlphaAsNumbers, showDisabledActions, honorActionMnemonics);
|
||||
builder.buildGroup(actionGroup);
|
||||
final List<ActionItem> items = builder.getItems();
|
||||
private static ListPopupStep createActionsStep(ActionGroup actionGroup, @NotNull DataContext dataContext,
|
||||
boolean showNumbers, boolean useAlphaAsNumbers, boolean showDisabledActions,
|
||||
String title, Component component, boolean honorActionMnemonics,
|
||||
final int defaultOptionIndex, final boolean autoSelectionEnabled) {
|
||||
final List<ActionItem> items = makeActionItemsFromActionGroup(actionGroup, dataContext, showNumbers, useAlphaAsNumbers,
|
||||
showDisabledActions, honorActionMnemonics);
|
||||
return new ActionPopupStep(items, title, component, showNumbers || honorActionMnemonics && itemsHaveMnemonics(items),
|
||||
new Condition<AnAction>() {
|
||||
@Override
|
||||
public boolean value(AnAction action) {
|
||||
return defaultOptionIndex >= 0 &&
|
||||
defaultOptionIndex < items.size() &&
|
||||
items.get(defaultOptionIndex).getAction().equals(action);
|
||||
}
|
||||
}, autoSelectionEnabled, showDisabledActions);
|
||||
}
|
||||
|
||||
return new ActionPopupStep(items, title, component, showNumbers || honorActionMnemonics && itemsHaveMnemonics(items), defaultOptionIndex,
|
||||
private static List<ActionItem> makeActionItemsFromActionGroup(ActionGroup actionGroup,
|
||||
DataContext dataContext,
|
||||
boolean showNumbers,
|
||||
boolean useAlphaAsNumbers,
|
||||
boolean showDisabledActions,
|
||||
boolean honorActionMnemonics) {
|
||||
final ActionStepBuilder builder = new ActionStepBuilder(dataContext, showNumbers, useAlphaAsNumbers, showDisabledActions,
|
||||
honorActionMnemonics);
|
||||
builder.buildGroup(actionGroup);
|
||||
return builder.getItems();
|
||||
}
|
||||
|
||||
private static ListPopupStep createActionsStep(ActionGroup actionGroup, @NotNull DataContext dataContext,
|
||||
boolean showNumbers, boolean useAlphaAsNumbers, boolean showDisabledActions,
|
||||
String title, Component component, boolean honorActionMnemonics,
|
||||
Condition<AnAction> preselectActionCondition, boolean autoSelectionEnabled) {
|
||||
final List<ActionItem> items = makeActionItemsFromActionGroup(actionGroup, dataContext, showNumbers, useAlphaAsNumbers,
|
||||
showDisabledActions, honorActionMnemonics);
|
||||
return new ActionPopupStep(items, title, component, showNumbers || honorActionMnemonics && itemsHaveMnemonics(items), preselectActionCondition,
|
||||
autoSelectionEnabled, showDisabledActions);
|
||||
}
|
||||
|
||||
@@ -487,21 +503,35 @@ public class PopupFactoryImpl extends JBPopupFactory {
|
||||
private final boolean myAutoSelectionEnabled;
|
||||
private final boolean myShowDisabledActions;
|
||||
private Runnable myFinalRunnable;
|
||||
@Nullable private final Condition<AnAction> myPreselectActionCondition;
|
||||
|
||||
private ActionPopupStep(@NotNull final List<ActionItem> items,
|
||||
final String title,
|
||||
Component context,
|
||||
boolean enableMnemonics,
|
||||
final int defaultOptionIndex, final boolean autoSelection, boolean showDisabledActions) {
|
||||
private ActionPopupStep(@NotNull final List<ActionItem> items, final String title, Component context, boolean enableMnemonics,
|
||||
@Nullable Condition<AnAction> preselectActionCondition, final boolean autoSelection, boolean showDisabledActions) {
|
||||
myItems = items;
|
||||
myTitle = title;
|
||||
myContext = context;
|
||||
myEnableMnemonics = enableMnemonics;
|
||||
myDefaultOptionIndex = defaultOptionIndex;
|
||||
myDefaultOptionIndex = getDefaultOptionIndexFromSelectCondition(preselectActionCondition, items);
|
||||
myPreselectActionCondition = preselectActionCondition;
|
||||
myAutoSelectionEnabled = autoSelection;
|
||||
myShowDisabledActions = showDisabledActions;
|
||||
}
|
||||
|
||||
private static int getDefaultOptionIndexFromSelectCondition(@Nullable Condition<AnAction> preselectActionCondition,
|
||||
@NotNull List<ActionItem> items) {
|
||||
int defaultOptionIndex = 0;
|
||||
if (preselectActionCondition != null) {
|
||||
for (int i = 0; i < items.size(); i++) {
|
||||
final AnAction action = items.get(i).getAction();
|
||||
if (preselectActionCondition.value(action)) {
|
||||
defaultOptionIndex = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return defaultOptionIndex;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public List<ActionItem> getValues() {
|
||||
return myItems;
|
||||
@@ -552,13 +582,14 @@ public class PopupFactoryImpl extends JBPopupFactory {
|
||||
final DataContext dataContext = myContext != null ? mgr.getDataContext(myContext) : mgr.getDataContext();
|
||||
|
||||
if (action instanceof ActionGroup && (!finalChoice || !((ActionGroup)action).canBePerformed(dataContext))) {
|
||||
return JBPopupFactory.getInstance().createActionsStep((ActionGroup)action, dataContext, myEnableMnemonics, myShowDisabledActions, null, myContext, false);
|
||||
return createActionsStep((ActionGroup)action, dataContext, myEnableMnemonics, true, myShowDisabledActions, null, myContext, false,
|
||||
myPreselectActionCondition, false);
|
||||
}
|
||||
else {
|
||||
myFinalRunnable = new Runnable() {
|
||||
public void run() {
|
||||
action.actionPerformed(
|
||||
new AnActionEvent(null, dataContext, ActionPlaces.UNKNOWN, (Presentation)action.getTemplatePresentation().clone(),
|
||||
new AnActionEvent(null, dataContext, ActionPlaces.UNKNOWN, action.getTemplatePresentation().clone(),
|
||||
ActionManager.getInstance(), 0));
|
||||
}
|
||||
};
|
||||
|
||||
@@ -190,11 +190,15 @@
|
||||
<externalAnnotator language="XML" implementationClass="org.jetbrains.android.inspections.lint.AndroidLintExternalAnnotator"/>
|
||||
<externalAnnotator language="TEXT" implementationClass="org.jetbrains.android.inspections.lint.AndroidLintExternalAnnotator"/>
|
||||
|
||||
<usageTargetProvider implementation="org.jetbrains.android.AndroidUsagesTargetProvider"/>
|
||||
<renameHandler implementation="org.jetbrains.android.AndroidRenameHandler" order="first"/>
|
||||
|
||||
<compileServer.plugin jar-path="jps/android-jps-plugin.jar"/>
|
||||
<compileServer.plugin jar-path="android-rt.jar"/>
|
||||
|
||||
<compileServer.plugin jar-path="sdklib.jar"/>
|
||||
<compileServer.plugin jar-path="../../../../../community/plugins/android/lib/sdklib.jar"/>
|
||||
<compileServer.plugin jar-path="../../../../../plugins/android/lib/sdklib.jar"/>
|
||||
</extensions>
|
||||
|
||||
<extensionPoints>
|
||||
|
||||
@@ -0,0 +1,98 @@
|
||||
package org.jetbrains.android;
|
||||
|
||||
import com.intellij.ide.TitledHandler;
|
||||
import com.intellij.openapi.actionSystem.DataContext;
|
||||
import com.intellij.openapi.actionSystem.LangDataKeys;
|
||||
import com.intellij.openapi.actionSystem.PlatformDataKeys;
|
||||
import com.intellij.openapi.application.ApplicationManager;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.DialogWrapper;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.xml.XmlAttribute;
|
||||
import com.intellij.psi.xml.XmlAttributeValue;
|
||||
import com.intellij.psi.xml.XmlTag;
|
||||
import com.intellij.refactoring.rename.PsiElementRenameHandler;
|
||||
import com.intellij.refactoring.rename.RenameDialog;
|
||||
import com.intellij.refactoring.rename.RenameHandler;
|
||||
import org.jetbrains.android.dom.wrappers.ValueResourceElementWrapper;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
/**
|
||||
* @author Eugene.Kudelevsky
|
||||
*/
|
||||
public class AndroidRenameHandler implements RenameHandler, TitledHandler {
|
||||
@Override
|
||||
public boolean isAvailableOnDataContext(DataContext dataContext) {
|
||||
final Editor editor = PlatformDataKeys.EDITOR.getData(dataContext);
|
||||
if (editor == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
final PsiFile file = LangDataKeys.PSI_FILE.getData(dataContext);
|
||||
if (file == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return AndroidUsagesTargetProvider.findValueResourceTagInContext(editor, file) != null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isRenaming(DataContext dataContext) {
|
||||
return isAvailableOnDataContext(dataContext);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void invoke(@NotNull Project project, Editor editor, PsiFile file, DataContext dataContext) {
|
||||
if (file == null || editor == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final XmlTag tag = AndroidUsagesTargetProvider.findValueResourceTagInContext(editor, file);
|
||||
if (tag == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final XmlAttribute nameAttribute = tag.getAttribute("name");
|
||||
if (nameAttribute == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final XmlAttributeValue attributeValue = nameAttribute.getValueElement();
|
||||
if (attributeValue == null) {
|
||||
return;
|
||||
}
|
||||
final RenameDialog dialog = new RenameDialog(project, new ValueResourceElementWrapper(attributeValue), null, editor);
|
||||
|
||||
if (ApplicationManager.getApplication().isUnitTestMode()) {
|
||||
final String name = PsiElementRenameHandler.DEFAULT_NAME.getData(dataContext);
|
||||
//noinspection TestOnlyProblems
|
||||
dialog.performRename(name);
|
||||
dialog.close(DialogWrapper.OK_EXIT_CODE);
|
||||
}
|
||||
else {
|
||||
dialog.show();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void invoke(@NotNull Project project, @NotNull PsiElement[] elements, DataContext dataContext) {
|
||||
final Editor editor = PlatformDataKeys.EDITOR.getData(dataContext);
|
||||
if (editor == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final PsiFile file = LangDataKeys.PSI_FILE.getData(dataContext);
|
||||
if (file == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
invoke(project, editor, file, dataContext);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getActionTitle() {
|
||||
return "Rename Android value resource";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
package org.jetbrains.android;
|
||||
|
||||
import com.android.resources.ResourceFolderType;
|
||||
import com.intellij.find.findUsages.PsiElement2UsageTargetAdapter;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiFile;
|
||||
import com.intellij.psi.util.PsiTreeUtil;
|
||||
import com.intellij.psi.xml.XmlFile;
|
||||
import com.intellij.psi.xml.XmlTag;
|
||||
import com.intellij.usages.UsageTarget;
|
||||
import com.intellij.usages.UsageTargetProvider;
|
||||
import org.jetbrains.android.facet.AndroidFacet;
|
||||
import org.jetbrains.android.resourceManagers.ResourceManager;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
/**
|
||||
* @author Eugene.Kudelevsky
|
||||
*/
|
||||
public class AndroidUsagesTargetProvider implements UsageTargetProvider {
|
||||
@Override
|
||||
public UsageTarget[] getTargets(Editor editor, PsiFile file) {
|
||||
if (editor == null || file == null) {
|
||||
return UsageTarget.EMPTY_ARRAY;
|
||||
}
|
||||
|
||||
final XmlTag tag = findValueResourceTagInContext(editor, file);
|
||||
return tag != null
|
||||
? new UsageTarget[]{new PsiElement2UsageTargetAdapter(tag)}
|
||||
: UsageTarget.EMPTY_ARRAY;
|
||||
}
|
||||
|
||||
@Override
|
||||
public UsageTarget[] getTargets(PsiElement psiElement) {
|
||||
return UsageTarget.EMPTY_ARRAY;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
static XmlTag findValueResourceTagInContext(@NotNull Editor editor, @NotNull PsiFile file) {
|
||||
if (!(file instanceof XmlFile)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
final AndroidFacet facet = AndroidFacet.getInstance(file);
|
||||
if (facet == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (!ResourceManager.isInResourceSubdirectory(file, ResourceFolderType.VALUES.getName())) {
|
||||
return null;
|
||||
}
|
||||
|
||||
final PsiElement element = file.findElementAt(editor.getCaretModel().getOffset());
|
||||
if (element == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
final XmlTag tag = PsiTreeUtil.getParentOfType(element, XmlTag.class);
|
||||
if (tag == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
final String name = tag.getAttributeValue("name");
|
||||
if (name == null || name.length() == 0) {
|
||||
return null;
|
||||
}
|
||||
|
||||
final XmlTag parentTag = tag.getParentTag();
|
||||
return parentTag != null && parentTag.getParentTag() == null ? tag : null;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
<resources>
|
||||
<caret><string name="hello">hello</string>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr"></string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,5 @@
|
||||
<resources>
|
||||
<stri<caret>ng name="hello">hello</string>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr"></string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,5 @@
|
||||
<resources>
|
||||
<string<caret> name="hello">hello</string>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr"></string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,5 @@
|
||||
<resources>
|
||||
<string name="he<caret>llo">hello</string>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr"></string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,5 @@
|
||||
<resources>
|
||||
<string name="hello"<caret>>hello</string>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr"></string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,5 @@
|
||||
<resources>
|
||||
<string name="hello">he<caret>llo</string>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr"></string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,5 @@
|
||||
<resources>
|
||||
<string name="hello">hello</s<caret>tring>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr"></string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,5 @@
|
||||
<resources>
|
||||
<string name="hello">hello<<caret>/string>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr"></string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,8 @@
|
||||
<resources>
|
||||
<string name="hello">hello</string>
|
||||
<item name="hi" type="string"/>
|
||||
<string-array name="str_arr">
|
||||
<item>str1</item>
|
||||
<item>str2</item>
|
||||
</string-array>
|
||||
</resources>
|
||||
@@ -0,0 +1,4 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<TextView android:text="@string/str"/>
|
||||
</LinearLayout>
|
||||
@@ -0,0 +1,4 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<TextView android:text="@string/str1"/>
|
||||
</LinearLayout>
|
||||
@@ -0,0 +1,3 @@
|
||||
<resources>
|
||||
<string name="s<caret>tr">HellO!</string>
|
||||
</resources>
|
||||
@@ -0,0 +1,3 @@
|
||||
<resources>
|
||||
<string name="str">He<caret>llO!</string>
|
||||
</resources>
|
||||
@@ -0,0 +1,3 @@
|
||||
<resources>
|
||||
<string name="str">HellO!</stri<caret>ng>
|
||||
</resources>
|
||||
@@ -0,0 +1,3 @@
|
||||
<resources>
|
||||
<s<caret>tring name="str">HellO!</string>
|
||||
</resources>
|
||||
@@ -17,21 +17,23 @@
|
||||
package org.jetbrains.android;
|
||||
|
||||
import com.intellij.codeInsight.TargetElementUtilBase;
|
||||
import com.intellij.openapi.actionSystem.DataProvider;
|
||||
import com.intellij.openapi.editor.ex.EditorEx;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.testFramework.fixtures.JavaCodeInsightTestFixture;
|
||||
import com.intellij.usageView.UsageInfo;
|
||||
import com.intellij.usages.PsiElementUsageTarget;
|
||||
import com.intellij.usages.UsageTarget;
|
||||
import com.intellij.usages.UsageTargetUtil;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import java.util.ArrayList;
|
||||
|
||||
/**
|
||||
* Created by IntelliJ IDEA.
|
||||
* User: Eugene.Kudelevsky
|
||||
* Date: Aug 5, 2009
|
||||
* Time: 4:48:01 PM
|
||||
* To change this template use File | Settings | File Templates.
|
||||
* @author Eugene.Kudelevsky
|
||||
*/
|
||||
public class AndroidFindUsagesTest extends AndroidTestCase {
|
||||
private static final String BASE_PATH = "/findUsages/";
|
||||
@@ -39,13 +41,12 @@ public class AndroidFindUsagesTest extends AndroidTestCase {
|
||||
@Override
|
||||
public void setUp() throws Exception {
|
||||
super.setUp();
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "picture3.gif", "res/drawable/picture3.gif");
|
||||
myFixture.copyFileToProject(BASE_PATH + "R.java", "gen/p1/p2/R.java");
|
||||
}
|
||||
|
||||
public List<UsageInfo> findCodeUsages(String path) throws Throwable {
|
||||
Collection<UsageInfo> usages = findElementAtCaret(path, myFixture, BASE_PATH);
|
||||
public List<UsageInfo> findCodeUsages(String path, String pathInProject) throws Throwable {
|
||||
Collection<UsageInfo> usages = findUsages(path, myFixture, pathInProject);
|
||||
List<UsageInfo> result = new ArrayList<UsageInfo>();
|
||||
for (UsageInfo usage : usages) {
|
||||
if (!usage.isNonCodeUsage) {
|
||||
@@ -56,70 +57,146 @@ public class AndroidFindUsagesTest extends AndroidTestCase {
|
||||
}
|
||||
|
||||
public void testFileResource() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "styles.xml", "res/values/styles.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu1_layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu1_layout.xml", "res/layout/fu1_layout.xml");
|
||||
assertEquals(3, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_layout.xml", "res/layout/fu2_layout.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource1() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu1_values.xml", "res/values/fu1_values.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource2() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_values.xml", "res/values/fu2_values.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource3() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_values.xml", "res/values/fu3_values.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource4() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_values.xml", "res/values/fu4_values.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource5() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_values.xml", "res/values/fu5_values.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource6() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_values.xml", "res/values/fu6_values.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource7() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_values.xml", "res/values/fu7_values.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResource8() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu2_values.xml", "res/values/f8_values.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueItemResource() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu5_layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu5_layout.xml", "res/layout/fu5_layout.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testFileResourceField() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("Fu3.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("Fu3.java", "src/p1/p2/Fu3.java");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueResourceField() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("Fu4.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("Fu4.java", "src/p1/p2/Fu4.java");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testValueItemResourceField() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("Fu6.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("Fu6.java", "src/p1/p2/Fu6.java");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testIdResource() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu7_layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu7_layout.xml", "res/layout/fu7_layout.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testIdResourceField() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "layout.xml", "res/layout/layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("Fu8.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("Fu8.java", "src/p1/p2/Fu8.java");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testIdResourceDeclaration() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu9_layout.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("fu9_layout.xml", "res/layout/fu9_layout.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
public void testStringArray() throws Throwable {
|
||||
myFixture.copyFileToProject(BASE_PATH + "strings.xml", "res/values/strings.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "Class.java", "src/p1/p2/Class.java");
|
||||
Collection<UsageInfo> references = findCodeUsages("stringArray.xml");
|
||||
Collection<UsageInfo> references = findCodeUsages("stringArray.xml", "res/layout/stringArray.xml");
|
||||
assertEquals(2, references.size());
|
||||
}
|
||||
|
||||
private static Collection<UsageInfo> findElementAtCaret(String fileName, JavaCodeInsightTestFixture fixture, String basePath) throws Throwable {
|
||||
String newFilePath = "res/layout/" + fileName;
|
||||
VirtualFile file = fixture.copyFileToProject(basePath + fileName, newFilePath);
|
||||
return findUsages(file, fixture);
|
||||
private static Collection<UsageInfo> findUsages(String fileName, final JavaCodeInsightTestFixture fixture, String newFilePath)
|
||||
throws Throwable {
|
||||
VirtualFile file = fixture.copyFileToProject(BASE_PATH + fileName, newFilePath);
|
||||
fixture.configureFromExistingVirtualFile(file);
|
||||
|
||||
final UsageTarget[] targets = UsageTargetUtil.findUsageTargets(new DataProvider() {
|
||||
@Override
|
||||
public Object getData(@NonNls String dataId) {
|
||||
return ((EditorEx)fixture.getEditor()).getDataContext().getData(dataId);
|
||||
}
|
||||
});
|
||||
|
||||
assert targets != null && targets.length > 0 && targets[0] instanceof PsiElementUsageTarget;
|
||||
return fixture.findUsages(((PsiElementUsageTarget)targets[0]).getElement());
|
||||
}
|
||||
|
||||
public static Collection<UsageInfo> findUsages(VirtualFile file, JavaCodeInsightTestFixture fixture) throws Exception {
|
||||
|
||||
@@ -18,8 +18,10 @@ package org.jetbrains.android;
|
||||
|
||||
import com.android.sdklib.SdkConstants;
|
||||
import com.intellij.codeInsight.TargetElementUtilBase;
|
||||
import com.intellij.openapi.actionSystem.DataContext;
|
||||
import com.intellij.openapi.command.WriteCommandAction;
|
||||
import com.intellij.openapi.editor.Editor;
|
||||
import com.intellij.openapi.editor.ex.EditorEx;
|
||||
import com.intellij.openapi.fileEditor.FileDocumentManager;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.*;
|
||||
@@ -28,8 +30,10 @@ import com.intellij.psi.search.GlobalSearchScope;
|
||||
import com.intellij.refactoring.PackageWrapper;
|
||||
import com.intellij.refactoring.move.moveClassesOrPackages.MoveClassesOrPackagesProcessor;
|
||||
import com.intellij.refactoring.move.moveClassesOrPackages.SingleSourceRootMoveDestination;
|
||||
import com.intellij.refactoring.rename.RenameProcessor;
|
||||
import com.intellij.refactoring.rename.RenamePsiElementProcessor;
|
||||
import com.intellij.refactoring.rename.*;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
/**
|
||||
* Created by IntelliJ IDEA.
|
||||
@@ -132,6 +136,53 @@ public class AndroidRenameTest extends AndroidTestCase {
|
||||
myFixture.checkResultByFile("res/values/strings.xml", BASE_PATH + "strings_after.xml", true);
|
||||
}
|
||||
|
||||
public void testValueResource1() throws Throwable {
|
||||
doTestStringRename("strings1.xml");
|
||||
}
|
||||
|
||||
public void testValueResource2() throws Throwable {
|
||||
doTestStringRename("strings2.xml");
|
||||
}
|
||||
|
||||
public void testValueResource3() throws Throwable {
|
||||
doTestStringRename("strings3.xml");
|
||||
}
|
||||
|
||||
public void testValueResource4() throws Throwable {
|
||||
doTestStringRename("strings4.xml");
|
||||
}
|
||||
|
||||
private void doTestStringRename(String fileName) throws IOException {
|
||||
createManifest();
|
||||
VirtualFile file = myFixture.copyFileToProject(BASE_PATH + fileName, "res/values/strings.xml");
|
||||
myFixture.configureFromExistingVirtualFile(file);
|
||||
|
||||
myFixture.copyFileToProject(BASE_PATH + "layoutStrUsage.xml", "res/layout/layoutStrUsage.xml");
|
||||
myFixture.copyFileToProject(BASE_PATH + "R2.java", R_JAVA_PATH);
|
||||
|
||||
findHandlerAndDoRename();
|
||||
|
||||
myFixture.checkResultByFile(BASE_PATH + "strings_after.xml");
|
||||
myFixture.checkResultByFile(R_JAVA_PATH, BASE_PATH + "R_value_after.java", true);
|
||||
myFixture.checkResultByFile("res/layout/layoutStrUsage.xml", BASE_PATH + "layoutStrUsage_after.xml", true);
|
||||
}
|
||||
|
||||
private void findHandlerAndDoRename() throws IOException {
|
||||
final DataContext editorContext = ((EditorEx)myFixture.getEditor()).getDataContext();
|
||||
final DataContext context = new DataContext() {
|
||||
@Override
|
||||
public Object getData(@NonNls String dataId) {
|
||||
return PsiElementRenameHandler.DEFAULT_NAME.getName().equals(dataId)
|
||||
? "str1"
|
||||
: editorContext.getData(dataId);
|
||||
}
|
||||
};
|
||||
final RenameHandler renameHandler = RenameHandlerRegistry.getInstance().getRenameHandler(context);
|
||||
assertNotNull(renameHandler);
|
||||
|
||||
renameHandler.invoke(myFixture.getProject(), myFixture.getEditor(), myFixture.getFile(), context);
|
||||
}
|
||||
|
||||
public void testJavaReferenceToFileResource() throws Throwable {
|
||||
createManifest();
|
||||
VirtualFile file = myFixture.copyFileToProject(BASE_PATH + "R3.java", R_JAVA_PATH);
|
||||
|
||||
@@ -37,7 +37,7 @@
|
||||
</group>
|
||||
|
||||
<group id="GitRepositoryActions">
|
||||
<action id="Git.Branches" class="git4idea.ui.branch.GitBranchesAction" text="_Branches"/>
|
||||
<action id="Git.Branches" class="git4idea.ui.branch.GitBranchesAction" text="_Branches" icon="/icons/branch.png"/>
|
||||
<separator/>
|
||||
|
||||
<action id="Git.Tag" class="git4idea.actions.GitTag" text="Tag Files..."/>
|
||||
|
||||
@@ -34,6 +34,7 @@ import com.intellij.util.Function;
|
||||
import com.intellij.util.ui.UIUtil;
|
||||
import git4idea.*;
|
||||
import git4idea.commands.GitMessageWithFilesDetector;
|
||||
import git4idea.config.GitVcsSettings;
|
||||
import git4idea.merge.GitConflictResolver;
|
||||
import git4idea.repo.GitRepository;
|
||||
import git4idea.util.UntrackedFilesNotifier;
|
||||
@@ -59,18 +60,22 @@ abstract class GitBranchOperation {
|
||||
|
||||
@NotNull protected final Project myProject;
|
||||
@NotNull private final Collection<GitRepository> myRepositories;
|
||||
@NotNull private final String myCurrentBranchOrRev;
|
||||
@NotNull private final ProgressIndicator myIndicator;
|
||||
private final GitVcsSettings mySettings;
|
||||
|
||||
@NotNull private final Collection<GitRepository> mySuccessfulRepositories;
|
||||
@NotNull private final Collection<GitRepository> myRemainingRepositories;
|
||||
|
||||
protected GitBranchOperation(@NotNull Project project, @NotNull Collection<GitRepository> repositories,
|
||||
@NotNull ProgressIndicator indicator) {
|
||||
@NotNull String currentBranchOrRev, @NotNull ProgressIndicator indicator) {
|
||||
myProject = project;
|
||||
myRepositories = repositories;
|
||||
myCurrentBranchOrRev = currentBranchOrRev;
|
||||
myIndicator = indicator;
|
||||
mySuccessfulRepositories = new ArrayList<GitRepository>();
|
||||
myRemainingRepositories = new ArrayList<GitRepository>(myRepositories);
|
||||
mySettings = GitVcsSettings.getInstance(myProject);
|
||||
}
|
||||
|
||||
protected abstract void execute();
|
||||
@@ -159,7 +164,7 @@ abstract class GitBranchOperation {
|
||||
NotificationManager.getInstance(myProject).notify(GitVcs.NOTIFICATION_GROUP_ID, "", message, NotificationType.INFORMATION);
|
||||
}
|
||||
|
||||
protected void notifySuccess() {
|
||||
protected final void notifySuccess() {
|
||||
notifySuccess(getSuccessMessage());
|
||||
}
|
||||
|
||||
@@ -242,6 +247,20 @@ abstract class GitBranchOperation {
|
||||
return pluralize("repository", getSuccessfulRepositories().size());
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates the recently visited branch in the settings.
|
||||
* This is to be performed after successful checkout operation.
|
||||
*/
|
||||
protected void updateRecentBranch() {
|
||||
if (getRepositories().size() == 1) {
|
||||
GitRepository repository = myRepositories.iterator().next();
|
||||
mySettings.setRecentBranchOfRepository(repository.getRoot().getPath(), myCurrentBranchOrRev);
|
||||
}
|
||||
else {
|
||||
mySettings.setRecentCommonBranch(myCurrentBranchOrRev);
|
||||
}
|
||||
}
|
||||
|
||||
private void showUnmergedFilesDialogWithRollback() {
|
||||
final AtomicBoolean ok = new AtomicBoolean();
|
||||
UIUtil.invokeAndWaitIfNeeded(new Runnable() {
|
||||
|
||||
@@ -81,7 +81,7 @@ public final class GitBranchOperationsProcessor {
|
||||
}
|
||||
|
||||
@NotNull
|
||||
private String getCurrentBranch() {
|
||||
private String getCurrentBranchOrRev() {
|
||||
if (myRepositories.size() > 1) {
|
||||
GitMultiRootBranchConfig multiRootBranchConfig = new GitMultiRootBranchConfig(myRepositories);
|
||||
String currentBranch = multiRootBranchConfig.getCurrentBranch();
|
||||
@@ -121,7 +121,7 @@ public final class GitBranchOperationsProcessor {
|
||||
}
|
||||
|
||||
private void doCheckoutNewBranch(@NotNull final String name, @NotNull ProgressIndicator indicator) {
|
||||
new GitCheckoutNewBranchOperation(myProject, myRepositories, name, getCurrentBranch(), indicator).execute();
|
||||
new GitCheckoutNewBranchOperation(myProject, myRepositories, name, getCurrentBranchOrRev(), indicator).execute();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -162,7 +162,7 @@ public final class GitBranchOperationsProcessor {
|
||||
}
|
||||
|
||||
private void doCheckout(@NotNull ProgressIndicator indicator, @NotNull String reference, @Nullable String newBranch) {
|
||||
new GitCheckoutOperation(myProject, myRepositories, reference, newBranch, getCurrentBranch(), indicator).execute();
|
||||
new GitCheckoutOperation(myProject, myRepositories, reference, newBranch, getCurrentBranchOrRev(), indicator).execute();
|
||||
}
|
||||
|
||||
public void deleteBranch(final String branchName) {
|
||||
@@ -174,7 +174,7 @@ public final class GitBranchOperationsProcessor {
|
||||
}
|
||||
|
||||
private void doDelete(final String branchName, ProgressIndicator indicator) {
|
||||
new GitDeleteBranchOperation(myProject, myRepositories, branchName, getCurrentBranch(), indicator).execute();
|
||||
new GitDeleteBranchOperation(myProject, myRepositories, branchName, getCurrentBranchOrRev(), indicator).execute();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -197,7 +197,7 @@ public final class GitBranchOperationsProcessor {
|
||||
LOG.error("The task to get compare info didn't finish. Repositories: \n" + myRepositories + "\nbranch name: " + branchName);
|
||||
return;
|
||||
}
|
||||
displayCompareDialog(branchName, getCurrentBranch(), myCompareInfo);
|
||||
displayCompareDialog(branchName, getCurrentBranchOrRev(), myCompareInfo);
|
||||
}
|
||||
}.runInBackground();
|
||||
}
|
||||
@@ -247,7 +247,7 @@ public final class GitBranchOperationsProcessor {
|
||||
for (GitRepository repository : myRepositories) {
|
||||
revisions.put(repository, repository.getCurrentRevision());
|
||||
}
|
||||
new GitMergeOperation(myProject, myRepositories, branchName, getCurrentBranch(), revisions, indicator).execute();
|
||||
new GitMergeOperation(myProject, myRepositories, branchName, getCurrentBranchOrRev(), mySelectedRepository, revisions, indicator).execute();
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -44,9 +44,8 @@ class GitCheckoutNewBranchOperation extends GitBranchOperation {
|
||||
@NotNull private final String myPreviousBranch;
|
||||
|
||||
GitCheckoutNewBranchOperation(@NotNull Project project, @NotNull Collection<GitRepository> repositories,
|
||||
@NotNull String newBranchName, @NotNull String previousBranch,
|
||||
@NotNull ProgressIndicator indicator) {
|
||||
super(project, repositories, indicator);
|
||||
@NotNull String newBranchName, @NotNull String previousBranch, @NotNull ProgressIndicator indicator) {
|
||||
super(project, repositories, previousBranch, indicator);
|
||||
myNewBranchName = newBranchName;
|
||||
myProject = project;
|
||||
myPreviousBranch = previousBranch;
|
||||
@@ -77,6 +76,7 @@ class GitCheckoutNewBranchOperation extends GitBranchOperation {
|
||||
|
||||
if (!fatalErrorHappened) {
|
||||
notifySuccess();
|
||||
updateRecentBranch();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -59,7 +59,7 @@ class GitCheckoutOperation extends GitBranchOperation {
|
||||
GitCheckoutOperation(@NotNull Project project, @NotNull Collection<GitRepository> repositories,
|
||||
@NotNull String startPointReference, @Nullable String newBranch, @NotNull String previousBranch,
|
||||
@NotNull ProgressIndicator indicator) {
|
||||
super(project, repositories, indicator);
|
||||
super(project, repositories, previousBranch, indicator);
|
||||
myStartPointReference = startPointReference;
|
||||
myNewBranch = newBranch;
|
||||
myPreviousBranch = previousBranch;
|
||||
@@ -104,10 +104,11 @@ class GitCheckoutOperation extends GitBranchOperation {
|
||||
|
||||
if (!fatalErrorHappened) {
|
||||
notifySuccess();
|
||||
updateRecentBranch();
|
||||
}
|
||||
}
|
||||
|
||||
private boolean smartCheckoutOrNotify(@NotNull GitRepository repository,
|
||||
private boolean smartCheckoutOrNotify(@NotNull GitRepository repository,
|
||||
@NotNull GitMessageWithFilesDetector localChangesOverwrittenByCheckout) {
|
||||
Pair<List<GitRepository>, List<Change>> conflictingRepositoriesAndAffectedChanges =
|
||||
getConflictingRepositoriesAndAffectedChanges(repository, localChangesOverwrittenByCheckout, myPreviousBranch, myStartPointReference);
|
||||
|
||||
@@ -53,8 +53,8 @@ class GitDeleteBranchOperation extends GitBranchOperation {
|
||||
private final String myCurrentBranch;
|
||||
|
||||
GitDeleteBranchOperation(@NotNull Project project, @NotNull Collection<GitRepository> repositories,
|
||||
@NotNull String branchName, @NotNull String currentBranch, @NotNull ProgressIndicator indicator) {
|
||||
super(project, repositories, indicator);
|
||||
@NotNull String branchName, @NotNull String currentBranch, @NotNull ProgressIndicator indicator) {
|
||||
super(project, repositories, currentBranch, indicator);
|
||||
myBranchName = branchName;
|
||||
myCurrentBranch = currentBranch;
|
||||
}
|
||||
|
||||
@@ -15,6 +15,8 @@
|
||||
*/
|
||||
package git4idea.branch;
|
||||
|
||||
import com.intellij.notification.Notification;
|
||||
import com.intellij.notification.NotificationListener;
|
||||
import com.intellij.notification.NotificationType;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.progress.ProgressIndicator;
|
||||
@@ -35,6 +37,7 @@ import git4idea.repo.GitRepository;
|
||||
import git4idea.util.GitPreservingProcess;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import javax.swing.event.HyperlinkEvent;
|
||||
import java.util.*;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
|
||||
@@ -52,6 +55,7 @@ class GitMergeOperation extends GitBranchOperation {
|
||||
@NotNull private final ChangeListManager myChangeListManager;
|
||||
@NotNull private final String myBranchToMerge;
|
||||
@NotNull private final String myCurrentBranch;
|
||||
@NotNull private final GitRepository myCurrentRepository;
|
||||
@NotNull private final Map<GitRepository, String> myCurrentRevisionsBeforeMerge;
|
||||
|
||||
// true in value if unstash will be needed after resolving conflicts.
|
||||
@@ -59,13 +63,13 @@ class GitMergeOperation extends GitBranchOperation {
|
||||
private GitPreservingProcess myPreservingProcess;
|
||||
|
||||
protected GitMergeOperation(@NotNull Project project, @NotNull Collection<GitRepository> repositories,
|
||||
@NotNull String branchToMerge,
|
||||
@NotNull String currentBranch,
|
||||
@NotNull String branchToMerge, @NotNull String currentBranch, @NotNull GitRepository currentRepository,
|
||||
@NotNull Map<GitRepository, String> currentRevisionsBeforeMerge,
|
||||
@NotNull ProgressIndicator indicator) {
|
||||
super(project, repositories, indicator);
|
||||
super(project, repositories, currentBranch, indicator);
|
||||
myBranchToMerge = branchToMerge;
|
||||
myCurrentBranch = currentBranch;
|
||||
myCurrentRepository = currentRepository;
|
||||
myCurrentRevisionsBeforeMerge = currentRevisionsBeforeMerge;
|
||||
myChangeListManager = ChangeListManager.getInstance(myProject);
|
||||
}
|
||||
@@ -126,13 +130,28 @@ class GitMergeOperation extends GitBranchOperation {
|
||||
notifySuccess();
|
||||
}
|
||||
else {
|
||||
notifySuccess("Already up-to-date.");
|
||||
notifySuccess("Already up-to-date");
|
||||
}
|
||||
}
|
||||
|
||||
restoreLocalChanges();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void notifySuccess(@NotNull String message) {
|
||||
String description = message + "<br/><a href='delete'>Delete " + myBranchToMerge + "</a>";
|
||||
NotificationManager.getInstance(myProject).notify(GitVcs.NOTIFICATION_GROUP_ID, "", description, NotificationType.INFORMATION,
|
||||
new NotificationListener() {
|
||||
@Override
|
||||
public void hyperlinkUpdate(@NotNull Notification notification, @NotNull HyperlinkEvent event) {
|
||||
if (event.getEventType() == HyperlinkEvent.EventType.ACTIVATED && event.getDescription().equalsIgnoreCase("delete")) {
|
||||
new GitBranchOperationsProcessor(myProject, new ArrayList<GitRepository>(getRepositories()), myCurrentRepository).
|
||||
deleteBranch(myBranchToMerge);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private boolean resolveConflicts() {
|
||||
if (!myConflictedRepositories.isEmpty()) {
|
||||
GitMerger merger = new GitMerger(myProject);
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2000-2011 JetBrains s.r.o.
|
||||
* Copyright 2000-2012 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.
|
||||
@@ -17,7 +17,6 @@ package git4idea.branch;
|
||||
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.DialogWrapper;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.openapi.vcs.changes.Change;
|
||||
import com.intellij.openapi.vcs.changes.ui.ChangesBrowser;
|
||||
import com.intellij.ui.IdeBorderFactory;
|
||||
@@ -31,6 +30,8 @@ import java.awt.event.ActionEvent;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.atomic.AtomicInteger;
|
||||
|
||||
import static com.intellij.openapi.util.text.StringUtil.capitalize;
|
||||
|
||||
/**
|
||||
* The dialog that is shown when the error
|
||||
* "Your local changes to the following files would be overwritten by merge/checkout"
|
||||
@@ -46,7 +47,7 @@ class GitSmartOperationDialog extends DialogWrapper {
|
||||
|
||||
private final Project myProject;
|
||||
private final List<Change> myChanges;
|
||||
@NotNull private final String myCapitalizedOperationTitle;
|
||||
@NotNull private final String myOperationTitle;
|
||||
private final boolean myForceButton;
|
||||
|
||||
/**
|
||||
@@ -71,10 +72,10 @@ class GitSmartOperationDialog extends DialogWrapper {
|
||||
super(project);
|
||||
myProject = project;
|
||||
myChanges = changes;
|
||||
myCapitalizedOperationTitle = StringUtil.capitalize(operationTitle);
|
||||
myOperationTitle = operationTitle;
|
||||
myForceButton = forceButton;
|
||||
setOKButtonText("Smart " + myCapitalizedOperationTitle);
|
||||
setCancelButtonText("Don't " + myCapitalizedOperationTitle);
|
||||
setOKButtonText("Smart " + capitalize(myOperationTitle));
|
||||
setCancelButtonText("Don't " + capitalize(myOperationTitle));
|
||||
getCancelAction().putValue(FOCUSED_ACTION, Boolean.TRUE);
|
||||
init();
|
||||
}
|
||||
@@ -82,15 +83,15 @@ class GitSmartOperationDialog extends DialogWrapper {
|
||||
@Override
|
||||
protected Action[] createLeftSideActions() {
|
||||
if (myForceButton) {
|
||||
return new Action[] {new ForceCheckoutAction(myCapitalizedOperationTitle) };
|
||||
return new Action[] {new ForceCheckoutAction(myOperationTitle) };
|
||||
}
|
||||
return new Action[0];
|
||||
}
|
||||
|
||||
@Override
|
||||
protected JComponent createNorthPanel() {
|
||||
JBLabel description = new JBLabel("<html>Your local changes to the following files would be overwritten by checkout.<br/>" +
|
||||
"IDEA can stash the changes, checkout and unstash them after that.</html>");
|
||||
JBLabel description = new JBLabel("<html>Your local changes to the following files would be overwritten by " + myOperationTitle +
|
||||
".<br/>IDEA can stash the changes, " + myOperationTitle + " and unstash them after that.</html>");
|
||||
description.setBorder(IdeBorderFactory.createEmptyBorder(0, 0, 10, 0));
|
||||
return description;
|
||||
}
|
||||
@@ -112,7 +113,7 @@ class GitSmartOperationDialog extends DialogWrapper {
|
||||
private class ForceCheckoutAction extends AbstractAction {
|
||||
|
||||
ForceCheckoutAction(@NotNull String operationTitle) {
|
||||
super("Force " + operationTitle);
|
||||
super("&Force " + capitalize(operationTitle));
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -26,7 +26,9 @@ import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Git VCS settings
|
||||
@@ -70,6 +72,8 @@ public class GitVcsSettings implements PersistentStateComponent<GitVcsSettings.S
|
||||
public boolean PUSH_AUTO_UPDATE = false;
|
||||
public GitBranchSyncSetting SYNC_SETTING = GitBranchSyncSetting.NOT_DECIDED;
|
||||
public String RECENT_GIT_ROOT_PATH = null;
|
||||
public Map<String, String> RECENT_BRANCH_BY_REPOSITORY = new HashMap<String, String>();
|
||||
public String RECENT_COMMON_BRANCH = null;
|
||||
}
|
||||
|
||||
public GitVcsSettings(GitVcsApplicationSettings appSettings) {
|
||||
@@ -80,11 +84,7 @@ public class GitVcsSettings implements PersistentStateComponent<GitVcsSettings.S
|
||||
return myAppSettings;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static GitVcsSettings getInstance(Project project) {
|
||||
if (project == null || project.isDisposed()) {
|
||||
return null;
|
||||
}
|
||||
return PeriodicalTasksCloser.getInstance().safeGetService(project, GitVcsSettings.class);
|
||||
}
|
||||
|
||||
@@ -172,4 +172,22 @@ public class GitVcsSettings implements PersistentStateComponent<GitVcsSettings.S
|
||||
myState.RECENT_GIT_ROOT_PATH = recentGitRootPath;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public Map<String, String> getRecentBranchesByRepository() {
|
||||
return myState.RECENT_BRANCH_BY_REPOSITORY;
|
||||
}
|
||||
|
||||
public void setRecentBranchOfRepository(@NotNull String repositoryPath, @NotNull String branch) {
|
||||
myState.RECENT_BRANCH_BY_REPOSITORY.put(repositoryPath, branch);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public String getRecentCommonBranch() {
|
||||
return myState.RECENT_COMMON_BRANCH;
|
||||
}
|
||||
|
||||
public void setRecentCommonBranch(@NotNull String branch) {
|
||||
myState.RECENT_COMMON_BRANCH = branch;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -51,6 +51,11 @@ public abstract class GitChangesSaver {
|
||||
|
||||
protected GitConflictResolver.Params myParams;
|
||||
|
||||
/**
|
||||
* Refreshes files changed during save or load.
|
||||
*/
|
||||
public abstract void refresh();
|
||||
|
||||
/**
|
||||
* Returns an instance of the proper GitChangesSaver depending on the chosen save changes policy.
|
||||
* @return {@link GitStashChangesSaver}, {@link GitShelveChangesSaver} or {@link GitDumbChangesSaver}
|
||||
|
||||
@@ -89,11 +89,19 @@ public class GitShelveChangesSaver extends GitChangesSaver {
|
||||
return myShelvedChangeList != null;
|
||||
}
|
||||
|
||||
@Override public String getSaverName() {
|
||||
@Override
|
||||
public String getSaverName() {
|
||||
return "shelf";
|
||||
}
|
||||
|
||||
@Override protected void showSavedChanges() {
|
||||
@Override
|
||||
protected void showSavedChanges() {
|
||||
myShelveViewManager.activateView(myShelvedChangeList);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void refresh() {
|
||||
// refreshed inside shelve manager
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -35,8 +35,8 @@ import git4idea.commands.*;
|
||||
import git4idea.config.GitVcsSettings;
|
||||
import git4idea.convert.GitFileSeparatorConverter;
|
||||
import git4idea.merge.GitConflictResolver;
|
||||
import git4idea.util.GitUIUtil;
|
||||
import git4idea.ui.GitUnstashDialog;
|
||||
import git4idea.util.GitUIUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
@@ -77,11 +77,21 @@ public class GitStashChangesSaver extends GitChangesSaver {
|
||||
}
|
||||
|
||||
public void load() throws VcsException {
|
||||
Collection<VirtualFile> conflictedRoots = new ArrayList<VirtualFile>();
|
||||
for (VirtualFile root : myStashedRoots) {
|
||||
loadRoot(root);
|
||||
boolean conflict = loadRoot(root);
|
||||
if (conflict) {
|
||||
conflictedRoots.add(root);
|
||||
}
|
||||
}
|
||||
|
||||
boolean conflictsResolved = new UnstashConflictResolver(myProject, myStashedRoots, myParams).merge();
|
||||
if (conflictsResolved) {
|
||||
LOG.info("load: all conflicts resolved, dropping stash in " + myStashedRoots);
|
||||
for (VirtualFile root : conflictedRoots) {
|
||||
GitStashUtils.dropStash(myProject, root);
|
||||
}
|
||||
}
|
||||
// we'll refresh more but this way we needn't compute what files under roots etc
|
||||
LocalFileSystem.getInstance().refreshIoFiles(myChangeManager.getAffectedPaths());
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -89,14 +99,22 @@ public class GitStashChangesSaver extends GitChangesSaver {
|
||||
return !myStashedRoots.isEmpty();
|
||||
}
|
||||
|
||||
@Override public String getSaverName() {
|
||||
@Override
|
||||
public String getSaverName() {
|
||||
return "stash";
|
||||
}
|
||||
|
||||
@Override protected void showSavedChanges() {
|
||||
@Override
|
||||
protected void showSavedChanges() {
|
||||
GitUnstashDialog.showUnstashDialog(myProject, new ArrayList<VirtualFile>(myStashedRoots), myStashedRoots.iterator().next(), new HashSet<VirtualFile>());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void refresh() {
|
||||
// we'll refresh more but this way we needn't compute what files under roots etc
|
||||
LocalFileSystem.getInstance().refreshIoFiles(myChangeManager.getAffectedPaths());
|
||||
}
|
||||
|
||||
private void stash(Collection<VirtualFile> roots) throws VcsException {
|
||||
for (VirtualFile root : roots) {
|
||||
final String message = GitHandlerUtil.formatOperationName("Stashing changes from", root);
|
||||
@@ -122,7 +140,11 @@ public class GitStashChangesSaver extends GitChangesSaver {
|
||||
}
|
||||
}
|
||||
|
||||
private void loadRoot(final VirtualFile root) throws VcsException {
|
||||
/**
|
||||
* Returns true if the root was loaded with conflict.
|
||||
* False is returned in all other cases: in the case of success and in case of some other error.
|
||||
*/
|
||||
private boolean loadRoot(final VirtualFile root) throws VcsException {
|
||||
LOG.info("loadRoot " + root);
|
||||
myProgressIndicator.setText(GitHandlerUtil.formatOperationName("Unstashing changes to", root));
|
||||
final GitLineHandler handler = new GitLineHandler(myProject, root, GitCommand.STASH);
|
||||
@@ -159,26 +181,21 @@ public class GitStashChangesSaver extends GitChangesSaver {
|
||||
|
||||
if (failure.get()) {
|
||||
if (conflict.get()) {
|
||||
boolean conflictsResolved = new UnstashConflictResolver(myProject, root, myStashedRoots, myParams).merge();
|
||||
if (conflictsResolved) {
|
||||
LOG.info("loadRoot " + root + " conflicts resolved, dropping stash");
|
||||
GitStashUtils.dropStash(myProject, root);
|
||||
}
|
||||
return true;
|
||||
} else {
|
||||
LOG.info("unstash failed " + handler.errors());
|
||||
GitUIUtil.notifyImportantError(myProject, "Couldn't unstash", "<br/>" + GitUIUtil.stringifyErrors(handler.errors()));
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private static class UnstashConflictResolver extends GitConflictResolver {
|
||||
|
||||
private final VirtualFile myRoot;
|
||||
private final Set<VirtualFile> myStashedRoots;
|
||||
|
||||
public UnstashConflictResolver(@NotNull Project project, @NotNull VirtualFile root, @NotNull Set<VirtualFile> stashedRoots, @Nullable Params params) {
|
||||
super(project, Collections.singleton(root), makeParamsOrUse(params));
|
||||
myRoot = root;
|
||||
public UnstashConflictResolver(@NotNull Project project, @NotNull Set<VirtualFile> stashedRoots, @Nullable Params params) {
|
||||
super(project, stashedRoots, makeParamsOrUse(params));
|
||||
myStashedRoots = stashedRoots;
|
||||
}
|
||||
|
||||
@@ -206,7 +223,7 @@ public class GitStashChangesSaver extends GitChangesSaver {
|
||||
if (event.getEventType() == HyperlinkEvent.EventType.ACTIVATED) {
|
||||
if (event.getDescription().equals("saver")) {
|
||||
// we don't use #showSavedChanges to specify unmerged root first
|
||||
GitUnstashDialog.showUnstashDialog(myProject, new ArrayList<VirtualFile>(myStashedRoots), myRoot,
|
||||
GitUnstashDialog.showUnstashDialog(myProject, new ArrayList<VirtualFile>(myStashedRoots), myStashedRoots.iterator().next(),
|
||||
new HashSet<VirtualFile>());
|
||||
} else if (event.getDescription().equals("resolve")) {
|
||||
mergeNoProceed();
|
||||
|
||||
@@ -27,6 +27,7 @@ import com.intellij.openapi.options.ShowSettingsUtil;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.popup.ListPopup;
|
||||
import com.intellij.openapi.ui.popup.PopupStep;
|
||||
import com.intellij.openapi.util.Condition;
|
||||
import com.intellij.openapi.util.IconLoader;
|
||||
import com.intellij.ui.popup.PopupFactoryImpl;
|
||||
import com.intellij.ui.popup.WizardPopup;
|
||||
@@ -88,10 +89,33 @@ class GitBranchPopup {
|
||||
|
||||
String title = createPopupTitle(currentRepository);
|
||||
|
||||
Condition<AnAction> preselectActionCondition = new Condition<AnAction>() {
|
||||
@Override
|
||||
public boolean value(AnAction action) {
|
||||
if (action instanceof GitBranchPopupActions.LocalBranchActions) {
|
||||
GitBranchPopupActions.LocalBranchActions branchAction = (GitBranchPopupActions.LocalBranchActions)action;
|
||||
String branchName = branchAction.getBranchName();
|
||||
|
||||
String recentBranch;
|
||||
List<GitRepository> repositories = branchAction.getRepositories();
|
||||
if (repositories.size() == 1) {
|
||||
recentBranch = myVcsSettings.getRecentBranchesByRepository().get(repositories.iterator().next().getRoot().getPath());
|
||||
}
|
||||
else {
|
||||
recentBranch = myVcsSettings.getRecentCommonBranch();
|
||||
}
|
||||
|
||||
if (recentBranch != null && recentBranch.equals(branchName)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
};
|
||||
myPopup = new PopupFactoryImpl.ActionGroupPopup(
|
||||
title, createActions(),
|
||||
SimpleDataContext.getProjectContext(project),
|
||||
false, false, false, true, null, -1, null, null) {
|
||||
false, false, false, true, null, -1, preselectActionCondition, null) {
|
||||
@Override
|
||||
protected WizardPopup createPopup(WizardPopup parent, PopupStep step, Object parentValue) {
|
||||
WizardPopup popup = super.createPopup(parent, step, parentValue);
|
||||
|
||||
@@ -180,6 +180,16 @@ class GitBranchPopupActions {
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
List<GitRepository> getRepositories() {
|
||||
return myRepositories;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public String getBranchName() {
|
||||
return myBranchName;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public AnAction[] getChildren(@Nullable AnActionEvent e) {
|
||||
|
||||
@@ -215,6 +215,7 @@ public class GitUpdateProcess {
|
||||
final ContinuationFinalTasksInserter finalTasksInserter = new ContinuationFinalTasksInserter(context);
|
||||
finalTasksInserter.allNextAreFinal();
|
||||
mySaver.restoreLocalChanges(context);
|
||||
mySaver.refresh();
|
||||
finalTasksInserter.removeFinalPropertyAdder();
|
||||
}
|
||||
|
||||
|
||||
@@ -492,7 +492,7 @@ public class GitBranchOperationsTest extends AbstractVcsTestCase {
|
||||
public void merge_simple_without_problems() throws Exception {
|
||||
prepareBranchWithCommit("feature", myUltimate, myCommunity, myContrib);
|
||||
doMerge("feature");
|
||||
assertNotify(NotificationType.INFORMATION, "Merged feature to master");
|
||||
assertNotify(NotificationType.INFORMATION, "Merged feature to master<br/>Delete feature");
|
||||
|
||||
assertFile(myUltimate, "unmerged_branch_file", "content");
|
||||
assertFile(myCommunity, "unmerged_branch_file", "content");
|
||||
@@ -514,7 +514,7 @@ public class GitBranchOperationsTest extends AbstractVcsTestCase {
|
||||
|
||||
doMerge("master2");
|
||||
|
||||
assertNotify(NotificationType.INFORMATION, "Already up-to-date.");
|
||||
assertNotify(NotificationType.INFORMATION, "Already up-to-date<br/>Delete master2");
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -525,7 +525,7 @@ public class GitBranchOperationsTest extends AbstractVcsTestCase {
|
||||
|
||||
doMerge("master2");
|
||||
|
||||
assertNotify(NotificationType.INFORMATION, "Merged master2 to master");
|
||||
assertNotify(NotificationType.INFORMATION, "Merged master2 to master<br/>Delete master2");
|
||||
assertFile(myCommunity, "unmerged_branch_file", "content");
|
||||
assertNull(myUltimate.getRoot().findChild("unmerged_branch_file"));
|
||||
}
|
||||
|
||||
+4
-4
@@ -89,14 +89,14 @@ public class SvnChangesCorrectlyRefreshedTest extends SvnTestCase {
|
||||
//ChangeListManagerImpl.DEBUG = true;
|
||||
final SubTree subTree = new SubTree(myWorkingCopyDir);
|
||||
checkin();
|
||||
sleep(1000);
|
||||
sleep(100);
|
||||
|
||||
editFileInCommand(myProject, subTree.myS1File, "new");
|
||||
editFileInCommand(myProject, subTree.myS1File, "new content");
|
||||
|
||||
final CharSequence text1 = LoadTextUtil.loadText(subTree.myS1File);
|
||||
Assert.assertEquals("new", text1.toString());
|
||||
Assert.assertEquals("new content", text1.toString());
|
||||
|
||||
sleep(1000);
|
||||
sleep(100);
|
||||
LocalFileSystem.getInstance().refreshAndFindFileByIoFile(new File(subTree.myS1File.getPath()));
|
||||
VcsDirtyScopeManager.getInstance(myProject).markEverythingDirty();
|
||||
clManager.ensureUpToDate(false);
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
package com.intellij.xml.refactoring;
|
||||
|
||||
import com.intellij.featureStatistics.FeatureUsageTracker;
|
||||
import com.intellij.ide.TitledHandler;
|
||||
import com.intellij.lang.Language;
|
||||
import com.intellij.openapi.actionSystem.DataContext;
|
||||
import com.intellij.openapi.actionSystem.LangDataKeys;
|
||||
@@ -45,7 +46,7 @@ import com.intellij.xml.impl.schema.AnyXmlElementDescriptor;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
public class XmlTagRenameHandler implements RenameHandler {
|
||||
public class XmlTagRenameHandler implements RenameHandler, TitledHandler {
|
||||
private static final Logger LOG = Logger.getInstance("#com.intellij.xml.refactoring.XmlTagRenameHandler");
|
||||
|
||||
|
||||
@@ -74,6 +75,11 @@ public class XmlTagRenameHandler implements RenameHandler {
|
||||
return isAvailableOnDataContext(dataContext);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getActionTitle() {
|
||||
return "Rename XML tag";
|
||||
}
|
||||
|
||||
private static boolean isInplaceRenameAvailable(final Editor editor) {
|
||||
return editor.getSettings().isVariableInplaceRenameEnabled();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user