DebugOptionsScreen.java

net.minecraft.client.gui.screens.debug.DebugOptionsScreen

信息

  • 全限定名:net.minecraft.client.gui.screens.debug.DebugOptionsScreen
  • 类型:public class
  • 包:net.minecraft.client.gui.screens.debug
  • 源码路径:src/main/java/net/minecraft/client/gui/screens/debug/DebugOptionsScreen.java
  • 起始行号:L45
  • 继承:Screen
  • 职责:

    TODO

字段/常量

  • TITLE

    • 类型: Component
    • 修饰符: private static final
    • 源码定位: L46
    • 说明:

      TODO

  • SUBTITLE

    • 类型: Component
    • 修饰符: private static final
    • 源码定位: L47
    • 说明:

      TODO

  • ENABLED_TEXT

    • 类型: Component
    • 修饰符: private static final
    • 源码定位: L48
    • 说明:

      TODO

  • IN_OVERLAY_TEXT

    • 类型: Component
    • 修饰符: private static final
    • 源码定位: L49
    • 说明:

      TODO

  • DISABLED_TEXT

    • 类型: Component
    • 修饰符: private static final
    • 源码定位: L50
    • 说明:

      TODO

  • NOT_ALLOWED_TOOLTIP

    • 类型: Component
    • 修饰符: private static final
    • 源码定位: L51
    • 说明:

      TODO

  • SEARCH

    • 类型: Component
    • 修饰符: private static final
    • 源码定位: L52
    • 说明:

      TODO

  • layout

    • 类型: HeaderAndFooterLayout
    • 修饰符: private final
    • 源码定位: L53
    • 说明:

      TODO

  • optionList

    • 类型: DebugOptionsScreen.OptionList
    • 修饰符: private
    • 源码定位: L54
    • 说明:

      TODO

  • searchBox

    • 类型: EditBox
    • 修饰符: private
    • 源码定位: L55
    • 说明:

      TODO

  • profileButtons

    • 类型: List<Button>
    • 修饰符: private final
    • 源码定位: L56
    • 说明:

      TODO

内部类/嵌套类型

  • net.minecraft.client.gui.screens.debug.DebugOptionsScreen.AbstractOptionEntry

    • 类型: class
    • 修饰符: public abstract static
    • 源码定位: L126
    • 说明:

      TODO

  • net.minecraft.client.gui.screens.debug.DebugOptionsScreen.CategoryEntry

    • 类型: class
    • 修饰符: private
    • 源码定位: L131
    • 说明:

      TODO

  • net.minecraft.client.gui.screens.debug.DebugOptionsScreen.OptionEntry

    • 类型: class
    • 修饰符: private
    • 源码定位: L177
    • 说明:

      TODO

  • net.minecraft.client.gui.screens.debug.DebugOptionsScreen.OptionList

    • 类型: class
    • 修饰符: public
    • 源码定位: L285
    • 说明:

      TODO

构造器

public DebugOptionsScreen() @ L58

  • 构造器名:DebugOptionsScreen
  • 源码定位:L58
  • 修饰符:public

参数:

说明:

TODO

方法

下面的方法块按源码顺序生成。

protected void init() @ L62

  • 方法名:init
  • 源码定位:L62
  • 返回类型:void
  • 修饰符:protected

参数:

说明:

TODO

public void extractBlurredBackground(GuiGraphicsExtractor graphics) @ L85

  • 方法名:extractBlurredBackground
  • 源码定位:L85
  • 返回类型:void
  • 修饰符:public

参数:

  • graphics: GuiGraphicsExtractor

说明:

TODO

protected void setInitialFocus() @ L91

  • 方法名:setInitialFocus
  • 源码定位:L91
  • 返回类型:void
  • 修饰符:protected

参数:

说明:

TODO

private void addProfileButton(DebugScreenProfile profile, LinearLayout bottomButtons) @ L96

  • 方法名:addProfileButton
  • 源码定位:L96
  • 返回类型:void
  • 修饰符:private

