RealmsSelectWorldTemplateScreen.java
com.mojang.realmsclient.gui.screens.RealmsSelectWorldTemplateScreen
信息
- 全限定名:com.mojang.realmsclient.gui.screens.RealmsSelectWorldTemplateScreen
- 类型:public class
- 包:com.mojang.realmsclient.gui.screens
- 源码路径:src/main/java/com/mojang/realmsclient/gui/screens/RealmsSelectWorldTemplateScreen.java
- 起始行号:L43
- 继承:RealmsScreen
- 职责:
TODO
字段/常量
-
LOGGER- 类型:
Logger - 修饰符:
private static final - 源码定位:
L44 - 说明:
TODO
- 类型:
-
SLOT_FRAME_SPRITE- 类型:
Identifier - 修饰符:
private static final - 源码定位:
L45 - 说明:
TODO
- 类型:
-
SELECT_BUTTON_NAME- 类型:
Component - 修饰符:
private static final - 源码定位:
L46 - 说明:
TODO
- 类型:
-
TRAILER_BUTTON_NAME- 类型:
Component - 修饰符:
private static final - 源码定位:
L47 - 说明:
TODO
- 类型:
-
PUBLISHER_BUTTON_NAME- 类型:
Component - 修饰符:
private static final - 源码定位:
L48 - 说明:
TODO
- 类型:
-
BUTTON_WIDTH- 类型:
int - 修饰符:
private static final - 源码定位:
L49 - 说明:
TODO
- 类型:
-
layout- 类型:
HeaderAndFooterLayout - 修饰符:
private final - 源码定位:
L50 - 说明:
TODO
- 类型:
-
callback- 类型:
Consumer<WorldTemplate> - 修饰符:
private final - 源码定位:
L51 - 说明:
TODO
- 类型:
-
worldTemplateList- 类型:
RealmsSelectWorldTemplateScreen.WorldTemplateList - 修饰符:
private - 源码定位:
L52 - 说明:
TODO
- 类型:
-
worldType- 类型:
RealmsServer.WorldType - 修饰符:
private final - 源码定位:
L53 - 说明:
TODO
- 类型:
-
subtitle- 类型:
List<Component> - 修饰符:
private final - 源码定位:
L54 - 说明:
TODO
- 类型:
-
selectButton- 类型:
Button - 修饰符:
private - 源码定位:
L55 - 说明:
TODO
- 类型:
-
trailerButton- 类型:
Button - 修饰符:
private - 源码定位:
L56 - 说明:
TODO
- 类型:
-
publisherButton- 类型:
Button - 修饰符:
private - 源码定位:
L57 - 说明:
TODO
- 类型:
-
selectedTemplate- 类型:
WorldTemplate - 修饰符:
private - 源码定位:
L58 - 说明:
TODO
- 类型:
-
currentLink- 类型:
String - 修饰符:
private - 源码定位:
L59 - 说明:
TODO
- 类型:
-
noTemplatesMessage- 类型:
List<TextRenderingUtils.Line> - 修饰符:
private - 源码定位:
L60 - 说明:
TODO
- 类型:
内部类/嵌套类型
-
com.mojang.realmsclient.gui.screens.RealmsSelectWorldTemplateScreen.Entry- 类型:
class - 修饰符:
private - 源码定位:
L246 - 说明:
TODO
- 类型:
-
com.mojang.realmsclient.gui.screens.RealmsSelectWorldTemplateScreen.WorldTemplateList- 类型:
class - 修饰符:
private - 源码定位:
L351 - 说明:
TODO
- 类型:
构造器
public RealmsSelectWorldTemplateScreen(Component title, Consumer<WorldTemplate> callback, RealmsServer.WorldType worldType, WorldTemplatePaginatedList alreadyFetched) @ L62
- 构造器名:RealmsSelectWorldTemplateScreen
- 源码定位:L62
- 修饰符:public
参数:
- title: Component
- callback: Consumer
- worldType: RealmsServer.WorldType
- alreadyFetched: WorldTemplatePaginatedList
说明:
TODO
public RealmsSelectWorldTemplateScreen(Component title, Consumer<WorldTemplate> callback, RealmsServer.WorldType worldType, WorldTemplatePaginatedList alreadyFetched, List<Component> subtitle) @ L68
- 构造器名:RealmsSelectWorldTemplateScreen
- 源码定位:L68
- 修饰符:public
参数:
- title: Component
- callback: Consumer
- worldType: RealmsServer.WorldType
- alreadyFetched: WorldTemplatePaginatedList
- subtitle: List
说明:
TODO
方法
下面的方法块按源码顺序生成。
public void init() @ L89
- 方法名:init
- 源码定位:L89
- 返回类型:void
- 修饰符:public
参数:
- 无
说明:
TODO
protected void repositionElements() @ L108
- 方法名:repositionElements
- 源码定位:L108
- 返回类型:void
- 修饰符:protected
参数:
- 无
说明:
TODO
public Component getNarrationMessage() @ L114
- 方法名:getNarrationMessage
- 源码定位:L114
- 返回类型:Component
- 修饰符:public
参数:
- 无
说明:
TODO
private void updateButtonStates() @ L122
- 方法名:updateButtonStates
- 源码定位:L122
- 返回类型:void
- 修饰符:private
参数:
- 无
说明:
TODO
public void onClose() @ L128
- 方法名:onClose
- 源码定位:L128
- 返回类型:void
- 修饰符:public
参数:
- 无
说明:
TODO
private void selectTemplate() @ L133
- 方法名:selectTemplate
- 源码定位:L133
- 返回类型:void
- 修饰符:private
参数:
- 无
说明:
TODO
private void onTrailer() @ L139
- 方法名:onTrailer
- 源码定位:L139
- 返回类型:void
- 修饰符:private
参数:
- 无
说明:
TODO
private void onPublish() @ L145
- 方法名:onPublish
- 源码定位:L145
- 返回类型:void
- 修饰符:private
参数:
- 无
说明:
TODO
private void fetchTemplatesAsync(WorldTemplatePaginatedList startPage) @ L151
- 方法名:fetchTemplatesAsync
- 源码定位:L151
- 返回类型:void
- 修饰符:private
参数:
- startPage: WorldTemplatePaginatedList
说明:
TODO
private Either<WorldTemplatePaginatedList,Exception> fetchTemplates(WorldTemplatePaginatedList paginatedList, RealmsClient client) @ L206
- 方法名:fetchTemplates
- 源码定位:L206
- 返回类型:Either<WorldTemplatePaginatedList,Exception>
- 修饰符:private
参数:
- paginatedList: WorldTemplatePaginatedList
- client: RealmsClient
说明:
TODO
public void extractRenderState(GuiGraphicsExtractor graphics, int xm, int ym, float a) @ L214
- 方法名:extractRenderState
- 源码定位:L214
- 返回类型:void
- 修饰符:public
参数:
- graphics: GuiGraphicsExtractor
- xm: int
- ym: int
- a: float
说明:
TODO
private void extractMultilineMessage(GuiGraphicsExtractor graphics, int xm, int ym, List<TextRenderingUtils.Line> noTemplatesMessage) @ L223
- 方法名:extractMultilineMessage
- 源码定位:L223
- 返回类型:void
- 修饰符:private
参数:
- graphics: GuiGraphicsExtractor
- xm: int
- ym: int
- noTemplatesMessage: List<TextRenderingUtils.Line>
说明:
TODO
代码
@OnlyIn(Dist.CLIENT)
public class RealmsSelectWorldTemplateScreen extends RealmsScreen {
private static final Logger LOGGER = LogUtils.getLogger();
private static final Identifier SLOT_FRAME_SPRITE = Identifier.withDefaultNamespace("widget/slot_frame");
private static final Component SELECT_BUTTON_NAME = Component.translatable("mco.template.button.select");
private static final Component TRAILER_BUTTON_NAME = Component.translatable("mco.template.button.trailer");
private static final Component PUBLISHER_BUTTON_NAME = Component.translatable("mco.template.button.publisher");
private static final int BUTTON_WIDTH = 100;
private final HeaderAndFooterLayout layout = new HeaderAndFooterLayout(this);
private final Consumer<WorldTemplate> callback;
private RealmsSelectWorldTemplateScreen.WorldTemplateList worldTemplateList;
private final RealmsServer.WorldType worldType;
private final List<Component> subtitle;
private Button selectButton;
private Button trailerButton;
private Button publisherButton;
private @Nullable WorldTemplate selectedTemplate = null;
private @Nullable String currentLink;
private @Nullable List<TextRenderingUtils.Line> noTemplatesMessage;
public RealmsSelectWorldTemplateScreen(
Component title, Consumer<WorldTemplate> callback, RealmsServer.WorldType worldType, @Nullable WorldTemplatePaginatedList alreadyFetched
) {
this(title, callback, worldType, alreadyFetched, List.of());
}
public RealmsSelectWorldTemplateScreen(
Component title,
Consumer<WorldTemplate> callback,
RealmsServer.WorldType worldType,
@Nullable WorldTemplatePaginatedList alreadyFetched,
List<Component> subtitle
) {
super(title);
this.callback = callback;
this.worldType = worldType;
if (alreadyFetched == null) {
this.worldTemplateList = new RealmsSelectWorldTemplateScreen.WorldTemplateList();
this.fetchTemplatesAsync(new WorldTemplatePaginatedList(10));
} else {
this.worldTemplateList = new RealmsSelectWorldTemplateScreen.WorldTemplateList(Lists.newArrayList(alreadyFetched.templates()));
this.fetchTemplatesAsync(alreadyFetched);
}
this.subtitle = subtitle;
}
@Override
public void init() {
this.layout.setHeaderHeight(33 + this.subtitle.size() * (9 + 4));
LinearLayout header = this.layout.addToHeader(LinearLayout.vertical().spacing(4));
header.defaultCellSetting().alignHorizontallyCenter();
header.addChild(new StringWidget(this.title, this.font));
this.subtitle.forEach(warning -> header.addChild(new StringWidget(warning, this.font)));
this.worldTemplateList = this.layout.addToContents(new RealmsSelectWorldTemplateScreen.WorldTemplateList(this.worldTemplateList.getTemplates()));
LinearLayout bottomButtons = this.layout.addToFooter(LinearLayout.horizontal().spacing(8));
bottomButtons.defaultCellSetting().alignHorizontallyCenter();
this.trailerButton = bottomButtons.addChild(Button.builder(TRAILER_BUTTON_NAME, button -> this.onTrailer()).width(100).build());
this.selectButton = bottomButtons.addChild(Button.builder(SELECT_BUTTON_NAME, button -> this.selectTemplate()).width(100).build());
bottomButtons.addChild(Button.builder(CommonComponents.GUI_CANCEL, button -> this.onClose()).width(100).build());
this.publisherButton = bottomButtons.addChild(Button.builder(PUBLISHER_BUTTON_NAME, button -> this.onPublish()).width(100).build());
this.updateButtonStates();
this.layout.visitWidgets(x$0 -> this.addRenderableWidget(x$0));
this.repositionElements();
}
@Override
protected void repositionElements() {
this.worldTemplateList.updateSize(this.width, this.layout);
this.layout.arrangeElements();
}
@Override
public Component getNarrationMessage() {
List<Component> parts = Lists.newArrayListWithCapacity(2);
parts.add(this.title);
parts.addAll(this.subtitle);
return CommonComponents.joinLines(parts);
}
private void updateButtonStates() {
this.publisherButton.visible = this.selectedTemplate != null && !this.selectedTemplate.link().isEmpty();
this.trailerButton.visible = this.selectedTemplate != null && !this.selectedTemplate.trailer().isEmpty();
this.selectButton.active = this.selectedTemplate != null;
}
@Override
public void onClose() {
this.callback.accept(null);
}
private void selectTemplate() {
if (this.selectedTemplate != null) {
this.callback.accept(this.selectedTemplate);
}
}
private void onTrailer() {
if (this.selectedTemplate != null && !this.selectedTemplate.trailer().isBlank()) {
ConfirmLinkScreen.confirmLinkNow(this, this.selectedTemplate.trailer());
}
}
private void onPublish() {
if (this.selectedTemplate != null && !this.selectedTemplate.link().isBlank()) {
ConfirmLinkScreen.confirmLinkNow(this, this.selectedTemplate.link());
}
}
private void fetchTemplatesAsync(WorldTemplatePaginatedList startPage) {
(new Thread("realms-template-fetcher") {
{
Objects.requireNonNull(RealmsSelectWorldTemplateScreen.this);
}
@Override
public void run() {
WorldTemplatePaginatedList page = startPage;
RealmsClient client = RealmsClient.getOrCreate();
while (page != null) {
Either<WorldTemplatePaginatedList, Exception> result = RealmsSelectWorldTemplateScreen.this.fetchTemplates(page, client);
page = RealmsSelectWorldTemplateScreen.this.minecraft
.submit(
() -> {
if (result.right().isPresent()) {
RealmsSelectWorldTemplateScreen.LOGGER.error("Couldn't fetch templates", result.right().get());
if (RealmsSelectWorldTemplateScreen.this.worldTemplateList.isEmpty()) {
RealmsSelectWorldTemplateScreen.this.noTemplatesMessage = TextRenderingUtils.decompose(
I18n.get("mco.template.select.failure")
);
}
return null;
} else {
WorldTemplatePaginatedList currentPage = result.left().get();
for (WorldTemplate template : currentPage.templates()) {
RealmsSelectWorldTemplateScreen.this.worldTemplateList.addEntry(template);
}
if (currentPage.templates().isEmpty()) {
if (RealmsSelectWorldTemplateScreen.this.worldTemplateList.isEmpty()) {
String withoutLink = I18n.get("mco.template.select.none", "%link");
TextRenderingUtils.LineSegment link = TextRenderingUtils.LineSegment.link(
I18n.get("mco.template.select.none.linkTitle"), CommonLinks.REALMS_CONTENT_CREATION.toString()
);
RealmsSelectWorldTemplateScreen.this.noTemplatesMessage = TextRenderingUtils.decompose(withoutLink, link);
}
return null;
} else {
return currentPage;
}
}
}
)
.join();
}
}
})
.start();
}
private Either<WorldTemplatePaginatedList, Exception> fetchTemplates(WorldTemplatePaginatedList paginatedList, RealmsClient client) {
try {
return Either.left(client.fetchWorldTemplates(paginatedList.page() + 1, paginatedList.size(), this.worldType));
} catch (RealmsServiceException var4) {
return Either.right(var4);
}
}
@Override
public void extractRenderState(GuiGraphicsExtractor graphics, int xm, int ym, float a) {
super.extractRenderState(graphics, xm, ym, a);
this.currentLink = null;
if (this.noTemplatesMessage != null) {
this.extractMultilineMessage(graphics, xm, ym, this.noTemplatesMessage);
}
}
private void extractMultilineMessage(GuiGraphicsExtractor graphics, int xm, int ym, List<TextRenderingUtils.Line> noTemplatesMessage) {
for (int i = 0; i < noTemplatesMessage.size(); i++) {
TextRenderingUtils.Line line = noTemplatesMessage.get(i);
int lineY = row(4 + i);
int lineWidth = line.segments.stream().mapToInt(s -> this.font.width(s.renderedText())).sum();
int startX = this.width / 2 - lineWidth / 2;
for (TextRenderingUtils.LineSegment segment : line.segments) {
int color = segment.isLink() ? -13408581 : -1;
String text = segment.renderedText();
graphics.text(this.font, text, startX, lineY, color);
int endX = startX + this.font.width(text);
if (segment.isLink() && xm > startX && xm < endX && ym > lineY - 3 && ym < lineY + 8) {
graphics.setTooltipForNextFrame(Component.literal(segment.getLinkUrl()), xm, ym);
this.currentLink = segment.getLinkUrl();
}
startX = endX;
}
}
}
@OnlyIn(Dist.CLIENT)
private class Entry extends ObjectSelectionList.Entry<RealmsSelectWorldTemplateScreen.Entry> {
private static final WidgetSprites WEBSITE_LINK_SPRITES = new WidgetSprites(
Identifier.withDefaultNamespace("icon/link"), Identifier.withDefaultNamespace("icon/link_highlighted")
);
private static final WidgetSprites TRAILER_LINK_SPRITES = new WidgetSprites(
Identifier.withDefaultNamespace("icon/video_link"), Identifier.withDefaultNamespace("icon/video_link_highlighted")
);
private static final Component PUBLISHER_LINK_TOOLTIP = Component.translatable("mco.template.info.tooltip");
private static final Component TRAILER_LINK_TOOLTIP = Component.translatable("mco.template.trailer.tooltip");
public final WorldTemplate template;
private @Nullable ImageButton websiteButton;
private @Nullable ImageButton trailerButton;
public Entry(WorldTemplate template) {
Objects.requireNonNull(RealmsSelectWorldTemplateScreen.this);
super();
this.template = template;
if (!template.link().isBlank()) {
this.websiteButton = new ImageButton(
15, 15, WEBSITE_LINK_SPRITES, ConfirmLinkScreen.confirmLink(RealmsSelectWorldTemplateScreen.this, template.link()), PUBLISHER_LINK_TOOLTIP
);
this.websiteButton.setTooltip(Tooltip.create(PUBLISHER_LINK_TOOLTIP));
}
if (!template.trailer().isBlank()) {
this.trailerButton = new ImageButton(
15, 15, TRAILER_LINK_SPRITES, ConfirmLinkScreen.confirmLink(RealmsSelectWorldTemplateScreen.this, template.trailer()), TRAILER_LINK_TOOLTIP
);
this.trailerButton.setTooltip(Tooltip.create(TRAILER_LINK_TOOLTIP));
}
}
@Override
public boolean mouseClicked(MouseButtonEvent event, boolean doubleClick) {
RealmsSelectWorldTemplateScreen.this.selectedTemplate = this.template;
RealmsSelectWorldTemplateScreen.this.updateButtonStates();
if (doubleClick && this.isFocused()) {
RealmsSelectWorldTemplateScreen.this.callback.accept(this.template);
}
if (this.websiteButton != null) {
this.websiteButton.mouseClicked(event, doubleClick);
}
if (this.trailerButton != null) {
this.trailerButton.mouseClicked(event, doubleClick);
}
return super.mouseClicked(event, doubleClick);
}
@Override
public void extractContent(GuiGraphicsExtractor graphics, int mouseX, int mouseY, boolean hovered, float a) {
graphics.blit(
RenderPipelines.GUI_TEXTURED,
RealmsTextureManager.worldTemplate(this.template.id(), this.template.image()),
this.getContentX() + 1,
this.getContentY() + 1 + 1,
0.0F,
0.0F,
38,
38,
38,
38
);
graphics.blitSprite(
RenderPipelines.GUI_TEXTURED, RealmsSelectWorldTemplateScreen.SLOT_FRAME_SPRITE, this.getContentX(), this.getContentY() + 1, 40, 40
);
int padding = 5;
int versionTextWidth = RealmsSelectWorldTemplateScreen.this.font.width(this.template.version());
if (this.websiteButton != null) {
this.websiteButton.setPosition(this.getContentRight() - versionTextWidth - this.websiteButton.getWidth() - 10, this.getContentY());
this.websiteButton.extractRenderState(graphics, mouseX, mouseY, a);
}
if (this.trailerButton != null) {
this.trailerButton.setPosition(this.getContentRight() - versionTextWidth - this.trailerButton.getWidth() * 2 - 15, this.getContentY());
this.trailerButton.extractRenderState(graphics, mouseX, mouseY, a);
}
int textX = this.getContentX() + 45 + 20;
int textY = this.getContentY() + 5;
graphics.text(RealmsSelectWorldTemplateScreen.this.font, this.template.name(), textX, textY, -1);
graphics.text(RealmsSelectWorldTemplateScreen.this.font, this.template.version(), this.getContentRight() - versionTextWidth - 5, textY, -6250336);
graphics.text(RealmsSelectWorldTemplateScreen.this.font, this.template.author(), textX, textY + 9 + 5, -6250336);
if (!this.template.recommendedPlayers().isBlank()) {
graphics.text(
RealmsSelectWorldTemplateScreen.this.font, this.template.recommendedPlayers(), textX, this.getContentBottom() - 9 / 2 - 5, -8355712
);
}
}
@Override
public Component getNarration() {
Component entryName = CommonComponents.joinLines(
Component.literal(this.template.name()),
Component.translatable("mco.template.select.narrate.authors", this.template.author()),
Component.literal(this.template.recommendedPlayers()),
Component.translatable("mco.template.select.narrate.version", this.template.version())
);
return Component.translatable("narrator.select", entryName);
}
}
@OnlyIn(Dist.CLIENT)
private class WorldTemplateList extends ObjectSelectionList<RealmsSelectWorldTemplateScreen.Entry> {
public WorldTemplateList() {
this(Collections.emptyList());
}
public WorldTemplateList(Iterable<WorldTemplate> templates) {
Objects.requireNonNull(RealmsSelectWorldTemplateScreen.this);
super(
Minecraft.getInstance(),
RealmsSelectWorldTemplateScreen.this.width,
RealmsSelectWorldTemplateScreen.this.layout.getContentHeight(),
RealmsSelectWorldTemplateScreen.this.layout.getHeaderHeight(),
46
);
templates.forEach(this::addEntry);
}
public void addEntry(WorldTemplate template) {
this.addEntry(RealmsSelectWorldTemplateScreen.this.new Entry(template));
}
@Override
public boolean mouseClicked(MouseButtonEvent event, boolean doubleClick) {
if (RealmsSelectWorldTemplateScreen.this.currentLink != null) {
ConfirmLinkScreen.confirmLinkNow(RealmsSelectWorldTemplateScreen.this, RealmsSelectWorldTemplateScreen.this.currentLink);
return true;
} else {
return super.mouseClicked(event, doubleClick);
}
}
public void setSelected(RealmsSelectWorldTemplateScreen.@Nullable Entry selected) {
super.setSelected(selected);
RealmsSelectWorldTemplateScreen.this.selectedTemplate = selected == null ? null : selected.template;
RealmsSelectWorldTemplateScreen.this.updateButtonStates();
}
@Override
public int getRowWidth() {
return 300;
}
public boolean isEmpty() {
return this.getItemCount() == 0;
}
public List<WorldTemplate> getTemplates() {
return this.children().stream().map(c -> c.template).collect(Collectors.toList());
}
}
}引用的其他类
-
- 引用位置:
参数/方法调用 - 关联成员:
RealmsClient.getOrCreate()
- 引用位置:
-
- 引用位置:
参数/字段
- 引用位置:
-
- 引用位置:
参数/字段
- 引用位置:
-
- 引用位置:
参数/构造调用/返回值 - 关联成员:
WorldTemplatePaginatedList()
- 引用位置:
-
- 引用位置:
方法调用 - 关联成员:
RealmsTextureManager.worldTemplate()
- 引用位置:
-
- 引用位置:
参数/字段/方法调用 - 关联成员:
TextRenderingUtils.LineSegment.link(), TextRenderingUtils.decompose()
- 引用位置:
-
- 引用位置:
方法调用 - 关联成员:
Minecraft.getInstance()
- 引用位置:
-
- 引用位置:
参数
- 引用位置:
-
- 引用位置:
字段/方法调用 - 关联成员:
Button.builder()
- 引用位置:
-
- 引用位置:
构造调用 - 关联成员:
ImageButton()
- 引用位置:
-
- 引用位置:
构造调用 - 关联成员:
StringWidget()
- 引用位置:
-
- 引用位置:
方法调用 - 关联成员:
Tooltip.create()
- 引用位置:
-
- 引用位置:
构造调用 - 关联成员:
WidgetSprites()
- 引用位置:
-
- 引用位置:
字段/构造调用 - 关联成员:
HeaderAndFooterLayout()
- 引用位置:
-
- 引用位置:
方法调用 - 关联成员:
LinearLayout.horizontal(), LinearLayout.vertical()
- 引用位置:
-
- 引用位置:
方法调用 - 关联成员:
ConfirmLinkScreen.confirmLink(), ConfirmLinkScreen.confirmLinkNow()
- 引用位置:
-
- 引用位置:
方法调用 - 关联成员:
I18n.get()
- 引用位置:
-
- 引用位置:
方法调用 - 关联成员:
CommonComponents.joinLines()
- 引用位置:
-
- 引用位置:
参数/字段/方法调用/返回值 - 关联成员:
Component.literal(), Component.translatable()
- 引用位置:
-
- 引用位置:
继承
- 引用位置:
-
- 引用位置:
字段/方法调用 - 关联成员:
Identifier.withDefaultNamespace()
- 引用位置: