Abstract out structure modifiers to allow internal structures to be read

This commit is contained in:
Dan Mulloy 2021-06-24 17:13:05 -04:00
parent 9b6603e2eb
commit 99504dab8f
No known key found for this signature in database
GPG Key ID: 2B62F7DACFF133E8
5 changed files with 1245 additions and 1112 deletions

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,45 @@
package com.comphenix.protocol.events;
import com.comphenix.protocol.reflect.EquivalentConverter;
import com.comphenix.protocol.reflect.StructureModifier;
import com.comphenix.protocol.wrappers.Converters;
import java.util.List;
import java.util.Optional;
public class InternalStructure extends AbstractStructure {
protected InternalStructure(Object handle, StructureModifier<Object> structureModifier) {
super(handle, structureModifier);
}
protected static final EquivalentConverter<InternalStructure> CONVERTER = new EquivalentConverter<InternalStructure>() {
@Override
public Object getGeneric(InternalStructure specific) {
return specific.handle;
}
@Override
public InternalStructure getSpecific(Object generic) {
return new InternalStructure(generic, new StructureModifier<>(generic.getClass()).withTarget(generic));
}
@Override
public Class<InternalStructure> getSpecificType() {
return InternalStructure.class;
}
};
public StructureModifier<InternalStructure> getStructures() {
return structureModifier.withType(Object.class, CONVERTER);
}
public StructureModifier<Optional<InternalStructure>> getOptionalStructures() {
return structureModifier.withType(Optional.class, Converters.optional(CONVERTER));
}
@Override
public String toString() {
return "InternalStructure[handle=" + handle + " (" + handle.getClass().getSimpleName() + ")]";
}
}

View File

@ -17,6 +17,7 @@
package com.comphenix.protocol.wrappers;
import java.lang.reflect.Array;
import java.util.Optional;
import java.util.function.Function;
import com.comphenix.protocol.reflect.EquivalentConverter;
@ -150,4 +151,24 @@ public class Converters {
}
};
}
public static <T> EquivalentConverter<Optional<T>> optional(final EquivalentConverter<T> converter) {
return new EquivalentConverter<Optional<T>>() {
@Override
public Object getGeneric(Optional<T> specific) {
return specific.map(converter::getGeneric);
}
@Override
public Optional<T> getSpecific(Object generic) {
Optional<Object> optional = (Optional<Object>) generic;
return optional.map(converter::getSpecific);
}
@Override
public Class<Optional<T>> getSpecificType() {
return (Class<Optional<T>>) Optional.empty().getClass();
}
};
}
}

View File

@ -515,6 +515,24 @@ public class PacketContainerTest {
// assertEquals(container.getEnumModifier(Action.class, PacketPlayOutBoss.d.class).read(0), Action.UPDATE_PCT);
}
@Test
public void testInternalStructures() {
PacketContainer container = new PacketContainer(PacketType.Play.Server.SCOREBOARD_TEAM);
Optional<InternalStructure> optStruct = container.getOptionalStructures().read(0);
assertTrue(optStruct.isPresent());
InternalStructure struct = optStruct.get();
struct.getChatComponents().write(0, WrappedChatComponent.fromText("hi there"));
container.getOptionalStructures().write(0, Optional.of(struct));
optStruct = container.getOptionalStructures().read(0);
assertTrue(optStruct.isPresent());
struct = optStruct.get();
testEquality(
struct.getChatComponents().read(0),
WrappedChatComponent.fromText("hi there")
);
}
// @Test
public void testDimensions() {
// TODO this won't work in testing, but hopefully will in live