mirror of
https://gitlab.bixilon.de/bixilon/minosoft.git
synced 2025-09-12 00:47:26 -04:00
team invisibility name
This commit is contained in:
parent
1567b14583
commit
fddea73f3a
@ -14,7 +14,9 @@
|
|||||||
package de.bixilon.minosoft.data.entities.entities.player.additional
|
package de.bixilon.minosoft.data.entities.entities.player.additional
|
||||||
|
|
||||||
import de.bixilon.minosoft.data.scoreboard.team.Team
|
import de.bixilon.minosoft.data.scoreboard.team.Team
|
||||||
|
import de.bixilon.minosoft.data.scoreboard.team.TeamFormatting
|
||||||
import de.bixilon.minosoft.data.text.BaseComponent
|
import de.bixilon.minosoft.data.text.BaseComponent
|
||||||
|
import de.bixilon.minosoft.data.text.ChatComponent
|
||||||
import de.bixilon.minosoft.data.text.TextComponent
|
import de.bixilon.minosoft.data.text.TextComponent
|
||||||
import de.bixilon.minosoft.data.text.formatting.color.ChatColors
|
import de.bixilon.minosoft.data.text.formatting.color.ChatColors
|
||||||
import org.testng.Assert.assertEquals
|
import org.testng.Assert.assertEquals
|
||||||
@ -38,25 +40,25 @@ class PlayerAdditionalTest {
|
|||||||
|
|
||||||
fun `team prefix`() {
|
fun `team prefix`() {
|
||||||
val additional = PlayerAdditional("Me")
|
val additional = PlayerAdditional("Me")
|
||||||
additional.team = Team("test", prefix = TextComponent("[P]").color(ChatColors.RED))
|
additional.team = Team("test", TeamFormatting(ChatComponent.EMPTY, prefix = TextComponent("[P]").color(ChatColors.RED)))
|
||||||
assertEquals(additional.tabDisplayName, BaseComponent(TextComponent("[P]").color(ChatColors.RED), TextComponent("Me")))
|
assertEquals(additional.tabDisplayName, BaseComponent(TextComponent("[P]").color(ChatColors.RED), TextComponent("Me")))
|
||||||
}
|
}
|
||||||
|
|
||||||
fun `team suffix`() {
|
fun `team suffix`() {
|
||||||
val additional = PlayerAdditional("Me")
|
val additional = PlayerAdditional("Me")
|
||||||
additional.team = Team("test", suffix = TextComponent("[S]").color(ChatColors.BLUE))
|
additional.team = Team("test", TeamFormatting(ChatComponent.EMPTY, suffix = TextComponent("[S]").color(ChatColors.BLUE)))
|
||||||
assertEquals(additional.tabDisplayName, BaseComponent(TextComponent("Me"), TextComponent("[S]").color(ChatColors.BLUE)))
|
assertEquals(additional.tabDisplayName, BaseComponent(TextComponent("Me"), TextComponent("[S]").color(ChatColors.BLUE)))
|
||||||
}
|
}
|
||||||
|
|
||||||
fun `team prefix and suffix`() {
|
fun `team prefix and suffix`() {
|
||||||
val additional = PlayerAdditional("Me")
|
val additional = PlayerAdditional("Me")
|
||||||
additional.team = Team("test", prefix = TextComponent("[P]").color(ChatColors.RED), suffix = TextComponent("[S]").color(ChatColors.BLUE))
|
additional.team = Team("test", TeamFormatting(ChatComponent.EMPTY, prefix = TextComponent("[P]").color(ChatColors.RED), suffix = TextComponent("[S]").color(ChatColors.BLUE)))
|
||||||
assertEquals(additional.tabDisplayName, BaseComponent(TextComponent("[P]").color(ChatColors.RED), TextComponent("Me"), TextComponent("[S]").color(ChatColors.BLUE)))
|
assertEquals(additional.tabDisplayName, BaseComponent(TextComponent("[P]").color(ChatColors.RED), TextComponent("Me"), TextComponent("[S]").color(ChatColors.BLUE)))
|
||||||
}
|
}
|
||||||
|
|
||||||
fun `team prefix and suffix and color`() {
|
fun `team prefix and suffix and color`() {
|
||||||
val additional = PlayerAdditional("Me")
|
val additional = PlayerAdditional("Me")
|
||||||
additional.team = Team("test", color = ChatColors.LIGHT_PURPLE, prefix = TextComponent("[P]").color(ChatColors.RED), suffix = TextComponent("[S]").color(ChatColors.BLUE))
|
additional.team = Team("test", TeamFormatting(ChatComponent.EMPTY, color = ChatColors.LIGHT_PURPLE, prefix = TextComponent("[P]").color(ChatColors.RED), suffix = TextComponent("[S]").color(ChatColors.BLUE)))
|
||||||
assertEquals(additional.tabDisplayName, BaseComponent(TextComponent("[P]").color(ChatColors.RED), TextComponent("Me").color(ChatColors.LIGHT_PURPLE), TextComponent("[S]").color(ChatColors.BLUE)))
|
assertEquals(additional.tabDisplayName, BaseComponent(TextComponent("[P]").color(ChatColors.RED), TextComponent("Me").color(ChatColors.LIGHT_PURPLE), TextComponent("[S]").color(ChatColors.BLUE)))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -13,9 +13,10 @@
|
|||||||
|
|
||||||
package de.bixilon.minosoft.data.registries.versions.registries.pixlyzer
|
package de.bixilon.minosoft.data.registries.versions.registries.pixlyzer
|
||||||
|
|
||||||
import de.bixilon.minosoft.protocol.protocol.VersionSupport
|
import de.bixilon.minosoft.protocol.versions.Version
|
||||||
import de.bixilon.minosoft.protocol.versions.VersionTypes
|
import de.bixilon.minosoft.protocol.versions.VersionTypes
|
||||||
import de.bixilon.minosoft.protocol.versions.Versions
|
import de.bixilon.minosoft.protocol.versions.Versions
|
||||||
|
import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap
|
||||||
import org.testng.SkipException
|
import org.testng.SkipException
|
||||||
import org.testng.annotations.Test
|
import org.testng.annotations.Test
|
||||||
|
|
||||||
@ -24,7 +25,13 @@ class Latest : PixLyzerLoadingTest("tba") {
|
|||||||
|
|
||||||
@Test(priority = -20)
|
@Test(priority = -20)
|
||||||
override fun loadVersion() {
|
override fun loadVersion() {
|
||||||
val version = Versions.getById(VersionSupport.LATEST_VERSION)!!
|
val id = Versions::class.java.getDeclaredField("id").apply { isAccessible = true }.get(Versions) as Int2ObjectOpenHashMap<Version>
|
||||||
|
var highest = 0
|
||||||
|
for ((id, _) in id) {
|
||||||
|
if (id < highest) continue
|
||||||
|
highest = id
|
||||||
|
}
|
||||||
|
val version = Versions.getById(highest)!!
|
||||||
if (version.type == VersionTypes.RELEASE) {
|
if (version.type == VersionTypes.RELEASE) {
|
||||||
throw SkipException("Version should already be tested!")
|
throw SkipException("Version should already be tested!")
|
||||||
}
|
}
|
||||||
|
@ -30,6 +30,7 @@ import de.bixilon.minosoft.data.entities.entities.player.local.SignatureKeyManag
|
|||||||
import de.bixilon.minosoft.data.entities.entities.player.tab.TabList
|
import de.bixilon.minosoft.data.entities.entities.player.tab.TabList
|
||||||
import de.bixilon.minosoft.data.registries.entities.EntityFactory
|
import de.bixilon.minosoft.data.registries.entities.EntityFactory
|
||||||
import de.bixilon.minosoft.data.registries.entities.EntityType
|
import de.bixilon.minosoft.data.registries.entities.EntityType
|
||||||
|
import de.bixilon.minosoft.data.registries.identified.Namespaces.minosoft
|
||||||
import de.bixilon.minosoft.data.scoreboard.ScoreboardManager
|
import de.bixilon.minosoft.data.scoreboard.ScoreboardManager
|
||||||
import de.bixilon.minosoft.gui.rendering.RenderContext
|
import de.bixilon.minosoft.gui.rendering.RenderContext
|
||||||
import de.bixilon.minosoft.gui.rendering.camera.Camera
|
import de.bixilon.minosoft.gui.rendering.camera.Camera
|
||||||
@ -45,7 +46,7 @@ import de.bixilon.minosoft.test.IT
|
|||||||
import java.util.*
|
import java.util.*
|
||||||
|
|
||||||
object EntityRendererTestUtil {
|
object EntityRendererTestUtil {
|
||||||
val PIG = EntityType(Pig.identifier, null, 1.0f, 1.0f, mapOf(), Pig, null)
|
val PIG = EntityType(Pig.identifier, minosoft("key"), 1.0f, 1.0f, mapOf(), Pig, null)
|
||||||
|
|
||||||
fun createContext(): RenderContext {
|
fun createContext(): RenderContext {
|
||||||
val connection = ConnectionTestUtil.createConnection()
|
val connection = ConnectionTestUtil.createConnection()
|
||||||
|
@ -23,9 +23,14 @@ import de.bixilon.minosoft.data.entities.entities.Entity
|
|||||||
import de.bixilon.minosoft.data.entities.entities.animal.Pig
|
import de.bixilon.minosoft.data.entities.entities.animal.Pig
|
||||||
import de.bixilon.minosoft.data.entities.entities.decoration.armorstand.ArmorStand
|
import de.bixilon.minosoft.data.entities.entities.decoration.armorstand.ArmorStand
|
||||||
import de.bixilon.minosoft.data.entities.entities.monster.Zombie
|
import de.bixilon.minosoft.data.entities.entities.monster.Zombie
|
||||||
|
import de.bixilon.minosoft.data.entities.entities.player.PlayerEntity
|
||||||
import de.bixilon.minosoft.data.entities.entities.player.RemotePlayerEntity
|
import de.bixilon.minosoft.data.entities.entities.player.RemotePlayerEntity
|
||||||
import de.bixilon.minosoft.data.entities.entities.vehicle.boat.Boat
|
import de.bixilon.minosoft.data.entities.entities.vehicle.boat.Boat
|
||||||
|
import de.bixilon.minosoft.data.language.lang.Language
|
||||||
import de.bixilon.minosoft.data.registries.entities.EntityFactory
|
import de.bixilon.minosoft.data.registries.entities.EntityFactory
|
||||||
|
import de.bixilon.minosoft.data.scoreboard.NameTagVisibilities
|
||||||
|
import de.bixilon.minosoft.data.scoreboard.team.Team
|
||||||
|
import de.bixilon.minosoft.data.scoreboard.team.TeamVisibility
|
||||||
import de.bixilon.minosoft.data.text.ChatComponent
|
import de.bixilon.minosoft.data.text.ChatComponent
|
||||||
import de.bixilon.minosoft.data.text.TextComponent
|
import de.bixilon.minosoft.data.text.TextComponent
|
||||||
import de.bixilon.minosoft.gui.rendering.entities.EntityRendererTestUtil.create
|
import de.bixilon.minosoft.gui.rendering.entities.EntityRendererTestUtil.create
|
||||||
@ -53,7 +58,6 @@ class EntityNameFeatureTest {
|
|||||||
private fun EntityNameFeature.isNameVisible(visible: Boolean) {
|
private fun EntityNameFeature.isNameVisible(visible: Boolean) {
|
||||||
renderer.entity.data[Entity.CUSTOM_NAME_VISIBLE_DATA] = visible
|
renderer.entity.data[Entity.CUSTOM_NAME_VISIBLE_DATA] = visible
|
||||||
}
|
}
|
||||||
// TODO: hasCustomName?
|
|
||||||
|
|
||||||
private fun EntityNameFeature.isInvisible(invisible: Boolean) {
|
private fun EntityNameFeature.isInvisible(invisible: Boolean) {
|
||||||
var flags = renderer.entity.data.get(Entity.FLAGS_DATA, 0x00)
|
var flags = renderer.entity.data.get(Entity.FLAGS_DATA, 0x00)
|
||||||
@ -64,6 +68,16 @@ class EntityNameFeatureTest {
|
|||||||
renderer.entity.data[Entity.FLAGS_DATA] = flags
|
renderer.entity.data[Entity.FLAGS_DATA] = flags
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun EntityNameFeature.cameraTeam(same: Boolean) {
|
||||||
|
val team = if (same) renderer.entity.unsafeCast<PlayerEntity>().additional.team ?: throw IllegalArgumentException("Not in a team") else Team("other")
|
||||||
|
renderer.renderer.connection.camera.entity.unsafeCast<PlayerEntity>().additional.team = team
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun EntityNameFeature.team(invisibles: Boolean = true, name: NameTagVisibilities = NameTagVisibilities.ALWAYS) {
|
||||||
|
val team = Team("own", visibility = TeamVisibility(invisibleTeam = invisibles, name = name))
|
||||||
|
renderer.entity.unsafeCast<PlayerEntity>().additional.team = team
|
||||||
|
}
|
||||||
|
|
||||||
private fun EntityNameFeature.setTargeted(target: Boolean = true, distance: Double = 1.0) {
|
private fun EntityNameFeature.setTargeted(target: Boolean = true, distance: Double = 1.0) {
|
||||||
val target = if (target) EntityTarget(Vec3d(0, 0, 0), distance, Directions.DOWN, renderer.entity) else null
|
val target = if (target) EntityTarget(Vec3d(0, 0, 0), distance, Directions.DOWN, renderer.entity) else null
|
||||||
renderer.renderer.connection.camera.target::target.forceSet(DataObserver(target))
|
renderer.renderer.connection.camera.target::target.forceSet(DataObserver(target))
|
||||||
@ -165,6 +179,14 @@ class EntityNameFeatureTest {
|
|||||||
name.assertEmpty()
|
name.assertEmpty()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun `targeted armor stand with custom name set`() {
|
||||||
|
val name = create(ArmorStand)
|
||||||
|
name.customName("Jonny")
|
||||||
|
name.setTargeted(true)
|
||||||
|
name.updateName()
|
||||||
|
name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
fun `armor stand with custom visible name set`() {
|
fun `armor stand with custom visible name set`() {
|
||||||
val name = create(ArmorStand)
|
val name = create(ArmorStand)
|
||||||
@ -199,6 +221,14 @@ class EntityNameFeatureTest {
|
|||||||
fun `boat targeted and custom name set`() {
|
fun `boat targeted and custom name set`() {
|
||||||
val name = create(Boat)
|
val name = create(Boat)
|
||||||
name.customName("Titanic")
|
name.customName("Titanic")
|
||||||
|
name.setTargeted(true) // TODO: a boat is somehow not targetable?
|
||||||
|
name.updateName()
|
||||||
|
// name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `boat targeted and just custom name visible`() {
|
||||||
|
val name = create(Boat)
|
||||||
|
name.isNameVisible(true)
|
||||||
name.setTargeted(true)
|
name.setTargeted(true)
|
||||||
name.updateName()
|
name.updateName()
|
||||||
name.assertEmpty()
|
name.assertEmpty()
|
||||||
@ -222,8 +252,9 @@ class EntityNameFeatureTest {
|
|||||||
fun `zombie with visible name`() {
|
fun `zombie with visible name`() {
|
||||||
val name = create(Zombie)
|
val name = create(Zombie)
|
||||||
name.isNameVisible(true)
|
name.isNameVisible(true)
|
||||||
|
name.renderer.renderer.connection.language = Language("abc", mutableMapOf("key" to "Zombie"))
|
||||||
name.updateName()
|
name.updateName()
|
||||||
name.assertText() // TODO: Zombie
|
name.assertText()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun `zombie with visible custom name`() {
|
fun `zombie with visible custom name`() {
|
||||||
@ -234,11 +265,18 @@ class EntityNameFeatureTest {
|
|||||||
name.assertText()
|
name.assertText()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun `zombie with invisibility potion and custom name`() {
|
fun `zombie with invisibility and custom name`() {
|
||||||
val name = create(Zombie)
|
val name = create(Zombie)
|
||||||
name.customName("Notch")
|
name.customName("Notch")
|
||||||
name.isNameVisible(true)
|
name.isNameVisible(true)
|
||||||
// TODO: invis potion
|
name.isInvisible(true)
|
||||||
|
name.updateName()
|
||||||
|
name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `player with invisibility`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.isInvisible(true)
|
||||||
name.updateName()
|
name.updateName()
|
||||||
name.assertEmpty()
|
name.assertEmpty()
|
||||||
}
|
}
|
||||||
@ -252,9 +290,117 @@ class EntityNameFeatureTest {
|
|||||||
name.assertEmpty()
|
name.assertEmpty()
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: targeted mob, invisible zombie
|
fun `camera not in team and always visible`() {
|
||||||
// TODO: mob, armor stand, player (local/remote), pig, non living (boat?)
|
val name = create(RemotePlayerEntity)
|
||||||
// TODO: isInvisible, teams (with team nametag visibility),
|
name.team(name = NameTagVisibilities.ALWAYS)
|
||||||
|
name.updateName()
|
||||||
|
name.assertText()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `camera not in team and hide for other team`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.HIDE_FOR_ENEMIES)
|
||||||
|
name.updateName()
|
||||||
|
name.assertText()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `camera not in team and hide for own team`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.HIDE_FOR_MATES)
|
||||||
|
name.updateName()
|
||||||
|
name.assertText()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `camera not in team and never`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.NEVER)
|
||||||
|
name.updateName()
|
||||||
|
name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `camera different team and always visible`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.ALWAYS)
|
||||||
|
name.cameraTeam(false)
|
||||||
|
name.updateName()
|
||||||
|
name.assertText()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `camera different team and hide for other team`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.HIDE_FOR_ENEMIES)
|
||||||
|
name.cameraTeam(false)
|
||||||
|
name.updateName()
|
||||||
|
name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `camera different team and hide for own team`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.HIDE_FOR_MATES)
|
||||||
|
name.cameraTeam(false)
|
||||||
|
name.updateName()
|
||||||
|
name.assertText()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `camera different team and never visible`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.NEVER)
|
||||||
|
name.cameraTeam(false)
|
||||||
|
name.updateName()
|
||||||
|
name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `same team and always visible`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.ALWAYS)
|
||||||
|
name.cameraTeam(true)
|
||||||
|
name.updateName()
|
||||||
|
name.assertText()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `same team and hide for other teams`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.HIDE_FOR_ENEMIES)
|
||||||
|
name.cameraTeam(true)
|
||||||
|
name.updateName()
|
||||||
|
name.assertText()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `same team and hide for own team`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.HIDE_FOR_MATES)
|
||||||
|
name.cameraTeam(true)
|
||||||
|
name.updateName()
|
||||||
|
name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `same team and hide for never visible`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(name = NameTagVisibilities.NEVER)
|
||||||
|
name.cameraTeam(true)
|
||||||
|
name.updateName()
|
||||||
|
name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `same team and invisible`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(invisibles = true)
|
||||||
|
name.cameraTeam(true)
|
||||||
|
name.isInvisible(true)
|
||||||
|
name.updateName()
|
||||||
|
name.assertText()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun `same team and invisible but invisible to mates`() {
|
||||||
|
val name = create(RemotePlayerEntity)
|
||||||
|
name.team(invisibles = false)
|
||||||
|
name.cameraTeam(true)
|
||||||
|
name.isInvisible(true)
|
||||||
|
name.updateName()
|
||||||
|
name.assertEmpty()
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: item frame
|
||||||
// TODO: profile
|
// TODO: profile
|
||||||
// TODO: render distance, sneaking
|
// TODO: render distance, sneaking
|
||||||
}
|
}
|
||||||
|
@ -38,6 +38,7 @@ class EntityScoreFeatureTest {
|
|||||||
private fun createScore(): EntityScoreFeature {
|
private fun createScore(): EntityScoreFeature {
|
||||||
val renderer = create().create(RemotePlayerEntity).unsafeCast<PlayerRenderer<*>>()
|
val renderer = create().create(RemotePlayerEntity).unsafeCast<PlayerRenderer<*>>()
|
||||||
renderer::score.forceSet(null) // remove
|
renderer::score.forceSet(null) // remove
|
||||||
|
renderer.name.text = TextComponent("not empty")
|
||||||
|
|
||||||
return EntityScoreFeature(renderer)
|
return EntityScoreFeature(renderer)
|
||||||
}
|
}
|
||||||
@ -83,7 +84,7 @@ class EntityScoreFeatureTest {
|
|||||||
score.setScore()
|
score.setScore()
|
||||||
score.updateScore()
|
score.updateScore()
|
||||||
score.updateNameOffset()
|
score.updateNameOffset()
|
||||||
assertEquals(score.renderer.name.offset, BillboardTextFeature.DEFAULT_OFFSET + 0.24f)
|
assertEquals(score.renderer.name.offset, BillboardTextFeature.DEFAULT_OFFSET + 0.22f)
|
||||||
}
|
}
|
||||||
|
|
||||||
fun `profile disabled`() {
|
fun `profile disabled`() {
|
||||||
@ -100,6 +101,4 @@ class EntityScoreFeatureTest {
|
|||||||
score.updateScore()
|
score.updateScore()
|
||||||
assertEquals(score.text, BaseComponent("1", " ", TextComponent("Score").color(ChatColors.LIGHT_PURPLE)))
|
assertEquals(score.text, BaseComponent("1", " ", TextComponent("Score").color(ChatColors.LIGHT_PURPLE)))
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: teams, invisibility
|
|
||||||
}
|
}
|
||||||
|
@ -19,12 +19,14 @@ import de.bixilon.kutil.cast.CastUtil.unsafeCast
|
|||||||
import de.bixilon.kutil.cast.CastUtil.unsafeNull
|
import de.bixilon.kutil.cast.CastUtil.unsafeNull
|
||||||
import de.bixilon.kutil.reflection.ReflectionUtil.forceSet
|
import de.bixilon.kutil.reflection.ReflectionUtil.forceSet
|
||||||
import de.bixilon.kutil.time.TimeUtil.millis
|
import de.bixilon.kutil.time.TimeUtil.millis
|
||||||
|
import de.bixilon.minosoft.data.abilities.Gamemodes
|
||||||
import de.bixilon.minosoft.data.entities.EntityAnimations
|
import de.bixilon.minosoft.data.entities.EntityAnimations
|
||||||
import de.bixilon.minosoft.data.entities.EntityRenderInfo
|
import de.bixilon.minosoft.data.entities.EntityRenderInfo
|
||||||
import de.bixilon.minosoft.data.entities.EntityRotation
|
import de.bixilon.minosoft.data.entities.EntityRotation
|
||||||
import de.bixilon.minosoft.data.entities.Poses
|
import de.bixilon.minosoft.data.entities.Poses
|
||||||
import de.bixilon.minosoft.data.entities.data.EntityData
|
import de.bixilon.minosoft.data.entities.data.EntityData
|
||||||
import de.bixilon.minosoft.data.entities.data.EntityDataField
|
import de.bixilon.minosoft.data.entities.data.EntityDataField
|
||||||
|
import de.bixilon.minosoft.data.entities.entities.player.PlayerEntity
|
||||||
import de.bixilon.minosoft.data.entities.entities.player.local.LocalPlayerEntity
|
import de.bixilon.minosoft.data.entities.entities.player.local.LocalPlayerEntity
|
||||||
import de.bixilon.minosoft.data.entities.entities.properties.EntityAttachment
|
import de.bixilon.minosoft.data.entities.entities.properties.EntityAttachment
|
||||||
import de.bixilon.minosoft.data.registries.entities.EntityType
|
import de.bixilon.minosoft.data.registries.entities.EntityType
|
||||||
@ -87,7 +89,7 @@ abstract class Entity(
|
|||||||
|
|
||||||
open val physics: EntityPhysics<*> = unsafeNull()
|
open val physics: EntityPhysics<*> = unsafeNull()
|
||||||
|
|
||||||
open val canRaycast: Boolean get() = false
|
open val canRaycast: Boolean get() = !isInvisible
|
||||||
|
|
||||||
var age = 0
|
var age = 0
|
||||||
private set
|
private set
|
||||||
@ -249,6 +251,11 @@ abstract class Entity(
|
|||||||
physics.tickRiding()
|
physics.tickRiding()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
open fun isInvisible(camera: Entity): Boolean {
|
||||||
|
if (camera is PlayerEntity && camera.additional.gamemode == Gamemodes.SPECTATOR) return false
|
||||||
|
return isInvisible
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
private val renderInfo = Entity::renderInfo.javaField!!.apply { isAccessible = true }
|
private val renderInfo = Entity::renderInfo.javaField!!.apply { isAccessible = true }
|
||||||
|
@ -28,6 +28,7 @@ import de.bixilon.minosoft.data.entities.event.events.damage.DamageListener
|
|||||||
import de.bixilon.minosoft.data.registries.effects.attributes.EntityAttributes
|
import de.bixilon.minosoft.data.registries.effects.attributes.EntityAttributes
|
||||||
import de.bixilon.minosoft.data.registries.effects.attributes.MinecraftAttributes
|
import de.bixilon.minosoft.data.registries.effects.attributes.MinecraftAttributes
|
||||||
import de.bixilon.minosoft.data.registries.entities.EntityType
|
import de.bixilon.minosoft.data.registries.entities.EntityType
|
||||||
|
import de.bixilon.minosoft.data.text.ChatComponent
|
||||||
import de.bixilon.minosoft.data.text.formatting.color.ChatColors
|
import de.bixilon.minosoft.data.text.formatting.color.ChatColors
|
||||||
import de.bixilon.minosoft.data.text.formatting.color.RGBColor
|
import de.bixilon.minosoft.data.text.formatting.color.RGBColor
|
||||||
import de.bixilon.minosoft.data.text.formatting.color.RGBColor.Companion.asRGBColor
|
import de.bixilon.minosoft.data.text.formatting.color.RGBColor.Companion.asRGBColor
|
||||||
@ -45,7 +46,8 @@ abstract class LivingEntity(connection: PlayConnection, entityType: EntityType,
|
|||||||
val attributes = EntityAttributes(entityType.attributes)
|
val attributes = EntityAttributes(entityType.attributes)
|
||||||
|
|
||||||
|
|
||||||
override val canRaycast: Boolean get() = health > 0.0
|
override val canRaycast: Boolean get() = super.canRaycast && health > 0.0
|
||||||
|
override val name: ChatComponent? get() = super.name ?: connection.language.translate(type.translationKey)
|
||||||
|
|
||||||
private fun getLivingEntityFlag(bitMask: Int): Boolean {
|
private fun getLivingEntityFlag(bitMask: Int): Boolean {
|
||||||
return data.getBitMask(FLAGS_DATA, bitMask, 0x00)
|
return data.getBitMask(FLAGS_DATA, bitMask, 0x00)
|
||||||
|
@ -26,6 +26,7 @@ import de.bixilon.minosoft.data.entities.GlobalPosition
|
|||||||
import de.bixilon.minosoft.data.entities.Poses
|
import de.bixilon.minosoft.data.entities.Poses
|
||||||
import de.bixilon.minosoft.data.entities.data.EntityData
|
import de.bixilon.minosoft.data.entities.data.EntityData
|
||||||
import de.bixilon.minosoft.data.entities.data.EntityDataField
|
import de.bixilon.minosoft.data.entities.data.EntityDataField
|
||||||
|
import de.bixilon.minosoft.data.entities.entities.Entity
|
||||||
import de.bixilon.minosoft.data.entities.entities.LivingEntity
|
import de.bixilon.minosoft.data.entities.entities.LivingEntity
|
||||||
import de.bixilon.minosoft.data.entities.entities.SynchronizedEntityData
|
import de.bixilon.minosoft.data.entities.entities.SynchronizedEntityData
|
||||||
import de.bixilon.minosoft.data.entities.entities.player.additional.PlayerAdditional
|
import de.bixilon.minosoft.data.entities.entities.player.additional.PlayerAdditional
|
||||||
@ -150,6 +151,14 @@ abstract class PlayerEntity(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override fun isInvisible(camera: Entity): Boolean {
|
||||||
|
if (!super.isInvisible(camera)) return false
|
||||||
|
if (camera !is PlayerEntity) return true
|
||||||
|
val team = additional.team ?: return true
|
||||||
|
if (team != camera.additional.team) return true
|
||||||
|
return !team.visibility.invisibleTeam
|
||||||
|
}
|
||||||
|
|
||||||
companion object : Identified {
|
companion object : Identified {
|
||||||
override val identifier = minecraft("player")
|
override val identifier = minecraft("player")
|
||||||
|
|
||||||
|
@ -21,6 +21,7 @@ import de.bixilon.minosoft.data.text.ChatComponent
|
|||||||
import de.bixilon.minosoft.gui.rendering.entities.feature.EntityRenderFeature
|
import de.bixilon.minosoft.gui.rendering.entities.feature.EntityRenderFeature
|
||||||
import de.bixilon.minosoft.gui.rendering.entities.renderer.EntityRenderer
|
import de.bixilon.minosoft.gui.rendering.entities.renderer.EntityRenderer
|
||||||
import de.bixilon.minosoft.gui.rendering.font.renderer.component.ChatComponentRenderer
|
import de.bixilon.minosoft.gui.rendering.font.renderer.component.ChatComponentRenderer
|
||||||
|
import de.bixilon.minosoft.gui.rendering.font.renderer.element.CharSpacing
|
||||||
import de.bixilon.minosoft.gui.rendering.font.renderer.element.TextRenderInfo
|
import de.bixilon.minosoft.gui.rendering.font.renderer.element.TextRenderInfo
|
||||||
import de.bixilon.minosoft.gui.rendering.font.renderer.element.TextRenderProperties
|
import de.bixilon.minosoft.gui.rendering.font.renderer.element.TextRenderProperties
|
||||||
import de.bixilon.minosoft.gui.rendering.system.base.BlendingFunctions
|
import de.bixilon.minosoft.gui.rendering.system.base.BlendingFunctions
|
||||||
@ -126,7 +127,7 @@ open class BillboardTextFeature(
|
|||||||
}
|
}
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
val PROPERTIES = TextRenderProperties(allowNewLine = false)
|
val PROPERTIES = TextRenderProperties(allowNewLine = false, shadow = false, charSpacing = CharSpacing(top = 1.0f, bottom = 1.0f))
|
||||||
val MAX_SIZE = Vec2(300.0f, PROPERTIES.lineHeight)
|
val MAX_SIZE = Vec2(300.0f, PROPERTIES.lineHeight)
|
||||||
const val DEFAULT_OFFSET = 0.25f
|
const val DEFAULT_OFFSET = 0.25f
|
||||||
const val RENDER_DISTANCE = 48
|
const val RENDER_DISTANCE = 48
|
||||||
|
@ -15,12 +15,17 @@ package de.bixilon.minosoft.gui.rendering.entities.feature.text.name
|
|||||||
|
|
||||||
import de.bixilon.kutil.cast.CastUtil.nullCast
|
import de.bixilon.kutil.cast.CastUtil.nullCast
|
||||||
import de.bixilon.kutil.cast.CastUtil.unsafeCast
|
import de.bixilon.kutil.cast.CastUtil.unsafeCast
|
||||||
|
import de.bixilon.kutil.exception.Broken
|
||||||
import de.bixilon.minosoft.camera.target.targets.EntityTarget
|
import de.bixilon.minosoft.camera.target.targets.EntityTarget
|
||||||
import de.bixilon.minosoft.data.entities.Poses
|
import de.bixilon.minosoft.data.entities.Poses
|
||||||
import de.bixilon.minosoft.data.entities.entities.Entity
|
import de.bixilon.minosoft.data.entities.entities.Entity
|
||||||
import de.bixilon.minosoft.data.entities.entities.LivingEntity
|
import de.bixilon.minosoft.data.entities.entities.LivingEntity
|
||||||
import de.bixilon.minosoft.data.entities.entities.Mob
|
import de.bixilon.minosoft.data.entities.entities.Mob
|
||||||
|
import de.bixilon.minosoft.data.entities.entities.decoration.ItemFrame
|
||||||
|
import de.bixilon.minosoft.data.entities.entities.decoration.armorstand.ArmorStand
|
||||||
|
import de.bixilon.minosoft.data.entities.entities.player.PlayerEntity
|
||||||
import de.bixilon.minosoft.data.entities.entities.player.local.LocalPlayerEntity
|
import de.bixilon.minosoft.data.entities.entities.player.local.LocalPlayerEntity
|
||||||
|
import de.bixilon.minosoft.data.scoreboard.NameTagVisibilities
|
||||||
import de.bixilon.minosoft.data.text.ChatComponent
|
import de.bixilon.minosoft.data.text.ChatComponent
|
||||||
import de.bixilon.minosoft.gui.rendering.entities.feature.text.BillboardTextFeature
|
import de.bixilon.minosoft.gui.rendering.entities.feature.text.BillboardTextFeature
|
||||||
import de.bixilon.minosoft.gui.rendering.entities.renderer.EntityRenderer
|
import de.bixilon.minosoft.gui.rendering.entities.renderer.EntityRenderer
|
||||||
@ -45,31 +50,82 @@ class EntityNameFeature(renderer: EntityRenderer<*>) : BillboardTextFeature(rend
|
|||||||
this.text = getEntityName()
|
this.text = getEntityName()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun Entity.getName(): ChatComponent? {
|
private fun Entity.getName(invisible: Boolean): ChatComponent? {
|
||||||
|
if (invisible) return null
|
||||||
if (this.isNameVisible) return name
|
if (this.isNameVisible) return name
|
||||||
if (!isTargeted()) return null
|
if (!isTargeted()) return null
|
||||||
return name
|
return name
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun LivingEntity.getName(): ChatComponent? {
|
private fun LivingEntity.getName(invisible: Boolean): ChatComponent? {
|
||||||
val distance = if (this.pose == Poses.SNEAKING) SNEAKING_DISTANCE * SNEAKING_DISTANCE else RENDER_DISTANCE * RENDER_DISTANCE
|
|
||||||
if (this@EntityNameFeature.renderer.distance >= distance) return null
|
|
||||||
if (this.primaryPassenger != null) return null
|
if (this.primaryPassenger != null) return null
|
||||||
|
|
||||||
val renderer = this@EntityNameFeature.renderer.renderer
|
val renderer = this@EntityNameFeature.renderer.renderer
|
||||||
val profile = renderer.profile.features.name
|
val profile = renderer.profile.features.name
|
||||||
if (this === renderer.connection.camera.entity && (!renderer.context.camera.view.view.renderSelf || !profile.local)) return null
|
if (this === renderer.connection.camera.entity && (!renderer.context.camera.view.view.renderSelf || !profile.local)) return null
|
||||||
|
if (!this.isNameVisible) return null
|
||||||
|
|
||||||
// TODO: invisibility (w/ teams)
|
if (invisible) return null
|
||||||
|
|
||||||
return this.name
|
return this.name
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun ArmorStand.getName(): ChatComponent? {
|
||||||
|
if (!isNameVisible) return null
|
||||||
|
|
||||||
|
return customName
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun ItemFrame.getName(): ChatComponent? {
|
||||||
|
if (!isTargeted()) return null
|
||||||
|
val item = this.item ?: return null
|
||||||
|
|
||||||
|
return item._display?._customDisplayName
|
||||||
|
}
|
||||||
|
|
||||||
private fun getEntityName(): ChatComponent? {
|
private fun getEntityName(): ChatComponent? {
|
||||||
|
val profile = renderer.renderer.profile.features.name
|
||||||
|
if (!profile.enabled) return null
|
||||||
|
|
||||||
|
val entity = renderer.entity
|
||||||
|
|
||||||
|
val distance = if (entity is LivingEntity && entity.pose == Poses.SNEAKING) SNEAKING_DISTANCE * SNEAKING_DISTANCE else RENDER_DISTANCE * RENDER_DISTANCE
|
||||||
|
if (renderer.distance >= distance) return null
|
||||||
|
|
||||||
|
val invisible = isInvisible()
|
||||||
|
|
||||||
return when (renderer.entity) {
|
return when (renderer.entity) {
|
||||||
is Mob -> renderer.entity.unsafeCast<Entity>().getName()
|
is ItemFrame -> renderer.entity.getName()
|
||||||
is LivingEntity -> renderer.entity.getName()
|
is ArmorStand -> renderer.entity.getName()
|
||||||
else -> renderer.entity.getName()
|
is Mob -> renderer.entity.unsafeCast<Entity>().getName(invisible)
|
||||||
|
is LivingEntity -> renderer.entity.getName(invisible)
|
||||||
|
else -> renderer.entity.getName(invisible)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun isInvisible(): Boolean {
|
||||||
|
val camera = renderer.renderer.connection.camera.entity
|
||||||
|
val entity = renderer.entity
|
||||||
|
val invisible = entity.isInvisible(camera)
|
||||||
|
|
||||||
|
if (entity !is PlayerEntity) return invisible
|
||||||
|
val team = entity.additional.team ?: return invisible
|
||||||
|
val name = team.visibility.name
|
||||||
|
|
||||||
|
when (name) {
|
||||||
|
NameTagVisibilities.ALWAYS -> return invisible
|
||||||
|
NameTagVisibilities.NEVER -> return true
|
||||||
|
else -> Unit
|
||||||
|
}
|
||||||
|
|
||||||
|
val cTeam = camera.nullCast<PlayerEntity>()?.additional?.team ?: return invisible
|
||||||
|
val sameTeam = team.name == cTeam.name
|
||||||
|
|
||||||
|
|
||||||
|
return when (name) {
|
||||||
|
NameTagVisibilities.HIDE_FOR_ENEMIES -> !sameTeam || (team.visibility.invisibleTeam && invisible)
|
||||||
|
NameTagVisibilities.HIDE_FOR_MATES -> sameTeam || invisible
|
||||||
|
else -> Broken()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -57,7 +57,7 @@ class EntityScoreFeature(renderer: PlayerRenderer<*>) : BillboardTextFeature(ren
|
|||||||
if (!profile.enabled) return false
|
if (!profile.enabled) return false
|
||||||
if (this.renderer.entity === renderer.connection.camera.entity && (!renderer.context.camera.view.view.renderSelf || !profile.local)) return false
|
if (this.renderer.entity === renderer.connection.camera.entity && (!renderer.context.camera.view.view.renderSelf || !profile.local)) return false
|
||||||
|
|
||||||
return true
|
return this.renderer.name.text != null
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getScore(): ChatComponent? {
|
private fun getScore(): ChatComponent? {
|
||||||
|
@ -1,24 +0,0 @@
|
|||||||
/*
|
|
||||||
* Minosoft
|
|
||||||
* Copyright (C) 2020-2023 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 <https://www.gnu.org/licenses/>.
|
|
||||||
*
|
|
||||||
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
|
|
||||||
*/
|
|
||||||
|
|
||||||
package de.bixilon.minosoft.protocol.protocol
|
|
||||||
|
|
||||||
import de.bixilon.minosoft.protocol.protocol.ProtocolVersions.V_13W41B
|
|
||||||
import de.bixilon.minosoft.protocol.protocol.ProtocolVersions.V_1_20_2
|
|
||||||
import de.bixilon.minosoft.protocol.protocol.ProtocolVersions.V_23W42A
|
|
||||||
|
|
||||||
object VersionSupport {
|
|
||||||
const val MINIMUM_VERSION = V_13W41B
|
|
||||||
const val LATEST_VERSION = V_23W42A
|
|
||||||
const val LATEST_RELEASE = V_1_20_2
|
|
||||||
}
|
|
Loading…
x
Reference in New Issue
Block a user