Files
2026-05-19 11:55:24 +08:00

303 lines
9.2 KiB
TypeScript
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { _decorator, Node, tween, Vec3, Sprite, Asset, ImageAsset, SpriteFrame, Texture2D, Label, EventTouch, UITransform } from 'cc';
import BaseView from '../../../../../../extensions/app/assets/base/BaseView';
import { PageTips } from '../../tips/native/PageTips';
import { app } from 'db://assets/app/app';
import { PageRewardhistory } from '../../rewardhistory/native/PageRewardhistory';
import { Tools } from 'db://assets/res-native/tools/Tools';
import { USERDATA } from 'db://assets/res-native/data/UserData';
const { ccclass, property } = _decorator;
@ccclass('PageMain')
export class PageMain extends BaseView {
/** 音乐按钮 */
@property(Node)
btn_music: Node = null!;
/** 奖励文字 */
@property(Label)
lab_rw: Label = null!;
/** 奖励 */
@property(Node)
reward_bg: Node = null!;
/** 奖励 */
@property(Node)
noreward_bg: Node = null!;
/** 宝箱item */
@property(Node)
box_item: Node = null!;
/** 宝箱列表 */
@property(Node)
list_box: Node = null!;
/** 奖励icon */
@property(Sprite)
icon_rw: Sprite = null!;
/** 剩余次数 */
@property(Label)
lab_remain: Label = null!;
/** 钻石 */
@property(Node)
diomand: Node[] = [];
/** 钻石 */
@property(Node)
logo: Node = null!;
/** 奖励icon */
@property(Sprite)
game_logo: Sprite = null!;
/** 奖励icon */
@property(Sprite)
game_logo_bg: Sprite = null!;
/** 宝箱位置 */
private _position: { [key: number]: Vec3 } = {
0: new Vec3(-310, 320, 0),
1: new Vec3(0, 320, 0),
2: new Vec3(310, 320, 0),
3: new Vec3(310, 0, 0),
4: new Vec3(310, -320, 0),
5: new Vec3(0, -320, 0),
6: new Vec3(-310, -320, 0),
7: new Vec3(-310, 0, 0),
};
/** 是否可以开始游戏 */
private _canStart = true;
/** 宝箱管理 */
private _boxMgr : Node[] = []
/** 是否正在播放动画 */
private _isSpinning: boolean = false;
// 初始化的相关逻辑写在这
onLoad() {}
// 界面打开时的相关逻辑写在这(onShow可被多次调用-它与onHide不成对)
onShow(params: any) {
this.lab_remain.string = "CHANCE:" + USERDATA.point.toString()
this.initRw()
this.startAnimation()
// 加载配置的logo
if (USERDATA.logo && this.game_logo) {
Tools.remoteLoadSprite(USERDATA.logo, this.game_logo)
}
if (USERDATA.logo_back && this.game_logo_bg) {
Tools.remoteLoadSprite(USERDATA.logo_back, this.game_logo_bg)
}
}
// 界面关闭时的相关逻辑写在这(已经关闭的界面不会触发onHide)
onHide(result: undefined) {
// app.manager.ui.show<PageMain>({name: 'PageMain', onHide:(result) => { 接收到return的数据并且有类型提示 }})
return result;
}
startAnimation(){
// 钻石上下移动动画
this.diomand.forEach((diamond, index) => {
if (diamond) {
tween(diamond)
.repeatForever(
tween()
.by(0.5, { position: new Vec3(0, 10, 0) })
.by(0.5, { position: new Vec3(0, -10, 0) })
)
.start();
}
});
// Logo放大缩小动画
if (this.logo) {
tween(this.logo)
.repeatForever(
tween()
.to(0.8, { scale: new Vec3(1.1, 1.1, 1) })
.to(0.8, { scale: new Vec3(1, 1, 1) })
)
.start();
}
}
initRw(){
this._boxMgr = []
for (let i = 0; i < 8; i++) {
this._boxMgr[i] = Tools.AddChild(this.list_box, this.box_item, "item_" + i)
let item = this._boxMgr[i]
item.setPosition(this._position[i])
item.active = true
if (USERDATA.prize_list[i]){
Tools.remoteLoadSprite(USERDATA.prize_list[i].pic, Tools.GetChildComp(item, "icon", Sprite))
Tools.SetChildText(item, "lab", USERDATA.prize_list[i].name)
}
}
this._canStart = true
}
/** 点击奖励确定 */
onClickRewardSure(){
this.reward_bg.active = false
this.noreward_bg.active = false
this._canStart = true
}
/** 点击提示 */
onClickTips(){
app.manager.ui.show<PageTips>({name: 'PageTips'})
}
/** 点击音乐 */
oncClickMusic(){
let music = app.manager.sound.isMusicPlaying
music ? app.manager.sound.stopMusic() : app.manager.sound.playDefaultMusic()
this.loadSprite(music ? "main_btn_sounds_off" : "main_btn_sounds_on", this.btn_music)
}
/** 点击历史 */
onClickRwHis(){
app.manager.ui.show<PageRewardhistory>({name: 'PageRewardhistory'})
}
/** 点击开始 */
onStartGame() {
if (!this._canStart) return;
if (USERDATA.point <= 0) {
app.manager.ui.showToast(Tools.GetLocalized("no chance"));
return;
}
this._canStart = false;
Tools.httpReq("lottery", {}, (res:any)=>{
let n = this.checkRwId(res.prize_id)
if (n == null){
app.manager.ui.showToast(Tools.GetLocalized("fail"))
return
}
USERDATA.point--
this.lab_remain.string = "CHANCE:" + USERDATA.point.toString()
this.lab_rw.string = Tools.StringLFormat(res.message)
Tools.remoteLoadSprite(USERDATA.prize_list[n].pic, this.icon_rw)
// 开始转格子动画
this.startSpinAnimation(n, res.prize_type);
},()=>{
this._canStart = true;
})
}
checkRwId(prize_id: number){
let n = null
for (let i = 0; i < USERDATA.prize_list.length; i++) {
const element = USERDATA.prize_list[i];
if (prize_id == element.id){
n = i
break
}
}
return n
}
loadSprite(pic: string, node: Node){
this.loadRes(pic, Asset, (res: ImageAsset)=>{
let sp = new SpriteFrame()
let tex = new Texture2D();
tex.image = res;
sp.texture = tex
node.getComponent(Sprite).spriteFrame = sp
});
}
/**
* 开始转格子动画
* @param targetIndex 目标格子索引
*/
private startSpinAnimation(targetIndex: number, prize_type:number) {
if (this._isSpinning) return;
this._isSpinning = true;
// 先清除所有高亮
this.clearAllHighlights();
// 开始动画 - 至少转3圈再停到目标位置
const totalSpins = 3;
const totalSteps = totalSpins * 8 + targetIndex;
this.spinStep(0, totalSteps, targetIndex, prize_type);
}
/**
* 执行旋转步骤
* @param currentStep 当前步数
* @param totalSteps 总步数
* @param targetIndex 目标索引
* @param prize_type 奖品类型
*/
private spinStep(currentStep: number, totalSteps: number, targetIndex: number, prize_type:number) {
if (currentStep >= totalSteps) {
// 动画结束 - 确保目标格子高亮
this.clearAllHighlights();
this.highlightBox(targetIndex);
this._isSpinning = false;
// 延迟显示奖励面板
this.scheduleOnce(() => {
this.reward_bg.active = prize_type != 3;
this.noreward_bg.active = prize_type == 3;
app.manager.sound.playEffect({name: 'effect/win'});
}, 0.5);
return;
}
// 计算当前应该高亮的格子索引
const currentIndex = currentStep % 8;
// 清除之前高亮并设置新的高亮
this.clearAllHighlights();
this.highlightBox(currentIndex);
// 根据进度调整速度(越接近终点越慢)
let delay = 100; // 默认速度
const remainingSteps = totalSteps - currentStep;
if (remainingSteps < 8) {
delay = 200 + (8 - remainingSteps) * 50; // 最后几帧逐渐变慢
}
// 继续下一步动画
this.scheduleOnce(() => {
app.manager.sound.playEffect({name: 'effect/jump'});
this.spinStep(currentStep + 1, totalSteps, targetIndex, prize_type);
}, delay / 1000); // scheduleOnce 使用秒为单位
}
/**
* 高亮指定格子
* @param index 格子索引
*/
private highlightBox(index: number) {
if (index < 0 || index >= this._boxMgr.length) return;
const boxNode = this._boxMgr[index];
if (boxNode) {
Tools.ActChild(boxNode, "select", true);
}
}
/**
* 清除所有格子的高亮状态
*/
private clearAllHighlights() {
for (let i = 0; i < this._boxMgr.length; i++) {
const boxNode = this._boxMgr[i];
Tools.ActChild(boxNode, "select", false);
}
}
}