当前位置: 首页 > news >正文

spine 动画层 动态权重

 前奏.业务背景

这边想实现一个功能,项目中有 一只猫 猫的头会盯着逗猫棒移动。因为素材还没到所以这里使用了 spine 自带的猫头鹰。他的动画 刚好挺有针对性:(关联上篇)icon-default.png?t=O83Ahttps://blog.csdn.net/nicepainkiller/article/details/144113214

一共有六组动画:

        idel  空闲动画全身都会动 多帧动画

        blink 眨眼睛动画 头不动 多帧动画

        其余几个动画只有有头会动 单帧动画 只有一帧

  •     blink  眼睛在中间的动画 会眨眼睛
  •     down 眼睛朝下看 单帧
  •     left     眼睛朝左看 单帧
  •     right   眼睛朝右看 单帧
  •     up      眼睛朝上看 单帧
  •     idel    空闲动画 全身动

 猫头鹰眼睛可以盯着 屏幕物体移动,实现效果如下 :

最初想的实现方式是:类似 Unity3D 有一个二位动画权重的东西。但是找遍 cocos creator  API 发现没找到,

那么只能纯手撸了:

        思路就是动态控制 动画层的权重来显示不同动画头上,头右,头下,头左)的播放权重。

实操1.逗猫棒位置计算

首先就确定一个屏幕可以拖动的元素,并且计算出一个区域,用来确定 向量 Vec2:

  1. 屏幕触点 转 屏幕坐标
  2. 根据屏幕坐标计算出 用来表示范围的  一个 向量
核心代码:
//获取 触点坐标位置
touchMove(event: EventTouch) {//更新 拖拽元素位置console.log('touchMove');this.potion.x = event.getLocationX();this.potion.y = event.getLocationY();//触点坐标转 屏幕坐标this.worldPostion = this.camera.screenToWorld(this.potion);//屏幕坐标转 局部坐标this.node.position = this.nodeParent.getComponent(UITransform).convertToNodeSpaceAR(this.worldPostion);//console.log("this.node.position:", this.node.position);//计算向量this.localPostion.x = clamp(this.node.position.x, -this.range, this.range) / this.range;this.localPostion.y = clamp(this.node.position.y, -this.range, this.range) / this.range;//console.log("this.localPostion:", this.localPostion);this.spinMerge1.updateAnimation(this.localPostion);
}
功能完整代码:
import { _decorator, Component, Node, EventTouch, Camera, Vec3, UITransform, Vec2, clamp, director, view } from 'cc';
import { SpinMerge1 } from './SpinMerge1';
const { ccclass, property } = _decorator;@ccclass('TouchMove')
export class TouchMove extends Component {@property({ type: Node })private nodeParent: Node;@property({ type: Camera })private camera: Camera;//控制 Spine 动画的脚步@property({ type: SpinMerge1 })private spinMerge1: SpinMerge1;private potion: Vec3 = new Vec3();private worldPostion: Vec3 = new Vec3();private localPostion: Vec2 = new Vec2();private range: number;onLoad() {this.node.on(Node.EventType.TOUCH_START, this.touchStart, this);this.node.on(Node.EventType.TOUCH_MOVE, this.touchMove, this);this.node.on(Node.EventType.TOUCH_END, this.touchEnd, this)this.node.on(Node.EventType.TOUCH_CANCEL, this.touchCancel, this)}start() {this.range = view.getVisibleSize().width / 2;}//展示只有 在拖拽情况下才显示的 元素 equipmentFlytouchStart(event: EventTouch) {//Log.trace('touchStart');console.log('touchStart');}//获取 触点坐标位置touchMove(event: EventTouch) {//更新 拖拽元素位置console.log('touchMove');this.potion.x = event.getLocationX();this.potion.y = event.getLocationY();//触点坐标转 屏幕坐标this.worldPostion = this.camera.screenToWorld(this.potion);//屏幕坐标转 局部坐标this.node.position = this.nodeParent.getComponent(UITransform).convertToNodeSpaceAR(this.worldPostion);//console.log("this.node.position:", this.node.position);//计算向量this.localPostion.x = clamp(this.node.position.x, -this.range, this.range) / this.range;this.localPostion.y = clamp(this.node.position.y, -this.range, this.range) / this.range;//console.log("this.localPostion:", this.localPostion);this.spinMerge1.updateAnimation(this.localPostion);}//结束拖拽 隐藏拖拽元素touchCancel(event: EventTouch) {console.log('touchCancel');this.node.position = new Vec3();this.spinMerge1.resetAnimation();}//结束拖拽touchEnd(event: EventTouch) {console.log('touchEnd');this.node.position = new Vec3();this.spinMerge1.resetAnimation();}}

实操2.猫头鹰盯着逗猫棒

猫头随着物体移动的核心就是

