Add ability to open an accessed fields parent class.

This commit is contained in:
Cody 2024-09-12 18:42:35 -06:00
parent 262a408c95
commit afeab95f0b

AI 샘플 코드 생성 중입니다

Loading...
4 changed files with 595 additions and 526 deletions

View File

@ -2,6 +2,9 @@ package the.bytecode.club.bytecodeviewer.gui.components.actions;
import org.fife.ui.rsyntaxtextarea.RSyntaxTextArea;
import org.fife.ui.rsyntaxtextarea.Token;
import org.objectweb.asm.tree.ClassNode;
import the.bytecode.club.bytecodeviewer.BytecodeViewer;
import the.bytecode.club.bytecodeviewer.resources.ResourceContainer;
import the.bytecode.club.bytecodeviewer.resources.classcontainer.ClassFileContainer;
import the.bytecode.club.bytecodeviewer.resources.classcontainer.locations.ClassFieldLocation;
import the.bytecode.club.bytecodeviewer.resources.classcontainer.parser.TokenUtil;
@ -31,7 +34,21 @@ public class GoToAction extends AbstractAction
int column = textArea.getCaretOffsetFromLineStart();
container.fieldMembers.values().forEach(fields -> fields.forEach(field -> {
if (field.line == line && field.columnStart - 1 <= column && field.columnEnd >= column) {
if (field.line == line && field.columnStart - 1 <= column && field.columnEnd >= column)
{
// Open the class that is associated with the field's owner.
if (!field.owner.equals(container.getName()))
{
ResourceContainer resourceContainer = BytecodeViewer.getFileContainer(container.getParentContainer());
if (resourceContainer != null)
{
String s = container.getImport(field.owner);
BytecodeViewer.viewer.workPane.addClassResource(resourceContainer, s + ".class");
}
return;
}
Element root = textArea.getDocument().getDefaultRootElement();
ClassFieldLocation first = fields.get(0);
int startOffset = root.getElement(first.line - 1).getStartOffset() + (first.columnStart - 1);
@ -40,15 +57,19 @@ public class GoToAction extends AbstractAction
}));
container.methodParameterMembers.values().forEach(parameters -> parameters.forEach(parameter -> {
if (parameter.line == line && parameter.columnStart - 1 <= column && parameter.columnEnd >= column) {
if (parameter.line == line && parameter.columnStart - 1 <= column && parameter.columnEnd >= column)
{
Element root = textArea.getDocument().getDefaultRootElement();
if (parameter.decRef.equalsIgnoreCase("declaration")) {
if (parameter.decRef.equalsIgnoreCase("declaration"))
{
int startOffset = root.getElement(parameter.line - 1).getStartOffset() + (parameter.columnStart - 1);
textArea.setCaretPosition(startOffset);
} else {
} else
{
String method = parameter.method;
parameters.stream().filter(classParameterLocation -> classParameterLocation.method.equals(method)).forEach(classParameterLocation -> {
if (classParameterLocation.decRef.equalsIgnoreCase("declaration")) {
if (classParameterLocation.decRef.equalsIgnoreCase("declaration"))
{
int startOffset = root.getElement(classParameterLocation.line - 1).getStartOffset() + (classParameterLocation.columnStart - 1);
textArea.setCaretPosition(startOffset);
}
@ -58,15 +79,19 @@ public class GoToAction extends AbstractAction
}));
container.methodLocalMembers.values().forEach(localMembers -> localMembers.forEach(localMember -> {
if (localMember.line == line && localMember.columnStart - 1 <= column && localMember.columnEnd >= column) {
if (localMember.line == line && localMember.columnStart - 1 <= column && localMember.columnEnd >= column)
{
Element root = textArea.getDocument().getDefaultRootElement();
if (localMember.decRef.equals("declaration")) {
if (localMember.decRef.equals("declaration"))
{
int startOffset = root.getElement(localMember.line - 1).getStartOffset() + (localMember.columnStart - 1);
textArea.setCaretPosition(startOffset);
} else {
} else
{
String method = localMember.method;
localMembers.stream().filter(classLocalVariableLocation -> classLocalVariableLocation.method.equals(method)).forEach(classLocalVariableLocation -> {
if (classLocalVariableLocation.decRef.equalsIgnoreCase("declaration")) {
if (classLocalVariableLocation.decRef.equalsIgnoreCase("declaration"))
{
int startOffset = root.getElement(classLocalVariableLocation.line - 1).getStartOffset() + (classLocalVariableLocation.columnStart - 1);
textArea.setCaretPosition(startOffset);
}

View File

@ -26,15 +26,18 @@ public class ClassFileContainer
public transient NavigableMap<String, ArrayList<ClassParameterLocation>> methodParameterMembers = new TreeMap<>();
public transient NavigableMap<String, ArrayList<ClassLocalVariableLocation>> methodLocalMembers = new TreeMap<>();
public transient NavigableMap<String, ArrayList<ClassMethodLocation>> methodMembers = new TreeMap<>();
public transient NavigableMap<String, String> imports = new TreeMap<>();
public boolean hasBeenParsed = false;
public final String className;
private final String content;
private final String parentContainer;
public ClassFileContainer(String className, String content)
public ClassFileContainer(String className, String content, String parentContainer)
{
this.className = className;
this.content = content;
this.parentContainer = parentContainer;
}
public void parse()
@ -50,6 +53,15 @@ public class ClassFileContainer
}
}
public String getName() {
return this.className.substring(this.className.lastIndexOf('.') + 1);
}
public String getParentContainer()
{
return this.parentContainer;
}
public void putField(String key, ClassFieldLocation value)
{
this.fieldMembers.computeIfAbsent(key, v -> new ArrayList<>()).add(value);
@ -89,4 +101,14 @@ public class ClassFileContainer
{
return methodMembers.getOrDefault(key, new ArrayList<>());
}
public void putImport(String key, String value)
{
this.imports.put(key, value);
}
public String getImport(String key) {
String value = this.imports.get(key);
return value + "/" + key;
}
}

View File

@ -2,9 +2,11 @@ package the.bytecode.club.bytecodeviewer.resources.classcontainer.parser;
import com.github.javaparser.Range;
import com.github.javaparser.ast.CompilationUnit;
import com.github.javaparser.ast.ImportDeclaration;
import com.github.javaparser.ast.body.*;
import com.github.javaparser.ast.expr.*;
import com.github.javaparser.ast.stmt.*;
import com.github.javaparser.ast.type.ClassOrInterfaceType;
import com.github.javaparser.ast.visitor.VoidVisitorAdapter;
import com.github.javaparser.resolution.UnsolvedSymbolException;
import com.github.javaparser.resolution.declarations.ResolvedValueDeclaration;
@ -14,6 +16,7 @@ import the.bytecode.club.bytecodeviewer.resources.classcontainer.locations.Class
import the.bytecode.club.bytecodeviewer.resources.classcontainer.locations.ClassMethodLocation;
import the.bytecode.club.bytecodeviewer.resources.classcontainer.locations.ClassParameterLocation;
import java.util.Objects;
import java.util.concurrent.atomic.AtomicInteger;
/**
@ -34,7 +37,7 @@ public class MyVoidVisitor extends VoidVisitorAdapter<Object>
private String getOwner()
{
return this.classFileContainer.className.substring(this.classFileContainer.className.lastIndexOf('.') + 1);
return this.classFileContainer.getName();
}
private String getMethod(CallableDeclaration<?> method)
@ -66,6 +69,17 @@ public class MyVoidVisitor extends VoidVisitorAdapter<Object>
});
}
@Override
public void visit(ImportDeclaration n, Object arg)
{
super.visit(n, arg);
Name class_ = n.getName();
String className = class_.getIdentifier();
String package_ = Objects.requireNonNull(class_.getQualifier().orElse(null)).asString();
package_ = package_.replace('.', '/');
this.classFileContainer.putImport(className, package_);
}
/**
* Visit all {@link FieldAccessExpr}s.
* <p>
@ -85,7 +99,6 @@ public class MyVoidVisitor extends VoidVisitorAdapter<Object>
int line = range.begin.line;
int columnStart = range.begin.column;
int columnEnd = range.end.column;
this.classFileContainer.putField(fieldName, new ClassFieldLocation(getOwner(), "reference", line, columnStart, columnEnd + 1));
if (n.hasScope())
{
@ -101,15 +114,15 @@ public class MyVoidVisitor extends VoidVisitorAdapter<Object>
if (scope instanceof NameExpr)
{
NameExpr nameExpr = (NameExpr) scope;
SimpleName simpleName1 = nameExpr.getName();
String name1 = simpleName1.getIdentifier();
Range range1 = nameExpr.getRange().get();
int line1 = range1.begin.line;
int columnStart1 = range1.begin.column;
int columnEnd1 = range1.end.column;
try
{
ResolvedValueDeclaration vd = nameExpr.resolve();
SimpleName simpleName1 = nameExpr.getName();
String name1 = simpleName1.getIdentifier();
Range range1 = nameExpr.getRange().get();
int line1 = range1.begin.line;
int columnStart1 = range1.begin.column;
int columnEnd1 = range1.end.column;
if (vd.isField())
{
this.classFileContainer.putField(name1, new ClassFieldLocation(getOwner(), "reference", line1, columnStart1, columnEnd1 + 1));
@ -122,12 +135,20 @@ public class MyVoidVisitor extends VoidVisitorAdapter<Object>
}
} catch (UnsolvedSymbolException ignore)
{
this.classFileContainer.putField(fieldName, new ClassFieldLocation(name1, "reference", line, columnStart, columnEnd + 1));
}
}
}
}
}
@Override
public void visit(ClassOrInterfaceType n, Object arg)
{
super.visit(n, arg);
// System.err.println(n.getName().getIdentifier());
}
/**
* Visit all {@link ConstructorDeclaration}s.
* <p>