mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
[java] more fool-proof inner class detection
This commit is contained in:
@@ -60,23 +60,18 @@ public class ClassFileViewProvider extends SingleRootFileViewProvider {
|
||||
|
||||
public static boolean isInnerClass(@NotNull VirtualFile file) {
|
||||
String name = file.getNameWithoutExtension();
|
||||
int index = name.lastIndexOf('$');
|
||||
if (index > 0 && index < name.length() - 1) {
|
||||
String parentName = name.substring(0, index), childName = name.substring(index + 1);
|
||||
if (file.getParent().findChild(parentName + ".class") != null) {
|
||||
return isInnerClass(file, parentName, childName);
|
||||
}
|
||||
}
|
||||
return false;
|
||||
return name.indexOf('$') >= 0 && detectInnerClass(file);
|
||||
}
|
||||
|
||||
private static boolean isInnerClass(VirtualFile file, final String parentName, final String childName) {
|
||||
private static boolean detectInnerClass(VirtualFile file) {
|
||||
Boolean isInner = IS_INNER_CLASS.get(file);
|
||||
if (isInner != null) return isInner;
|
||||
|
||||
final Ref<Boolean> ref = Ref.create(Boolean.FALSE);
|
||||
try {
|
||||
new ClassReader(file.contentsToByteArray(false)).accept(new ClassVisitor(Opcodes.ASM5) {
|
||||
ClassReader reader = new ClassReader(file.contentsToByteArray(false));
|
||||
final String className = reader.getClassName();
|
||||
reader.accept(new ClassVisitor(Opcodes.ASM5) {
|
||||
@Override
|
||||
public void visitOuterClass(String owner, String name, String desc) {
|
||||
ref.set(Boolean.TRUE);
|
||||
@@ -85,8 +80,7 @@ public class ClassFileViewProvider extends SingleRootFileViewProvider {
|
||||
|
||||
@Override
|
||||
public void visitInnerClass(String name, String outer, String inner, int access) {
|
||||
if ((inner == null || childName.equals(inner)) && outer != null && parentName.equals(outer.substring(outer.lastIndexOf('/') + 1)) ||
|
||||
inner == null && outer == null && name.substring(name.lastIndexOf('/') + 1).equals(parentName + '$' + childName)) {
|
||||
if (className.equals(name)) {
|
||||
ref.set(Boolean.TRUE);
|
||||
throw new ProcessCanceledException();
|
||||
}
|
||||
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -0,0 +1,6 @@
|
||||
package pkg
|
||||
|
||||
class Groovy {
|
||||
static class Inner { }
|
||||
Runnable r = { println("I'm runnable") }
|
||||
}
|
||||
@@ -1,3 +1,6 @@
|
||||
package pkg;
|
||||
|
||||
class KindaInner { }
|
||||
class KindaInner {
|
||||
static class RealInner$ { }
|
||||
static class Real$Inner { }
|
||||
}
|
||||
@@ -166,6 +166,10 @@ public class ClsMirrorBuildingTest extends LightIdeaTestCase {
|
||||
assertTrue(isInner("pkg/Nested$Inner1$Inner2"));
|
||||
assertTrue(isInner("pkg/NormalClass$1"));
|
||||
assertTrue(isInner("pkg/LocalClass$1MyRunnable"));
|
||||
assertTrue(isInner("pkg/KindaInner$RealInner$"));
|
||||
assertTrue(isInner("pkg/KindaInner$Real$Inner"));
|
||||
assertTrue(isInner("pkg/Groovy$Inner"));
|
||||
assertTrue(isInner("pkg/Groovy$_closure1"));
|
||||
assertTrue(isInner("weird/ToStringStyle$1"));
|
||||
|
||||
assertFalse(isInner("pkg/KindaInner$Class"));
|
||||
|
||||
Reference in New Issue
Block a user