diff --git a/README.md b/README.md index 0e04db7..1b1227a 100644 --- a/README.md +++ b/README.md @@ -53,3 +53,13 @@ * `LP.KeepLeashNotDropTime` - 此规则决定,当拴绳关系创建时一段时间里,即是距离已经达到了断裂距离,也保持其不断裂 [默认值: 240ticks ,可设置范围[80, 1200]ticks] * `LP.DisableMoveCheck` - 此规则启用将会禁止服务器对玩家进行速度过快修正 [默认值: True] + +Please use a paste site for large blocks of code/logs, instead of dumping it in chat or taking a screenshot. + +Here's a list of some paste sites and their size limits: +https://gist.github.com/: [Free] [SignUp] 100MB +https://paste.gemwire.uk/: [Free] 10MB +https://paste.ee/: [Free] 1MB, [SignUp] 6MB +https://pastebin.com/: [Free] 512KB, [SignUp] [Paid] 10MB +https://hastebin.com/: [Free] 400KB +https://gist.github.com/: [Free] [SignUp] 100MB \ No newline at end of file diff --git a/build.gradle b/build.gradle index 58bcbe4..943e2c2 100644 --- a/build.gradle +++ b/build.gradle @@ -3,7 +3,7 @@ plugins { id 'eclipse' id 'idea' id 'maven-publish' - id 'net.neoforged.gradle.userdev' version '7.0.145' + id 'net.neoforged.gradle.userdev' version '7.0.165' } tasks.named('wrapper', Wrapper).configure { @@ -25,11 +25,10 @@ repositories { base { archivesName = mod_id } - // Mojang ships Java 21 to end users starting in 1.20.5, so mods should target Java 21. java.toolchain.languageVersion = JavaLanguageVersion.of(21) -//minecraft.accessTransformers.file rootProject.file('src/main/resources/META-INF/accesstransformer.cfg') +minecraft.accessTransformers.file file('src/main/resources/META-INF/accesstransformer.cfg') //minecraft.accessTransformers.entry public net.minecraft.client.Minecraft textureManager # textureManager // Default run configurations. @@ -172,4 +171,4 @@ idea { downloadSources = true downloadJavadoc = true } -} +} \ No newline at end of file diff --git a/gradle.properties b/gradle.properties index 068bebb..46c5e7c 100644 --- a/gradle.properties +++ b/gradle.properties @@ -2,6 +2,14 @@ org.gradle.jvmargs=-Xmx8G org.gradle.daemon=false org.gradle.debug=false +org.gradle.parallel=true +org.gradle.caching=true +org.gradle.configuration-cache=false + +#read more on this at https://github.com/neoforged/ModDevGradle?tab=readme-ov-file#better-minecraft-parameter-names--javadoc-parchment +# you can also find the latest versions at: https://parchmentmc.org/docs/getting-started +parchment_minecraft_version=1.21 +parchment_mappings_version=2024.07.28 #read more on this at https://github.com/neoforged/NeoGradle/blob/NG_7.0/README.md#apply-parchment-mappings # you can also find the latest versions at: https://parchmentmc.org/docs/getting-started @@ -10,17 +18,19 @@ neogradle.subsystems.parchment.mappingsVersion=2024.07.28 # Environment Properties # You can find the latest versions here: https://projects.neoforged.net/neoforged/neoforge # The Minecraft version must agree with the Neo version to get a valid artifact -minecraft_version=1.21 +minecraft_version=1.21.3 # The Minecraft version range can use any release version of Minecraft as bounds. # Snapshots, pre-releases, and release candidates are not guaranteed to sort properly # as they do not follow standard versioning conventions. -minecraft_version_range=[1.21,1.22) +minecraft_version_range=[1.21.1,1.22) +enable_accesstransformers=true # The Neo version must agree with the Minecraft version to get a valid artifact -neo_version=21.0.157 +neo_version=21.3.0-beta # The Neo version range can use any version of Neo as bounds -neo_version_range=[21.0.0-beta,) +neo_version_range=[21.1.0,) # The loader version range can only use the major version of FML as bounds loader_version_range=[4,) +neoform_version=1.21.3-20241023.131943 ## Mod Properties @@ -32,7 +42,7 @@ mod_name=Leashed Player # The license of the mod. Review your options at https://choosealicense.com/. All Rights Reserved is the default. mod_license=MIT # The mod version. See https://semver.org/ -mod_version=0.0.3.9.4 +mod_version=1.21.3 0.0.3.9.4 # The group ID for the mod. It is only important when publishing as an artifact to a Maven repository. # This should match the base package used for the mod sources. # See https://maven.apache.org/guides/mini/guide-naming-conventions.html diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 06c32f6..09523c0 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://mirrors.cloud.tencent.com/gradle/gradle-8.9-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-8.9-bin.zip networkTimeout=10000 validateDistributionUrl=true zipStoreBase=GRADLE_USER_HOME diff --git a/gradlew b/gradlew index f5feea6..b26d411 100755 --- a/gradlew +++ b/gradlew @@ -249,4 +249,4 @@ eval "set -- $( tr '\n' ' ' )" '"$@"' -exec "$JAVACMD" "$@" +exec "$JAVACMD" "$@" \ No newline at end of file diff --git a/gradlew.bat b/gradlew.bat index 9b42019..b808aea 100644 --- a/gradlew.bat +++ b/gradlew.bat @@ -91,4 +91,4 @@ exit /b %EXIT_CODE% :mainEnd if "%OS%"=="Windows_NT" endlocal -:omega +:omega \ No newline at end of file diff --git a/src/generated/resources/.cache/0aef4464247e697f9a7226f384437b478152c21c b/src/generated/resources/.cache/0aef4464247e697f9a7226f384437b478152c21c index ffc6767..443e9fd 100644 --- a/src/generated/resources/.cache/0aef4464247e697f9a7226f384437b478152c21c +++ b/src/generated/resources/.cache/0aef4464247e697f9a7226f384437b478152c21c @@ -1,4 +1,4 @@ -// 1.21 2024-10-23T13:15:06.1102778 Item Models: leashedplayer +// 1.21.3 2024-10-27T23:14:21.0486567 Item Models: leashedplayer 5846df9d85726428905701120ef34c9324c20faf assets/leashedplayer/models/item/bow_lra_pulling_0.json 845a7316b86e26f88c6932d4ef2656126503727a assets/leashedplayer/models/item/bow_lra_pulling_1.json 5bd1f9f28b91005c587f1c38fb77cd19b59495e3 assets/leashedplayer/models/item/bow_lra_pulling_2.json diff --git a/src/generated/resources/.cache/103d9f3f36b01595f1aa5172191e60eff02e6924 b/src/generated/resources/.cache/103d9f3f36b01595f1aa5172191e60eff02e6924 index fa93094..10886c0 100644 --- a/src/generated/resources/.cache/103d9f3f36b01595f1aa5172191e60eff02e6924 +++ b/src/generated/resources/.cache/103d9f3f36b01595f1aa5172191e60eff02e6924 @@ -1,2 +1,2 @@ -// 1.21 2024-10-23T13:15:06.1082841 Registries -6f79a674215db9f9d2820b1c7f052c60ce729fee data/leashedplayer/painting_variant/group_photo.json +// 1.21.3 2024-10-27T23:14:21.047502 Registries +84106976f4f71012fc5bd1784303a0d135623c77 data/leashedplayer/painting_variant/group_photo.json diff --git a/src/generated/resources/.cache/1749bb0c3e8c52cfb2d8ed2140e4678c71e770f5 b/src/generated/resources/.cache/1749bb0c3e8c52cfb2d8ed2140e4678c71e770f5 index 0dabe2b..d7c30d8 100644 --- a/src/generated/resources/.cache/1749bb0c3e8c52cfb2d8ed2140e4678c71e770f5 +++ b/src/generated/resources/.cache/1749bb0c3e8c52cfb2d8ed2140e4678c71e770f5 @@ -1,2 +1,2 @@ -// 1.21 2024-10-23T13:15:06.1012494 Tags for minecraft:item mod id leashedplayer +// 1.21.3 2024-10-27T23:14:21.0349914 Tags for minecraft:item mod id leashedplayer 36c1cccc1dfa448620c4e9cbc4a7d73986ff9e47 data/minecraft/tags/item/arrows.json diff --git a/src/generated/resources/.cache/211976637bfb5e111401ad2bfb58570ef2fb3dff b/src/generated/resources/.cache/211976637bfb5e111401ad2bfb58570ef2fb3dff index eaa23cd..18311bc 100644 --- a/src/generated/resources/.cache/211976637bfb5e111401ad2bfb58570ef2fb3dff +++ b/src/generated/resources/.cache/211976637bfb5e111401ad2bfb58570ef2fb3dff @@ -1,2 +1,2 @@ -// 1.21 2024-10-23T14:43:16.8619078 Languages: en_us for mod: leashedplayer +// 1.21.3 2024-10-27T23:14:21.0486567 Languages: en_us for mod: leashedplayer 4dc2ca922a540c7133a4a6867dfcd8bfec5a1db4 assets/leashedplayer/lang/en_us.json diff --git a/src/generated/resources/.cache/456392f19d2beac1e6e71432fcc2128b993c47e1 b/src/generated/resources/.cache/456392f19d2beac1e6e71432fcc2128b993c47e1 index c85a2ed..365509e 100644 --- a/src/generated/resources/.cache/456392f19d2beac1e6e71432fcc2128b993c47e1 +++ b/src/generated/resources/.cache/456392f19d2beac1e6e71432fcc2128b993c47e1 @@ -1 +1 @@ -// 1.21 2024-10-23T13:15:06.1052755 Tags for minecraft:block mod id leashedplayer +// 1.21.3 2024-10-27T23:14:21.0429914 Tags for minecraft:block mod id leashedplayer diff --git a/src/generated/resources/.cache/818caf9537d536e2a9ffeae84514691689356c22 b/src/generated/resources/.cache/818caf9537d536e2a9ffeae84514691689356c22 index 5920da0..72d5e4b 100644 --- a/src/generated/resources/.cache/818caf9537d536e2a9ffeae84514691689356c22 +++ b/src/generated/resources/.cache/818caf9537d536e2a9ffeae84514691689356c22 @@ -1,2 +1,2 @@ -// 1.21 2024-10-23T13:15:06.1052755 Tags for minecraft:painting_variant mod id leashedplayer +// 1.21.3 2024-10-27T23:14:21.0429914 Tags for minecraft:painting_variant mod id leashedplayer e081a053d7c2f2d3238cf38436185ef23d234505 data/minecraft/tags/painting_variant/placeable.json diff --git a/src/generated/resources/.cache/853329c6e706e45295e80307b8a95a5709025422 b/src/generated/resources/.cache/853329c6e706e45295e80307b8a95a5709025422 index dfd28dc..78110c5 100644 --- a/src/generated/resources/.cache/853329c6e706e45295e80307b8a95a5709025422 +++ b/src/generated/resources/.cache/853329c6e706e45295e80307b8a95a5709025422 @@ -1,2 +1,2 @@ -// 1.21 2024-10-23T13:15:06.1042677 Languages: lzh for mod: leashedplayer +// 1.21.3 2024-10-27T23:14:21.0429914 Languages: lzh for mod: leashedplayer bf21a9e8fbc5a3846fb05b4fa0859e0917b2202f assets/leashedplayer/lang/lzh.json diff --git a/src/generated/resources/.cache/9fb1092f32d4fcbf9e061ffd718d4ec689c6c95e b/src/generated/resources/.cache/9fb1092f32d4fcbf9e061ffd718d4ec689c6c95e deleted file mode 100644 index 045e4a7..0000000 --- a/src/generated/resources/.cache/9fb1092f32d4fcbf9e061ffd718d4ec689c6c95e +++ /dev/null @@ -1,7 +0,0 @@ -// 1.21 2024-10-23T13:15:06.1092763 Recipes -1b45d1ad8dc73f1787c97777ad13d9771c9e0ad1 data/leashedplayer/advancement/recipes/misc/leash_rope_arrow.json -974d74538b3e172946f2e169036b453b6eb6bc0a data/leashedplayer/recipe/leash_rope_arrow.json -c0e05f359296d3e28573fa1b205ac44736376622 data/minecraft/advancement/recipes/misc/spectral_leash_rope_arrow_with_glowstone_dust.json -131fcbef603bfde7204d8e1ad15e4544696926bf data/minecraft/advancement/recipes/misc/spectral_leash_rope_arrow_with_leash_rope_arrow.json -bb5909aa91d878c8f0ef9999881cfe89532509dd data/minecraft/recipe/spectral_leash_rope_arrow_with_glowstone_dust.json -a1381da885fbedec01243c78afbb0a50ca803ee4 data/minecraft/recipe/spectral_leash_rope_arrow_with_leash_rope_arrow.json diff --git a/src/generated/resources/.cache/a1129211d3ad6d65c101bb152ae8c66c8256bccb b/src/generated/resources/.cache/a1129211d3ad6d65c101bb152ae8c66c8256bccb index 97fa50f..78a5f8e 100644 --- a/src/generated/resources/.cache/a1129211d3ad6d65c101bb152ae8c66c8256bccb +++ b/src/generated/resources/.cache/a1129211d3ad6d65c101bb152ae8c66c8256bccb @@ -1,2 +1,2 @@ -// 1.21 2024-10-23T14:43:16.860909 Languages: zh_cn for mod: leashedplayer +// 1.21.3 2024-10-27T23:14:21.047502 Languages: zh_cn for mod: leashedplayer 35bc6c3001138c5306d1ee9d55ef3dfbfd417e08 assets/leashedplayer/lang/zh_cn.json diff --git a/src/generated/resources/.cache/e5c5eb35b4ba40351ecb7d9f04c3527f2f5779b0 b/src/generated/resources/.cache/e5c5eb35b4ba40351ecb7d9f04c3527f2f5779b0 index 907f395..4daeaa7 100644 --- a/src/generated/resources/.cache/e5c5eb35b4ba40351ecb7d9f04c3527f2f5779b0 +++ b/src/generated/resources/.cache/e5c5eb35b4ba40351ecb7d9f04c3527f2f5779b0 @@ -1,4 +1,4 @@ -// 1.21 2024-10-23T14:19:10.2054361 Advancements +// 1.21.3 2024-10-27T23:14:21.0497079 Advancements 4d97adba079f1966090a52443bb439319f550680 data/leashedplayer/advancement/advancement_leash_arrow.json f16184b81ea35a0fbd8f2c49b085a96c32818c69 data/leashedplayer/advancement/dog_running_player.json bce12ed339b3b0fded263ba039f7a4e6fcfb84ca data/leashedplayer/advancement/follow_arrow.json diff --git a/src/generated/resources/.cache/ed628fd843215c1bf29a07b9cbd1b26a6af0636d b/src/generated/resources/.cache/ed628fd843215c1bf29a07b9cbd1b26a6af0636d index 7d99a80..edce4e1 100644 --- a/src/generated/resources/.cache/ed628fd843215c1bf29a07b9cbd1b26a6af0636d +++ b/src/generated/resources/.cache/ed628fd843215c1bf29a07b9cbd1b26a6af0636d @@ -1,2 +1,2 @@ -// 1.21 2024-10-23T14:43:16.8589078 Languages: zh_tw for mod: leashedplayer +// 1.21.3 2024-10-27T23:14:21.0467812 Languages: zh_tw for mod: leashedplayer c6df14a1f53a3e892ebc6b396b552ff27f1a7580 assets/leashedplayer/lang/zh_tw.json diff --git a/src/generated/resources/data/leashedplayer/painting_variant/group_photo.json b/src/generated/resources/data/leashedplayer/painting_variant/group_photo.json index d908454..b64931b 100644 --- a/src/generated/resources/data/leashedplayer/painting_variant/group_photo.json +++ b/src/generated/resources/data/leashedplayer/painting_variant/group_photo.json @@ -1,5 +1,11 @@ { "asset_id": "leashedplayer:group_photo", + "author": { + "translate": "painting.leashedplayer.group_photo.author" + }, "height": 3, + "title": { + "translate": "painting.leashedplayer.group_photo.title" + }, "width": 4 } \ No newline at end of file diff --git a/src/generated/resources/data/leashedplayer/recipe/leash_rope_arrow.json b/src/generated/resources/data/leashedplayer/recipe/leash_rope_arrow.json index 52df510..b1b4630 100644 --- a/src/generated/resources/data/leashedplayer/recipe/leash_rope_arrow.json +++ b/src/generated/resources/data/leashedplayer/recipe/leash_rope_arrow.json @@ -2,12 +2,8 @@ "type": "minecraft:crafting_shapeless", "category": "misc", "ingredients": [ - { - "item": "minecraft:lead" - }, - { - "item": "minecraft:arrow" - } + "minecraft:lead", + "minecraft:arrow" ], "result": { "count": 1, diff --git a/src/generated/resources/data/minecraft/advancement/recipes/misc/spectral_leash_rope_arrow_with_glowstone_dust.json b/src/generated/resources/data/minecraft/advancement/recipes/misc/spectral_leash_rope_arrow_with_glowstone_dust.json deleted file mode 100644 index 63dfc08..0000000 --- a/src/generated/resources/data/minecraft/advancement/recipes/misc/spectral_leash_rope_arrow_with_glowstone_dust.json +++ /dev/null @@ -1,43 +0,0 @@ -{ - "parent": "minecraft:recipes/root", - "criteria": { - "has_glowstone_dust": { - "conditions": { - "items": [ - { - "items": "minecraft:glowstone_dust" - } - ] - }, - "trigger": "minecraft:inventory_changed" - }, - "has_lead": { - "conditions": { - "items": [ - { - "items": "minecraft:lead" - } - ] - }, - "trigger": "minecraft:inventory_changed" - }, - "has_the_recipe": { - "conditions": { - "recipe": "minecraft:spectral_leash_rope_arrow_with_glowstone_dust" - }, - "trigger": "minecraft:recipe_unlocked" - } - }, - "requirements": [ - [ - "has_the_recipe", - "has_lead", - "has_glowstone_dust" - ] - ], - "rewards": { - "recipes": [ - "minecraft:spectral_leash_rope_arrow_with_glowstone_dust" - ] - } -} \ No newline at end of file diff --git a/src/generated/resources/data/minecraft/advancement/recipes/misc/spectral_leash_rope_arrow_with_leash_rope_arrow.json b/src/generated/resources/data/minecraft/advancement/recipes/misc/spectral_leash_rope_arrow_with_leash_rope_arrow.json deleted file mode 100644 index 1c247aa..0000000 --- a/src/generated/resources/data/minecraft/advancement/recipes/misc/spectral_leash_rope_arrow_with_leash_rope_arrow.json +++ /dev/null @@ -1,43 +0,0 @@ -{ - "parent": "minecraft:recipes/root", - "criteria": { - "has_lead": { - "conditions": { - "items": [ - { - "items": "minecraft:lead" - } - ] - }, - "trigger": "minecraft:inventory_changed" - }, - "has_spectral_arrow": { - "conditions": { - "items": [ - { - "items": "minecraft:spectral_arrow" - } - ] - }, - "trigger": "minecraft:inventory_changed" - }, - "has_the_recipe": { - "conditions": { - "recipe": "minecraft:spectral_leash_rope_arrow_with_leash_rope_arrow" - }, - "trigger": "minecraft:recipe_unlocked" - } - }, - "requirements": [ - [ - "has_the_recipe", - "has_lead", - "has_spectral_arrow" - ] - ], - "rewards": { - "recipes": [ - "minecraft:spectral_leash_rope_arrow_with_leash_rope_arrow" - ] - } -} \ No newline at end of file diff --git a/src/generated/resources/data/minecraft/recipe/spectral_leash_rope_arrow_with_glowstone_dust.json b/src/generated/resources/data/minecraft/recipe/spectral_leash_rope_arrow_with_glowstone_dust.json deleted file mode 100644 index 8a79e64..0000000 --- a/src/generated/resources/data/minecraft/recipe/spectral_leash_rope_arrow_with_glowstone_dust.json +++ /dev/null @@ -1,21 +0,0 @@ -{ - "type": "minecraft:crafting_shaped", - "category": "misc", - "key": { - "#": { - "item": "leashedplayer:leash_rope_arrow" - }, - "$": { - "item": "minecraft:glowstone_dust" - } - }, - "pattern": [ - " $ ", - "$#$", - " $ " - ], - "result": { - "count": 1, - "id": "leashedplayer:spectral_leash_rope_arrow" - } -} \ No newline at end of file diff --git a/src/generated/resources/data/minecraft/recipe/spectral_leash_rope_arrow_with_leash_rope_arrow.json b/src/generated/resources/data/minecraft/recipe/spectral_leash_rope_arrow_with_leash_rope_arrow.json deleted file mode 100644 index e0b59e4..0000000 --- a/src/generated/resources/data/minecraft/recipe/spectral_leash_rope_arrow_with_leash_rope_arrow.json +++ /dev/null @@ -1,16 +0,0 @@ -{ - "type": "minecraft:crafting_shapeless", - "category": "misc", - "ingredients": [ - { - "item": "minecraft:lead" - }, - { - "item": "minecraft:spectral_arrow" - } - ], - "result": { - "count": 1, - "id": "leashedplayer:spectral_leash_rope_arrow" - } -} \ No newline at end of file diff --git a/src/main/java/com/r3944realms/leashedplayer/ClientEventHandler.java b/src/main/java/com/r3944realms/leashedplayer/ClientEventHandler.java index 5bc9153..aadefb2 100644 --- a/src/main/java/com/r3944realms/leashedplayer/ClientEventHandler.java +++ b/src/main/java/com/r3944realms/leashedplayer/ClientEventHandler.java @@ -1,10 +1,14 @@ package com.r3944realms.leashedplayer; +import com.mojang.blaze3d.vertex.PoseStack; +import com.r3944realms.leashedplayer.client.renders.LeashRendererUtil; import com.r3944realms.leashedplayer.client.renders.entities.LeashRopeArrowRenderer; import com.r3944realms.leashedplayer.client.renders.entities.SpectralLeashRopeArrowRenderer; import com.r3944realms.leashedplayer.content.entities.ModEntityRegister; import com.r3944realms.leashedplayer.content.items.ModItemRegister; import com.r3944realms.leashedplayer.content.items.type.ILeashRopeArrow; +import com.r3944realms.leashedplayer.modInterface.IPlayerRenderStateExtension; +import net.minecraft.client.renderer.entity.state.PlayerRenderState; import net.minecraft.client.renderer.item.ItemProperties; import net.minecraft.core.component.DataComponents; import net.minecraft.resources.ResourceLocation; @@ -15,28 +19,44 @@ import net.neoforged.bus.api.SubscribeEvent; import net.neoforged.fml.common.EventBusSubscriber; import net.neoforged.fml.event.lifecycle.FMLClientSetupEvent; import net.neoforged.neoforge.client.event.EntityRenderersEvent; +import net.neoforged.neoforge.client.event.RenderLevelStageEvent; +import net.neoforged.neoforge.client.event.RenderPlayerEvent; + -@EventBusSubscriber(value = Dist.CLIENT, bus = EventBusSubscriber.Bus.MOD, modid = LeashedPlayer.MOD_ID) public class ClientEventHandler { - @SubscribeEvent - public static void onRegisterItemProperties(FMLClientSetupEvent event) { - event.enqueueWork(() -> { - ItemProperties.register(Items.CROSSBOW, ResourceLocation.withDefaultNamespace("leash_rope_arrow"), - ((pStack, pLevel, pEntity, pSeed) -> { - ChargedProjectiles chargedProjectiles = pStack.get(DataComponents.CHARGED_PROJECTILES); - return chargedProjectiles != null && (chargedProjectiles.contains(ModItemRegister.LEASH_ROPE_ARROW.get()) || chargedProjectiles.contains(ModItemRegister.SPECTRAL_LEASH_ROPE_ARROW.get())) ? 1.0F : 0.0F; - })); - ItemProperties.register(Items.BOW, ResourceLocation.withDefaultNamespace("leash_rope_arrow_pulling"), - ((pStack, pLevel, pEntity, pSeed) -> - (pEntity != null && pEntity.isUsingItem() && pEntity.getUseItem() == pStack && ILeashRopeArrow.isLeashRopeArrow(pStack, pEntity)) ? 1.0F: 0.0F - )); - }); + @EventBusSubscriber(value = Dist.CLIENT, bus = EventBusSubscriber.Bus.GAME, modid = LeashedPlayer.MOD_ID) + public static class Game { + @SubscribeEvent + public static void onPlayerRendererEventPre(RenderPlayerEvent.Pre event) { + PlayerRenderState renderState = event.getRenderState(); + if(((IPlayerRenderStateExtension)renderState).getPlayerLeashState() != null) { + LeashRendererUtil.renderLeash(event.getPoseStack(), event.getMultiBufferSource(), renderState); + } + } + } + @EventBusSubscriber(value = Dist.CLIENT, bus = EventBusSubscriber.Bus.MOD, modid = LeashedPlayer.MOD_ID) + public static class Mod { + @SubscribeEvent + public static void onRegisterItemProperties(FMLClientSetupEvent event) { + event.enqueueWork(() -> { + ItemProperties.register(Items.CROSSBOW, ResourceLocation.withDefaultNamespace("leash_rope_arrow"), + ((pStack, pLevel, pEntity, pSeed) -> { + ChargedProjectiles chargedProjectiles = pStack.get(DataComponents.CHARGED_PROJECTILES); + return chargedProjectiles != null && (chargedProjectiles.contains(ModItemRegister.LEASH_ROPE_ARROW.get()) || chargedProjectiles.contains(ModItemRegister.SPECTRAL_LEASH_ROPE_ARROW.get())) ? 1.0F : 0.0F; + })); + ItemProperties.register(Items.BOW, ResourceLocation.withDefaultNamespace("leash_rope_arrow_pulling"), + ((pStack, pLevel, pEntity, pSeed) -> + (pEntity != null && pEntity.isUsingItem() && pEntity.getUseItem() == pStack && ILeashRopeArrow.isLeashRopeArrow(pStack, pEntity)) ? 1.0F: 0.0F + )); + }); + } + @SubscribeEvent + public static void RegisterRenderer(EntityRenderersEvent.RegisterRenderers event) { + event.registerEntityRenderer(ModEntityRegister.LEASH_ROPE_ARROW.get(), LeashRopeArrowRenderer::new); + event.registerEntityRenderer(ModEntityRegister.SPECTRAL_LEASH_ROPE_ARROW.get(), SpectralLeashRopeArrowRenderer::new); + } } - @SubscribeEvent - public static void RegisterRenderer(EntityRenderersEvent.RegisterRenderers event) { - event.registerEntityRenderer(ModEntityRegister.LEASH_ROPE_ARROW.get(), LeashRopeArrowRenderer::new); - event.registerEntityRenderer(ModEntityRegister.SPECTRAL_LEASH_ROPE_ARROW.get(), SpectralLeashRopeArrowRenderer::new); - } + } diff --git a/src/main/java/com/r3944realms/leashedplayer/client/renders/LeashRendererUtil.java b/src/main/java/com/r3944realms/leashedplayer/client/renders/LeashRendererUtil.java new file mode 100644 index 0000000..254101d --- /dev/null +++ b/src/main/java/com/r3944realms/leashedplayer/client/renders/LeashRendererUtil.java @@ -0,0 +1,367 @@ +package com.r3944realms.leashedplayer.client.renders; + +import com.mojang.blaze3d.vertex.PoseStack; +import com.mojang.blaze3d.vertex.VertexConsumer; +import com.mojang.datafixers.util.Either; +import com.r3944realms.leashedplayer.LeashedPlayer; +import com.r3944realms.leashedplayer.content.entities.LeashRopeArrow; +import com.r3944realms.leashedplayer.modInterface.ILivingEntityExtension; +import com.r3944realms.leashedplayer.modInterface.IPlayerRenderStateExtension; +import com.r3944realms.leashedplayer.modInterface.IPlayerRendererExtension; +import com.r3944realms.leashedplayer.modInterface.PlayerLeashable; +import net.minecraft.client.Camera; +import net.minecraft.client.Minecraft; +import net.minecraft.client.multiplayer.ClientLevel; +import net.minecraft.client.player.AbstractClientPlayer; +import net.minecraft.client.renderer.LightTexture; +import net.minecraft.client.renderer.MultiBufferSource; +import net.minecraft.client.renderer.RenderType; +import net.minecraft.client.renderer.entity.player.PlayerRenderer; +import net.minecraft.client.renderer.entity.state.PlayerRenderState; +import net.minecraft.core.BlockPos; +import net.minecraft.util.Mth; +import net.minecraft.world.entity.Entity; +import net.minecraft.world.entity.Leashable; +import net.minecraft.world.entity.decoration.LeashFenceKnotEntity; +import net.minecraft.world.entity.player.Player; +import net.minecraft.world.entity.vehicle.AbstractMinecart; +import net.minecraft.world.entity.vehicle.NewMinecartBehavior; +import net.minecraft.world.level.Level; +import net.minecraft.world.level.LightLayer; +import net.minecraft.world.phys.AABB; +import net.minecraft.world.phys.Vec3; +import org.joml.Matrix4f; + +import java.util.List; +import java.util.UUID; + +public class LeashRendererUtil { + /** + *

