From 714c65c354be1d0b95a1b030c140ffdff0861879 Mon Sep 17 00:00:00 2001 From: Bixilon Date: Mon, 10 Jan 2022 20:39:06 +0100 Subject: [PATCH] merge `HUDElements` and `Elements` --- .../rendering/gui/elements/LayoutedElement.kt | 20 ++++ .../gui/elements/layout/grid/GridLayout.kt | 2 +- .../elements/primitive/AtlasImageElement.kt | 82 ++++++++++++++++ .../gui/elements/primitive/ColorElement.kt | 2 +- .../gui/elements/primitive/ImageElement.kt | 2 - .../gui/elements/spacer/LineSpacerElement.kt | 8 +- .../gui/elements/spacer/SpacerElement.kt | 6 +- .../gui/elements/text/TextFlowElement.kt | 10 +- .../gui/elements/util/ProgressElement.kt | 3 +- .../gui/rendering/gui/gui/screen/Screen.kt | 4 +- .../gui/rendering/gui/hud/HUDRenderer.kt | 34 +++---- .../gui/rendering/gui/hud/Initializable.kt | 20 ++++ .../gui/hud/elements/LayoutedHUDElement.kt | 49 +++++++--- ...{BossbarHUDElement.kt => BossbarLayout.kt} | 19 ++-- .../bossbar/BossbarProgressElement.kt | 6 +- .../{ChatHUDElement.kt => ChatElement.kt} | 29 +++--- ...DElement.kt => InternalMessagesElement.kt} | 26 ++--- .../hotbar/AbstractHotbarHealthElement.kt | 4 +- .../hud/elements/hotbar/HotbarAirElement.kt | 4 +- .../hud/elements/hotbar/HotbarBaseElement.kt | 6 +- .../gui/hud/elements/hotbar/HotbarElement.kt | 56 ++++++++++- .../hud/elements/hotbar/HotbarHUDElement.kt | 79 --------------- .../elements/hotbar/HotbarHealthElement.kt | 4 +- .../elements/hotbar/HotbarHungerElement.kt | 6 +- .../elements/hotbar/HotbarOffhandElement.kt | 4 +- .../hotbar/HotbarProtectionElement.kt | 4 +- .../hotbar/HotbarVehicleHealthElement.kt | 4 +- .../elements/other/BreakProgressHUDElement.kt | 16 ++-- .../hud/elements/other/CrosshairHUDElement.kt | 7 +- .../gui/hud/elements/other/DebugHUDElement.kt | 29 +++--- .../hud/elements/other/WorldInfoHUDElement.kt | 18 ++-- .../scoreboard/ScoreboardHUDElement.kt | 95 ------------------- .../scoreboard/ScoreboardSideElement.kt | 75 ++++++++++++++- .../gui/hud/elements/tab/TabListElement.kt | 63 +++++++++++- .../hud/elements/tab/TabListEntryElement.kt | 6 +- .../gui/hud/elements/tab/TabListHUDElement.kt | 82 ---------------- .../gui/hud/elements/title/TitleElement.kt | 56 ++++++++++- .../gui/hud/elements/title/TitleHUDElement.kt | 74 --------------- .../gui/rendering/renderer/Drawable.kt | 4 +- 39 files changed, 539 insertions(+), 479 deletions(-) create mode 100644 src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/LayoutedElement.kt create mode 100644 src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/AtlasImageElement.kt create mode 100644 src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/Initializable.kt rename src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/{BossbarHUDElement.kt => BossbarLayout.kt} (87%) rename src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/{ChatHUDElement.kt => ChatElement.kt} (71%) rename src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/{InternalMessagesHUDElement.kt => InternalMessagesElement.kt} (68%) delete mode 100644 src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHUDElement.kt delete mode 100644 src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/scoreboard/ScoreboardHUDElement.kt delete mode 100644 src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListHUDElement.kt delete mode 100644 src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/title/TitleHUDElement.kt diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/LayoutedElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/LayoutedElement.kt new file mode 100644 index 000000000..20a1f34e4 --- /dev/null +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/LayoutedElement.kt @@ -0,0 +1,20 @@ +/* + * Minosoft + * Copyright (C) 2020-2022 Moritz Zwerger + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + * + * This software is not affiliated with Mojang AB, the original developer of Minecraft. + */ + +package de.bixilon.minosoft.gui.rendering.gui.elements + +import glm_.vec2.Vec2i + +interface LayoutedElement { + val layoutOffset: Vec2i +} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/layout/grid/GridLayout.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/layout/grid/GridLayout.kt index 20ffdca49..af92a48c8 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/layout/grid/GridLayout.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/layout/grid/GridLayout.kt @@ -24,7 +24,7 @@ import glm_.vec2.Vec2i import java.lang.Integer.min import kotlin.math.max -class GridLayout(guiRenderer: AbstractGUIRenderer, val grid: Vec2i) : Element(guiRenderer) { +open class GridLayout(guiRenderer: AbstractGUIRenderer, val grid: Vec2i) : Element(guiRenderer) { val columnConstraints: Array = Array(grid.x) { GridColumnConstraint() } val rowConstraints: Array = Array(grid.y) { GridRowConstraint() } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/AtlasImageElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/AtlasImageElement.kt new file mode 100644 index 000000000..5500c0e19 --- /dev/null +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/AtlasImageElement.kt @@ -0,0 +1,82 @@ +/* + * Minosoft + * Copyright (C) 2020-2022 Moritz Zwerger + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + * + * This software is not affiliated with Mojang AB, the original developer of Minecraft. + */ + +package de.bixilon.minosoft.gui.rendering.gui.elements.primitive + +import de.bixilon.minosoft.data.text.ChatColors +import de.bixilon.minosoft.data.text.RGBColor +import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer +import de.bixilon.minosoft.gui.rendering.gui.atlas.TextureLike +import de.bixilon.minosoft.gui.rendering.gui.elements.Element +import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIMesh +import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer +import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions +import de.bixilon.minosoft.gui.rendering.system.base.texture.texture.AbstractTexture +import glm_.vec2.Vec2 +import glm_.vec2.Vec2i + +open class AtlasImageElement( + guiRenderer: AbstractGUIRenderer, + val textureLike: TextureLike, + size: Vec2i = textureLike.size, + tint: RGBColor = ChatColors.WHITE, +) : Element(guiRenderer) { + override var initialCacheSize: Int = GUIMesh.GUIMeshStruct.FLOATS_PER_VERTEX * 6 + var texture: AbstractTexture = textureLike.texture + set(value) { + field = value + cacheUpToDate = false + } + var uvStart: Vec2? = null + set(value) { + field = value + cacheUpToDate = false + } + var uvEnd: Vec2? = null + set(value) { + field = value + cacheUpToDate = false + } + + override var size: Vec2i + get() = super.size + set(value) { + super.size = value + cacheUpToDate = false + } + + override var prefSize: Vec2i + get() = size + set(value) { + size = value + } + + var tint: RGBColor = tint + set(value) { + field = value + cacheUpToDate = false + } + + init { + this.size = size + } + + + override fun forceRender(offset: Vec2i, z: Int, consumer: GUIVertexConsumer, options: GUIVertexOptions?): Int { + consumer.addQuad(offset, offset + size, z, texture, uvStart ?: textureLike.uvStart, uvEnd ?: textureLike.uvEnd, tint, options) + return 1 + } + + override fun forceSilentApply() = Unit + override fun silentApply(): Boolean = false +} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/ColorElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/ColorElement.kt index f7ca34425..6643efd59 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/ColorElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/ColorElement.kt @@ -22,6 +22,6 @@ class ColorElement( guiRenderer: AbstractGUIRenderer, size: Vec2i, color: RGBColor = ChatColors.WHITE, -) : ImageElement(guiRenderer, guiRenderer.renderWindow.WHITE_TEXTURE, size, color) { +) : AtlasImageElement(guiRenderer, guiRenderer.renderWindow.WHITE_TEXTURE, size, color) { var color by this::tint } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/ImageElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/ImageElement.kt index 0ef68341d..85337befc 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/ImageElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/primitive/ImageElement.kt @@ -16,7 +16,6 @@ package de.bixilon.minosoft.gui.rendering.gui.elements.primitive import de.bixilon.minosoft.data.text.ChatColors import de.bixilon.minosoft.data.text.RGBColor import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer -import de.bixilon.minosoft.gui.rendering.gui.atlas.TextureLike import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIMesh import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer @@ -74,7 +73,6 @@ open class ImageElement( this.size = size } - constructor(guiRenderer: AbstractGUIRenderer, texture: TextureLike, size: Vec2i = texture.size, tint: RGBColor = ChatColors.WHITE) : this(guiRenderer, texture.texture, texture.uvStart, texture.uvEnd, size, tint) constructor(guiRenderer: AbstractGUIRenderer, texture: AbstractTexture, uvStart: Vec2i, uvEnd: Vec2i, size: Vec2i = texture.size, tint: RGBColor = ChatColors.WHITE) : this(guiRenderer, texture, Vec2(uvStart) * texture.singlePixelSize, Vec2(uvEnd) * texture.singlePixelSize, size, tint) diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/spacer/LineSpacerElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/spacer/LineSpacerElement.kt index cdca1cb3a..d63e057f1 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/spacer/LineSpacerElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/spacer/LineSpacerElement.kt @@ -1,6 +1,6 @@ /* * Minosoft - * Copyright (C) 2021 Moritz Zwerger + * Copyright (C) 2020-2022 Moritz Zwerger * * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. * @@ -14,14 +14,14 @@ package de.bixilon.minosoft.gui.rendering.gui.elements.spacer import de.bixilon.minosoft.gui.rendering.font.Font -import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY import glm_.vec2.Vec2i class LineSpacerElement( - hudRenderer: HUDRenderer, + guiRenderer: AbstractGUIRenderer, lines: Int = 1, -) : SpacerElement(hudRenderer, Vec2i.EMPTY) { +) : SpacerElement(guiRenderer, Vec2i.EMPTY) { var lines: Int = 0 set(value) { field = value diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/spacer/SpacerElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/spacer/SpacerElement.kt index 98e3f45ec..07559d3c2 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/spacer/SpacerElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/spacer/SpacerElement.kt @@ -1,6 +1,6 @@ /* * Minosoft - * Copyright (C) 2021 Moritz Zwerger + * Copyright (C) 2020-2022 Moritz Zwerger * * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. * @@ -13,13 +13,13 @@ package de.bixilon.minosoft.gui.rendering.gui.elements.spacer +import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element -import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import glm_.vec2.Vec2i -open class SpacerElement(hudRenderer: HUDRenderer, override var size: Vec2i) : Element(hudRenderer) { +open class SpacerElement(guiRenderer: AbstractGUIRenderer, override var size: Vec2i) : Element(guiRenderer) { override fun forceRender(offset: Vec2i, z: Int, consumer: GUIVertexConsumer, options: GUIVertexOptions?): Int = 0 diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/text/TextFlowElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/text/TextFlowElement.kt index c029031a4..366ab710c 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/text/TextFlowElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/text/TextFlowElement.kt @@ -19,23 +19,23 @@ import de.bixilon.kutil.time.TimeUtil import de.bixilon.minosoft.data.text.ChatComponent import de.bixilon.minosoft.gui.rendering.RenderConstants import de.bixilon.minosoft.gui.rendering.font.Font +import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ColorElement -import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.max import glm_.vec2.Vec2i -class TextFlowElement( - hudRenderer: HUDRenderer, +open class TextFlowElement( + guiRenderer: AbstractGUIRenderer, var messageExpireTime: Long, -) : Element(hudRenderer) { +) : Element(guiRenderer) { private val messages: MutableList = synchronizedListOf() // all messages **from newest to oldest** private var visibleLines: List = listOf() // all visible lines **from bottom to top** - private val background = ColorElement(hudRenderer, size, RenderConstants.TEXT_BACKGROUND_COLOR) + private val background = ColorElement(guiRenderer, size, RenderConstants.TEXT_BACKGROUND_COLOR) // Used for scrolling in GUI (not hud) private val active: Boolean = false // if always all lines should be displayed when possible diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/util/ProgressElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/util/ProgressElement.kt index 553cf1308..278b4b8f8 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/util/ProgressElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/elements/util/ProgressElement.kt @@ -16,6 +16,7 @@ package de.bixilon.minosoft.gui.rendering.gui.elements.util import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.atlas.AtlasElement import de.bixilon.minosoft.gui.rendering.gui.elements.Element +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions @@ -38,7 +39,7 @@ open class ProgressElement( forceSilentApply() // ToDo: Animate } - protected val emptyImage = ImageElement(guiRenderer, emptyAtlasElement) + protected val emptyImage = AtlasImageElement(guiRenderer, emptyAtlasElement) protected lateinit var progressImage: ImageElement diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/gui/screen/Screen.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/gui/screen/Screen.kt index 5b93f1ca9..d680658e0 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/gui/screen/Screen.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/gui/screen/Screen.kt @@ -17,11 +17,11 @@ import de.bixilon.minosoft.data.text.RGBColor import de.bixilon.minosoft.gui.rendering.RenderWindow import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.GUIElement -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement abstract class Screen( override val guiRenderer: AbstractGUIRenderer, ) : GUIElement { override val renderWindow: RenderWindow = guiRenderer.renderWindow - val background = ImageElement(guiRenderer, renderWindow.WHITE_TEXTURE, size = guiRenderer.scaledSize, tint = RGBColor(1.0f, 1.0f, 1.0f, 0.8f)) + val background = AtlasImageElement(guiRenderer, renderWindow.WHITE_TEXTURE, size = guiRenderer.scaledSize, tint = RGBColor(1.0f, 1.0f, 1.0f, 0.8f)) } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/HUDRenderer.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/HUDRenderer.kt index b75ed31e8..57e2bbd1a 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/HUDRenderer.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/HUDRenderer.kt @@ -28,17 +28,17 @@ import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.bossbar.BossbarHUDElement -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.chat.ChatHUDElement -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.chat.InternalMessagesHUDElement -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.hotbar.HotbarHUDElement +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.bossbar.BossbarLayout +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.chat.ChatElement +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.chat.InternalMessagesElement +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.hotbar.HotbarElement import de.bixilon.minosoft.gui.rendering.gui.hud.elements.other.BreakProgressHUDElement import de.bixilon.minosoft.gui.rendering.gui.hud.elements.other.CrosshairHUDElement import de.bixilon.minosoft.gui.rendering.gui.hud.elements.other.DebugHUDElement import de.bixilon.minosoft.gui.rendering.gui.hud.elements.other.WorldInfoHUDElement -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.scoreboard.ScoreboardHUDElement -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.tab.TabListHUDElement -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.title.TitleHUDElement +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.scoreboard.ScoreboardSideElement +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.tab.TabListElement +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.title.TitleElement import de.bixilon.minosoft.gui.rendering.modding.events.ResizeWindowEvent import de.bixilon.minosoft.gui.rendering.renderer.Drawable import de.bixilon.minosoft.gui.rendering.renderer.Renderer @@ -95,16 +95,16 @@ class HUDRenderer( private fun registerDefaultElements() { registerElement(DebugHUDElement) registerElement(CrosshairHUDElement) - registerElement(BossbarHUDElement) - registerElement(ChatHUDElement) + registerElement(BossbarLayout) + registerElement(ChatElement) - registerElement(InternalMessagesHUDElement) + registerElement(InternalMessagesElement) registerElement(BreakProgressHUDElement) - registerElement(TabListHUDElement) - registerElement(HotbarHUDElement) + registerElement(TabListElement) + registerElement(HotbarElement) registerElement(WorldInfoHUDElement) - registerElement(TitleHUDElement) - registerElement(ScoreboardHUDElement) + registerElement(TitleElement) + registerElement(ScoreboardSideElement) } private fun recalculateMatrices(windowSize: Vec2i = renderWindow.window.size, scale: Float = profile.scale) { @@ -114,7 +114,7 @@ class HUDRenderer( for (element in hudElements.toSynchronizedMap().values) { if (element is LayoutedHUDElement<*>) { - element.layout.silentApply() + element.elementLayout.silentApply() } element.apply() } @@ -205,8 +205,8 @@ class HUDRenderer( } } - operator fun > get(hudBuilder: HUDBuilder<*>): T? { - return hudElements[hudBuilder.RESOURCE_LOCATION].unsafeCast() + operator fun get(hudBuilder: HUDBuilder): T? { + return hudElements[hudBuilder.RESOURCE_LOCATION]?.unsafeCast() } companion object : RendererBuilder { diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/Initializable.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/Initializable.kt new file mode 100644 index 000000000..93279b311 --- /dev/null +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/Initializable.kt @@ -0,0 +1,20 @@ +/* + * Minosoft + * Copyright (C) 2020-2022 Moritz Zwerger + * + * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with this program. If not, see . + * + * This software is not affiliated with Mojang AB, the original developer of Minecraft. + */ + +package de.bixilon.minosoft.gui.rendering.gui.hud + +interface Initializable { + + fun init() {} + fun postInit() {} +} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/LayoutedHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/LayoutedHUDElement.kt index 7af17f6c8..d2b589b27 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/LayoutedHUDElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/LayoutedHUDElement.kt @@ -13,27 +13,44 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements +import de.bixilon.kutil.cast.CastUtil.unsafeCast import de.bixilon.minosoft.gui.rendering.RenderWindow +import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDElement -import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIMesh +import de.bixilon.minosoft.gui.rendering.renderer.Drawable import de.bixilon.minosoft.gui.rendering.util.mesh.Mesh import de.bixilon.minosoft.util.collections.floats.DirectArrayFloatList -import glm_.vec2.Vec2i -abstract class LayoutedHUDElement(final override val guiRenderer: HUDRenderer) : HUDElement { - final override val renderWindow: RenderWindow = guiRenderer.renderWindow +class LayoutedHUDElement( + val layout: T, +) : HUDElement, Drawable { + val elementLayout = layout.unsafeCast() + override val guiRenderer: AbstractGUIRenderer = elementLayout.guiRenderer + override val renderWindow: RenderWindow = guiRenderer.renderWindow override var enabled = true var mesh: GUIMesh = GUIMesh(renderWindow, guiRenderer.matrix, DirectArrayFloatList(1000)) private var lastRevision = 0L - - - abstract val layout: T - abstract val layoutOffset: Vec2i + override val skipDraw: Boolean + get() = if (layout is Drawable) layout.skipDraw else false override fun tick() { - layout.tick() + elementLayout.tick() + } + + override fun init() { + if (layout is Initializable) { + layout.init() + } + } + + override fun postInit() { + if (layout is Initializable) { + layout.postInit() + } } private fun createNewMesh() { @@ -45,10 +62,10 @@ abstract class LayoutedHUDElement(final override val guiRenderer: H } fun prepare(z: Int): Int { - val layoutOffset = layoutOffset - val usedZ = layout.render(layoutOffset, z, mesh, null) + val layoutOffset = layout.layoutOffset + val usedZ = elementLayout.render(layoutOffset, z, mesh, null) - val revision = layout.cache.revision + val revision = elementLayout.cache.revision if (revision != lastRevision) { createNewMesh() this.mesh.load() @@ -58,9 +75,15 @@ abstract class LayoutedHUDElement(final override val guiRenderer: H return usedZ } + override fun draw() { + if (layout is Drawable) { + layout.draw() + } + } + fun initMesh() { - layout.cache.data = mesh.data + elementLayout.cache.data = mesh.data mesh.load() } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarLayout.kt similarity index 87% rename from src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarHUDElement.kt rename to src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarLayout.kt index 81e89e278..60fbb1912 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarHUDElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarLayout.kt @@ -17,8 +17,10 @@ import de.bixilon.kutil.collections.CollectionUtil.synchronizedMapOf import de.bixilon.minosoft.data.bossbar.Bossbar import de.bixilon.minosoft.data.registries.ResourceLocation import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.layout.RowLayout import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement import de.bixilon.minosoft.modding.event.events.bossbar.* @@ -26,13 +28,12 @@ import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i -class BossbarHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer) { +class BossbarLayout(hudRenderer: HUDRenderer) : RowLayout(hudRenderer, HorizontalAlignments.CENTER, 2), LayoutedElement, Initializable { private val connection = renderWindow.connection - override val layout: RowLayout = RowLayout(hudRenderer, HorizontalAlignments.CENTER, 2) private val bossbars: MutableMap = synchronizedMapOf() override val layoutOffset: Vec2i - get() = Vec2i((guiRenderer.scaledSize.x - layout.size.x) / 2, 2) + get() = Vec2i((guiRenderer.scaledSize.x - super.size.x) / 2, 2) val atlasManager = hudRenderer.atlasManager @@ -93,14 +94,14 @@ class BossbarHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement { val element = BossbarElement(guiRenderer, it.bossbar, atlas) - layout += element + this += element val previous = bossbars.put(it.bossbar, element) ?: return@of - layout -= previous + this -= previous }) connection.registerEvent(CallbackEventInvoker.of { val element = bossbars.remove(it.bossbar) ?: return@of - layout -= element + this -= element }) connection.registerEvent(CallbackEventInvoker.of { @@ -115,11 +116,11 @@ class BossbarHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement { + companion object : HUDBuilder> { override val RESOURCE_LOCATION: ResourceLocation = "minosoft:bossbar".toResourceLocation() - override fun build(hudRenderer: HUDRenderer): BossbarHUDElement { - return BossbarHUDElement(hudRenderer) + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(BossbarLayout(hudRenderer)) } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarProgressElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarProgressElement.kt index 553b68b92..37ab318e8 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarProgressElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/bossbar/BossbarProgressElement.kt @@ -15,7 +15,7 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.bossbar import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.atlas.AtlasElement -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.elements.util.ProgressElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions @@ -29,8 +29,8 @@ open class BossbarProgressElement( fullNotchesElement: AtlasElement?, progress: Float = 0.0f, ) : ProgressElement(guiRenderer, emptyProgressAtlasElement, fullProgressAtlasElement, progress) { - private val emptyNotchesImage = emptyNotchesElement?.let { ImageElement(guiRenderer, it, emptyProgressAtlasElement.size) } - private val fullNotchesImage = fullNotchesElement?.let { ImageElement(guiRenderer, it, emptyProgressAtlasElement.size) } + private val emptyNotchesImage = emptyNotchesElement?.let { AtlasImageElement(guiRenderer, it, emptyProgressAtlasElement.size) } + private val fullNotchesImage = fullNotchesElement?.let { AtlasImageElement(guiRenderer, it, emptyProgressAtlasElement.size) } constructor(guiRenderer: AbstractGUIRenderer, progressElements: Array, notchesElements: Array?, progress: Float = 0.0f) : this(guiRenderer, progressElements[0], progressElements[1], notchesElements?.get(0), notchesElements?.get(1), progress) diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/ChatHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/ChatElement.kt similarity index 71% rename from src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/ChatHUDElement.kt rename to src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/ChatElement.kt index 98f5c82a8..cada2b790 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/ChatHUDElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/ChatElement.kt @@ -16,35 +16,38 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.chat import de.bixilon.minosoft.config.profile.delegate.watcher.SimpleProfileDelegateWatcher.Companion.profileWatchRendering import de.bixilon.minosoft.data.ChatTextPositions import de.bixilon.minosoft.data.registries.ResourceLocation +import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextFlowElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement +import de.bixilon.minosoft.gui.rendering.renderer.Drawable import de.bixilon.minosoft.modding.event.events.ChatMessageReceiveEvent import de.bixilon.minosoft.modding.event.events.InternalMessageReceiveEvent import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i -class ChatHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer) { +class ChatElement(guiRenderer: AbstractGUIRenderer) : TextFlowElement(guiRenderer, 20000), LayoutedElement, Initializable, Drawable { private val connection = renderWindow.connection private val profile = connection.profiles.hud private val chatProfile = profile.chat - override val layout = TextFlowElement(hudRenderer, 20000) - override var enabled: Boolean - get() = !chatProfile.hidden + override var skipDraw: Boolean + get() = chatProfile.hidden set(value) { chatProfile.hidden = !value } override val layoutOffset: Vec2i - get() = Vec2i(2, guiRenderer.scaledSize.y - layout.size.y - BOTTOM_OFFSET) + get() = Vec2i(2, guiRenderer.scaledSize.y - super.size.y - BOTTOM_OFFSET) init { - layout.prefMaxSize = Vec2i(chatProfile.width, chatProfile.height) - chatProfile::width.profileWatchRendering(this, profile = profile) { layout.prefMaxSize = Vec2i(it, layout.prefMaxSize.y) } - chatProfile::height.profileWatchRendering(this, profile = profile) { layout.prefMaxSize = Vec2i(layout.prefMaxSize.x, it) } + super.prefMaxSize = Vec2i(chatProfile.width, chatProfile.height) + chatProfile::width.profileWatchRendering(this, profile = profile) { super.prefMaxSize = Vec2i(it, super.prefMaxSize.y) } + chatProfile::height.profileWatchRendering(this, profile = profile) { super.prefMaxSize = Vec2i(super.prefMaxSize.x, it) } } @@ -53,23 +56,23 @@ class ChatHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement { if (!profile.chat.internal.hidden) { return@of } - layout += it.message + this += it.message }) } - companion object : HUDBuilder { + companion object : HUDBuilder> { override val RESOURCE_LOCATION: ResourceLocation = "minosoft:chat_hud".toResourceLocation() private const val BOTTOM_OFFSET = 30 - override fun build(hudRenderer: HUDRenderer): ChatHUDElement { - return ChatHUDElement(hudRenderer) + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(ChatElement(hudRenderer)) } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/InternalMessagesHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/InternalMessagesElement.kt similarity index 68% rename from src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/InternalMessagesHUDElement.kt rename to src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/InternalMessagesElement.kt index 02b6e8000..b6edf4afb 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/InternalMessagesHUDElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/chat/InternalMessagesElement.kt @@ -15,48 +15,50 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.chat import de.bixilon.minosoft.config.profile.delegate.watcher.SimpleProfileDelegateWatcher.Companion.profileWatchRendering import de.bixilon.minosoft.data.registries.ResourceLocation +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextFlowElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement +import de.bixilon.minosoft.gui.rendering.renderer.Drawable import de.bixilon.minosoft.modding.event.events.InternalMessageReceiveEvent import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i -class InternalMessagesHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer) { +class InternalMessagesElement(hudRenderer: HUDRenderer) : TextFlowElement(hudRenderer, 15000), LayoutedElement, Initializable, Drawable { private val connection = renderWindow.connection private val profile = connection.profiles.hud private val internalChatProfile = profile.chat.internal - override val layout = TextFlowElement(hudRenderer, 15000) - override var enabled: Boolean - get() = !internalChatProfile.hidden + override var skipDraw: Boolean + get() = internalChatProfile.hidden set(value) { internalChatProfile.hidden = !value } override val layoutOffset: Vec2i - get() = guiRenderer.scaledSize - Vec2i(layout.size.x, layout.size.y + BOTTOM_OFFSET) + get() = super.size.let { return@let guiRenderer.scaledSize - Vec2i(it.x, it.y + BOTTOM_OFFSET) } init { - layout.prefMaxSize = Vec2i(internalChatProfile.width, internalChatProfile.height) - internalChatProfile::width.profileWatchRendering(this, profile = profile) { layout.prefMaxSize = Vec2i(it, layout.prefMaxSize.y) } - internalChatProfile::height.profileWatchRendering(this, profile = profile) { layout.prefMaxSize = Vec2i(layout.prefMaxSize.x, it) } + super.prefMaxSize = Vec2i(internalChatProfile.width, internalChatProfile.height) + internalChatProfile::width.profileWatchRendering(this, profile = profile) { super.prefMaxSize = Vec2i(it, super.prefMaxSize.y) } + internalChatProfile::height.profileWatchRendering(this, profile = profile) { super.prefMaxSize = Vec2i(super.prefMaxSize.x, it) } } override fun init() { - connection.registerEvent(CallbackEventInvoker.of { layout += it.message }) + connection.registerEvent(CallbackEventInvoker.of { this += it.message }) } - companion object : HUDBuilder { + companion object : HUDBuilder> { override val RESOURCE_LOCATION: ResourceLocation = "minosoft:internal_messages_hud".toResourceLocation() private const val BOTTOM_OFFSET = 30 - override fun build(hudRenderer: HUDRenderer): InternalMessagesHUDElement { - return InternalMessagesHUDElement(hudRenderer) + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(InternalMessagesElement(hudRenderer)) } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/AbstractHotbarHealthElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/AbstractHotbarHealthElement.kt index cd4d61a7c..6def8dc3a 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/AbstractHotbarHealthElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/AbstractHotbarHealthElement.kt @@ -19,7 +19,7 @@ import de.bixilon.minosoft.data.text.RGBColor.Companion.asColor import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.atlas.AtlasElement import de.bixilon.minosoft.gui.rendering.gui.elements.Element -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions @@ -59,7 +59,7 @@ abstract class AbstractHotbarHealthElement(guiRenderer: AbstractGUIRenderer) : E val row = heart / HEARTS_PER_ROW val column = heart % HEARTS_PER_ROW - val image = ImageElement(guiRenderer, atlasElement) + val image = AtlasImageElement(guiRenderer, atlasElement) image.render(offset + Vec2i(column, (rows - 1) - row) * HEART_SIZE, z, consumer, options) } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarAirElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarAirElement.kt index 6e9e5e15e..e9eaeb58c 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarAirElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarAirElement.kt @@ -18,7 +18,7 @@ import de.bixilon.minosoft.data.registries.fluid.DefaultFluids import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY @@ -48,7 +48,7 @@ class HotbarAirElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer), atlasElement = poppingAirBubble } - val image = ImageElement(guiRenderer, atlasElement) + val image = AtlasImageElement(guiRenderer, atlasElement) image.render(offset + Vec2i(i * BUBBLE_SIZE.x, 0), z, consumer, options) } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarBaseElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarBaseElement.kt index 1915d34bb..b3a3343e1 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarBaseElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarBaseElement.kt @@ -18,7 +18,7 @@ import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable import de.bixilon.minosoft.gui.rendering.gui.elements.items.ContainerItemsElement -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import de.bixilon.minosoft.util.KUtil.toResourceLocation @@ -26,8 +26,8 @@ import glm_.vec2.Vec2i class HotbarBaseElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer), Pollable { private val baseAtlasElement = guiRenderer.renderWindow.atlasManager[BASE]!! - private val base = ImageElement(guiRenderer, baseAtlasElement) - private val frame = ImageElement(guiRenderer, guiRenderer.renderWindow.atlasManager[FRAME]!!, size = Vec2i(FRAME_SIZE)) + private val base = AtlasImageElement(guiRenderer, baseAtlasElement) + private val frame = AtlasImageElement(guiRenderer, guiRenderer.renderWindow.atlasManager[FRAME]!!, size = Vec2i(FRAME_SIZE)) private val containerElement = ContainerItemsElement(guiRenderer, guiRenderer.renderWindow.connection.player.inventory, baseAtlasElement.slots) diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarElement.kt index be04f2f24..31b44a1cf 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarElement.kt @@ -13,23 +13,37 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.hotbar +import de.bixilon.minosoft.data.ChatTextPositions import de.bixilon.minosoft.data.inventory.InventorySlots import de.bixilon.minosoft.data.inventory.ItemStack import de.bixilon.minosoft.data.player.Arms +import de.bixilon.minosoft.data.registries.ResourceLocation +import de.bixilon.minosoft.data.registries.other.game.event.handlers.gamemode.GamemodeChangeEvent import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments.Companion.getOffset +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.FadingTextElement +import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY import de.bixilon.minosoft.gui.rendering.util.vec.vec4.Vec4iUtil.left import de.bixilon.minosoft.gui.rendering.util.vec.vec4.Vec4iUtil.right +import de.bixilon.minosoft.modding.event.events.ChatMessageReceiveEvent +import de.bixilon.minosoft.modding.event.events.ExperienceChangeEvent +import de.bixilon.minosoft.modding.event.events.SelectHotbarSlotEvent +import de.bixilon.minosoft.modding.event.events.container.ContainerRevisionChangeEvent +import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker +import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i import java.lang.Integer.max -class HotbarElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer) { +class HotbarElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer), LayoutedElement, Initializable { val core = HotbarCoreElement(guiRenderer) val offhand = HotbarOffhandElement(guiRenderer) @@ -43,6 +57,10 @@ class HotbarElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer) { private var lastItemSlot = -1 private var itemTextShown = true + + override val layoutOffset: Vec2i + get() = size.let { Vec2i((guiRenderer.scaledSize.x - it.x) / 2, guiRenderer.scaledSize.y - it.y) } + private var renderElements = setOf( itemText, hoverText, @@ -151,8 +169,42 @@ class HotbarElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer) { offhand.tick() } - companion object { + + override fun postInit() { + prefMaxSize = Vec2i(-1, -1) + + val connection = renderWindow.connection + connection.registerEvent(CallbackEventInvoker.of { core.experience.apply() }) + + connection.registerEvent(CallbackEventInvoker.of { forceApply() }) + + connection.registerEvent(CallbackEventInvoker.of { core.base.apply() }) + + connection.registerEvent(CallbackEventInvoker.of { + if (it.container != connection.player.inventory) { + return@of + } + core.base.apply() + offhand.apply() + }) + + connection.registerEvent(CallbackEventInvoker.of { + if (it.position != ChatTextPositions.ABOVE_HOTBAR) { + return@of + } + hoverText.text = it.message + hoverText.show() + }) + } + + + companion object : HUDBuilder> { + override val RESOURCE_LOCATION: ResourceLocation = "minosoft:hotbar".toResourceLocation() private const val HOVER_TEXT_OFFSET = 15 private const val ITEM_NAME_OFFSET = 5 + + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(HotbarElement(hudRenderer)) + } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHUDElement.kt deleted file mode 100644 index c4202ebb9..000000000 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHUDElement.kt +++ /dev/null @@ -1,79 +0,0 @@ -/* - * Minosoft - * Copyright (C) 2020-2022 Moritz Zwerger - * - * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with this program. If not, see . - * - * This software is not affiliated with Mojang AB, the original developer of Minecraft. - */ - -package de.bixilon.minosoft.gui.rendering.gui.hud.elements.hotbar - -import de.bixilon.minosoft.data.ChatTextPositions -import de.bixilon.minosoft.data.registries.ResourceLocation -import de.bixilon.minosoft.data.registries.other.game.event.handlers.gamemode.GamemodeChangeEvent -import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement -import de.bixilon.minosoft.modding.event.events.ChatMessageReceiveEvent -import de.bixilon.minosoft.modding.event.events.ExperienceChangeEvent -import de.bixilon.minosoft.modding.event.events.SelectHotbarSlotEvent -import de.bixilon.minosoft.modding.event.events.container.ContainerRevisionChangeEvent -import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker -import de.bixilon.minosoft.util.KUtil.toResourceLocation -import glm_.vec2.Vec2i - -class HotbarHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer) { - private val connection = renderWindow.connection - override lateinit var layout: HotbarElement - - - override val layoutOffset: Vec2i - get() = Vec2i((guiRenderer.scaledSize.x - layout.size.x) / 2, guiRenderer.scaledSize.y - layout.size.y) - - override fun postInit() { - layout = HotbarElement(guiRenderer) // ToDo: The base uses image elements, that are available after init stage - layout.prefMaxSize = Vec2i(-1, -1) - - connection.registerEvent(CallbackEventInvoker.of { - layout.core.experience.apply() - }) - - connection.registerEvent(CallbackEventInvoker.of { - layout.forceApply() - }) - - connection.registerEvent(CallbackEventInvoker.of { - layout.core.base.apply() - }) - - connection.registerEvent(CallbackEventInvoker.of { - if (it.container != connection.player.inventory) { - return@of - } - layout.core.base.apply() - layout.offhand.apply() - }) - - connection.registerEvent(CallbackEventInvoker.of { - if (it.position != ChatTextPositions.ABOVE_HOTBAR) { - return@of - } - layout.hoverText.text = it.message - layout.hoverText.show() - }) - } - - - companion object : HUDBuilder { - override val RESOURCE_LOCATION: ResourceLocation = "minosoft:hotbar".toResourceLocation() - - override fun build(hudRenderer: HUDRenderer): HotbarHUDElement { - return HotbarHUDElement(hudRenderer) - } - } -} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHealthElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHealthElement.kt index 05bda8590..bc9023628 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHealthElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHealthElement.kt @@ -25,7 +25,7 @@ import de.bixilon.minosoft.data.text.TextComponent import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.atlas.AtlasElement import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import glm_.vec2.Vec2i @@ -197,7 +197,7 @@ class HotbarHealthElement(guiRenderer: AbstractGUIRenderer) : AbstractHotbarHeal val image = selectArray.unsafeCast>()[when { halfHeart -> 1 else -> 0 - }]?.let { ImageElement(guiRenderer, it) } + }]?.let { AtlasImageElement(guiRenderer, it) } image?.render(offset + Vec2i(column, (rows - 1) - row) * HEART_SIZE, z + 1, consumer, options) diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHungerElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHungerElement.kt index 6c2aecde5..683061663 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHungerElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarHungerElement.kt @@ -18,7 +18,7 @@ import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.atlas.AtlasElement import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import glm_.vec2.Vec2i @@ -98,7 +98,7 @@ class HotbarHungerElement(guiRenderer: AbstractGUIRenderer) : Element(guiRendere } else -> normalHungerContainer } - ImageElement(guiRenderer, container).render(hungerOffset, z, consumer, options) + AtlasImageElement(guiRenderer, container).render(hungerOffset, z, consumer, options) val selectArray: Array<*> = if (hungerEffect) { @@ -121,7 +121,7 @@ class HotbarHungerElement(guiRenderer: AbstractGUIRenderer) : Element(guiRendere hungerElement = selectArray[0] as AtlasElement } - ImageElement(guiRenderer, hungerElement).render(hungerOffset, z + 1, consumer, options) + AtlasImageElement(guiRenderer, hungerElement).render(hungerOffset, z + 1, consumer, options) } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarOffhandElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarOffhandElement.kt index 87f303a6b..ae498fa08 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarOffhandElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarOffhandElement.kt @@ -18,7 +18,7 @@ import de.bixilon.minosoft.data.player.Arms.Companion.opposite import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.items.ContainerItemsElement -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import de.bixilon.minosoft.gui.rendering.util.vec.vec4.Vec4iUtil.marginOf @@ -34,7 +34,7 @@ class HotbarOffhandElement(guiRenderer: AbstractGUIRenderer) : Element(guiRender val offArm = guiRenderer.renderWindow.connection.player.mainArm.opposite // ToDo: Support arm change private val frame = frames[offArm.ordinal]!! - private var frameImage = ImageElement(guiRenderer, frame) + private var frameImage = AtlasImageElement(guiRenderer, frame) private val containerElement = ContainerItemsElement(guiRenderer, guiRenderer.renderWindow.connection.player.inventory, frame.slots) init { diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarProtectionElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarProtectionElement.kt index ccbcfcb76..a00cd6a97 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarProtectionElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarProtectionElement.kt @@ -16,7 +16,7 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.hotbar import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY @@ -47,7 +47,7 @@ class HotbarProtectionElement(guiRenderer: AbstractGUIRenderer) : Element(guiRen else -> fullProtection } - val image = ImageElement(guiRenderer, atlasElement) + val image = AtlasImageElement(guiRenderer, atlasElement) image.render(offset + Vec2i(i * ARMOR_SIZE.x, 0), z, consumer, options) diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarVehicleHealthElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarVehicleHealthElement.kt index 80214a9cf..960260cf5 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarVehicleHealthElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/hotbar/HotbarVehicleHealthElement.kt @@ -22,7 +22,7 @@ import de.bixilon.minosoft.data.text.RGBColor.Companion.asColor import de.bixilon.minosoft.data.text.TextComponent import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions import glm_.vec2.Vec2i @@ -65,7 +65,7 @@ class HotbarVehicleHealthElement(guiRenderer: AbstractGUIRenderer) : AbstractHot val image = hearts[when { halfHeart -> 1 else -> 0 - }]?.let { ImageElement(guiRenderer, it) } + }]?.let { AtlasImageElement(guiRenderer, it) } image?.render(offset + Vec2i(column, (rows - 1) - row) * HEART_SIZE, z + 1, consumer, options) diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/BreakProgressHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/BreakProgressHUDElement.kt index d8359080d..30effb4c4 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/BreakProgressHUDElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/BreakProgressHUDElement.kt @@ -16,6 +16,7 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.other import de.bixilon.minosoft.data.registries.ResourceLocation import de.bixilon.minosoft.data.text.ChatColors import de.bixilon.minosoft.data.text.TextComponent +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder @@ -24,19 +25,18 @@ import de.bixilon.minosoft.gui.rendering.renderer.Drawable import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i -class BreakProgressHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer), Drawable { - override val layout: TextElement = TextElement(hudRenderer, "") +class BreakProgressHUDElement(hudRenderer: HUDRenderer) : TextElement(hudRenderer, ""), LayoutedElement, Drawable { private val breakInteractionHandler = hudRenderer.renderWindow.inputHandler.interactionManager.`break` override val layoutOffset: Vec2i - get() = Vec2i((guiRenderer.scaledSize.x / 2) + CrosshairHUDElement.CROSSHAIR_SIZE / 2 + 5, (guiRenderer.scaledSize.y - layout.size.y) / 2) + get() = Vec2i((guiRenderer.scaledSize.x / 2) + CrosshairHUDElement.CROSSHAIR_SIZE / 2 + 5, (guiRenderer.scaledSize.y - super.size.y) / 2) private var percent = -1 override fun draw() { val breakProgress = breakInteractionHandler.breakProgress if (breakProgress <= 0 || breakProgress >= 1.0) { - layout.text = "" + super.text = "" this.percent = -1 return } @@ -44,7 +44,7 @@ class BreakProgressHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement ChatColors.RED percent <= 70 -> ChatColors.YELLOW @@ -54,11 +54,11 @@ class BreakProgressHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement { + companion object : HUDBuilder> { override val RESOURCE_LOCATION: ResourceLocation = "minosoft:progress_indicator".toResourceLocation() - override fun build(hudRenderer: HUDRenderer): BreakProgressHUDElement { - return BreakProgressHUDElement(hudRenderer) + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(BreakProgressHUDElement(hudRenderer)) } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/CrosshairHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/CrosshairHUDElement.kt index 922b30808..c799a1640 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/CrosshairHUDElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/CrosshairHUDElement.kt @@ -22,12 +22,13 @@ import de.bixilon.minosoft.gui.rendering.gui.atlas.AtlasElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer import de.bixilon.minosoft.gui.rendering.gui.hud.elements.CustomHUDElement import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIMesh import de.bixilon.minosoft.gui.rendering.system.base.BlendingFunctions import de.bixilon.minosoft.util.KUtil.toResourceLocation import de.bixilon.minosoft.util.collections.floats.DirectArrayFloatList -class CrosshairHUDElement(hudRenderer: HUDRenderer) : CustomHUDElement(hudRenderer) { +class CrosshairHUDElement(private val hudRenderer: HUDRenderer) : CustomHUDElement(hudRenderer) { private val profile = hudRenderer.connection.profiles.hud private val crosshairProfile = profile.crosshair private lateinit var crosshairAtlasElement: AtlasElement @@ -41,7 +42,7 @@ class CrosshairHUDElement(hudRenderer: HUDRenderer) : CustomHUDElement(hudRender } override fun draw() { - val debugHUDElement: DebugHUDElement? = guiRenderer[DebugHUDElement] + val debugHUDElement: LayoutedHUDElement? = hudRenderer[DebugHUDElement] if (debugHUDElement?.enabled != previousDebugEnabled || reapply) { apply() @@ -75,7 +76,7 @@ class CrosshairHUDElement(hudRenderer: HUDRenderer) : CustomHUDElement(hudRender } } - val debugHUDElement: DebugHUDElement? = guiRenderer[DebugHUDElement] + val debugHUDElement: LayoutedHUDElement? = guiRenderer[DebugHUDElement] if (debugHUDElement?.enabled == true) { // ToDo: Debug crosshair diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/DebugHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/DebugHUDElement.kt index 41286f97f..45638bc80 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/DebugHUDElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/DebugHUDElement.kt @@ -25,8 +25,10 @@ import de.bixilon.minosoft.data.text.BaseComponent import de.bixilon.minosoft.data.text.ChatColors import de.bixilon.minosoft.data.text.TextComponent import de.bixilon.minosoft.data.world.Chunk +import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.layout.RowLayout import de.bixilon.minosoft.gui.rendering.gui.elements.layout.grid.GridGrow import de.bixilon.minosoft.gui.rendering.gui.elements.layout.grid.GridLayout @@ -34,6 +36,7 @@ import de.bixilon.minosoft.gui.rendering.gui.elements.spacer.LineSpacerElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.AutoTextElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement import de.bixilon.minosoft.gui.rendering.modding.events.ResizeWindowEvent @@ -53,10 +56,11 @@ import glm_.vec2.Vec2i import glm_.vec4.Vec4i import kotlin.math.abs -class DebugHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer) { +class DebugHUDElement(hudRenderer: HUDRenderer) : GridLayout(hudRenderer, Vec2i(3, 1)), LayoutedElement, Initializable { private val connection = renderWindow.connection override val layoutOffset: Vec2i = Vec2i.EMPTY - override val layout = GridLayout(hudRenderer, Vec2i(3, 1)).apply { + + init { columnConstraints[0].apply { grow = GridGrow.NEVER } @@ -70,12 +74,11 @@ class DebugHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement override fun init() { - enabled = false - layout[Vec2i(0, 0)] = initLeft() - layout[Vec2i(2, 0)] = initRight() + this[Vec2i(0, 0)] = initLeft() + this[Vec2i(2, 0)] = initRight() - layout.prefMaxSize = Vec2i(-1, Int.MAX_VALUE) - layout.ignoreDisplaySize = true + this.prefMaxSize = Vec2i(-1, Int.MAX_VALUE) + this.ignoreDisplaySize = true } private fun initLeft(): Element { @@ -237,10 +240,10 @@ class DebugHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement return layout } - private class DebugWorldInfo(hudRenderer: HUDRenderer) : RowLayout(hudRenderer) { + private class DebugWorldInfo(guiRenderer: AbstractGUIRenderer) : RowLayout(guiRenderer) { private var lastChunk: Chunk? = null - private val world = hudRenderer.connection.world - private val entity = hudRenderer.connection.player + private val world = guiRenderer.renderWindow.connection.world + private val entity = guiRenderer.renderWindow.connection.player init { showWait() @@ -283,7 +286,7 @@ class DebugHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement } } - companion object : HUDBuilder { + companion object : HUDBuilder> { override val RESOURCE_LOCATION: ResourceLocation = "minosoft:debug_hud".toResourceLocation() override val ENABLE_KEY_BINDING_NAME: ResourceLocation = "minosoft:enable_debug_hud".toResourceLocation() override val DEFAULT_ENABLED: Boolean = false @@ -293,8 +296,8 @@ class DebugHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement ), ) - override fun build(hudRenderer: HUDRenderer): DebugHUDElement { - return DebugHUDElement(hudRenderer) + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(DebugHUDElement(hudRenderer)).apply { enabled = false } } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/WorldInfoHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/WorldInfoHUDElement.kt index bf8ac1e3d..a1284913e 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/WorldInfoHUDElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/other/WorldInfoHUDElement.kt @@ -15,6 +15,7 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.other import de.bixilon.kutil.math.MMath.round10 import de.bixilon.minosoft.data.registries.ResourceLocation +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer @@ -23,11 +24,11 @@ import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i -class WorldInfoHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer), Pollable { - override val layout: TextElement = TextElement(hudRenderer, "") +class WorldInfoHUDElement(private val hudRenderer: HUDRenderer) : TextElement(hudRenderer, ""), LayoutedElement, Pollable { override val layoutOffset: Vec2i = Vec2i(2, 2) private var fps = -1.0 private var hide: Boolean = false + private val initialized = true override fun tick() { if (hide) { @@ -40,7 +41,10 @@ class WorldInfoHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement { + companion object : HUDBuilder> { override val RESOURCE_LOCATION: ResourceLocation = "minosoft:world_info".toResourceLocation() - override fun build(hudRenderer: HUDRenderer): WorldInfoHUDElement { - return WorldInfoHUDElement(hudRenderer) + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(WorldInfoHUDElement(hudRenderer)) } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/scoreboard/ScoreboardHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/scoreboard/ScoreboardHUDElement.kt deleted file mode 100644 index 5bc9e3f46..000000000 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/scoreboard/ScoreboardHUDElement.kt +++ /dev/null @@ -1,95 +0,0 @@ -/* - * Minosoft - * Copyright (C) 2020-2022 Moritz Zwerger - * - * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with this program. If not, see . - * - * This software is not affiliated with Mojang AB, the original developer of Minecraft. - */ - -package de.bixilon.minosoft.gui.rendering.gui.hud.elements.scoreboard - -import de.bixilon.minosoft.data.registries.ResourceLocation -import de.bixilon.minosoft.data.scoreboard.ScoreboardPositions -import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement -import de.bixilon.minosoft.gui.rendering.renderer.Drawable -import de.bixilon.minosoft.modding.event.events.scoreboard.* -import de.bixilon.minosoft.modding.event.events.scoreboard.team.TeamUpdateEvent -import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker -import de.bixilon.minosoft.util.KUtil.toResourceLocation -import glm_.vec2.Vec2i - -class ScoreboardHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer), Drawable { - private val connection = hudRenderer.connection - override val layout = ScoreboardSideElement(hudRenderer) - - override val layoutOffset: Vec2i - get() = Vec2i(guiRenderer.scaledSize.x - layout.size.x, (guiRenderer.scaledSize.y - layout.size.y) / 2) - - override val skipDraw: Boolean - get() = layout.objective == null - - override fun init() { - connection.registerEvent(CallbackEventInvoker.of { - if (it.position != ScoreboardPositions.SIDEBAR) { - return@of - } - - layout.objective = it.objective - }) - connection.registerEvent(CallbackEventInvoker.of { - if (it.objective != layout.objective) { - return@of - } - layout.updateName() - }) - connection.registerEvent(CallbackEventInvoker.of { - if (it.score.objective != layout.objective) { - return@of - } - layout.removeScore(it.score) - }) - connection.registerEvent(CallbackEventInvoker.of { - if (it.score.objective != layout.objective) { - return@of - } - layout.updateScore(it.score) - }) - connection.registerEvent(CallbackEventInvoker.of { - if (it.score.objective != layout.objective) { - return@of - } - layout.updateScore(it.score) - }) - connection.registerEvent(CallbackEventInvoker.of { - val objective = layout.objective ?: return@of - for ((_, score) in objective.scores) { - if (it.team != score.team) { - continue - } - layout.updateScore(score) - } - }) - } - - override fun draw() { - // check if content was changed, and we need to re-prepare before drawing - if (!layout.cacheUpToDate) { - layout.recalculateSize() - } - } - - companion object : HUDBuilder { - override val RESOURCE_LOCATION: ResourceLocation = "minosoft:scoreboard".toResourceLocation() - - override fun build(hudRenderer: HUDRenderer): ScoreboardHUDElement { - return ScoreboardHUDElement(hudRenderer) - } - } -} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/scoreboard/ScoreboardSideElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/scoreboard/ScoreboardSideElement.kt index c85bd3184..9958e6d55 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/scoreboard/ScoreboardSideElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/scoreboard/ScoreboardSideElement.kt @@ -15,27 +15,42 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.scoreboard import de.bixilon.kutil.collections.CollectionUtil.synchronizedMapOf import de.bixilon.kutil.collections.CollectionUtil.toSynchronizedMap +import de.bixilon.minosoft.data.registries.ResourceLocation import de.bixilon.minosoft.data.scoreboard.ScoreboardObjective +import de.bixilon.minosoft.data.scoreboard.ScoreboardPositions import de.bixilon.minosoft.data.scoreboard.ScoreboardScore import de.bixilon.minosoft.gui.rendering.RenderConstants import de.bixilon.minosoft.gui.rendering.font.Font import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments.Companion.getOffset +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ColorElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions +import de.bixilon.minosoft.gui.rendering.renderer.Drawable import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY +import de.bixilon.minosoft.modding.event.events.scoreboard.* +import de.bixilon.minosoft.modding.event.events.scoreboard.team.TeamUpdateEvent +import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker +import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i -class ScoreboardSideElement(hudRenderer: HUDRenderer) : Element(hudRenderer) { +class ScoreboardSideElement(hudRenderer: HUDRenderer) : Element(hudRenderer), LayoutedElement, Initializable, Drawable { private val backgroundElement = ColorElement(hudRenderer, size = Vec2i.EMPTY, color = RenderConstants.TEXT_BACKGROUND_COLOR) private val nameBackgroundElement = ColorElement(hudRenderer, size = Vec2i.EMPTY, color = RenderConstants.TEXT_BACKGROUND_COLOR) private val nameElement = TextElement(hudRenderer, "", background = false, parent = this) private val scores: MutableMap = synchronizedMapOf() + override val layoutOffset: Vec2i + get() = super.size.let { return@let Vec2i(guiRenderer.scaledSize.x - it.x, (guiRenderer.scaledSize.y - it.y) / 2) } + override val skipDraw: Boolean + get() = objective == null var objective: ScoreboardObjective? = null set(value) { @@ -138,10 +153,66 @@ class ScoreboardSideElement(hudRenderer: HUDRenderer) : Element(hudRenderer) { queueSizeRecalculation() } - companion object { + override fun init() { + val connection = renderWindow.connection + connection.registerEvent(CallbackEventInvoker.of { + if (it.position != ScoreboardPositions.SIDEBAR) { + return@of + } + + this.objective = it.objective + }) + connection.registerEvent(CallbackEventInvoker.of { + if (it.objective != this.objective) { + return@of + } + this.updateName() + }) + connection.registerEvent(CallbackEventInvoker.of { + if (it.score.objective != this.objective) { + return@of + } + this.removeScore(it.score) + }) + connection.registerEvent(CallbackEventInvoker.of { + if (it.score.objective != this.objective) { + return@of + } + this.updateScore(it.score) + }) + connection.registerEvent(CallbackEventInvoker.of { + if (it.score.objective != this.objective) { + return@of + } + this.updateScore(it.score) + }) + connection.registerEvent(CallbackEventInvoker.of { + val objective = this.objective ?: return@of + for ((_, score) in objective.scores) { + if (it.team != score.team) { + continue + } + this.updateScore(score) + } + }) + } + + override fun draw() { + // check if content was changed, and we need to re-prepare before drawing + if (!cacheUpToDate) { + recalculateSize() + } + } + + companion object : HUDBuilder> { + override val RESOURCE_LOCATION: ResourceLocation = "minosoft:scoreboard".toResourceLocation() const val MAX_SCORES = 15 const val MIN_WIDTH = 30 const val SCORE_HEIGHT = Font.TOTAL_CHAR_HEIGHT const val MAX_SCOREBOARD_WIDTH = 200 + + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(ScoreboardSideElement(hudRenderer)) + } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListElement.kt index c6be80854..54345894a 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListElement.kt @@ -16,22 +16,36 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.tab import de.bixilon.kutil.collections.CollectionUtil.synchronizedMapOf import de.bixilon.kutil.collections.CollectionUtil.toSynchronizedMap import de.bixilon.kutil.primitive.BooleanUtil.decide +import de.bixilon.minosoft.config.key.KeyAction +import de.bixilon.minosoft.config.key.KeyBinding +import de.bixilon.minosoft.config.key.KeyCodes +import de.bixilon.minosoft.data.registries.ResourceLocation import de.bixilon.minosoft.data.text.RGBColor import de.bixilon.minosoft.gui.rendering.gui.AbstractGUIRenderer import de.bixilon.minosoft.gui.rendering.gui.atlas.AtlasElement import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments.Companion.getOffset +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ColorElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextElement +import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions +import de.bixilon.minosoft.gui.rendering.renderer.Drawable import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY +import de.bixilon.minosoft.modding.event.events.TabListEntryChangeEvent +import de.bixilon.minosoft.modding.event.events.TabListInfoChangeEvent +import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker +import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i import java.util.* import java.util.concurrent.locks.ReentrantLock -class TabListElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer) { +class TabListElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer), LayoutedElement, Initializable, Drawable { val header = TextElement(guiRenderer, "", background = false, fontAlignment = HorizontalAlignments.CENTER, parent = this) val footer = TextElement(guiRenderer, "", background = false, fontAlignment = HorizontalAlignments.CENTER, parent = this) @@ -45,6 +59,9 @@ class TabListElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer) { private set private var columns = 0 + override val layoutOffset: Vec2i + get() = Vec2i((guiRenderer.scaledSize.x - super.size.x) / 2, 20) + private val atlasManager = guiRenderer.renderWindow.atlasManager val pingBarsAtlasElements: Array = arrayOf( atlasManager["minecraft:tab_list_ping_0"]!!, @@ -55,6 +72,10 @@ class TabListElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer) { atlasManager["minecraft:tab_list_ping_5"]!!, ) + init { + super.prefMaxSize = Vec2i(-1, -1) + } + override fun forceRender(offset: Vec2i, z: Int, consumer: GUIVertexConsumer, options: GUIVertexOptions?): Int { background.render(offset, z, consumer, options) @@ -201,11 +222,49 @@ class TabListElement(guiRenderer: AbstractGUIRenderer) : Element(guiRenderer) { } - companion object { + override fun init() { + val connection = renderWindow.connection + connection.registerEvent(CallbackEventInvoker.of { + header.text = it.header + footer.text = it.footer + }) + connection.registerEvent(CallbackEventInvoker.of { + for ((uuid, entry) in it.items) { + if (entry == null) { + remove(uuid) + continue + } + update(uuid) + } + }) + + // ToDo: Also check team changes, scoreboard changes, etc + } + + + override fun draw() { + // check if content was changed, and we need to re-prepare before drawing + if (needsApply) { + forceApply() + } + } + + companion object : HUDBuilder> { private const val ENTRIES_PER_COLUMN = 20 private const val ENTRY_HORIZONTAL_SPACING = 5 private const val ENTRY_VERTICAL_SPACING = 1 private const val BACKGROUND_PADDING = 3 private const val MAX_ENTRIES = 80 + override val RESOURCE_LOCATION: ResourceLocation = "minosoft:tab_list".toResourceLocation() + override val ENABLE_KEY_BINDING_NAME: ResourceLocation = "minosoft:enable_tab_list".toResourceLocation() + override val ENABLE_KEY_BINDING: KeyBinding = KeyBinding( + mapOf( + KeyAction.CHANGE to setOf(KeyCodes.KEY_TAB), + ), + ) + + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(TabListElement(hudRenderer)).apply { enabled = false } + } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListEntryElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListEntryElement.kt index 0194036aa..cddb57361 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListEntryElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListEntryElement.kt @@ -22,8 +22,8 @@ import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments.Companion.getOffset import de.bixilon.minosoft.gui.rendering.gui.elements.Pollable +import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.AtlasImageElement import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ColorElement -import de.bixilon.minosoft.gui.rendering.gui.elements.primitive.ImageElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions @@ -46,7 +46,7 @@ class TabListEntryElement( private val background: ColorElement private val nameElement = TextElement(guiRenderer, "", background = false, parent = this) - private lateinit var pingElement: ImageElement + private lateinit var pingElement: AtlasImageElement private var displayName: ChatComponent = item.displayName private var ping = item.ping @@ -86,7 +86,7 @@ class TabListEntryElement( override fun forceSilentApply() { // ToDo (Performance): If something changed, should we just prepare the changed - pingElement = ImageElement(guiRenderer, tabList.pingBarsAtlasElements[when { + pingElement = AtlasImageElement(guiRenderer, tabList.pingBarsAtlasElements[when { ping < 0 -> 0 ping < 150 -> 5 ping < 300 -> 4 diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListHUDElement.kt deleted file mode 100644 index 78a74aef1..000000000 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/tab/TabListHUDElement.kt +++ /dev/null @@ -1,82 +0,0 @@ -/* - * Minosoft - * Copyright (C) 2020-2022 Moritz Zwerger - * - * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with this program. If not, see . - * - * This software is not affiliated with Mojang AB, the original developer of Minecraft. - */ - -package de.bixilon.minosoft.gui.rendering.gui.hud.elements.tab - -import de.bixilon.minosoft.config.key.KeyAction -import de.bixilon.minosoft.config.key.KeyBinding -import de.bixilon.minosoft.config.key.KeyCodes -import de.bixilon.minosoft.data.registries.ResourceLocation -import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement -import de.bixilon.minosoft.gui.rendering.renderer.Drawable -import de.bixilon.minosoft.modding.event.events.TabListEntryChangeEvent -import de.bixilon.minosoft.modding.event.events.TabListInfoChangeEvent -import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker -import de.bixilon.minosoft.util.KUtil.toResourceLocation -import glm_.vec2.Vec2i - -class TabListHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer), Drawable { - private val connection = renderWindow.connection - override val layout = TabListElement(hudRenderer) - - override val layoutOffset: Vec2i - get() = Vec2i((guiRenderer.scaledSize.x - layout.size.x) / 2, 20) - - init { - enabled = false - layout.prefMaxSize = Vec2i(-1, -1) - } - - - override fun init() { - connection.registerEvent(CallbackEventInvoker.of { - layout.header.text = it.header - layout.footer.text = it.footer - }) - connection.registerEvent(CallbackEventInvoker.of { - for ((uuid, entry) in it.items) { - if (entry == null) { - layout.remove(uuid) - continue - } - layout.update(uuid) - } - }) - - // ToDo: Also check team changes, scoreboard changes, etc - } - - override fun draw() { - // check if content was changed, and we need to re-prepare before drawing - if (layout.needsApply) { - layout.forceApply() - } - } - - - companion object : HUDBuilder { - override val RESOURCE_LOCATION: ResourceLocation = "minosoft:tab_list".toResourceLocation() - override val ENABLE_KEY_BINDING_NAME: ResourceLocation = "minosoft:enable_tab_list".toResourceLocation() - override val ENABLE_KEY_BINDING: KeyBinding = KeyBinding( - mapOf( - KeyAction.CHANGE to setOf(KeyCodes.KEY_TAB), - ), - ) - - override fun build(hudRenderer: HUDRenderer): TabListHUDElement { - return TabListHUDElement(hudRenderer) - } - } -} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/title/TitleElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/title/TitleElement.kt index 549586f3c..2baacc225 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/title/TitleElement.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/title/TitleElement.kt @@ -1,6 +1,6 @@ /* * Minosoft - * Copyright (C) 2021 Moritz Zwerger + * Copyright (C) 2020-2022 Moritz Zwerger * * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. * @@ -13,20 +13,29 @@ package de.bixilon.minosoft.gui.rendering.gui.hud.elements.title +import de.bixilon.minosoft.data.registries.ResourceLocation import de.bixilon.minosoft.gui.rendering.gui.elements.Element import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments import de.bixilon.minosoft.gui.rendering.gui.elements.HorizontalAlignments.Companion.getOffset +import de.bixilon.minosoft.gui.rendering.gui.elements.LayoutedElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.FadingTextElement import de.bixilon.minosoft.gui.rendering.gui.elements.text.TextElement import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer +import de.bixilon.minosoft.gui.rendering.gui.hud.Initializable +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder +import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexConsumer import de.bixilon.minosoft.gui.rendering.gui.mesh.GUIVertexOptions +import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY +import de.bixilon.minosoft.modding.event.events.title.* +import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker import de.bixilon.minosoft.protocol.protocol.ProtocolDefinition +import de.bixilon.minosoft.util.KUtil.toResourceLocation import glm_.vec2.Vec2i import java.lang.Integer.max // ToDo: Remove subtitle when hidden -class TitleElement(hudRenderer: HUDRenderer) : Element(hudRenderer) { +class TitleElement(hudRenderer: HUDRenderer) : Element(hudRenderer), LayoutedElement, Initializable { val title = FadingTextElement(hudRenderer, "", background = false, scale = 4.0f, parent = this) val subtitle = FadingTextElement(hudRenderer, "", background = false, scale = 2.0f, parent = this) var fadeInTime = 0L @@ -58,6 +67,18 @@ class TitleElement(hudRenderer: HUDRenderer) : Element(hudRenderer) { super.cacheEnabled = value } + override val layoutOffset: Vec2i + get() { + val layoutOffset = Vec2i.EMPTY + + val scaledSize = guiRenderer.scaledSize + + layoutOffset.x = (scaledSize.x - super.size.x / 2) / 2 + layoutOffset.y = (scaledSize.y / 2 - title.size.y) + + return layoutOffset + } + init { fadeInTime = DEFAULT_FADE_IN_TIME stayTime = DEFAULT_STAY_TIME @@ -103,10 +124,39 @@ class TitleElement(hudRenderer: HUDRenderer) : Element(hudRenderer) { fadeOutTime = DEFAULT_FADE_OUT_TIME } - companion object { + override fun init() { + val connection = renderWindow.connection + + connection.registerEvent(CallbackEventInvoker.of { + this.reset() + }) + connection.registerEvent(CallbackEventInvoker.of { + this.hide() + }) + connection.registerEvent(CallbackEventInvoker.of { + this.title.text = it.title + this.show() + }) + connection.registerEvent(CallbackEventInvoker.of { + this.subtitle.text = it.subtitle + // layout.show() // non vanilla behavior + }) + connection.registerEvent(CallbackEventInvoker.of { + this.fadeInTime = it.fadeInTime * ProtocolDefinition.TICK_TIME.toLong() + this.stayTime = it.stayTime * ProtocolDefinition.TICK_TIME.toLong() + this.fadeOutTime = it.fadeOutTime * ProtocolDefinition.TICK_TIME.toLong() + }) + } + + companion object : HUDBuilder> { + override val RESOURCE_LOCATION: ResourceLocation = "minosoft:title".toResourceLocation() const val SUBTITLE_VERTICAL_OFFSET = 10 const val DEFAULT_FADE_IN_TIME = 20L * ProtocolDefinition.TICK_TIME const val DEFAULT_STAY_TIME = 60L * ProtocolDefinition.TICK_TIME const val DEFAULT_FADE_OUT_TIME = 20L * ProtocolDefinition.TICK_TIME + + override fun build(hudRenderer: HUDRenderer): LayoutedHUDElement { + return LayoutedHUDElement(TitleElement(hudRenderer)) + } } } diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/title/TitleHUDElement.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/title/TitleHUDElement.kt deleted file mode 100644 index 31eac2b08..000000000 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/gui/hud/elements/title/TitleHUDElement.kt +++ /dev/null @@ -1,74 +0,0 @@ -/* - * Minosoft - * Copyright (C) 2020-2022 Moritz Zwerger - * - * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along with this program. If not, see . - * - * This software is not affiliated with Mojang AB, the original developer of Minecraft. - */ - -package de.bixilon.minosoft.gui.rendering.gui.hud.elements.title - -import de.bixilon.minosoft.data.registries.ResourceLocation -import de.bixilon.minosoft.gui.rendering.gui.hud.HUDRenderer -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.HUDBuilder -import de.bixilon.minosoft.gui.rendering.gui.hud.elements.LayoutedHUDElement -import de.bixilon.minosoft.gui.rendering.util.vec.vec2.Vec2iUtil.EMPTY -import de.bixilon.minosoft.modding.event.events.title.* -import de.bixilon.minosoft.modding.event.invoker.CallbackEventInvoker -import de.bixilon.minosoft.protocol.protocol.ProtocolDefinition -import de.bixilon.minosoft.util.KUtil.toResourceLocation -import glm_.vec2.Vec2i - -class TitleHUDElement(hudRenderer: HUDRenderer) : LayoutedHUDElement(hudRenderer) { - override val layout: TitleElement = TitleElement(hudRenderer) - override val layoutOffset: Vec2i - get() { - val layoutOffset = Vec2i.EMPTY - - val scaledSize = guiRenderer.scaledSize - - layoutOffset.x = (scaledSize.x - layout.size.x / 2) / 2 - layoutOffset.y = (scaledSize.y / 2 - layout.title.size.y) - - return layoutOffset - } - - override fun init() { - val connection = guiRenderer.connection - - connection.registerEvent(CallbackEventInvoker.of { - layout.reset() - }) - connection.registerEvent(CallbackEventInvoker.of { - layout.hide() - }) - connection.registerEvent(CallbackEventInvoker.of { - layout.title.text = it.title - layout.show() - }) - connection.registerEvent(CallbackEventInvoker.of { - layout.subtitle.text = it.subtitle - // layout.show() // non vanilla behavior - }) - connection.registerEvent(CallbackEventInvoker.of { - layout.fadeInTime = it.fadeInTime * ProtocolDefinition.TICK_TIME.toLong() - layout.stayTime = it.stayTime * ProtocolDefinition.TICK_TIME.toLong() - layout.fadeOutTime = it.fadeOutTime * ProtocolDefinition.TICK_TIME.toLong() - }) - } - - - companion object : HUDBuilder { - override val RESOURCE_LOCATION: ResourceLocation = "minosoft:title".toResourceLocation() - - override fun build(hudRenderer: HUDRenderer): TitleHUDElement { - return TitleHUDElement(hudRenderer) - } - } - -} diff --git a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/Drawable.kt b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/Drawable.kt index 13cd2b01f..a350e73a3 100644 --- a/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/Drawable.kt +++ b/src/main/java/de/bixilon/minosoft/gui/rendering/renderer/Drawable.kt @@ -1,6 +1,6 @@ /* * Minosoft - * Copyright (C) 2021 Moritz Zwerger + * Copyright (C) 2020-2022 Moritz Zwerger * * This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. * @@ -20,5 +20,5 @@ interface Drawable { /** * Functions gets called every frame */ - fun draw() + fun draw() {} }