Skip to content

Commit

Permalink
data element changes given feedback
Browse files Browse the repository at this point in the history
  • Loading branch information
lukebemish committed May 27, 2024
1 parent 4a8eb6e commit ad12ebd
Show file tree
Hide file tree
Showing 6 changed files with 60 additions and 42 deletions.
Original file line number Diff line number Diff line change
@@ -1,24 +1,24 @@
package dev.lukebemish.codecextras.mutable;

import com.mojang.datafixers.util.Pair;
import com.mojang.serialization.Codec;
import com.mojang.serialization.DataResult;
import com.mojang.serialization.Dynamic;
import com.mojang.serialization.JsonOps;
import com.mojang.serialization.MapCodec;
import com.mojang.serialization.codecs.RecordCodecBuilder;
import dev.lukebemish.codecextras.Asymmetry;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.function.Consumer;
import java.util.function.Function;

public interface DataElementType<D, T> {
DataElement<T> from(D data);
Codec<T> codec();
DataElement<T> create();
String name();

static <D, T> DataElementType<D, T> defaulted(Codec<T> codec, T defaultValue, Function<D, DataElement<T>> getter) {
static <D, T> DataElementType<D, T> defaulted(String name, Codec<T> codec, Function<D, DataElement<T>> getter) {
return new DataElementType<>() {
@Override
public DataElement<T> from(D data) {
Expand All @@ -31,21 +31,29 @@ public Codec<T> codec() {
}

@Override
public DataElement<T> create() {
return new DataElement.Simple<>(defaultValue);
public String name() {
return name;
}
};
}

static <D> Codec<Asymmetry<Consumer<D>, D>> codec(List<? extends DataElementType<D, ?>> elements, boolean encodeAll) {
MapCodec<Pair<Integer, Dynamic<?>>> partial = RecordCodecBuilder.mapCodec(i -> i.group(
Codec.INT.fieldOf("index").forGetter(Pair::getFirst),
Codec.PASSTHROUGH.fieldOf("value").forGetter(Pair::getSecond)
).apply(i, Pair::of));
@SafeVarargs
static <D> Codec<Asymmetry<Consumer<D>, D>> codec(boolean encodeAll, DataElementType<D, ?>... elements) {
List<DataElementType<D, ?>> list = List.of(elements);
return codec(encodeAll, list);
}

static <D> Codec<Asymmetry<Consumer<D>, D>> codec(boolean encodeAll, List<? extends DataElementType<D, ?>> elements) {
Map<String, DataElementType<D, ?>> elementTypeMap = new HashMap<>();
for (var element : elements) {
elementTypeMap.put(element.name(), element);
}

Codec<Map<String, Dynamic<?>>> partial = Codec.unboundedMap(Codec.STRING, Codec.PASSTHROUGH);

return Asymmetry.flatSplit(
partial.codec().listOf(),
list -> {
partial,
map -> {
record Mutation<D, T>(DataElementType<D, T> element, T value) {
private static <D, T> DataResult<Mutation<D, T>> of(DataElementType<D, T> type, Dynamic<?> dynamic) {
return type.codec().parse(dynamic).map(value -> new Mutation<>(type, value));
Expand All @@ -57,13 +65,13 @@ public void set(D data) {
}

List<Mutation<D, ?>> mutations = new ArrayList<>();
for (var pair : list) {
int index = pair.getFirst();
if (index < 0 || index >= elements.size()) {
return DataResult.error(() -> "Invalid index for DataElementType: " + index);
for (var pair : map.entrySet()) {
String name = pair.getKey();
var type = elementTypeMap.get(name);
if (type == null) {
return DataResult.error(() -> "Invalid name for DataElementType: " + name);
}
var type = elements.get(index);
var mutation = Mutation.of(type, pair.getSecond());
var mutation = Mutation.of(type, pair.getValue());
if (mutation.error().isPresent()) {
return DataResult.error(mutation.error().get().messageSupplier());
}
Expand All @@ -77,20 +85,19 @@ public void set(D data) {
});
},
data -> {
List<Pair<Integer, Dynamic<?>>> list = new ArrayList<>();
for (int i = 0; i < elements.size(); i++) {
var type = elements.get(i);
Map<String, Dynamic<?>> map = new HashMap<>();
for (DataElementType<D, ?> type : elements) {
var element = type.from(data);
if (encodeAll || element.dirty()) {
var result = forElement(type, data);
if (result.result().isPresent()) {
list.add(Pair.of(i, result.result().get()));
map.put(type.name(), result.result().get());
} else {
return DataResult.error(result.error().get().messageSupplier(), list);
return DataResult.error(result.error().get().messageSupplier(), map);
}
}
}
return DataResult.success(list);
return DataResult.success(map);
}
);
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
@NullMarked
@ApiStatus.Experimental
package dev.lukebemish.codecextras.mutable;

import org.jetbrains.annotations.ApiStatus;
import org.jspecify.annotations.NullMarked;
Original file line number Diff line number Diff line change
Expand Up @@ -6,17 +6,18 @@
import dev.lukebemish.codecextras.mutable.DataElement;
import dev.lukebemish.codecextras.mutable.DataElementType;
import io.netty.handler.codec.DecoderException;
import net.minecraft.network.FriendlyByteBuf;
import net.minecraft.network.codec.StreamCodec;

import java.util.ArrayList;
import java.util.List;
import java.util.function.Consumer;
import java.util.function.Function;
import net.minecraft.network.FriendlyByteBuf;
import net.minecraft.network.codec.StreamCodec;

public interface StreamDataElementType<B, D, T> extends DataElementType<D, T> {
StreamCodec<B, T> streamCodec();

static <B, D, T> StreamDataElementType<B, D, T> defaulted(Codec<T> codec, StreamCodec<B, T> streamCodec, T defaultValue, Function<D, DataElement<T>> getter) {
static <B, D, T> StreamDataElementType<B, D, T> defaulted(String name, Codec<T> codec, StreamCodec<B, T> streamCodec, Function<D, DataElement<T>> getter) {
return new StreamDataElementType<>() {
@Override
public StreamCodec<B, T> streamCodec() {
Expand All @@ -34,13 +35,19 @@ public Codec<T> codec() {
}

@Override
public DataElement<T> create() {
return new DataElement.Simple<>(defaultValue);
public String name() {
return name;
}
};
}

static <B extends FriendlyByteBuf, D> StreamCodec<B, Asymmetry<Consumer<D>, D>> streamCodec(List<? extends StreamDataElementType<B, D, ?>> elements, boolean encodeAll) {
@SafeVarargs
static <B extends FriendlyByteBuf, D> StreamCodec<B, Asymmetry<Consumer<D>, D>> streamCodec(boolean encodeAll, StreamDataElementType<B, D, ?>... elements) {
List<StreamDataElementType<B, D, ?>> list = List.of(elements);
return streamCodec(encodeAll, list);
}

static <B extends FriendlyByteBuf, D> StreamCodec<B, Asymmetry<Consumer<D>, D>> streamCodec(boolean encodeAll, List<? extends StreamDataElementType<B, D, ?>> elements) {
return StreamCodec.of((buffer, asymmetry) -> {
var data = asymmetry.encoding().getOrThrow();
List<Pair<Integer, Consumer<B>>> toEncode = new ArrayList<>();
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
@NullMarked
@ApiStatus.Experimental
package dev.lukebemish.codecextras.stream.mutable;

import org.jetbrains.annotations.ApiStatus;
import org.jspecify.annotations.NullMarked;
Original file line number Diff line number Diff line change
Expand Up @@ -9,21 +9,21 @@
import dev.lukebemish.codecextras.mutable.DataElement;
import dev.lukebemish.codecextras.mutable.DataElementType;
import dev.lukebemish.codecextras.test.CodecAssertions;
import java.util.List;
import java.util.Objects;
import java.util.function.Consumer;
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;

import java.util.Objects;
import java.util.function.Consumer;

class TestDataElements {
private static class WithDataElements {
private static final DataElementType<WithDataElements, String> STRING = DataElementType.defaulted(Codec.STRING, "", d -> d.string);
private static final DataElementType<WithDataElements, Integer> INTEGER = DataElementType.defaulted(Codec.INT, 0, d -> d.integer);
private static final Codec<Asymmetry<Consumer<WithDataElements>, WithDataElements>> CODEC = DataElementType.codec(List.of(STRING, INTEGER), true);
private static final Codec<Asymmetry<Consumer<WithDataElements>, WithDataElements>> CHANGED_CODEC = DataElementType.codec(List.of(STRING, INTEGER), false);
private static final DataElementType<WithDataElements, String> STRING = DataElementType.defaulted("string", Codec.STRING, d -> d.string);
private static final DataElementType<WithDataElements, Integer> INTEGER = DataElementType.defaulted("integer", Codec.INT, d -> d.integer);
private static final Codec<Asymmetry<Consumer<WithDataElements>, WithDataElements>> CODEC = DataElementType.codec(true, STRING, INTEGER);
private static final Codec<Asymmetry<Consumer<WithDataElements>, WithDataElements>> CHANGED_CODEC = DataElementType.codec(false, STRING, INTEGER);

private final DataElement<String> string = STRING.create();
private final DataElement<Integer> integer = INTEGER.create();
private final DataElement<String> string = new DataElement.Simple<>("");
private final DataElement<Integer> integer = new DataElement.Simple<>(0);

@Override
public boolean equals(Object o) {
Expand Down
2 changes: 1 addition & 1 deletion version.properties
Original file line number Diff line number Diff line change
@@ -1 +1 @@
version=2.1.0
version=2.2.0

0 comments on commit ad12ebd

Please sign in to comment.