├── versions └── mainProject ├── .github ├── FUNDING.yml └── workflows │ ├── tag.yml │ └── build.yml ├── .gitattributes ├── gradle └── gradle-compose.jar ├── src ├── main │ ├── resources │ │ ├── icon.png │ │ ├── assets │ │ │ └── notenoughanimations │ │ │ │ ├── icon.png │ │ │ │ ├── recipe_book.png │ │ │ │ ├── textures │ │ │ │ └── recipe_book.png │ │ │ │ └── lang │ │ │ │ ├── pt_pt.json │ │ │ │ ├── uk_ua.json │ │ │ │ ├── zh_tw.json │ │ │ │ ├── zh_cn.json │ │ │ │ ├── sv_se.json │ │ │ │ ├── fr_fr.json │ │ │ │ ├── pt_br.json │ │ │ │ └── ru_ru.json │ │ └── notenoughanimations.mixins.json │ └── java │ │ └── dev │ │ └── tr7zw │ │ └── notenoughanimations │ │ ├── access │ │ ├── ExtendedItemStackRenderState.java │ │ ├── ExtendedLivingRenderState.java │ │ └── PlayerData.java │ │ ├── NEAnimationsMod.java │ │ ├── mixins │ │ ├── PlayerModelAccessor.java │ │ ├── ItemStackRenderStateMixin.java │ │ ├── ClientLevelMixin.java │ │ ├── LivingRenderStateMixin.java │ │ ├── LivingEntityMixin.java │ │ ├── ItemInHandRendererMixin.java │ │ ├── LivingEntityRendererMixin.java │ │ ├── PlayerEntityMixin.java │ │ ├── LevelRendererMixin.java │ │ ├── PlayerRendererMixin.java │ │ ├── ItemInHandLayerMixin.java │ │ └── PlayerEntityModelMixin.java │ │ ├── api │ │ ├── PoseOverwrite.java │ │ ├── NotEnoughAnimationsApi.java │ │ └── BasicAnimation.java │ │ ├── NEAModMenu.java │ │ ├── util │ │ ├── RenderStateHolder.java │ │ └── NMSWrapper.java │ │ ├── animations │ │ ├── vanilla │ │ │ ├── RiptideAnimation.java │ │ │ ├── DeathAnimation.java │ │ │ ├── SwimAnimation.java │ │ │ ├── SleepAnimation.java │ │ │ ├── VanillaTwoHandedAnimation.java │ │ │ ├── VanillaShieldAnimation.java │ │ │ ├── VanillaSingleHandedAnimation.java │ │ │ └── ElytraAnimation.java │ │ ├── fullbody │ │ │ ├── PassengerAnimation.java │ │ │ ├── ActionRotationLockAnimation.java │ │ │ ├── BurningAnimation.java │ │ │ ├── FreezingAnimation.java │ │ │ ├── HorseAnimation.java │ │ │ ├── FallingAnimation.java │ │ │ ├── LadderAnimation.java │ │ │ └── CrawlingAnimation.java │ │ └── hands │ │ │ ├── VanillaProjectileWeaponAnimation.java │ │ │ ├── NarutoRunningAnimation.java │ │ │ ├── ClampCrossbowAnimations.java │ │ │ ├── BoatAnimation.java │ │ │ ├── HugAnimation.java │ │ │ ├── EatDrinkAnimation.java │ │ │ ├── CustomBowAnimation.java │ │ │ ├── ItemSwapAnimation.java │ │ │ ├── PetAnimation.java │ │ │ ├── MapHoldingAnimation.java │ │ │ └── LookAtItemAnimation.java │ │ ├── NEABootstrap.java │ │ ├── NEAnimationsLoader.java │ │ └── logic │ │ └── AnimationProvider.java └── test │ └── java │ └── dev │ └── tr7zw │ └── tests │ ├── TestMod.java │ ├── MixinTests.java │ └── TestUtil.java ├── NEAVersionless └── src │ └── main │ └── java │ └── dev │ └── tr7zw │ └── notenoughanimations │ └── versionless │ ├── RotationLock.java │ ├── animations │ ├── DataHolder.java │ ├── HoldUpTarget.java │ ├── BowAnimation.java │ ├── HoldUpModes.java │ └── BodyPart.java │ ├── NEABaseMod.java │ └── config │ ├── ConfigUpgrader.java │ └── Config.java ├── .gitignore ├── LICENSE ├── settings.json ├── gradle-compose.yml ├── README.md ├── gradlecw.bat └── gradlecw /versions/mainProject: -------------------------------------------------------------------------------- 1 | 1.21.11-fabric -------------------------------------------------------------------------------- /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | # These are supported funding model platforms 2 | ko_fi: tr7zw -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | # Auto detect text files and perform LF normalization 2 | * text=auto 3 | -------------------------------------------------------------------------------- /gradle/gradle-compose.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tr7zw/NotEnoughAnimations/HEAD/gradle/gradle-compose.jar -------------------------------------------------------------------------------- /src/main/resources/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tr7zw/NotEnoughAnimations/HEAD/src/main/resources/icon.png -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tr7zw/NotEnoughAnimations/HEAD/src/main/resources/assets/notenoughanimations/icon.png -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/recipe_book.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tr7zw/NotEnoughAnimations/HEAD/src/main/resources/assets/notenoughanimations/recipe_book.png -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/textures/recipe_book.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tr7zw/NotEnoughAnimations/HEAD/src/main/resources/assets/notenoughanimations/textures/recipe_book.png -------------------------------------------------------------------------------- /src/test/java/dev/tr7zw/tests/TestMod.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.tests; 2 | 3 | import dev.tr7zw.notenoughanimations.NEAnimationsLoader; 4 | 5 | public class TestMod extends NEAnimationsLoader { 6 | 7 | } 8 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/RotationLock.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless; 2 | 3 | public enum RotationLock { 4 | NONE, FIXED, SMOOTH 5 | } 6 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/animations/DataHolder.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless.animations; 2 | 3 | public interface DataHolder { 4 | 5 | } 6 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/animations/HoldUpTarget.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless.animations; 2 | 3 | public enum HoldUpTarget { 4 | NONE, CAMERA 5 | } 6 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/animations/BowAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless.animations; 2 | 3 | public enum BowAnimation { 4 | VANILLA, CUSTOM_V1 5 | } 6 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/animations/HoldUpModes.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless.animations; 2 | 3 | public enum HoldUpModes { 4 | CONFIG, ALL, NONE, CONFIG_INVERTED 5 | } 6 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/animations/BodyPart.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless.animations; 2 | 3 | public enum BodyPart { 4 | LEFT_ARM, RIGHT_ARM, LEFT_LEG, RIGHT_LEG, BODY, HEAD 5 | } 6 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/access/ExtendedItemStackRenderState.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.access; 2 | 3 | import net.minecraft.world.item.ItemStack; 4 | 5 | public interface ExtendedItemStackRenderState { 6 | 7 | public ItemStack getItemStack(); 8 | 9 | public void setItemStack(ItemStack item); 10 | 11 | } 12 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/access/ExtendedLivingRenderState.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.access; 2 | 3 | import net.minecraft.client.player.AbstractClientPlayer; 4 | import net.minecraft.world.entity.LivingEntity; 5 | 6 | public interface ExtendedLivingRenderState { 7 | 8 | void setEntity(LivingEntity entity); 9 | 10 | LivingEntity getEntity(); 11 | } 12 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/NEAnimationsMod.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations; 2 | 3 | public class NEAnimationsMod extends NEAnimationsLoader 4 | //? if fabric { 5 | 6 | implements net.fabricmc.api.ClientModInitializer 7 | //? } 8 | { 9 | //? if fabric { 10 | 11 | @Override 12 | //? } 13 | public void onInitializeClient() { 14 | onEnable(); 15 | } 16 | 17 | } 18 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/PlayerModelAccessor.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | //? if >= 1.21.11 { 4 | 5 | import net.minecraft.client.model.player.*; 6 | //? } else { 7 | /* 8 | import net.minecraft.client.model.*; 9 | *///? } 10 | import org.spongepowered.asm.mixin.Mixin; 11 | import org.spongepowered.asm.mixin.gen.Accessor; 12 | 13 | @Mixin(PlayerModel.class) 14 | public interface PlayerModelAccessor { 15 | 16 | @Accessor("slim") 17 | boolean getSlim(); 18 | } 19 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/api/PoseOverwrite.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.api; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | //? if >= 1.21.11 { 5 | 6 | import net.minecraft.client.model.player.*; 7 | //? } else { 8 | /* 9 | import net.minecraft.client.model.*; 10 | *///? } 11 | import net.minecraft.client.player.AbstractClientPlayer; 12 | 13 | public interface PoseOverwrite { 14 | 15 | public void updateState(AbstractClientPlayer entity, PlayerData data, PlayerModel playerModel); 16 | 17 | } 18 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/NEAModMenu.java: -------------------------------------------------------------------------------- 1 | //? if fabric { 2 | 3 | package dev.tr7zw.notenoughanimations; 4 | 5 | import com.terraformersmc.modmenu.api.ConfigScreenFactory; 6 | import com.terraformersmc.modmenu.api.ModMenuApi; 7 | 8 | import dev.tr7zw.notenoughanimations.config.ConfigScreenProvider; 9 | 10 | public class NEAModMenu implements ModMenuApi { 11 | 12 | @Override 13 | public ConfigScreenFactory getModConfigScreenFactory() { 14 | return parent -> { 15 | return ConfigScreenProvider.createConfigScreen(parent); 16 | }; 17 | } 18 | 19 | } 20 | //? } 21 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/util/RenderStateHolder.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.util; 2 | 3 | import dev.tr7zw.notenoughanimations.versionless.animations.DataHolder; 4 | 5 | public class RenderStateHolder implements DataHolder { 6 | 7 | public static final RenderStateHolder INSTANCE = new RenderStateHolder(); 8 | 9 | public static class RenderStateData { 10 | //? if >= 1.21.9 { 11 | 12 | public net.minecraft.client.renderer.entity.state.AvatarRenderState renderState; 13 | //? } else if >= 1.21.2 { 14 | /* 15 | public net.minecraft.client.renderer.entity.state.PlayerRenderState renderState; 16 | *///? } 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /src/main/resources/notenoughanimations.mixins.json: -------------------------------------------------------------------------------- 1 | { 2 | "required": true, 3 | "minVersion": "0.8", 4 | "package": "dev.tr7zw.notenoughanimations.mixins", 5 | "compatibilityLevel": "JAVA_8", 6 | "mixins": [], 7 | "client": [ 8 | "ItemInHandLayerMixin", 9 | "ItemInHandRendererMixin", 10 | "LevelRendererMixin", 11 | "LivingEntityMixin", 12 | "LivingEntityRendererMixin", 13 | "LivingRenderStateMixin", 14 | "PlayerEntityMixin", 15 | "PlayerEntityModelMixin", 16 | "PlayerModelAccessor", 17 | "PlayerRendererMixin", 18 | "ItemStackRenderStateMixin", 19 | "ClientLevelMixin" 20 | ], 21 | "injectors": { 22 | "defaultRequire": 1 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/ItemStackRenderStateMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | 5 | import dev.tr7zw.notenoughanimations.access.ExtendedItemStackRenderState; 6 | import lombok.Getter; 7 | import lombok.Setter; 8 | import net.minecraft.world.item.ItemStack; 9 | //? if >= 1.21.4 { 10 | 11 | import net.minecraft.client.renderer.item.ItemStackRenderState; 12 | 13 | @Mixin(ItemStackRenderState.class) 14 | public class ItemStackRenderStateMixin implements ExtendedItemStackRenderState { 15 | 16 | @Getter 17 | @Setter 18 | private ItemStack itemStack = null; 19 | 20 | } 21 | //? } else { 22 | /* 23 | @Mixin(ItemStack.class) 24 | public class ItemStackRenderStateMixin {} 25 | *///? } 26 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/ClientLevelMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import dev.tr7zw.notenoughanimations.NEAnimationsMod; 9 | import net.minecraft.client.multiplayer.ClientLevel; 10 | 11 | // Port of the Fabric mixin to (Neo)Forge, as the (Neo)Forge events do weird stuff 12 | @Mixin(ClientLevel.class) 13 | public class ClientLevelMixin { 14 | 15 | @Inject(method = "tickEntities", at = @At("HEAD")) 16 | private void startWorldTick(CallbackInfo ci) { 17 | NEAnimationsMod.INSTANCE.clientTick(); 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/util/NMSWrapper.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.util; 2 | 3 | import net.minecraft.world.entity.*; 4 | import net.minecraft.world.item.ItemStack; 5 | 6 | public class NMSWrapper { 7 | 8 | public static boolean hasCustomModel(ItemStack itemStack) { 9 | //? if <= 1.20.4 { 10 | /* 11 | return itemStack.hasTag() && itemStack.getTag().contains("CustomModelData"); 12 | *///? } else { 13 | 14 | return itemStack.getComponents().has(net.minecraft.core.component.DataComponents.CUSTOM_MODEL_DATA); 15 | //? } 16 | } 17 | 18 | public static boolean onGround(Entity entity) { 19 | //? if >= 1.20.0 { 20 | 21 | return entity.onGround(); 22 | //? } else { 23 | /* 24 | return entity.isOnGround(); 25 | *///? } 26 | } 27 | 28 | } 29 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/api/NotEnoughAnimationsApi.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.api; 2 | 3 | import dev.tr7zw.notenoughanimations.NEAnimationsMod; 4 | 5 | public class NotEnoughAnimationsApi { 6 | 7 | /** 8 | * Register a new {@link BasicAnimation} to the mod. BasicAnimations can 9 | * implement {@link PoseOverwrite} to access these features. 10 | * 11 | * @param animation 12 | */ 13 | public static void registerAnimation(BasicAnimation animation) { 14 | NEAnimationsMod.INSTANCE.animationProvider.addAnimation(animation); 15 | } 16 | 17 | /** 18 | * Refreshes which animations are enabled right now. Should be called after 19 | * {@link BasicAnimation#isEnabled()} might have changed. 20 | */ 21 | public static void refreshEnabledAnimations() { 22 | NEAnimationsMod.INSTANCE.animationProvider.refreshEnabledAnimations(); 23 | } 24 | 25 | } 26 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/LivingRenderStateMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import dev.tr7zw.notenoughanimations.access.ExtendedLivingRenderState; 4 | import net.minecraft.world.entity.LivingEntity; 5 | import org.spongepowered.asm.mixin.Mixin; 6 | import org.spongepowered.asm.mixin.Unique; 7 | 8 | //? if >= 1.21.2 { 9 | 10 | import net.minecraft.client.renderer.entity.state.LivingEntityRenderState; 11 | 12 | @Mixin(LivingEntityRenderState.class) 13 | public class LivingRenderStateMixin implements ExtendedLivingRenderState { 14 | 15 | @Unique 16 | private LivingEntity entity; 17 | 18 | @Override 19 | public void setEntity(LivingEntity player) { 20 | this.entity = player; 21 | } 22 | 23 | @Override 24 | public LivingEntity getEntity() { 25 | return entity; 26 | } 27 | } 28 | //? } else { 29 | /* 30 | import net.minecraft.client.Minecraft; 31 | @Mixin(Minecraft.class) 32 | public class LivingRenderStateMixin {} 33 | *///? } 34 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # gradle 2 | 3 | .gradle/ 4 | build/ 5 | out/ 6 | classes/ 7 | 8 | # eclipse 9 | 10 | *.launch 11 | 12 | # idea 13 | 14 | .idea/ 15 | *.iml 16 | *.ipr 17 | *.iws 18 | 19 | # vscode 20 | 21 | .settings/ 22 | .vscode/ 23 | bin/ 24 | .classpath 25 | .project 26 | 27 | # macos 28 | 29 | *.DS_Store 30 | 31 | # fabric 32 | 33 | run/ 34 | logs/ 35 | 36 | # compose 37 | 38 | *.gradle 39 | *.properties 40 | gradle/wrapper 41 | VersionShared 42 | UtilityCode 43 | formatter.xml 44 | src/main/fabric-resources/fabric.mod.json 45 | src/main/forge-resources/META-INF/mods.toml 46 | src/main/neoforge-resources/META-INF/mods.toml 47 | **/src/main/java/dev/tr7zw/config/CustomConfigScreen.java 48 | **/src/main/java/dev/tr7zw/util/ComponentProvider.java 49 | src/main/resources/pack.mcmeta 50 | src/main/java/dev/tr7zw/notenoughanimations/NEAnimationsMod.java 51 | src/main/java/dev/tr7zw/util/NMSHelper.java 52 | src/main/java/dev/tr7zw/util/ModLoaderUtil.java 53 | src/main/neoforge-resources/META-INF/neoforge.mods.toml 54 | /src/main/java/dev/tr7zw/util 55 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | tr7zw Protective License 2 | 3 | Copyright (c) tr7zw, 2021 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software (in source or binary form) and associated documentation files 7 | (the "Software"), to use, modify and compile the Software, subject to the 8 | following conditions: 9 | 10 | The Software may not be used to get a) a commercial advantage, or b) monetary 11 | compensation. 12 | 13 | The above copyright notice and this permission notice shall be included in 14 | all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 22 | THE SOFTWARE. 23 | -------------------------------------------------------------------------------- /.github/workflows/tag.yml: -------------------------------------------------------------------------------- 1 | name: Create Release 2 | on: 3 | release: 4 | types: [published] 5 | jobs: 6 | build: 7 | runs-on: ubuntu-latest 8 | steps: 9 | - name: checkout repository 10 | uses: actions/checkout@v2 11 | - name: setup jdk 21 12 | uses: actions/setup-java@v1 13 | with: 14 | java-version: 21 15 | - name: Get Release Changelog 16 | run: | 17 | # Read the event payload to get the changelog and save it to a file 18 | changelog=$(jq -r '.release.body' $GITHUB_EVENT_PATH) 19 | echo "$changelog" > changelog.md 20 | echo "Changelog saved to changelog.md" 21 | - name: make gradle wrapper executable 22 | run: chmod +x ./gradlecw 23 | - name: build 24 | run: ./gradlecw build publishMods -Pbuild.release=true --info 25 | env: 26 | CURSEFORGE_TOKEN: ${{ secrets.CURSEFORGE_TOKEN }} 27 | MODRINTH_TOKEN: ${{ secrets.MODRINTH_TOKEN }} 28 | - name: Release 29 | uses: softprops/action-gh-release@v1 30 | with: 31 | files: 'versions/**/build/libs/!(*-@(dev|sources|javadoc|all)).jar' -------------------------------------------------------------------------------- /settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "versions": [ 3 | "1.16.5-fabric", 4 | "1.18.2-forge", 5 | "1.18.2-fabric", 6 | "1.19.2-forge", 7 | "1.19.2-fabric", 8 | "1.19.4-forge", 9 | "1.19.4-fabric", 10 | "1.20.1-forge", 11 | "1.20.1-fabric", 12 | "1.20.2-forge", 13 | "1.20.2-neoforge", 14 | "1.20.2-fabric", 15 | "1.20.4-forge", 16 | "1.20.4-neoforge", 17 | "1.20.4-fabric", 18 | "1.20.6-forge", 19 | "1.20.6-neoforge", 20 | "1.20.6-fabric", 21 | "1.21.1-forge", 22 | "1.21.1-neoforge", 23 | "1.21.1-fabric", 24 | "1.21.3-forge", 25 | "1.21.3-neoforge", 26 | "1.21.3-fabric", 27 | "1.21.4-forge", 28 | "1.21.4-neoforge", 29 | "1.21.4-fabric", 30 | "1.21.5-forge", 31 | "1.21.5-neoforge", 32 | "1.21.5-fabric", 33 | "1.21.8-forge", 34 | "1.21.8-neoforge", 35 | "1.21.8-fabric", 36 | "1.21.10-neoforge", 37 | "1.21.10-forge", 38 | "1.21.10-fabric", 39 | "1.21.11-neoforge", 40 | "1.21.11-fabric" 41 | ] 42 | } 43 | -------------------------------------------------------------------------------- /gradle-compose.yml: -------------------------------------------------------------------------------- 1 | version: '0.0.2' 2 | source: "https://github.com/tr7zw/ProcessedModTemplate/tree/stonecutter" 3 | replacements: 4 | name: "NotEnoughAnimations" 5 | id: "notenoughanimations" 6 | version: "1.11.1" 7 | description: "Adding and improving animations in Third-Person." 8 | homepageUrl: "https://modrinth.com/mod/not-enough-animations" 9 | sourcesUrl: "https://github.com/tr7zw/NotEnoughAnimations" 10 | issuesUrl: "https://github.com/tr7zw/NotEnoughAnimations/issues" 11 | fabric_entrypoint: "dev.tr7zw.notenoughanimations.NEAnimationsMod" 12 | fabric_modmenu_entrypoint: "dev.tr7zw.notenoughanimations.NEAModMenu" 13 | relocationpackage: "dev.tr7zw.notenoughanimations" 14 | modrinthid: MPCX6s5C 15 | curseforgeid: 433760 16 | versionlessname: "NEAVersionless" 17 | enabledFlags: 18 | - autopublish 19 | - publishFabric 20 | - publishForge 21 | - publishNeo 22 | - modrinth 23 | - curseforge 24 | - versionless 25 | - includeLibs 26 | - addTRenderLib 27 | - addTRansitionLib 28 | rootProject: 29 | template: "." 30 | subProjects: 31 | NEAVersionless: 32 | template: "Versionless" 33 | replacements: 34 | dependencies: ' 35 | compileOnly "com.google.code.gson:gson:2.10.1" 36 | 37 | compileOnly "org.apache.logging.log4j:log4j-core:2.20.0" 38 | ' -------------------------------------------------------------------------------- /.github/workflows/build.yml: -------------------------------------------------------------------------------- 1 | # Automatically build the project and run any configured tests for every push 2 | # and submitted pull request. This can help catch issues that only occur on 3 | # certain platforms or Java versions, and provides a first line of defence 4 | # against bad commits. 5 | name: build 6 | on: [pull_request, push] 7 | jobs: 8 | build: 9 | runs-on: ubuntu-latest 10 | steps: 11 | - name: checkout repository 12 | uses: actions/checkout@v2 13 | - name: setup jdk 21 14 | uses: actions/setup-java@v4 15 | with: 16 | distribution: temurin 17 | java-version: 21 18 | # to cache gradle files 19 | - name: Setup Gradle 20 | uses: gradle/actions/setup-gradle@v4 21 | with: 22 | gradle-home-cache-cleanup: true 23 | dependency-graph: generate-and-submit 24 | - name: build 25 | run: ./gradlecw build --stacktrace 26 | - name: capture build artifacts 27 | uses: actions/upload-artifact@v4 28 | with: 29 | name: Artifacts 30 | path: 'versions/**/build/libs/*.jar' 31 | 32 | # - name: Test Report 33 | # uses: dorny/test-reporter@v1 34 | # if: success() || failure() 35 | # with: 36 | # name: JUnit Tests 37 | # path: '**/build/test-results/test/TEST-*.xml' 38 | # reporter: java-junit -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/vanilla/RiptideAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.vanilla; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 6 | //? if >= 1.21.11 { 7 | 8 | import net.minecraft.client.model.player.*; 9 | //? } else { 10 | /* 11 | import net.minecraft.client.model.*; 12 | *///? } 13 | import net.minecraft.client.player.AbstractClientPlayer; 14 | 15 | public class RiptideAnimation extends BasicAnimation { 16 | 17 | @Override 18 | public boolean isEnabled() { 19 | return true; 20 | } 21 | 22 | @Override 23 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 24 | return entity.isAutoSpinAttack(); 25 | } 26 | 27 | @Override 28 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 29 | return BodyPart.values(); 30 | } 31 | 32 | @Override 33 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 34 | return 3600; 35 | } 36 | 37 | @Override 38 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 39 | float tickCounter) { 40 | // Do nothing 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/vanilla/DeathAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.vanilla; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 6 | //? if >= 1.21.11 { 7 | 8 | import net.minecraft.client.model.player.*; 9 | //? } else { 10 | /* 11 | import net.minecraft.client.model.*; 12 | *///? } 13 | import net.minecraft.client.player.AbstractClientPlayer; 14 | import net.minecraft.world.entity.Pose; 15 | 16 | public class DeathAnimation extends BasicAnimation { 17 | 18 | @Override 19 | public boolean isEnabled() { 20 | return true; 21 | } 22 | 23 | @Override 24 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 25 | return entity.getPose() == Pose.DYING; 26 | } 27 | 28 | @Override 29 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 30 | return BodyPart.values(); 31 | } 32 | 33 | @Override 34 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 35 | return 3600; 36 | } 37 | 38 | @Override 39 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 40 | float tickCounter) { 41 | // Do nothing 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/fullbody/PassengerAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.fullbody; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 6 | //? if >= 1.21.11 { 7 | 8 | import net.minecraft.client.model.player.*; 9 | //? } else { 10 | /* 11 | import net.minecraft.client.model.*; 12 | *///? } 13 | import net.minecraft.client.player.AbstractClientPlayer; 14 | 15 | public class PassengerAnimation extends BasicAnimation { 16 | 17 | @Override 18 | public boolean isEnabled() { 19 | return true; 20 | } 21 | 22 | @Override 23 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 24 | return entity.isPassenger(); 25 | } 26 | 27 | private final BodyPart[] parts = new BodyPart[] { BodyPart.BODY }; 28 | 29 | @Override 30 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 31 | return parts; 32 | } 33 | 34 | @Override 35 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 36 | return 3500; 37 | } 38 | 39 | @Override 40 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 41 | float tickCounter) { 42 | // Do nothing, prevents other animations like Ladder taking controll 43 | } 44 | 45 | } 46 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/LivingEntityMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | //? if >= 1.21.5 { 7 | 8 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 9 | //? } else { 10 | /* 11 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; 12 | *///? } 13 | 14 | import dev.tr7zw.notenoughanimations.access.PlayerData; 15 | import net.minecraft.world.entity.LivingEntity; 16 | 17 | @Mixin(LivingEntity.class) 18 | public class LivingEntityMixin { 19 | 20 | //? if >= 1.21.5 { 21 | 22 | @Inject(method = "tickHeadTurn", at = @At("HEAD"), cancellable = true) 23 | protected void tickHeadTurn(float g, CallbackInfo info) { 24 | //? } else { 25 | /* 26 | @Inject(method = "tickHeadTurn", at = @At("HEAD"), cancellable = true) 27 | protected void tickHeadTurn(float f, float g, CallbackInfoReturnable info) { 28 | *///? } 29 | if (this instanceof PlayerData) { 30 | PlayerData data = (PlayerData) this; 31 | if (data.isDisableBodyRotation()) { 32 | data.setDisableBodyRotation(false); 33 | //? if < 1.21.5 { 34 | /* 35 | info.setReturnValue(g); 36 | *///? } 37 | info.cancel(); 38 | } 39 | } 40 | } 41 | 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/access/PlayerData.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.access; 2 | 3 | import java.util.function.Supplier; 4 | 5 | import dev.tr7zw.notenoughanimations.versionless.animations.DataHolder; 6 | import net.minecraft.world.entity.Pose; 7 | import net.minecraft.world.item.ItemStack; 8 | 9 | public interface PlayerData { 10 | 11 | public int isUpdated(int frameId); 12 | 13 | public void setUpdated(int frameId); 14 | 15 | public float[] getLastRotations(); 16 | 17 | public ItemStack getSideSword(); 18 | 19 | public void setSideSword(ItemStack item); 20 | 21 | /** 22 | * Disables rotationlocking, so the animation has full controll 23 | * 24 | * @param val 25 | */ 26 | public void setDisableBodyRotation(boolean val); 27 | 28 | public boolean isDisableBodyRotation(); 29 | 30 | /** 31 | * Overwrites rotationlocking to be active 32 | * 33 | * @param val 34 | */ 35 | public void setRotateBodyToHead(boolean val); 36 | 37 | public boolean isRotateBodyToHead(); 38 | 39 | public ItemStack[] getLastHeldItems(); 40 | 41 | public int getItemSwapAnimationTimer(); 42 | 43 | public void setItemSwapAnimationTimer(int count); 44 | 45 | public int getLastAnimationSwapTick(); 46 | 47 | public void setLastAnimationSwapTick(int count); 48 | 49 | public void setPoseOverwrite(Pose state); 50 | 51 | public Pose getPoseOverwrite(); 52 | 53 | public T getData(DataHolder holder, Supplier builder); 54 | 55 | } 56 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/NEABootstrap.java: -------------------------------------------------------------------------------- 1 | //? if forge { 2 | /* 3 | package dev.tr7zw.notenoughanimations; 4 | 5 | import net.minecraftforge.api.distmarker.Dist; 6 | import net.minecraftforge.fml.DistExecutor; 7 | import net.minecraftforge.fml.common.Mod; 8 | import net.minecraftforge.fml.javafmlmod.FMLJavaModLoadingContext; 9 | import dev.tr7zw.transition.loader.ModLoaderUtil; 10 | 11 | @Mod("notenoughanimations") 12 | public class NEABootstrap { 13 | 14 | public NEABootstrap(FMLJavaModLoadingContext context) { 15 | ModLoaderUtil.setModLoadingContext(context); 16 | DistExecutor.unsafeRunWhenOn(Dist.CLIENT, () -> () -> new NEAnimationsMod().onInitializeClient()); 17 | } 18 | public NEABootstrap() { 19 | this(FMLJavaModLoadingContext.get()); 20 | } 21 | 22 | } 23 | *///? } else if neoforge { 24 | /* 25 | package dev.tr7zw.notenoughanimations; 26 | 27 | import net.neoforged.api.distmarker.Dist; 28 | import net.neoforged.fml.loading.FMLEnvironment; 29 | import net.neoforged.fml.common.Mod; 30 | import dev.tr7zw.transition.loader.ModLoaderEventUtil; 31 | 32 | @Mod("notenoughanimations") 33 | public class NEABootstrap { 34 | 35 | public NEABootstrap() { 36 | //? if < 1.21.9 { 37 | /^ 38 | if(FMLEnvironment.dist == Dist.CLIENT) { 39 | ^///? } else { 40 | 41 | if(FMLEnvironment.getDist() == Dist.CLIENT) { 42 | //? } 43 | ModLoaderEventUtil.registerClientSetupListener(() -> new NEAnimationsMod().onInitializeClient()); 44 | } 45 | } 46 | 47 | } 48 | *///? } 49 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/vanilla/SwimAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.vanilla; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 6 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 7 | //? if >= 1.21.11 { 8 | 9 | import net.minecraft.client.model.player.*; 10 | //? } else { 11 | /* 12 | import net.minecraft.client.model.*; 13 | *///? } 14 | import net.minecraft.client.player.AbstractClientPlayer; 15 | import net.minecraft.world.entity.Pose; 16 | 17 | public class SwimAnimation extends BasicAnimation { 18 | 19 | @Override 20 | public boolean isEnabled() { 21 | return true; 22 | } 23 | 24 | @Override 25 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 26 | return entity.getPose() == Pose.SWIMMING && (entity.isInWater() || !NEABaseMod.config.enableCrawlingAnimation); 27 | } 28 | 29 | @Override 30 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 31 | return BodyPart.values(); 32 | } 33 | 34 | @Override 35 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 36 | return 3600; 37 | } 38 | 39 | @Override 40 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 41 | float tickCounter) { 42 | // Do nothing 43 | } 44 | 45 | } 46 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/NEABaseMod.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless; 2 | 3 | import java.io.File; 4 | import java.io.IOException; 5 | import java.nio.charset.StandardCharsets; 6 | import java.nio.file.Files; 7 | 8 | import org.apache.logging.log4j.LogManager; 9 | import org.apache.logging.log4j.Logger; 10 | 11 | import com.google.gson.Gson; 12 | import com.google.gson.GsonBuilder; 13 | 14 | import dev.tr7zw.notenoughanimations.versionless.animations.BowAnimation; 15 | import dev.tr7zw.notenoughanimations.versionless.config.Config; 16 | 17 | public class NEABaseMod { 18 | 19 | public static final Logger LOGGER = LogManager.getLogger("NotEnoughAnimations"); 20 | public static Config config; 21 | protected final File settingsFile = new File("config", "notenoughanimations.json"); 22 | protected final Gson gson = new GsonBuilder().setPrettyPrinting().create(); 23 | 24 | public NEABaseMod() { 25 | super(); 26 | } 27 | 28 | protected void setupConfig() { 29 | try { 30 | Class clientClass = Class.forName("dev.tr7zw.firstperson.FirstPersonModelCore"); 31 | // Firstperson is installed, change some default settings to fit 32 | config.bowAnimation = BowAnimation.CUSTOM_V1; 33 | } catch (Throwable ex) { 34 | // ignored 35 | } 36 | } 37 | 38 | public void writeConfig() { 39 | if (settingsFile.exists()) 40 | settingsFile.delete(); 41 | try { 42 | Files.write(settingsFile.toPath(), gson.toJson(config).getBytes(StandardCharsets.UTF_8)); 43 | } catch (IOException e1) { 44 | e1.printStackTrace(); 45 | } 46 | } 47 | 48 | } -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/vanilla/SleepAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.vanilla; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | //? if >= 1.21.11 { 9 | 10 | import net.minecraft.client.model.player.*; 11 | //? } else { 12 | /* 13 | import net.minecraft.client.model.*; 14 | *///? } 15 | import net.minecraft.client.player.AbstractClientPlayer; 16 | import net.minecraft.world.entity.HumanoidArm; 17 | 18 | public class SleepAnimation extends BasicAnimation { 19 | 20 | @Override 21 | public boolean isEnabled() { 22 | return true; 23 | } 24 | 25 | @Override 26 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 27 | return entity.isSleeping(); 28 | } 29 | 30 | private final BodyPart[] bothHands = BodyPart.values(); 31 | 32 | @Override 33 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 34 | return bothHands; 35 | } 36 | 37 | @Override 38 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 39 | return 3600; 40 | } 41 | 42 | @Override 43 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 44 | float tickCounter) { 45 | if (NEABaseMod.config.freezeArmsInBed) { 46 | HumanoidArm arm = part == BodyPart.LEFT_ARM ? HumanoidArm.LEFT : HumanoidArm.RIGHT; 47 | AnimationUtil.applyArmTransforms(model, arm, 0, 0f, 0f); 48 | } 49 | } 50 | 51 | } 52 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/VanillaProjectileWeaponAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import java.util.EnumSet; 4 | 5 | import dev.tr7zw.notenoughanimations.access.PlayerData; 6 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 7 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 8 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 9 | import net.minecraft.client.model.HumanoidModel.ArmPose; 10 | import net.minecraft.client.player.AbstractClientPlayer; 11 | import net.minecraft.world.InteractionHand; 12 | import net.minecraft.world.entity.HumanoidArm; 13 | 14 | public abstract class VanillaProjectileWeaponAnimation extends BasicAnimation { 15 | 16 | private ArmPose rightArmPose; 17 | private ArmPose leftArmPose; 18 | private final BodyPart[] parts = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM, BodyPart.BODY }; 19 | 20 | @Override 21 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 22 | rightArmPose = AnimationUtil.getArmPose(entity, 23 | entity.getMainArm() == HumanoidArm.LEFT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 24 | leftArmPose = AnimationUtil.getArmPose(entity, 25 | entity.getMainArm() == HumanoidArm.RIGHT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 26 | return getTwoHandedAnimations().contains(leftArmPose) || getTwoHandedAnimations().contains(rightArmPose); 27 | } 28 | 29 | protected abstract EnumSet getTwoHandedAnimations(); 30 | 31 | @Override 32 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 33 | return parts; 34 | } 35 | 36 | @Override 37 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 38 | return 3200; 39 | } 40 | 41 | } 42 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/fullbody/ActionRotationLockAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.fullbody; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 6 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 7 | //? if >= 1.21.11 { 8 | 9 | import net.minecraft.client.model.player.*; 10 | //? } else { 11 | /* 12 | import net.minecraft.client.model.*; 13 | *///? } 14 | import net.minecraft.client.player.AbstractClientPlayer; 15 | 16 | public class ActionRotationLockAnimation extends BasicAnimation { 17 | 18 | private BodyPart[] target = new BodyPart[] { BodyPart.BODY }; 19 | 20 | @Override 21 | public boolean isEnabled() { 22 | return NEABaseMod.config.enableRotationLocking; 23 | } 24 | 25 | @Override 26 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 27 | if (entity.getUseItemRemainingTicks() > 0) { 28 | var action = entity.getUseItem().getUseAnimation(); 29 | // Eating/Drinking 30 | // funky way of accessing the enum because it got renamed between versions 31 | if (action == action.EAT || action == action.DRINK || action == action.BLOCK) { 32 | return true; 33 | } 34 | } 35 | return false; 36 | } 37 | 38 | @Override 39 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 40 | return target; 41 | } 42 | 43 | @Override 44 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 45 | // lower than animations like ladder 46 | return 1250; 47 | } 48 | 49 | @Override 50 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 51 | float tickCounter) { 52 | data.setRotateBodyToHead(true); 53 | } 54 | 55 | } 56 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/NarutoRunningAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | //? if >= 1.21.11 { 9 | 10 | import net.minecraft.client.model.player.*; 11 | //? } else { 12 | /* 13 | import net.minecraft.client.model.*; 14 | *///? } 15 | import net.minecraft.client.player.AbstractClientPlayer; 16 | import net.minecraft.world.entity.HumanoidArm; 17 | 18 | public class NarutoRunningAnimation extends BasicAnimation { 19 | 20 | @Override 21 | public boolean isEnabled() { 22 | return NEABaseMod.config.narutoRunning; 23 | } 24 | 25 | @Override 26 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 27 | return entity.isSprinting(); 28 | } 29 | 30 | private final BodyPart[] arms = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM }; 31 | 32 | @Override 33 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 34 | return arms; 35 | } 36 | 37 | @Override 38 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 39 | return 500; 40 | } 41 | 42 | @Override 43 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 44 | float tickCounter) { 45 | if (part == BodyPart.LEFT_ARM && !AnimationUtil.isSwingingArm(entity, part)) { 46 | AnimationUtil.applyArmTransforms(model, HumanoidArm.LEFT, 1f, -0.2f, 0.3f); 47 | } 48 | if (part == BodyPart.RIGHT_ARM && !AnimationUtil.isSwingingArm(entity, part)) { 49 | AnimationUtil.applyArmTransforms(model, HumanoidArm.RIGHT, 1f, -0.2f, 0.3f); 50 | } 51 | } 52 | 53 | } 54 | -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/lang/pt_pt.json: -------------------------------------------------------------------------------- 1 | { 2 | "text.nea.title": "Definições de Not Enough Animations", 3 | "text.nea.enable.animationsmoothing": "Suavização da Animação", 4 | "text.nea.smoothingSpeed": "Intensidade da Suavização", 5 | "text.nea.enable.inworldmaprendering": "Mostrar Mapa a Todos", 6 | "text.nea.enable.offhandhiding": "Corrigir Animações do Arco", 7 | "text.nea.enable.rotationlocking": "Prender Animação Quando Move", 8 | "text.nea.enable.ladderanimation": "Animação na Escada", 9 | "text.nea.enable.eatdrinkanimation": "Animação de Comer/Beber", 10 | "text.nea.enable.rowboatanimation": "Animação de Remar", 11 | "text.nea.enable.horseanimation": "Animação de Andar a Cavalo", 12 | "text.nea.enable.dontholditemsinbed": "Não Segurar Itens A Dormir", 13 | "text.nea.enable.freezearmsinbed": "Não Se Mexer a Dormir", 14 | "text.nea.rotationlock": "Prender Rotação", 15 | "text.nea.rotationlock.NONE": "Nenhum", 16 | "text.nea.rotationlock.FIXED": "Corrigido", 17 | "text.nea.rotationlock.SMOOTH": "Suave", 18 | "text.nea.enable.showlastusedsword": "Exibir Última Espada", 19 | "text.nea.enable.crawling": "Animação de Ratejar", 20 | "text.nea.enable.rotatetoladder": "Enconstar o Corpo À Escada", 21 | "text.nea.enable.holdupallitems": "Elevar Todos os Itens", 22 | "text.nea.ladderAnimationAmplifier": "Intensidade do Braço na Escada", 23 | "text.nea.ladderAnimationArmHeight": "Altura do Braço na Escada", 24 | "text.nea.ladderAnimationArmSpeed": "Velocidade do Braço na Escada", 25 | "text.nea.enable.itemSwapAnimation": "Animação de Trocar Itens", 26 | "text.nea.enable.tweakElytraAnimation": "Mudar o Voo de Elytra", 27 | "text.nea.enable.petAnimation": "Acariciar Lobos/Gatos", 28 | "text.nea.enable.fallingAnimation": "[WIP]Animação de Queda", 29 | "text.nea.enable.freezingAnimation": "Animação de Congelar", 30 | "text.nea.enable.huggingAnimation": "Simples Animação de Abraçar", 31 | "text.nea.enable.narutoRunning": "❝Naruto Running❞", 32 | "text.nea.enable.enableInWorldBookRendering": "[WIP]Mostrar Livros a Todos", 33 | "text.nea.disableLegSmoothing": "Desativar Suavizar Pernas" 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/ItemInHandRendererMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import com.mojang.blaze3d.vertex.PoseStack; 9 | 10 | import dev.tr7zw.notenoughanimations.NEAnimationsLoader; 11 | import net.minecraft.client.renderer.ItemInHandRenderer; 12 | import net.minecraft.world.entity.HumanoidArm; 13 | 14 | @Mixin(ItemInHandRenderer.class) 15 | public class ItemInHandRendererMixin { 16 | 17 | @Inject(method = "renderPlayerArm", at = @At("HEAD")) 18 | //? if >= 1.21.9 { 19 | 20 | private void renderPlayerArm(PoseStack poseStack, 21 | net.minecraft.client.renderer.SubmitNodeCollector submitNodeCollector, int i, float f, float g, 22 | HumanoidArm humanoidArm, CallbackInfo info) { 23 | //? } else { 24 | /* 25 | private void renderPlayerArm(PoseStack poseStack, net.minecraft.client.renderer.MultiBufferSource multiBufferSource, int packedLight, 26 | float equippedProgress, float swingProgress, net.minecraft.world.entity.HumanoidArm humanoidArm, CallbackInfo info) { 27 | *///? } 28 | NEAnimationsLoader.INSTANCE.playerTransformer.renderingFirstPersonArm(true); 29 | } 30 | 31 | @Inject(method = "renderPlayerArm", at = @At("RETURN")) 32 | //? if >= 1.21.9 { 33 | 34 | private void renderPlayerArmEnd(PoseStack poseStack, 35 | net.minecraft.client.renderer.SubmitNodeCollector submitNodeCollector, int i, float f, float g, 36 | HumanoidArm humanoidArm, CallbackInfo info) { 37 | //? } else { 38 | /* 39 | private void renderPlayerArmEnd(PoseStack poseStack, net.minecraft.client.renderer.MultiBufferSource multiBufferSource, int packedLight, 40 | float equippedProgress, float swingProgress, net.minecraft.world.entity.HumanoidArm humanoidArm, CallbackInfo info) { 41 | *///? } 42 | NEAnimationsLoader.INSTANCE.playerTransformer.renderingFirstPersonArm(false); 43 | } 44 | 45 | } 46 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/config/ConfigUpgrader.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless.config; 2 | 3 | public class ConfigUpgrader { 4 | 5 | public static boolean upgradeConfig(Config config) { 6 | boolean changed = false; 7 | if (config.configVersion <= 1) { 8 | config.configVersion = 2; 9 | changed = true; 10 | } 11 | if (config.configVersion <= 2) { 12 | config.configVersion = 3; 13 | changed = true; 14 | } 15 | if (config.configVersion <= 3) { 16 | config.configVersion = 4; 17 | config.dontHoldItemsInBed = true; 18 | config.freezeArmsInBed = true; 19 | changed = true; 20 | } 21 | if (config.configVersion <= 4) { 22 | config.configVersion = 5; 23 | config.holdingItems.add("minecraft:soul_torch"); 24 | config.holdingItems.add("minecraft:soul_lantern"); 25 | changed = true; 26 | } 27 | if (config.configVersion <= 5) { 28 | config.configVersion = 6; 29 | changed = true; 30 | } 31 | if (config.configVersion <= 6) { 32 | config.configVersion = 7; 33 | changed = true; 34 | } 35 | if (config.configVersion <= 7) { 36 | config.configVersion = 8; 37 | config.holdingItems.add("minecraft:recovery_compass"); 38 | changed = true; 39 | } 40 | if (config.configVersion <= 8) { 41 | config.configVersion = 9; 42 | config.showLastUsedSword = false; // turning this off by default 43 | changed = true; 44 | } 45 | if (config.configVersion <= 9) { 46 | config.configVersion = 10; 47 | config.animationSmoothingSpeed = 0.5f; // size changed 48 | changed = true; 49 | } 50 | if (config.configVersion <= 10) { 51 | config.configVersion = 11; 52 | config.animationSmoothingSpeed = 0.2f; // 0.2 instead of 0.5, what was I thinking 53 | changed = true; 54 | } 55 | // check for more changes here 56 | 57 | return changed; 58 | } 59 | 60 | } 61 | -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/lang/uk_ua.json: -------------------------------------------------------------------------------- 1 | { 2 | "text.nea.title": "Not Enough Animations Settings", 3 | "text.nea.enable.animationsmoothing": "Згладжування анімації", 4 | "text.nea.smoothingSpeed": "Значення згладжування", 5 | "text.nea.enable.inworldmaprendering": "Візуалізація мапи світу", 6 | "text.nea.enable.offhandhiding": "Виправлення анімації лука", 7 | "text.nea.enable.rotationlocking": "Блокування повороту анімації", 8 | "text.nea.enable.ladderanimation": "Анімація драбини", 9 | "text.nea.enable.eatdrinkanimation": "Анімація їжі/пиття", 10 | "text.nea.enable.rowboatanimation": "Анімація веслування на човні", 11 | "text.nea.enable.horseanimation": "Анімація верхової їзди", 12 | "text.nea.enable.dontholditemsinbed": "Без предметів під час сну", 13 | "text.nea.enable.freezearmsinbed": "Без рухів під час сну", 14 | "text.nea.rotationlock": "Блокування обертання", 15 | "text.nea.rotationlock.NONE": "Жоден", 16 | "text.nea.rotationlock.FIXED": "Фіксоване", 17 | "text.nea.rotationlock.SMOOTH": "Згладжене", 18 | "text.nea.enable.showlastusedsword": "Меч у піхвах", 19 | "text.nea.enable.crawling": "Анімація повзання", 20 | "text.nea.enable.rotatetoladder": "Прив'язати тіло до драбини", 21 | "text.nea.enable.holdupallitems": "Тримати усі предмети", 22 | "text.nea.ladderAnimationAmplifier": "Підсилювач руки на драбині", 23 | "text.nea.ladderAnimationArmHeight": "Висота руки на драбині", 24 | "text.nea.ladderAnimationArmSpeed": "Швидкість руки на драбині", 25 | "text.nea.enable.itemSwapAnimation": "Анімація зміни предметів", 26 | "text.nea.enable.tweakElytraAnimation": "Налаштувати політ елітри", 27 | "text.nea.enable.petAnimation": "Вовки/Коти", 28 | "text.nea.enable.fallingAnimation": "[WIP]Анімація падіння", 29 | "text.nea.enable.freezingAnimation": "Анімація обморожування", 30 | "text.nea.enable.huggingAnimation": "Анімація обіймів", 31 | "text.nea.enable.narutoRunning": "❝Біг Наруто❞", 32 | "text.nea.enable.enableInWorldBookRendering": "[WIP]Книги", 33 | "text.nea.disableLegSmoothing": "Вимкнути згладжування ніг", 34 | "text.nea.enable.bowAnimation": "Анімація лука", 35 | "text.nea.enable.bowAnimation.VANILLA": "Ваніль", 36 | "text.nea.enable.bowAnimation.CUSTOM_V1": "Спеціальний V1" 37 | } 38 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/fullbody/BurningAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.fullbody; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | //? if >= 1.21.11 { 9 | 10 | import net.minecraft.client.model.player.*; 11 | //? } else { 12 | /* 13 | import net.minecraft.client.model.*; 14 | *///? } 15 | import net.minecraft.client.player.AbstractClientPlayer; 16 | import net.minecraft.util.Mth; 17 | import net.minecraft.world.effect.MobEffects; 18 | import net.minecraft.world.entity.HumanoidArm; 19 | import net.minecraft.world.level.block.Blocks; 20 | 21 | public class BurningAnimation extends BasicAnimation { 22 | 23 | @Override 24 | public boolean isEnabled() { 25 | return NEABaseMod.config.burningAnimation; 26 | } 27 | 28 | @Override 29 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 30 | return entity.isOnFire() && !entity.hasEffect(MobEffects.FIRE_RESISTANCE); 31 | } 32 | 33 | private BodyPart[] parts = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM, BodyPart.HEAD }; 34 | 35 | @Override 36 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 37 | return parts; 38 | } 39 | 40 | @Override 41 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 42 | return 400; 43 | } 44 | 45 | @Override 46 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 47 | float tickCounter) { 48 | if (part == BodyPart.HEAD) { 49 | AnimationUtil.setHeadYRot(model, model.head.yRot + Mth.sin(entity.tickCount) * 0.1f); 50 | return; 51 | } 52 | float armHeight = Mth.sin(entity.tickCount) * 0.1f; 53 | if (part == BodyPart.LEFT_ARM) 54 | armHeight *= -1; 55 | AnimationUtil.applyArmTransforms(model, part == BodyPart.LEFT_ARM ? HumanoidArm.LEFT : HumanoidArm.RIGHT, 56 | -2.6f + armHeight, -0.2f, -0.3f); 57 | } 58 | 59 | } 60 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/LivingEntityRendererMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import dev.tr7zw.notenoughanimations.access.ExtendedItemStackRenderState; 4 | import dev.tr7zw.notenoughanimations.access.ExtendedLivingRenderState; 5 | import net.minecraft.client.renderer.entity.LivingEntityRenderer; 6 | import net.minecraft.world.entity.HumanoidArm; 7 | import net.minecraft.world.entity.LivingEntity; 8 | import org.spongepowered.asm.mixin.Mixin; 9 | import org.spongepowered.asm.mixin.injection.At; 10 | import org.spongepowered.asm.mixin.injection.Inject; 11 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 12 | //? if >= 1.21.4 { 13 | 14 | import net.minecraft.client.renderer.entity.state.ArmedEntityRenderState; 15 | //? } 16 | 17 | @Mixin(LivingEntityRenderer.class) 18 | public class LivingEntityRendererMixin { 19 | 20 | //? if >= 1.21.2 { 21 | 22 | @Inject(method = "extractRenderState(Lnet/minecraft/world/entity/LivingEntity;Lnet/minecraft/client/renderer/entity/state/LivingEntityRenderState;F)V", at = @At("HEAD")) 23 | private void addEntityToRenderState(LivingEntity livingEntity, 24 | net.minecraft.client.renderer.entity.state.LivingEntityRenderState livingEntityRenderState, float f, 25 | CallbackInfo ci) { 26 | ((ExtendedLivingRenderState) livingEntityRenderState).setEntity(livingEntity); 27 | //? if >= 1.21.11 { 28 | 29 | if (livingEntityRenderState instanceof ArmedEntityRenderState armed) { 30 | ((ExtendedItemStackRenderState) armed.leftHandItemState) 31 | .setItemStack(livingEntity.getItemHeldByArm(HumanoidArm.LEFT)); 32 | ((ExtendedItemStackRenderState) armed.rightHandItemState) 33 | .setItemStack(livingEntity.getItemHeldByArm(HumanoidArm.RIGHT)); 34 | } 35 | //? } else if >= 1.21.4 { 36 | /* 37 | if (livingEntityRenderState instanceof ArmedEntityRenderState armed) { 38 | ((ExtendedItemStackRenderState) armed.leftHandItem) 39 | .setItemStack(livingEntity.getItemHeldByArm(HumanoidArm.LEFT)); 40 | ((ExtendedItemStackRenderState) armed.rightHandItem) 41 | .setItemStack(livingEntity.getItemHeldByArm(HumanoidArm.RIGHT)); 42 | } 43 | *///? } 44 | } 45 | //? } 46 | } 47 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/vanilla/VanillaTwoHandedAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.vanilla; 2 | 3 | import java.util.EnumSet; 4 | 5 | import dev.tr7zw.notenoughanimations.access.PlayerData; 6 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 7 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 8 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 9 | import net.minecraft.client.model.HumanoidModel.ArmPose; 10 | //? if >= 1.21.11 { 11 | 12 | import net.minecraft.client.model.player.*; 13 | //? } else { 14 | /* 15 | import net.minecraft.client.model.*; 16 | *///? } 17 | import net.minecraft.client.player.AbstractClientPlayer; 18 | import net.minecraft.world.InteractionHand; 19 | import net.minecraft.world.entity.HumanoidArm; 20 | 21 | public class VanillaTwoHandedAnimation extends BasicAnimation { 22 | 23 | @Override 24 | public boolean isEnabled() { 25 | return true; 26 | } 27 | 28 | private ArmPose rightArmPose; 29 | private ArmPose leftArmPose; 30 | private final EnumSet twoHandedAnimatios = EnumSet.of(ArmPose.CROSSBOW_CHARGE, ArmPose.BOW_AND_ARROW, 31 | ArmPose.CROSSBOW_HOLD); 32 | private final BodyPart[] parts = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM, BodyPart.BODY }; 33 | 34 | @Override 35 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 36 | rightArmPose = AnimationUtil.getArmPose(entity, 37 | entity.getMainArm() == HumanoidArm.LEFT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 38 | leftArmPose = AnimationUtil.getArmPose(entity, 39 | entity.getMainArm() == HumanoidArm.RIGHT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 40 | return twoHandedAnimatios.contains(leftArmPose) || twoHandedAnimatios.contains(rightArmPose); 41 | } 42 | 43 | @Override 44 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 45 | return parts; 46 | } 47 | 48 | @Override 49 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 50 | return 3100; 51 | } 52 | 53 | @Override 54 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 55 | float tickCounter) { 56 | // Vanilla, do nothing 57 | } 58 | 59 | } 60 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/vanilla/VanillaShieldAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.vanilla; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | import net.minecraft.client.model.HumanoidModel.ArmPose; 9 | //? if >= 1.21.11 { 10 | 11 | import net.minecraft.client.model.player.*; 12 | //? } else { 13 | /* 14 | import net.minecraft.client.model.*; 15 | *///? } 16 | import net.minecraft.client.player.AbstractClientPlayer; 17 | import net.minecraft.world.InteractionHand; 18 | import net.minecraft.world.entity.HumanoidArm; 19 | 20 | public class VanillaShieldAnimation extends BasicAnimation { 21 | 22 | @Override 23 | public boolean isEnabled() { 24 | return true; 25 | } 26 | 27 | private ArmPose rightArmPose; 28 | private ArmPose leftArmPose; 29 | private final BodyPart[] left = new BodyPart[] { BodyPart.LEFT_ARM }; 30 | private final BodyPart[] right = new BodyPart[] { BodyPart.RIGHT_ARM }; 31 | 32 | @Override 33 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 34 | rightArmPose = AnimationUtil.getArmPose(entity, 35 | entity.getMainArm() == HumanoidArm.LEFT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 36 | leftArmPose = AnimationUtil.getArmPose(entity, 37 | entity.getMainArm() == HumanoidArm.RIGHT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 38 | return ArmPose.BLOCK == leftArmPose || ArmPose.BLOCK == rightArmPose; 39 | } 40 | 41 | @Override 42 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 43 | if (ArmPose.BLOCK == leftArmPose) { 44 | return left; 45 | } 46 | if (ArmPose.BLOCK == rightArmPose) { 47 | return right; 48 | } 49 | // ??? 50 | return new BodyPart[0]; 51 | } 52 | 53 | @Override 54 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 55 | return 3100; 56 | } 57 | 58 | @Override 59 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 60 | float tickCounter) { 61 | 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /src/test/java/dev/tr7zw/tests/MixinTests.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.tests; 2 | 3 | import org.junit.jupiter.api.BeforeAll; 4 | import org.junit.jupiter.api.Test; 5 | import org.objenesis.Objenesis; 6 | import org.objenesis.ObjenesisStd; 7 | 8 | import net.minecraft.SharedConstants; 9 | //? if >= 1.21.11 { 10 | 11 | import net.minecraft.client.model.player.*; 12 | //? } else { 13 | /* 14 | import net.minecraft.client.model.*; 15 | *///? } 16 | import net.minecraft.client.player.RemotePlayer; 17 | import net.minecraft.client.renderer.ItemInHandRenderer; 18 | import net.minecraft.client.renderer.LevelRenderer; 19 | import net.minecraft.client.renderer.entity.layers.ItemInHandLayer; 20 | import net.minecraft.server.Bootstrap; 21 | 22 | public class MixinTests { 23 | 24 | @BeforeAll 25 | public static void setup() { 26 | SharedConstants.tryDetectVersion(); 27 | Bootstrap.bootStrap(); 28 | } 29 | 30 | @Test 31 | public void testMixins() { 32 | Objenesis objenesis = new ObjenesisStd(); 33 | objenesis.newInstance(ItemInHandLayer.class); 34 | objenesis.newInstance(ItemInHandRenderer.class); 35 | objenesis.newInstance(LevelRenderer.class); 36 | objenesis.newInstance(RemotePlayer.class); 37 | objenesis.newInstance(PlayerModel.class); 38 | //? if >= 1.21.9 { 39 | 40 | objenesis.newInstance(net.minecraft.client.renderer.entity.player.AvatarRenderer.class); 41 | //? } else { 42 | /* 43 | objenesis.newInstance(net.minecraft.client.renderer.entity.player.PlayerRenderer.class); 44 | *///? } 45 | objenesis.newInstance(LevelRenderer.class); 46 | } 47 | 48 | // @Test 49 | // public void langTests() throws Throwable { 50 | // Language lang = TestUtil.loadDefault("/assets/notenoughanimations/lang/en_us.json"); 51 | // NEAnimationsLoader.INSTANCE = new TestMod(); 52 | // NEAnimationsLoader.config = new Config(); 53 | // CustomConfigScreen screen = (CustomConfigScreen) ConfigScreenProvider.createConfigScreen(null); 54 | // List> options = TestUtil.bootStrapCustomConfigScreen(screen); 55 | // assertNotEquals(screen.getTitle().getString(), lang.getOrDefault(screen.getTitle().getString())); 56 | // for (OptionInstance option : options) { 57 | // Set keys = TestUtil.getKeys(option, true); 58 | // for (String key : keys) { 59 | // System.out.println(key + " " + lang.getOrDefault(key)); 60 | // assertNotEquals(key, lang.getOrDefault(key)); 61 | // } 62 | // } 63 | // } 64 | 65 | } 66 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/fullbody/FreezingAnimation.java: -------------------------------------------------------------------------------- 1 | //? if >= 1.17.0 { 2 | 3 | package dev.tr7zw.notenoughanimations.animations.fullbody; 4 | 5 | import dev.tr7zw.notenoughanimations.access.PlayerData; 6 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 7 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 8 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 9 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 10 | import dev.tr7zw.transition.mc.*; 11 | //? if >= 1.21.11 { 12 | 13 | import net.minecraft.client.model.player.*; 14 | //? } else { 15 | /* 16 | import net.minecraft.client.model.*; 17 | *///? } 18 | import net.minecraft.client.player.AbstractClientPlayer; 19 | import net.minecraft.world.entity.HumanoidArm; 20 | import net.minecraft.world.level.block.Blocks; 21 | 22 | public class FreezingAnimation extends BasicAnimation { 23 | 24 | @Override 25 | public boolean isEnabled() { 26 | return NEABaseMod.config.freezingAnimation; 27 | } 28 | 29 | @Override 30 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 31 | //? if >= 1.18.0 { 32 | 33 | return entity.canFreeze() 34 | && GeneralUtil.getWorld().getBlockStatesIfLoaded(entity.getBoundingBox().deflate(1.0E-6D)) 35 | //? } else { 36 | 37 | // return entity.canFreeze() && entity.level.getBlockStatesIfLoaded(entity.getBoundingBox().deflate(1.0E-6D)) 38 | //? } 39 | .anyMatch(blockState -> (blockState.is(Blocks.POWDER_SNOW) 40 | || blockState.is(Blocks.POWDER_SNOW_CAULDRON))); 41 | } 42 | 43 | private BodyPart[] parts = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM }; 44 | 45 | @Override 46 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 47 | return parts; 48 | } 49 | 50 | @Override 51 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 52 | return 400; 53 | } 54 | 55 | @Override 56 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 57 | float tickCounter) { 58 | 59 | if (part == BodyPart.LEFT_ARM) { 60 | float position = (float) (Math.random() / 10 + -1.3f); 61 | AnimationUtil.applyArmTransforms(model, HumanoidArm.LEFT, -0.6f, 0.2f, position); 62 | } 63 | if (part == BodyPart.RIGHT_ARM) { 64 | float position = (float) (Math.random() / 10 + -1.0f); 65 | AnimationUtil.applyArmTransforms(model, HumanoidArm.RIGHT, -0.5f, 0.2f, position); 66 | } 67 | } 68 | 69 | } 70 | //? } 71 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/ClampCrossbowAnimations.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import java.util.EnumSet; 4 | 5 | import dev.tr7zw.notenoughanimations.access.PlayerData; 6 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 7 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 8 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 9 | import lombok.Getter; 10 | import net.minecraft.client.model.HumanoidModel.ArmPose; 11 | //? if >= 1.21.11 { 12 | 13 | import net.minecraft.client.model.player.*; 14 | //? } else { 15 | /* 16 | import net.minecraft.client.model.*; 17 | *///? } 18 | import net.minecraft.client.model.geom.ModelPart; 19 | import net.minecraft.client.player.AbstractClientPlayer; 20 | import net.minecraft.util.Mth; 21 | import net.minecraft.world.InteractionHand; 22 | import net.minecraft.world.entity.HumanoidArm; 23 | 24 | public class ClampCrossbowAnimations extends VanillaProjectileWeaponAnimation { 25 | 26 | @Getter 27 | private final EnumSet twoHandedAnimations = EnumSet.of(ArmPose.CROSSBOW_HOLD, ArmPose.CROSSBOW_CHARGE); 28 | 29 | @Override 30 | public boolean isEnabled() { 31 | return NEABaseMod.config.clampCrossbowAnimations; 32 | } 33 | 34 | @Override 35 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 36 | float tickCounter) { 37 | ModelPart mainArm = model.rightArm; 38 | ModelPart offArm = model.leftArm; 39 | BodyPart mainPart = BodyPart.RIGHT_ARM; 40 | BodyPart offPart = BodyPart.LEFT_ARM; 41 | boolean bowInLeftHand = (entity.getMainArm() == HumanoidArm.RIGHT 42 | && entity.getUsedItemHand() == InteractionHand.OFF_HAND) 43 | || (entity.getMainArm() == HumanoidArm.LEFT && entity.getUsedItemHand() == InteractionHand.MAIN_HAND) 44 | || (entity.getMainArm() == HumanoidArm.RIGHT 45 | && AnimationUtil.isChargedCrossbow(entity.getOffhandItem())) 46 | || (entity.getMainArm() == HumanoidArm.LEFT 47 | && AnimationUtil.isChargedCrossbow(entity.getMainHandItem())); 48 | if (bowInLeftHand) { 49 | mainArm = model.leftArm; 50 | offArm = model.rightArm; 51 | mainPart = BodyPart.LEFT_ARM; 52 | offPart = BodyPart.RIGHT_ARM; 53 | } 54 | 55 | if (part == mainPart) { 56 | mainArm.xRot = Mth.clamp(AnimationUtil.wrapDegrees(mainArm.xRot), -1.75f, 0f); 57 | } 58 | 59 | if (part == offPart) { 60 | offArm.xRot = Mth.clamp(AnimationUtil.wrapDegrees(offArm.xRot), -1.75f, 0f); 61 | } 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/NEAnimationsLoader.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations; 2 | 3 | import java.nio.charset.StandardCharsets; 4 | import java.nio.file.Files; 5 | 6 | import dev.tr7zw.notenoughanimations.config.ConfigScreenProvider; 7 | import dev.tr7zw.notenoughanimations.logic.AnimationProvider; 8 | import dev.tr7zw.notenoughanimations.logic.HeldItemHandler; 9 | import dev.tr7zw.notenoughanimations.logic.PlayerTransformer; 10 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 11 | import dev.tr7zw.notenoughanimations.versionless.config.Config; 12 | import dev.tr7zw.notenoughanimations.versionless.config.ConfigUpgrader; 13 | import dev.tr7zw.transition.loader.ModLoaderUtil; 14 | 15 | public abstract class NEAnimationsLoader extends NEABaseMod { 16 | 17 | public static NEAnimationsLoader INSTANCE; 18 | public PlayerTransformer playerTransformer; 19 | public HeldItemHandler heldItemHandler; 20 | public AnimationProvider animationProvider; 21 | private boolean lateInitCompleted = false; 22 | 23 | protected NEAnimationsLoader() { 24 | INSTANCE = this; 25 | ModLoaderUtil.disableDisplayTest(); 26 | ModLoaderUtil.registerConfigScreen(ConfigScreenProvider::createConfigScreen); 27 | } 28 | 29 | public void onEnable() { 30 | if (settingsFile.exists()) { 31 | try { 32 | config = gson.fromJson(new String(Files.readAllBytes(settingsFile.toPath()), StandardCharsets.UTF_8), 33 | Config.class); 34 | } catch (Exception ex) { 35 | System.out.println("Error while loading config! Creating a new one!"); 36 | ex.printStackTrace(); 37 | } 38 | } 39 | if (config == null) { 40 | config = new Config(); 41 | setupConfig(); 42 | writeConfig(); 43 | } else { 44 | if (ConfigUpgrader.upgradeConfig(config)) { 45 | writeConfig(); 46 | } 47 | } 48 | enable(); 49 | } 50 | 51 | private void enable() { 52 | playerTransformer = new PlayerTransformer(); 53 | heldItemHandler = new HeldItemHandler(); 54 | animationProvider = new AnimationProvider(); 55 | heldItemHandler.onLoad(); 56 | } 57 | 58 | private void lateInit() { 59 | animationProvider.refreshEnabledAnimations(); // refresh once after the game is loaded, so all other mods are 60 | // done initializing 61 | } 62 | 63 | public void clientTick() { 64 | // run this code later, so all other mods are done loading 65 | if (!lateInitCompleted) { 66 | lateInitCompleted = true; 67 | lateInit(); 68 | } 69 | playerTransformer.nextTick(); 70 | } 71 | 72 | } 73 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Not Enough Animations 2 | 3 | This mod brings a lot of missing third-person animations from the first-person or modifies them to be better representative to how they should look like or look like in the first-person. This mod was created as an expansion for the [First-Person Mod](https://www.curseforge.com/minecraft/mc-mods/first-person-model), but works completely on its own and is fully vanilla/3rd party server compatible(since it's all just visual). 4 | 5 | ### All features can be enabled/disabled individually in an ingame config screen! (Accessible via the ModList/ModMenu) 6 | 7 | Added/fixed animations: 8 | 9 | - Eating/Drinking 10 | 11 | ![](https://tr7zw.dev/nea/eating.png) 12 | ![](https://tr7zw.dev/nea/drinking.png) 13 | 14 | - Maps(Yes you can see the map content if your client has been sent the map by holding it once/seeing it in an item frame) 15 | 16 | ![](https://tr7zw.dev/nea/maps1.PNG) 17 | ![](https://tr7zw.dev/nea/maps2.PNG) 18 | 19 | - Shield placement(you block where you look, not where the body is rotated to. So this will rotate the body with the head while blocking) 20 | 21 | ![](https://tr7zw.dev/nea/shield.png) 22 | 23 | - Don't show items during two-handed animations(Hide the offhand item while using a bow/crossbow) 24 | 25 | ![](https://tr7zw.dev/nea/twoHands.PNG) 26 | 27 | - Boat rowing(No longer sitting there and staring at the self-moving Paddles) 28 | 29 | ![](https://tr7zw.dev/nea/boat.png) 30 | 31 | - Horses(at least act like you're holding the reins) 32 | 33 | ![](https://tr7zw.dev/nea/horse.png) 34 | 35 | - Looking at a compass/clock(this one is actually more eye candy for the First-person Mod to make the compass better usable, but won't hurt outside of that, can be modified in the config file to extend to more items) 36 | 37 | ![](https://tr7zw.dev/nea/compass.PNG) 38 | 39 | - Ladder/climbing animation 40 | 41 | ![](https://tr7zw.dev/nea/ladder.gif) 42 | 43 | - Crawling animation, replacing the swimming one while out of water 44 | 45 | ![](https://tr7zw.dev/nea/crawling.gif) 46 | 47 | - Smooth arm movement and transitions 48 | 49 | ![](https://tr7zw.dev/nea/smootharms.gif) 50 | 51 | ## License 52 | 53 | This project is licensed under [``tr7zw Protective License``](LICENSE). 54 | This license does not allow others to distribute the software/derivative works(in source or binary form). 55 | You have to contact the author to get permission for redistribution. (For example: Modpacks(that are not hosted on CurseForge), "Clients", mod hosting sites). 56 | Keep in mind that [Githubs TOS](https://docs.github.com/en/github/site-policy/github-terms-of-service#d-user-generated-content) and [Overwolfs TOS](https://www.overwolf.com/legal/terms/) apply at their respective places. This (among other things) means you don't need to ask to include the mod in a CurseForge Modpack and that by contributing code it explicitly gets the same license as the repository. 57 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/BoatAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | //? if >= 1.21.11 { 9 | 10 | import net.minecraft.world.entity.vehicle.boat.*; 11 | import net.minecraft.client.model.player.*; 12 | //? } else { 13 | /* 14 | import net.minecraft.client.model.*; 15 | import net.minecraft.world.entity.vehicle.*; 16 | *///? } 17 | import net.minecraft.client.player.AbstractClientPlayer; 18 | import net.minecraft.util.Mth; 19 | import net.minecraft.world.entity.HumanoidArm; 20 | 21 | public class BoatAnimation extends BasicAnimation { 22 | 23 | @Override 24 | public boolean isEnabled() { 25 | return NEABaseMod.config.enableRowBoatAnimation; 26 | } 27 | 28 | @Override 29 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 30 | //? if > 1.21.2 { 31 | 32 | return entity.isPassenger() && entity.getVehicle() instanceof AbstractBoat; 33 | //? } else { 34 | /* 35 | return entity.isPassenger() && entity.getVehicle() instanceof net.minecraft.world.entity.vehicle.Boat; 36 | *///? } 37 | } 38 | 39 | private final BodyPart[] bothHands = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM }; 40 | 41 | @Override 42 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 43 | return bothHands; 44 | } 45 | 46 | @Override 47 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 48 | return 1500; 49 | } 50 | 51 | @Override 52 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 53 | float tickCounter) { 54 | if (part == BodyPart.BODY) { 55 | return; 56 | } 57 | if (part == BodyPart.LEFT_ARM && AnimationUtil.isSwingingArm(entity, part)) { 58 | return; 59 | } 60 | if (part == BodyPart.RIGHT_ARM && AnimationUtil.isSwingingArm(entity, part)) { 61 | return; 62 | } 63 | HumanoidArm arm = part == BodyPart.LEFT_ARM ? HumanoidArm.LEFT : HumanoidArm.RIGHT; 64 | //? if > 1.21.2 { 65 | 66 | AbstractBoat boat = (AbstractBoat) entity.getVehicle(); 67 | //? } else { 68 | /* 69 | net.minecraft.world.entity.vehicle.Boat boat = (net.minecraft.world.entity.vehicle.Boat) entity.getVehicle(); 70 | *///? } 71 | int id = boat.getPassengers().indexOf(entity); 72 | if (id == 0) { 73 | float paddle = boat.getRowingTime(arm == HumanoidArm.LEFT ? 0 : 1, delta); 74 | AnimationUtil.applyArmTransforms(model, arm, -1.1f - Mth.sin(paddle) * 0.3f, 0.2f, 0.3f); 75 | } 76 | } 77 | 78 | } 79 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/vanilla/VanillaSingleHandedAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.vanilla; 2 | 3 | import java.util.EnumSet; 4 | 5 | import dev.tr7zw.notenoughanimations.access.PlayerData; 6 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 7 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 8 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 9 | import net.minecraft.client.model.HumanoidModel.ArmPose; 10 | //? if >= 1.21.11 { 11 | 12 | import net.minecraft.client.model.player.*; 13 | //? } else { 14 | /* 15 | import net.minecraft.client.model.*; 16 | *///? } 17 | import net.minecraft.client.player.AbstractClientPlayer; 18 | import net.minecraft.world.InteractionHand; 19 | import net.minecraft.world.entity.HumanoidArm; 20 | 21 | public class VanillaSingleHandedAnimation extends BasicAnimation { 22 | 23 | @Override 24 | public boolean isEnabled() { 25 | return true; 26 | } 27 | 28 | private ArmPose rightArmPose; 29 | private ArmPose leftArmPose; 30 | //? if >= 1.21.11 { 31 | 32 | private final EnumSet singleHandedAnimatios = EnumSet.of(ArmPose.SPYGLASS, ArmPose.THROW_TRIDENT, 33 | ArmPose.SPEAR); 34 | //? } else if >= 1.17.0 { 35 | /* 36 | private final EnumSet singleHandedAnimatios = EnumSet.of(ArmPose.SPYGLASS, ArmPose.THROW_SPEAR); 37 | *///? } else { 38 | 39 | // private final EnumSet singleHandedAnimatios = EnumSet.of(ArmPose.THROW_SPEAR); 40 | //? } 41 | private final BodyPart[] left = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.BODY }; 42 | private final BodyPart[] right = new BodyPart[] { BodyPart.RIGHT_ARM, BodyPart.BODY }; 43 | 44 | @Override 45 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 46 | rightArmPose = AnimationUtil.getArmPose(entity, 47 | entity.getMainArm() == HumanoidArm.LEFT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 48 | leftArmPose = AnimationUtil.getArmPose(entity, 49 | entity.getMainArm() == HumanoidArm.RIGHT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 50 | return singleHandedAnimatios.contains(leftArmPose) || singleHandedAnimatios.contains(rightArmPose); 51 | } 52 | 53 | @Override 54 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 55 | if (singleHandedAnimatios.contains(leftArmPose)) { 56 | return left; 57 | } 58 | if (singleHandedAnimatios.contains(rightArmPose)) { 59 | return right; 60 | } 61 | // ??? 62 | return new BodyPart[0]; 63 | } 64 | 65 | @Override 66 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 67 | return 3100; 68 | } 69 | 70 | @Override 71 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 72 | float tickCounter) { 73 | // Vanilla, do nothing 74 | } 75 | 76 | } 77 | -------------------------------------------------------------------------------- /gradlecw.bat: -------------------------------------------------------------------------------- 1 | @rem 2 | @rem Copyright 2015 the original author or authors. 3 | @rem 4 | @rem Licensed under the Apache License, Version 2.0 (the "License"); 5 | @rem you may not use this file except in compliance with the License. 6 | @rem You may obtain a copy of the License at 7 | @rem 8 | @rem https://www.apache.org/licenses/LICENSE-2.0 9 | @rem 10 | @rem Unless required by applicable law or agreed to in writing, software 11 | @rem distributed under the License is distributed on an "AS IS" BASIS, 12 | @rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | @rem See the License for the specific language governing permissions and 14 | @rem limitations under the License. 15 | @rem 16 | 17 | @if "%DEBUG%" == "" @echo off 18 | @rem ########################################################################## 19 | @rem 20 | @rem Gradle startup script for Windows 21 | @rem 22 | @rem ########################################################################## 23 | 24 | @rem Set local scope for the variables with windows NT shell 25 | if "%OS%"=="Windows_NT" setlocal 26 | 27 | set DIRNAME=%~dp0 28 | if "%DIRNAME%" == "" set DIRNAME=. 29 | set APP_BASE_NAME=%~n0 30 | set APP_HOME=%DIRNAME% 31 | 32 | @rem Resolve any "." and ".." in APP_HOME to make it shorter. 33 | for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi 34 | 35 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 36 | set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" 37 | 38 | @rem Find java.exe 39 | if defined JAVA_HOME goto findJavaFromJavaHome 40 | 41 | set JAVA_EXE=java.exe 42 | %JAVA_EXE% -version >NUL 2>&1 43 | if "%ERRORLEVEL%" == "0" goto execute 44 | 45 | echo. 46 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 47 | echo. 48 | echo Please set the JAVA_HOME variable in your environment to match the 49 | echo location of your Java installation. 50 | 51 | goto fail 52 | 53 | :findJavaFromJavaHome 54 | set JAVA_HOME=%JAVA_HOME:"=% 55 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe 56 | 57 | if exist "%JAVA_EXE%" goto execute 58 | 59 | echo. 60 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% 61 | echo. 62 | echo Please set the JAVA_HOME variable in your environment to match the 63 | echo location of your Java installation. 64 | 65 | goto fail 66 | 67 | :execute 68 | @rem Setup the command line 69 | 70 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar 71 | 72 | set COMPOSE=%APP_HOME%\gradle\gradle-compose.jar 73 | 74 | 75 | @rem Execute Gradle 76 | "%JAVA_EXE%" -jar "%COMPOSE%" %* 77 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* 78 | 79 | :end 80 | @rem End local scope for the variables with windows NT shell 81 | if "%ERRORLEVEL%"=="0" goto mainEnd 82 | 83 | :fail 84 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of 85 | rem the _cmd.exe /c_ return code! 86 | if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1 87 | exit /b 1 88 | 89 | :mainEnd 90 | if "%OS%"=="Windows_NT" endlocal 91 | 92 | :omega 93 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/HugAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | //? if >= 1.21.11 { 9 | 10 | import net.minecraft.client.model.player.*; 11 | //? } else { 12 | /* 13 | import net.minecraft.client.model.*; 14 | *///? } 15 | import net.minecraft.client.player.AbstractClientPlayer; 16 | import net.minecraft.world.entity.EntityType; 17 | import net.minecraft.world.entity.HumanoidArm; 18 | import net.minecraft.world.entity.projectile.ProjectileUtil; 19 | import net.minecraft.world.phys.AABB; 20 | import net.minecraft.world.phys.EntityHitResult; 21 | import net.minecraft.world.phys.Vec3; 22 | 23 | public class HugAnimation extends BasicAnimation { 24 | 25 | @Override 26 | public boolean isEnabled() { 27 | return NEABaseMod.config.huggingAnimation; 28 | } 29 | 30 | @Override 31 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 32 | if (!entity.isCrouching()) { 33 | return false; 34 | } 35 | double d = 1;// range 36 | Vec3 vec3 = entity.getEyePosition(0); 37 | Vec3 vec32 = entity.getViewVector(1.0F); 38 | Vec3 vec33 = vec3.add(vec32.x * d, vec32.y * d, vec32.z * d); 39 | AABB aABB = entity.getBoundingBox().expandTowards(vec32.scale(d)).inflate(1.0D, 1.0D, 1.0D); 40 | EntityHitResult entHit = ProjectileUtil.getEntityHitResult(entity, vec3, vec33, aABB, en -> (!en.isSpectator()), 41 | d); 42 | if (entHit != null && (entHit.getEntity().getType() == EntityType.PLAYER)) { 43 | AbstractClientPlayer otherPlayer = (AbstractClientPlayer) entHit.getEntity(); 44 | double dif = otherPlayer.getY() - entity.getY(); 45 | if (otherPlayer.isCrouching() && Math.abs(dif) < 0.3) { // Making sure they are about on the same height 46 | return true; 47 | } 48 | } 49 | return false; 50 | } 51 | 52 | private final BodyPart[] arms = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM }; 53 | 54 | @Override 55 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 56 | return arms; 57 | } 58 | 59 | @Override 60 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 61 | return 2100; 62 | } 63 | 64 | @Override 65 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 66 | float tickCounter) { 67 | if (part == BodyPart.LEFT_ARM) { 68 | AnimationUtil.applyArmTransforms(model, HumanoidArm.LEFT, -1f, -0.2f, 0.3f); 69 | } 70 | if (part == BodyPart.RIGHT_ARM) { 71 | AnimationUtil.applyArmTransforms(model, HumanoidArm.RIGHT, -1.5f, -0.2f, 0.3f); 72 | } 73 | } 74 | 75 | } 76 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/EatDrinkAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | import dev.tr7zw.transition.mc.EntityUtil; 9 | //? if >= 1.21.11 { 10 | 11 | import net.minecraft.client.model.player.*; 12 | //? } else { 13 | /* 14 | import net.minecraft.client.model.*; 15 | *///? } 16 | import net.minecraft.client.player.AbstractClientPlayer; 17 | import net.minecraft.util.Mth; 18 | import net.minecraft.world.InteractionHand; 19 | import net.minecraft.world.entity.HumanoidArm; 20 | 21 | public class EatDrinkAnimation extends BasicAnimation { 22 | 23 | private BodyPart[] target; 24 | private final BodyPart[] left = new BodyPart[] { BodyPart.LEFT_ARM }; 25 | private final BodyPart[] right = new BodyPart[] { BodyPart.RIGHT_ARM }; 26 | 27 | @Override 28 | public boolean isEnabled() { 29 | return NEABaseMod.config.enableEatDrinkAnimation; 30 | } 31 | 32 | @Override 33 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 34 | if (entity.getUseItemRemainingTicks() > 0) { 35 | var action = entity.getUseItem().getUseAnimation(); 36 | // Eating/Drinking 37 | // funky way of accessing the enum because it got renamed between versions 38 | if (action == action.EAT || action == action.DRINK) { 39 | if (entity.getUsedItemHand() == InteractionHand.MAIN_HAND) { 40 | if (entity.getMainArm() == HumanoidArm.RIGHT) { 41 | target = right; 42 | } else { 43 | target = left; 44 | } 45 | } else { 46 | if (entity.getMainArm() == HumanoidArm.RIGHT) { 47 | target = left; 48 | } else { 49 | target = right; 50 | } 51 | } 52 | return true; 53 | } 54 | } 55 | return false; 56 | } 57 | 58 | @Override 59 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 60 | return target; 61 | } 62 | 63 | @Override 64 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 65 | return 2500; 66 | } 67 | 68 | @Override 69 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 70 | float tickCounter) { 71 | HumanoidArm arm = part == BodyPart.LEFT_ARM ? HumanoidArm.LEFT : HumanoidArm.RIGHT; 72 | float g = entity.getUseItemRemainingTicks() - delta + 1.0F; 73 | // float h = g / entity.getUseItem().getUseDuration(); 74 | AnimationUtil.applyArmTransforms(model, arm, 75 | -(Mth.lerp(-1f * (EntityUtil.getXRot(entity) - 90f) / 180f, 1f, 2f)) 76 | + Mth.abs(Mth.cos(g / 4.0F * 3.1415927F) * 0.2F), 77 | -0.3f, 0.3f); 78 | } 79 | 80 | } 81 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/api/BasicAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.api; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 5 | //? if >= 1.21.11 { 6 | 7 | import net.minecraft.client.model.player.*; 8 | //? } else { 9 | /* 10 | import net.minecraft.client.model.*; 11 | *///? } 12 | import net.minecraft.client.player.AbstractClientPlayer; 13 | 14 | public abstract class BasicAnimation { 15 | 16 | private boolean isPrepared = false; 17 | 18 | /** 19 | * Check if the animation is enabled in the settings. 20 | * 21 | * @return true when enabled 22 | */ 23 | public abstract boolean isEnabled(); 24 | 25 | /** 26 | * Check if this animation wants to apply to the provided player right now. When 27 | * true, the priorities determine if and which body parts will be assigned to 28 | * this animation. 29 | * 30 | * @param entity 31 | * @param data 32 | * @return 33 | */ 34 | public abstract boolean isValid(AbstractClientPlayer entity, PlayerData data); 35 | 36 | /** 37 | * Gets the body parts this animation should be applied to, expects that isValid 38 | * is called before, so state can be cached from isValid to this method. 39 | * 40 | * @param entity 41 | * @param data 42 | * @return 43 | */ 44 | public abstract BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data); 45 | 46 | /** 47 | * Higher priority = overwrites other animations. -1 = Don't play 0 = not used, 48 | * falls back to vanilla 1-999 = low priority passive animations(item holding 49 | * for example) 1000-1999 = active side animations(boats, ladder) 2000-2999 = 50 | * active direct animations(eating food) 3000-3999 = Highly important 51 | * animations(vanilla bow animation for example) 52 | * 53 | * @param entity 54 | * @param data 55 | * @return 56 | */ 57 | public abstract int getPriority(AbstractClientPlayer entity, PlayerData data); 58 | 59 | public void prepare(AbstractClientPlayer entity, PlayerData data, PlayerModel model, float delta, float swing) { 60 | if (!isPrepared) { 61 | precalculate(entity, data, model, delta, swing); 62 | isPrepared = true; 63 | } 64 | } 65 | 66 | public void cleanup() { 67 | isPrepared = false; 68 | } 69 | 70 | /** 71 | * This method allows to precalculate data to be then used in the apply method 72 | * to reduce overhead. 73 | * 74 | * @param entity 75 | * @param data 76 | * @param model 77 | * @param delta 78 | * @param tickCounter 79 | */ 80 | protected void precalculate(AbstractClientPlayer entity, PlayerData data, PlayerModel model, float delta, 81 | float tickCounter) { 82 | // not used by default 83 | } 84 | 85 | /** 86 | * Apply the animation to the provided bodypart. 87 | * 88 | * @param entity 89 | * @param data 90 | * @param model 91 | * @param part 92 | * @param delta 93 | * @param tickCounter 94 | */ 95 | public abstract void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, 96 | float delta, float tickCounter); 97 | 98 | } 99 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/CustomBowAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import java.util.EnumSet; 4 | 5 | import dev.tr7zw.notenoughanimations.access.PlayerData; 6 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 7 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 8 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 9 | import dev.tr7zw.notenoughanimations.versionless.animations.BowAnimation; 10 | import dev.tr7zw.transition.mc.EntityUtil; 11 | import lombok.Getter; 12 | import net.minecraft.client.model.HumanoidModel.ArmPose; 13 | import net.minecraft.client.model.geom.ModelPart; 14 | //? if >= 1.21.11 { 15 | 16 | import net.minecraft.client.model.player.*; 17 | //? } else { 18 | /* 19 | import net.minecraft.client.model.*; 20 | *///? } 21 | import net.minecraft.client.player.AbstractClientPlayer; 22 | import net.minecraft.util.Mth; 23 | import net.minecraft.world.InteractionHand; 24 | import net.minecraft.world.entity.HumanoidArm; 25 | 26 | public class CustomBowAnimation extends VanillaProjectileWeaponAnimation { 27 | 28 | @Getter 29 | private final EnumSet twoHandedAnimations = EnumSet.of(ArmPose.BOW_AND_ARROW); 30 | 31 | @Override 32 | public boolean isEnabled() { 33 | return NEABaseMod.config.bowAnimation == BowAnimation.CUSTOM_V1; 34 | } 35 | 36 | @Override 37 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 38 | float tickCounter) { 39 | ModelPart mainArm = model.rightArm; 40 | ModelPart offArm = model.leftArm; 41 | BodyPart mainPart = BodyPart.RIGHT_ARM; 42 | BodyPart offPart = BodyPart.LEFT_ARM; 43 | boolean bowInLeftHand = (entity.getMainArm() == HumanoidArm.RIGHT 44 | && entity.getUsedItemHand() == InteractionHand.OFF_HAND) 45 | || (entity.getMainArm() == HumanoidArm.LEFT && entity.getUsedItemHand() == InteractionHand.MAIN_HAND); 46 | if (bowInLeftHand) { 47 | mainArm = model.leftArm; 48 | offArm = model.rightArm; 49 | mainPart = BodyPart.LEFT_ARM; 50 | offPart = BodyPart.RIGHT_ARM; 51 | } 52 | int invert = bowInLeftHand ? -1 : 1; 53 | 54 | if (part == mainPart) { 55 | mainArm.yRot = invert * Mth.clamp(-0.1F + AnimationUtil.wrapDegrees(-model.head.xRot), -1.25f, 0.5f); 56 | mainArm.xRot = Mth.clamp(-1.5707964F + (invert * AnimationUtil.wrapDegrees(model.head.yRot)), -2f, 0); 57 | mainArm.zRot += invert * 1.5F; 58 | } 59 | 60 | if (part == offPart) { 61 | offArm.yRot = invert * Mth.clamp(0.1F + AnimationUtil.wrapDegrees(-model.head.xRot), -1.05f, 0.7f); 62 | offArm.xRot = Mth.clamp(-1.5707964F + (invert * AnimationUtil.wrapDegrees(model.head.yRot)) + 0.8f, -1.05f, 63 | -0.65f); 64 | offArm.zRot += invert * 1.5F; 65 | } 66 | 67 | if (part == BodyPart.BODY && NEABaseMod.config.customBowRotationLock) { 68 | if (bowInLeftHand) { 69 | entity.yBodyRot = EntityUtil.getYRot(entity) + 40; 70 | entity.yBodyRotO = entity.yRotO + 40; 71 | } else { 72 | entity.yBodyRot = EntityUtil.getYRot(entity) - 40; 73 | entity.yBodyRotO = entity.yRotO - 40; 74 | } 75 | } 76 | } 77 | 78 | } 79 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/ItemSwapAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | //? if >= 1.21.11 { 9 | 10 | import net.minecraft.client.model.player.*; 11 | //? } else { 12 | /* 13 | import net.minecraft.client.model.*; 14 | *///? } 15 | import net.minecraft.client.player.AbstractClientPlayer; 16 | import net.minecraft.util.Mth; 17 | import net.minecraft.world.entity.HumanoidArm; 18 | import net.minecraft.world.item.ItemStack; 19 | 20 | public class ItemSwapAnimation extends BasicAnimation { 21 | 22 | @Override 23 | public boolean isEnabled() { 24 | return NEABaseMod.config.itemSwapAnimation; 25 | } 26 | 27 | @Override 28 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 29 | if (data.getLastAnimationSwapTick() != entity.tickCount) { // run data updates 30 | data.setLastAnimationSwapTick(entity.tickCount); 31 | if (data.getLastHeldItems()[0] == null) { // init vars 32 | data.getLastHeldItems()[0] = entity.getMainHandItem(); 33 | data.getLastHeldItems()[1] = entity.getOffhandItem(); 34 | } 35 | ItemStack mainHand = entity.getMainHandItem(); 36 | ItemStack offHand = entity.getOffhandItem(); 37 | if ((!mainHand.isEmpty() || !offHand.isEmpty()) 38 | && data.getLastHeldItems()[0].getItem() != data.getLastHeldItems()[1].getItem() 39 | && data.getLastHeldItems()[0].getItem() == offHand.getItem() 40 | && data.getLastHeldItems()[1].getItem() == mainHand.getItem()) { 41 | data.setItemSwapAnimationTimer(10); 42 | } 43 | data.getLastHeldItems()[0] = entity.getMainHandItem(); 44 | data.getLastHeldItems()[1] = entity.getOffhandItem(); 45 | if (data.getItemSwapAnimationTimer() > 0) { 46 | data.setItemSwapAnimationTimer(data.getItemSwapAnimationTimer() - 1); 47 | } 48 | } 49 | return data.getItemSwapAnimationTimer() > 0; 50 | } 51 | 52 | private final BodyPart[] parts = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM }; 53 | 54 | @Override 55 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 56 | return parts; 57 | } 58 | 59 | @Override 60 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 61 | return 3500; 62 | } 63 | 64 | @Override 65 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 66 | float tickCounter) { 67 | 68 | int animationTick = data.getItemSwapAnimationTimer(); 69 | float position = animationTick / 10f * -1f; 70 | position = Mth.lerp(delta, (animationTick + 1) / 10f * -1f, position); 71 | if (part == BodyPart.LEFT_ARM) 72 | AnimationUtil.applyArmTransforms(model, HumanoidArm.LEFT, -0.5f, 0.2f, position); 73 | if (part == BodyPart.RIGHT_ARM) 74 | AnimationUtil.applyArmTransforms(model, HumanoidArm.RIGHT, -0.5f, 0.2f, position); 75 | 76 | } 77 | 78 | } 79 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/vanilla/ElytraAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.vanilla; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.api.PoseOverwrite; 6 | import dev.tr7zw.notenoughanimations.util.RenderStateHolder; 7 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 8 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 9 | //? if >= 1.21.11 { 10 | 11 | import net.minecraft.client.model.player.*; 12 | //? } else { 13 | /* 14 | import net.minecraft.client.model.*; 15 | *///? } 16 | import net.minecraft.client.player.AbstractClientPlayer; 17 | import net.minecraft.util.Mth; 18 | import net.minecraft.world.entity.Pose; 19 | 20 | public class ElytraAnimation extends BasicAnimation implements PoseOverwrite { 21 | 22 | @Override 23 | public boolean isEnabled() { 24 | return true; 25 | } 26 | 27 | @Override 28 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 29 | return entity.getPose() == Pose.FALL_FLYING; 30 | } 31 | 32 | @Override 33 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 34 | return BodyPart.values(); 35 | } 36 | 37 | @Override 38 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 39 | return 3600; 40 | } 41 | 42 | @Override 43 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 44 | float tickCounter) { 45 | if (!NEABaseMod.config.tweakElytraAnimation) { 46 | // Do nothing 47 | return; 48 | } 49 | // move arms and legs a bit to the side 50 | float k = (float) entity.getDeltaMovement().lengthSqr(); 51 | k /= 0.2F; 52 | k *= k * k; 53 | if (k < 1.0F) 54 | k = 1.0F; 55 | float moveOut = 0.1507964F / k; 56 | moveOut = Math.min(moveOut, 0.25f); 57 | moveOut = Math.max(moveOut, 0.1F); 58 | if (part == BodyPart.LEFT_ARM) { 59 | model.leftArm.xRot = Mth.cos(tickCounter * 0.6662F) * 0.5F / k; 60 | model.leftArm.zRot = -moveOut; 61 | } 62 | if (part == BodyPart.RIGHT_ARM) { 63 | model.rightArm.xRot = Mth.cos(tickCounter * 0.6662F + 3.1415927F) * 0.5F / k; 64 | model.rightArm.zRot = moveOut; 65 | } 66 | if (part == BodyPart.LEFT_LEG) { 67 | model.leftLeg.xRot = Mth.cos(tickCounter * 0.6662F + 3.1415927F) * 0.7F / k; 68 | model.leftLeg.zRot = -moveOut; 69 | } 70 | if (part == BodyPart.RIGHT_LEG) { 71 | model.rightLeg.xRot = Mth.cos(tickCounter * 0.6662F) * 0.7F / k; 72 | model.rightLeg.zRot = moveOut; 73 | } 74 | } 75 | 76 | @Override 77 | public void updateState(AbstractClientPlayer entity, PlayerData data, PlayerModel playerModel) { 78 | if (isValid(entity, data)) { 79 | //? if >= 1.21.2 { 80 | 81 | RenderStateHolder.RenderStateData stateData = data.getData(RenderStateHolder.INSTANCE, 82 | RenderStateHolder.RenderStateData::new); 83 | stateData.renderState.isCrouching = false; 84 | //? } else { 85 | /* 86 | playerModel.crouching = false; 87 | *///? } 88 | } 89 | } 90 | 91 | } 92 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/fullbody/HorseAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.fullbody; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | //? if >= 1.21.11 { 9 | 10 | import net.minecraft.world.entity.animal.equine.*; 11 | import net.minecraft.client.model.player.*; 12 | //? } else { 13 | /* 14 | import net.minecraft.world.entity.animal.horse.*; 15 | import net.minecraft.client.model.*; 16 | *///? } 17 | import net.minecraft.client.player.AbstractClientPlayer; 18 | import net.minecraft.util.Mth; 19 | import net.minecraft.world.entity.HumanoidArm; 20 | 21 | public class HorseAnimation extends BasicAnimation { 22 | 23 | @Override 24 | public boolean isEnabled() { 25 | return NEABaseMod.config.enableHorseAnimation; 26 | } 27 | 28 | @Override 29 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 30 | return entity.isPassenger() && entity.getVehicle() instanceof AbstractHorse horse && horse.isSaddled(); 31 | } 32 | 33 | private final BodyPart[] bothHands = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM, BodyPart.BODY }; 34 | private final BodyPart[] fullBody = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM, BodyPart.BODY, 35 | BodyPart.LEFT_LEG, BodyPart.RIGHT_LEG }; 36 | 37 | @Override 38 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 39 | return NEABaseMod.config.enableHorseLegAnimation ? fullBody : bothHands; 40 | } 41 | 42 | @Override 43 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 44 | return 1500; 45 | } 46 | 47 | @Override 48 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 49 | float tickCounter) { 50 | if (part == BodyPart.BODY) { 51 | return; 52 | } 53 | if (part == BodyPart.LEFT_ARM && AnimationUtil.isSwingingArm(entity, part)) { 54 | return; 55 | } 56 | if (part == BodyPart.RIGHT_ARM && AnimationUtil.isSwingingArm(entity, part)) { 57 | return; 58 | } 59 | HumanoidArm arm = part == BodyPart.LEFT_ARM ? HumanoidArm.LEFT : HumanoidArm.RIGHT; 60 | AbstractHorse horse = (AbstractHorse) entity.getVehicle(); 61 | int id = horse.getPassengers().indexOf(entity); 62 | if (id == 0) { 63 | if (part == BodyPart.LEFT_LEG || part == BodyPart.RIGHT_LEG) { 64 | if (horse.isStanding()) { 65 | AnimationUtil.applyTransforms(model, part, -0.8f, 0f, 0.8f); 66 | } else { 67 | AnimationUtil.applyTransforms(model, part, -0.2f, 0f, 0.8f); 68 | } 69 | } else { 70 | //? if >= 1.19.4 { 71 | 72 | float rotation = -Mth.cos(horse.walkAnimation.position() * 0.3f); 73 | //? } else { 74 | /* 75 | float rotation = -Mth.cos(horse.animationPosition * 0.3f); 76 | *///? } 77 | rotation *= 0.1; 78 | AnimationUtil.applyArmTransforms(model, arm, -1.1f - rotation, -0.2f, 0.3f); 79 | } 80 | } 81 | } 82 | 83 | } 84 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/PlayerEntityMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | import java.util.function.Supplier; 6 | 7 | import org.spongepowered.asm.mixin.Mixin; 8 | import org.spongepowered.asm.mixin.injection.At; 9 | import org.spongepowered.asm.mixin.injection.Inject; 10 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 11 | 12 | import dev.tr7zw.notenoughanimations.access.PlayerData; 13 | import dev.tr7zw.notenoughanimations.logic.PlayerTransformer; 14 | import dev.tr7zw.notenoughanimations.versionless.animations.DataHolder; 15 | import lombok.Getter; 16 | import lombok.Setter; 17 | import net.minecraft.world.entity.Pose; 18 | import net.minecraft.world.entity.player.Player; 19 | import net.minecraft.world.item.ItemStack; 20 | 21 | @Mixin(Player.class) 22 | public class PlayerEntityMixin implements PlayerData { 23 | 24 | private int armsUpdated = 0; 25 | @Getter 26 | @Setter 27 | private float[] lastRotations = new float[PlayerTransformer.ENTRY_AMOUNT * PlayerTransformer.ENTRY_SIZE]; 28 | @Getter 29 | @Setter 30 | private ItemStack sideSword = ItemStack.EMPTY; 31 | private ItemStack[] lastHeldItems = new ItemStack[2]; 32 | @Getter 33 | @Setter 34 | private boolean disableBodyRotation = false; 35 | @Getter 36 | @Setter 37 | private boolean rotateBodyToHead = false; 38 | private int itemSwapAnimationTimer = 0; 39 | private int lastAnimationSwapTick = -1; 40 | private Pose poseOverwrite = null; 41 | private Map, Object> animationData = new HashMap<>(); 42 | 43 | @Inject(method = "tick", at = @At("RETURN")) 44 | public void tick(CallbackInfo info) { 45 | updateRenderLayerItems(); 46 | setRotateBodyToHead(false); 47 | } 48 | 49 | @Override 50 | public int isUpdated(int frameId) { 51 | return Math.abs(frameId - armsUpdated); 52 | } 53 | 54 | @Override 55 | public void setUpdated(int frameId) { 56 | armsUpdated = frameId; 57 | } 58 | 59 | private void updateRenderLayerItems() { 60 | //? if < 1.21.9 { 61 | /* 62 | dev.tr7zw.notenoughanimations.renderlayer.SwordRenderLayer.update((Player) (Object) this); 63 | *///? } 64 | } 65 | 66 | @Override 67 | public ItemStack[] getLastHeldItems() { 68 | return lastHeldItems; 69 | } 70 | 71 | @Override 72 | public int getItemSwapAnimationTimer() { 73 | return itemSwapAnimationTimer; 74 | } 75 | 76 | @Override 77 | public void setItemSwapAnimationTimer(int count) { 78 | this.itemSwapAnimationTimer = count; 79 | } 80 | 81 | @Override 82 | public int getLastAnimationSwapTick() { 83 | return lastAnimationSwapTick; 84 | } 85 | 86 | @Override 87 | public void setLastAnimationSwapTick(int count) { 88 | this.lastAnimationSwapTick = count; 89 | } 90 | 91 | @Override 92 | public void setPoseOverwrite(Pose state) { 93 | this.poseOverwrite = state; 94 | } 95 | 96 | @Override 97 | public Pose getPoseOverwrite() { 98 | return poseOverwrite; 99 | } 100 | 101 | @SuppressWarnings("unchecked") 102 | @Override 103 | public T getData(DataHolder holder, Supplier builder) { 104 | return (T) animationData.computeIfAbsent(holder, (h) -> builder.get()); 105 | } 106 | 107 | } 108 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/LevelRendererMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import dev.tr7zw.notenoughanimations.NEAnimationsLoader; 9 | import net.minecraft.client.Camera; 10 | import net.minecraft.client.renderer.LevelRenderer; 11 | 12 | //? if < 1.21.6 { 13 | /* 14 | import net.minecraft.client.renderer.GameRenderer; 15 | import net.minecraft.client.renderer.LightTexture; 16 | *///? } 17 | 18 | //? if >= 1.21.0 { 19 | 20 | import net.minecraft.client.DeltaTracker; 21 | 22 | //? if >= 1.21.2 { 23 | 24 | import com.mojang.blaze3d.resource.GraphicsResourceAllocator; 25 | //? } 26 | //? } 27 | //? if <= 1.20.4 { 28 | /* 29 | import com.mojang.blaze3d.vertex.PoseStack; 30 | *///? } 31 | //? if >= 1.19.3 { 32 | 33 | import org.joml.Matrix4f; 34 | import org.joml.Vector4f; 35 | //? } else { 36 | /* 37 | import com.mojang.math.Matrix4f; 38 | *///? } 39 | 40 | @Mixin(LevelRenderer.class) 41 | public class LevelRendererMixin { 42 | 43 | @Inject(method = "renderLevel", at = @At("HEAD")) 44 | //? if >= 1.21.9 { 45 | 46 | public void renderLevel(GraphicsResourceAllocator graphicsResourceAllocator, DeltaTracker deltaTracker, boolean bl, 47 | Camera camera, Matrix4f matrix4f, Matrix4f matrix4f2, Matrix4f matrix4f3, 48 | com.mojang.blaze3d.buffers.GpuBufferSlice gpuBufferSlice, Vector4f vector4f, boolean bl2, CallbackInfo ci) { 49 | float tickDelta = deltaTracker.getGameTimeDeltaPartialTick(false); 50 | //? } else if <= 1.20.4 { 51 | /* 52 | private void beforeRender(PoseStack matrices, float tickDelta, long limitTime, boolean renderBlockOutline, 53 | Camera camera, GameRenderer gameRenderer, LightTexture lightmapTextureManager, Matrix4f matrix4f, CallbackInfo ci) { 54 | *///? } else if < 1.21.0 { 55 | /* 56 | private void beforeRender(float tickDelta, long l, boolean bl, Camera camera, GameRenderer gameRenderer, 57 | LightTexture lightTexture, Matrix4f matrix4f, Matrix4f matrix4f2, CallbackInfo ci) { 58 | *///? } else if < 1.21.2 { 59 | /* 60 | private void beforeRender(DeltaTracker deltaTracker, boolean bl, Camera camera, GameRenderer gameRenderer, 61 | LightTexture lightTexture, Matrix4f matrix4f, Matrix4f matrix4f2, CallbackInfo ci) { 62 | float tickDelta = deltaTracker.getGameTimeDeltaPartialTick(false); 63 | *///? } else if < 1.21.6 { 64 | /* 65 | private void beforeRender(GraphicsResourceAllocator graphicsResourceAllocator, DeltaTracker deltaTracker, 66 | boolean bl, Camera camera, GameRenderer gameRenderer, 67 | //? if <= 1.21.3 { 68 | /^ 69 | LightTexture lightTexture, 70 | ^///? } 71 | Matrix4f matrix4f, Matrix4f matrix4f2, CallbackInfo ci) { 72 | float tickDelta = deltaTracker.getGameTimeDeltaPartialTick(false); 73 | *///? } else { 74 | /* 75 | public void renderLevel(GraphicsResourceAllocator graphicsResourceAllocator, DeltaTracker deltaTracker, boolean bl, 76 | Camera camera, Matrix4f matrix4f, Matrix4f matrix4f2, 77 | com.mojang.blaze3d.buffers.GpuBufferSlice gpuBufferSlice, Vector4f vector4f, boolean bl2, CallbackInfo ci) { 78 | float tickDelta = deltaTracker.getGameTimeDeltaPartialTick(false); 79 | *///? } 80 | NEAnimationsLoader.INSTANCE.playerTransformer.setDeltaTick(tickDelta); 81 | // NEAnimationsLoader.INSTANCE.playerTransformer.nextFrame(); 82 | } 83 | 84 | } 85 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/PetAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | import dev.tr7zw.transition.mc.EntityUtil; 9 | //? if >= 1.21.11 { 10 | 11 | import net.minecraft.client.model.player.*; 12 | //? } else { 13 | /* 14 | import net.minecraft.client.model.*; 15 | *///? } 16 | import net.minecraft.client.player.AbstractClientPlayer; 17 | import net.minecraft.util.Mth; 18 | import net.minecraft.world.entity.Entity; 19 | import net.minecraft.world.entity.EntityType; 20 | import net.minecraft.world.entity.HumanoidArm; 21 | import net.minecraft.world.entity.TamableAnimal; 22 | import net.minecraft.world.entity.projectile.ProjectileUtil; 23 | import net.minecraft.world.phys.AABB; 24 | import net.minecraft.world.phys.EntityHitResult; 25 | import net.minecraft.world.phys.Vec3; 26 | 27 | public class PetAnimation extends BasicAnimation { 28 | 29 | private Entity targetPet = null; 30 | // private double posDif = 0; 31 | 32 | @Override 33 | public boolean isEnabled() { 34 | return NEABaseMod.config.petAnimation; 35 | } 36 | 37 | @Override 38 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 39 | if (!entity.isCrouching()) { 40 | return false; 41 | } 42 | double d = 1;// range 43 | Vec3 vec3 = entity.getEyePosition(0); 44 | Vec3 vec32 = entity.getViewVector(1.0F); 45 | Vec3 vec33 = vec3.add(vec32.x * d, vec32.y * d, vec32.z * d); 46 | AABB aABB = entity.getBoundingBox().expandTowards(vec32.scale(d)).inflate(1.0D, 1.0D, 1.0D); 47 | EntityHitResult entHit = ProjectileUtil.getEntityHitResult(entity, vec3, vec33, aABB, en -> (!en.isSpectator()), 48 | d); 49 | if (entHit != null && (entHit.getEntity().getType() == EntityType.WOLF 50 | || entHit.getEntity().getType() == EntityType.CAT)) { 51 | TamableAnimal pet = (TamableAnimal) entHit.getEntity(); 52 | double dif = pet.getY() - entity.getY(); 53 | if (Math.abs(dif) < 0.6) { // Making sure they are about on the same height 54 | targetPet = pet; 55 | // posDif = dif; 56 | return true; 57 | } 58 | } 59 | targetPet = null; 60 | return false; 61 | } 62 | 63 | private final BodyPart[] leftHanded = new BodyPart[] { BodyPart.LEFT_ARM }; 64 | private final BodyPart[] rightHanded = new BodyPart[] { BodyPart.RIGHT_ARM }; 65 | 66 | @Override 67 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 68 | return entity.getMainArm() == HumanoidArm.RIGHT ? rightHanded : leftHanded; 69 | } 70 | 71 | @Override 72 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 73 | return 2100; 74 | } 75 | 76 | @Override 77 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 78 | float tickCounter) { 79 | if (Math.random() < 0.005) 80 | targetPet.handleEntityEvent((byte) 18); 81 | HumanoidArm arm = part == BodyPart.LEFT_ARM ? HumanoidArm.LEFT : HumanoidArm.RIGHT; 82 | AnimationUtil.applyArmTransforms(model, arm, 83 | -(Mth.lerp(-1f * (EntityUtil.getXRot(entity) - 90f) / 180f, 1f, 2f)), -0.6f, 84 | 0.3f + Mth.sin((System.currentTimeMillis() % 20000) / 60f) * 0.2f); 85 | targetPet = null; 86 | } 87 | 88 | } 89 | -------------------------------------------------------------------------------- /NEAVersionless/src/main/java/dev/tr7zw/notenoughanimations/versionless/config/Config.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.versionless.config; 2 | 3 | import java.util.Arrays; 4 | import java.util.HashSet; 5 | import java.util.Set; 6 | 7 | import dev.tr7zw.notenoughanimations.versionless.RotationLock; 8 | import dev.tr7zw.notenoughanimations.versionless.animations.BowAnimation; 9 | import dev.tr7zw.notenoughanimations.versionless.animations.HoldUpModes; 10 | import dev.tr7zw.notenoughanimations.versionless.animations.HoldUpTarget; 11 | 12 | public class Config { 13 | 14 | public int configVersion = 10; 15 | public float animationSmoothingSpeed = 0.1f; 16 | public Set holdingItems = new HashSet<>(Arrays.asList("minecraft:clock", "minecraft:compass", 17 | "minecraft:torch", "minecraft:lantern", "minecraft:soul_torch", "minecraft:soul_lantern", 18 | "minecraft:recovery_compass", "quad-mstv-mtv:acacia_torch", "quad-mstv-mtv:bamboo_torch", 19 | "quad-mstv-mtv:birch_torch", "quad-mstv-mtv:cherry_torch", "quad-mstv-mtv:crimson_torch", 20 | "quad-mstv-mtv:dark_oak_torch", "quad-mstv-mtv:pale_oak_torch", "quad-mstv-mtv:jungle_torch", 21 | "quad-mstv-mtv:mangrove_torch", "quad-mstv-mtv:spruce_torch", "quad-mstv-mtv:warped_torch", 22 | "quad-mstv-mtv:acacia_soul_torch", "quad-mstv-mtv:bamboo_soul_torch", "quad-mstv-mtv:birch_soul_torch", 23 | "quad-mstv-mtv:cherry_soul_torch", "quad-mstv-mtv:crimson_soul_torch", "quad-mstv-mtv:dark_oak_soul_torch", 24 | "quad-mstv-mtv:pale_oak_soul_torch", "quad-mstv-mtv:jungle_soul_torch", "quad-mstv-mtv:mangrove_soul_torch", 25 | "quad-mstv-mtv:spruce_soul_torch", "quad-mstv-mtv:warped_soul_torch")); 26 | public boolean enableAnimationSmoothing = true; 27 | public boolean enableInWorldMapRendering = true; 28 | public boolean enableOffhandHiding = true; 29 | public boolean enableRotationLocking = true; 30 | public boolean enableLadderAnimation = true; 31 | public float ladderAnimationAmplifier = 0.35f; 32 | public float ladderAnimationArmHeight = 1.7f; 33 | public float ladderAnimationArmSpeed = 2f; 34 | public boolean enableRotateToLadder = true; 35 | public boolean enableEatDrinkAnimation = true; 36 | public boolean enableRowBoatAnimation = true; 37 | public boolean enableHorseAnimation = true; 38 | public boolean enableHorseLegAnimation = false; 39 | public boolean dontHoldItemsInBed = true; 40 | public boolean freezeArmsInBed = true; 41 | public RotationLock rotationLock = RotationLock.NONE; 42 | public boolean limitRotationLockToFP = true; 43 | public boolean showLastUsedSword = false; 44 | public Set sheathSwords = new HashSet<>(Arrays.asList("minecraft:wooden_sword", "minecraft:stone_sword", 45 | "minecraft:golden_sword", "minecraft:iron_sword", "minecraft:diamond_sword", "minecraft:netherite_sword")); 46 | public boolean enableCrawlingAnimation = true; 47 | public HoldUpModes holdUpItemsMode = HoldUpModes.CONFIG; 48 | public HoldUpTarget holdUpTarget = HoldUpTarget.CAMERA; 49 | public float holdUpCameraOffset = 0.1f; 50 | public boolean holdUpOnlySelf = false; 51 | public float holdUpItemOffset = 0; 52 | public boolean itemSwapAnimation = true; 53 | public boolean tweakElytraAnimation = true; 54 | public boolean petAnimation = true; 55 | public boolean fallingAnimation = false; 56 | public boolean freezingAnimation = true; 57 | public boolean huggingAnimation = false; 58 | public boolean narutoRunning = false; 59 | public boolean disableLegSmoothing = false; 60 | public BowAnimation bowAnimation = BowAnimation.VANILLA; 61 | public boolean customBowRotationLock = false; 62 | public boolean clampCrossbowAnimations = false; 63 | public boolean burningAnimation = true; 64 | public Set hideItemsForTheseBows = new HashSet<>(); 65 | public Set mapHolding = new HashSet<>(Arrays.asList("minecraft:filled_map", "antiqueatlas:antique_atlas")); 66 | } 67 | -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/lang/zh_tw.json: -------------------------------------------------------------------------------- 1 | { 2 | "text.nea.title": "Not Enough Animations 設定", 3 | "text.nea.enable.animationsmoothing": "動畫平滑", 4 | "text.nea.enable.animationsmoothing.tooltip": "平滑手臂和腿部的動畫,讓它們看起還更自然並更少拼湊感", 5 | "text.nea.smoothingSpeed": "平滑量", 6 | "text.nea.smoothingSpeed.tooltip": "套用於手臂和腿部動畫的平滑量", 7 | "text.nea.enable.inworldmaprendering": "世界內地圖繪製", 8 | "text.nea.enable.inworldmaprendering.tooltip": "在世界中繪製地圖,而不是僅在第一人稱視角中", 9 | "text.nea.enable.offhandhiding": "弓動畫修復", 10 | "text.nea.enable.offhandhiding.tooltip": "在拉弓時隱藏非慣用手物品", 11 | "text.nea.enable.rotationlocking": "動畫旋轉鎖定", 12 | "text.nea.enable.rotationlocking.tooltip": "將玩家身體的旋轉鎖定到玩家頭部的旋轉", 13 | "text.nea.enable.ladderanimation": "爬梯動畫", 14 | "text.nea.enable.ladderanimation.tooltip": "加入攀爬梯子的動畫(注意:只有梯子,不包括藤蔓、鷹架等)", 15 | "text.nea.enable.eatdrinkanimation": "進食/飲食動畫", 16 | "text.nea.enable.eatdrinkanimation.tooltip": "加入進食和飲食的動畫", 17 | "text.nea.enable.rowboatanimation": "划船動畫", 18 | "text.nea.enable.rowboatanimation.tooltip": "加入划船的動畫", 19 | "text.nea.enable.horseanimation": "騎馬動畫", 20 | "text.nea.enable.horseanimation.tooltip": "加入騎馬的動畫", 21 | "text.nea.enable.dontholditemsinbed": "睡覺時不拿物品", 22 | "text.nea.enable.dontholditemsinbed.tooltip": "防止玩家在床上拿著物品", 23 | "text.nea.enable.freezearmsinbed": "睡覺時不移動", 24 | "text.nea.enable.freezearmsinbed.tooltip": "防止玩家在床上移動手臂", 25 | "text.nea.rotationlock": "旋轉鎖定", 26 | "text.nea.rotationlock.tooltip": "要使用的旋轉鎖定類型", 27 | "text.nea.rotationlock.NONE": "無", 28 | "text.nea.rotationlock.FIXED": "固定", 29 | "text.nea.rotationlock.SMOOTH": "平滑", 30 | "text.nea.enable.showlastusedsword": "【已棄用】收劍", 31 | "text.nea.enable.showlastusedsword.tooltip": "【已棄用,將被移除!請使用其他模組實現此功能!】顯示玩家上次使用的劍。這只是一種視覺效果,並不知道實際的物品欄。請不要回報劍在丟棄/放入儲物箱等後仍然被繪製的「錯誤」", 32 | "text.nea.enable.crawling": "潛行動畫", 33 | "text.nea.enable.crawling.tooltip": "加入潛行的動畫,取代原版的「爬行」(游泳)動畫", 34 | "text.nea.enable.rotatetoladder": "身體對齊梯子", 35 | "text.nea.enable.rotatetoladder.tooltip": "攀爬梯子時將玩家身體旋轉至面向梯子", 36 | "text.nea.holdUpItemsMode": "舉起物品模式", 37 | "text.nea.holdUpItemsMode.tooltip": "讓玩家舉起物品(就像他們正在看著物品/將物品舉在面前一樣)", 38 | "text.nea.holdUpItemsMode.ALL": "全部物品", 39 | "text.nea.holdUpItemsMode.NONE": "無物品", 40 | "text.nea.holdUpItemsMode.CONFIG": "僅設定中的物品", 41 | "text.nea.holdUpItemOffset": "手持物品的高度調整", 42 | "text.nea.holdUpItemOffset.tooltip": "修改物品被舉起的高度程度", 43 | "text.nea.ladderAnimationAmplifier": "爬梯手臂放大", 44 | "text.nea.ladderAnimationAmplifier.tooltip": "在爬梯時套用的手臂移動量", 45 | "text.nea.ladderAnimationArmHeight": "爬梯手臂高度", 46 | "text.nea.ladderAnimationArmHeight.tooltip": "爬梯時手臂的高度", 47 | "text.nea.ladderAnimationArmSpeed": "爬梯手臂速度", 48 | "text.nea.ladderAnimationArmSpeed.tooltip": "爬梯時手臂的速度", 49 | "text.nea.enable.itemSwapAnimation": "物品交換動畫", 50 | "text.nea.enable.itemSwapAnimation.tooltip": "加入慣用手與非慣用手交換物品的動畫", 51 | "text.nea.enable.tweakElytraAnimation": "調整鞘翅飛行", 52 | "text.nea.enable.tweakElytraAnimation.tooltip": "調整滑翔翼的飛行動畫,使其看起來更自然", 53 | "text.nea.enable.petAnimation": "寵物貓狼", 54 | "text.nea.enable.petAnimation.tooltip": "為撫摸狼和貓加入動畫。潛行並注視狼或貓時,可以撫摸它", 55 | "text.nea.enable.fallingAnimation": "【開發中】墜落動畫", 56 | "text.nea.enable.fallingAnimation.tooltip": "加入墜落動畫", 57 | "text.nea.enable.freezingAnimation": "冰凍動畫", 58 | "text.nea.enable.freezingAnimation.tooltip": "加入冰凍動畫", 59 | "text.nea.enable.huggingAnimation": "簡易抱抱動畫", 60 | "text.nea.enable.huggingAnimation.tooltip": "加入抱抱動畫。潛行時看著其他玩家來「擁抱」他們", 61 | "text.nea.enable.narutoRunning": "「火影跑」", 62 | "text.nea.enable.narutoRunning.tooltip": "加入火影忍者風格的跑步動畫(復活節彩蛋)", 63 | "text.nea.enable.enableInWorldBookRendering": "【開發中】世界內書本", 64 | "text.nea.enable.enableInWorldBookRendering.tooltip": "在世界中繪製帶有文字的書籍。這仍在開發中,可能無法正常運作", 65 | "text.nea.disableLegSmoothing": "停用腿部平滑", 66 | "text.nea.disableLegSmoothing.tooltip": "停用腿部平滑", 67 | "text.nea.enable.bowAnimation": "弓動畫", 68 | "text.nea.enable.bowAnimation.tooltip": "要使用的弓箭動畫類型", 69 | "text.nea.enable.bowAnimation.VANILLA": "原版", 70 | "text.nea.enable.bowAnimation.CUSTOM_V1": "自訂 V1" 71 | } 72 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/fullbody/FallingAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.fullbody; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.*; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | import dev.tr7zw.notenoughanimations.versionless.animations.DataHolder; 9 | //? if >= 1.21.11 { 10 | 11 | import net.minecraft.client.model.player.*; 12 | //? } else { 13 | /* 14 | import net.minecraft.client.model.*; 15 | *///? } 16 | import net.minecraft.client.player.AbstractClientPlayer; 17 | import net.minecraft.client.player.LocalPlayer; 18 | import net.minecraft.util.Mth; 19 | 20 | public class FallingAnimation extends BasicAnimation 21 | implements DataHolder { 22 | 23 | @Override 24 | public boolean isEnabled() { 25 | return NEABaseMod.config.fallingAnimation; 26 | } 27 | 28 | @Override 29 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 30 | //? if >= 1.17.0 { 31 | 32 | if (!entity.isFallFlying() && !NMSWrapper.onGround(entity) && !entity.onClimbable() 33 | && !entity.getAbilities().flying 34 | //? } else { 35 | 36 | // if (!entity.isFallFlying() && !entity.isOnGround() && !entity.onClimbable() && !entity.abilities.flying 37 | //? } 38 | && !entity.isSwimming()) { 39 | FallingData fallData = data.getData(this, () -> new FallingData(entity.getY())); 40 | if (entity instanceof LocalPlayer) { 41 | fallData.fallingSpeed = (float) (entity.getDeltaMovement().lengthSqr() / 11); 42 | return entity.fallDistance > 3; 43 | } 44 | if (entity.getY() == fallData.lastY) { // rerender in same tick 45 | return fallData.fallingSpeed > 0.5f / 3.5f; 46 | } else { 47 | fallData.fallingSpeed = (float) (fallData.lastY - entity.getY()) / 3.5f; 48 | fallData.lastY = entity.getY(); 49 | return fallData.fallingSpeed > 0.5f / 3.5f; 50 | } 51 | } 52 | return false; 53 | } 54 | 55 | @Override 56 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 57 | return BodyPart.values(); 58 | } 59 | 60 | @Override 61 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 62 | return 400; 63 | } 64 | 65 | @Override 66 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 67 | float tickCounter) { 68 | FallingData fallData = data.getData(this, () -> new FallingData(entity.getY())); 69 | float moveSqrt = fallData.fallingSpeed; 70 | float armsMove = Math.min(1, moveSqrt * 2); 71 | moveSqrt = Math.min(1, moveSqrt); 72 | float moveOutArms = 1.9F * armsMove; 73 | float moveOutLegs = 0.6F * moveSqrt; 74 | 75 | float movement = entity.tickCount + delta; 76 | if (part == BodyPart.LEFT_ARM) { 77 | model.leftArm.xRot = Mth.cos(movement * 0.6662F) * moveSqrt; 78 | model.leftArm.zRot = -moveOutArms; 79 | } 80 | if (part == BodyPart.RIGHT_ARM) { 81 | model.rightArm.xRot = Mth.cos(movement * 0.6662F + 3.1415927F) * moveSqrt; 82 | model.rightArm.zRot = moveOutArms; 83 | } 84 | if (part == BodyPart.LEFT_LEG) { 85 | model.leftLeg.xRot = Mth.cos(movement * 0.6662F + 3.1415927F) * 1.4F * moveSqrt; 86 | model.leftLeg.zRot = -moveOutLegs; 87 | } 88 | if (part == BodyPart.RIGHT_LEG) { 89 | model.rightLeg.xRot = Mth.cos(movement * 0.6662F) * 1.4F * moveSqrt; 90 | model.rightLeg.zRot = moveOutLegs; 91 | } 92 | } 93 | 94 | public static class FallingData { 95 | public FallingData(double y) { 96 | this.lastY = y; 97 | } 98 | 99 | public double lastY = 0; 100 | public float fallingSpeed = 0; 101 | } 102 | 103 | } 104 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/MapHoldingAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import java.util.HashSet; 4 | import java.util.Set; 5 | 6 | import dev.tr7zw.notenoughanimations.*; 7 | import dev.tr7zw.notenoughanimations.access.PlayerData; 8 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 9 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 10 | import dev.tr7zw.notenoughanimations.util.NMSWrapper; 11 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 12 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 13 | import dev.tr7zw.transition.mc.EntityUtil; 14 | //? if >= 1.21.11 { 15 | 16 | import net.minecraft.client.model.player.*; 17 | //? } else { 18 | /* 19 | import net.minecraft.client.model.*; 20 | *///? } 21 | import net.minecraft.client.player.AbstractClientPlayer; 22 | import net.minecraft.util.Mth; 23 | import net.minecraft.world.InteractionHand; 24 | import net.minecraft.world.entity.HumanoidArm; 25 | import net.minecraft.world.item.Item; 26 | import net.minecraft.world.item.ItemStack; 27 | 28 | public class MapHoldingAnimation extends BasicAnimation { 29 | 30 | private Set compatibleMaps = new HashSet<>(); 31 | 32 | @Override 33 | public boolean isEnabled() { 34 | bind(); 35 | return NEABaseMod.config.enableInWorldMapRendering || !compatibleMaps.isEmpty(); 36 | } 37 | 38 | private void bind() { 39 | compatibleMaps.clear(); 40 | compatibleMaps.addAll(AnimationUtil.parseItemList(NEAnimationsMod.config.mapHolding)); 41 | } 42 | 43 | @Override 44 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 45 | ItemStack itemInMainHand = entity.getItemInHand(InteractionHand.MAIN_HAND); 46 | ItemStack itemInOffHand = entity.getItemInHand(InteractionHand.OFF_HAND); 47 | if (compatibleMaps.contains(itemInMainHand.getItem()) && itemInOffHand.isEmpty()) { 48 | if (NMSWrapper.hasCustomModel(itemInMainHand)) { 49 | return false; 50 | } else { 51 | target = bothHands; 52 | return true; 53 | } 54 | } 55 | if (compatibleMaps.contains(itemInMainHand.getItem()) && !itemInOffHand.isEmpty()) { 56 | if (NMSWrapper.hasCustomModel(itemInMainHand)) { 57 | return false; 58 | } else { 59 | target = entity.getMainArm() == HumanoidArm.RIGHT ? right : left; 60 | return true; 61 | } 62 | 63 | } 64 | if (compatibleMaps.contains(itemInOffHand.getItem()) && !itemInOffHand.isEmpty()) { 65 | if (NMSWrapper.hasCustomModel(itemInOffHand)) { 66 | return false; 67 | } else { 68 | target = entity.getMainArm() == HumanoidArm.RIGHT ? left : right; 69 | return true; 70 | } 71 | } 72 | 73 | return false; 74 | } 75 | 76 | private final BodyPart[] bothHands = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM }; 77 | private final BodyPart[] left = new BodyPart[] { BodyPart.LEFT_ARM }; 78 | private final BodyPart[] right = new BodyPart[] { BodyPart.RIGHT_ARM }; 79 | private BodyPart[] target = bothHands; 80 | 81 | @Override 82 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 83 | return target; 84 | } 85 | 86 | @Override 87 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 88 | return 300; 89 | } 90 | 91 | @Override 92 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 93 | float tickCounter) { 94 | HumanoidArm arm = part == BodyPart.LEFT_ARM ? HumanoidArm.LEFT : HumanoidArm.RIGHT; 95 | if (target == bothHands) { 96 | AnimationUtil.applyArmTransforms(model, arm, 97 | -(Mth.lerp(-1f * (EntityUtil.getXRot(entity) - 90f) / 180f, 0.7f, 0.9f)), 98 | (Mth.lerp(-1f * (EntityUtil.getXRot(entity) - 90f) / 180f, -0.3f, -0.2f)), 0.3f); 99 | return; 100 | } 101 | AnimationUtil.applyArmTransforms(model, arm, 102 | -(Mth.lerp(-1f * (EntityUtil.getXRot(entity) - 90f) / 180f, 0.5f, 1.5f)), 0f, 0.3f); 103 | } 104 | 105 | } 106 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/PlayerRendererMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.util.RenderStateHolder; 5 | import org.spongepowered.asm.mixin.Mixin; 6 | import org.spongepowered.asm.mixin.injection.At; 7 | import org.spongepowered.asm.mixin.injection.Inject; 8 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 9 | 10 | import dev.tr7zw.notenoughanimations.renderlayer.SwordRenderLayer; 11 | import net.minecraft.client.model.HumanoidModel; 12 | import net.minecraft.client.player.AbstractClientPlayer; 13 | 14 | import net.minecraft.client.renderer.entity.LivingEntityRenderer; 15 | //? if >= 1.21.2 { 16 | 17 | import net.minecraft.client.renderer.entity.state.HumanoidRenderState; 18 | //? } 19 | //? if >= 1.17.0 { 20 | 21 | import net.minecraft.client.renderer.entity.EntityRendererProvider.Context; 22 | //? } else { 23 | 24 | // import net.minecraft.client.renderer.entity.EntityRenderDispatcher; 25 | //? } 26 | 27 | //? if >= 1.21.9 { 28 | 29 | @Mixin(net.minecraft.client.renderer.entity.player.AvatarRenderer.class) 30 | //? } else { 31 | /* 32 | @Mixin(net.minecraft.client.renderer.entity.player.PlayerRenderer.class) 33 | *///? } 34 | //? if >= 1.21.2 { 35 | 36 | public abstract class PlayerRendererMixin 37 | extends LivingEntityRenderer> { 38 | //? } else { 39 | /* 40 | public abstract class PlayerRendererMixin 41 | extends LivingEntityRenderer> { 42 | *///? } 43 | 44 | //? if >= 1.21.9 { 45 | 46 | public PlayerRendererMixin(Context context, HumanoidModel model, float shadowRadius) { 47 | super(context, model, shadowRadius); 48 | } 49 | //? } else if >= 1.21.2 { 50 | /* 51 | public PlayerRendererMixin(Context context, net.minecraft.client.model.HumanoidModel model, float shadowRadius) { 52 | super(context, model, shadowRadius); 53 | } 54 | *///? } else if >= 1.17.0 { 55 | /* 56 | public PlayerRendererMixin(Context context, net.minecraft.client.model.PlayerModel entityModel, float f) { 57 | super(context, entityModel, f); 58 | } 59 | *///? } else { 60 | 61 | // public PlayerRendererMixin(EntityRenderDispatcher entityRenderDispatcher, 62 | // net.minecraft.client.model.PlayerModel entityModel, float f) { 63 | // super(entityRenderDispatcher, entityModel, f); 64 | // } 65 | //? } 66 | 67 | @Inject(method = "*", at = @At("RETURN")) 68 | public void onCreate(CallbackInfo info) { 69 | //? if < 1.21.9 { 70 | /* 71 | this.addLayer(new SwordRenderLayer(this)); 72 | *///? } 73 | } 74 | 75 | //? if >= 1.21.9 { 76 | 77 | @Inject(method = "extractRenderState(Lnet/minecraft/world/entity/Avatar;Lnet/minecraft/client/renderer/entity/state/AvatarRenderState;F)V", at = @At("HEAD")) 78 | private void includeData(net.minecraft.world.entity.Avatar abstractClientPlayer, 79 | net.minecraft.client.renderer.entity.state.AvatarRenderState playerRenderState, float f, CallbackInfo ci) { 80 | if (abstractClientPlayer instanceof PlayerData playerData) { 81 | RenderStateHolder.RenderStateData data = playerData.getData(RenderStateHolder.INSTANCE, 82 | RenderStateHolder.RenderStateData::new); 83 | data.renderState = playerRenderState; 84 | } 85 | } 86 | //? } else if >= 1.21.2 { 87 | /* 88 | @Inject(method = "extractRenderState(Lnet/minecraft/client/player/AbstractClientPlayer;Lnet/minecraft/client/renderer/entity/state/PlayerRenderState;F)V", at = @At("HEAD")) 89 | private void includeData(AbstractClientPlayer abstractClientPlayer, net.minecraft.client.renderer.entity.state.PlayerRenderState playerRenderState, float f, 90 | CallbackInfo ci) { 91 | if (abstractClientPlayer instanceof PlayerData playerData) { 92 | RenderStateHolder.RenderStateData data = playerData.getData(RenderStateHolder.INSTANCE, 93 | RenderStateHolder.RenderStateData::new); 94 | data.renderState = playerRenderState; 95 | } 96 | } 97 | *///? } 98 | 99 | } 100 | -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/lang/zh_cn.json: -------------------------------------------------------------------------------- 1 | { 2 | "modmenu.descriptionTranslation.notenoughanimations": "添加和改进第三人称动画。", 3 | "text.nea.title": "Not Enough Animations 模组设置", 4 | "text.nea.enable.animationsmoothing": "平滑动画", 5 | "text.nea.enable.animationsmoothing.tooltip": "平滑手臂和腿部的动画,让它们看起来还更自然", 6 | "text.nea.smoothingSpeed": "平滑程度", 7 | "text.nea.smoothingSpeed.tooltip": "应用于手臂和腿部动画的平滑程度", 8 | "text.nea.enable.inworldmaprendering": "在世界上绘制地图", 9 | "text.nea.enable.inworldmaprendering.tooltip": "在世界中呈现地图,而不是只在第一人称视角中呈现", 10 | "text.nea.enable.offhandhiding": "弓动画修复", 11 | "text.nea.enable.offhandhiding.tooltip": "在拉弓时隐藏副手物品", 12 | "text.nea.enable.rotationlocking": "x动画", 13 | "text.nea.enable.rotationlocking.tooltip": "锁定玩家身体的旋转与玩家头部的旋转保持一致", 14 | "text.nea.enable.ladderanimation": "爬梯动画", 15 | "text.nea.enable.ladderanimation.tooltip": "新增攀爬梯子的动画(注意:只有梯子,不包括藤蔓、脚手架等)", 16 | "text.nea.enable.eatdrinkanimation": "吃与喝动画", 17 | "text.nea.enable.eatdrinkanimation.tooltip": "新增吃和喝的动画", 18 | "text.nea.enable.rowboatanimation": "划船动画", 19 | "text.nea.enable.rowboatanimation.tooltip": "新增划船的动画", 20 | "text.nea.enable.horseanimation": "骑马动画", 21 | "text.nea.enable.horseanimation.tooltip": "新增骑马的动画", 22 | "text.nea.enable.dontholditemsinbed": "睡觉时无物品", 23 | "text.nea.enable.dontholditemsinbed.tooltip": "防止玩家在床里拿着物品", 24 | "text.nea.enable.freezearmsinbed": "睡觉时无动作", 25 | "text.nea.enable.freezearmsinbed.tooltip": "防止玩家在床里移动手臂", 26 | "text.nea.rotationlock": "旋转锁定", 27 | "text.nea.rotationlock.tooltip": "旋转锁定使用的类型", 28 | "text.nea.rotationlock.NONE": "无", 29 | "text.nea.rotationlock.FIXED": "修复", 30 | "text.nea.rotationlock.SMOOTH": "平滑", 31 | "text.nea.enable.showlastusedsword": "【已弃用】收剑", 32 | "text.nea.enable.showlastusedsword.tooltip": "【已弃用,将来会移除!使用其他模组实现此功能!】显示玩家上次使用的剑。这只是一种视觉效果,并不知道实际的物品列表。请不要报告剑在丢弃/放入箱子等后仍然呈现的“错误”", 33 | "text.nea.enable.crawling": "潜行动画", 34 | "text.nea.enable.crawling.tooltip": "新增潜行的动画,取代原版的“爬行”(游泳)动画", 35 | "text.nea.enable.rotatetoladder": "将身体贴合在梯子上", 36 | "text.nea.enable.rotatetoladder.tooltip": "玩家爬梯子时将玩家的身体转向梯子", 37 | "text.nea.holdUpItemsMode": "握持模式", 38 | "text.nea.holdUpItemsMode.tooltip": "使玩家握持物品(就像他们在看着它们/在前方握持着物品)", 39 | "text.nea.holdUpItemsMode.ALL": "全部物品", 40 | "text.nea.holdUpItemsMode.NONE": "无物品", 41 | "text.nea.holdUpItemsMode.CONFIG": "仅设置中的物品", 42 | "text.nea.holdUpItemOffset": "手持物品的高度调整", 43 | "text.nea.holdUpItemOffset.tooltip": "修改物品被举起的高度程度", 44 | "text.nea.enable.holdupallitems": "拿着所有物品", 45 | "text.nea.enable.holdupallitems.tooltip": "允许玩家握住所有物品,而不仅限于设置中的物品", 46 | "text.nea.ladderAnimationAmplifier": "爬梯手臂放大", 47 | "text.nea.ladderAnimationAmplifier.tooltip": "在爬梯时应用的手臂移动量", 48 | "text.nea.ladderAnimationArmHeight": "爬梯手臂高度", 49 | "text.nea.ladderAnimationArmHeight.tooltip": "爬梯时手臂的高度", 50 | "text.nea.ladderAnimationArmSpeed": "爬梯手臂速度", 51 | "text.nea.ladderAnimationArmSpeed.tooltip": "爬梯时手臂的速度", 52 | "text.nea.enable.itemSwapAnimation": "物品交换动画", 53 | "text.nea.enable.itemSwapAnimation.tooltip": "新增主手与副手交换物品的动画", 54 | "text.nea.enable.tweakElytraAnimation": "调整鞘翅飞行", 55 | "text.nea.enable.tweakElytraAnimation.tooltip": "调整鞘翅的飞行动画,使其看起来更自然", 56 | "text.nea.enable.petAnimation": "宠物猫、狼", 57 | "text.nea.enable.petAnimation.tooltip": "为抚摸狼和猫添加动画。潜行并注视狼或猫时,可以抚摸它", 58 | "text.nea.enable.fallingAnimation": "【制作中】摔落动画", 59 | "text.nea.enable.fallingAnimation.tooltip": "新增摔落的动画", 60 | "text.nea.enable.freezingAnimation": "冻结动画", 61 | "text.nea.enable.freezingAnimation.tooltip": "新增冻结的动画", 62 | "text.nea.enable.huggingAnimation": "简易的抱抱动画", 63 | "text.nea.enable.huggingAnimation.tooltip": "新增抱抱的动画。当潜行时,注视另一个玩家以“拥抱”他们", 64 | "text.nea.enable.narutoRunning": "「火影忍者跑步」", 65 | "text.nea.enable.narutoRunning.tooltip": "新增火影忍者风格的跑步动画(复活节彩蛋)", 66 | "text.nea.enable.enableInWorldBookRendering": "【制作中】世界上书本", 67 | "text.nea.enable.enableInWorldBookRendering.tooltip": "在世界中绘制带有文字的书籍。这仍在开发中,可能无法正常运作", 68 | "text.nea.disableLegSmoothing": "禁用腿部平滑", 69 | "text.nea.disableLegSmoothing.tooltip": "禁用腿部平滑", 70 | "text.nea.enable.bowAnimation": "弓动画", 71 | "text.nea.enable.bowAnimation.tooltip": "弓使用的动画类型", 72 | "text.nea.enable.bowAnimation.VANILLA": "原版", 73 | "text.nea.enable.bowAnimation.CUSTOM_V1": "自定义 V1", 74 | "text.nea.enable.burningAnimation": "燃烧动画", 75 | "text.nea.enable.burningAnimation.tooltip": "为玩家处于着火状态时添加动画效果。", 76 | "text.nea.holdUpTarget": "举起物品", 77 | "text.nea.holdUpTarget.tooltip": "改变举起物品时的指向位置", 78 | "text.nea.holdUpTarget.NONE": "无指向", 79 | "text.nea.holdUpTarget.CAMERA": "摄像头", 80 | "text.nea.holdUpCameraOffset": "举起摄像头偏移", 81 | "text.nea.holdUpCameraOffset.tooltip": "修改在摄像头模式下举起物品时手臂向两侧的偏移量", 82 | "text.nea.enable.holdUpOnlySelf": "仅玩家", 83 | "text.nea.enable.holdUpOnlySelf.tooltip": "仅对玩家自身应用举起效果,不对其他玩家应用", 84 | "text.nea.enable.limitRotationLockToFP": "限制旋转锁定到第一人称", 85 | "text.nea.enable.limitRotationLockToFP.tooltip": "仅在第一人称视角中应用旋转锁定效果" 86 | } 87 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/hands/LookAtItemAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.hands; 2 | 3 | import java.util.HashSet; 4 | import java.util.Set; 5 | 6 | import dev.tr7zw.notenoughanimations.access.PlayerData; 7 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 8 | import dev.tr7zw.notenoughanimations.util.AnimationUtil; 9 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 10 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 11 | import dev.tr7zw.notenoughanimations.versionless.animations.HoldUpModes; 12 | import dev.tr7zw.transition.mc.EntityUtil; 13 | import net.minecraft.client.Minecraft; 14 | //? if >= 1.21.11 { 15 | 16 | import net.minecraft.client.model.player.*; 17 | //? } else { 18 | /* 19 | import net.minecraft.client.model.*; 20 | *///? } 21 | import net.minecraft.client.player.AbstractClientPlayer; 22 | import net.minecraft.util.Mth; 23 | import net.minecraft.world.InteractionHand; 24 | import net.minecraft.world.entity.HumanoidArm; 25 | import net.minecraft.world.item.Item; 26 | import net.minecraft.world.item.ItemStack; 27 | 28 | public class LookAtItemAnimation extends BasicAnimation { 29 | 30 | private Set holdingItems = new HashSet<>(); 31 | 32 | @Override 33 | public boolean isEnabled() { 34 | bind(); 35 | return NEABaseMod.config.holdUpItemsMode != HoldUpModes.NONE && !holdingItems.isEmpty(); 36 | } 37 | 38 | private void bind() { 39 | holdingItems.clear(); 40 | holdingItems.addAll(AnimationUtil.parseItemList(NEABaseMod.config.holdingItems)); 41 | } 42 | 43 | @Override 44 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 45 | if (NEABaseMod.config.holdUpOnlySelf && entity != Minecraft.getInstance().player) { 46 | return false; 47 | } 48 | boolean allItems = NEABaseMod.config.holdUpItemsMode == HoldUpModes.ALL; 49 | ItemStack itemInRightHand = entity.getItemInHand( 50 | entity.getMainArm() == HumanoidArm.LEFT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 51 | ItemStack itemInLeftHand = entity.getItemInHand( 52 | entity.getMainArm() == HumanoidArm.RIGHT ? InteractionHand.OFF_HAND : InteractionHand.MAIN_HAND); 53 | boolean rightArm = (NEABaseMod.config.holdUpItemsMode == HoldUpModes.CONFIG 54 | && holdingItems.contains(itemInRightHand.getItem())) 55 | || (NEABaseMod.config.holdUpItemsMode == HoldUpModes.CONFIG_INVERTED 56 | && !holdingItems.contains(itemInRightHand.getItem())) 57 | || (allItems && !itemInRightHand.isEmpty() 58 | && (!entity.swinging || entity.getMainArm() != HumanoidArm.RIGHT)); 59 | boolean leftArm = (NEABaseMod.config.holdUpItemsMode == HoldUpModes.CONFIG 60 | && holdingItems.contains(itemInLeftHand.getItem())) 61 | || (NEABaseMod.config.holdUpItemsMode == HoldUpModes.CONFIG_INVERTED 62 | && !holdingItems.contains(itemInLeftHand.getItem())) 63 | || (allItems && !itemInLeftHand.isEmpty() 64 | && (!entity.swinging || entity.getMainArm() != HumanoidArm.LEFT)); 65 | if (rightArm && leftArm && !entity.swinging) { // can't be both hands while swinging 66 | target = bothHands; 67 | return true; 68 | } 69 | if (rightArm && !(entity.swinging 70 | && entity.swingingArm == (entity.getMainArm() == HumanoidArm.LEFT ? InteractionHand.OFF_HAND 71 | : InteractionHand.MAIN_HAND))) { 72 | target = right; 73 | return true; 74 | } 75 | if (leftArm && !(entity.swinging 76 | && entity.swingingArm == (entity.getMainArm() == HumanoidArm.RIGHT ? InteractionHand.OFF_HAND 77 | : InteractionHand.MAIN_HAND))) { 78 | target = left; 79 | return true; 80 | } 81 | return false; 82 | } 83 | 84 | private final BodyPart[] bothHands = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM }; 85 | private final BodyPart[] left = new BodyPart[] { BodyPart.LEFT_ARM }; 86 | private final BodyPart[] right = new BodyPart[] { BodyPart.RIGHT_ARM }; 87 | private BodyPart[] target = bothHands; 88 | 89 | @Override 90 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 91 | return target; 92 | } 93 | 94 | @Override 95 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 96 | return 300; 97 | } 98 | 99 | @Override 100 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 101 | float tickCounter) { 102 | HumanoidArm arm = part == BodyPart.LEFT_ARM ? HumanoidArm.LEFT : HumanoidArm.RIGHT; 103 | switch (NEABaseMod.config.holdUpTarget) { 104 | case NONE: 105 | AnimationUtil.applyArmTransforms(model, arm, -NEABaseMod.config.holdUpItemOffset 106 | - (Mth.lerp(-1f * (EntityUtil.getXRot(entity) - 90f) / 180f, 1f, 1.5f)), -0.2f, 0.3f); 107 | break; 108 | case CAMERA: 109 | float invert = part == BodyPart.LEFT_ARM ? -1 : 1; 110 | AnimationUtil.applyArmTransforms(model, arm, Mth.clamp(-1.5707964F + model.head.xRot, -2.5f, 0), 111 | Mth.clamp(NEABaseMod.config.holdUpCameraOffset + (model.head.yRot) * invert, -0.2f, 112 | Math.max(0.2f, NEABaseMod.config.holdUpCameraOffset)), 113 | 0.1f); 114 | break; 115 | } 116 | } 117 | 118 | } 119 | -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/lang/sv_se.json: -------------------------------------------------------------------------------- 1 | { 2 | "text.nea.title": "Inte Tillräckligt Med Animationsinställningar", 3 | "text.nea.enable.animationsmoothing": "Animationsutjämning", 4 | "text.nea.enable.animationsmoothing.tooltip": "Jämnar ut arm/ben-animationerna för att få dem att se mer naturliga och mindre hoppiga ut", 5 | "text.nea.smoothingSpeed": "Utjämningsmängd", 6 | "text.nea.smoothingSpeed.tooltip": "Mängden utjämning som ska tillämpas på arm/ben-animationerna", 7 | "text.nea.enable.inworldmaprendering": "Kartrendering i världen", 8 | "text.nea.enable.inworldmaprendering.tooltip": "Renderar kartan i världen istället för bara i första person", 9 | "text.nea.enable.offhandhiding": "Bågeanimationsfixar", 10 | "text.nea.enable.offhandhiding.tooltip": "Göm föremål i sekundära handen när du drar en båge", 11 | "text.nea.enable.rotationlocking": "Animationsrotationslåsning", 12 | "text.nea.enable.rotationlocking.tooltip": "Låser rotationen av spelarens kropp till rotationen av spelarens huvud", 13 | "text.nea.enable.ladderanimation": "Stegeanimation", 14 | "text.nea.enable.ladderanimation.tooltip": "Lägger till en animation för att klättra på stegar(notera: endast stegar, inte vinrankor, byggnadsställningar, etc.)", 15 | "text.nea.enable.eatdrinkanimation": "Ät/Drick Animation", 16 | "text.nea.enable.eatdrinkanimation.tooltip": "Lägger till en animation för att äta och dricka", 17 | "text.nea.enable.rowboatanimation": "Båtroddanimation", 18 | "text.nea.enable.rowboatanimation.tooltip": "Lägger till en animation för att ro en båt", 19 | "text.nea.enable.horseanimation": "Ridningsanimation", 20 | "text.nea.enable.horseanimation.tooltip": "Lägger till en animation för att rida en häst", 21 | "text.nea.enable.dontholditemsinbed": "Inga Sömnföremål", 22 | "text.nea.enable.dontholditemsinbed.tooltip": "Förhindrar spelaren från att hålla föremål i sängen", 23 | "text.nea.enable.freezearmsinbed": "Ingen Sömnrörelse", 24 | "text.nea.enable.freezearmsinbed.tooltip": "Förhindrar spelaren från att röra armarna i sängen", 25 | "text.nea.rotationlock": "Rotationslås", 26 | "text.nea.rotationlock.tooltip": "Typ av rotationslåsning som ska användas", 27 | "text.nea.rotationlock.NONE": "Ingen", 28 | "text.nea.rotationlock.FIXED": "Fixad", 29 | "text.nea.rotationlock.SMOOTH": "Jämn", 30 | "text.nea.enable.showlastusedsword": "[Utfasad]Skida Svärd", 31 | "text.nea.enable.showlastusedsword.tooltip": "[Utfasad för borttagning! Använd andra mods för den här funktionen!] Visar det senast använda svärdet på spelaren. Detta är bara en visuell effekt utan kunskap om det faktiska lagret. Vänligen rapportera inte 'buggar' att svärdet fortfarande renderas efter att ha kastat det/lagt det i en kista/etc..", 32 | "text.nea.enable.crawling": "Krypanimation", 33 | "text.nea.enable.crawling.tooltip": "Lägger till en animation för krypning, ersätter vanilj 'krypande' (simnings) animationen", 34 | "text.nea.enable.rotatetoladder": "Fäst Kropp Till Stege", 35 | "text.nea.enable.rotatetoladder.tooltip": "Roterar spelarens kropp så att den är vänd mot stegen när du klättrar på den", 36 | "text.nea.holdUpItemsMode": "Hålla Upp Läge", 37 | "text.nea.holdUpItemsMode.tooltip": "Får spelaren att hålla upp föremål(som om de tittar på dem/håller dem framför sig)", 38 | "text.nea.holdUpItemsMode.ALL": "Alla Föremål", 39 | "text.nea.holdUpItemsMode.NONE": "Inga Föremål", 40 | "text.nea.holdUpItemsMode.CONFIG": "Endast Konfigurerade Föremål", 41 | "text.nea.holdUpItemOffset": "Hålla Upp Offset", 42 | "text.nea.holdUpItemOffset.tooltip": "Justera hur mycket föremålet hålls uppe", 43 | "text.nea.ladderAnimationAmplifier": "Stegearmsförstärkare", 44 | "text.nea.ladderAnimationAmplifier.tooltip": "Mängden rörelse som ska tillämpas på armarna när du klättrar på en stege", 45 | "text.nea.ladderAnimationArmHeight": "Stegearmshöjd", 46 | "text.nea.ladderAnimationArmHeight.tooltip": "Armarnas höjd när man klättrar på en stege", 47 | "text.nea.ladderAnimationArmSpeed": "Stegearmshastighet", 48 | "text.nea.ladderAnimationArmSpeed.tooltip": "Armarnas hastighet när man klättrar på en stege", 49 | "text.nea.enable.itemSwapAnimation": "Föremålsbyteanimation", 50 | "text.nea.enable.itemSwapAnimation.tooltip": "Lägger till en animation för att byta objekt från primära handen till sekundära handen och vice versa", 51 | "text.nea.enable.tweakElytraAnimation": "Justera Elytraflygning", 52 | "text.nea.enable.tweakElytraAnimation.tooltip": "Justerar elytraflyganimationen för att få den att se mer naturlig ut", 53 | "text.nea.enable.petAnimation": "Klappa Vargar/Katter", 54 | "text.nea.enable.petAnimation.tooltip": "Lägger till en animation för att klappa vargar och katter. Titta på vargen/katten medan du smyger för att klappa den", 55 | "text.nea.enable.fallingAnimation": "[WIP]Fallanimation", 56 | "text.nea.enable.fallingAnimation.tooltip": "Lägger till en animation för att falla", 57 | "text.nea.enable.freezingAnimation": "Frysanimation", 58 | "text.nea.enable.freezingAnimation.tooltip": "Lägger till en animation för att frysa", 59 | "text.nea.enable.huggingAnimation": "Enkel Kramanimation", 60 | "text.nea.enable.huggingAnimation.tooltip": "Lägger till en animation för att kramas. Titta på en annan spelare medan du smyger för att 'krama' dem", 61 | "text.nea.enable.narutoRunning": "❝Naruto Running❞", 62 | "text.nea.enable.narutoRunning.tooltip": "Lägger till en animering för att springa i stil med Naruto(easter egg)", 63 | "text.nea.enable.enableInWorldBookRendering": "[WIP]Böcker i Världen", 64 | "text.nea.enable.enableInWorldBookRendering.tooltip": "Renderar böcker i världen med sin text. This is still a work in progress and may not work properly", 65 | "text.nea.disableLegSmoothing": "Inaktivera benutjämning", 66 | "text.nea.disableLegSmoothing.tooltip": "Inaktiverar utjämningen av benen", 67 | "text.nea.enable.bowAnimation": "Bågeanimation", 68 | "text.nea.enable.bowAnimation.tooltip": "Typ av bågeanimation som ska användas", 69 | "text.nea.enable.bowAnimation.VANILLA": "Vanilj", 70 | "text.nea.enable.bowAnimation.CUSTOM_V1": "Anpassad V1" 71 | } 72 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/ItemInHandLayerMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import com.mojang.blaze3d.vertex.PoseStack; 9 | 10 | import dev.tr7zw.notenoughanimations.NEAnimationsLoader; 11 | import net.minecraft.client.model.EntityModel; 12 | import net.minecraft.client.renderer.entity.RenderLayerParent; 13 | import net.minecraft.client.renderer.entity.layers.ItemInHandLayer; 14 | import net.minecraft.client.renderer.entity.layers.RenderLayer; 15 | import net.minecraft.world.entity.HumanoidArm; 16 | import net.minecraft.world.entity.LivingEntity; 17 | import net.minecraft.world.item.ItemStack; 18 | //? if >= 1.21.4 { 19 | 20 | import net.minecraft.client.renderer.item.ItemStackRenderState; 21 | import dev.tr7zw.notenoughanimations.access.ExtendedItemStackRenderState; 22 | //? } 23 | //? if >= 1.21.2 { 24 | 25 | import dev.tr7zw.notenoughanimations.access.ExtendedLivingRenderState; 26 | import net.minecraft.client.model.ArmedModel; 27 | //? if < 1.21.4 { 28 | /* 29 | import net.minecraft.client.resources.model.BakedModel; 30 | *///? } 31 | //? } 32 | //? if >= 1.19.4 { 33 | 34 | //? if < 1.21.4 { 35 | /* 36 | import net.minecraft.world.item.ItemDisplayContext; 37 | *///? } 38 | //? } else { 39 | /* 40 | import net.minecraft.client.renderer.block.model.ItemTransforms.TransformType; 41 | *///? } 42 | 43 | @Mixin(ItemInHandLayer.class) 44 | //? if >= 1.21.9 { 45 | 46 | public abstract class ItemInHandLayerMixin & ArmedModel> 47 | extends RenderLayer { 48 | public ItemInHandLayerMixin(RenderLayerParent renderer) { 49 | super(renderer); 50 | } 51 | //? } else if >= 1.21.2 { 52 | /* 53 | public abstract class ItemInHandLayerMixin & ArmedModel> 54 | extends RenderLayer { 55 | public ItemInHandLayerMixin(RenderLayerParent renderer) { 56 | super(renderer); 57 | } 58 | *///? } else { 59 | /* 60 | public abstract class ItemInHandLayerMixin> extends RenderLayer { 61 | public ItemInHandLayerMixin(RenderLayerParent renderLayerParent) { 62 | super(renderLayerParent); 63 | } 64 | *///? } 65 | 66 | //? if >= 1.21.9 { 67 | 68 | @Inject(at = @At("HEAD"), method = "submitArmWithItem", cancellable = true) 69 | private void submitArmWithItem(S armedEntityRenderState, ItemStackRenderState itemStackRenderState, 70 | //? if >= 1.21.11 { 71 | 72 | ItemStack passedItem, 73 | //? } 74 | HumanoidArm humanoidArm, PoseStack poseStack, 75 | net.minecraft.client.renderer.SubmitNodeCollector submitNodeCollector, int i, CallbackInfo ci) { 76 | LivingEntity livingEntity = ((ExtendedLivingRenderState) armedEntityRenderState).getEntity(); 77 | ItemStack itemStack = null; 78 | //? if >= 1.21.11 { 79 | 80 | itemStack = passedItem; 81 | //? } 82 | if (itemStackRenderState instanceof ExtendedItemStackRenderState ext && ext.getItemStack() != null) { 83 | itemStack = ext.getItemStack(); 84 | } else if (itemStack == null) { 85 | return; 86 | } 87 | NEAnimationsLoader.INSTANCE.heldItemHandler.onRenderItem(livingEntity, this.getParentModel(), itemStack, 88 | humanoidArm, poseStack, submitNodeCollector, armedEntityRenderState, i, ci); 89 | } 90 | //? } else { 91 | /* 92 | @Inject(at = @At("HEAD"), method = "renderArmWithItem", cancellable = true) 93 | //? if >= 1.21.4 { 94 | 95 | private void renderArmWithItem(net.minecraft.client.renderer.entity.state.ArmedEntityRenderState livingEntityRenderState, 96 | ItemStackRenderState itemStackRenderState, HumanoidArm humanoidArm, PoseStack poseStack, 97 | net.minecraft.client.renderer.MultiBufferSource multiBufferSource, int i, CallbackInfo ci) { 98 | LivingEntity livingEntity = ((ExtendedLivingRenderState) livingEntityRenderState).getEntity(); 99 | ItemStack itemStack = null; 100 | if (itemStackRenderState instanceof ExtendedItemStackRenderState ext && ext.getItemStack() != null) { 101 | itemStack = ext.getItemStack(); 102 | } else { 103 | return; 104 | } 105 | //? } else if >= 1.21.2 { 106 | /^ 107 | private void renderArmWithItem(net.minecraft.client.renderer.entity.state.LivingEntityRenderState livingEntityRenderState, BakedModel bakedModel, 108 | ItemStack itemStack, ItemDisplayContext itemDisplayContext, HumanoidArm humanoidArm, PoseStack poseStack, 109 | net.minecraft.client.renderer.MultiBufferSource multiBufferSource, int i, CallbackInfo ci) { 110 | LivingEntity livingEntity = ((ExtendedLivingRenderState) livingEntityRenderState).getEntity(); 111 | ^///? } else if >= 1.19.4 { 112 | /^ 113 | private void renderArmWithItem(LivingEntity livingEntity, ItemStack itemStack, 114 | ItemDisplayContext itemDisplayContext, HumanoidArm humanoidArm, PoseStack poseStack, 115 | net.minecraft.client.renderer.MultiBufferSource multiBufferSource, int i, CallbackInfo ci) { 116 | ^///? } else { 117 | /^ 118 | private void renderArmWithItem(LivingEntity livingEntity, ItemStack itemStack, TransformType transformType, HumanoidArm humanoidArm, PoseStack poseStack, net.minecraft.client.renderer.MultiBufferSource multiBufferSource, int i, CallbackInfo ci) { 119 | ^///? } 120 | if (livingEntity == null) { 121 | return; 122 | } 123 | NEAnimationsLoader.INSTANCE.heldItemHandler.onRenderItem(livingEntity, this.getParentModel(), itemStack, 124 | humanoidArm, poseStack, multiBufferSource, i, ci); 125 | } 126 | *///? } 127 | 128 | } 129 | -------------------------------------------------------------------------------- /src/test/java/dev/tr7zw/tests/TestUtil.java: -------------------------------------------------------------------------------- 1 | //package dev.tr7zw.tests; 2 | // 3 | //import java.io.InputStream; 4 | //import java.lang.reflect.Field; 5 | //import java.lang.reflect.Method; 6 | //import java.util.ArrayList; 7 | //import java.util.HashSet; 8 | //import java.util.List; 9 | //import java.util.Objects; 10 | //import java.util.Set; 11 | //import java.util.function.BiConsumer; 12 | // 13 | //import com.google.common.collect.ImmutableMap; 14 | // 15 | //import dev.tr7zw.config.CustomConfigScreen; 16 | //import net.minecraft.client.OptionInstance; 17 | //import net.minecraft.client.gui.components.OptionsList; 18 | //import net.minecraft.client.model.PlayerModel; 19 | //import net.minecraft.client.model.geom.EntityModelSet; 20 | //import net.minecraft.client.model.geom.ModelLayerLocation; 21 | //import net.minecraft.client.model.geom.ModelPart; 22 | //import net.minecraft.client.model.geom.PartPose; 23 | //import net.minecraft.client.model.geom.builders.CubeDeformation; 24 | //import net.minecraft.client.model.geom.builders.CubeListBuilder; 25 | //import net.minecraft.client.model.geom.builders.PartDefinition; 26 | //import net.minecraft.client.renderer.entity.EntityRendererProvider; 27 | //import net.minecraft.client.renderer.entity.EntityRendererProvider.Context; 28 | //import net.minecraft.client.renderer.entity.player.PlayerRenderer; 29 | //import net.minecraft.locale.Language; 30 | //import net.minecraft.network.chat.FormattedText; 31 | //import net.minecraft.util.FormattedCharSequence; 32 | // 33 | //public class TestUtil { 34 | // 35 | // public static PlayerRenderer getPlayerRenderer() { 36 | // EntityRendererProvider.Context context = new Context(null, null, null, null, null, new DummyModelSet(), null); 37 | // return new PlayerRenderer(context, false); 38 | // } 39 | // 40 | // private static class DummyModelSet extends EntityModelSet { 41 | // 42 | // @Override 43 | // public ModelPart bakeLayer(ModelLayerLocation modelLayerLocation) { 44 | // PartDefinition part = PlayerModel.createMesh(CubeDeformation.NONE, false).getRoot(); 45 | // part.getChild("head").addOrReplaceChild("jaw", CubeListBuilder.create(), PartPose.ZERO); 46 | // part.getChild("head").addOrReplaceChild("left_ear", CubeListBuilder.create(), PartPose.ZERO); 47 | // part.getChild("head").addOrReplaceChild("right_ear", CubeListBuilder.create(), PartPose.ZERO); 48 | // part.addOrReplaceChild("left_wing", CubeListBuilder.create(), PartPose.ZERO); 49 | // part.addOrReplaceChild("right_wing", CubeListBuilder.create(), PartPose.ZERO); 50 | // part.addOrReplaceChild("tail", CubeListBuilder.create(), PartPose.ZERO); 51 | // part.getChild("head").addOrReplaceChild("feather", CubeListBuilder.create(), PartPose.ZERO); 52 | // part.addOrReplaceChild("box", CubeListBuilder.create(), PartPose.ZERO); 53 | // return part.bake(0, 0); 54 | // } 55 | // 56 | // } 57 | // 58 | // public static Language loadDefault(String file) throws Throwable { 59 | // ImmutableMap.Builder builder = ImmutableMap.builder(); 60 | // Objects.requireNonNull(builder); 61 | // BiConsumer biConsumer = builder::put; 62 | // InputStream inputStream = Language.class.getResourceAsStream(file); 63 | // try { 64 | // Language.loadFromJson(inputStream, biConsumer); 65 | // if (inputStream != null) 66 | // inputStream.close(); 67 | // } catch (Throwable throwable) { 68 | // if (inputStream != null) 69 | // try { 70 | // inputStream.close(); 71 | // } catch (Throwable throwable1) { 72 | // throwable.addSuppressed(throwable1); 73 | // } 74 | // throw throwable; 75 | // } 76 | // final ImmutableMap storage = builder.build(); 77 | // return new Language() { 78 | // public String getOrDefault(String string) { 79 | // return (String) storage.getOrDefault(string, string); 80 | // } 81 | // 82 | // public boolean has(String string) { 83 | // return storage.containsKey(string); 84 | // } 85 | // 86 | // public boolean isDefaultRightToLeft() { 87 | // return false; 88 | // } 89 | // 90 | // public FormattedCharSequence getVisualOrder(FormattedText formattedText) { 91 | // return null; 92 | // } 93 | // 94 | // @Override 95 | // public String getOrDefault(String paramString1, String paramString2) { 96 | // return (String) storage.getOrDefault(paramString1, paramString2); 97 | // } 98 | // }; 99 | // } 100 | // 101 | // public static Set getKeys(OptionInstance optionsInstance, boolean tooltips) { 102 | // Set keys = new HashSet<>(); 103 | // keys.add(optionsInstance.toString()); 104 | // if (tooltips) { 105 | // keys.add(optionsInstance.toString() + ".tooltip"); 106 | // } 107 | // return keys; 108 | // } 109 | // 110 | // public static List> bootStrapCustomConfigScreen(CustomConfigScreen screen) throws Exception { 111 | // Field optionsField = CustomConfigScreen.class.getDeclaredField("list"); 112 | // optionsField.setAccessible(true); 113 | // CustomOptionsList list = new CustomOptionsList(); 114 | // optionsField.set(screen, list); 115 | // Method init = CustomConfigScreen.class.getDeclaredMethod("initialize"); 116 | // init.setAccessible(true); 117 | // init.invoke(screen); 118 | // return list.options; 119 | // } 120 | // 121 | // private static class CustomOptionsList extends OptionsList { 122 | // 123 | // public List> options = new ArrayList<>(); 124 | // 125 | // public CustomOptionsList() { 126 | // super(null, 0, 0, 0, 0, 0); 127 | // } 128 | // 129 | // @Override 130 | // public int addBig(OptionInstance optionInstance) { 131 | // options.add(optionInstance); 132 | // return 0; 133 | // } 134 | // 135 | // @Override 136 | // public void addSmall(OptionInstance optionInstance, OptionInstance optionInstance2) { 137 | // options.add(optionInstance); 138 | // } 139 | // 140 | // } 141 | // 142 | //} 143 | -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/lang/fr_fr.json: -------------------------------------------------------------------------------- 1 | { 2 | "text.nea.title": "Paramètres de Not Enough Animations", 3 | "text.nea.enable.animationsmoothing": "Lissage des animations", 4 | "text.nea.enable.animationsmoothing.tooltip": "Lisse les animations des bras/jambes pour les rendre plus naturelles et moins saccadées", 5 | "text.nea.smoothingSpeed": "Intensité du lissage", 6 | "text.nea.smoothingSpeed.tooltip": "L'intensité du lissage à appliquer aux animations des bras/jambes", 7 | "text.nea.enable.inworldmaprendering": "Rendu de la carte dans le monde", 8 | "text.nea.enable.inworldmaprendering.tooltip": "Affiche la carte dans le monde plutôt que seulement en vue à la première personne", 9 | "text.nea.enable.offhandhiding": "Corrections d'animation de la seconde main", 10 | "text.nea.enable.offhandhiding.tooltip": "Masque les objets de la seconde main lors du tir à l'arc", 11 | "text.nea.enable.rotationlocking": "Verrouillage de rotation de l'animation", 12 | "text.nea.enable.rotationlocking.tooltip": "Verrouille la rotation du corps du joueur sur la rotation de la tête du joueur", 13 | "text.nea.enable.ladderanimation": "Animation d'escalade des échelles", 14 | "text.nea.enable.ladderanimation.tooltip": "Ajoute une animation pour grimper aux échelles (note : uniquement les échelles, pas les lianes, les échafaudages, etc.)", 15 | "text.nea.enable.eatdrinkanimation": "Animation de manger/boire", 16 | "text.nea.enable.eatdrinkanimation.tooltip": "Ajoute une animation pour manger et boire", 17 | "text.nea.enable.rowboatanimation": "Animation de rame de bateau", 18 | "text.nea.enable.rowboatanimation.tooltip": "Ajoute une animation pour ramer un bateau", 19 | "text.nea.enable.horseanimation": "Animation à cheval", 20 | "text.nea.enable.horseanimation.tooltip": "Ajoute une animation à cheval", 21 | "text.nea.enable.dontholditemsinbed": "Pas d'objets en dormant", 22 | "text.nea.enable.dontholditemsinbed.tooltip": "Empêche le joueur de tenir des objets lorsqu'il est dans un lit", 23 | "text.nea.enable.freezearmsinbed": "Pas de mouvement en dormant", 24 | "text.nea.enable.freezearmsinbed.tooltip": "Empêche le joueur de bouger les bras lorsqu'il est dans un lit", 25 | "text.nea.rotationlock": "Verrouillage de rotation", 26 | "text.nea.rotationlock.tooltip": "Type de verrouillage de rotation à utiliser", 27 | "text.nea.rotationlock.NONE": "Aucun", 28 | "text.nea.rotationlock.FIXED": "Fixe", 29 | "text.nea.rotationlock.SMOOTH": "Lisse", 30 | "text.nea.enable.showlastusedsword": "[Obsolète] Étui d'épée", 31 | "text.nea.enable.showlastusedsword.tooltip": "[Obsolète ! Utilisez d'autres mods pour cette fonctionnalité !] Affiche la dernière épée utilisée sur le joueur. Il s'agit uniquement d'un effet visuel sans connaissance de l'inventaire réel. Veuillez ne pas signaler de 'bugs' indiquant que l'épée est toujours rendue après l'avoir jetée/stockée dans un coffre, etc.", 32 | "text.nea.enable.crawling": "Animation de ramper", 33 | "text.nea.enable.crawling.tooltip": "Ajoute une animation de ramper, remplaçant l'animation de 'nage' (crawling) classique", 34 | "text.nea.enable.rotatetoladder": "Corps aligné sur l'échelle", 35 | "text.nea.enable.rotatetoladder.tooltip": "Oriente le corps du joueur vers l'échelle lorsqu'il la grimpe", 36 | "text.nea.holdUpItemsMode": "Mode de tenue des objets", 37 | "text.nea.holdUpItemsMode.tooltip": "Fait tenir les objets au joueur (comme s'il les regardait/les tenait devant lui)", 38 | "text.nea.holdUpItemsMode.ALL": "Tous les objets", 39 | "text.nea.holdUpItemsMode.NONE": "Aucun objet", 40 | "text.nea.holdUpItemsMode.CONFIG": "Uniquement les objets de configuration", 41 | "text.nea.holdUpItemOffset": "Décalage de tenue", 42 | "text.nea.holdUpItemOffset.tooltip": "Modifie la façon dont l'objet est tenu en l'air", 43 | "text.nea.ladderAnimationAmplifier": "Amplificateur de mouvement des bras sur une échelle", 44 | "text.nea.ladderAnimationAmplifier.tooltip": "La quantité de mouvement à appliquer aux bras lors de l'escalade d'une échelle", 45 | "text.nea.ladderAnimationArmHeight": "Hauteur des bras sur une échelle", 46 | "text.nea.ladderAnimationArmHeight.tooltip": "La hauteur des bras lors de l'escalade d'une échelle", 47 | "text.nea.ladderAnimationArmSpeed": "Vitesse des bras sur une échelle", 48 | "text.nea.ladderAnimationArmSpeed.tooltip": "La vitesse des bras lors de l'escalade d'une échelle", 49 | "text.nea.enable.itemSwapAnimation": "Animation d'échange d'objets", 50 | "text.nea.enable.itemSwapAnimation.tooltip": "Ajoute une animation pour l'échange d'objets de la main principale à la main secondaire et vice versa", 51 | "text.nea.enable.tweakElytraAnimation": "Ajustement de l'animation de vol en élytres", 52 | "text.nea.enable.tweakElytraAnimation.tooltip": "Ajuste l'animation de vol en élytres pour la rendre plus naturelle", 53 | "text.nea.enable.petAnimation": "Animation de caresse d'animaux", 54 | "text.nea.enable.petAnimation.tooltip": "Ajoute une animation pour caresser les loups et les chats. Regardez le loup/le chat en étant accroupi pour le caresser", 55 | "text.nea.enable.fallingAnimation": "[TRAVAIL EN COURS] Animation de chute", 56 | "text.nea.enable.fallingAnimation.tooltip": "Ajoute une animation pour la chute", 57 | "text.nea.enable.freezingAnimation": "Animation de congélation", 58 | "text.nea.enable.freezingAnimation.tooltip": "Ajoute une animation pour la congélation", 59 | "text.nea.enable.huggingAnimation": "Animation de câlin simple", 60 | "text.nea.enable.huggingAnimation.tooltip": "Ajoute une animation pour les câlins. Regardez un autre joueur en étant accroupi pour le 'câliner'", 61 | "text.nea.enable.narutoRunning": "❝Course à la Naruto❞", 62 | "text.nea.enable.narutoRunning.tooltip": "Ajoute une animation pour courir dans le style de Naruto (easter egg)", 63 | "text.nea.enable.enableInWorldBookRendering": "[TRAVAIL EN COURS] Livres en jeu", 64 | "text.nea.enable.enableInWorldBookRendering.tooltip": "Affiche les livres dans le monde avec leur texte. Ceci est encore en cours de développement et peut ne pas fonctionner correctement", 65 | "text.nea.disableLegSmoothing": "Désactiver le lissage des jambes", 66 | "text.nea.disableLegSmoothing.tooltip": "Désactive le lissage des jambes", 67 | "text.nea.enable.bowAnimation": "Animation d'arc", 68 | "text.nea.enable.bowAnimation.tooltip": "Le type d'animation d'arc à utiliser", 69 | "text.nea.enable.bowAnimation.VANILLA": "Vanilla", 70 | "text.nea.enable.bowAnimation.CUSTOM_V1": "Personnalisé V1" 71 | } 72 | -------------------------------------------------------------------------------- /gradlecw: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env sh 2 | 3 | # 4 | # Copyright 2015 the original author or authors. 5 | # 6 | # Licensed under the Apache License, Version 2.0 (the "License"); 7 | # you may not use this file except in compliance with the License. 8 | # You may obtain a copy of the License at 9 | # 10 | # https://www.apache.org/licenses/LICENSE-2.0 11 | # 12 | # Unless required by applicable law or agreed to in writing, software 13 | # distributed under the License is distributed on an "AS IS" BASIS, 14 | # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 15 | # See the License for the specific language governing permissions and 16 | # limitations under the License. 17 | # 18 | 19 | ############################################################################## 20 | ## 21 | ## Gradle start up script for UN*X 22 | ## 23 | ############################################################################## 24 | 25 | # Attempt to set APP_HOME 26 | # Resolve links: $0 may be a link 27 | PRG="$0" 28 | # Need this for relative symlinks. 29 | while [ -h "$PRG" ] ; do 30 | ls=`ls -ld "$PRG"` 31 | link=`expr "$ls" : '.*-> \(.*\)$'` 32 | if expr "$link" : '/.*' > /dev/null; then 33 | PRG="$link" 34 | else 35 | PRG=`dirname "$PRG"`"/$link" 36 | fi 37 | done 38 | SAVED="`pwd`" 39 | cd "`dirname \"$PRG\"`/" >/dev/null 40 | APP_HOME="`pwd -P`" 41 | cd "$SAVED" >/dev/null 42 | 43 | APP_NAME="Gradle" 44 | APP_BASE_NAME=`basename "$0"` 45 | 46 | # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 47 | DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' 48 | 49 | # Use the maximum available, or set MAX_FD != -1 to use that value. 50 | MAX_FD="maximum" 51 | 52 | warn () { 53 | echo "$*" 54 | } 55 | 56 | die () { 57 | echo 58 | echo "$*" 59 | echo 60 | exit 1 61 | } 62 | 63 | # OS specific support (must be 'true' or 'false'). 64 | cygwin=false 65 | msys=false 66 | darwin=false 67 | nonstop=false 68 | case "`uname`" in 69 | CYGWIN* ) 70 | cygwin=true 71 | ;; 72 | Darwin* ) 73 | darwin=true 74 | ;; 75 | MINGW* ) 76 | msys=true 77 | ;; 78 | NONSTOP* ) 79 | nonstop=true 80 | ;; 81 | esac 82 | 83 | CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar 84 | 85 | COMPOSE=$APP_HOME/gradle/gradle-compose.jar 86 | 87 | # Determine the Java command to use to start the JVM. 88 | if [ -n "$JAVA_HOME" ] ; then 89 | if [ -x "$JAVA_HOME/jre/sh/java" ] ; then 90 | # IBM's JDK on AIX uses strange locations for the executables 91 | JAVACMD="$JAVA_HOME/jre/sh/java" 92 | else 93 | JAVACMD="$JAVA_HOME/bin/java" 94 | fi 95 | if [ ! -x "$JAVACMD" ] ; then 96 | die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME 97 | 98 | Please set the JAVA_HOME variable in your environment to match the 99 | location of your Java installation." 100 | fi 101 | else 102 | JAVACMD="java" 103 | which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 104 | 105 | Please set the JAVA_HOME variable in your environment to match the 106 | location of your Java installation." 107 | fi 108 | 109 | # Increase the maximum file descriptors if we can. 110 | if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then 111 | MAX_FD_LIMIT=`ulimit -H -n` 112 | if [ $? -eq 0 ] ; then 113 | if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then 114 | MAX_FD="$MAX_FD_LIMIT" 115 | fi 116 | ulimit -n $MAX_FD 117 | if [ $? -ne 0 ] ; then 118 | warn "Could not set maximum file descriptor limit: $MAX_FD" 119 | fi 120 | else 121 | warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT" 122 | fi 123 | fi 124 | 125 | # For Darwin, add options to specify how the application appears in the dock 126 | if $darwin; then 127 | GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\"" 128 | fi 129 | 130 | # For Cygwin or MSYS, switch paths to Windows format before running java 131 | if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then 132 | APP_HOME=`cygpath --path --mixed "$APP_HOME"` 133 | CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` 134 | 135 | JAVACMD=`cygpath --unix "$JAVACMD"` 136 | 137 | # We build the pattern for arguments to be converted via cygpath 138 | ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null` 139 | SEP="" 140 | for dir in $ROOTDIRSRAW ; do 141 | ROOTDIRS="$ROOTDIRS$SEP$dir" 142 | SEP="|" 143 | done 144 | OURCYGPATTERN="(^($ROOTDIRS))" 145 | # Add a user-defined pattern to the cygpath arguments 146 | if [ "$GRADLE_CYGPATTERN" != "" ] ; then 147 | OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)" 148 | fi 149 | # Now convert the arguments - kludge to limit ourselves to /bin/sh 150 | i=0 151 | for arg in "$@" ; do 152 | CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -` 153 | CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option 154 | 155 | if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition 156 | eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"` 157 | else 158 | eval `echo args$i`="\"$arg\"" 159 | fi 160 | i=`expr $i + 1` 161 | done 162 | case $i in 163 | 0) set -- ;; 164 | 1) set -- "$args0" ;; 165 | 2) set -- "$args0" "$args1" ;; 166 | 3) set -- "$args0" "$args1" "$args2" ;; 167 | 4) set -- "$args0" "$args1" "$args2" "$args3" ;; 168 | 5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;; 169 | 6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;; 170 | 7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;; 171 | 8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;; 172 | 9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;; 173 | esac 174 | fi 175 | 176 | 177 | 178 | "$JAVACMD" -jar $COMPOSE 179 | 180 | # Escape application args 181 | save () { 182 | for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done 183 | echo " " 184 | } 185 | APP_ARGS=`save "$@"` 186 | 187 | # Collect all arguments for the java command, following the shell quoting and substitution rules 188 | eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS" 189 | 190 | exec "$JAVACMD" "$@" 191 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/mixins/PlayerEntityModelMixin.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.mixins; 2 | 3 | //? if >= 1.21.2 { 4 | 5 | import dev.tr7zw.notenoughanimations.access.ExtendedLivingRenderState; 6 | //? } 7 | import org.spongepowered.asm.mixin.Mixin; 8 | import org.spongepowered.asm.mixin.Unique; 9 | import org.spongepowered.asm.mixin.injection.At; 10 | import org.spongepowered.asm.mixin.injection.Inject; 11 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 12 | 13 | import dev.tr7zw.notenoughanimations.NEAnimationsLoader; 14 | import dev.tr7zw.notenoughanimations.access.PlayerData; 15 | import net.minecraft.client.model.HumanoidModel; 16 | //? if >= 1.21.11 { 17 | 18 | import net.minecraft.client.model.player.*; 19 | //? } else { 20 | /* 21 | import net.minecraft.client.model.*; 22 | *///? } 23 | import net.minecraft.client.player.AbstractClientPlayer; 24 | 25 | @Mixin(PlayerModel.class) 26 | //? if >= 1.21.9 { 27 | 28 | public abstract class PlayerEntityModelMixin 29 | extends HumanoidModel { 30 | //? } else if >= 1.21.2 { 31 | /* 32 | public abstract class PlayerEntityModelMixin extends HumanoidModel { 33 | *///? } else { 34 | /* 35 | public abstract class PlayerEntityModelMixin extends HumanoidModel { 36 | *///? } 37 | 38 | @Unique 39 | //? if >= 1.21.2 && < 1.21.9 { 40 | /* 41 | private static final String SETUP_ANIM_METHOD = "setupAnim(Lnet/minecraft/client/renderer/entity/state/PlayerRenderState;)V"; 42 | *///? } else { 43 | 44 | private static final String SETUP_ANIM_METHOD = "setupAnim"; 45 | //? } 46 | 47 | public PlayerEntityModelMixin() { 48 | //? if >= 1.17.0 { 49 | 50 | super(null); 51 | //? } else { 52 | 53 | // super(0); 54 | //? } 55 | 56 | } 57 | 58 | @Inject(method = SETUP_ANIM_METHOD, at = @At(value = "HEAD")) 59 | //? if >= 1.21.2 { 60 | 61 | public void setupAnimHEAD( 62 | //? if >= 1.21.9 { 63 | 64 | net.minecraft.client.renderer.entity.state.AvatarRenderState state, 65 | //? } else { 66 | /* 67 | net.minecraft.client.renderer.entity.state.PlayerRenderState state, 68 | *///? } 69 | CallbackInfo info) { 70 | if (state == null || !(state instanceof ExtendedLivingRenderState)) { 71 | return; 72 | } 73 | float limbSwing = state.walkAnimationPos; // makes total sense :thumbs_up: 74 | PlayerModel model = (PlayerModel) (Object) this; 75 | AbstractClientPlayer player = null; 76 | if (((ExtendedLivingRenderState) state).getEntity() != null 77 | && ((ExtendedLivingRenderState) state).getEntity() instanceof AbstractClientPlayer p) { 78 | player = p; 79 | } 80 | if (player == null) { 81 | return; 82 | } 83 | //? } else { 84 | /* 85 | public void setupAnimHEAD(T livingEntity, float limbSwing, float limbSwingAmount, float ageInTicks, 86 | float netHeadYaw, float headPitch, CallbackInfo info) { 87 | PlayerModel model = (PlayerModel) (Object) this; 88 | if (!(livingEntity instanceof AbstractClientPlayer)) return; 89 | AbstractClientPlayer player = (AbstractClientPlayer) livingEntity; 90 | *///? } 91 | NEAnimationsLoader.INSTANCE.playerTransformer.preUpdate(player, model, limbSwing, info); 92 | } 93 | 94 | //? if >= 1.21.2 { 95 | 96 | @Inject(method = SETUP_ANIM_METHOD, at = @At(value = "RETURN")) 97 | public void setupAnim( 98 | //? if >= 1.21.9 { 99 | 100 | net.minecraft.client.renderer.entity.state.AvatarRenderState state, 101 | //? } else { 102 | /* 103 | net.minecraft.client.renderer.entity.state.PlayerRenderState state, 104 | *///? } 105 | CallbackInfo info) { 106 | float limbSwing = state.walkAnimationPos; // makes total sense :thumbs_up: 107 | PlayerModel model = (PlayerModel) (Object) this; 108 | AbstractClientPlayer player = null; 109 | if (((ExtendedLivingRenderState) state).getEntity() != null 110 | && ((ExtendedLivingRenderState) state).getEntity() instanceof AbstractClientPlayer p) { 111 | player = p; 112 | } 113 | if (player == null) { 114 | return; 115 | } 116 | //? } else { 117 | /* 118 | @Inject(method = "setupAnim", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/model/geom/ModelPart;copyFrom(Lnet/minecraft/client/model/geom/ModelPart;)V", ordinal = 0)) 119 | public void setupAnim(T livingEntity, float limbSwing, float limbSwingAmount, float ageInTicks, 120 | float netHeadYaw, float headPitch, CallbackInfo info) { 121 | PlayerModel model = (PlayerModel) (Object) this; 122 | if (!(livingEntity instanceof AbstractClientPlayer)) return; 123 | AbstractClientPlayer player = (AbstractClientPlayer) livingEntity; 124 | *///? } 125 | NEAnimationsLoader.INSTANCE.playerTransformer.updateModel(player, model, limbSwing, info); 126 | } 127 | 128 | @Inject(method = SETUP_ANIM_METHOD, at = @At(value = "RETURN")) 129 | //? if >= 1.21.2 { 130 | 131 | public void setupAnimEnd( 132 | //? if >= 1.21.9 { 133 | 134 | net.minecraft.client.renderer.entity.state.AvatarRenderState state, 135 | //? } else { 136 | /* 137 | net.minecraft.client.renderer.entity.state.PlayerRenderState state, 138 | *///? } 139 | CallbackInfo info) { 140 | AbstractClientPlayer player = null; 141 | if (((ExtendedLivingRenderState) state).getEntity() != null 142 | && ((ExtendedLivingRenderState) state).getEntity() instanceof AbstractClientPlayer p) { 143 | player = p; 144 | } 145 | if (player == null) { 146 | return; 147 | } 148 | PlayerData data = (PlayerData) player; 149 | //? } else { 150 | /* 151 | public void setupAnimEnd(T livingEntity, float limbSwing, float limbSwingAmount, float ageInTicks, 152 | float netHeadYaw, float headPitch, CallbackInfo info) { 153 | if (!(livingEntity instanceof PlayerData)) return; 154 | PlayerData data = (PlayerData) livingEntity; 155 | AbstractClientPlayer player = (AbstractClientPlayer) livingEntity; 156 | *///? } 157 | if (data.getPoseOverwrite() != null) { 158 | player.setPose(data.getPoseOverwrite()); 159 | data.setPoseOverwrite(null); 160 | } 161 | } 162 | 163 | } 164 | -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/lang/pt_br.json: -------------------------------------------------------------------------------- 1 | { 2 | "text.nea.title": "Configurações do Not Enough Animations", 3 | "text.nea.enable.animationsmoothing": "Suavização de Animação", 4 | "text.nea.enable.animationsmoothing.tooltip": "Suaviza os movimentos dos braços/pernas para parecerem mais naturais e menos bruscos", 5 | "text.nea.smoothingSpeed": "Intensidade da Suavização", 6 | "text.nea.smoothingSpeed.tooltip": "Define quanto de suavização aplicar às animações dos braços/pernas", 7 | "text.nea.enable.inworldmaprendering": "Renderizar Mapas no Mundo", 8 | "text.nea.enable.inworldmaprendering.tooltip": "Renderiza os mapas no mundo e não apenas em primeira pessoa", 9 | "text.nea.enable.offhandhiding": "Corrigir Animação com Arco", 10 | "text.nea.enable.offhandhiding.tooltip": "Oculta itens da mão secundária ao puxar o arco", 11 | "text.nea.enable.rotationlocking": "Travar Rotação da Animação", 12 | "text.nea.enable.rotationlocking.tooltip": "Trava a rotação do corpo do jogador à rotação da cabeça", 13 | "text.nea.enable.ladderanimation": "Animação na Escada", 14 | "text.nea.enable.ladderanimation.tooltip": "Adiciona animação ao subir escadas (nota: apenas escadas, não cipós, andaimes, etc.)", 15 | "text.nea.enable.eatdrinkanimation": "Animação de Comer/Beber", 16 | "text.nea.enable.eatdrinkanimation.tooltip": "Adiciona animações ao comer e beber", 17 | "text.nea.enable.rowboatanimation": "Animação de Remar", 18 | "text.nea.enable.rowboatanimation.tooltip": "Adiciona animação ao remar barcos", 19 | "text.nea.enable.horseanimation": "Animação de Montaria", 20 | "text.nea.enable.horseanimation.tooltip": "Adiciona animação ao montar em cavalos", 21 | "text.nea.enable.enableHorseLegAnimation": "Animação das Pernas ao Cavalgar", 22 | "text.nea.enable.enableHorseLegAnimation.tooltip": "Altera a pose das pernas do jogador ao cavalgar", 23 | "text.nea.enable.dontholditemsinbed": "Não Segurar Itens na Cama", 24 | "text.nea.enable.dontholditemsinbed.tooltip": "Impede o jogador de segurar itens enquanto dorme", 25 | "text.nea.enable.freezearmsinbed": "Congelar Movimento Dormindo", 26 | "text.nea.enable.freezearmsinbed.tooltip": "Impede o movimento dos braços do jogador na cama", 27 | "text.nea.rotationlock": "Tipo de Travamento de Rotação", 28 | "text.nea.rotationlock.tooltip": "Define o tipo de travamento de rotação a ser usado", 29 | "text.nea.rotationlock.NONE": "Nenhum", 30 | "text.nea.rotationlock.FIXED": "Fixado", 31 | "text.nea.rotationlock.SMOOTH": "Suave", 32 | "text.nea.enable.showlastusedsword": "[Obsoleto] Espada na Bainha", 33 | "text.nea.enable.showlastusedsword.tooltip": "[Obsoleto! Use outros mods para isso!] Mostra a última espada usada no jogador. É apenas visual e não verifica o inventário real.", 34 | "text.nea.enable.crawling": "Animação de Rastejar", 35 | "text.nea.enable.crawling.tooltip": "Adiciona uma animação personalizada ao engatinhar, substituindo a nativa de natação", 36 | "text.nea.enable.rotatetoladder": "Girar Corpo para Escada", 37 | "text.nea.enable.rotatetoladder.tooltip": "Faz o corpo do jogador virar para a escada ao subir", 38 | "text.nea.holdUpItemsMode": "Modo de Levantar Itens", 39 | "text.nea.holdUpItemsMode.tooltip": "Faz o jogador levantar os itens como se estivesse olhando para eles", 40 | "text.nea.holdUpItemsMode.ALL": "Todos os Itens", 41 | "text.nea.holdUpItemsMode.NONE": "Nenhum Item", 42 | "text.nea.holdUpItemsMode.CONFIG": "Somente Itens Configurados", 43 | "text.nea.holdUpItemOffset": "Altura ao Levantar Item", 44 | "text.nea.holdUpItemOffset.tooltip": "Ajusta a altura que o item é levantado", 45 | "text.nea.ladderAnimationAmplifier": "Intensidade do Movimento do Braço", 46 | "text.nea.ladderAnimationAmplifier.tooltip": "Define quanto os braços se movimentam ao subir escadas", 47 | "text.nea.ladderAnimationArmHeight": "Altura do Braço na Escada", 48 | "text.nea.ladderAnimationArmHeight.tooltip": "Define a altura dos braços ao subir escadas", 49 | "text.nea.ladderAnimationArmSpeed": "Velocidade do Braço na Escada", 50 | "text.nea.ladderAnimationArmSpeed.tooltip": "Define a velocidade dos braços ao subir escadas", 51 | "text.nea.enable.itemSwapAnimation": "Animação de Trocar Itens", 52 | "text.nea.enable.itemSwapAnimation.tooltip": "Adiciona uma animação ao trocar itens entre as mãos", 53 | "text.nea.enable.tweakElytraAnimation": "Ajuste da Animação com Elytra", 54 | "text.nea.enable.tweakElytraAnimation.tooltip": "Ajusta a animação de voo com elytra para parecer mais natural", 55 | "text.nea.enable.petAnimation": "Acariciar Lobos/Gatos", 56 | "text.nea.enable.petAnimation.tooltip": "Adiciona animação ao acariciar lobos e gatos (agache e olhe para eles)", 57 | "text.nea.enable.fallingAnimation": "[WIP] Animação de Queda", 58 | "text.nea.enable.fallingAnimation.tooltip": "Adiciona animação ao cair", 59 | "text.nea.enable.freezingAnimation": "Animação de Congelamento", 60 | "text.nea.enable.freezingAnimation.tooltip": "Adiciona uma animação ao congelar", 61 | "text.nea.enable.huggingAnimation": "Animação de Abraço Simples", 62 | "text.nea.enable.huggingAnimation.tooltip": "Adiciona animação de abraço (agache e olhe para outro jogador para abraçar)", 63 | "text.nea.enable.narutoRunning": "❝Corrida Naruto❞", 64 | "text.nea.enable.narutoRunning.tooltip": "Adiciona uma animação de corrida no estilo Naruto (easter egg)", 65 | "text.nea.enable.enableInWorldBookRendering": "[WIP] Livros no Mundo", 66 | "text.nea.enable.enableInWorldBookRendering.tooltip": "Renderiza livros abertos no mundo com seu texto (ainda em desenvolvimento)", 67 | "text.nea.disableLegSmoothing": "Desativar Suavização das Pernas", 68 | "text.nea.disableLegSmoothing.tooltip": "Desativa o efeito de suavização nas pernas", 69 | "text.nea.enable.bowAnimation": "Animação do Arco", 70 | "text.nea.enable.bowAnimation.tooltip": "Define o tipo de animação usada ao usar arco", 71 | "text.nea.enable.bowAnimation.VANILLA": "Padrão (Vanilla)", 72 | "text.nea.enable.bowAnimation.CUSTOM_V1": "Personalizada V1", 73 | "text.nea.enable.burningAnimation": "Animação de Queimando", 74 | "text.nea.enable.burningAnimation.tooltip": "Adiciona uma animação ao jogador quando está pegando fogo", 75 | "text.nea.holdUpTarget": "Direção ao Levantar Item", 76 | "text.nea.holdUpTarget.tooltip": "Muda para onde o item aponta quando levantado", 77 | "text.nea.holdUpTarget.NONE": "Nenhum", 78 | "text.nea.holdUpTarget.CAMERA": "Câmera", 79 | "text.nea.holdUpCameraOffset": "Deslocamento da Câmera ao Levantar", 80 | "text.nea.holdUpCameraOffset.tooltip": "Ajusta o quanto o braço é deslocado lateralmente em modo Câmera", 81 | "text.nea.enable.holdUpOnlySelf": "Apenas para o Jogador Local", 82 | "text.nea.enable.holdUpOnlySelf.tooltip": "Aplica o efeito de levantar itens apenas no próprio jogador", 83 | "text.nea.enable.limitRotationLockToFP": "Travar Rotação Apenas em Primeira Pessoa", 84 | "text.nea.enable.limitRotationLockToFP.tooltip": "Aplica o efeito de rotação travada somente na visão em primeira pessoa" 85 | } 86 | -------------------------------------------------------------------------------- /src/main/resources/assets/notenoughanimations/lang/ru_ru.json: -------------------------------------------------------------------------------- 1 | { 2 | "text.nea.title": "Настройки Not Enough Animations", 3 | "text.nea.tab.settings": "Настройки", 4 | "text.nea.tab.holdup": "Осмотр предметов", 5 | "text.nea.line.legacy": "Устаревшее/Незавершённое", 6 | "text.nea.line.fun": "Развлечения", 7 | "text.nea.line.fixes": "Исправления", 8 | "text.nea.line.holdup": "Осмотр предметов", 9 | "text.nea.line.rotation": "Поворот", 10 | "text.nea.line.smoothing": "Сглаживание", 11 | "text.nea.line.animations": "Анимации", 12 | "text.nea.enable.animationsmoothing": "Сглаживание анимаций", 13 | "text.nea.enable.animationsmoothing.tooltip": "Сглаживает анимации рук/ног для более естественного вида", 14 | "text.nea.smoothingSpeed": "Сила сглаживания", 15 | "text.nea.smoothingSpeed.tooltip": "Интенсивность сглаживания анимаций рук/ног", 16 | "text.nea.enable.inworldmaprendering": "Отображение карты в мире", 17 | "text.nea.enable.inworldmaprendering.tooltip": "Отображает карту в мире, а не только от первого лица", 18 | "text.nea.enable.offhandhiding": "Исправления анимации лука", 19 | "text.nea.enable.offhandhiding.tooltip": "Скрывает предмет в второй руке при натягивании лука", 20 | "text.nea.enable.rotationlocking": "Фиксация поворота", 21 | "text.nea.enable.rotationlocking.tooltip": "Фиксирует поворот тела относительно направления взгляда", 22 | "text.nea.enable.ladderanimation": "Анимация лестницы", 23 | "text.nea.enable.ladderanimation.tooltip": "Добавляет анимацию лазания по лестницам (только лестницы, не лианы/строительные леса)", 24 | "text.nea.enable.eatdrinkanimation": "Анимация еды/питья", 25 | "text.nea.enable.eatdrinkanimation.tooltip": "Добавляет анимацию приёма пищи и питья", 26 | "text.nea.enable.rowboatanimation": "Анимация гребли", 27 | "text.nea.enable.rowboatanimation.tooltip": "Добавляет анимацию гребли в лодке", 28 | "text.nea.enable.horseanimation": "Анимация верховой езды", 29 | "text.nea.enable.horseanimation.tooltip": "Добавляет анимацию езды на лошади", 30 | "text.nea.enable.enableHorseLegAnimation": "Анимация ног при верховой езде", 31 | "text.nea.enable.enableHorseLegAnimation.tooltip": "Изменяет позу ног игрока при езде на лошади", 32 | "text.nea.enable.dontholditemsinbed": "Без предметов в кровати", 33 | "text.nea.enable.dontholditemsinbed.tooltip": "Убирает предметы из рук при нахождении в кровати", 34 | "text.nea.enable.freezearmsinbed": "Без движения в кровати", 35 | "text.nea.enable.freezearmsinbed.tooltip": "Фиксирует положение рук при нахождении в кровати", 36 | "text.nea.rotationlock": "Тип фиксации поворота", 37 | "text.nea.rotationlock.tooltip": "Способ фиксации поворота тела", 38 | "text.nea.rotationlock.NONE": "Отключено", 39 | "text.nea.rotationlock.FIXED": "Фиксированный", 40 | "text.nea.rotationlock.SMOOTH": "Плавный", 41 | "text.nea.enable.showlastusedsword": "[Устарело] Ножны", 42 | "text.nea.enable.showlastusedsword.tooltip": "[Устарело! Используйте другие моды!] Визуально отображает последний использованный меч. Это чисто декоративный эффект без учёта инвентаря.", 43 | "text.nea.enable.crawling": "Анимация ползания", 44 | "text.nea.enable.crawling.tooltip": "Заменяет стандартную анимацию 'ползания' (плавания) в узких пространствах", 45 | "text.nea.enable.rotatetoladder": "Поворот к лестнице", 46 | "text.nea.enable.rotatetoladder.tooltip": "Поворачивает тело лицом к лестнице при лазании", 47 | "text.nea.holdUpItemsMode": "Режим осмотра предметов", 48 | "text.nea.holdUpItemsMode.tooltip": "Анимация рассматривания предметов в руках", 49 | "text.nea.holdUpItemsMode.ALL": "Все предметы", 50 | "text.nea.holdUpItemsMode.NONE": "Отключено", 51 | "text.nea.holdUpItemsMode.CONFIG": "Только настроенные", 52 | "text.nea.holdUpItemOffset": "Смещение при осмотре", 53 | "text.nea.holdUpItemOffset.tooltip": "Регулировка высоты предмета при осмотре", 54 | "text.nea.ladderAnimationAmplifier": "Амплитуда рук на лестнице", 55 | "text.nea.ladderAnimationAmplifier.tooltip": "Интенсивность движения рук при лазании", 56 | "text.nea.ladderAnimationArmHeight": "Высота рук на лестнице", 57 | "text.nea.ladderAnimationArmHeight.tooltip": "Положение рук при лазании по лестнице", 58 | "text.nea.ladderAnimationArmSpeed": "Скорость рук на лестнице", 59 | "text.nea.ladderAnimationArmSpeed.tooltip": "Скорость движения рук при лазании", 60 | "text.nea.enable.itemSwapAnimation": "Анимация смены рук", 61 | "text.nea.enable.itemSwapAnimation.tooltip": "Анимация перекладывания предметов между руками", 62 | "text.nea.enable.tweakElytraAnimation": "Правки анимации элитр", 63 | "text.nea.enable.tweakElytraAnimation.tooltip": "Улучшает анимацию полёта в элитрах", 64 | "text.nea.enable.petAnimation": "Поглаживание животных", 65 | "text.nea.enable.petAnimation.tooltip": "Анимация поглаживания волков и кошек (присесть + смотреть на животное)", 66 | "text.nea.enable.fallingAnimation": "[В разработке] Анимация падения", 67 | "text.nea.enable.fallingAnimation.tooltip": "Добавляет анимацию свободного падения", 68 | "text.nea.enable.freezingAnimation": "Анимация замерзания", 69 | "text.nea.enable.freezingAnimation.tooltip": "Анимация дрожи при замерзании", 70 | "text.nea.enable.huggingAnimation": "Простая анимация объятий", 71 | "text.nea.enable.huggingAnimation.tooltip": "Анимация объятий с другими игроками (присесть + смотреть на игрока)", 72 | "text.nea.enable.narutoRunning": "❝Бег Наруто❞", 73 | "text.nea.enable.narutoRunning.tooltip": "Добавляет анимацию бега в стиле Наруто (пасхалка)", 74 | "text.nea.enable.enableInWorldBookRendering": "[В разработке] Книги в мире", 75 | "text.nea.enable.enableInWorldBookRendering.tooltip": "Отображает текст книг при их чтении в мире (экспериментально)", 76 | "text.nea.disableLegSmoothing": "Отключить сглаживание ног", 77 | "text.nea.disableLegSmoothing.tooltip": "Отключает сглаживание анимации ног", 78 | "text.nea.enable.bowAnimation": "Анимация лука", 79 | "text.nea.enable.bowAnimation.tooltip": "Тип анимации при стрельбе из лука", 80 | "text.nea.enable.bowAnimation.VANILLA": "Стандартная", 81 | "text.nea.enable.bowAnimation.CUSTOM_V1": "Пользовательская V1", 82 | "text.nea.enable.burningAnimation": "Анимация горения", 83 | "text.nea.enable.burningAnimation.tooltip": "Анимация движений при горении", 84 | "text.nea.holdUpTarget": "Направление осмотра", 85 | "text.nea.holdUpTarget.tooltip": "Направление взгляда при осмотре предметов", 86 | "text.nea.holdUpTarget.NONE": "Нет", 87 | "text.nea.holdUpTarget.CAMERA": "В камеру", 88 | "text.nea.holdUpCameraOffset": "Смещение рук при осмотре", 89 | "text.nea.holdUpCameraOffset.tooltip": "Смещение рук в стороны при осмотре предметов в режиме 'В камеру'", 90 | "text.nea.enable.holdUpOnlySelf": "Осмотр только у себя", 91 | "text.nea.enable.holdUpOnlySelf.tooltip": "Применять анимацию осмотра только к своему персонажу", 92 | "text.nea.enable.limitRotationLockToFP": "Только от первого лица", 93 | "text.nea.enable.limitRotationLockToFP.tooltip": "Фиксация поворота только в режиме от первого лица" 94 | } 95 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/fullbody/LadderAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.fullbody; 2 | 3 | import java.util.Arrays; 4 | import java.util.HashSet; 5 | import java.util.Set; 6 | 7 | import dev.tr7zw.notenoughanimations.access.PlayerData; 8 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 9 | import dev.tr7zw.notenoughanimations.api.PoseOverwrite; 10 | import dev.tr7zw.notenoughanimations.util.*; 11 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 12 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 13 | import dev.tr7zw.transition.mc.*; 14 | //? if >= 1.21.11 { 15 | 16 | import net.minecraft.client.model.player.*; 17 | //? } else { 18 | /* 19 | import net.minecraft.client.model.*; 20 | *///? } 21 | import net.minecraft.client.player.AbstractClientPlayer; 22 | import net.minecraft.core.Direction; 23 | import net.minecraft.util.Mth; 24 | import net.minecraft.world.entity.HumanoidArm; 25 | import net.minecraft.world.entity.Pose; 26 | import net.minecraft.world.level.block.Block; 27 | import net.minecraft.world.level.block.HorizontalDirectionalBlock; 28 | import net.minecraft.world.level.block.LadderBlock; 29 | import net.minecraft.world.level.block.TrapDoorBlock; 30 | import net.minecraft.world.level.block.state.BlockState; 31 | 32 | public class LadderAnimation extends BasicAnimation implements PoseOverwrite { 33 | 34 | @Override 35 | public boolean isEnabled() { 36 | return NEABaseMod.config.enableLadderAnimation; 37 | } 38 | 39 | @Override 40 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 41 | if (entity.onClimbable() && !NMSWrapper.onGround(entity) && entity.getLastClimbablePos().isPresent()) { 42 | for (Class blocktype : ladderLikeBlocks) { 43 | if (blocktype.isAssignableFrom( 44 | //? if >= 1.18.0 { 45 | 46 | GeneralUtil.getWorld().getBlockState(entity.getLastClimbablePos().get()).getBlock().getClass())) 47 | //? } else { 48 | 49 | // entity.level.getBlockState(entity.getLastClimbablePos().get()).getBlock().getClass())) 50 | //? } 51 | 52 | return true; 53 | } 54 | return false; 55 | } 56 | return false; 57 | } 58 | 59 | private final Set> ladderLikeBlocks = new HashSet<>( 60 | Arrays.asList(LadderBlock.class, TrapDoorBlock.class)); 61 | 62 | private final BodyPart[] parts = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM, BodyPart.BODY, 63 | BodyPart.LEFT_LEG, BodyPart.RIGHT_LEG, BodyPart.HEAD }; 64 | private final BodyPart[] partsSneakingRight = new BodyPart[] { BodyPart.RIGHT_ARM, BodyPart.BODY, BodyPart.LEFT_LEG, 65 | BodyPart.RIGHT_LEG, BodyPart.HEAD }; 66 | private final BodyPart[] partsSneakingLeft = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.BODY, BodyPart.LEFT_LEG, 67 | BodyPart.RIGHT_LEG, BodyPart.HEAD }; 68 | 69 | @Override 70 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 71 | if (entity.isCrouching() && entity.getDeltaMovement().y == -0.0784000015258789) { // magic value while being not 72 | // moving on a ladder cause mc 73 | if (entity.getMainArm() == HumanoidArm.RIGHT) { 74 | return partsSneakingLeft; 75 | } else { 76 | return partsSneakingRight; 77 | } 78 | } 79 | return parts; 80 | } 81 | 82 | @Override 83 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 84 | return 1400; 85 | } 86 | 87 | @Override 88 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 89 | float tickCounter) { 90 | if (part == BodyPart.HEAD) { 91 | // this gets handled in the body block 92 | return; 93 | } 94 | if (part == BodyPart.BODY) { 95 | if (NEABaseMod.config.enableRotateToLadder) { 96 | //? if >= 1.20.5 { 97 | 98 | BlockState blockState = entity.getInBlockState(); 99 | //? } else { 100 | /* 101 | BlockState blockState = entity.getFeetBlockState(); 102 | *///? } 103 | if (blockState.hasProperty(HorizontalDirectionalBlock.FACING)) { 104 | Direction dir = blockState.getValue(HorizontalDirectionalBlock.FACING); 105 | data.setDisableBodyRotation(true); 106 | switch (dir) { 107 | case NORTH: 108 | entity.setYBodyRot(0); 109 | entity.yBodyRotO = 0; 110 | break; 111 | case EAST: 112 | entity.setYBodyRot(90); 113 | entity.yBodyRotO = 90; 114 | break; 115 | case SOUTH: 116 | entity.setYBodyRot(180); 117 | entity.yBodyRotO = 180; 118 | break; 119 | case WEST: 120 | entity.setYBodyRot(270); 121 | entity.yBodyRotO = 270; 122 | break; 123 | default: 124 | } 125 | AnimationUtil.minMaxHeadRotation(entity, model); 126 | } 127 | return; 128 | } 129 | } 130 | 131 | if (part == BodyPart.LEFT_LEG || part == BodyPart.RIGHT_LEG) { 132 | float rotation = -Mth.cos((float) (entity.getY() * NEABaseMod.config.ladderAnimationArmSpeed)); 133 | rotation *= NEABaseMod.config.ladderAnimationAmplifier; 134 | if (part == BodyPart.LEFT_LEG) { 135 | rotation *= -1; 136 | } 137 | AnimationUtil.applyTransforms(model, part, -1 - rotation, -0.2f, 0.3f); 138 | return; 139 | } 140 | float rotation = -Mth.cos((float) (entity.getY() * NEABaseMod.config.ladderAnimationArmSpeed)); 141 | rotation *= NEABaseMod.config.ladderAnimationAmplifier; 142 | // arms 143 | if (part == BodyPart.LEFT_ARM) 144 | rotation *= -1; 145 | AnimationUtil.applyTransforms(model, part, -NEABaseMod.config.ladderAnimationArmHeight - rotation, -0.2f, 0.3f); 146 | } 147 | 148 | @Override 149 | public void updateState(AbstractClientPlayer entity, PlayerData data, PlayerModel playerModel) { 150 | if (entity.isCrouching() && isValid(entity, data)) { 151 | data.setPoseOverwrite(entity.getPose()); 152 | entity.setPose(Pose.STANDING); 153 | //? if >= 1.21.2 { 154 | 155 | RenderStateHolder.RenderStateData stateData = data.getData(RenderStateHolder.INSTANCE, 156 | RenderStateHolder.RenderStateData::new); 157 | stateData.renderState.isCrouching = false; 158 | //? } else { 159 | /* 160 | playerModel.crouching = false; 161 | *///? } 162 | } 163 | } 164 | 165 | } 166 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/animations/fullbody/CrawlingAnimation.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.animations.fullbody; 2 | 3 | import dev.tr7zw.notenoughanimations.access.PlayerData; 4 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 5 | import dev.tr7zw.notenoughanimations.util.RenderStateHolder; 6 | import dev.tr7zw.notenoughanimations.versionless.NEABaseMod; 7 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 8 | //? if >= 1.21.11 { 9 | 10 | import net.minecraft.client.model.player.*; 11 | //? } else { 12 | /* 13 | import net.minecraft.client.model.*; 14 | *///? } 15 | import net.minecraft.client.player.AbstractClientPlayer; 16 | import net.minecraft.util.Mth; 17 | import net.minecraft.world.InteractionHand; 18 | import net.minecraft.world.entity.HumanoidArm; 19 | import net.minecraft.world.entity.Pose; 20 | import net.minecraft.world.entity.player.Player; 21 | 22 | public class CrawlingAnimation extends BasicAnimation { 23 | 24 | private BodyPart[] bodyParts = new BodyPart[] { BodyPart.LEFT_ARM, BodyPart.RIGHT_ARM, BodyPart.LEFT_LEG, 25 | BodyPart.RIGHT_LEG }; 26 | 27 | @Override 28 | public boolean isEnabled() { 29 | return NEABaseMod.config.enableCrawlingAnimation; 30 | } 31 | 32 | @Override 33 | public boolean isValid(AbstractClientPlayer entity, PlayerData data) { 34 | return entity.getPose() == Pose.SWIMMING && !entity.isInWater(); 35 | } 36 | 37 | @Override 38 | public BodyPart[] getBodyParts(AbstractClientPlayer entity, PlayerData data) { 39 | return bodyParts; 40 | } 41 | 42 | @Override 43 | public int getPriority(AbstractClientPlayer entity, PlayerData data) { 44 | return 350; 45 | } 46 | 47 | private final float speedMul = 2.5F; 48 | private float swimAmount; 49 | private float attackTime; 50 | private float animationStep; 51 | private float animationStep2; 52 | private HumanoidArm humanoidArm; 53 | private float m; 54 | private float n; 55 | private float armMoveHight = 0.3707964F; 56 | private final float legPitch = 0.15F; 57 | private final float r = 0.33333334F; 58 | 59 | @Override 60 | protected void precalculate(AbstractClientPlayer entity, PlayerData data, PlayerModel model, float delta, 61 | float swing) { 62 | //? if >= 1.21.2 { 63 | 64 | RenderStateHolder.RenderStateData stateData = data.getData(RenderStateHolder.INSTANCE, 65 | RenderStateHolder.RenderStateData::new); 66 | swimAmount = stateData.renderState.swimAmount; 67 | attackTime = stateData.renderState.attackTime; 68 | //? } else { 69 | /* 70 | swimAmount = model.swimAmount; 71 | attackTime = model.attackTime; 72 | *///? } 73 | if (swimAmount > 0.0F) { 74 | animationStep = swing * speedMul % 26.0F; 75 | animationStep2 = animationStep + 13F; 76 | animationStep2 %= 26F; 77 | humanoidArm = getAttackArm(entity); 78 | m = (humanoidArm == HumanoidArm.RIGHT && attackTime > 0.0F) ? 0.0F : swimAmount; 79 | n = (humanoidArm == HumanoidArm.LEFT && attackTime > 0.0F) ? 0.0F : swimAmount; 80 | } 81 | } 82 | 83 | @Override 84 | public void apply(AbstractClientPlayer entity, PlayerData data, PlayerModel model, BodyPart part, float delta, 85 | float tickCounter) { 86 | if (swimAmount > 0.0F) { 87 | if (part == BodyPart.RIGHT_ARM) 88 | if (animationStep < 14.0F) { 89 | model.rightArm.xRot = Mth.lerp(m, model.rightArm.xRot, 0.0F); 90 | model.rightArm.yRot = Mth.lerp(m, model.rightArm.yRot, 3.1415927F); 91 | model.rightArm.zRot = Mth.lerp(m, model.rightArm.zRot, 92 | 3.1415927F - 1.8707964F * quadraticArmUpdate(animationStep) / quadraticArmUpdate(14.0F)); 93 | } else if (animationStep >= 14.0F && animationStep < 24.0F) { 94 | float o = (animationStep - 14.0F) / 10.0F; 95 | model.rightArm.xRot = Mth.lerp(m, model.rightArm.xRot, -armMoveHight * o); 96 | model.rightArm.yRot = Mth.lerp(m, model.rightArm.yRot, 3.1415927F); 97 | model.rightArm.zRot = Mth.lerp(m, model.rightArm.zRot, 1.2707963F + 1.8707964F * o); 98 | } else if (animationStep >= 24.0F && animationStep < 26.0F) { 99 | float p = (animationStep - 24.0F) / 2.0F; 100 | model.rightArm.xRot = Mth.lerp(m, model.rightArm.xRot, -armMoveHight + armMoveHight * p); 101 | model.rightArm.yRot = Mth.lerp(m, model.rightArm.yRot, 3.1415927F); 102 | model.rightArm.zRot = Mth.lerp(m, model.rightArm.zRot, 3.1415927F); 103 | } 104 | if (part == BodyPart.LEFT_ARM) 105 | if (animationStep2 < 14.0F) { 106 | model.leftArm.xRot = rotlerpRad(n, model.leftArm.xRot, 0.0F); 107 | model.leftArm.yRot = rotlerpRad(n, model.leftArm.yRot, 3.1415927F); 108 | model.leftArm.zRot = rotlerpRad(n, model.leftArm.zRot, 109 | 3.1415927F + 1.8707964F * quadraticArmUpdate(animationStep2) / quadraticArmUpdate(14.0F)); 110 | } else if (animationStep2 >= 14.0F && animationStep2 < 24.0F) { 111 | float o = (animationStep2 - 14.0F) / 10.0F; 112 | model.leftArm.xRot = rotlerpRad(n, model.leftArm.xRot, -armMoveHight * o); 113 | model.leftArm.yRot = rotlerpRad(n, model.leftArm.yRot, 3.1415927F); 114 | model.leftArm.zRot = rotlerpRad(n, model.leftArm.zRot, 5.012389F - 1.8707964F * o); 115 | } else if (animationStep2 >= 24.0F && animationStep2 < 26.0F) { 116 | float p = (animationStep2 - 24.0F) / 2.0F; 117 | model.leftArm.xRot = rotlerpRad(n, model.leftArm.xRot, -armMoveHight + armMoveHight * p); 118 | model.leftArm.yRot = rotlerpRad(n, model.leftArm.yRot, 3.1415927F); 119 | model.leftArm.zRot = rotlerpRad(n, model.leftArm.zRot, 3.1415927F); 120 | } 121 | } 122 | tickCounter *= speedMul; 123 | if (part == BodyPart.LEFT_LEG) { 124 | model.leftLeg.xRot = Mth.lerp(swimAmount, model.leftLeg.xRot, 125 | legPitch * Mth.cos(tickCounter * r + 3.1415927F)); 126 | model.leftLeg.zRot = -0.1507964F; 127 | } 128 | if (part == BodyPart.RIGHT_LEG) { 129 | model.rightLeg.xRot = Mth.lerp(swimAmount, model.rightLeg.xRot, legPitch * Mth.cos(tickCounter * r)); 130 | model.rightLeg.zRot = 0.1507964F; 131 | } 132 | } 133 | 134 | private float rotlerpRad(float f, float g, float h) { 135 | float i = (h - g) % 6.2831855F; 136 | if (i < -3.1415927F) 137 | i += 6.2831855F; 138 | if (i >= 3.1415927F) 139 | i -= 6.2831855F; 140 | return g + f * i; 141 | } 142 | 143 | private float quadraticArmUpdate(float f) { 144 | return -65.0F * f + f * f; 145 | } 146 | 147 | private HumanoidArm getAttackArm(Player livingEntity) { 148 | HumanoidArm humanoidArm = livingEntity.getMainArm(); 149 | return (livingEntity.swingingArm == InteractionHand.MAIN_HAND) ? humanoidArm : humanoidArm.getOpposite(); 150 | } 151 | 152 | } 153 | -------------------------------------------------------------------------------- /src/main/java/dev/tr7zw/notenoughanimations/logic/AnimationProvider.java: -------------------------------------------------------------------------------- 1 | package dev.tr7zw.notenoughanimations.logic; 2 | 3 | import java.util.ArrayList; 4 | import java.util.HashSet; 5 | import java.util.List; 6 | import java.util.Set; 7 | 8 | import dev.tr7zw.notenoughanimations.access.PlayerData; 9 | import dev.tr7zw.notenoughanimations.animations.fullbody.ActionRotationLockAnimation; 10 | import dev.tr7zw.notenoughanimations.animations.fullbody.BurningAnimation; 11 | import dev.tr7zw.notenoughanimations.animations.fullbody.CrawlingAnimation; 12 | import dev.tr7zw.notenoughanimations.animations.fullbody.FallingAnimation; 13 | import dev.tr7zw.notenoughanimations.animations.fullbody.LadderAnimation; 14 | import dev.tr7zw.notenoughanimations.animations.fullbody.PassengerAnimation; 15 | import dev.tr7zw.notenoughanimations.animations.hands.BoatAnimation; 16 | import dev.tr7zw.notenoughanimations.animations.hands.CustomBowAnimation; 17 | import dev.tr7zw.notenoughanimations.animations.hands.ClampCrossbowAnimations; 18 | import dev.tr7zw.notenoughanimations.animations.hands.EatDrinkAnimation; 19 | import dev.tr7zw.notenoughanimations.animations.hands.HugAnimation; 20 | import dev.tr7zw.notenoughanimations.animations.hands.ItemSwapAnimation; 21 | import dev.tr7zw.notenoughanimations.animations.hands.LookAtItemAnimation; 22 | import dev.tr7zw.notenoughanimations.animations.hands.MapHoldingAnimation; 23 | import dev.tr7zw.notenoughanimations.animations.hands.NarutoRunningAnimation; 24 | import dev.tr7zw.notenoughanimations.animations.hands.PetAnimation; 25 | import dev.tr7zw.notenoughanimations.animations.vanilla.DeathAnimation; 26 | import dev.tr7zw.notenoughanimations.animations.vanilla.ElytraAnimation; 27 | import dev.tr7zw.notenoughanimations.animations.vanilla.RiptideAnimation; 28 | import dev.tr7zw.notenoughanimations.animations.vanilla.SleepAnimation; 29 | import dev.tr7zw.notenoughanimations.animations.vanilla.SwimAnimation; 30 | import dev.tr7zw.notenoughanimations.animations.vanilla.VanillaShieldAnimation; 31 | import dev.tr7zw.notenoughanimations.animations.vanilla.VanillaSingleHandedAnimation; 32 | import dev.tr7zw.notenoughanimations.animations.vanilla.VanillaTwoHandedAnimation; 33 | import dev.tr7zw.notenoughanimations.api.BasicAnimation; 34 | import dev.tr7zw.notenoughanimations.api.PoseOverwrite; 35 | import dev.tr7zw.notenoughanimations.versionless.animations.BodyPart; 36 | import net.minecraft.client.model.*; 37 | //? if >= 1.21.11 { 38 | 39 | import net.minecraft.client.model.player.*; 40 | //? } else { 41 | /* 42 | import net.minecraft.client.model.*; 43 | *///? } 44 | import net.minecraft.client.player.AbstractClientPlayer; 45 | //? if >= 1.17.0 { 46 | 47 | import dev.tr7zw.notenoughanimations.animations.fullbody.FreezingAnimation; 48 | //? } 49 | import dev.tr7zw.notenoughanimations.animations.fullbody.HorseAnimation; 50 | 51 | public class AnimationProvider { 52 | 53 | private Set basicAnimations = new HashSet<>(); 54 | private Set enabledBasicAnimations = new HashSet<>(); 55 | private Set enabledPoseOverwrites = new HashSet<>(); 56 | private boolean dumpPrios = false; 57 | 58 | public AnimationProvider() { 59 | loadAnimations(); 60 | refreshEnabledAnimations(); 61 | } 62 | 63 | public void applyAnimations(AbstractClientPlayer entity, PlayerModel model, float delta, float swing) { 64 | PlayerData playerData = (PlayerData) entity; 65 | int[] priorities = new int[BodyPart.values().length]; 66 | BasicAnimation[] animation = new BasicAnimation[priorities.length]; 67 | for (BasicAnimation basicAnimation : enabledBasicAnimations) { 68 | if (basicAnimation.isValid(entity, playerData)) { 69 | int prio = basicAnimation.getPriority(entity, playerData); 70 | if (prio > 0) { 71 | for (BodyPart part : basicAnimation.getBodyParts(entity, playerData)) { 72 | if (prio > priorities[part.ordinal()]) { 73 | priorities[part.ordinal()] = prio; 74 | animation[part.ordinal()] = basicAnimation; 75 | } 76 | } 77 | } 78 | } 79 | } 80 | 81 | for (int i = 0; i < priorities.length; i++) { 82 | if (animation[i] != null) { 83 | animation[i].prepare(entity, playerData, model, delta, swing); 84 | animation[i].apply(entity, playerData, model, BodyPart.values()[i], delta, swing); 85 | } 86 | } 87 | for (int i = 0; i < priorities.length; i++) { 88 | if (animation[i] != null) { 89 | animation[i].cleanup(); 90 | } 91 | } 92 | } 93 | 94 | public void preUpdate(AbstractClientPlayer livingEntity, PlayerModel playerModel) { 95 | for (PoseOverwrite po : enabledPoseOverwrites) { 96 | po.updateState(livingEntity, (PlayerData) livingEntity, playerModel); 97 | } 98 | } 99 | 100 | private void loadAnimations() { 101 | addAnimation(new CrawlingAnimation()); 102 | addAnimation(new VanillaSingleHandedAnimation()); 103 | addAnimation(new VanillaTwoHandedAnimation()); 104 | addAnimation(new ItemSwapAnimation()); 105 | addAnimation(new LookAtItemAnimation()); 106 | addAnimation(new SleepAnimation()); 107 | addAnimation(new MapHoldingAnimation()); 108 | addAnimation(new BoatAnimation()); 109 | addAnimation(new HorseAnimation()); 110 | addAnimation(new LadderAnimation()); 111 | addAnimation(new EatDrinkAnimation()); 112 | addAnimation(new VanillaShieldAnimation()); 113 | addAnimation(new PassengerAnimation()); 114 | addAnimation(new RiptideAnimation()); 115 | addAnimation(new DeathAnimation()); 116 | addAnimation(new ElytraAnimation()); 117 | addAnimation(new SwimAnimation()); 118 | addAnimation(new PetAnimation()); 119 | addAnimation(new FallingAnimation()); 120 | addAnimation(new HugAnimation()); 121 | addAnimation(new NarutoRunningAnimation()); 122 | addAnimation(new CustomBowAnimation()); 123 | addAnimation(new ActionRotationLockAnimation()); 124 | addAnimation(new BurningAnimation()); 125 | addAnimation(new ClampCrossbowAnimations()); 126 | //? if >= 1.17.0 { 127 | 128 | addAnimation(new FreezingAnimation()); 129 | //? } 130 | } 131 | 132 | public void addAnimation(BasicAnimation animation) { 133 | basicAnimations.add(animation); 134 | } 135 | 136 | public void refreshEnabledAnimations() { 137 | enabledBasicAnimations.clear(); 138 | enabledPoseOverwrites.clear(); 139 | for (BasicAnimation basicAnimation : basicAnimations) { 140 | if (basicAnimation.isEnabled()) { 141 | enabledBasicAnimations.add(basicAnimation); 142 | if (basicAnimation instanceof PoseOverwrite) { 143 | enabledPoseOverwrites.add((PoseOverwrite) basicAnimation); 144 | } 145 | } 146 | } 147 | if (dumpPrios) { 148 | List list = new ArrayList<>(basicAnimations); 149 | list.sort((a, b) -> Integer.compare(a.getPriority(null, null), b.getPriority(null, null))); 150 | for (BasicAnimation an : list) { 151 | System.out.println(an.getPriority(null, null) + " " + an.getClass().getSimpleName()); 152 | } 153 | } 154 | } 155 | 156 | } 157 | --------------------------------------------------------------------------------