Skip to content

Commit 453d32a

Browse files
committed
Improve shadow support a bit
1 parent 47cbeab commit 453d32a

13 files changed

Lines changed: 239 additions & 115 deletions

gradle.properties

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ org.gradle.jvmargs=-Xmx1G
33

44
# Fabric Properties
55
# check these on https://fabricmc.net/use
6-
minecraft_version=1.21.5-pre3
7-
yarn_mappings=1.21.5-pre3+build.2
6+
minecraft_version=1.21.5-rc1
7+
yarn_mappings=1.21.5-rc1+build.1
88
loader_version=0.16.10
99

1010
#Fabric api

src/main/java/eu/pb4/placeholders/api/ParserContext.java

Lines changed: 20 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,38 @@
11
package eu.pb4.placeholders.api;
22

3+
import eu.pb4.placeholders.api.node.parent.DynamicShadowNode;
34
import net.minecraft.registry.RegistryWrapper;
5+
import net.minecraft.text.Text;
46
import org.jetbrains.annotations.Nullable;
57

68
import java.util.HashMap;
79
import java.util.Map;
810
import java.util.Objects;
11+
import java.util.function.Function;
912
import java.util.function.Supplier;
1013

1114
public final class ParserContext {
12-
private final Map<Key<?>, Object> map = new HashMap<>();
15+
private Map<Key<?>, Object> map;
16+
private boolean copyOnWrite;
1317

14-
private ParserContext() {}
18+
private ParserContext(Map<Key<?>, Object> map, boolean copyOnWrite) {
19+
this.map = map;
20+
this.copyOnWrite = copyOnWrite;
21+
}
1522

1623
public static ParserContext of() {
17-
return new ParserContext();
24+
return new ParserContext(new HashMap<>(), false);
1825
}
1926

2027
public static <T> ParserContext of(Key<T> key, T object) {
21-
return new ParserContext().with(key, object);
28+
return of().with(key, object);
2229
}
2330

2431
public <T> ParserContext with(Key<T> key, T object) {
32+
if (this.copyOnWrite) {
33+
this.map = new HashMap<>(this.map);
34+
this.copyOnWrite = false;
35+
}
2536
this.map.put(key, object);
2637
return this;
2738
}
@@ -55,13 +66,16 @@ public boolean contains(Key<?> key) {
5566
return this.map.containsKey(key);
5667
}
5768

58-
69+
public ParserContext copy() {
70+
this.copyOnWrite = true;
71+
return new ParserContext(this.map, true);
72+
}
5973

6074

6175
public record Key<T>(String key, @Nullable Class<T> type) {
6276
public static final Key<Boolean> COMPACT_TEXT = new Key<>("compact_text", Boolean.class);
6377
public static final Key<RegistryWrapper.WrapperLookup> WRAPPER_LOOKUP = new Key<>("wrapper_lookup", RegistryWrapper.WrapperLookup.class);
64-
public static final Key<Integer> DEFAULT_TEXT_COLOR = new Key<>("default_text_color", Integer.class);
78+
public static final Key<DynamicShadowNode.Transformer> DEFAULT_SHADOW_STYLER = Key.of("default_shadow_styler");
6579

6680
public static <T> Key<T> of(String key, T type) {
6781
//noinspection unchecked

src/main/java/eu/pb4/placeholders/api/node/parent/ColorBasedShadowNode.java

Lines changed: 0 additions & 46 deletions
This file was deleted.

src/main/java/eu/pb4/placeholders/api/node/parent/ColorNode.java

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,12 @@
33
import eu.pb4.placeholders.api.ParserContext;
44
import eu.pb4.placeholders.api.node.TextNode;
55
import net.minecraft.text.Style;
6+
import net.minecraft.text.Text;
67
import net.minecraft.text.TextColor;
78

89
import java.util.Arrays;
910

10-
public final class ColorNode extends SimpleStylingNode {
11+
public final class ColorNode extends SimpleStylingNode implements DynamicShadowNode.SimpleColoredTransformer {
1112
private final TextColor color;
1213

1314
public ColorNode(TextNode[] children, TextColor color) {
@@ -32,4 +33,9 @@ public String toString() {
3233
", children=" + Arrays.toString(children) +
3334
'}';
3435
}
36+
37+
@Override
38+
public int getDefaultShadowColor(Text out, float scale, float alpha, ParserContext context) {
39+
return DynamicShadowNode.modifiedColor(this.color.getRgb(), scale, alpha);
40+
}
3541
}

src/main/java/eu/pb4/placeholders/api/node/parent/DynamicColorNode.java

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,12 @@
44
import eu.pb4.placeholders.api.node.TextNode;
55
import eu.pb4.placeholders.api.parsers.NodeParser;
66
import net.minecraft.text.Style;
7+
import net.minecraft.text.Text;
78
import net.minecraft.text.TextColor;
89

910
import java.util.Arrays;
1011

11-
public final class DynamicColorNode extends SimpleStylingNode {
12+
public final class DynamicColorNode extends SimpleStylingNode implements DynamicShadowNode.SimpleColoredTransformer {
1213
private final TextNode color;
1314

1415
public DynamicColorNode(TextNode[] children, TextNode color) {
@@ -44,4 +45,19 @@ public String toString() {
4445
", children=" + Arrays.toString(children) +
4546
'}';
4647
}
48+
49+
@Override
50+
public int getDefaultShadowColor(Text out, float scale, float alpha, ParserContext context) {
51+
var color = TextColor.parse(this.color.toText(context).getString());
52+
53+
if (color.result().isPresent()) {
54+
return DynamicShadowNode.modifiedColor(color.getOrThrow().getRgb(), scale, alpha);
55+
}
56+
return 0;
57+
}
58+
59+
@Override
60+
public boolean hasShadowColor(ParserContext context) {
61+
return TextColor.parse(this.color.toText(context).getString()).result().isPresent();
62+
}
4763
}
Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,76 @@
1+
package eu.pb4.placeholders.api.node.parent;
2+
3+
import eu.pb4.placeholders.api.ParserContext;
4+
import eu.pb4.placeholders.api.node.TextNode;
5+
import eu.pb4.placeholders.impl.GeneralUtils;
6+
import net.minecraft.text.MutableText;
7+
import net.minecraft.text.Text;
8+
import net.minecraft.util.math.ColorHelper;
9+
10+
public final class DynamicShadowNode extends ParentNode {
11+
private final float scale;
12+
private final float alpha;
13+
14+
public DynamicShadowNode(TextNode[] children) {
15+
this(children, 0.25f, 1f);
16+
}
17+
18+
public DynamicShadowNode(TextNode[] children, float scale, float alpha) {
19+
super(children);
20+
this.scale = scale;
21+
this.alpha = alpha;
22+
}
23+
24+
@Override
25+
protected Text applyFormatting(MutableText out, ParserContext context) {
26+
var transformer = context.get(ParserContext.Key.DEFAULT_SHADOW_STYLER);
27+
if (transformer == null) {
28+
var defaultColor = modifiedColor(out.getStyle().getColor() != null ? out.getStyle().getColor().getRgb() : 0xFFFFFF, this.scale, this.alpha);
29+
30+
return GeneralUtils.cloneTransformText(out, text -> {
31+
var color = text.getStyle().getColor();
32+
return text.setStyle(text.getStyle().withShadowColor(color != null ? modifiedColor(color.getRgb(), this.scale, this.alpha) : defaultColor));
33+
}, text -> text == out || text.getStyle().getShadowColor() == null && text.getStyle().getColor() != null);
34+
}
35+
36+
37+
return transformer.applyShadowColors(out, this.scale, this.alpha, context);
38+
}
39+
40+
public static int modifiedColor(int color, float scale, float alpha) {
41+
return ColorHelper.scaleRgb(color, scale) | 0xFF000000;
42+
}
43+
44+
@Override
45+
public ParentTextNode copyWith(TextNode[] children) {
46+
return new DynamicShadowNode(children, this.scale, this.alpha);
47+
}
48+
49+
@Override
50+
public String toString() {
51+
return "DynamicShadowNode{" +
52+
"scale=" + scale +
53+
'}';
54+
}
55+
56+
public interface Transformer {
57+
Text applyShadowColors(Text text, float scale, float alpha, ParserContext context);
58+
59+
default boolean hasShadowColor(ParserContext context) {
60+
return true;
61+
}
62+
}
63+
64+
public interface SimpleColoredTransformer extends Transformer {
65+
@Override
66+
default Text applyShadowColors(Text out, float scale, float alpha, ParserContext context) {
67+
var defaultColor = this.getDefaultShadowColor(out, scale, alpha, context);
68+
return GeneralUtils.cloneTransformText(out, text -> {
69+
var color = text.getStyle().getColor();
70+
return text.setStyle(text.getStyle().withShadowColor(color != null ? modifiedColor(color.getRgb(), scale, alpha) : defaultColor));
71+
}, text -> text == out || text.getStyle().getShadowColor() == null && text.getStyle().getColor() != null);
72+
}
73+
74+
int getDefaultShadowColor(Text out, float scale, float alpha, ParserContext context);
75+
}
76+
}

src/main/java/eu/pb4/placeholders/api/node/parent/FormattingNode.java

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,12 +5,13 @@
55
import net.minecraft.text.MutableText;
66
import net.minecraft.text.Style;
77
import net.minecraft.text.Text;
8+
import net.minecraft.text.TextColor;
89
import net.minecraft.util.Formatting;
910

1011
import java.util.Arrays;
1112

1213

13-
public final class FormattingNode extends SimpleStylingNode {
14+
public final class FormattingNode extends SimpleStylingNode implements DynamicShadowNode.SimpleColoredTransformer {
1415
private final Formatting[] formatting;
1516

1617
public FormattingNode(TextNode[] children, Formatting formatting) {
@@ -39,4 +40,25 @@ public String toString() {
3940
", children=" + Arrays.toString(children) +
4041
'}';
4142
}
43+
44+
@Override
45+
public int getDefaultShadowColor(Text out, float scale, float alpha, ParserContext context) {
46+
for (var form : formatting) {
47+
if (form.isColor()) {
48+
//noinspection DataFlowIssue
49+
return DynamicShadowNode.modifiedColor(form.getColorValue(), scale, alpha);
50+
}
51+
}
52+
return -1;
53+
}
54+
55+
@Override
56+
public boolean hasShadowColor(ParserContext context) {
57+
for (var form : formatting) {
58+
if (form.isColor()) {
59+
return true;
60+
}
61+
}
62+
return false;
63+
}
4264
}

src/main/java/eu/pb4/placeholders/api/node/parent/GradientNode.java

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
import java.util.Arrays;
1616
import java.util.List;
1717

18-
public final class GradientNode extends ParentNode {
18+
public final class GradientNode extends ParentNode implements DynamicShadowNode.Transformer {
1919
private final GradientProvider gradientProvider;
2020

2121
public GradientNode(TextNode[] children, GradientProvider gradientBuilder) {
@@ -85,6 +85,11 @@ public String toString() {
8585
'}';
8686
}
8787

88+
@Override
89+
public Text applyShadowColors(Text text, float scale, float alpha, ParserContext context) {
90+
return GeneralUtils.toGradientShadow(text, scale, alpha, this.gradientProvider);
91+
}
92+
8893
@FunctionalInterface
8994
public interface GradientProvider {
9095
TextColor getColorAt(int index, int length);

src/main/java/eu/pb4/placeholders/api/node/parent/ParentNode.java

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -35,15 +35,21 @@ public ParentTextNode copyWith(TextNode[] children) {
3535
@Override
3636
public final Text toText(ParserContext context, boolean removeBackslashes) {
3737
var compact = context != null && context.get(ParserContext.Key.COMPACT_TEXT) != Boolean.FALSE;
38+
var oldShadow = context.get(ParserContext.Key.DEFAULT_SHADOW_STYLER);
39+
40+
if (this instanceof DynamicShadowNode.Transformer transformer && transformer.hasShadowColor(context)) {
41+
context.with(ParserContext.Key.DEFAULT_SHADOW_STYLER, transformer);
42+
}
3843

3944
if (this.children.length == 0) {
45+
context.with(ParserContext.Key.DEFAULT_SHADOW_STYLER, oldShadow);
4046
return Text.empty();
4147
} else if ((this.children.length == 1 && this.children[0] != null) && compact) {
4248
var out = this.children[0].toText(context, true);
4349
if (GeneralUtils.isEmpty(out)) {
4450
return out;
4551
}
46-
52+
context.with(ParserContext.Key.DEFAULT_SHADOW_STYLER, oldShadow);
4753
return this.applyFormatting(out.copy(), context);
4854
} else {
4955
MutableText base = compact ? null : Text.empty();
@@ -66,6 +72,7 @@ public final Text toText(ParserContext context, boolean removeBackslashes) {
6672
}
6773
}
6874
}
75+
context.with(ParserContext.Key.DEFAULT_SHADOW_STYLER, oldShadow);
6976

7077
if (base == null || GeneralUtils.isEmpty(base)) {
7178
return Text.empty();
@@ -75,7 +82,9 @@ public final Text toText(ParserContext context, boolean removeBackslashes) {
7582
}
7683
}
7784

78-
protected Text applyFormatting(MutableText out, ParserContext context) { return out.setStyle(applyFormatting(out.getStyle(), context)); };
85+
protected Text applyFormatting(MutableText out, ParserContext context) {
86+
return out.setStyle(applyFormatting(out.getStyle(), context));
87+
}
7988

8089
protected Style applyFormatting(Style style, ParserContext context) {
8190
return style;

0 commit comments

Comments
 (0)