Files
2025-09-21 20:36:25 +08:00

504 lines
11 KiB
TypeScript

import {
_decorator,
Node,
tween,
Vec3,
UITransform,
view,
UIOpacity,
} from "cc";
import { logger } from "db://assets/Scripts/Main/Common/Logger";
const { ccclass, property } = _decorator;
/**
* UI过渡动画帮助类
*
* 提供常用的UI过渡动画效果,如滑入滑出等
*
* @author AI Chat System
* @version 1.0.0
*/
@ccclass("UITransitionHelper")
export class UITransitionHelper {
/**
* 让节点从右侧滑入到屏幕中心
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static slideInFromRight(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for slideInFromRight");
return;
}
const screenWidth = view.getVisibleSize().width;
const targetPosition = new Vec3(0, 0, 0);
// 设置初始位置为屏幕右侧外
node.setPosition(screenWidth, 0, 0);
// 执行滑入动画到屏幕中心
tween(node)
.to(
duration,
{ position: targetPosition },
{
easing: "cubicOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 让节点向左滑出到屏幕外
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static slideOutToLeft(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for slideOutToLeft");
return;
}
const screenWidth = view.getVisibleSize().width;
const currentPosition = node.getPosition();
const targetPosition = new Vec3(
-screenWidth,
currentPosition.y,
currentPosition.z
);
// 执行滑出动画
tween(node)
.to(
duration,
{ position: targetPosition },
{
easing: "cubicOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 让节点从左侧滑入到屏幕中心
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static slideInFromLeft(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for slideInFromLeft");
return;
}
const screenWidth = view.getVisibleSize().width;
const targetPosition = new Vec3(0, 0, 0);
// 设置初始位置为屏幕左侧外
node.setPosition(-screenWidth, 0, 0);
// 执行滑入动画到屏幕中心
tween(node)
.to(
duration,
{ position: targetPosition },
{
easing: "cubicOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 让节点向右滑出到屏幕外
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static slideOutToRight(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for slideOutToRight");
return;
}
const screenWidth = view.getVisibleSize().width;
const currentPosition = node.getPosition();
const targetPosition = new Vec3(
screenWidth,
currentPosition.y,
currentPosition.z
);
// 执行滑出动画
tween(node)
.to(
duration,
{ position: targetPosition },
{
easing: "cubicOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 让节点从顶部滑入到屏幕中心
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static slideInFromTop(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for slideInFromTop");
return;
}
const screenHeight = view.getVisibleSize().height;
const targetPosition = new Vec3(0, 0, 0);
// 设置初始位置为屏幕顶部外
node.setPosition(0, screenHeight, 0);
// 执行滑入动画到屏幕中心
tween(node)
.to(
duration,
{ position: targetPosition },
{
easing: "cubicOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 让节点向顶部滑出到屏幕外
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static slideOutToTop(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for slideOutToTop");
return;
}
const screenHeight = view.getVisibleSize().height;
const currentPosition = node.getPosition();
const targetPosition = new Vec3(
currentPosition.x,
screenHeight,
currentPosition.z
);
// 执行滑出动画
tween(node)
.to(
duration,
{ position: targetPosition },
{
easing: "cubicOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 让节点从底部滑入到屏幕中心
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static slideInFromBottom(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for slideInFromBottom");
return;
}
const screenHeight = view.getVisibleSize().height;
const targetPosition = new Vec3(0, 0, 0);
// 设置初始位置为屏幕底部外
node.setPosition(0, -screenHeight, 0);
// 执行滑入动画到屏幕中心
tween(node)
.to(
duration,
{ position: targetPosition },
{
easing: "cubicOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 让节点向底部滑出到屏幕外
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static slideOutToBottom(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for slideOutToBottom");
return;
}
const screenHeight = view.getVisibleSize().height;
const currentPosition = node.getPosition();
const targetPosition = new Vec3(
currentPosition.x,
-screenHeight,
currentPosition.z
);
// 执行滑出动画
tween(node)
.to(
duration,
{ position: targetPosition },
{
easing: "cubicOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 淡入效果
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static fadeIn(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for fadeIn");
return;
}
let opacity = node.getComponent(UIOpacity);
if (!opacity) {
opacity = node.addComponent(UIOpacity);
}
// 设置初始透明度为0
opacity.opacity = 0;
// 执行淡入动画
tween(opacity)
.to(
duration,
{ opacity: 255 },
{
easing: "sineOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 淡出效果
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static fadeOut(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for fadeOut");
return;
}
let opacity = node.getComponent(UIOpacity);
if (!opacity) {
opacity = node.addComponent(UIOpacity);
}
// 执行淡出动画
tween(opacity)
.to(
duration,
{ opacity: 0 },
{
easing: "sineOut",
}
)
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 缩放进入效果
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static scaleIn(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for scaleIn");
return;
}
// 设置初始缩放为0
node.setScale(0, 0, 1);
// 执行缩放进入动画
tween(node)
.to(duration, { scale: new Vec3(1, 1, 1) }, { easing: "backOut" })
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 缩放退出效果
*
* @param {Node} node - 要执行动画的节点
* @param {number} duration - 动画持续时间(秒),默认0.3秒
* @param {Function} callback - 动画完成后的回调函数
*/
public static scaleOut(
node: Node,
duration: number = 0.3,
callback?: Function
): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for scaleOut");
return;
}
// 执行缩放退出动画
tween(node)
.to(duration, { scale: new Vec3(0, 0, 1) }, { easing: "backIn" })
.call(() => {
if (callback) {
callback();
}
})
.start();
}
/**
* 停止节点上的所有动画
*
* @param {Node} node - 要停止动画的节点
*/
public static stopAllTweens(node: Node): void {
if (!node || !node.isValid) {
logger.warn("UITransitionHelper: Invalid node for stopAllTweens");
return;
}
tween(node).stop();
}
}