mirror of
https://github.com/KAMKEEL/CustomNPC-Plus.git
synced 2026-11-12 23:37:32 +00:00
Implemented TypeParamInfo to TypeInfo and JSTypeInfo, and resolved all type params of JS API types after all are loaded
This commit is contained in:
1 parent
798e238804
commit
7725d16e82
5 files changed
+203
-42
No files matched your search
+35
-38
@@ -1,5 +1,7 @@
|
||||
package noppes.npcs.client.gui.util.script.interpreter.js_parser;
|
||||
|
||||
import noppes.npcs.client.gui.util.script.interpreter.type.TypeInfo;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
@@ -8,34 +10,6 @@ import java.util.*;
|
||||
*/
|
||||
public class JSTypeInfo {
|
||||
|
||||
/**
|
||||
* Represents a generic type parameter like "T extends Entity".
|
||||
* Stores the parameter name, the bound type, and optionally the full Java class name.
|
||||
*/
|
||||
public static class TypeParamInfo {
|
||||
private final String name; // e.g., "T"
|
||||
private final String boundType; // e.g., "EntityPlayerMP"
|
||||
private final String fullBoundType; // e.g., "net.minecraft.entity.player.EntityPlayerMP"
|
||||
|
||||
public TypeParamInfo(String name, String boundType, String fullBoundType) {
|
||||
this.name = name;
|
||||
this.boundType = boundType;
|
||||
this.fullBoundType = fullBoundType;
|
||||
}
|
||||
|
||||
public String getName() { return name; }
|
||||
public String getBoundType() { return boundType; }
|
||||
public String getFullBoundType() { return fullBoundType; }
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
if (boundType != null) {
|
||||
return name + " extends " + boundType + (fullBoundType != null ? " (" + fullBoundType + ")" : "");
|
||||
}
|
||||
return name;
|
||||
}
|
||||
}
|
||||
|
||||
private final String simpleName; // e.g., "InteractEvent"
|
||||
private final String fullName; // e.g., "IPlayerEvent.InteractEvent"
|
||||
private final String namespace; // e.g., "IPlayerEvent" (parent namespace, null for top-level)
|
||||
@@ -102,11 +76,7 @@ public class JSTypeInfo {
|
||||
public void setResolvedParent(JSTypeInfo parent) {
|
||||
this.resolvedParent = parent;
|
||||
}
|
||||
|
||||
public void addTypeParam(TypeParamInfo param) {
|
||||
typeParams.add(param);
|
||||
}
|
||||
|
||||
|
||||
// Getters
|
||||
public String getSimpleName() { return simpleName; }
|
||||
public String getFullName() { return fullName; }
|
||||
@@ -133,16 +103,43 @@ public class JSTypeInfo {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public void addTypeParam(TypeParamInfo param) {
|
||||
typeParams.add(param);
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve all type parameters for this type.
|
||||
* Called during Phase 2 after all types are loaded into the registry.
|
||||
*/
|
||||
public void resolveTypeParameters() {
|
||||
for (TypeParamInfo param : typeParams) {
|
||||
param.resolveBoundType();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolves a type parameter to its bound type.
|
||||
* For example, if this type has "T extends EntityPlayerMP", resolveTypeParam("T") returns "EntityPlayerMP".
|
||||
* If no type parameter is found with that name, returns the input.
|
||||
* Resolves a type parameter to its bound TypeInfo.
|
||||
* For example, if this type has "T extends EntityPlayerMP", resolveTypeParam("T") returns the TypeInfo for EntityPlayerMP.
|
||||
* If no type parameter is found with that name, returns null.
|
||||
*/
|
||||
public TypeInfo resolveTypeParamToTypeInfo(String typeName) {
|
||||
TypeParamInfo param = getTypeParam(typeName);
|
||||
if (param != null) {
|
||||
return param.getBoundTypeInfo();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolves a type parameter to its bound type name (for backward compatibility).
|
||||
* @deprecated Use resolveTypeParamToTypeInfo instead
|
||||
*/
|
||||
@Deprecated
|
||||
public String resolveTypeParam(String typeName) {
|
||||
TypeParamInfo param = getTypeParam(typeName);
|
||||
if (param != null && param.getBoundType() != null) {
|
||||
return param.getBoundType();
|
||||
if (param != null && param.getBoundTypeInfo() != null) {
|
||||
return param.getBoundTypeInfo().getSimpleName();
|
||||
}
|
||||
return typeName;
|
||||
}
|
||||
|
||||
+16
@@ -83,6 +83,9 @@ public class JSTypeRegistry {
|
||||
}
|
||||
}
|
||||
|
||||
// Phase 2: Resolve all type parameters now that all types are loaded
|
||||
resolveAllTypeParameters();
|
||||
|
||||
resolveInheritance();
|
||||
registerEngineGlobalObjects();
|
||||
|
||||
@@ -223,6 +226,7 @@ public class JSTypeRegistry {
|
||||
try {
|
||||
TypeScriptDefinitionParser parser = new TypeScriptDefinitionParser(this);
|
||||
parser.parseDirectory(directory);
|
||||
resolveAllTypeParameters();
|
||||
resolveInheritance();
|
||||
initialized = true;
|
||||
System.out.println("[JSTypeRegistry] Loaded " + types.size() + " types, " + hooks.size() + " hooks");
|
||||
@@ -241,6 +245,7 @@ public class JSTypeRegistry {
|
||||
try {
|
||||
TypeScriptDefinitionParser parser = new TypeScriptDefinitionParser(this);
|
||||
parser.parseVsixArchive(vsixFile);
|
||||
resolveAllTypeParameters();
|
||||
resolveInheritance();
|
||||
initialized = true;
|
||||
System.out.println("[JSTypeRegistry] Loaded " + types.size() + " types, " + hooks.size() + " hooks from VSIX");
|
||||
@@ -360,6 +365,17 @@ public class JSTypeRegistry {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve all type parameters for all types.
|
||||
* Called after all .d.ts files are loaded (Phase 2).
|
||||
* This ensures that type parameters can reference any type in the registry.
|
||||
*/
|
||||
public void resolveAllTypeParameters() {
|
||||
for (JSTypeInfo type : types.values()) {
|
||||
type.resolveTypeParameters();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve inheritance relationships between types.
|
||||
* For each type, walks up the parent chain and resolves all ancestors.
|
||||
|
||||
+68
@@ -0,0 +1,68 @@
|
||||
package noppes.npcs.client.gui.util.script.interpreter.js_parser;
|
||||
|
||||
import noppes.npcs.client.gui.util.script.interpreter.type.TypeInfo;
|
||||
import noppes.npcs.client.gui.util.script.interpreter.type.TypeResolver;
|
||||
|
||||
/**
|
||||
* Represents a generic type parameter like "T extends Entity".
|
||||
* Stores the parameter name and both the string representation (for deferred resolution)
|
||||
* and the resolved TypeInfo for the bound.
|
||||
*/
|
||||
public class TypeParamInfo {
|
||||
private final String name; // e.g., "T"
|
||||
private final String boundType; // Simple name like "EntityPlayerMP" (may be null)
|
||||
private final String fullBoundType; // Full name like "net.minecraft.entity.player.EntityPlayerMP" (may be null)
|
||||
private TypeInfo boundTypeInfo; // Resolved TypeInfo for the bound (resolved in Phase 2)
|
||||
|
||||
/**
|
||||
* Constructor for parse-time (Phase 1) - stores string names only.
|
||||
*/
|
||||
public TypeParamInfo(String name, String boundType, String fullBoundType) {
|
||||
this.name = name;
|
||||
this.boundType = boundType;
|
||||
this.fullBoundType = fullBoundType;
|
||||
this.boundTypeInfo = null; // Will be resolved later
|
||||
}
|
||||
|
||||
public String getName() { return name; }
|
||||
|
||||
public TypeInfo getBoundTypeInfo() {
|
||||
return boundTypeInfo;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve the bound type using TypeResolver.
|
||||
* Called during Phase 2 after all types are loaded.
|
||||
*/
|
||||
public void resolveBoundType() {
|
||||
if (boundTypeInfo != null)
|
||||
return; // Already resolved
|
||||
|
||||
if (fullBoundType != null && !fullBoundType.isEmpty()) {
|
||||
// Try to load the Java class using the full name
|
||||
boundTypeInfo = TypeResolver.getInstance().resolveFullName(fullBoundType);
|
||||
} else if (boundType != null && !boundType.isEmpty()) {
|
||||
// Try to resolve using the simple name
|
||||
boundTypeInfo = TypeResolver.getInstance().resolveJSType(boundType);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get simple display name for the bound type.
|
||||
*/
|
||||
public String getBoundTypeName() {
|
||||
if (boundTypeInfo == null)
|
||||
return null;
|
||||
return boundTypeInfo.getSimpleName();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
if (boundTypeInfo != null) {
|
||||
return name + " extends " + boundTypeInfo.getSimpleName();
|
||||
} else if (boundType != null || fullBoundType != null) {
|
||||
return name + " extends " + (boundType != null ? boundType : fullBoundType);
|
||||
}
|
||||
return name;
|
||||
}
|
||||
}
|
||||
+5
-3
@@ -311,6 +311,7 @@ public class TypeScriptDefinitionParser {
|
||||
/**
|
||||
* Parse type parameters from a string like "T extends EntityPlayerMP /* net.minecraft.entity.player.EntityPlayerMP *`/".
|
||||
* Handles multiple parameters separated by commas.
|
||||
* Stores strings only - resolution happens in Phase 2 after all types are loaded.
|
||||
*/
|
||||
private void parseTypeParameters(String typeParamsStr, JSTypeInfo typeInfo) {
|
||||
// Split by comma, but be careful with nested generics (shouldn't happen at this level, but be safe)
|
||||
@@ -322,10 +323,11 @@ public class TypeScriptDefinitionParser {
|
||||
Matcher m = TYPE_PARAM_PATTERN.matcher(param);
|
||||
if (m.find()) {
|
||||
String name = m.group(1);
|
||||
String boundType = m.group(2);
|
||||
String fullBoundType = m.group(3);
|
||||
String boundType = m.group(2); // Simple name like "EntityPlayerMP"
|
||||
String fullBoundType = m.group(3); // Full name like "net.minecraft.entity.player.EntityPlayerMP"
|
||||
|
||||
typeInfo.addTypeParam(new JSTypeInfo.TypeParamInfo(name, boundType, fullBoundType));
|
||||
// Store strings only - resolution happens in Phase 2
|
||||
typeInfo.addTypeParam(new TypeParamInfo(name, boundType, fullBoundType));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,6 +5,7 @@ import noppes.npcs.client.gui.util.script.interpreter.field.FieldInfo;
|
||||
import noppes.npcs.client.gui.util.script.interpreter.js_parser.JSFieldInfo;
|
||||
import noppes.npcs.client.gui.util.script.interpreter.js_parser.JSMethodInfo;
|
||||
import noppes.npcs.client.gui.util.script.interpreter.js_parser.JSTypeInfo;
|
||||
import noppes.npcs.client.gui.util.script.interpreter.js_parser.TypeParamInfo;
|
||||
import noppes.npcs.client.gui.util.script.interpreter.method.MethodInfo;
|
||||
import noppes.npcs.client.gui.util.script.interpreter.token.TokenType;
|
||||
|
||||
@@ -60,6 +61,9 @@ public class TypeInfo {
|
||||
|
||||
// JavaScript/TypeScript type info (for types from .d.ts files)
|
||||
private final JSTypeInfo jsTypeInfo; // The JS type info (null if Java type)
|
||||
|
||||
// Type parameters (generics)
|
||||
private final List<TypeParamInfo> typeParams = new ArrayList<>();
|
||||
|
||||
private TypeInfo(String simpleName, String fullName, String packageName,
|
||||
Kind kind, Class<?> javaClass, boolean resolved, TypeInfo enclosingType) {
|
||||
@@ -477,7 +481,8 @@ public class TypeInfo {
|
||||
// Check JS type first
|
||||
if (jsTypeInfo != null) {
|
||||
for (JSMethodInfo jsMethod : jsTypeInfo.getMethodOverloads(methodName)) {
|
||||
overloads.add(MethodInfo.fromJSMethod(jsMethod, this));
|
||||
// Pass jsTypeInfo as context for type parameter resolution
|
||||
overloads.add(MethodInfo.fromJSMethod(jsMethod, this, jsTypeInfo));
|
||||
}
|
||||
return overloads;
|
||||
}
|
||||
@@ -679,6 +684,79 @@ public class TypeInfo {
|
||||
public void validate() {
|
||||
// Default: no validation for Java types
|
||||
}
|
||||
|
||||
// ==================== Type Parameter Methods ====================
|
||||
|
||||
/**
|
||||
* Add a type parameter to this type.
|
||||
* Used during parsing/construction of types with generics.
|
||||
*/
|
||||
public void addTypeParam(TypeParamInfo param) {
|
||||
// If this is a JS type, delegate to JSTypeInfo
|
||||
if (jsTypeInfo != null) {
|
||||
jsTypeInfo.addTypeParam(param);
|
||||
} else {
|
||||
typeParams.add(param);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get all type parameters for this type.
|
||||
* @return List of type parameters (empty if none)
|
||||
*/
|
||||
public List<TypeParamInfo> getTypeParams() {
|
||||
// If this is a JS type, delegate to JSTypeInfo
|
||||
if (jsTypeInfo != null) {
|
||||
return jsTypeInfo.getTypeParams();
|
||||
}
|
||||
return typeParams;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve all type parameters for this type.
|
||||
* Called during Phase 2 after all types are loaded into the registry.
|
||||
*/
|
||||
public void resolveTypeParameters() {
|
||||
// If this is a JS type, delegate to JSTypeInfo
|
||||
if (jsTypeInfo != null) {
|
||||
jsTypeInfo.resolveTypeParameters();
|
||||
} else {
|
||||
for (TypeParamInfo param : typeParams) {
|
||||
param.resolveBoundType();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the type parameter info for a given parameter name (e.g., "T").
|
||||
* @return TypeParamInfo or null if not found
|
||||
*/
|
||||
public TypeParamInfo getTypeParam(String name) {
|
||||
// If this is a JS type, delegate to JSTypeInfo
|
||||
if (jsTypeInfo != null) {
|
||||
return jsTypeInfo.getTypeParam(name);
|
||||
}
|
||||
|
||||
for (TypeParamInfo param : typeParams) {
|
||||
if (param.getName().equals(name)) {
|
||||
return param;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolves a type parameter to its bound TypeInfo.
|
||||
* For example, if this type has "T extends EntityPlayerMP", resolveTypeParamToTypeInfo("T") returns the TypeInfo for EntityPlayerMP.
|
||||
* If no type parameter is found with that name, returns null.
|
||||
*/
|
||||
public TypeInfo resolveTypeParamToTypeInfo(String typeName) {
|
||||
TypeParamInfo param = getTypeParam(typeName);
|
||||
if (param != null) {
|
||||
return param.getBoundTypeInfo();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
|
||||
Reference in new issue
Block a user