Unity中Animator组件Runtime控制动画的正向和反向播放

2023-12-22 04:36

本文主要是介绍Unity中Animator组件Runtime控制动画的正向和反向播放,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

        最初的想法是希望能够完全不改变美工的工作流程,通过代码解决所有问题。但是以笔者目前的认知水平还不行,还得麻烦一下美工,郁闷。

        本来以为Animator.speed这个值设置为负数就可以倒播动画了,但是实际上设置为小于0的数和0没有区别,就是等同于暂停而已。

        那么剩下就是改AnimatorState的speed了。本来以为只要获取到当前的AnimatorState就好办了,但是发现这是不可能的!你只能通过GetCurrentAnimatorStateInfo获取到当前的AnimatorStateInfo,而AnimatorStateInfo的speed值是只读的,国内国外搜了好几圈,没找到能在运行时获取AnimatorState的办法。

        那就只能麻烦美工了,如图:

        默认的AnimatorState是moveUpDown,复制这个AnimatorState,改名叫moveUpDown-1,Speed改成-1,这样虽然两个AnimatorState引用的是一个AnimatorClip,但是一个可以正向播放,一个可以反向播放。

        不过还有问题,如果使用Animator.Play(string stateName)这个重载去播放的话,每次都是重头播放,这样假如用户正向播放动画的时候,如果在动画没有播放到结尾就选择倒播,我们会发现动画不是在当前状态开始倒播,而是从结尾往回倒播,这样就会产生跳跃感。解决的办法就是,先获取当前动画已经正向播放了的归一化时间,就是Animator.normalizedTime,用1-Animator.normalizedTime这个时间作为开始反向播放的其实时间就好了,代码上用的是Animator.Play(string stateName,int layer,float normalizedTime)这个重载。反向播放改正向播放道理一样。

        代码示例如下:

