[java-typing] fix typing { inside a Java string in switch-case expression adding } outside the string literal

fix IDEA-368266

Merge-request: IJ-MR-156690
Merged-by: Bartek Pacia <bartek.pacia@jetbrains.com>

GitOrigin-RevId: 68b837ddad0bc7e614ee51fa1934e86b13df69b4
This commit is contained in:
Bartek Pacia
2025-03-04 22:19:59 +00:00
committed by intellij-monorepo-bot
parent 911cc27a46
commit 248f36eac8
12 changed files with 119 additions and 1 deletions
@@ -17,6 +17,7 @@ import com.intellij.openapi.util.text.StringUtil;
import com.intellij.psi.*;
import com.intellij.psi.codeStyle.CodeStyleManager;
import com.intellij.psi.impl.source.BasicJavaAstTreeUtil;
import com.intellij.psi.tree.IElementType;
import com.intellij.psi.tree.ParentAwareTokenSet;
import com.intellij.psi.util.PsiTreeUtil;
import com.intellij.util.text.CharArrayUtil;
@@ -129,7 +130,7 @@ public abstract class AbstractBasicJavaTypedHandler extends TypedHandlerDelegate
}
}
if (fileType instanceof JavaFileType && c == '{') {
int offset = editor.getCaretModel().getOffset();
final int offset = editor.getCaretModel().getOffset();
if (offset == 0) {
return Result.CONTINUE;
}
@@ -234,6 +235,12 @@ public abstract class AbstractBasicJavaTypedHandler extends TypedHandlerDelegate
private static boolean afterArrowInCase(@Nullable PsiElement leaf) {
if (leaf == null) return false;
IElementType leafElementType = leaf.getNode().getElementType();
if (leafElementType == JavaTokenType.STRING_LITERAL ||
leafElementType == JavaTokenType.TEXT_BLOCK_LITERAL ||
leafElementType == JavaTokenType.CHARACTER_LITERAL) {
return false;
}
PsiElement prevLeaf = PsiTreeUtil.prevVisibleLeaf(leaf);
if (prevLeaf == null) return false;
if (prevLeaf.getNode().getElementType() != JavaTokenType.ARROW) return false;
@@ -0,0 +1,10 @@
class X {
public static String foo(int bar) {
String path1 = null;
switch (foo) {
case 1 -> path1 = "bar{<caret>";
case 2 -> path1 = "Hello";
}
return path1;
}
}
@@ -0,0 +1,10 @@
class X {
public static String foo(int bar) {
String path1 = null;
switch (foo) {
case 1 -> path1 = "bar<caret>";
case 2 -> path1 = "Hello";
}
return path1;
}
}
@@ -0,0 +1,7 @@
class X {
public static void main(String[] args) {
var a = switch (new Object()){
case Object object -> '{<caret>';
};
}
}
@@ -0,0 +1,7 @@
class X {
public static void main(String[] args) {
var a = switch (new Object()){
case Object object -> '<caret>';
};
}
}
@@ -0,0 +1,7 @@
class X {
public static void main(String[] args) {
var a = switch (new Object()){
case Object object -> "here{<caret>";
};
}
}
@@ -0,0 +1,7 @@
class X {
public static void main(String[] args) {
var a = switch (new Object()){
case Object object -> "here<caret>";
};
}
}
@@ -0,0 +1,9 @@
class X {
public static void main(String[] args) {
var a = switch (new Object()){
case Object object -> """
hello{<caret>
""";
};
}
}
@@ -0,0 +1,9 @@
class X {
public static void main(String[] args) {
var a = switch (new Object()){
case Object object -> """
hello<caret>
""";
};
}
}
@@ -0,0 +1,10 @@
class X {
public static String foo(int bar) {
switch (bar) {
case 10:
return "matched{<caret>";
default:
return "default";
}
}
}
@@ -0,0 +1,10 @@
class X {
public static String foo(int bar) {
switch (bar) {
case 10:
return "matched<caret>";
default:
return "default";
}
}
}
@@ -105,4 +105,29 @@ public class JavaTypingTest extends AbstractBasicJavaTypingTest {
setLanguageLevel(LanguageLevel.JDK_21);
doTest('{');
}
public void testOpenBracesAfterSwitchRuleStatementInStringLiteral() {
setLanguageLevel(LanguageLevel.JDK_21);
doTest('{');
}
public void testOpenBracesAfterSwitchRuleExpressionAssignmentInStringLiteral() {
setLanguageLevel(LanguageLevel.JDK_21);
doTest('{');
}
public void testOpenBracesAfterSwitchRuleExpressionInStringLiteral() {
setLanguageLevel(LanguageLevel.JDK_21);
doTest('{');
}
public void testOpenBracesAfterSwitchRuleExpressionInTextBlockLiteral() {
setLanguageLevel(LanguageLevel.JDK_21);
doTest('{');
}
public void testOpenBracesAfterSwitchRuleExpressionInCharLiteral() {
setLanguageLevel(LanguageLevel.JDK_21);
doTest('{');
}
}