1. 角度与弧度转换

+ * {@snippet lang=java : + * double d0 = (double)(pEntity.getPreciseBodyRotation(pPartialTick) * (float)(Math.PI / 180.0)) + (Math.PI / 2); + * } + * + * + *

+ *

2. 三角函数计算位移

+ * {@snippet lang=java : + * double d1 = Math.cos(d0) * vec31.z + Math.sin(d0) * vec31.x; + * double d2 = Math.sin(d0) * vec31.z - Math.cos(d0) * vec31.x; + * } + * + *

+ *

3. 线性插值 (Lerp)

+ * {@snippet lang=java : + * double d3 = Mth.lerp(pPartialTick, pEntity.xo, pEntity.getX()) + d1; + * double d4 = Mth.lerp(pPartialTick, pEntity.yo, pEntity.getY()) + vec31.y; + * double d5 = Mth.lerp(pPartialTick, pEntity.zo, pEntity.getZ()) + d2; + * } + * + *

+ *

4. 向量差值

+ * {@snippet lang=java : + * float f = (float)(vec3.x - d3); + * float f1 = (float)(vec3.y - d4); + * float f2 = (float)(vec3.z - d5); + * } + * + *

+ *

5. 逆平方根与比例因子

+ * {@snippet lang=java : + * float f4 = Mth.invSqrt(f * f + f2 * f2) * 0.025F / 2.0F; + * } + * + *