参数:

  • profile: DebugScreenProfile
  • bottomButtons: LinearLayout

说明:

TODO

protected void repositionElements() @ L113

  • 方法名:repositionElements
  • 源码定位:L113
  • 返回类型:void
  • 修饰符:protected

参数:

说明:

TODO

public DebugOptionsScreen.OptionList getOptionList() @ L121

  • 方法名:getOptionList
  • 源码定位:L121
  • 返回类型:DebugOptionsScreen.OptionList
  • 修饰符:public

参数:

说明:

TODO

代码

@OnlyIn(Dist.CLIENT)
public class DebugOptionsScreen extends Screen {
    private static final Component TITLE = Component.translatable("debug.options.title");
    private static final Component SUBTITLE = Component.translatable("debug.options.warning").withColor(-2142128);
    private static final Component ENABLED_TEXT = Component.translatable("debug.entry.always");
    private static final Component IN_OVERLAY_TEXT = Component.translatable("debug.entry.overlay");
    private static final Component DISABLED_TEXT = CommonComponents.OPTION_OFF;
    private static final Component NOT_ALLOWED_TOOLTIP = Component.translatable("debug.options.notAllowed.tooltip");
    private static final Component SEARCH = Component.translatable("debug.options.search").withStyle(EditBox.SEARCH_HINT_STYLE);
    private final HeaderAndFooterLayout layout = new HeaderAndFooterLayout(this, 61, 33);
    private DebugOptionsScreen.@Nullable OptionList optionList;
    private EditBox searchBox;
    private final List<Button> profileButtons = new ArrayList<>();
 
    public DebugOptionsScreen() {
        super(TITLE);
    }
 
    @Override
    protected void init() {
        LinearLayout header = this.layout.addToHeader(LinearLayout.vertical().spacing(8));
        this.optionList = new DebugOptionsScreen.OptionList();
        int optionListWidth = this.optionList.getRowWidth();
        LinearLayout title = LinearLayout.horizontal().spacing(8);
        title.addChild(new SpacerElement(optionListWidth / 3, 1));
        title.addChild(new StringWidget(TITLE, this.font), title.newCellSettings().alignVerticallyMiddle());
        this.searchBox = new EditBox(this.font, 0, 0, optionListWidth / 3, 20, this.searchBox, SEARCH);
        this.searchBox.setResponder(value -> this.optionList.updateSearch(value));
        this.searchBox.setHint(SEARCH);
        title.addChild(this.searchBox);
        header.addChild(title, LayoutSettings::alignHorizontallyCenter);
        header.addChild(new MultiLineTextWidget(SUBTITLE, this.font).setMaxWidth(optionListWidth).setCentered(true), LayoutSettings::alignHorizontallyCenter);
        this.layout.addToContents(this.optionList);
        LinearLayout bottomButtons = this.layout.addToFooter(LinearLayout.horizontal().spacing(8));
        this.addProfileButton(DebugScreenProfile.DEFAULT, bottomButtons);
        this.addProfileButton(DebugScreenProfile.PERFORMANCE, bottomButtons);
        bottomButtons.addChild(Button.builder(CommonComponents.GUI_DONE, button -> this.onClose()).width(60).build());
        this.layout.visitWidgets(x$0 -> this.addRenderableWidget(x$0));
        this.repositionElements();
    }
 
    @Override
    public void extractBlurredBackground(GuiGraphicsExtractor graphics) {
        this.minecraft.gui.extractDebugOverlay(graphics);
        super.extractBlurredBackground(graphics);
    }
 
    @Override
    protected void setInitialFocus() {
        this.setInitialFocus(this.searchBox);
    }
 
