470 lines
17 KiB
Java
470 lines
17 KiB
Java
package com.mojang.realmsclient.gui.screens;
|
|
|
|
import com.google.common.collect.Lists;
|
|
import com.mojang.logging.LogUtils;
|
|
import com.mojang.realmsclient.RealmsMainScreen;
|
|
import com.mojang.realmsclient.client.RealmsClient;
|
|
import com.mojang.realmsclient.dto.RealmsServer;
|
|
import com.mojang.realmsclient.dto.RealmsWorldOptions;
|
|
import com.mojang.realmsclient.dto.WorldTemplate;
|
|
import com.mojang.realmsclient.dto.RealmsServer.WorldType;
|
|
import com.mojang.realmsclient.dto.WorldTemplate.WorldTemplateType;
|
|
import com.mojang.realmsclient.exception.RealmsServiceException;
|
|
import com.mojang.realmsclient.gui.RealmsWorldSlotButton;
|
|
import com.mojang.realmsclient.gui.RealmsWorldSlotButton.State;
|
|
import com.mojang.realmsclient.util.task.CloseServerTask;
|
|
import com.mojang.realmsclient.util.task.OpenServerTask;
|
|
import com.mojang.realmsclient.util.task.SwitchMinigameTask;
|
|
import com.mojang.realmsclient.util.task.SwitchSlotTask;
|
|
import java.util.List;
|
|
import java.util.Objects;
|
|
import java.util.function.Supplier;
|
|
import net.fabricmc.api.EnvType;
|
|
import net.fabricmc.api.Environment;
|
|
import net.minecraft.client.gui.GuiGraphics;
|
|
import net.minecraft.client.gui.components.Button;
|
|
import net.minecraft.client.renderer.RenderType;
|
|
import net.minecraft.network.chat.CommonComponents;
|
|
import net.minecraft.network.chat.Component;
|
|
import net.minecraft.realms.RealmsScreen;
|
|
import net.minecraft.resources.ResourceLocation;
|
|
import net.minecraft.util.StringUtil;
|
|
import org.jetbrains.annotations.Nullable;
|
|
import org.slf4j.Logger;
|
|
|
|
@Environment(EnvType.CLIENT)
|
|
public class RealmsConfigureWorldScreen extends RealmsScreen {
|
|
private static final ResourceLocation EXPIRED_SPRITE = ResourceLocation.withDefaultNamespace("realm_status/expired");
|
|
private static final ResourceLocation EXPIRES_SOON_SPRITE = ResourceLocation.withDefaultNamespace("realm_status/expires_soon");
|
|
private static final ResourceLocation OPEN_SPRITE = ResourceLocation.withDefaultNamespace("realm_status/open");
|
|
private static final ResourceLocation CLOSED_SPRITE = ResourceLocation.withDefaultNamespace("realm_status/closed");
|
|
private static final Logger LOGGER = LogUtils.getLogger();
|
|
private static final Component WORLD_LIST_TITLE = Component.translatable("mco.configure.worlds.title");
|
|
private static final Component TITLE = Component.translatable("mco.configure.world.title");
|
|
private static final Component SERVER_EXPIRED_TOOLTIP = Component.translatable("mco.selectServer.expired");
|
|
private static final Component SERVER_EXPIRING_SOON_TOOLTIP = Component.translatable("mco.selectServer.expires.soon");
|
|
private static final Component SERVER_EXPIRING_IN_DAY_TOOLTIP = Component.translatable("mco.selectServer.expires.day");
|
|
private static final Component SERVER_OPEN_TOOLTIP = Component.translatable("mco.selectServer.open");
|
|
private static final Component SERVER_CLOSED_TOOLTIP = Component.translatable("mco.selectServer.closed");
|
|
private static final int DEFAULT_BUTTON_WIDTH = 80;
|
|
private static final int DEFAULT_BUTTON_OFFSET = 5;
|
|
@Nullable
|
|
private Component toolTip;
|
|
private final RealmsMainScreen lastScreen;
|
|
@Nullable
|
|
private RealmsServer serverData;
|
|
private final long serverId;
|
|
private int leftX;
|
|
private int rightX;
|
|
private Button playersButton;
|
|
private Button settingsButton;
|
|
private Button subscriptionButton;
|
|
private Button optionsButton;
|
|
private Button backupButton;
|
|
private Button resetWorldButton;
|
|
private Button switchMinigameButton;
|
|
private boolean stateChanged;
|
|
private final List<RealmsWorldSlotButton> slotButtonList = Lists.<RealmsWorldSlotButton>newArrayList();
|
|
|
|
public RealmsConfigureWorldScreen(RealmsMainScreen lastScreen, long serverId) {
|
|
super(TITLE);
|
|
this.lastScreen = lastScreen;
|
|
this.serverId = serverId;
|
|
}
|
|
|
|
@Override
|
|
public void init() {
|
|
if (this.serverData == null) {
|
|
this.fetchServerData(this.serverId);
|
|
}
|
|
|
|
this.leftX = this.width / 2 - 187;
|
|
this.rightX = this.width / 2 + 190;
|
|
this.playersButton = this.addRenderableWidget(
|
|
Button.builder(
|
|
Component.translatable("mco.configure.world.buttons.players"), button -> this.minecraft.setScreen(new RealmsPlayerScreen(this, this.serverData))
|
|
)
|
|
.bounds(this.centerButton(0, 3), row(0), 100, 20)
|
|
.build()
|
|
);
|
|
this.settingsButton = this.addRenderableWidget(
|
|
Button.builder(
|
|
Component.translatable("mco.configure.world.buttons.settings"),
|
|
button -> this.minecraft.setScreen(new RealmsSettingsScreen(this, this.serverData.clone()))
|
|
)
|
|
.bounds(this.centerButton(1, 3), row(0), 100, 20)
|
|
.build()
|
|
);
|
|
this.subscriptionButton = this.addRenderableWidget(
|
|
Button.builder(
|
|
Component.translatable("mco.configure.world.buttons.subscription"),
|
|
button -> this.minecraft.setScreen(new RealmsSubscriptionInfoScreen(this, this.serverData.clone(), this.lastScreen))
|
|
)
|
|
.bounds(this.centerButton(2, 3), row(0), 100, 20)
|
|
.build()
|
|
);
|
|
this.slotButtonList.clear();
|
|
|
|
for (int i = 1; i < 5; i++) {
|
|
this.slotButtonList.add(this.addSlotButton(i));
|
|
}
|
|
|
|
this.switchMinigameButton = this.addRenderableWidget(
|
|
Button.builder(
|
|
Component.translatable("mco.configure.world.buttons.switchminigame"),
|
|
button -> this.minecraft
|
|
.setScreen(
|
|
new RealmsSelectWorldTemplateScreen(Component.translatable("mco.template.title.minigame"), this::templateSelectionCallback, WorldType.MINIGAME)
|
|
)
|
|
)
|
|
.bounds(this.leftButton(0), row(13) - 5, 100, 20)
|
|
.build()
|
|
);
|
|
this.optionsButton = this.addRenderableWidget(
|
|
Button.builder(
|
|
Component.translatable("mco.configure.world.buttons.options"),
|
|
button -> this.minecraft
|
|
.setScreen(
|
|
new RealmsSlotOptionsScreen(
|
|
this, ((RealmsWorldOptions)this.serverData.slots.get(this.serverData.activeSlot)).clone(), this.serverData.worldType, this.serverData.activeSlot
|
|
)
|
|
)
|
|
)
|
|
.bounds(this.leftButton(0), row(13) - 5, 90, 20)
|
|
.build()
|
|
);
|
|
this.backupButton = this.addRenderableWidget(
|
|
Button.builder(
|
|
Component.translatable("mco.configure.world.backup"),
|
|
button -> this.minecraft.setScreen(new RealmsBackupScreen(this, this.serverData.clone(), this.serverData.activeSlot))
|
|
)
|
|
.bounds(this.leftButton(1), row(13) - 5, 90, 20)
|
|
.build()
|
|
);
|
|
this.resetWorldButton = this.addRenderableWidget(
|
|
Button.builder(
|
|
Component.translatable("mco.configure.world.buttons.resetworld"),
|
|
button -> this.minecraft
|
|
.setScreen(
|
|
RealmsResetWorldScreen.forResetSlot(this, this.serverData.clone(), () -> this.minecraft.execute(() -> this.minecraft.setScreen(this.getNewScreen())))
|
|
)
|
|
)
|
|
.bounds(this.leftButton(2), row(13) - 5, 90, 20)
|
|
.build()
|
|
);
|
|
this.addRenderableWidget(Button.builder(CommonComponents.GUI_BACK, button -> this.onClose()).bounds(this.rightX - 80 + 8, row(13) - 5, 70, 20).build());
|
|
this.backupButton.active = true;
|
|
if (this.serverData == null) {
|
|
this.hideMinigameButtons();
|
|
this.hideRegularButtons();
|
|
this.playersButton.active = false;
|
|
this.settingsButton.active = false;
|
|
this.subscriptionButton.active = false;
|
|
} else {
|
|
this.disableButtons();
|
|
if (this.isMinigame()) {
|
|
this.hideRegularButtons();
|
|
} else {
|
|
this.hideMinigameButtons();
|
|
}
|
|
}
|
|
}
|
|
|
|
private RealmsWorldSlotButton addSlotButton(int index) {
|
|
int i = this.frame(index);
|
|
int j = row(5) + 5;
|
|
RealmsWorldSlotButton realmsWorldSlotButton = new RealmsWorldSlotButton(i, j, 80, 80, index, button -> {
|
|
State state = ((RealmsWorldSlotButton)button).getState();
|
|
if (state != null) {
|
|
switch (state.action) {
|
|
case NOTHING:
|
|
break;
|
|
case JOIN:
|
|
this.joinRealm(this.serverData);
|
|
break;
|
|
case SWITCH_SLOT:
|
|
if (state.minigame) {
|
|
this.switchToMinigame();
|
|
} else if (state.empty) {
|
|
this.switchToEmptySlot(index, this.serverData);
|
|
} else {
|
|
this.switchToFullSlot(index, this.serverData);
|
|
}
|
|
break;
|
|
default:
|
|
throw new IllegalStateException("Unknown action " + state.action);
|
|
}
|
|
}
|
|
});
|
|
if (this.serverData != null) {
|
|
realmsWorldSlotButton.setServerData(this.serverData);
|
|
}
|
|
|
|
return this.addRenderableWidget(realmsWorldSlotButton);
|
|
}
|
|
|
|
private int leftButton(int index) {
|
|
return this.leftX + index * 95;
|
|
}
|
|
|
|
private int centerButton(int row, int column) {
|
|
return this.width / 2 - (column * 105 - 5) / 2 + row * 105;
|
|
}
|
|
|
|
@Override
|
|
public void render(GuiGraphics guiGraphics, int mouseX, int mouseY, float partialTick) {
|
|
super.render(guiGraphics, mouseX, mouseY, partialTick);
|
|
this.toolTip = null;
|
|
guiGraphics.drawCenteredString(this.font, WORLD_LIST_TITLE, this.width / 2, row(4), -1);
|
|
if (this.serverData == null) {
|
|
guiGraphics.drawCenteredString(this.font, this.title, this.width / 2, 17, -1);
|
|
} else {
|
|
String string = (String)Objects.requireNonNullElse(this.serverData.getName(), "");
|
|
int i = this.font.width(string);
|
|
int j = this.serverData.state == com.mojang.realmsclient.dto.RealmsServer.State.CLOSED ? -6250336 : 8388479;
|
|
int k = this.font.width(this.title);
|
|
guiGraphics.drawCenteredString(this.font, this.title, this.width / 2, 12, -1);
|
|
guiGraphics.drawCenteredString(this.font, string, this.width / 2, 24, j);
|
|
int l = Math.min(this.centerButton(2, 3) + 80 - 11, this.width / 2 + i / 2 + k / 2 + 10);
|
|
this.drawServerStatus(guiGraphics, l, 7, mouseX, mouseY);
|
|
if (this.isMinigame()) {
|
|
String string2 = this.serverData.getMinigameName();
|
|
if (string2 != null) {
|
|
guiGraphics.drawString(this.font, Component.translatable("mco.configure.world.minigame", string2), this.leftX + 80 + 20 + 10, row(13), -1);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
private int frame(int index) {
|
|
return this.leftX + (index - 1) * 98;
|
|
}
|
|
|
|
@Override
|
|
public void onClose() {
|
|
this.minecraft.setScreen(this.lastScreen);
|
|
if (this.stateChanged) {
|
|
this.lastScreen.resetScreen();
|
|
}
|
|
}
|
|
|
|
public void fetchServerData(long serverId) {
|
|
new Thread(() -> {
|
|
RealmsClient realmsClient = RealmsClient.getOrCreate();
|
|
|
|
try {
|
|
RealmsServer realmsServer = realmsClient.getOwnRealm(serverId);
|
|
this.minecraft.execute(() -> {
|
|
this.serverData = realmsServer;
|
|
this.disableButtons();
|
|
if (this.isMinigame()) {
|
|
this.show(this.switchMinigameButton);
|
|
} else {
|
|
this.show(this.optionsButton);
|
|
this.show(this.backupButton);
|
|
this.show(this.resetWorldButton);
|
|
}
|
|
|
|
for (RealmsWorldSlotButton realmsWorldSlotButton : this.slotButtonList) {
|
|
realmsWorldSlotButton.setServerData(realmsServer);
|
|
}
|
|
});
|
|
} catch (RealmsServiceException var5) {
|
|
LOGGER.error("Couldn't get own world", (Throwable)var5);
|
|
this.minecraft.execute(() -> this.minecraft.setScreen(new RealmsGenericErrorScreen(var5, this.lastScreen)));
|
|
}
|
|
}).start();
|
|
}
|
|
|
|
private void disableButtons() {
|
|
this.playersButton.active = !this.serverData.expired;
|
|
this.settingsButton.active = !this.serverData.expired;
|
|
this.subscriptionButton.active = true;
|
|
this.switchMinigameButton.active = !this.serverData.expired;
|
|
this.optionsButton.active = !this.serverData.expired;
|
|
this.resetWorldButton.active = !this.serverData.expired;
|
|
}
|
|
|
|
private void joinRealm(RealmsServer server) {
|
|
if (this.serverData.state == com.mojang.realmsclient.dto.RealmsServer.State.OPEN) {
|
|
RealmsMainScreen.play(server, this);
|
|
} else {
|
|
this.openTheWorld(true);
|
|
}
|
|
}
|
|
|
|
private void switchToMinigame() {
|
|
RealmsSelectWorldTemplateScreen realmsSelectWorldTemplateScreen = new RealmsSelectWorldTemplateScreen(
|
|
Component.translatable("mco.template.title.minigame"), this::templateSelectionCallback, WorldType.MINIGAME
|
|
);
|
|
realmsSelectWorldTemplateScreen.setWarning(Component.translatable("mco.minigame.world.info.line1"), Component.translatable("mco.minigame.world.info.line2"));
|
|
this.minecraft.setScreen(realmsSelectWorldTemplateScreen);
|
|
}
|
|
|
|
private void switchToFullSlot(int slot, RealmsServer server) {
|
|
this.minecraft
|
|
.setScreen(
|
|
RealmsPopups.infoPopupScreen(
|
|
this,
|
|
Component.translatable("mco.configure.world.slot.switch.question.line1"),
|
|
popupScreen -> {
|
|
this.stateChanged();
|
|
this.minecraft
|
|
.setScreen(
|
|
new RealmsLongRunningMcoTaskScreen(
|
|
this.lastScreen, new SwitchSlotTask(server.id, slot, () -> this.minecraft.execute(() -> this.minecraft.setScreen(this.getNewScreen())))
|
|
)
|
|
);
|
|
}
|
|
)
|
|
);
|
|
}
|
|
|
|
private void switchToEmptySlot(int slot, RealmsServer server) {
|
|
this.minecraft
|
|
.setScreen(
|
|
RealmsPopups.infoPopupScreen(
|
|
this,
|
|
Component.translatable("mco.configure.world.slot.switch.question.line1"),
|
|
popupScreen -> {
|
|
this.stateChanged();
|
|
RealmsResetWorldScreen realmsResetWorldScreen = RealmsResetWorldScreen.forEmptySlot(
|
|
this, slot, server, () -> this.minecraft.execute(() -> this.minecraft.setScreen(this.getNewScreen()))
|
|
);
|
|
this.minecraft.setScreen(realmsResetWorldScreen);
|
|
}
|
|
)
|
|
);
|
|
}
|
|
|
|
private void drawServerStatus(GuiGraphics guiGraphics, int x, int y, int mouseX, int mouseY) {
|
|
if (this.serverData.expired) {
|
|
this.drawRealmStatus(guiGraphics, x, y, mouseX, mouseY, EXPIRED_SPRITE, () -> SERVER_EXPIRED_TOOLTIP);
|
|
} else if (this.serverData.state == com.mojang.realmsclient.dto.RealmsServer.State.CLOSED) {
|
|
this.drawRealmStatus(guiGraphics, x, y, mouseX, mouseY, CLOSED_SPRITE, () -> SERVER_CLOSED_TOOLTIP);
|
|
} else if (this.serverData.state == com.mojang.realmsclient.dto.RealmsServer.State.OPEN) {
|
|
if (this.serverData.daysLeft < 7) {
|
|
this.drawRealmStatus(
|
|
guiGraphics,
|
|
x,
|
|
y,
|
|
mouseX,
|
|
mouseY,
|
|
EXPIRES_SOON_SPRITE,
|
|
() -> {
|
|
if (this.serverData.daysLeft <= 0) {
|
|
return SERVER_EXPIRING_SOON_TOOLTIP;
|
|
} else {
|
|
return (Component)(this.serverData.daysLeft == 1
|
|
? SERVER_EXPIRING_IN_DAY_TOOLTIP
|
|
: Component.translatable("mco.selectServer.expires.days", this.serverData.daysLeft));
|
|
}
|
|
}
|
|
);
|
|
} else {
|
|
this.drawRealmStatus(guiGraphics, x, y, mouseX, mouseY, OPEN_SPRITE, () -> SERVER_OPEN_TOOLTIP);
|
|
}
|
|
}
|
|
}
|
|
|
|
private void drawRealmStatus(GuiGraphics guiGraphics, int x, int y, int mouseX, int mouseY, ResourceLocation sprite, Supplier<Component> tooltipSupplier) {
|
|
guiGraphics.blitSprite(RenderType::guiTextured, sprite, x, y, 10, 28);
|
|
if (mouseX >= x && mouseX <= x + 9 && mouseY >= y && mouseY <= y + 27) {
|
|
this.setTooltipForNextRenderPass((Component)tooltipSupplier.get());
|
|
}
|
|
}
|
|
|
|
private boolean isMinigame() {
|
|
return this.serverData != null && this.serverData.isMinigameActive();
|
|
}
|
|
|
|
private void hideRegularButtons() {
|
|
this.hide(this.optionsButton);
|
|
this.hide(this.backupButton);
|
|
this.hide(this.resetWorldButton);
|
|
}
|
|
|
|
private void hide(Button button) {
|
|
button.visible = false;
|
|
}
|
|
|
|
private void show(Button button) {
|
|
button.visible = true;
|
|
}
|
|
|
|
private void hideMinigameButtons() {
|
|
this.hide(this.switchMinigameButton);
|
|
}
|
|
|
|
public void saveSlotSettings(RealmsWorldOptions worldOptions) {
|
|
RealmsWorldOptions realmsWorldOptions = (RealmsWorldOptions)this.serverData.slots.get(this.serverData.activeSlot);
|
|
worldOptions.templateId = realmsWorldOptions.templateId;
|
|
worldOptions.templateImage = realmsWorldOptions.templateImage;
|
|
RealmsClient realmsClient = RealmsClient.getOrCreate();
|
|
|
|
try {
|
|
realmsClient.updateSlot(this.serverData.id, this.serverData.activeSlot, worldOptions);
|
|
this.serverData.slots.put(this.serverData.activeSlot, worldOptions);
|
|
if (realmsWorldOptions.gameMode != worldOptions.gameMode || realmsWorldOptions.hardcore != worldOptions.hardcore) {
|
|
RealmsMainScreen.refreshServerList();
|
|
}
|
|
} catch (RealmsServiceException var5) {
|
|
LOGGER.error("Couldn't save slot settings", (Throwable)var5);
|
|
this.minecraft.setScreen(new RealmsGenericErrorScreen(var5, this));
|
|
return;
|
|
}
|
|
|
|
this.minecraft.setScreen(this);
|
|
}
|
|
|
|
public void saveSettings(String key, String value) {
|
|
String string = StringUtil.isBlank(value) ? "" : value;
|
|
RealmsClient realmsClient = RealmsClient.getOrCreate();
|
|
|
|
try {
|
|
realmsClient.update(this.serverData.id, key, string);
|
|
this.serverData.setName(key);
|
|
this.serverData.setDescription(string);
|
|
this.stateChanged();
|
|
} catch (RealmsServiceException var6) {
|
|
LOGGER.error("Couldn't save settings", (Throwable)var6);
|
|
this.minecraft.setScreen(new RealmsGenericErrorScreen(var6, this));
|
|
return;
|
|
}
|
|
|
|
this.minecraft.setScreen(this);
|
|
}
|
|
|
|
public void openTheWorld(boolean join) {
|
|
RealmsConfigureWorldScreen realmsConfigureWorldScreen = this.getNewScreen();
|
|
this.minecraft
|
|
.setScreen(
|
|
new RealmsLongRunningMcoTaskScreen(realmsConfigureWorldScreen, new OpenServerTask(this.serverData, realmsConfigureWorldScreen, join, this.minecraft))
|
|
);
|
|
}
|
|
|
|
public void closeTheWorld() {
|
|
RealmsConfigureWorldScreen realmsConfigureWorldScreen = this.getNewScreen();
|
|
this.minecraft.setScreen(new RealmsLongRunningMcoTaskScreen(realmsConfigureWorldScreen, new CloseServerTask(this.serverData, realmsConfigureWorldScreen)));
|
|
}
|
|
|
|
public void stateChanged() {
|
|
this.stateChanged = true;
|
|
}
|
|
|
|
private void templateSelectionCallback(@Nullable WorldTemplate worldTemplate) {
|
|
if (worldTemplate != null && WorldTemplateType.MINIGAME == worldTemplate.type) {
|
|
this.stateChanged();
|
|
this.minecraft
|
|
.setScreen(new RealmsLongRunningMcoTaskScreen(this.lastScreen, new SwitchMinigameTask(this.serverData.id, worldTemplate, this.getNewScreen())));
|
|
} else {
|
|
this.minecraft.setScreen(this);
|
|
}
|
|
}
|
|
|
|
public RealmsConfigureWorldScreen getNewScreen() {
|
|
RealmsConfigureWorldScreen realmsConfigureWorldScreen = new RealmsConfigureWorldScreen(this.lastScreen, this.serverId);
|
|
realmsConfigureWorldScreen.stateChanged = this.stateChanged;
|
|
return realmsConfigureWorldScreen;
|
|
}
|
|
}
|