Skip to content

Commit bc9aa54

Browse files
committed
Todo: Emoji chat renderer
1 parent 5212a3b commit bc9aa54

File tree

3 files changed

+52
-21
lines changed

3 files changed

+52
-21
lines changed

common/src/main/java/com/lambda/mixin/render/ChatScreenMixin.java

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,44 @@
11
package com.lambda.mixin.render;
22

33
import com.lambda.command.CommandManager;
4+
import com.lambda.graphics.renderer.gui.font.FontRenderer;
5+
import com.lambda.graphics.renderer.gui.font.LambdaEmoji;
6+
import com.lambda.graphics.renderer.gui.font.glyph.GlyphInfo;
7+
import kotlin.Pair;
8+
import kotlin.ranges.IntRange;
49
import net.minecraft.client.gui.screen.ChatScreen;
510
import org.spongepowered.asm.mixin.Mixin;
611
import org.spongepowered.asm.mixin.injection.At;
712
import org.spongepowered.asm.mixin.injection.Inject;
13+
import org.spongepowered.asm.mixin.injection.ModifyArg;
814
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
915

16+
import java.util.Collections;
17+
import java.util.List;
18+
1019
@Mixin(ChatScreen.class)
1120
public abstract class ChatScreenMixin {
21+
@ModifyArg(method = "sendMessage", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/network/ClientPlayNetworkHandler;sendChatMessage(Ljava/lang/String;)V"), index = 0)
22+
private String modifyChatText(String chatText) {
23+
List<Pair<GlyphInfo, IntRange>> emojis = FontRenderer.Companion.parseEmojis(chatText, LambdaEmoji.Twemoji);
24+
Collections.reverse(emojis);
25+
26+
for (Pair<GlyphInfo, IntRange> emoji : emojis) {
27+
String emojiString = chatText.substring(emoji.getSecond().getStart() + 1, emoji.getSecond().getEndInclusive());
28+
if (LambdaEmoji.Twemoji.get(emojiString) == null)
29+
continue;
30+
31+
// Because the width of a char is bigger than an emoji
32+
// we can simply replace the matches string by a space
33+
// and render it after the text
34+
chatText = chatText.substring(0, emoji.getSecond().getStart()) + " " + chatText.substring(emoji.getSecond().getEndInclusive() + 1);
35+
36+
// TODO: Build a renderer for the emojis
37+
// TODO: Render the emojis at their correct position
38+
}
39+
40+
return chatText;
41+
}
1242

1343
@Inject(method = "sendMessage", at = @At("HEAD"), cancellable = true)
1444
void sendMessageInject(String chatText, boolean addToHistory, CallbackInfoReturnable<Boolean> cir) {

common/src/main/kotlin/com/lambda/graphics/renderer/gui/font/FontRenderer.kt

Lines changed: 21 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -19,22 +19,6 @@ class FontRenderer(
1919
private val vao = VAO(VertexMode.TRIANGLES, VertexAttrib.Group.FONT)
2020

2121
private val scaleMultiplier = 1.0
22-
private val emojiRegex = Regex(":[a-zA-Z0-9_]+:")
23-
24-
/**
25-
* Parses the emojis in the given text.
26-
*
27-
* @param text The text to parse.
28-
* @return A list of pairs containing the glyph info and the range of the emoji in the text.
29-
*/
30-
fun parseEmojis(text: String) =
31-
mutableListOf<Pair<GlyphInfo, IntRange>>().apply {
32-
emojiRegex.findAll(text).forEach { match ->
33-
val emojiKey = match.value.substring(1, match.value.length - 1)
34-
val charInfo = emojis[emojiKey] ?: return@forEach
35-
add(charInfo to match.range)
36-
}
37-
}
3822

3923
/**
4024
* Builds the vertex array for rendering the text.
@@ -101,7 +85,7 @@ class FontRenderer(
10185
var posX = 0.0
10286
val posY = getHeight(scale) * -0.5 + baselineOffset * actualScale
10387

104-
val emojis = parseEmojis(text)
88+
val emojis = parseEmojis(text, emojis)
10589

10690
fun draw(info: GlyphInfo, color: Color, offset: Double = 0.0) {
10791
val scaledSize = info.size * actualScale
@@ -170,8 +154,25 @@ class FontRenderer(
170154
companion object {
171155
private val shader = Shader("renderer/font")
172156

173-
private val shadowShift get() = RenderSettings.shadowShift * 5.0
174-
private val baselineOffset get() = RenderSettings.baselineOffset * 2.0f - 10f
175-
private val gap get() = RenderSettings.gap * 0.5f - 0.8f
157+
val shadowShift get() = RenderSettings.shadowShift * 5.0
158+
val baselineOffset get() = RenderSettings.baselineOffset * 2.0f - 10f
159+
val gap get() = RenderSettings.gap * 0.5f - 0.8f
160+
161+
private val emojiRegex = Regex(":[a-zA-Z0-9_]+:")
162+
163+
/**
164+
* Parses the emojis in the given text.
165+
*
166+
* @param text The text to parse.
167+
* @return A list of pairs containing the glyph info and the range of the emoji in the text.
168+
*/
169+
fun parseEmojis(text: String, emojis: LambdaEmoji) =
170+
mutableListOf<Pair<GlyphInfo, IntRange>>().apply {
171+
emojiRegex.findAll(text).forEach { match ->
172+
val emojiKey = match.value.substring(1, match.value.length - 1)
173+
val charInfo = emojis[emojiKey] ?: return@forEach
174+
add(charInfo to match.range)
175+
}
176+
}
176177
}
177178
}

common/src/main/kotlin/com/lambda/graphics/renderer/gui/font/LambdaEmoji.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ import com.lambda.graphics.renderer.gui.font.glyph.EmojiGlyphs
66
enum class LambdaEmoji(private val zipUrl: String) {
77
Twemoji("https://github.com/Edouard127/emoji-generator/releases/latest/download/emojis.zip");
88

9-
lateinit var glyphs: EmojiGlyphs // TODO: Support multiple emoji pools
9+
lateinit var glyphs: EmojiGlyphs
1010

1111
operator fun get(emoji: String) = glyphs.getEmoji(emoji)
1212

0 commit comments

Comments
 (0)