    private void addProfileButton(DebugScreenProfile profile, LinearLayout bottomButtons) {
        Button profileButton = Button.builder(Component.translatable(profile.translationKey()), button -> {
            this.minecraft.debugEntries.loadProfile(profile);
            this.minecraft.debugEntries.save();
            this.optionList.refreshEntries();
 
            for (Button listButton : this.profileButtons) {
                listButton.active = true;
            }
 
            button.active = false;
        }).width(120).build();
        profileButton.active = !this.minecraft.debugEntries.isUsingProfile(profile);
        this.profileButtons.add(profileButton);
        bottomButtons.addChild(profileButton);
    }
 
    @Override
    protected void repositionElements() {
        this.layout.arrangeElements();
        if (this.optionList != null) {
            this.optionList.updateSize(this.width, this.layout);
        }
    }
 
    public DebugOptionsScreen.@Nullable OptionList getOptionList() {
        return this.optionList;
    }
 
    @OnlyIn(Dist.CLIENT)
    public abstract static class AbstractOptionEntry extends ContainerObjectSelectionList.Entry<DebugOptionsScreen.AbstractOptionEntry> {
        public abstract void refreshEntry();
    }
 
    @OnlyIn(Dist.CLIENT)
    private class CategoryEntry extends DebugOptionsScreen.AbstractOptionEntry {
        private final Component category;
 
        public CategoryEntry(Component category) {
            Objects.requireNonNull(DebugOptionsScreen.this);
            super();
            this.category = category;
        }
 
        @Override
        public void extractContent(GuiGraphicsExtractor graphics, int mouseX, int mouseY, boolean hovered, float a) {
            graphics.centeredText(
                DebugOptionsScreen.this.minecraft.font, this.category, this.getContentX() + this.getContentWidth() / 2, this.getContentY() + 5, -1
            );
        }
 
        @Override
        public List<? extends GuiEventListener> children() {
            return ImmutableList.of();
        }
 
        @Override
        public List<? extends NarratableEntry> narratables() {
            return ImmutableList.of(new NarratableEntry() {
                {
                    Objects.requireNonNull(CategoryEntry.this);
                }
 
                @Override
                public NarratableEntry.NarrationPriority narrationPriority() {
                    return NarratableEntry.NarrationPriority.HOVERED;
                }
 
                @Override
                public void updateNarration(NarrationElementOutput output) {
                    output.add(NarratedElementType.TITLE, CategoryEntry.this.category);
                }
            });
        }
 
        @Override
        public void refreshEntry() {
        }
    }
 
    @OnlyIn(Dist.CLIENT)
    private class OptionEntry extends DebugOptionsScreen.AbstractOptionEntry {
        private static final int BUTTON_WIDTH = 60;
        private final Identifier location;
        protected final List<AbstractWidget> children;
        private final CycleButton<Boolean> always;
        private final CycleButton<Boolean> overlay;
        private final CycleButton<Boolean> never;
        private final String name;
        private final boolean isAllowed;
 
        public OptionEntry(Identifier location) {
            Objects.requireNonNull(DebugOptionsScreen.this);
            super();
            this.children = Lists.newArrayList();
            this.location = location;
            DebugScreenEntry entry = DebugScreenEntries.getEntry(location);
            this.isAllowed = entry != null && entry.isAllowed(DebugOptionsScreen.this.minecraft.showOnlyReducedInfo());
            String name = location.getPath();
            if (this.isAllowed) {
                this.name = name;
            } else {
                this.name = ChatFormatting.ITALIC + name;
            }
 
            this.always = CycleButton.booleanBuilder(
                    DebugOptionsScreen.ENABLED_TEXT.copy().withColor(-2142128), DebugOptionsScreen.ENABLED_TEXT.copy().withColor(-4539718), false
                )
                .displayOnlyValue()
                .withCustomNarration(this::narrateButton)
                .create(10, 5, 60, 16, Component.literal(name), (button, newValue) -> this.setValue(location, DebugScreenEntryStatus.ALWAYS_ON));
            this.overlay = CycleButton.booleanBuilder(
                    DebugOptionsScreen.IN_OVERLAY_TEXT.copy().withColor(-171), DebugOptionsScreen.IN_OVERLAY_TEXT.copy().withColor(-4539718), false
                )
                .displayOnlyValue()
                .withCustomNarration(this::narrateButton)
                .create(10, 5, 60, 16, Component.literal(name), (button, newValue) -> this.setValue(location, DebugScreenEntryStatus.IN_OVERLAY));
            this.never = CycleButton.booleanBuilder(
                    DebugOptionsScreen.DISABLED_TEXT.copy().withColor(-1), DebugOptionsScreen.DISABLED_TEXT.copy().withColor(-4539718), false
                )
                .displayOnlyValue()
                .withCustomNarration(this::narrateButton)
                .create(10, 5, 60, 16, Component.literal(name), (button, newValue) -> this.setValue(location, DebugScreenEntryStatus.NEVER));
            this.children.add(this.never);
            this.children.add(this.overlay);
            this.children.add(this.always);
            this.refreshEntry();
        }
 