+ *

6. 循环绘制

+ * {@snippet lang=java : + * for (int i1 = 0; i1 <= 24; i1++) { + * addVertexPair(vertexconsumer, matrix4f, f, f1, f2, i, j, k, l, 0.025F, 0.025F, f5, f6, i1, false); + * } + * } + * + *

+ *

总结

+ * 这些数学运算主要用于计算实体在三维空间中的位置和方向,以确保在渲染链状结构(如拴住的绳索)时,链条能够跟随实体的移动和旋转并正确显示。在图形编程中,这些计算非常常见,尤其是在处理旋转、插值和光照效果时。 + */ + + public static void renderLeash( + com.mojang.blaze3d.vertex.PoseStack poseStack, + net.minecraft.client.renderer.MultiBufferSource bufferSource, + PlayerRenderState playerRenderState + ) { + float f = 0.025F; + // 获得绳索持有者的位置 + PlayerLeashState leashState = ((IPlayerRenderStateExtension)playerRenderState).getPlayerLeashState(); + if (leashState == null) + return; + Vec3 Holder = leashState.pos; + Vec3 o = leashState.o; + // 计算实体的朝向角度(弧度) + float partialTick = playerRenderState.partialTick; + double entityRotationAngleRadians = (double)(leashState.getPreciseBodyRotation(partialTick) * (float) (Math.PI / 180.0)) + (Math.PI / 2); + // 计算实体的绳索偏移,此处add偏移让渲染拴绳显示在玩家头部下(大约在脖子处 + Vec3 cameraEntityLeashOffset = new Vec3(0.0, playerRenderState.eyeHeight , playerRenderState.boundingBoxWidth * 0.4F).add(0, 0, -0.2); + double leashOffsetX = Math.cos(entityRotationAngleRadians) * cameraEntityLeashOffset.z + Math.sin(entityRotationAngleRadians) * cameraEntityLeashOffset.x; + double leashOffsetZ = Math.sin(entityRotationAngleRadians) * cameraEntityLeashOffset.z - Math.cos(entityRotationAngleRadians) * cameraEntityLeashOffset.x; + // 计算实体当前的实际位置 + double entityPosX = Mth.lerp(partialTick, o.x, playerRenderState.x) + leashOffsetX; + double entityPosY = Mth.lerp(partialTick, o.y, playerRenderState.y) + cameraEntityLeashOffset.y; + double entityPosZ = Mth.lerp(partialTick, o.z, playerRenderState.z) + leashOffsetZ; + + // 计算绳索的相对位置差 + float deltaX = (float)(Holder.x - entityPosX); + float deltaY = (float)(Holder.y - entityPosY); + float deltaZ = (float)(Holder.z - entityPosZ); + // 计算比例因子,用于调节绳索的粗细 + float leashLengthRatio = Mth.invSqrt(deltaX * deltaX + deltaZ * deltaZ) * 0.025F / 2.0F; + // 计算比例因子,用于调节绳索的粗细 + float leashXZScaleX = deltaZ * leashLengthRatio; + float leashXZScaleZ = deltaX * leashLengthRatio; + poseStack.pushPose(); + poseStack.translate(leashState.offset); + VertexConsumer vertexconsumer = bufferSource.getBuffer(RenderType.leash()); + Matrix4f matrix4f = poseStack.last().pose(); + + for (int i = 0; i <= 24; i++) { + addVertexPair( + vertexconsumer, + matrix4f, + deltaX, + deltaY, + deltaZ, + leashState.startBlockLight, + leashState.endBlockLight, + leashState.startSkyLight, + leashState.endSkyLight, + 0.025F, + 0.025F, + leashXZScaleX, + leashXZScaleZ, + i, + false + ); + } + + for (int j = 24; j >= 0; j--) { + addVertexPair( + vertexconsumer, + matrix4f, + deltaX, + deltaY, + deltaZ, + leashState.startBlockLight, + leashState.endBlockLight, + leashState.startSkyLight, + leashState.endSkyLight, + 0.025F, + 0.0F, + leashXZScaleX, + leashXZScaleZ, + j, + true + ); + } + + poseStack.popPose(); + } + + protected static void addVertexPair( + VertexConsumer buffer, + Matrix4f pose, + float startX, + float startY, + float startZ, + int entityBlockLight, + int holderBlockLight, + int entitySkyLight, + int holderSkyLight, + float yOffset, + float dy, + float dx, + float dz, + int index, + boolean reverse + ) { + float f = (float)index / 24.0F; + int i = (int)Mth.lerp(f, (float)entityBlockLight, (float)holderBlockLight); + int j = (int)Mth.lerp(f, (float)entitySkyLight, (float)holderSkyLight); + int k = LightTexture.pack(i, j); + float f1 = index % 2 == (reverse ? 1 : 0) ? 0.7F : 1.0F; + float f2 = 0.5F * f1; + float f3 = 0.4F * f1; + float f4 = 0.3F * f1; + float f5 = startX * f; + float f6 = startY > 0.0F ? startY * f * f : startY - startY * (1.0F - f) * (1.0F - f); + float f7 = startZ * f; + buffer.addVertex(pose, f5 - dx, f6 + dy, f7 + dz).setColor(f2, f3, f4, 1.0F).setLight(k); + buffer.addVertex(pose, f5 + dx, f6 + yOffset - dy, f7 - dz).setColor(f2, f3, f4, 1.0F).setLight(k); + } + public static void renderLeashForCamera( + Camera camera, + float partialTick, + com.mojang.blaze3d.vertex.PoseStack poseStack, + net.minecraft.client.renderer.MultiBufferSource bufferSource, + E leashHolder, + Vec3 holderOffset + ) { + + poseStack.pushPose(); + + // 获得绳索持有者的位置 + Vec3 leashHolderPosition = leashHolder.getRopeHoldPosition(partialTick).add(holderOffset); + + // 获取当前观察的实体 + Entity cameraEntity = camera.getEntity(); + + // 计算实体的朝向角度(弧度) + double entityRotationAngleRadians = (double)(cameraEntity.getPreciseBodyRotation(partialTick) * (float) (Math.PI / 180.0)) + (Math.PI / 2); + + // 计算实体的绳索偏移,此处add偏移让渲染拴绳显示在玩家头部下(大约在脖子处 + Vec3 cameraEntityLeashOffset = cameraEntity.getLeashOffset(partialTick).add(0, -0.2, -0.5); + double leashOffsetX = Math.cos(entityRotationAngleRadians) * cameraEntityLeashOffset.z + Math.sin(entityRotationAngleRadians) * cameraEntityLeashOffset.x; + double leashOffsetZ = Math.sin(entityRotationAngleRadians) * cameraEntityLeashOffset.z - Math.cos(entityRotationAngleRadians) * cameraEntityLeashOffset.x; + + // 计算实体当前的实际位置 + double entityPosX = Mth.lerp(partialTick, cameraEntity.xo, cameraEntity.getX()) + leashOffsetX; + double entityPosY = Mth.lerp(partialTick, cameraEntity.yo, cameraEntity.getY()) + cameraEntityLeashOffset.y; + double entityPosZ = Mth.lerp(partialTick, cameraEntity.zo, cameraEntity.getZ()) + leashOffsetZ; + + // 在当前变换矩阵上应用偏移 + poseStack.translate(leashOffsetX, cameraEntityLeashOffset.y , leashOffsetZ); + + // 计算绳索的相对位置差 + float deltaX = (float)(leashHolderPosition.x - entityPosX); + float deltaY = (float)(leashHolderPosition.y - entityPosY); + float deltaZ = (float)(leashHolderPosition.z - entityPosZ); + + // 获取顶点消费者,用于绘制绳索 + VertexConsumer vertexConsumer = bufferSource.getBuffer(RenderType.leash()); + Matrix4f matrix = poseStack.last().pose(); + + // 计算比例因子,用于调节绳索的粗细 + float leashLengthRatio = Mth.invSqrt(deltaX * deltaX + deltaZ * deltaZ) * 0.025F / 2.0F; + float leashXZScaleX = deltaZ * leashLengthRatio; + float leashXZScaleZ = deltaX * leashLengthRatio; + + // 获取光照信息 + BlockPos cameraEntityBlockPos = BlockPos.containing(cameraEntity.getEyePosition(partialTick)); + BlockPos leashHolderBlockPos = BlockPos.containing(leashHolder.getEyePosition(partialTick)); + int cameraEntityBlockLightLevel = 15; + int leashHolderBlockLightLevel = 0; //getBlockLightLevel(leashHolder, leashHolderBlockPos); + int cameraEntitySkyLightLevel = cameraEntity.level().getBrightness(LightLayer.SKY, cameraEntityBlockPos); + int leashHolderSkyLightLevel = cameraEntity.level().getBrightness(LightLayer.SKY, leashHolderBlockPos); + + // 绘制绳索的上半部分 + for (int segment = 0; segment <= 24; segment++) { + addVertexPair(vertexConsumer, matrix, deltaX, deltaY, deltaZ, cameraEntityBlockLightLevel, leashHolderBlockLightLevel, cameraEntitySkyLightLevel, leashHolderSkyLightLevel, 0.025F, 0.025F, leashXZScaleX, leashXZScaleZ, segment, false); + } + + // 绘制绳索的下半部分 + for (int segment = 24; segment >= 0; segment--) { + addVertexPair(vertexConsumer, matrix, deltaX, deltaY, deltaZ, cameraEntityBlockLightLevel, leashHolderBlockLightLevel, cameraEntitySkyLightLevel, leashHolderSkyLightLevel, 0.025F, 0.0F, leashXZScaleX, leashXZScaleZ, segment, true); + } + + poseStack.popPose(); + } + public static void levelRenderLeash(ClientLevel level, Camera pCamera, PoseStack poseStack, MultiBufferSource.BufferSource multibuffersource$buffersource) { + for(Entity entity : level.entitiesForRendering()) { + //对于玩家实体拴绳渲染(从第一人称视角) + if (entity instanceof AbstractClientPlayer abstractClientPlayer) { + if(!(pCamera.getEntity() instanceof AbstractClientPlayer)) continue; + Minecraft mc = Minecraft.getInstance(); + PlayerRenderer playerRenderer = (PlayerRenderer) mc.getEntityRenderDispatcher().getRenderer(abstractClientPlayer); + IPlayerRendererExtension playerRendererExtension = (IPlayerRendererExtension) playerRenderer; + if (mc.options.getCameraType().isFirstPerson()) { + Leashable.LeashData leashDataFromEntityData = ((PlayerLeashable) abstractClientPlayer).getLeashDataFromEntityData(); + if(leashDataFromEntityData == null) continue; + Either delayedLeashInfo = leashDataFromEntityData.delayedLeashInfo; + if(delayedLeashInfo != null) { + float partialTickTime = pCamera.getPartialTickTime(); + Vec3 position = pCamera.getPosition(); + double dX = Mth.lerp(partialTickTime, abstractClientPlayer.xOld, abstractClientPlayer.getX()) - position.x; + double dY = Mth.lerp(partialTickTime, abstractClientPlayer.yOld, abstractClientPlayer.getY()) - position.y; + double dZ = Mth.lerp(partialTickTime, abstractClientPlayer.zOld, abstractClientPlayer.getZ()) - position.z; + Vec3 vec3 = getRenderOffset(entity, partialTickTime); + double dX_ = dX + vec3.x(); + double dY_ = dY + vec3.y(); + double dZ_ = dZ + vec3.z(); + poseStack.pushPose(); + poseStack.translate(dX_, dY_, dZ_); + if (delayedLeashInfo.right().isPresent() && delayedLeashInfo.left().isEmpty()) { + renderLeashForCamera(pCamera, partialTickTime, poseStack, multibuffersource$buffersource, LeashFenceKnotEntity.getOrCreateKnot(level, delayedLeashInfo.right().get()), Vec3.ZERO); + } else if (delayedLeashInfo.right().isEmpty() && delayedLeashInfo.left().isPresent()) { + Player playerByUUID = level.getPlayerByUUID(delayedLeashInfo.left().get()); + if (playerByUUID != null) { + renderLeashForCamera(pCamera, partialTickTime, poseStack, multibuffersource$buffersource, playerByUUID, Vec3.ZERO); + } else { + double MaxLeashLength = ((ILivingEntityExtension) abstractClientPlayer).getLeashLength() * LeashedPlayer.M1() * LeashedPlayer.M2(); + List entities = level.getEntities( + null, + new AABB( + abstractClientPlayer.getX() - MaxLeashLength, + abstractClientPlayer.getY() - MaxLeashLength, + abstractClientPlayer.getZ() - MaxLeashLength, + abstractClientPlayer.getX() + MaxLeashLength, + abstractClientPlayer.getY() + MaxLeashLength, + abstractClientPlayer.getZ() + MaxLeashLength + ) + ); + Entity holder = null; + for (Entity entity_ : entities) { + if(entity_.getUUID().equals(delayedLeashInfo.left().get())) { + holder = entity_; + break; + } + } + if (holder != null) { + if(holder instanceof LeashRopeArrow) { + renderLeashForCamera(pCamera, partialTickTime, poseStack, multibuffersource$buffersource, holder, new Vec3(0.,-0.09, 0));//TODO: 待擴展Vec3吗? + } + else renderLeashForCamera(pCamera, partialTickTime, poseStack, multibuffersource$buffersource, holder, Vec3.ZERO); + } + } + break; + } + + } + } + } + } + } + public static Vec3 getRenderOffset(Entity entity, float partialTickTime) { + Vec3 ret = Vec3.ZERO; + if(entity.isPassenger() + && entity.getVehicle() instanceof AbstractMinecart abstractminecart + && abstractminecart.getBehavior() instanceof NewMinecartBehavior newminecartbehavior + && newminecartbehavior.cartHasPosRotLerp() + ) { + double d2 = Mth.lerp(partialTickTime, abstractminecart.xOld, abstractminecart.getX()); + double d0 = Mth.lerp(partialTickTime, abstractminecart.yOld, abstractminecart.getY()); + double d1 = Mth.lerp(partialTickTime, abstractminecart.zOld, abstractminecart.getZ()); + ret = newminecartbehavior.getCartLerpPosition(partialTickTime).subtract(new Vec3(d2, d0, d1)); + } + return ret; + } +} diff --git a/src/main/java/com/r3944realms/leashedplayer/client/renders/PlayerLeashState.java b/src/main/java/com/r3944realms/leashedplayer/client/renders/PlayerLeashState.java new file mode 100644 index 0000000..93cc1ed --- /dev/null +++ b/src/main/java/com/r3944realms/leashedplayer/client/renders/PlayerLeashState.java @@ -0,0 +1,30 @@ +package com.r3944realms.leashedplayer.client.renders; + +import net.minecraft.util.Mth; +import net.minecraft.world.phys.Vec3; + +public class PlayerLeashState { + public Vec3 o, pos, offset; + public float yRotO, yRot; + public int startBlockLight; + public int endBlockLight; + public int startSkyLight; + public int endSkyLight; + + public float getPreciseBodyRotation(float pPartialTick) { + return Mth.lerp(pPartialTick, this.yRotO, this.yRot); + } + + + public PlayerLeashState() { + this.offset = Vec3.ZERO; + this.o = Vec3.ZERO; + this.pos = Vec3.ZERO; + this.yRot = 0.0f; + this.yRotO = 0.0f; + this.startBlockLight = 0; + this.endBlockLight = 0; + this.startSkyLight = 15; + this.endSkyLight = 15; + } +} diff --git a/src/main/java/com/r3944realms/leashedplayer/client/renders/entities/LeashRopeArrowRenderer.java b/src/main/java/com/r3944realms/leashedplayer/client/renders/entities/LeashRopeArrowRenderer.java index 1640127..c13fbf0 100644 --- a/src/main/java/com/r3944realms/leashedplayer/client/renders/entities/LeashRopeArrowRenderer.java +++ b/src/main/java/com/r3944realms/leashedplayer/client/renders/entities/LeashRopeArrowRenderer.java @@ -4,20 +4,27 @@ import com.r3944realms.leashedplayer.LeashedPlayer; import com.r3944realms.leashedplayer.content.entities.LeashRopeArrow; import net.minecraft.client.renderer.entity.ArrowRenderer; import net.minecraft.client.renderer.entity.EntityRendererProvider; +import net.minecraft.client.renderer.entity.state.ArrowRenderState; import net.minecraft.resources.ResourceLocation; import net.neoforged.api.distmarker.Dist; import net.neoforged.api.distmarker.OnlyIn; import org.jetbrains.annotations.NotNull; @OnlyIn(Dist.CLIENT) -public class LeashRopeArrowRenderer extends ArrowRenderer { +public class LeashRopeArrowRenderer extends ArrowRenderer { public static final ResourceLocation LEASH_ROPE_ARROW = ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "textures/entity/projectiles/leash_rope_arrow.png"); public LeashRopeArrowRenderer(EntityRendererProvider.Context pContext) { super(pContext); } @Override - public @NotNull ResourceLocation getTextureLocation(@NotNull LeashRopeArrow pEntity) { + public @NotNull ArrowRenderState createRenderState() { + return new ArrowRenderState(); + } + + @Override + protected @NotNull ResourceLocation getTextureLocation(@NotNull ArrowRenderState arrowRenderState) { return LEASH_ROPE_ARROW; } + } diff --git a/src/main/java/com/r3944realms/leashedplayer/client/renders/entities/SpectralLeashRopeArrowRenderer.java b/src/main/java/com/r3944realms/leashedplayer/client/renders/entities/SpectralLeashRopeArrowRenderer.java index 47db288..f306911 100644 --- a/src/main/java/com/r3944realms/leashedplayer/client/renders/entities/SpectralLeashRopeArrowRenderer.java +++ b/src/main/java/com/r3944realms/leashedplayer/client/renders/entities/SpectralLeashRopeArrowRenderer.java @@ -4,20 +4,28 @@ import com.r3944realms.leashedplayer.LeashedPlayer; import com.r3944realms.leashedplayer.content.entities.SpectralLeashRopeArrow; import net.minecraft.client.renderer.entity.ArrowRenderer; import net.minecraft.client.renderer.entity.EntityRendererProvider; +import net.minecraft.client.renderer.entity.state.ArrowRenderState; import net.minecraft.resources.ResourceLocation; import net.neoforged.api.distmarker.Dist; import net.neoforged.api.distmarker.OnlyIn; import org.jetbrains.annotations.NotNull; @OnlyIn(Dist.CLIENT) -public class SpectralLeashRopeArrowRenderer extends ArrowRenderer { +public class SpectralLeashRopeArrowRenderer extends ArrowRenderer { public static final ResourceLocation SPECTRAL_LEASH_ROPE_ARROW = ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "textures/entity/projectiles/spectral_leash_rope_arrow.png"); public SpectralLeashRopeArrowRenderer(EntityRendererProvider.Context pContext) { super(pContext); } + @Override - public @NotNull ResourceLocation getTextureLocation(@NotNull SpectralLeashRopeArrow pEntity) { + public @NotNull ArrowRenderState createRenderState() { + return new ArrowRenderState(); + } + + @Override + protected @NotNull ResourceLocation getTextureLocation(@NotNull ArrowRenderState arrowRenderState) { return SPECTRAL_LEASH_ROPE_ARROW; } + } diff --git a/src/main/java/com/r3944realms/leashedplayer/content/entities/ModEntityRegister.java b/src/main/java/com/r3944realms/leashedplayer/content/entities/ModEntityRegister.java index 75c067f..5a64912 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/entities/ModEntityRegister.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/entities/ModEntityRegister.java @@ -2,6 +2,8 @@ package com.r3944realms.leashedplayer.content.entities; import com.r3944realms.leashedplayer.LeashedPlayer; import net.minecraft.core.registries.Registries; +import net.minecraft.resources.ResourceKey; +import net.minecraft.resources.ResourceLocation; import net.minecraft.world.entity.EntityType; import net.minecraft.world.entity.MobCategory; import net.neoforged.bus.api.IEventBus; @@ -17,7 +19,7 @@ public class ModEntityRegister { .eyeHeight(0.13F) .clientTrackingRange(4) .updateInterval(20) - .build("leash_rope_arrow") + .build(ResourceKey.create(Registries.ENTITY_TYPE, ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "leash_rope_arrow"))) ); public static final DeferredHolder, EntityType> SPECTRAL_LEASH_ROPE_ARROW = ENTITY_TYPE.register( "spectral_leash_rope_arrow", @@ -26,7 +28,7 @@ public class ModEntityRegister { .eyeHeight(0.13F) .clientTrackingRange(4) .updateInterval(20) - .build("spectral_leash_rope_arrow") + .build(ResourceKey.create(Registries.ENTITY_TYPE, ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "spectral_leash_rope_arrow"))) ); // public static final DeferredHolder, EntityType> CHAIN_TIE = ENTITY_TYPE.register( // "chain_tie", diff --git a/src/main/java/com/r3944realms/leashedplayer/content/entities/SpectralLeashRopeArrow.java b/src/main/java/com/r3944realms/leashedplayer/content/entities/SpectralLeashRopeArrow.java index 2b4e376..54aa388 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/entities/SpectralLeashRopeArrow.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/entities/SpectralLeashRopeArrow.java @@ -33,7 +33,7 @@ public class SpectralLeashRopeArrow extends LeashRopeArrow { @Override public void tick() { super.tick(); - if (this.level().isClientSide && !this.inGround) { + if (this.level().isClientSide && !this.isInGround()) { this.level().addParticle(ParticleTypes.INSTANT_EFFECT, this.getX(), this.getY(), this.getZ(), 0.0, 0.0, 0.0); } } diff --git a/src/main/java/com/r3944realms/leashedplayer/content/gamerules/GameruleRegistry.java b/src/main/java/com/r3944realms/leashedplayer/content/gamerules/GameruleRegistry.java index 9e79968..3d20ee7 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/gamerules/GameruleRegistry.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/gamerules/GameruleRegistry.java @@ -1,6 +1,8 @@ package com.r3944realms.leashedplayer.content.gamerules; import net.minecraft.server.MinecraftServer; +import net.minecraft.server.level.ServerLevel; +import net.minecraft.world.flag.FeatureFlagSet; import net.minecraft.world.level.GameRules; import net.minecraft.world.level.Level; @@ -25,7 +27,7 @@ public enum GameruleRegistry { if (gameruleDataTypes.get(gameruleName) != RuleDataType.BOOLEAN) { return false; } - return level.getGameRules().getBoolean((GameRules.Key) gamerules.get(gameruleName)); + return ((ServerLevel)level).getGameRules().getBoolean((GameRules.Key) gamerules.get(gameruleName)); } @SuppressWarnings("unchecked") public static Integer getGameruleIntValue(Level level, String gameruleName) { @@ -35,7 +37,7 @@ public enum GameruleRegistry { if (gameruleDataTypes.get(gameruleName) != RuleDataType.INTEGER) { return 0; } - return level.getGameRules().getInt((GameRules.Key)gamerules.get(gameruleName)); + return ((ServerLevel)level).getGameRules().getInt((GameRules.Key)gamerules.get(gameruleName)); } public void registerGamerule(String gameruleName, GameRules.Category category, boolean pDefault) { @@ -53,7 +55,7 @@ public enum GameruleRegistry { gameruleDataTypes.put(gameruleName, RuleDataType.INTEGER); } public void registerGamerule(String gameruleName, GameRules.Category category, int pDefault, int pMin, int pMax, BiConsumer pChangeListener) { - gamerules.put(gameruleName, GameRules.register(gameruleName, category, GameRules.IntegerValue.create(pDefault, pMin, pMax, pChangeListener))); + gamerules.put(gameruleName, GameRules.register(gameruleName, category, GameRules.IntegerValue.create(pDefault, pMin, pMax, FeatureFlagSet.of(), pChangeListener))); gameruleDataTypes.put(gameruleName, RuleDataType.INTEGER); } public void registerGamerule(String gameruleName, GameRules.Category category,float value) { diff --git a/src/main/java/com/r3944realms/leashedplayer/content/gamerules/Gamerules.java b/src/main/java/com/r3944realms/leashedplayer/content/gamerules/Gamerules.java index ffab49c..316beca 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/gamerules/Gamerules.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/gamerules/Gamerules.java @@ -4,6 +4,7 @@ import com.mojang.brigadier.arguments.FloatArgumentType; import com.mojang.brigadier.context.CommandContext; import net.minecraft.commands.CommandSourceStack; import net.minecraft.server.MinecraftServer; +import net.minecraft.world.flag.FeatureFlagSet; import net.minecraft.world.level.GameRules; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; @@ -38,7 +39,8 @@ public class Gamerules { (FloatArgumentType::floatArg, pType -> new FloatValue(pType, pDefaultValue), pChangeListener, - GameRules.GameRuleTypeVisitor::visit + GameRules.GameRuleTypeVisitor::visit, + FeatureFlagSet.of() ); } public static GameRules.Type create( @@ -48,7 +50,8 @@ public class Gamerules { () -> FloatArgumentType.floatArg(pMin, pMax), pType -> new FloatValue(pType, pDefaultValue), pChangeListener, - GameRules.GameRuleTypeVisitor::visit + GameRules.GameRuleTypeVisitor::visit, + FeatureFlagSet.of() ); } public FloatValue(GameRules.Type pType, float value) { diff --git a/src/main/java/com/r3944realms/leashedplayer/content/items/ModItemRegister.java b/src/main/java/com/r3944realms/leashedplayer/content/items/ModItemRegister.java index 375c5f3..6c22755 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/items/ModItemRegister.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/items/ModItemRegister.java @@ -5,6 +5,9 @@ import com.r3944realms.leashedplayer.content.items.type.LeashRopeArrowItem; import com.r3944realms.leashedplayer.content.items.type.SpectralLeashRopeArrowItem; import com.r3944realms.leashedplayer.content.items.type.TestItem; import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.core.registries.Registries; +import net.minecraft.resources.ResourceKey; +import net.minecraft.resources.ResourceLocation; import net.minecraft.world.item.Item; import net.neoforged.bus.api.IEventBus; import net.neoforged.neoforge.registries.DeferredRegister; @@ -24,8 +27,8 @@ public class ModItemRegister { () -> new SpectralLeashRopeArrowItem(new Item.Properties().stacksTo(16))); public static final Supplier FABRIC = ModItemRegister.register("fabric", - () -> new TestItem(new Item.Properties().stacksTo(1)) - ); + () -> new TestItem(new Item.Properties().stacksTo(1) + .setId(ResourceKey.create(Registries.ITEM, ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "fabric"))))); public static Supplier register(String name, Supplier supplier) { return register(name, supplier, true); diff --git a/src/main/java/com/r3944realms/leashedplayer/content/items/type/LeashRopeArrowItem.java b/src/main/java/com/r3944realms/leashedplayer/content/items/type/LeashRopeArrowItem.java index 58b8089..6b67624 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/items/type/LeashRopeArrowItem.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/items/type/LeashRopeArrowItem.java @@ -1,11 +1,15 @@ package com.r3944realms.leashedplayer.content.items.type; +import com.r3944realms.leashedplayer.LeashedPlayer; import com.r3944realms.leashedplayer.content.entities.LeashRopeArrow; import com.r3944realms.leashedplayer.content.entities.ModEntityRegister; import net.minecraft.ChatFormatting; import net.minecraft.core.Direction; import net.minecraft.core.Position; +import net.minecraft.core.registries.Registries; import net.minecraft.network.chat.Component; +import net.minecraft.resources.ResourceKey; +import net.minecraft.resources.ResourceLocation; import net.minecraft.world.entity.LivingEntity; import net.minecraft.world.entity.projectile.AbstractArrow; import net.minecraft.world.entity.projectile.Projectile; @@ -22,7 +26,7 @@ import java.util.List; public class LeashRopeArrowItem extends ArrowItem implements ILeashRopeArrow{ public static final String descKey = "item.leash_rope_arrow.description"; public LeashRopeArrowItem(Item.Properties pProperties) { - super(pProperties); + super(pProperties.setId(ResourceKey.create(Registries.ITEM, ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "leash_rope_arrow")))) ; } public @NotNull AbstractArrow createArrow(@NotNull Level pLevel, @NotNull ItemStack pAmmo, @NotNull LivingEntity pShooter, @Nullable ItemStack pWeapon) { @@ -36,7 +40,7 @@ public class LeashRopeArrowItem extends ArrowItem implements ILeashRopeArrow{ return arrow; } - @Override + public @NotNull Component getDescription() { return Component.translatable(descKey).withStyle(ChatFormatting.GRAY); } diff --git a/src/main/java/com/r3944realms/leashedplayer/content/items/type/SpectralLeashRopeArrowItem.java b/src/main/java/com/r3944realms/leashedplayer/content/items/type/SpectralLeashRopeArrowItem.java index bcf7a44..bce1101 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/items/type/SpectralLeashRopeArrowItem.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/items/type/SpectralLeashRopeArrowItem.java @@ -1,12 +1,16 @@ package com.r3944realms.leashedplayer.content.items.type; +import com.r3944realms.leashedplayer.LeashedPlayer; import com.r3944realms.leashedplayer.content.entities.LeashRopeArrow; import com.r3944realms.leashedplayer.content.entities.ModEntityRegister; import com.r3944realms.leashedplayer.content.entities.SpectralLeashRopeArrow; import net.minecraft.ChatFormatting; import net.minecraft.core.Direction; import net.minecraft.core.Position; +import net.minecraft.core.registries.Registries; import net.minecraft.network.chat.Component; +import net.minecraft.resources.ResourceKey; +import net.minecraft.resources.ResourceLocation; import net.minecraft.world.entity.LivingEntity; import net.minecraft.world.entity.projectile.AbstractArrow; import net.minecraft.world.entity.projectile.Projectile; @@ -23,7 +27,7 @@ import java.util.List; public class SpectralLeashRopeArrowItem extends ArrowItem implements ILeashRopeArrow{ public static final String descKey = "item.spectral_leash_rope_arrow.description"; public SpectralLeashRopeArrowItem(Properties pProperties) { - super(pProperties); + super(pProperties.setId(ResourceKey.create(Registries.ITEM, ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "spectral_leash_rope_arrow")))); } public @NotNull AbstractArrow createArrow(@NotNull Level pLevel, @NotNull ItemStack pAmmo, @NotNull LivingEntity pShooter, @Nullable ItemStack pWeapon) { return new SpectralLeashRopeArrow(ModEntityRegister.SPECTRAL_LEASH_ROPE_ARROW.get(), pShooter, pLevel, pAmmo.copyWithCount(1), pWeapon); @@ -36,7 +40,6 @@ public class SpectralLeashRopeArrowItem extends ArrowItem implements ILeashRopeA return arrow; } - @Override public @NotNull Component getDescription() { return Component.translatable(descKey).withStyle(ChatFormatting.GRAY); } diff --git a/src/main/java/com/r3944realms/leashedplayer/content/items/type/TestItem.java b/src/main/java/com/r3944realms/leashedplayer/content/items/type/TestItem.java index b5f7f41..bf255b0 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/items/type/TestItem.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/items/type/TestItem.java @@ -7,10 +7,9 @@ import com.r3944realms.leashedplayer.client.renders.gui.IFadingProcessBarRendere import com.r3944realms.leashedplayer.client.renders.gui.IProcessBarRenderer; import com.r3944realms.leashedplayer.client.renders.gui.TestProcessBarRenderer; import net.minecraft.world.InteractionHand; -import net.minecraft.world.InteractionResultHolder; +import net.minecraft.world.InteractionResult; import net.minecraft.world.entity.player.Player; import net.minecraft.world.item.Item; -import net.minecraft.world.item.ItemStack; import net.minecraft.world.level.Level; import org.jetbrains.annotations.NotNull; @@ -21,7 +20,7 @@ public class TestItem extends Item { } @Override - public @NotNull InteractionResultHolder use(@NotNull Level pLevel, @NotNull Player pPlayer, @NotNull InteractionHand pUsedHand) { + public @NotNull InteractionResult use(@NotNull Level pLevel, @NotNull Player pPlayer, @NotNull InteractionHand pUsedHand) { if(!pLevel.isClientSide()){ //some lo } diff --git a/src/main/java/com/r3944realms/leashedplayer/content/paintings/ModPaintingsRegister.java b/src/main/java/com/r3944realms/leashedplayer/content/paintings/ModPaintingsRegister.java index 940052e..2cb87e4 100644 --- a/src/main/java/com/r3944realms/leashedplayer/content/paintings/ModPaintingsRegister.java +++ b/src/main/java/com/r3944realms/leashedplayer/content/paintings/ModPaintingsRegister.java @@ -1,19 +1,22 @@ package com.r3944realms.leashedplayer.content.paintings; import com.r3944realms.leashedplayer.LeashedPlayer; +import com.r3944realms.leashedplayer.datagen.provider.attributes.ModPaintingVariants; import net.minecraft.core.registries.Registries; +import net.minecraft.network.chat.Component; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.entity.decoration.PaintingVariant; import net.neoforged.bus.api.IEventBus; import net.neoforged.neoforge.registries.DeferredRegister; import org.jetbrains.annotations.NotNull; +import java.util.Optional; import java.util.function.Supplier; public class ModPaintingsRegister { public static final DeferredRegister PAINTING_VARIANT = DeferredRegister.create(Registries.PAINTING_VARIANT, LeashedPlayer.MOD_ID); - public static final Supplier GROUP_PHOTO = PAINTING_VARIANT.register("group_photo", () -> new PaintingVariant(1920, 1080, getAssetId("group_photo"))); + public static final Supplier GROUP_PHOTO = PAINTING_VARIANT.register("group_photo", () -> new PaintingVariant(1920, 1080, getAssetId("group_photo"), Optional.of(Component.translatable(ModPaintingVariants.getPaintingVariantTitleKey(ModPaintingVariants.GROUP_PHOTO))), Optional.of(Component.translatable(ModPaintingVariants.getPaintingVariantAuthorKey(ModPaintingVariants.GROUP_PHOTO))))); private static @NotNull ResourceLocation getAssetId( String paint_name) { return ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "textures/painting/"+paint_name+".png"); diff --git a/src/main/java/com/r3944realms/leashedplayer/datagen/ModDataGeneratorHandler.java b/src/main/java/com/r3944realms/leashedplayer/datagen/ModDataGeneratorHandler.java index 1590c94..5854830 100644 --- a/src/main/java/com/r3944realms/leashedplayer/datagen/ModDataGeneratorHandler.java +++ b/src/main/java/com/r3944realms/leashedplayer/datagen/ModDataGeneratorHandler.java @@ -5,6 +5,7 @@ import com.r3944realms.leashedplayer.datagen.provider.*; import com.r3944realms.leashedplayer.utils.Enum.LanguageEnum; import net.minecraft.core.HolderLookup; import net.minecraft.data.DataProvider; +import net.minecraft.data.PackOutput; import net.neoforged.bus.api.SubscribeEvent; import net.neoforged.fml.common.EventBusSubscriber; import net.neoforged.neoforge.common.data.ExistingFileHelper; @@ -17,7 +18,6 @@ public class ModDataGeneratorHandler { @SubscribeEvent public static void genData(GatherDataEvent event) { CompletableFuture holderFolder = event.getLookupProvider(); - ExistingFileHelper existingFileHelper = event.getExistingFileHelper(); /*Language Provider ENGLISH CHINESE(SIM/TRA)*/ addLanguage(event, LanguageEnum.English); @@ -44,9 +44,10 @@ public class ModDataGeneratorHandler { ); } private static void RecipeGenerator(GatherDataEvent event, CompletableFuture future) { + PackOutput packOutput = event.getGenerator().getPackOutput(); event.getGenerator().addProvider( event.includeServer(), - (DataProvider.Factory) pOutput -> new ModRecipeProvider(pOutput, future) + new ModRecipeProvider.Runner(packOutput, future) ); } private static void ModTagsProvider(GatherDataEvent event, CompletableFuture completableFuture, ExistingFileHelper helper) { diff --git a/src/main/java/com/r3944realms/leashedplayer/datagen/generator/ModAdvancementGenerator.java b/src/main/java/com/r3944realms/leashedplayer/datagen/generator/ModAdvancementGenerator.java index 2d758fd..888c240 100644 --- a/src/main/java/com/r3944realms/leashedplayer/datagen/generator/ModAdvancementGenerator.java +++ b/src/main/java/com/r3944realms/leashedplayer/datagen/generator/ModAdvancementGenerator.java @@ -10,7 +10,9 @@ import net.minecraft.advancements.Advancement; import net.minecraft.advancements.AdvancementHolder; import net.minecraft.advancements.AdvancementType; import net.minecraft.advancements.critereon.*; +import net.minecraft.core.HolderGetter; import net.minecraft.core.HolderLookup; +import net.minecraft.core.registries.Registries; import net.minecraft.network.chat.Component; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.entity.EntityType; @@ -26,6 +28,7 @@ public class ModAdvancementGenerator implements AdvancementProvider.AdvancementG private final ResourceLocation ADV_BG = ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, "textures/gui/advancements/backgrounds/leashed_player.png"); @Override public void generate(HolderLookup.@NotNull Provider registries, @NotNull Consumer saver, @NotNull ExistingFileHelper existingFileHelper) { + HolderGetter> holdergetter = registries.lookupOrThrow(Registries.ENTITY_TYPE); AdvancementHolder hasLeashRopeItem = Advancement.Builder.advancement().display( Items.LEAD, Component.translatable(ModAdvancementKey.LEASH_START.getNameKey()), @@ -74,7 +77,7 @@ public class ModAdvancementGenerator implements AdvancementProvider.AdvancementG true, true ).addCriterion("leash_self", LeashPlayerTrigger.TriggerInstance.LeashPlayer( - EntityPredicate.Builder.entity().entityType(EntityTypePredicate.of(EntityType.LEASH_KNOT)) + EntityPredicate.Builder.entity().entityType(EntityTypePredicate.of(holdergetter, EntityType.LEASH_KNOT)) )) .parent(hasLeashRopeItem).save(saver, ModAdvancementKey.LEASHED_SELF.getNameWithNameSpace()); AdvancementHolder followLeashRopeArrow = Advancement.Builder.advancement().display( @@ -87,7 +90,7 @@ public class ModAdvancementGenerator implements AdvancementProvider.AdvancementG false, true ).addCriterion("leash_arrow", LeashPlayerTrigger.TriggerInstance.LeashPlayer( - EntityPredicate.Builder.entity().entityType(EntityTypePredicate.of(ModEntityRegister.LEASH_ROPE_ARROW.get())) + EntityPredicate.Builder.entity().entityType(EntityTypePredicate.of(holdergetter, ModEntityRegister.LEASH_ROPE_ARROW.get())) )) .parent(hasLeashRopeArrow) .save(saver, ModAdvancementKey.FOLLOW_LEASH_ARROW.getNameWithNameSpace()); @@ -101,7 +104,7 @@ public class ModAdvancementGenerator implements AdvancementProvider.AdvancementG true, true ).addCriterion("leash_by_wo_do", LeashPlayerTrigger.TriggerInstance.LeashPlayer( - EntityPredicate.Builder.entity().entityType(EntityTypePredicate.of(EntityType.WOLF)) + EntityPredicate.Builder.entity().entityType(EntityTypePredicate.of(holdergetter, EntityType.WOLF)) )) .parent(hasLeashRopeArrow).save(saver, ModAdvancementKey.DOG_RUNNING_PLAYER.getNameWithNameSpace()); @@ -116,7 +119,7 @@ public class ModAdvancementGenerator implements AdvancementProvider.AdvancementG true ).addCriterion("leash_other_player", LeashPlayerTrigger.TriggerInstance.LeashPlayer( - EntityPredicate.Builder.entity().entityType(EntityTypePredicate.of(EntityType.PLAYER)) + EntityPredicate.Builder.entity().entityType(EntityTypePredicate.of(holdergetter, EntityType.PLAYER)) ) ) .parent(hasLeashRopeItem).save(saver, ModAdvancementKey.LEASHED_FRIEND.getNameWithNameSpace()); diff --git a/src/main/java/com/r3944realms/leashedplayer/datagen/provider/ModRecipeProvider.java b/src/main/java/com/r3944realms/leashedplayer/datagen/provider/ModRecipeProvider.java index 0e0a75a..d5afabb 100644 --- a/src/main/java/com/r3944realms/leashedplayer/datagen/provider/ModRecipeProvider.java +++ b/src/main/java/com/r3944realms/leashedplayer/datagen/provider/ModRecipeProvider.java @@ -1,34 +1,36 @@ package com.r3944realms.leashedplayer.datagen.provider; import com.r3944realms.leashedplayer.content.items.ModItemRegister; +import net.minecraft.core.HolderGetter; import net.minecraft.core.HolderLookup; import net.minecraft.data.PackOutput; import net.minecraft.data.recipes.*; +import net.minecraft.data.recipes.packs.VanillaRecipeProvider; +import net.minecraft.world.item.Item; import net.minecraft.world.item.Items; import org.jetbrains.annotations.NotNull; import java.util.concurrent.CompletableFuture; public class ModRecipeProvider extends RecipeProvider { - public ModRecipeProvider(PackOutput pOutput, CompletableFuture future) { - super(pOutput, future); + public ModRecipeProvider(HolderLookup.Provider registries, RecipeOutput output) { + super(registries, output); } @Override - protected void buildRecipes(@NotNull RecipeOutput pRecipeOutput) { - - ShapelessRecipeBuilder.shapeless(RecipeCategory.MISC, ModItemRegister.LEASH_ROPE_ARROW.get(),1) + protected void buildRecipes() { + this.shapeless(RecipeCategory.MISC, ModItemRegister.LEASH_ROPE_ARROW.get(), 1) .requires(Items.LEAD) .requires(Items.ARROW) .unlockedBy("has_lead",has(Items.LEAD)) - .save(pRecipeOutput); - ShapelessRecipeBuilder.shapeless(RecipeCategory.MISC, ModItemRegister.SPECTRAL_LEASH_ROPE_ARROW.get(),1) + .save(this.output); + this.shapeless(RecipeCategory.MISC, ModItemRegister.SPECTRAL_LEASH_ROPE_ARROW.get(),1) .requires(Items.LEAD) .requires(Items.SPECTRAL_ARROW) .unlockedBy("has_lead",has(Items.LEAD)) .unlockedBy("has_spectral_arrow",has(Items.SPECTRAL_ARROW)) - .save(pRecipeOutput, "spectral_leash_rope_arrow_with_leash_rope_arrow"); - ShapedRecipeBuilder.shaped(RecipeCategory.MISC, ModItemRegister.SPECTRAL_LEASH_ROPE_ARROW.get(),1) + .save(this.output); + this.shaped(RecipeCategory.MISC, ModItemRegister.SPECTRAL_LEASH_ROPE_ARROW.get(),1) .pattern(" $ ") .pattern("$#$") .pattern(" $ ") @@ -36,7 +38,24 @@ public class ModRecipeProvider extends RecipeProvider { .define('$', Items.GLOWSTONE_DUST) .unlockedBy("has_lead",has(Items.LEAD)) .unlockedBy("has_glowstone_dust",has(Items.GLOWSTONE_DUST)) - .save(pRecipeOutput,"spectral_leash_rope_arrow_with_glowstone_dust"); + .save(this.output,"2"); + } + public static class Runner extends RecipeProvider.Runner { + + public Runner(PackOutput pPackOutput, CompletableFuture providerCompletableFuture) { + super(pPackOutput, providerCompletableFuture); + } + + @Override + @NotNull + public RecipeProvider createRecipeProvider(HolderLookup.@NotNull Provider provider, @NotNull RecipeOutput output) { + return new ModRecipeProvider(provider, output); + } + + @Override + public @NotNull String getName() { + return "LeashedPlayer Recipes"; + } } diff --git a/src/main/java/com/r3944realms/leashedplayer/datagen/provider/attributes/ModPaintingVariants.java b/src/main/java/com/r3944realms/leashedplayer/datagen/provider/attributes/ModPaintingVariants.java index 17f4942..92df3e3 100644 --- a/src/main/java/com/r3944realms/leashedplayer/datagen/provider/attributes/ModPaintingVariants.java +++ b/src/main/java/com/r3944realms/leashedplayer/datagen/provider/attributes/ModPaintingVariants.java @@ -3,10 +3,13 @@ package com.r3944realms.leashedplayer.datagen.provider.attributes; import com.r3944realms.leashedplayer.LeashedPlayer; import net.minecraft.core.registries.Registries; import net.minecraft.data.worldgen.BootstrapContext; +import net.minecraft.network.chat.Component; import net.minecraft.resources.ResourceKey; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.entity.decoration.PaintingVariant; +import java.util.Optional; + public class ModPaintingVariants { public static final ResourceKey GROUP_PHOTO = create("group_photo"); @@ -14,10 +17,10 @@ public class ModPaintingVariants { PaintingVariantBootstrap(pContext); } public static void PaintingVariantBootstrap(BootstrapContext pContext) { - ModPaintingVariants.register(pContext, ModPaintingVariants.GROUP_PHOTO, 4, 3); + ModPaintingVariants.register(pContext, ModPaintingVariants.GROUP_PHOTO, 4, 3, Component.translatable(ModPaintingVariants.getPaintingVariantTitleKey(ModPaintingVariants.GROUP_PHOTO)), Component.translatable(ModPaintingVariants.getPaintingVariantAuthorKey(ModPaintingVariants.GROUP_PHOTO))); } - private static void register(BootstrapContext pContext, ResourceKey pKey, int pWidth, int pHeight) { - pContext.register(pKey, new PaintingVariant(pWidth, pHeight, pKey.location())); + private static void register(BootstrapContext pContext, ResourceKey pKey, int pWidth, int pHeight, Component title, Component author) { + pContext.register(pKey, new PaintingVariant(pWidth, pHeight, pKey.location(), Optional.of(title), Optional.of(author))); } private static ResourceKey create(String pName) { return ResourceKey.create(Registries.PAINTING_VARIANT, ResourceLocation.fromNamespaceAndPath(LeashedPlayer.MOD_ID, pName)); diff --git a/src/main/java/com/r3944realms/leashedplayer/mixin/both/MixinEntity.java b/src/main/java/com/r3944realms/leashedplayer/mixin/both/MixinEntity.java index 06b9350..10cbf4a 100644 --- a/src/main/java/com/r3944realms/leashedplayer/mixin/both/MixinEntity.java +++ b/src/main/java/com/r3944realms/leashedplayer/mixin/both/MixinEntity.java @@ -1,8 +1,10 @@ package com.r3944realms.leashedplayer.mixin.both; import com.r3944realms.leashedplayer.modInterface.PlayerLeashable; +import net.minecraft.server.level.ServerLevel; import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.Leashable; +import net.minecraft.world.level.Level; import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.Shadow; import org.spongepowered.asm.mixin.injection.At; @@ -12,6 +14,8 @@ import org.spongepowered.asm.mixin.injection.Redirect; public abstract class MixinEntity { @Shadow public abstract void igniteForSeconds(float pSeconds); + @Shadow public abstract Level level(); + /** * 这里重定向,当实体类实现了{@link PlayerLeashable}接口时,
* 阻止原版的{@link Leashable}中 的tickLeash方法调用,将其
@@ -21,11 +25,11 @@ public abstract class MixinEntity { */ @Redirect( method = "baseTick", - at = @At(value = "INVOKE", target = "Lnet/minecraft/world/entity/Leashable;tickLeash(Lnet/minecraft/world/entity/Entity;)V") + at = @At(value = "INVOKE", target = "Lnet/minecraft/world/entity/Leashable;tickLeash(Lnet/minecraft/server/level/ServerLevel;Lnet/minecraft/world/entity/Entity;)V") ) - void checkAndCancelIfTure(E entity) { - if(!(entity instanceof PlayerLeashable)) { - Leashable.tickLeash(entity); + void checkAndCancelIfTure(ServerLevel f, E entity) { + if(!(entity instanceof PlayerLeashable) && level() instanceof ServerLevel serverLevel_) { + Leashable.tickLeash(serverLevel_, entity); } } diff --git a/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinEntityRenderer.java b/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinEntityRenderer.java deleted file mode 100644 index b381ad1..0000000 --- a/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinEntityRenderer.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.r3944realms.leashedplayer.mixin.client; - -import net.minecraft.client.player.AbstractClientPlayer; -import net.minecraft.client.renderer.entity.EntityRenderer; -import net.minecraft.world.entity.Entity; -import net.minecraft.world.phys.Vec3; -import org.jetbrains.annotations.NotNull; -import org.spongepowered.asm.mixin.Mixin; -import org.spongepowered.asm.mixin.injection.At; -import org.spongepowered.asm.mixin.injection.Redirect; - -@Mixin(EntityRenderer.class) -public abstract class MixinEntityRenderer { - - @Redirect( - method = {"renderLeash"}, - at = @At( - value = "INVOKE", - target = "Lnet/minecraft/world/entity/Entity;getLeashOffset(F)Lnet/minecraft/world/phys/Vec3;" - ) - ) - private @NotNull Vec3 ret(Entity instance, float pPartialTick) { - if(instance instanceof AbstractClientPlayer) { - //为了使拴绳在在第三视角下位于玩家脖子处 - return instance.getLeashOffset(pPartialTick).add(0, -0.2, -0.2);//TODO:待擴展Vec3 - } - return instance.getLeashOffset(pPartialTick);//非实现这个接口则不变 - } - -} diff --git a/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinLevelRenderer.java b/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinLevelRenderer.java index 9c7292f..d907910 100644 --- a/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinLevelRenderer.java +++ b/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinLevelRenderer.java @@ -1,5 +1,6 @@ package com.r3944realms.leashedplayer.mixin.client; +import com.mojang.blaze3d.resource.GraphicsResourceAllocator; import com.mojang.blaze3d.vertex.PoseStack; import com.mojang.datafixers.util.Either; import com.r3944realms.leashedplayer.LeashedPlayer; @@ -34,6 +35,8 @@ import javax.annotation.Nullable; import java.util.List; import java.util.UUID; +import static com.r3944realms.leashedplayer.client.renders.LeashRendererUtil.levelRenderLeash; + @Mixin(LevelRenderer.class) public abstract class MixinLevelRenderer { @Shadow @@ -49,82 +52,15 @@ public abstract class MixinLevelRenderer { @Inject( method = {"renderLevel"}, - at = @At( - value = "INVOKE", - target = "Lnet/minecraft/client/renderer/RenderBuffers;bufferSource()Lnet/minecraft/client/renderer/MultiBufferSource$BufferSource;", - shift = At.Shift.AFTER - ) + at = @At(value = "HEAD") ) - private void renderLevel(DeltaTracker pDeltaTracker, boolean pRenderBlockOutline, Camera pCamera, GameRenderer pGameRenderer, LightTexture pLightTexture, Matrix4f pFrustumMatrix, Matrix4f pProjectionMatrix, CallbackInfo ci) { + private void renderLevel(GraphicsResourceAllocator pGraphicsResourceAllocator, DeltaTracker pDeltaTracker, boolean pRenderBlockOutline, Camera pCamera, GameRenderer pGameRenderer, LightTexture pLightTexture, Matrix4f pFrustumMatrix, Matrix4f pProjectionMatrix, CallbackInfo ci) { assert this.level != null; PoseStack poseStack = new PoseStack(); MultiBufferSource.BufferSource multibuffersource$buffersource = this.renderBuffers.bufferSource(); - for(Entity entity : this.level.entitiesForRendering()) { - //对于玩家实体拴绳渲染(从第一人称视角) - if (entity instanceof AbstractClientPlayer abstractClientPlayer) { - if(!(pCamera.getEntity() instanceof AbstractClientPlayer)) continue; - Minecraft mc = Minecraft.getInstance(); - PlayerRenderer playerRenderer = (PlayerRenderer) mc.getEntityRenderDispatcher().getRenderer(abstractClientPlayer); - IPlayerRendererExtension playerRendererExtension = (IPlayerRendererExtension) playerRenderer; - if (mc.options.getCameraType().isFirstPerson()) { - Leashable.LeashData leashDataFromEntityData = ((PlayerLeashable) abstractClientPlayer).getLeashDataFromEntityData(); - if(leashDataFromEntityData == null) continue; - Either delayedLeashInfo = leashDataFromEntityData.delayedLeashInfo; - if(delayedLeashInfo != null) { - float partialTickTime = pCamera.getPartialTickTime(); - Vec3 position = pCamera.getPosition(); - double dX = Mth.lerp(partialTickTime, abstractClientPlayer.xOld, abstractClientPlayer.getX()) - position.x; - double dY = Mth.lerp(partialTickTime, abstractClientPlayer.yOld, abstractClientPlayer.getY()) - position.y; - double dZ = Mth.lerp(partialTickTime, abstractClientPlayer.zOld, abstractClientPlayer.getZ()) - position.z; - Vec3 vec3 = playerRenderer.getRenderOffset(abstractClientPlayer, partialTickTime); - double dX_ = dX + vec3.x(); - double dY_ = dY + vec3.y(); - double dZ_ = dZ + vec3.z(); - poseStack.pushPose(); - poseStack.translate(dX_, dY_, dZ_); - ClientLevel level = mc.level; - if (delayedLeashInfo.right().isPresent() && delayedLeashInfo.left().isEmpty()) { - assert level != null; - playerRendererExtension.renderLeashForCamera(pCamera, partialTickTime, poseStack, multibuffersource$buffersource, LeashFenceKnotEntity.getOrCreateKnot(level, delayedLeashInfo.right().get())); - } else if (delayedLeashInfo.right().isEmpty() && delayedLeashInfo.left().isPresent()) { - assert level != null; - - Player playerByUUID = level.getPlayerByUUID(delayedLeashInfo.left().get()); - if (playerByUUID != null) { - playerRendererExtension.renderLeashForCamera(pCamera, partialTickTime, poseStack, multibuffersource$buffersource, playerByUUID); - } else { - double MaxLeashLength = ((ILivingEntityExtension) abstractClientPlayer).getLeashLength() * LeashedPlayer.M1() * LeashedPlayer.M2(); - List entities = level.getEntities( - null, - new AABB( - abstractClientPlayer.getX() - MaxLeashLength, - abstractClientPlayer.getY() - MaxLeashLength, - abstractClientPlayer.getZ() - MaxLeashLength, - abstractClientPlayer.getX() + MaxLeashLength, - abstractClientPlayer.getY() + MaxLeashLength, - abstractClientPlayer.getZ() + MaxLeashLength - ) - ); - Entity holder = null; - for (Entity entity_ : entities) { - if(entity_.getUUID().equals(delayedLeashInfo.left().get())) { - holder = entity_; - break; - } - } - if (holder != null) { - if(holder instanceof LeashRopeArrow) { - playerRendererExtension.renderLeashForCamera(pCamera, partialTickTime, poseStack, multibuffersource$buffersource, holder, new Vec3(0.,-0.09, 0));//TODO: 待擴展Vec3吗? - } - else playerRendererExtension.renderLeashForCamera(pCamera, partialTickTime, poseStack, multibuffersource$buffersource, holder); - } - } - break; - } - } - } - } - } + levelRenderLeash(level, pCamera, poseStack, multibuffersource$buffersource); } + + } diff --git a/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinPlayerRenderState.java b/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinPlayerRenderState.java new file mode 100644 index 0000000..4f1a218 --- /dev/null +++ b/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinPlayerRenderState.java @@ -0,0 +1,28 @@ +package com.r3944realms.leashedplayer.mixin.client; + +import com.r3944realms.leashedplayer.client.renders.PlayerLeashState; +import com.r3944realms.leashedplayer.modInterface.IPlayerRenderStateExtension; +import com.r3944realms.leashedplayer.modInterface.PlayerLeashable; +import net.minecraft.client.renderer.entity.state.PlayerRenderState; +import org.jetbrains.annotations.Nullable; +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.Unique; + +@SuppressWarnings({"AddedMixinMembersNamePattern"}) +@Mixin(PlayerRenderState.class) +public class MixinPlayerRenderState implements IPlayerRenderStateExtension { + @Unique + @Nullable + private PlayerLeashState playerLeashState; + + @Override + public @Nullable PlayerLeashState getPlayerLeashState() { + return playerLeashState; + } + + @Override + public void setPlayerLeashState(@Nullable PlayerLeashState playerRenderState) { + this.playerLeashState = playerRenderState; + } + +} diff --git a/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinPlayerRenderer.java b/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinPlayerRenderer.java index 4a8d989..b973369 100644 --- a/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinPlayerRenderer.java +++ b/src/main/java/com/r3944realms/leashedplayer/mixin/client/MixinPlayerRenderer.java @@ -4,8 +4,10 @@ import com.mojang.blaze3d.vertex.PoseStack; import com.mojang.blaze3d.vertex.VertexConsumer; import com.mojang.datafixers.util.Either; import com.r3944realms.leashedplayer.LeashedPlayer; +import com.r3944realms.leashedplayer.client.renders.PlayerLeashState; import com.r3944realms.leashedplayer.content.entities.LeashRopeArrow; import com.r3944realms.leashedplayer.modInterface.ILivingEntityExtension; +import com.r3944realms.leashedplayer.modInterface.IPlayerRenderStateExtension; import com.r3944realms.leashedplayer.modInterface.IPlayerRendererExtension; import com.r3944realms.leashedplayer.modInterface.PlayerLeashable; import net.minecraft.client.Camera; @@ -18,6 +20,8 @@ import net.minecraft.client.renderer.RenderType; import net.minecraft.client.renderer.entity.EntityRendererProvider; import net.minecraft.client.renderer.entity.LivingEntityRenderer; import net.minecraft.client.renderer.entity.player.PlayerRenderer; +import net.minecraft.client.renderer.entity.state.EntityRenderState; +import net.minecraft.client.renderer.entity.state.PlayerRenderState; import net.minecraft.core.BlockPos; import net.minecraft.util.Mth; import net.minecraft.world.entity.Entity; @@ -38,238 +42,66 @@ import java.util.List; import java.util.UUID; @Mixin(PlayerRenderer.class) -public abstract class MixinPlayerRenderer extends LivingEntityRenderer> implements IPlayerRendererExtension { - public MixinPlayerRenderer(EntityRendererProvider.Context pContext, PlayerModel pModel, float pShadowRadius) { +public abstract class MixinPlayerRenderer extends LivingEntityRenderer implements IPlayerRendererExtension { + public MixinPlayerRenderer(EntityRendererProvider.Context pContext, PlayerModel pModel, float pShadowRadius) { super(pContext, pModel, pShadowRadius); } - - @Inject( - at = @At("HEAD"), - method = "render(Lnet/minecraft/client/player/AbstractClientPlayer;FFLcom/mojang/blaze3d/vertex/PoseStack;Lnet/minecraft/client/renderer/MultiBufferSource;I)V" - ) - private void renderMixin(AbstractClientPlayer pEntity, float pEntityYaw, float pPartialTicks, PoseStack pPoseStack, MultiBufferSource pBuffer, int pPackedLight, CallbackInfo ci) { - Leashable.LeashData leashDataFromEntityData = ((PlayerLeashable) pEntity).getLeashDataFromEntityData(); - if(leashDataFromEntityData == null) return; - Either delayedLeashInfo = leashDataFromEntityData.delayedLeashInfo; - if(delayedLeashInfo != null) { - Minecraft mc = Minecraft.getInstance(); - ClientLevel level = mc.level; - if (delayedLeashInfo.right().isPresent() && delayedLeashInfo.left().isEmpty()) { - assert level != null; - renderLeash(pEntity, pPartialTicks, pPoseStack, pBuffer, LeashFenceKnotEntity.getOrCreateKnot(level, delayedLeashInfo.right().get())); - } else if (delayedLeashInfo.right().isEmpty() && delayedLeashInfo.left().isPresent()) { - assert level != null; - Player playerByUUID = level.getPlayerByUUID(delayedLeashInfo.left().get()); - if (playerByUUID != null) { - renderLeash(pEntity, pPartialTicks, pPoseStack, pBuffer, playerByUUID); - } else { - double breakDistanceTime = (leashDataFromEntityData.leashHolder instanceof LeashRopeArrow) ? LeashedPlayer.M1() * LeashedPlayer.M2() : LeashedPlayer.M1(); - double MaxLeashLength = ((ILivingEntityExtension) pEntity).getLeashLength() * breakDistanceTime; - List entities = level.getEntities( - null, - new AABB( - pEntity.getX() - MaxLeashLength, - pEntity.getY() - MaxLeashLength, - pEntity.getZ() - MaxLeashLength, - pEntity.getX() + MaxLeashLength, - pEntity.getY() + MaxLeashLength, - pEntity.getZ() + MaxLeashLength - ) - ); - Entity holder = null; - for (Entity entity_ : entities) { - if(entity_.getUUID().equals(delayedLeashInfo.left().get())) { - holder = entity_; - break; + @Inject(method = {"extractRenderState(Lnet/minecraft/client/player/AbstractClientPlayer;Lnet/minecraft/client/renderer/entity/state/PlayerRenderState;F)V"}, at = @At("TAIL")) + public void extractRenderState(AbstractClientPlayer abstractClientPlayer, PlayerRenderState playerRenderState, float partTicks, CallbackInfo ci) { + Leashable.LeashData leashDataFromEntityData = ((PlayerLeashable) abstractClientPlayer).getLeashDataFromEntityData(); + IPlayerRenderStateExtension iPlayerRenderStateExtension = (IPlayerRenderStateExtension) playerRenderState; + if(leashDataFromEntityData != null) { + Either delayedLeashInfo = leashDataFromEntityData.delayedLeashInfo; + PlayerLeashState playerLeashState = new PlayerLeashState(); + if (delayedLeashInfo != null) { + Minecraft mc = Minecraft.getInstance(); + ClientLevel level = mc.level; + if (delayedLeashInfo.right().isPresent() && delayedLeashInfo.left().isEmpty()) { + assert level != null; + playerLeashState.pos = delayedLeashInfo.right().get().getCenter().add(0.0, abstractClientPlayer.getEyeHeight() *0.7, 0); + } else if (delayedLeashInfo.right().isEmpty() && delayedLeashInfo.left().isPresent()) { + assert level != null; + Player playerByUUID = level.getPlayerByUUID(delayedLeashInfo.left().get()); + if (playerByUUID != null) { + playerLeashState.pos = playerByUUID.position().add(0.0, abstractClientPlayer.getEyeHeight() *0.7, 0); + } else { + double breakDistanceTime = (leashDataFromEntityData.leashHolder instanceof LeashRopeArrow) ? LeashedPlayer.M1() * LeashedPlayer.M2() : LeashedPlayer.M1(); + double MaxLeashLength = ((ILivingEntityExtension) abstractClientPlayer).getLeashLength() * breakDistanceTime; + List entities = level.getEntities( + null, + new AABB( + abstractClientPlayer.getX() - MaxLeashLength, + abstractClientPlayer.getY() - MaxLeashLength, + abstractClientPlayer.getZ() - MaxLeashLength, + abstractClientPlayer.getX() + MaxLeashLength, + abstractClientPlayer.getY() + MaxLeashLength, + abstractClientPlayer.getZ() + MaxLeashLength + ) + ); + Entity holder = null; + for (Entity entity_ : entities) { + if (entity_.getUUID().equals(delayedLeashInfo.left().get())) { + holder = entity_; + break; + } } - } - if (holder != null) { - if(holder instanceof LeashRopeArrow) { - renderLeash(pEntity, pPartialTicks, pPoseStack, pBuffer, holder, new Vec3(0,0, 0));//TODO: 待擴展Vec3 + if (holder != null) { + if (holder instanceof LeashRopeArrow) { + playerLeashState.pos = holder.position().add(0.0, abstractClientPlayer.getEyeHeight() *0.7, 0);//TODO: 待擴展Vec3 + } else playerLeashState.pos = holder.position().add(0.0, abstractClientPlayer.getEyeHeight() *0.7, 0); } - else renderLeash(pEntity, pPartialTicks, pPoseStack, pBuffer, holder); } } + playerLeashState.o = new Vec3(abstractClientPlayer.xo, abstractClientPlayer.yo, abstractClientPlayer.zo); + Entity leashHolder = leashDataFromEntityData.leashHolder; + playerLeashState.yRotO = abstractClientPlayer.yRotO; + playerLeashState.yRot = abstractClientPlayer.getYRot(); + iPlayerRenderStateExtension.setPlayerLeashState(playerLeashState); } - } - } - /** - *

1. 角度与弧度转换

- * {@snippet lang=java : - * double d0 = (double)(pEntity.getPreciseBodyRotation(pPartialTick) * (float)(Math.PI / 180.0)) + (Math.PI / 2); - * } - *
    - *
  • pEntity.getPreciseBodyRotation(pPartialTick) 返回实体的旋转角度(通常是以度为单位)。/li> - *
  • (Math.PI / 180.0) 是将度数转换为弧度的乘数,因为大多数三角函数(如 cossin)都需要弧度值。
  • - *
  • + (Math.PI / 2) 用于将结果平移90度(四分之一圆),可能是为了校正方向或设置起始方向。
  • - *
- * - *

- *

2. 三角函数计算位移

- * {@snippet lang=java : - * double d1 = Math.cos(d0) * vec31.z + Math.sin(d0) * vec31.x; - * double d2 = Math.sin(d0) * vec31.z - Math.cos(d0) * vec31.x; - * } - *
    - *
  • d1d2 是利用三角函数 cossin 计算出来的位移量,用于确定实体相对于其旋转的实际位置。
  • - *
  • Math.cos(d0) * vec31.zMath.sin(d0) * vec31.x 分别计算沿 X 和 Z 轴的位移分量,这种计算通常用于旋转一个点或向量。
  • - *
  • 两个公式结合起来用于旋转平面内的一个点 (vec31.x, vec31.z),从而得到旋转后的新坐标。
  • - *
- *

- *

3. 线性插值 (Lerp)

- * {@snippet lang=java : - * double d3 = Mth.lerp(pPartialTick, pEntity.xo, pEntity.getX()) + d1; - * double d4 = Mth.lerp(pPartialTick, pEntity.yo, pEntity.getY()) + vec31.y; - * double d5 = Mth.lerp(pPartialTick, pEntity.zo, pEntity.getZ()) + d2; - * } - *
    - *
  • Mth.lerp 是线性插值函数,通常用于在两个值之间平滑过渡。
  • - *
  • pEntity.xo, pEntity.yo, pEntity.zo 是实体在上一个刻度(tick)中的位置,而 pEntity.getX(), pEntity.getY(), pEntity.getZ() 是当前刻度的位置。
  • - *
  • pPartialTick 介于 01 之间,用来平滑过渡,使得动画更加流畅。
  • - *
- *

- *

4. 向量差值

- * {@snippet lang=java : - * float f = (float)(vec3.x - d3); - * float f1 = (float)(vec3.y - d4); - * float f2 = (float)(vec3.z - d5); - * } - *
    - *
  • 计算两个点(vec3(d3, d4, d5))之间的差值,得到的 ff1f2 是向量差,用于后续的渲染计算。
  • - *
- *

- *

5. 逆平方根与比例因子

- * {@snippet lang=java : - * float f4 = Mth.invSqrt(f * f + f2 * f2) * 0.025F / 2.0F; - * } - *
    - *
  • Mth.invSqrt 计算的是逆平方根(通常用于归一化向量或调整比例)。
  • - *
  • f * f + f2 * f2 是计算向量 (f, f2) 的平方和,用于得到其长度的平方。
  • - *
  • 乘以 0.025F / 2.0F 用于缩放结果,使得线条在渲染时具有合适的比例。
  • - *
- *

- *

6. 循环绘制

- * {@snippet lang=java : - * for (int i1 = 0; i1 <= 24; i1++) { - * addVertexPair(vertexconsumer, matrix4f, f, f1, f2, i, j, k, l, 0.025F, 0.025F, f5, f6, i1, false); - * } - * } - *
    - *
  • 循环从 024,用于创建24个顶点对,形成一个链状结构(或绳索)的外观。
  • - *
  • 每个循环迭代都会更新顶点的位置、颜色、光照等属性,使得链状结构被绘制出来。
  • - *
- *

- *

总结

- * 这些数学运算主要用于计算实体在三维空间中的位置和方向,以确保在渲染链状结构(如拴住的绳索)时,链条能够跟随实体的移动和旋转并正确显示。在图形编程中,这些计算非常常见,尤其是在处理旋转、插值和光照效果时。 - */ - - @SuppressWarnings("AddedMixinMembersNamePattern") - @Unique - public void renderLeashForCamera( - Camera camera, - float partialTick, - com.mojang.blaze3d.vertex.PoseStack poseStack, - net.minecraft.client.renderer.MultiBufferSource bufferSource, - E leashHolder, - Vec3 holderOffset - ) { - - poseStack.pushPose(); - - // 获得绳索持有者的位置 - Vec3 leashHolderPosition = leashHolder.getRopeHoldPosition(partialTick).add(holderOffset); - - // 获取当前观察的实体 - Entity cameraEntity = camera.getEntity(); - - // 计算实体的朝向角度(弧度) - double entityRotationAngleRadians = (double)(cameraEntity.getPreciseBodyRotation(partialTick) * (float) (Math.PI / 180.0)) + (Math.PI / 2); - - // 计算实体的绳索偏移,此处add偏移让渲染拴绳显示在玩家头部下(大约在脖子处 - Vec3 cameraEntityLeashOffset = cameraEntity.getLeashOffset(partialTick).add(0, -0.2, -0.5); - double leashOffsetX = Math.cos(entityRotationAngleRadians) * cameraEntityLeashOffset.z + Math.sin(entityRotationAngleRadians) * cameraEntityLeashOffset.x; - double leashOffsetZ = Math.sin(entityRotationAngleRadians) * cameraEntityLeashOffset.z - Math.cos(entityRotationAngleRadians) * cameraEntityLeashOffset.x; - - // 计算实体当前的实际位置 - double entityPosX = Mth.lerp(partialTick, cameraEntity.xo, cameraEntity.getX()) + leashOffsetX; - double entityPosY = Mth.lerp(partialTick, cameraEntity.yo, cameraEntity.getY()) + cameraEntityLeashOffset.y; - double entityPosZ = Mth.lerp(partialTick, cameraEntity.zo, cameraEntity.getZ()) + leashOffsetZ; - - // 在当前变换矩阵上应用偏移 - poseStack.translate(leashOffsetX, cameraEntityLeashOffset.y , leashOffsetZ); - - // 计算绳索的相对位置差 - float deltaX = (float)(leashHolderPosition.x - entityPosX); - float deltaY = (float)(leashHolderPosition.y - entityPosY); - float deltaZ = (float)(leashHolderPosition.z - entityPosZ); - - // 获取顶点消费者,用于绘制绳索 - VertexConsumer vertexConsumer = bufferSource.getBuffer(RenderType.leash()); - Matrix4f matrix = poseStack.last().pose(); - - // 计算比例因子,用于调节绳索的粗细 - float leashLengthRatio = Mth.invSqrt(deltaX * deltaX + deltaZ * deltaZ) * 0.025F / 2.0F; - float leashXZScaleX = deltaZ * leashLengthRatio; - float leashXZScaleZ = deltaX * leashLengthRatio; - - // 获取光照信息 - BlockPos cameraEntityBlockPos = BlockPos.containing(cameraEntity.getEyePosition(partialTick)); - BlockPos leashHolderBlockPos = BlockPos.containing(leashHolder.getEyePosition(partialTick)); - int cameraEntityBlockLightLevel = this.getBlockLightLevel((AbstractClientPlayer) cameraEntity, cameraEntityBlockPos); - int leashHolderBlockLightLevel = 0; //getBlockLightLevel(leashHolder, leashHolderBlockPos); - int cameraEntitySkyLightLevel = cameraEntity.level().getBrightness(LightLayer.SKY, cameraEntityBlockPos); - int leashHolderSkyLightLevel = cameraEntity.level().getBrightness(LightLayer.SKY, leashHolderBlockPos); - - // 绘制绳索的上半部分 - for (int segment = 0; segment <= 24; segment++) { - addVertexPair(vertexConsumer, matrix, deltaX, deltaY, deltaZ, cameraEntityBlockLightLevel, leashHolderBlockLightLevel, cameraEntitySkyLightLevel, leashHolderSkyLightLevel, 0.025F, 0.025F, leashXZScaleX, leashXZScaleZ, segment, false); + } else { + iPlayerRenderStateExtension.setPlayerLeashState(null); } - // 绘制绳索的下半部分 - for (int segment = 24; segment >= 0; segment--) { - addVertexPair(vertexConsumer, matrix, deltaX, deltaY, deltaZ, cameraEntityBlockLightLevel, leashHolderBlockLightLevel, cameraEntitySkyLightLevel, leashHolderSkyLightLevel, 0.025F, 0.0F, leashXZScaleX, leashXZScaleZ, segment, true); - } - - poseStack.popPose(); - } - @SuppressWarnings("AddedMixinMembersNamePattern") - @Unique - protected void renderLeash(AbstractClientPlayer pEntity, float pPartialTick, PoseStack pPoseStack, MultiBufferSource pBufferSource, E pLeashHolder, Vec3 holderOffset) { - pPoseStack.pushPose(); - Vec3 vec3 = pLeashHolder.getRopeHoldPosition(pPartialTick).add(holderOffset); - double d0 = (double)(pEntity.getPreciseBodyRotation(pPartialTick) * (float) (Math.PI / 180.0)) + (Math.PI / 2); - Vec3 vec31 = pEntity.getLeashOffset(pPartialTick).add(0, -0.2, -0.2);//TODO:待擴展Vec3); - double d1 = Math.cos(d0) * vec31.z + Math.sin(d0) * vec31.x; - double d2 = Math.sin(d0) * vec31.z - Math.cos(d0) * vec31.x; - double d3 = Mth.lerp(pPartialTick, pEntity.xo, pEntity.getX()) + d1; - double d4 = Mth.lerp(pPartialTick, pEntity.yo, pEntity.getY()) + vec31.y; - double d5 = Mth.lerp(pPartialTick, pEntity.zo, pEntity.getZ()) + d2; - pPoseStack.translate(d1, vec31.y, d2); - float f = (float)(vec3.x - d3); - float f1 = (float)(vec3.y - d4); - float f2 = (float)(vec3.z - d5); - float f3 = 0.025F; - VertexConsumer vertexconsumer = pBufferSource.getBuffer(RenderType.leash()); - Matrix4f matrix4f = pPoseStack.last().pose(); - float f4 = Mth.invSqrt(f * f + f2 * f2) * 0.025F / 2.0F; - float f5 = f2 * f4; - float f6 = f * f4; - BlockPos blockpos = BlockPos.containing(pEntity.getEyePosition(pPartialTick)); - BlockPos blockpos1 = BlockPos.containing(pLeashHolder.getEyePosition(pPartialTick)); - int i = this.getBlockLightLevel(pEntity, blockpos); - int j = 0; - int k = pEntity.level().getBrightness(LightLayer.SKY, blockpos); - int l = pEntity.level().getBrightness(LightLayer.SKY, blockpos1); - - for (int i1 = 0; i1 <= 24; i1++) { - addVertexPair(vertexconsumer, matrix4f, f, f1, f2, i, j, k, l, 0.025F, 0.025F, f5, f6, i1, false); - } - - for (int j1 = 24; j1 >= 0; j1--) { - addVertexPair(vertexconsumer, matrix4f, f, f1, f2, i, j, k, l, 0.025F, 0.0F, f5, f6, j1, true); - } - - pPoseStack.popPose(); } } \ No newline at end of file diff --git a/src/main/java/com/r3944realms/leashedplayer/mixin/server/MixinServerGamePacketListenerImpl.java b/src/main/java/com/r3944realms/leashedplayer/mixin/server/MixinServerGamePacketListenerImpl.java index 24ed41f..ee70469 100644 --- a/src/main/java/com/r3944realms/leashedplayer/mixin/server/MixinServerGamePacketListenerImpl.java +++ b/src/main/java/com/r3944realms/leashedplayer/mixin/server/MixinServerGamePacketListenerImpl.java @@ -7,7 +7,9 @@ import net.minecraft.network.protocol.game.ServerboundMovePlayerPacket; import net.minecraft.server.level.ServerPlayer; import net.minecraft.server.network.ServerGamePacketListenerImpl; import net.minecraft.world.entity.Entity; -import net.minecraft.world.entity.RelativeMovement; +import net.minecraft.world.entity.PositionMoveRotation; +import net.minecraft.world.entity.Relative; +import net.minecraft.world.phys.Vec3; import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.Shadow; import org.spongepowered.asm.mixin.Unique; @@ -26,8 +28,8 @@ public class MixinServerGamePacketListenerImpl { public ServerPlayer player; @Unique private List Pl$LeashPlayers = new ArrayList<>(); - @Inject(method = {"teleport(DDDFFLjava/util/Set;)V"}, at = {@At("HEAD")}) - private void teleportHead(double pX, double pY, double pZ, float pYaw, float pPitch, Set pRelativeSet, CallbackInfo ci) { + @Inject(method = {"teleport(Lnet/minecraft/world/entity/PositionMoveRotation;Ljava/util/Set;)V"}, at = {@At("HEAD")}) + private void teleportHead(PositionMoveRotation positionMoveRotation, Set pRelativeSet, CallbackInfo ci) { try { //獲取Holder this.Pl$LeashPlayers = ((PlayerLeashable)this.player).getLeashHolder() != null ? Collections.emptyList() : Objects.requireNonNull(this.player.getServer()).getPlayerList().getPlayers().stream().filter(serverPlayer -> (serverPlayer instanceof PlayerLeashable) && ((PlayerLeashable)serverPlayer).getLeashHolder() == this.player && player != serverPlayer).collect(Collectors.toList()); @@ -35,17 +37,18 @@ public class MixinServerGamePacketListenerImpl { logger.error("Internal Error:",e); } } - @Inject(method = {"teleport(DDDFFLjava/util/Set;)V"}, at = {@At("TAIL")}) - private void teleportTail(double pX, double pY, double pZ, float pYaw, float pPitch, Set pRelativeSet, CallbackInfo ci) { + @Inject(method = {"teleport(Lnet/minecraft/world/entity/PositionMoveRotation;Ljava/util/Set;)V"}, at = {@At("TAIL")}) + private void teleportTail(PositionMoveRotation moveRotation, Set pRelativeSet, CallbackInfo ci) { if(GameruleRegistry.getGameruleBoolValue(this.player.serverLevel(), TeleportWithLeashedPlayers.ID)) { for (Entity Pl$LeashPlayer : this.Pl$LeashPlayers) { if(Pl$LeashPlayer instanceof ServerPlayer) { if(Pl$LeashPlayer instanceof PlayerLeashable playerLeashable) { playerLeashable.dropLeash(false,false); if(((ServerPlayer) playerLeashable).serverLevel() == this.player.serverLevel()) { - ((ServerPlayer) playerLeashable).connection.teleport(pX, pY, pZ, pYaw, pPitch, pRelativeSet); + ((ServerPlayer) playerLeashable).connection.teleport(moveRotation, pRelativeSet); } else { - ((ServerPlayer) playerLeashable).teleportTo(this.player.serverLevel(), pX, pY, pZ, pYaw, pPitch); + Vec3 vec3 = moveRotation.deltaMovement(); + ((ServerPlayer) playerLeashable).teleportTo(this.player.serverLevel(), vec3.x, vec3.y, vec3.z, pRelativeSet, moveRotation.yRot(), moveRotation.yRot(),false); ((ServerPlayer) playerLeashable).stopRiding(); } playerLeashable.setLeashedTo(this.player, true); diff --git a/src/main/java/com/r3944realms/leashedplayer/modInterface/IPlayerRenderStateExtension.java b/src/main/java/com/r3944realms/leashedplayer/modInterface/IPlayerRenderStateExtension.java new file mode 100644 index 0000000..fdb7073 --- /dev/null +++ b/src/main/java/com/r3944realms/leashedplayer/modInterface/IPlayerRenderStateExtension.java @@ -0,0 +1,9 @@ +package com.r3944realms.leashedplayer.modInterface; + +import com.r3944realms.leashedplayer.client.renders.PlayerLeashState; +import net.minecraft.client.renderer.entity.state.PlayerRenderState; + +public interface IPlayerRenderStateExtension { + PlayerLeashState getPlayerLeashState(); + void setPlayerLeashState(PlayerLeashState playerRenderState); +} diff --git a/src/main/resources/META-INF/accesstransformer.cfg b/src/main/resources/META-INF/accesstransformer.cfg index dc553f0..6026431 100644 --- a/src/main/resources/META-INF/accesstransformer.cfg +++ b/src/main/resources/META-INF/accesstransformer.cfg @@ -5,9 +5,9 @@ protected net.minecraft.client.renderer.entity.EntityRenderer renderLeash(Lnet/m #priavte ->protected protected net.minecraft.client.renderer.entity.EntityRenderer addVertexPair(Lcom/mojang/blaze3d/vertex/VertexConsumer;Lorg/joml/Matrix4f;FFFIIIIFFFFIZ)V # addVertexPair #这个方法原包为package-priavet 有时需要限制范围故修改 -public net.minecraft.world.level.GameRules$IntegerValue create(IIILjava/util/function/BiConsumer;)Lnet/minecraft/world/level/GameRules$Type; # create +public net.minecraft.world.level.GameRules$IntegerValue create(IIILnet/minecraft/world/flag/FeatureFlagSet;Ljava/util/function/BiConsumer;)Lnet/minecraft/world/level/GameRules$Type; # create #因为'net.minecraft.world.level.GameRules.Type' 中不为 public。无法从外部软件包访问 -public net.minecraft.world.level.GameRules$Type (Ljava/util/function/Supplier;Ljava/util/function/Function;Ljava/util/function/BiConsumer;Lnet/minecraft/world/level/GameRules$VisitorCaller;)V # Type +public net.minecraft.world.level.GameRules$Type (Ljava/util/function/Supplier;Ljava/util/function/Function;Ljava/util/function/BiConsumer;Lnet/minecraft/world/level/GameRules$VisitorCaller;Lnet/minecraft/world/flag/FeatureFlagSet;)V # Type #因为'net.minecraft.world.level.GameRules.VisitorCaller' 在 'net.minecraft.world.level.GameRules' 中不为 public。无法从外部软件包访问 public net.minecraft.world.level.GameRules$VisitorCaller #Interface #private -> public @@ -18,4 +18,4 @@ protected net.minecraft.world.entity.projectile.AbstractArrow life # life public net.minecraft.world.effect.MobEffect (Lnet/minecraft/world/effect/MobEffectCategory;I)V # MobEffect #private -> protected protected net.minecraft.world.entity.projectile.Projectile cachedOwner # cachedOwner -protected net.minecraft.world.entity.projectile.Projectile ownerUUID # ownerUUID \ No newline at end of file +protected net.minecraft.world.entity.projectile.Projectile ownerUUID # ownerUUID diff --git a/src/main/resources/leashedplayer.mixins.json b/src/main/resources/leashedplayer.mixins.json index aba28ef..5d48b17 100644 --- a/src/main/resources/leashedplayer.mixins.json +++ b/src/main/resources/leashedplayer.mixins.json @@ -9,9 +9,9 @@ "server.MixinServerGamePacketListenerImpl" ], "client": [ - "client.MixinEntityRenderer", "client.MixinLevelRenderer", - "client.MixinPlayerRenderer" + "client.MixinPlayerRenderer", + "client.MixinPlayerRenderState" ], "refmap": "whimsicality.refmap.json", "required": true,