using UnityEngine;public class AnimOnOff : MonoBehaviour
{[SerializeField][Header("可暂停动画")]Animator[] anims;public void Play(float playSpeed){bool enabled = !Mathf.Approximately(playSpeed, 0);if (anims != null){foreach (Animator anim in anims){if (!anim) continue;//anim.enabled = enabled;if (anim.enabled){AnimatorClipInfo clipInfo = anim.GetCurrentAnimatorClipInfo(0)[0];AnimationClip clip = clipInfo.clip;if (!clip){Debug.Log("ULog:animator clip is null.");continue;}string clipName = clip.name;if (clipName.Contains("-1")){if (playSpeed > 0){clipName = clipName.Replace("-1", "");}}else{if (playSpeed < 0){clipName += "-1";}}AnimatorStateInfo stateInfo = anim.GetCurrentAnimatorStateInfo(0);float startPlayTime = stateInfo.normalizedTime;if(!clip.isLooping) startPlayTime = Mathf.Clamp01(startPlayTime);if (!stateInfo.IsName(clipName))startPlayTime = 1 - startPlayTime;anim.speed = Mathf.Abs(playSpeed);anim.Play(clipName, 0, startPlayTime);}}}}
}

        playSpeed形参获取的值如果是0,那么动画就停止了,如果是正数就正播,负数就倒播,绝对值的大小会影响播放速度。

        注意这行代码:

float startPlayTime = stateInfo.normalizedTime;
if(!clip.isLooping) startPlayTime = Mathf.Clamp01(startPlayTime);

        这个时间的获取是必须要手动处理一下,我一致以为normalizedTime始终会处于0到1之间,实际上是可以超过1的!!!!!

这篇关于Unity中Animator组件Runtime控制动画的正向和反向播放的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/522628

相关文章

Spring Security 基于表达式的权限控制

前言 spring security 3.0已经可以使用spring el表达式来控制授权,允许在表达式中使用复杂的布尔逻辑来控制访问的权限。 常见的表达式 Spring Security可用表达式对象的基类是SecurityExpressionRoot。 表达式描述hasRole([role])用户拥有制定的角色时返回true (Spring security默认会带有ROLE_前缀),去

JS常用组件收集

收集了一些平时遇到的前端比较优秀的组件,方便以后开发的时候查找!!! 函数工具: Lodash 页面固定: stickUp、jQuery.Pin 轮播: unslider、swiper 开关: switch 复选框: icheck 气泡: grumble 隐藏元素: Headroom

流媒体平台/视频监控/安防视频汇聚EasyCVR播放暂停后视频画面黑屏是什么原因?

视频智能分析/视频监控/安防监控综合管理系统EasyCVR视频汇聚融合平台,是TSINGSEE青犀视频垂直深耕音视频流媒体技术、AI智能技术领域的杰出成果。该平台以其强大的视频处理、汇聚与融合能力,在构建全栈视频监控系统中展现出了独特的优势。视频监控管理系统EasyCVR平台内置了强大的视频解码、转码、压缩等技术,能够处理多种视频流格式,并以多种格式(RTMP、RTSP、HTTP-FLV、WebS

【前端学习】AntV G6-08 深入图形与图形分组、自定义节点、节点动画(下)

【课程链接】 AntV G6:深入图形与图形分组、自定义节点、节点动画(下)_哔哩哔哩_bilibili 本章十吾老师讲解了一个复杂的自定义节点中,应该怎样去计算和绘制图形,如何给一个图形制作不间断的动画,以及在鼠标事件之后产生动画。(有点难,需要好好理解) <!DOCTYPE html><html><head><meta charset="UTF-8"><title>06

如何在页面调用utility bar并传递参数至lwc组件

1.在app的utility item中添加lwc组件: 2.调用utility bar api的方式有两种: 方法一,通过lwc调用: import {LightningElement,api ,wire } from 'lwc';import { publish, MessageContext } from 'lightning/messageService';import Ca

Android平台播放RTSP流的几种方案探究(VLC VS ExoPlayer VS SmartPlayer)

技术背景 好多开发者需要遴选Android平台RTSP直播播放器的时候,不知道如何选的好,本文针对常用的方案,做个大概的说明: 1. 使用VLC for Android VLC Media Player(VLC多媒体播放器),最初命名为VideoLAN客户端,是VideoLAN品牌产品,是VideoLAN计划的多媒体播放器。它支持众多音频与视频解码器及文件格式,并支持DVD影音光盘,VCD影

Flutter 进阶:绘制加载动画

绘制加载动画:由小圆组成的大圆 1. 定义 LoadingScreen 类2. 实现 _LoadingScreenState 类3. 定义 LoadingPainter 类4. 总结 实现加载动画 我们需要定义两个类:LoadingScreen 和 LoadingPainter。LoadingScreen 负责控制动画的状态,而 LoadingPainter 则负责绘制动画。

vue2 组件通信

props + emits props:用于接收父组件传递给子组件的数据。可以定义期望从父组件接收的数据结构和类型。‘子组件不可更改该数据’emits:用于定义组件可以向父组件发出的事件。这允许父组件监听子组件的事件并作出响应。(比如数据更新) props检查属性 属性名类型描述默认值typeFunction指定 prop 应该是什么类型,如 String, Number, Boolean,

用Unity2D制作一个人物,实现移动、跳起、人物静止和动起来时的动画:中(人物移动、跳起、静止动作)

上回我们学到创建一个地形和一个人物,今天我们实现一下人物实现移动和跳起,依次点击,我们准备创建一个C#文件 创建好我们点击进去,就会跳转到我们的Vision Studio,然后输入这些代码 using UnityEngine;public class Move : MonoBehaviour // 定义一个名为Move的类,继承自MonoBehaviour{private Rigidbo

kubelet组件的启动流程源码分析

概述 摘要: 本文将总结kubelet的作用以及原理,在有一定基础认识的前提下,通过阅读kubelet源码,对kubelet组件的启动流程进行分析。 正文 kubelet的作用 这里对kubelet的作用做一个简单总结。 节点管理 节点的注册 节点状态更新 容器管理(pod生命周期管理) 监听apiserver的容器事件 容器的创建、删除(CRI) 容器的网络的创建与删除