        private MutableComponent narrateButton(CycleButton<Boolean> booleanCycleButton) {
            DebugScreenEntryStatus status = DebugOptionsScreen.this.minecraft.debugEntries.getStatus(this.location);
            MutableComponent current = Component.translatable("debug.entry.currently." + status.getSerializedName(), this.name);
            return CommonComponents.optionNameValue(current, booleanCycleButton.getMessage());
        }
 
        private void setValue(Identifier location, DebugScreenEntryStatus never) {
            DebugOptionsScreen.this.minecraft.debugEntries.setStatus(location, never);
 
            for (Button profileButton : DebugOptionsScreen.this.profileButtons) {
                profileButton.active = true;
            }
 
            this.refreshEntry();
        }
 
        @Override
        public List<? extends GuiEventListener> children() {
            return this.children;
        }
 
        @Override
        public List<? extends NarratableEntry> narratables() {
            return this.children;
        }
 
        @Override
        public void extractContent(GuiGraphicsExtractor graphics, int mouseX, int mouseY, boolean hovered, float a) {
            int x = this.getContentX();
            int y = this.getContentY();
            graphics.text(DebugOptionsScreen.this.minecraft.font, this.name, x, y + 5, this.isAllowed ? -1 : -8355712);
            int buttonsStartX = x + this.getContentWidth() - this.never.getWidth() - this.overlay.getWidth() - this.always.getWidth();
            if (!this.isAllowed && hovered && mouseX < buttonsStartX) {
                graphics.setTooltipForNextFrame(DebugOptionsScreen.NOT_ALLOWED_TOOLTIP, mouseX, mouseY);
            }
 
            this.never.setX(buttonsStartX);
            this.overlay.setX(this.never.getX() + this.never.getWidth());
            this.always.setX(this.overlay.getX() + this.overlay.getWidth());
            this.always.setY(y);
            this.overlay.setY(y);
            this.never.setY(y);
            this.always.extractRenderState(graphics, mouseX, mouseY, a);
            this.overlay.extractRenderState(graphics, mouseX, mouseY, a);
            this.never.extractRenderState(graphics, mouseX, mouseY, a);
        }
 
        @Override
        public void refreshEntry() {
            DebugScreenEntryStatus status = DebugOptionsScreen.this.minecraft.debugEntries.getStatus(this.location);
            this.always.setValue(status == DebugScreenEntryStatus.ALWAYS_ON);
            this.overlay.setValue(status == DebugScreenEntryStatus.IN_OVERLAY);
            this.never.setValue(status == DebugScreenEntryStatus.NEVER);
            this.always.active = !this.always.getValue();
            this.overlay.active = !this.overlay.getValue();
            this.never.active = !this.never.getValue();
        }
    }
 
