
import { _decorator, Component, Node, Vec3, v3, toDegree, math } from 'cc';
import { UI_EVENT } from './Constants';
import { Global } from './Global';
import { Rocket } from './Rocket';
import { Shake } from './Shake';
const { ccclass, property } = _decorator;

let outV3 = v3();

class ShakeInfo {
    originalPos: Vec3 = v3();
    afterPos: Vec3 = v3();
    xShakes: Shake[] = [];
    yShakes: Shake[] = [];

    /**
     * 
     * @param amplitude 振幅（单位：像素）
     * @param frequence 频率（次/秒）
     * @param duration 即震屏持续时长（单位：秒）
     */
    shake(amplitude: number, frequence: number, duration: number) {
        this.xShakes.push(Shake.new(amplitude, frequence, duration));
        this.yShakes.push(Shake.new(amplitude, frequence, duration));
    }

    update(dt: number, node: Node) {
        let xShakeAmount = this.originalPos.x;
        let yShakeAmount = this.originalPos.y;
        if(this.xShakes.length > 0 || this.yShakes.length > 0) {
            for(let i = 0; i < this.xShakes.length; i++) {
                this.xShakes[i].update(dt);
                xShakeAmount += this.xShakes[i].getAmplitude();
                if(this.xShakes[i].notShaking) {
                    Shake.push(this.xShakes[i]);
                    this.xShakes.splice(i, 1);
                    i--;
                }
            }

            for(let j = 0; j < this.yShakes.length; j++) {
                this.yShakes[j].update(dt);
                yShakeAmount += this.yShakes[j].getAmplitude();
                if(this.yShakes[j].notShaking) {
                    Shake.push(this.yShakes[j]);
                    this.yShakes.splice(j, 1);
                    j--;
                }
            }
        }
        node.setPosition(xShakeAmount, yShakeAmount, this.originalPos.z);
    }
}

@ccclass('Planet')
export class Planet extends Component {

    @property({
        type: Rocket
    })
    rocket: Rocket;

    @property({
        type: Node,
        tooltip: '护罩'
    })
    planetShield: Node;

    shootInterval: number = 0.3;
    shootTimer: number = 0;
    
    heading: Vec3 = v3(0, 1, 0);
    targetHeading: Vec3 = v3(0, 1, 0);

    shakeInfo: ShakeInfo = new ShakeInfo();

    onLoad() {
        this.shakeInfo.originalPos.set(this.node.position);
        this.planetShield.active = false;
        Global.uiEvent.on(UI_EVENT.PLAYER_MOVE, this.onPlayerMove, this);
    }

    onPlayerMove(targetHeading: Vec3) {
        this.targetHeading.set(targetHeading);
    }

    shake() {
        this.shakeInfo.shake(5, 90, 0.2);
    }

    update(dt: number) {
        if(!Vec3.equals(this.heading, this.targetHeading, 0.01)) {
            Vec3.subtract(outV3, this.targetHeading, this.heading);
            outV3.multiplyScalar(0.015);
            this.heading.add(outV3);
            this.heading.normalize();
            this.rocket.node.angle = toDegree(Math.atan2(this.heading.y, this.heading.x)) - 90;
        }

        this.shootTimer += dt;
        if(this.shootTimer >= this.shootInterval) {
            this.shootTimer -= this.shootInterval;
            this.rocket.shoot(this.heading);
        }

        this.shakeInfo.update(dt, this.node);
    }
}