      通过动画层混合 分别控制 头上,头右,头下,头左 动画权重,做到动态控制展示的权重。

 

核心代码:
public updateAnimation(vec2: Vec2) {//console.log('updateAnimation:', vec2);this.ver2Normal.x = Math.abs(vec2.x);this.ver2Normal.y = Math.abs(vec2.y);//右上if (vec2.x > 0 && vec2.y > 0) {this.trackleft.alpha = 0.0;this.trackdown.alpha = 0.0;this.trackright.alpha = this.ver2Normal.x;this.trackUp.alpha = clamp(this.ver2Normal.y, 0, 1 - this.ver2Normal.x);//右下} else if (vec2.x > 0 && vec2.y < 0) {this.trackUp.alpha = 0;this.trackleft.alpha = 0;this.trackright.alpha = this.ver2Normal.x;this.trackdown.alpha = clamp(this.ver2Normal.y, 0, 1 - this.ver2Normal.x);//左下} else if (vec2.x < 0 && vec2.y < 0) {this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackleft.alpha = this.ver2Normal.x;this.trackdown.alpha = clamp(this.ver2Normal.y, 0, 1 - this.ver2Normal.x);//左上} else if (vec2.x < 0 && vec2.y > 0) {this.trackright.alpha = 0;this.trackdown.alpha = 0;this.trackleft.alpha = this.ver2Normal.x;this.trackUp.alpha = clamp(this.ver2Normal.y, 0, 1 - this.ver2Normal.x);} else {this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackdown.alpha = 0;this.trackleft.alpha = 0;}}
完整代码:
import { _decorator, Component, Node, sp, Button, Vec2, clamp } from 'cc';
const { ccclass, property } = _decorator;@ccclass('SpinMerge1')
export class SpinMerge1 extends Component {@property({ type: sp.Skeleton })private spinAnimation: sp.Skeleton;private trackUp: sp.spine.TrackEntry;private trackright: sp.spine.TrackEntry;private trackdown: sp.spine.TrackEntry;private trackleft: sp.spine.TrackEntry;private ver2Normal: Vec2 = new Vec2();start() {this.spinAnimation.setAnimation(0, 'idle', true);//猫头鹰的动画名 left right 反了//所以我们这里的顺序是: 上 -> 右 -> 下 -> 左 this.trackUp = this.spinAnimation.setAnimation(1, 'up', true);this.trackright = this.spinAnimation.setAnimation(4, 'left', true);this.trackdown = this.spinAnimation.setAnimation(3, 'down', true);this.trackleft = this.spinAnimation.setAnimation(2, 'right', true);//眨眼睛动画this.spinAnimation.addAnimation(5, 'blink', true, 2);this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackdown.alpha = 0;this.trackleft.alpha = 0;}onBtnTop() {this.trackUp.alpha = 1;this.trackright.alpha = 0;this.trackdown.alpha = 0;this.trackleft.alpha = 0;}onBtnRight() {this.trackUp.alpha = 0;this.trackright.alpha = 1;this.trackdown.alpha = 0;this.trackleft.alpha = 0;}onBtnBottom() {this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackdown.alpha = 1;this.trackleft.alpha = 0;}onBtnleft() {this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackdown.alpha = 0;this.trackleft.alpha = 1;}onBtnRightTop() {this.trackleft.alpha = 0.0;this.trackdown.alpha = 0.0;this.trackright.alpha = 0.5;this.trackUp.alpha = 0.5;}onBtnRightBottom() {this.trackUp.alpha = 0;this.trackleft.alpha = 0;this.trackright.alpha = 0.5;this.trackdown.alpha = 0.5;}onBtnleftBottom() {this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackleft.alpha = 0.5;this.trackdown.alpha = 0.5;}onBtnleftTop() {this.trackdown.alpha = 0;this.trackright.alpha = 0;this.trackleft.alpha = 0.5;this.trackUp.alpha = 0.5;}public updateAnimation(vec2: Vec2) {//console.log('updateAnimation:', vec2);this.ver2Normal.x = Math.abs(vec2.x);this.ver2Normal.y = Math.abs(vec2.y);//右上if (vec2.x > 0 && vec2.y > 0) {this.trackleft.alpha = 0.0;this.trackdown.alpha = 0.0;this.trackright.alpha = this.ver2Normal.x;this.trackUp.alpha = clamp(this.ver2Normal.y, 0, 1 - this.ver2Normal.x);//右下} else if (vec2.x > 0 && vec2.y < 0) {this.trackUp.alpha = 0;this.trackleft.alpha = 0;this.trackright.alpha = this.ver2Normal.x;this.trackdown.alpha = clamp(this.ver2Normal.y, 0, 1 - this.ver2Normal.x);//左下} else if (vec2.x < 0 && vec2.y < 0) {this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackleft.alpha = this.ver2Normal.x;this.trackdown.alpha = clamp(this.ver2Normal.y, 0, 1 - this.ver2Normal.x);//左上} else if (vec2.x < 0 && vec2.y > 0) {this.trackright.alpha = 0;this.trackdown.alpha = 0;this.trackleft.alpha = this.ver2Normal.x;this.trackUp.alpha = clamp(this.ver2Normal.y, 0, 1 - this.ver2Normal.x);} else {this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackdown.alpha = 0;this.trackleft.alpha = 0;}}public resetAnimation() {this.trackUp.alpha = 0;this.trackright.alpha = 0;this.trackdown.alpha = 0;this.trackleft.alpha = 0;}}

工程下载

相关文章:

spine 动画层 动态权重

前奏.业务背景 这边想实现一个功能&#xff0c;项目中有 一只猫 猫的头会盯着逗猫棒移动。因为素材还没到所以这里使用了 spine 自带的猫头鹰。他的动画 刚好挺有针对性&#xff1a;&#xff08;关联上篇&#xff09;https://blog.csdn.net/nicepainkiller/article/details/144…...

《Python基础》之Python中可以转换成json数据类型的数据

目录 一、JSON简介 JSON有两种基本结构 1、对象&#xff08;Object&#xff09; 2、数组&#xff08;Array&#xff09; 二、将数据装换成json数据类型方法 三、在Python中&#xff0c;以下数据类型可以直接转换为JSON数据类型 1、字典&#xff08;Dictionary&#xff09…...

在oracle下载jdk显示400 Bad Request Request Header Or Cookie Too Large

下载JDK17&#xff0c;官网地址&#xff1a;【https://www.oracle.com/cn/java/technologies/downloads/#jdk17-windows】 问题&#xff1a; 出现 400 Bad Request: Request Header Or Cookie Too Large 错误&#xff0c;通常是由于浏览器存储的 Cookies 或请求头过大所导致的…...

MongoDB注入攻击测试与防御技术深度解析

MongoDB注入攻击测试与防御技术深度解析 随着NoSQL数据库的兴起&#xff0c;MongoDB作为其中的佼佼者&#xff0c;因其灵活的数据模型和强大的查询能力&#xff0c;受到了众多开发者的青睐。然而&#xff0c;与任何技术一样&#xff0c;MongoDB也面临着安全威胁&#xff0c;其…...

【Java基础入门篇】前言

Java基础入门篇 本系列内容主要针对Java基础知识&#xff0c;总共包含四大部分内容&#xff1a; 变量、数据类型和运算符控制语句和递归算法面向对象和JVM底层分析数组和排序 学习需要具备&#xff1a; IDEA编译器 JDK1.8版本 写在前面 在Java入门的最开始&#xff0c;我们需…...

Oracle 建表的存储过程

建表的存储过程 下面是建表的存储过程&#xff0c;用途&#xff1a;通过不同的表&#xff0c;根据不同过滤条件&#xff0c;得到某个字段&#xff0c;例如neid&#xff0c;然后创建一个新表T&#xff0c;表T的表名为拼接XXXX_XXX_neid&#xff0c;表T的字段自行添加 xxx&…...

【Debug】hexo-github令牌认证 Support for password authentication was removed

title: 【Debug】hexo-github令牌认证 date: 2024-07-19 14:40:54 categories: bug解决日记 description: “Support for password authentication was removed on August 13, 2021.” cover: https://pic.imgdb.cn/item/669b38ebd9c307b7e9f3e5e0.jpg 第一章 第一篇博客记录一…...

torch.is_floating_point(input)

torch.is_floating_point(input) input: 输入张量 如果输入的数据类型是 浮点数据类型 ,则返回 True。否则返回False。 浮点数据类型&#xff1a;torch.float64、torch.float32、torch.float16 、 torch.bfloat16 import torch# 创建一个浮点数张量 float_tensor torch.te…...

【分布式】分布式事务

目录 1、事务的发展 2、本地事务 &#xff08;1&#xff09;如何保障原子性和持久性&#xff1f; &#xff08;2&#xff09;如何保障隔离性&#xff1f; 2、全局事务 &#xff08;1&#xff09;XA事务的两段式提交 &#xff08;2&#xff09;XA事务的三段式提交…...

Spring Data 简介

Spring Data 是一个用于简化数据库访问的框架&#xff0c;它是 Spring 生态系统中的重要组成部分。以下是详细介绍&#xff1a; 一、背景和目的 在开发应用程序时&#xff0c;数据访问层的实现往往是比较复杂和繁琐的。开发人员需要编写大量的代码来实现诸如数据库连接、查询…...

【娱乐项目】基于批处理脚本与JavaScript渲染视频列表的Web页面

Demo介绍 一个简单的视频播放器应用&#xff0c;其中包含了视频列表和一个视频播放区域。用户可以通过点击视频列表中的项来选择并播放相应的视频&#xff0c;播放器会自动播放每个视频并在播放完毕后切换到下一个视频。本项目旨在通过自动化脚本和动态网页渲染&#xff0c;帮助…...

[MySQL]流程控制语句

流程控制语句需要借助存储过程才有效。关于存储过程&#xff0c;我会在后续的文章详述&#xff0c;本篇文章只是阐述流程控制语句。因此&#xff0c;大家只需要注意存储过程中相应的流程控制语句即可。 如果文中阐述不全或不对的&#xff0c;多多交流。 参考笔记三&#xff0c…...

Flink在Linux系统上的安装与入门

一、Flink的引入 这几年大数据的飞速发展&#xff0c;出现了很多热门的开源社区&#xff0c;其中著名的有Hadoop、Storm&#xff0c;以及后来的Spark&#xff0c;他们都有着各自专注的应用场景。Spark 掀开了内存计算的先河&#xff0c;也以内存为赌注&#xff0c;赢得了内存计…...

微信小程序Webview与H5通信

背景 近期有个微信小程序需要用到web-view嵌套H5的场景&#xff0c;该应用场景需要小程序中频繁传递数据到H5进行渲染&#xff0c;且需要保证页面不刷新。 由于微信小程序与H5之间的通信限制比较大&#xff0c;显然无法满足于我的业务场景 探索 由于微信小程序与webview的环境是…...

Debezium Engine监听binlog实现缓存更新与业务解耦

飞书文档 解决缓存与数据源数据不一致的方案有很多, 各有优缺点; 1.0、旁路缓存策略, 直接同步更新 读取流程&#xff1a; 查询缓存。如果缓存命中&#xff0c;则直接返回结果。如果缓存未命中&#xff0c;则查询数据库。将数据库查询到的数据写入缓存&#xff0c;并设置一个…...

docker搭建socks5代理

准备工作 VPS安全组/策略放行相应端口如启用了防火墙&#xff0c;放行相应端口 实际操作 我们选用“历史悠久”的Dante socks5 代理服务器&#xff0c;轻量、稳定。Github也有对dante进行进一步精简的镜像&#xff0c;更为适宜。github项目地址如下&#xff1a; https://gi…...

scanf函数和printf函数的格式化输入输出

#include<stdio.h> int main() {int a;double b;char c;scanf("a%d,b%lf:c%c",&a,&b,&c); //float型输入时使用%f占位&#xff0c;double型使用%lf占位&#xff1b;输出时二者相同都是%f即可。if(a>0)printf("a%-10d,b%20.3lf,c%c",a…...

Day31 贪心算法 part05

56. 合并区间 本题也是重叠区间问题&#xff0c;如果昨天三道都吸收的话&#xff0c;本题就容易理解了。 代码随想录 class Solution {public int[][] merge(int[][] intervals) {Arrays.sort(intervals, (a,b) -> Integer.compare(a[0], b[0]));List<int[]> result …...

uniapp连接mqtt频繁断开原因和解决方法

mqtt参考文档&#xff1a;MQTT.js 入门教程 | EMQ、MQTT.js 入门教程 - EMQX - 博客园 uniapp引用MQTT频繁断开的问题可能由于以下几个原因导致&#xff1a; 网络不稳定&#xff1a;频繁断开可能是由于网络不稳定导致的&#xff0c;可以尝试优化网络连接。 心跳机制问题&…...

【数据结构-队列】力扣641. 设计循环双端队列

设计实现双端队列。 实现 MyCircularDeque 类: MyCircularDeque(int k) &#xff1a;构造函数,双端队列最大为 k 。 boolean insertFront()&#xff1a;将一个元素添加到双端队列头部。 如果操作成功返回 true &#xff0c;否则返回 false 。 boolean insertLast() &#xff1…...

砸108亿美元造芯!莫迪的野心,真能实现吗?

前言&#xff1a;从组装iPhone到造芯片&#xff0c;莫迪的野心藏不住&#xff0c;但别盲目乐观最近彭博社等外媒报道&#xff0c;印度政府计划推出规模超1万亿卢比&#xff08;约108亿美元&#xff09;的半导体专项基金&#xff0c;专门扶持本土芯片制造。这已经不是印度第一次…...

手把手拆解工业级ISP算法源码

ISP算法源码 资料最齐全&#xff0c;全网最低&#xff0c;包含Cmodel执行文件&#xff0c;可读源代码等等。 也有骗子搞成号称有Cmodel执行文件注意甄别&#xff0c;甚至宝贝描述都是抄我的 也可以在xilinx平台例化图形界面&#xff0c;方便使用 功能涵盖&#xff1a; DPC坏点缺…...

基于springboot企业车辆管理系统

一、系统核心定位 基于 SpringBoot 的企业车辆管理系统&#xff0c;是专为企业&#xff08;尤其是拥有多辆公务车、货运车的中大型企业&#xff09;打造的 “车辆调度 - 使用 - 维护 - 成本” 全流程数字化平台。该系统解决传统车辆管理中 “调度混乱、用车申请繁琐、维护不及时…...

一维线性插值算法C++详细实现

算法概述&#xff1a;算法实现&#xff1a;下面提供一套健壮的一维线性插值 C 实现&#xff0c;重点考虑了数据预处理、边界处理、重复点合并及浮点容差等鲁棒性细节。#include <vector> #include <algorithm> #include <stdexcept> #include <cmath> …...

AI智能体协议乱象背后:MCP、A2A、ACP……谁将成为下一代互联网的“HTTP“?

在AI智能体&#xff08;Agent&#xff09;迅猛发展的当下&#xff0c;MCP、A2A、ACP、UTCP、ANP……各种协议层出不穷&#xff0c;几乎每隔一段时间&#xff0c;科技公司就会为“字母家族”增添新成员。归根结底&#xff0c;所有AI智能体协议的目标都是标准化智能体的通信方式&…...

2026微信抢红包终极秘籍:从0.01元专业户到手气王锦鲤

2026年抢红包&#xff0c;早已不是“拼手速”那么简单&#xff01;微信红包的分配背后藏着明确的算法逻辑&#xff0c;掌握这套逻辑再搭配实用技巧&#xff0c;就能从“陪跑选手”逆袭成“红包锦鲤”。据统计&#xff0c;2026年除夕夜用户共抢到50.8亿个微信红包&#xff0c;但…...

如何使用Surya快速生成Solidity合约调用流程图?5分钟上手教程

如何使用Surya快速生成Solidity合约调用流程图&#xff1f;5分钟上手教程 【免费下载链接】surya A set of utilities for exploring Solidity contracts 项目地址: https://gitcode.com/gh_mirrors/sur/surya Surya是一套用于探索Solidity合约的实用工具&#xff0c;能…...

如何使用eCapture实现Zsh命令捕获:终端操作审计与安全分析完整指南

如何使用eCapture实现Zsh命令捕获&#xff1a;终端操作审计与安全分析完整指南 【免费下载链接】ecapture Capture SSL/TLS text content without a CA certificate using eBPF. This tool is compatible with Linux/Android x86_64/Aarch64. 项目地址: https://gitcode.com/…...

终极Android-PickerView使用指南:让每个人都能顺畅实现时间与省市区选择功能

终极Android-PickerView使用指南&#xff1a;让每个人都能顺畅实现时间与省市区选择功能 【免费下载链接】Android-PickerView This is a picker view for android , support linkage effect, timepicker and optionspicker.&#xff08;时间选择器、省市区三级联动&#xff09…...

(优选算法)斐波那契数列模型

动态规划解题步骤:首先&#xff0c;动态规划的题目主要的目的是为了填写表dp中的空缺部分。1. 状态表示&#xff1a;就是要填写到qp表中那个值的涵义。2. 状态转移方程&#xff1a;就是dp[i]值怎么得到的。3. 初始化&#xff1a;初始化一些值防止&#xff0c;在执行状态方程的时…...