summary refs log tree commit diff stats
path: root/src/main/java/ganarchy/friendcode/client/WaitingForFriendCodeScreen.java
diff options
context:
space:
mode:
Diffstat (limited to 'src/main/java/ganarchy/friendcode/client/WaitingForFriendCodeScreen.java')
-rw-r--r--src/main/java/ganarchy/friendcode/client/WaitingForFriendCodeScreen.java93
1 files changed, 93 insertions, 0 deletions
diff --git a/src/main/java/ganarchy/friendcode/client/WaitingForFriendCodeScreen.java b/src/main/java/ganarchy/friendcode/client/WaitingForFriendCodeScreen.java
new file mode 100644
index 0000000..8429a41
--- /dev/null
+++ b/src/main/java/ganarchy/friendcode/client/WaitingForFriendCodeScreen.java
@@ -0,0 +1,93 @@
+package ganarchy.friendcode.client;
+
+import net.minecraft.client.gui.screen.LoadingDisplay;
+import net.minecraft.client.gui.screen.Screen;
+import net.minecraft.client.gui.widget.ButtonWidget;
+import net.minecraft.client.util.math.MatrixStack;
+import net.minecraft.screen.ScreenTexts;
+import net.minecraft.text.MutableText;
+import net.minecraft.text.Text;
+import net.minecraft.util.Util;
+import org.apache.commons.codec.binary.Base32;
+
+import java.nio.charset.StandardCharsets;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.util.Base64;
+import java.util.Locale;
+
+public class WaitingForFriendCodeScreen extends Screen {
+    private final I2PSamPinger samPinger;
+
+    public WaitingForFriendCodeScreen(I2PSamPinger samPinger) {
+        super(Text.translatable("friendcode.opening"));
+        this.samPinger = samPinger;
+    }
+
+    @Override
+    protected void init() {
+        // cancel friend code.
+        this.addDrawableChild(new ButtonWidget(
+                this.width / 2 - 155,
+                this.height - 28,
+                310,
+                20,
+                ScreenTexts.CANCEL,
+                button -> this.close()
+        ));
+    }
+
+    @Override
+    public void render(MatrixStack matrices, int mouseX, int mouseY, float delta) {
+        this.renderBackground(matrices);
+        WaitingForFriendCodeScreen.drawCenteredText(matrices, this.textRenderer, this.title, this.width / 2, 50, 0xFFFFFF);
+        final String string = LoadingDisplay.get(Util.getMeasuringTimeMs());
+        this.client.textRenderer.draw(matrices, string, (float)(this.client.currentScreen.width / 2 - this.client.textRenderer.getWidth(string) / 2), (float)(this.client.currentScreen.height / 2 + this.client.textRenderer.fontHeight), 0x808080);
+        super.render(matrices, mouseX, mouseY, delta);
+    }
+
+    @Override
+    public void close() {
+        super.close();
+        this.samPinger.stopSam();
+        final MutableText text = Text.translatable("friendcode.publish.stopped");
+        this.client.inGameHud.getChatHud().addMessage(text);
+    }
+
+    @Override
+    public void tick() {
+        super.tick();
+        if (samPinger.status() != I2PSamPinger.Status.IDLE) {
+            this.client.setScreen(null);
+            switch (samPinger.status()) {
+                case CONNECTION_FAILED -> {
+                    final MutableText text = Text.translatable("friendcode.publish.no_i2p");
+                    this.client.inGameHud.getChatHud().addMessage(text);
+                    break;
+                }
+                case SETUP_FAILED, CONNECTION_CLOSED -> {
+                    final MutableText text = Text.translatable("friendcode.publish.failed");
+                    this.client.inGameHud.getChatHud().addMessage(text);
+                    break;
+                }
+                case RUNNING -> {
+                    // convert from I2P base64 to URL-safe base64 so we don't have to write our own Base64 decoder
+                    final String pubkey_b64 = samPinger.pubkey().replace('~', '_');
+                    final byte[] pubkey = Base64.getUrlDecoder().decode(pubkey_b64.getBytes(StandardCharsets.UTF_8));
+                    // a .b32.i2p is just a Base32-encoded SHA256
+                    final String b32;
+                    try {
+                        b32 = new Base32().encodeAsString(MessageDigest.getInstance("SHA-256").digest(pubkey));
+                    } catch (NoSuchAlgorithmException e) {
+                        throw new RuntimeException(e);
+                    }
+                    // but we wanna massage it a little
+                    final String b32_i2p = b32.replaceFirst("=+$", "").toLowerCase(Locale.ROOT) + ".b32.i2p";
+                    final MutableText text = Text.translatable("friendcode.publish.started", b32_i2p);
+                    this.client.inGameHud.getChatHud().addMessage(text);
+                    break;
+                }
+            }
+        }
+    }
+}