diff --git a/platform/lang-api/src/com/intellij/psi/codeStyle/CodeStyleSettings.java b/platform/lang-api/src/com/intellij/psi/codeStyle/CodeStyleSettings.java
index d7839337b8f8..37d71ce6f92a 100644
--- a/platform/lang-api/src/com/intellij/psi/codeStyle/CodeStyleSettings.java
+++ b/platform/lang-api/src/com/intellij/psi/codeStyle/CodeStyleSettings.java
@@ -755,7 +755,7 @@ public class CodeStyleSettings extends CommonCodeStyleSettings implements Clonea
* @see FileTypeIndentOptionsProvider
* @see LanguageCodeStyleSettingsProvider
*/
- public IndentOptions getIndentOptions(FileType fileType) {
+ public IndentOptions getIndentOptions(@Nullable FileType fileType) {
IndentOptions indentOptions = getLanguageIndentOptions(fileType);
if (indentOptions != null) return indentOptions;
@@ -771,7 +771,7 @@ public class CodeStyleSettings extends CommonCodeStyleSettings implements Clonea
}
@Nullable
- private IndentOptions getLanguageIndentOptions(FileType fileType) {
+ private IndentOptions getLanguageIndentOptions(@Nullable FileType fileType) {
if (fileType == null || !(fileType instanceof LanguageFileType)) return null;
Language lang = ((LanguageFileType)fileType).getLanguage();
CommonCodeStyleSettings langSettings = getCommonSettings(lang);
diff --git a/platform/platform-impl/src/com/intellij/openapi/editor/actions/DeleteToWordStartAction.java b/platform/platform-impl/src/com/intellij/openapi/editor/actions/DeleteToWordStartAction.java
index 36c139db623e..2003a410c773 100644
--- a/platform/platform-impl/src/com/intellij/openapi/editor/actions/DeleteToWordStartAction.java
+++ b/platform/platform-impl/src/com/intellij/openapi/editor/actions/DeleteToWordStartAction.java
@@ -24,31 +24,110 @@
*/
package com.intellij.openapi.editor.actions;
+import com.intellij.openapi.editor.CaretModel;
import com.intellij.openapi.editor.Document;
import com.intellij.openapi.editor.Editor;
-import com.intellij.openapi.editor.actionSystem.EditorAction;
import com.intellij.openapi.editor.actionSystem.EditorWriteActionHandler;
import com.intellij.openapi.command.CommandProcessor;
import com.intellij.openapi.actionSystem.DataContext;
+import gnu.trove.TIntHashSet;
+import gnu.trove.TIntIntHashMap;
+import org.jetbrains.annotations.NotNull;
public class DeleteToWordStartAction extends TextComponentEditorAction {
+
+ /**
+ * We need to provide special processing for quote symbols.
+ *
+ * Examples:
+ *
+ *
+ * | Text before action call
+ * | Text after action call
+ * |
+ *
+ * | one "two" [caret] |
+ * one [caret] |
+ *
+ *
+ * | one "two[caret]" |
+ * one "[caret]" |
+ *
+ *
+ */
+ private static final TIntHashSet QUOTE_SYMBOLS = new TIntHashSet();
+
+ static {
+ QUOTE_SYMBOLS.add('\'');
+ QUOTE_SYMBOLS.add('\"');
+ }
+
+ private static final int[] QUOTE_SYMBOLS_ARRAY = QUOTE_SYMBOLS.toArray();
+
public DeleteToWordStartAction() {
super(new Handler());
}
private static class Handler extends EditorWriteActionHandler {
+
+ @NotNull private final TIntIntHashMap myQuotesNumber = new TIntIntHashMap();
+
@Override
public void executeWriteAction(Editor editor, DataContext dataContext) {
CommandProcessor.getInstance().setCurrentCommandGroupId(EditorActionUtil.DELETE_COMMAND_GROUP);
deleteToWordStart(editor);
}
+
+ private void deleteToWordStart(Editor editor) {
+ CharSequence text = editor.getDocument().getCharsSequence();
+ CaretModel caretModel = editor.getCaretModel();
+ int endOffset = caretModel.getOffset();
+ int minOffset = editor.getDocument().getLineStartOffset(caretModel.getLogicalPosition().line);
+
+ myQuotesNumber.clear();
+ for (int i : QUOTE_SYMBOLS_ARRAY) {
+ myQuotesNumber.put(i, 0);
+ }
+ countQuotes(myQuotesNumber, text, minOffset, endOffset);
+
+ EditorActionUtil.moveCaretToPreviousWord(editor, false);
+
+ for (int offset = caretModel.getOffset(); offset > minOffset; offset = caretModel.getOffset()) {
+ char previous = text.charAt(offset - 1);
+ char current = text.charAt(offset);
+ if (QUOTE_SYMBOLS.contains(current)) {
+ if (Character.isWhitespace(previous)) {
+ break;
+ }
+ if (myQuotesNumber.get(current) % 2 == 0) {
+ // Was 'one "two" [caret]', now 'one "two[caret]"', we want to get 'one [caret]"two"'
+ EditorActionUtil.moveCaretToPreviousWord(editor, false);
+ continue;
+ }
+ break;
+ }
+
+ if (QUOTE_SYMBOLS.contains(previous)) {
+ if (myQuotesNumber.get(previous) % 2 == 0) {
+ // Was 'one "two[caret]", now 'one "[caret]two"', we want 'one [caret]"two"'
+ editor.getCaretModel().moveToOffset(offset - 1);
+ }
+ }
+ break;
+ }
+
+ int startOffset = caretModel.getOffset();
+ Document document = editor.getDocument();
+ document.deleteString(startOffset, endOffset);
+ }
}
- private static void deleteToWordStart(Editor editor) {
- int endOffset = editor.getCaretModel().getOffset();
- EditorActionUtil.moveCaretToPreviousWord(editor, false);
- int startOffset = editor.getCaretModel().getOffset();
- Document document = editor.getDocument();
- document.deleteString(startOffset, endOffset);
+ private static void countQuotes(@NotNull TIntIntHashMap holder, @NotNull CharSequence text, int start, int end) {
+ for (int i = end - 1; i >= start; i--) {
+ char c = text.charAt(i);
+ if (holder.containsKey(c)) {
+ holder.put(c, holder.get(c) + 1);
+ }
+ }
}
}
diff --git a/platform/platform-impl/src/com/intellij/openapi/editor/actions/EditorActionUtil.java b/platform/platform-impl/src/com/intellij/openapi/editor/actions/EditorActionUtil.java
index a7a047627dea..b01d2bef3d8d 100644
--- a/platform/platform-impl/src/com/intellij/openapi/editor/actions/EditorActionUtil.java
+++ b/platform/platform-impl/src/com/intellij/openapi/editor/actions/EditorActionUtil.java
@@ -44,7 +44,6 @@ import com.intellij.openapi.util.Pair;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.util.EditorPopupHandler;
-import gnu.trove.TIntHashSet;
import java.awt.*;
import java.awt.event.MouseEvent;
@@ -65,23 +64,16 @@ public class EditorActionUtil {
* expect the caret to be located at the near future.
*/
public static final Key EXPECTED_CARET_OFFSET = Key.create("expectedEditorOffset");
-
- protected static final Object EDIT_COMMAND_GROUP = Key.create("EditGroup");
- public static final Object DELETE_COMMAND_GROUP = Key.create("DeleteGroup");
-
- private static final TIntHashSet SPECIAL_NON_ID_SYMBOLS = new TIntHashSet();
-
- static {
- SPECIAL_NON_ID_SYMBOLS.add('\'');
- SPECIAL_NON_ID_SYMBOLS.add('\"');
- }
+
+ protected static final Object EDIT_COMMAND_GROUP = Key.create("EditGroup");
+ public static final Object DELETE_COMMAND_GROUP = Key.create("DeleteGroup");
private EditorActionUtil() {
}
/**
* Tries to change given editor's viewport position in vertical dimension by the given number of visual lines.
- *
+ *
* @param editor target editor which viewport position should be changed
* @param lineShift defines viewport position's vertical change length
* @param columnShift defines viewport position's horizontal change length
@@ -102,7 +94,7 @@ public class EditorActionUtil {
if (!moveCaret) {
return;
}
-
+
Rectangle viewRectangle = editor.getScrollingModel().getVisibleArea();
int lineNumber = editor.getCaretModel().getVisualPosition().line;
if (viewRectangle != null) {
@@ -228,26 +220,16 @@ public class EditorActionUtil {
final boolean firstIsIdentifierPart = Character.isJavaIdentifierPart(prev);
final boolean secondIsIdentifierPart = Character.isJavaIdentifierPart(current);
- if (!firstIsIdentifierPart && secondIsIdentifierPart && !SPECIAL_NON_ID_SYMBOLS.contains(prev)) {
+ if (!firstIsIdentifierPart && secondIsIdentifierPart) {
return true;
}
if (isCamel && firstIsIdentifierPart && secondIsIdentifierPart && isHumpBound(text, offset, true)) {
return true;
}
-
- if (Character.isWhitespace(current)) {
- return false;
- }
- else if (Character.isWhitespace(prev)) {
- return true;
- }
- else if (SPECIAL_NON_ID_SYMBOLS.contains(current)) {
- return false;
- }
- else {
- return firstIsIdentifierPart && !secondIsIdentifierPart;
- }
+
+ return (Character.isWhitespace(prev) || firstIsIdentifierPart) &&
+ !Character.isWhitespace(current) && !secondIsIdentifierPart;
}
private static boolean isLowerCaseOrDigit(char c) {