    @OnlyIn(Dist.CLIENT)
    public class OptionList extends ContainerObjectSelectionList<DebugOptionsScreen.AbstractOptionEntry> {
        private static final Comparator<Map.Entry<Identifier, DebugScreenEntry>> COMPARATOR = (o1, o2) -> {
            int byCategory = FloatComparators.NATURAL_COMPARATOR.compare(o1.getValue().category().sortKey(), o2.getValue().category().sortKey());
            return byCategory != 0 ? byCategory : o1.getKey().compareTo(o2.getKey());
        };
        private static final int ITEM_HEIGHT = 20;
 
        public OptionList() {
            Objects.requireNonNull(DebugOptionsScreen.this);
            super(
                Minecraft.getInstance(),
                DebugOptionsScreen.this.width,
                DebugOptionsScreen.this.layout.getContentHeight(),
                DebugOptionsScreen.this.layout.getHeaderHeight(),
                20
            );
            this.updateSearch("");
        }
 
        @Override
        public void extractWidgetRenderState(GuiGraphicsExtractor graphics, int mouseX, int mouseY, float a) {
            super.extractWidgetRenderState(graphics, mouseX, mouseY, a);
        }
 
        @Override
        public int getRowWidth() {
            return 350;
        }
 
        public void refreshEntries() {
            this.children().forEach(DebugOptionsScreen.AbstractOptionEntry::refreshEntry);
        }
 
        public void updateSearch(String value) {
            this.clearEntries();
            List<Map.Entry<Identifier, DebugScreenEntry>> all = new ArrayList<>(DebugScreenEntries.allEntries().entrySet());
            all.sort(COMPARATOR);
            DebugEntryCategory currentCategory = null;
 
            for (Map.Entry<Identifier, DebugScreenEntry> entry : all) {
                if (entry.getKey().getPath().contains(value)) {
                    DebugEntryCategory newCategory = entry.getValue().category();
                    if (!newCategory.equals(currentCategory)) {
                        this.addEntry(DebugOptionsScreen.this.new CategoryEntry(newCategory.label()));
                        currentCategory = newCategory;
                    }
 
                    this.addEntry(DebugOptionsScreen.this.new OptionEntry(entry.getKey()));
                }
            }
 
            this.notifyListUpdated();
        }
 
        private void notifyListUpdated() {
            this.refreshScrollAmount();
            DebugOptionsScreen.this.triggerImmediateNarration(true);
        }
    }
}

引用的其他类

  • Minecraft

    • 引用位置: 方法调用
    • 关联成员: Minecraft.getInstance()
  • GuiGraphicsExtractor

    • 引用位置: 参数
  • Button

    • 引用位置: 字段/方法调用
    • 关联成员: Button.builder()
  • CycleButton

    • 引用位置: 方法调用
    • 关联成员: CycleButton.booleanBuilder()
  • EditBox

    • 引用位置: 字段/构造调用
    • 关联成员: EditBox()
  • MultiLineTextWidget

    • 引用位置: 构造调用
    • 关联成员: MultiLineTextWidget()
  • StringWidget

    • 引用位置: 构造调用
    • 关联成员: StringWidget()
  • DebugScreenEntries

    • 引用位置: 方法调用
    • 关联成员: DebugScreenEntries.allEntries(), DebugScreenEntries.getEntry()
  • DebugScreenProfile

    • 引用位置: 参数
  • HeaderAndFooterLayout

    • 引用位置: 字段/构造调用
    • 关联成员: HeaderAndFooterLayout()
  • LinearLayout

    • 引用位置: 参数/方法调用
    • 关联成员: LinearLayout.horizontal(), LinearLayout.vertical()
  • SpacerElement

    • 引用位置: 构造调用
    • 关联成员: SpacerElement()
  • NarratableEntry

    • 引用位置: 构造调用
    • 关联成员: NarratableEntry()
  • Screen

    • 引用位置: 继承
  • CommonComponents

    • 引用位置: 方法调用
    • 关联成员: CommonComponents.optionNameValue()
  • Component

    • 引用位置: 字段/方法调用
    • 关联成员: Component.literal(), Component.translatable()