mirror of
https://github.com/konsoletyper/teavm.git
synced 2024-11-27 01:30:35 +08:00
Add support for Array.set
This commit is contained in:
parent
365e47882a
commit
d20accc20c
@ -53,6 +53,9 @@ public class ArrayNativeGenerator implements Generator, DependencyPlugin {
|
||||
case "getImpl":
|
||||
reachGet(agent, method);
|
||||
break;
|
||||
case "setImpl":
|
||||
reachSet(agent, method);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@ -68,6 +71,9 @@ public class ArrayNativeGenerator implements Generator, DependencyPlugin {
|
||||
case "getImpl":
|
||||
generateGet(context, writer);
|
||||
break;
|
||||
case "setImpl":
|
||||
generateSet(context, writer);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@ -126,6 +132,31 @@ public class ArrayNativeGenerator implements Generator, DependencyPlugin {
|
||||
writer.outdent().append("}").softNewLine();
|
||||
}
|
||||
|
||||
private void generateSet(GeneratorContext context, SourceWriter writer) throws IOException {
|
||||
String array = context.getParameterName(1);
|
||||
String item = context.getParameterName(3);
|
||||
writer.append("var type = " + array + ".constructor.$meta.item;").softNewLine();
|
||||
boolean first = true;
|
||||
for (int i = 0; i < primitives.length; ++i) {
|
||||
String wrapper = "java.lang." + primitiveWrappers[i];
|
||||
MethodReference methodRef = new MethodReference(wrapper, primitives[i].toLowerCase() + "Value",
|
||||
primitiveTypes[i]);
|
||||
ClassReader cls = context.getClassSource().get(methodRef.getClassName());
|
||||
if (cls == null || cls.getMethod(methodRef.getDescriptor()) == null) {
|
||||
continue;
|
||||
}
|
||||
if (!first) {
|
||||
writer.append(" else ");
|
||||
}
|
||||
first = false;
|
||||
writer.append("if (type === $rt_" + primitives[i].toLowerCase() + "cls()) {").indent().softNewLine();
|
||||
writer.append(item + " = ").appendMethodBody(methodRef).append("(" + item + ");").softNewLine();
|
||||
writer.outdent().append("}");
|
||||
}
|
||||
writer.softNewLine();
|
||||
writer.append(array + ".data[" + context.getParameterName(2) + "] = " + item + ";").softNewLine();
|
||||
}
|
||||
|
||||
private void reachGet(DependencyAgent agent, MethodDependency method) {
|
||||
method.getVariable(1).getArrayItem().connect(method.getResult());
|
||||
method.getVariable(1).addConsumer(type -> {
|
||||
@ -143,4 +174,21 @@ public class ArrayNativeGenerator implements Generator, DependencyPlugin {
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void reachSet(DependencyAgent agent, MethodDependency method) {
|
||||
method.getVariable(3).connect(method.getVariable(1).getArrayItem());
|
||||
method.getVariable(1).addConsumer(type -> {
|
||||
if (type.getName().startsWith("[")) {
|
||||
String typeName = type.getName().substring(1);
|
||||
for (int i = 0; i < primitiveTypes.length; ++i) {
|
||||
if (primitiveTypes[i].toString().equals(typeName)) {
|
||||
String wrapper = "java.lang." + primitiveWrappers[i];
|
||||
MethodReference methodRef = new MethodReference(wrapper,
|
||||
primitives[i].toLowerCase() + "Value", primitiveTypes[i]);
|
||||
agent.linkMethod(methodRef, null).use();
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -79,7 +79,19 @@ public final class TArray extends TObject {
|
||||
return getImpl(array, index);
|
||||
}
|
||||
|
||||
public static void set(TObject array, int index, TObject value) throws TIllegalArgumentException,
|
||||
TArrayIndexOutOfBoundsException {
|
||||
if (index < 0 || index >= getLength(array)) {
|
||||
throw new TArrayIndexOutOfBoundsException();
|
||||
}
|
||||
setImpl(array, index, value);
|
||||
}
|
||||
|
||||
@GeneratedBy(ArrayNativeGenerator.class)
|
||||
@PluggableDependency(ArrayNativeGenerator.class)
|
||||
private static native TObject getImpl(TObject array, int index);
|
||||
|
||||
@GeneratedBy(ArrayNativeGenerator.class)
|
||||
@PluggableDependency(ArrayNativeGenerator.class)
|
||||
private static native void setImpl(TObject array, int index, TObject value);
|
||||
}
|
||||
|
@ -15,6 +15,7 @@
|
||||
*/
|
||||
package org.teavm.classlib.java.lang.reflect;
|
||||
|
||||
import static org.junit.Assert.assertArrayEquals;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import java.lang.reflect.Array;
|
||||
import org.junit.Test;
|
||||
@ -36,4 +37,20 @@ public class ArrayTest {
|
||||
assertEquals(int[].class, instance.getClass());
|
||||
assertEquals(15, Array.getLength(instance));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void setWorks() {
|
||||
Object array = Array.newInstance(String.class, 2);
|
||||
Array.set(array, 0, "foo");
|
||||
Array.set(array, 1, "bar");
|
||||
assertArrayEquals(new String[] { "foo", "bar" }, (String[]) array);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void setPrimitiveWorks() {
|
||||
Object array = Array.newInstance(int.class, 2);
|
||||
Array.set(array, 0, 23);
|
||||
Array.set(array, 1, 42);
|
||||
assertArrayEquals(new int[] { 23, 42 }, (int[]) array);
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user