import { onHomeworkFinish, randomSortByArr, playDragonBoneAnimation } from "../script/util";
import { defaultData } from "../script/defaultData";

cc.Class({

	extends: cc.Component,

	properties: {
	},

	// 生命周期 onLoad
	onLoad() {
		this.initSceneData();
		this.initSize();
	},

	// 生命周期
	onDestroy() {
		if (this.timeA !== undefined) {
			clearTimeout(this.timeA);
		}
	},

	_imageResList: null,
	_audioResList: null,
	_animaResList: null,
	initSceneData() {
		this._imageResList = [];
		this._audioResList = [];
		this._animaResList = [];
	},

	_designSize: null,  // 设计分辨率
	_frameSize: null,  // 屏幕分辨率
	_mapScaleMin: null,  // 场景中常用缩放（取大值）
	_mapScaleMax: null,  // 场景中常用缩放（取小值）
	_cocosScale: null,  // cocos 自缩放 （较少用到）
	initSize() {
		// 注意cc.winSize只有在适配后(修改fitHeight/fitWidth后)才能获取到正确的值,因此使用cc.getFrameSize()来获取初始的屏幕大小
		let screen_size = cc.view.getFrameSize().width / cc.view.getFrameSize().height
		let design_size = cc.Canvas.instance.designResolution.width / cc.Canvas.instance.designResolution.height
		let f = screen_size >= design_size
		cc.Canvas.instance.fitHeight = f
		cc.Canvas.instance.fitWidth = !f

		const frameSize = cc.view.getFrameSize();
		this._frameSize = frameSize;

		this._designSize = cc.view.getDesignResolutionSize();

		let sx = cc.winSize.width / frameSize.width;
		let sy = cc.winSize.height / frameSize.height;
		this._cocosScale = Math.min(sx, sy);

		sx = frameSize.width / this._designSize.width;
		sy = frameSize.height / this._designSize.height;
		this._mapScaleMin = Math.min(sx, sy) * this._cocosScale;
		this._mapScaleMax = Math.max(sx, sy) * this._cocosScale;
	},


	// 生命周期 start
	start() {
		let getData = this.getData.bind(this);
		if (window && window.courseware) {
			getData = window.courseware.getData;
		}

		getData((data) => {
			console.log('data:' + JSON.stringify(data));
			this.data = data || this.getDefaultData();
			this.data = JSON.parse(JSON.stringify(this.data));
			this.preloadItem();
		})
	},

	getData(func) {
		if (window && window.courseware) {
			window.courseware.getData(func, 'scene');
			return;
		}

		const middleLayer = cc.find('middleLayer');
		if (middleLayer) {
			const middleLayerComponent = middleLayer.getComponent('middleLayer');
			middleLayerComponent.getData(func);
			return;
		}

		func(this.getDefaultData());
	},

	getDefaultData() {
		return defaultData;
	},

	preloadItem() {
		this.addPreloadImage();
		this.addPreloadAudio();
		this.addPreloadAnima();
		this.preload();
	},


	addPreloadImage() {
		this._imageResList.push(...this.data.question_arr.map(question => {
			return question.option_arr.map(option => {
				return { url: option.pic_url }
			});
		}).flat());
	},

	addPreloadAudio() {
		this._audioResList.push(this.data.startAudio);
		this._audioResList.push(this.data.endAudio);
		this._audioResList.push(...this.data.question_arr.map(question => {
			return question.option_arr.map(option => {
				return { url: option.audio_url };
			});
		}).flat());
		this._audioResList.push(...this.data.question_arr.map(question => {
			return { url: question.question_audio_url };
		}));
	},

	addPreloadAnima() {

	},

	preload() {
		const preloadArr = [
			...this._imageResList,
			...this._audioResList,
			...this._animaResList
		];
		cc.assetManager.loadAny(preloadArr, null, null, (err, data) => {

			if (window && window["air"]) {
				cc.find('Canvas').opacity = 0;
				window.air.onCourseInScreen = (next) => {
					cc.find('Canvas').opacity = 255;
					this.loadEnd();
					next();
				}
				window.air.hideAirClassLoading();
			} else {
				this.loadEnd();
			}

			cc.debug.setDisplayStats(false);
		});
	},

	loadEnd() {
		this.initData();
		this.initView();
		this.initListener();
	},

	initData() {
		this.status = {
			currentQuestionIdx: 0,
			wrongTime: 0
		}
	},

	initView() {
		this.refreshCoolCatPosition();

		//TODO:copy
		this.hideFlower();

		const box = cc.find('Canvas/bg/box');
		box.removeAllChildren();
		const box_mid = cc.find('Canvas/bg/box_mid');
		box_mid.removeAllChildren();
		let group1 = cc.find('Canvas/bg/group1');
		group1.removeAllChildren();
		let group2 = cc.find('Canvas/bg/group2');
		group2.removeAllChildren();

		this.coolCatSpeakStart(() => {
			this.showSubmitBtn();
			this.jumpToQuestion(this.status.currentQuestionIdx);
		});
	},

	refreshCoolCatPosition() {

	},

	jumpToQuestion(questionIdx) {
		const questionAudioUrl = this.data.question_arr[questionIdx].audio_url;
		this.playAudioByUrl(questionAudioUrl);

		const box = cc.find('Canvas/bg/box');
		box.removeAllChildren();

		const canvasWidth = cc.find('Canvas').width;
		const canvasHeight = cc.find('Canvas').height;
		const optionNum = this.data.question_arr[questionIdx].option_arr.length;
		//TODO:copy---start
		const maxOptionHeight = 400;
		const maxOptionWidth = (canvasWidth * 0.8) / optionNum;
		const box_mid = cc.find('Canvas/bg/box_mid');
		box_mid.removeAllChildren();
		//TODO:copy---end
		this.showIdx = 0;
		let group1 = cc.find('Canvas/bg/group1');
		group1.removeAllChildren();
		let group2 = cc.find('Canvas/bg/group2');
		group2.removeAllChildren();

		let la_layout = cc.find("Canvas/bg/paizi/la_layout");
		la_layout.removeAllChildren();
		let desc = cc.find("Canvas/bg/desc");
		const optiontext = this.data.question_arr[questionIdx].desc1;
		const optiontext2 = this.data.question_arr[questionIdx].desc2;
		let textArr = [optiontext, optiontext2];
		textArr.forEach((item) => {
			if (!item || item == "") return;
			let d = cc.instantiate(desc);
			d.getComponent(cc.Label).string = item;
			la_layout.addChild(d);
			d.y = 0;
		})
		let paizi = cc.find("Canvas/bg/paizi");
		paizi.active = la_layout.children.length > 0;
		let size = cc.view.getCanvasSize();
		let scale = (size.width / size.height) / (1280 / 720);
		group2.getComponent(cc.Layout).spacingX = scale < 1 ? 75 * scale : 85;

		const arr = randomSortByArr(this.data.question_arr[questionIdx].option_arr);
		arr.forEach(async (option, idx) => {
			const optionNode = await this.createOption(option);
			optionNode.name = `option_${idx}`;
			optionNode.x = (idx - (arr.length - 1) / 2) * maxOptionWidth * 1 - 150;//TODO：增加部分空隙1.1倍
			optionNode.y = 0;//-(canvasHeight / 2) -800;
			optionNode.scale = 0;
			optionNode.parent = box;
			// optionNode.targetScale = Math.min((maxOptionWidth * 0.80) / optionNode.width, maxOptionHeight / optionNode.height)
			console.log("targetScale: " + optionNode.targetScale);
			optionNode.width = 280;
			optionNode.height = 280;
			cc.tween(optionNode)
				.to(0.1, { scale: 1 })
				.start();
		});
	},

	createOption(optionData) {
		return new Promise((resolve, reject) => {
			const optionNode = cc.instantiate(cc.find('option'));
			this.loadSpriteByUrl(optionNode, optionData.pic_url, (texture) => {
				resolve(optionNode);
			});
			optionNode.optionData = optionData;
			optionNode.optionData.selected = false;


			const box = cc.find('Canvas/bg/box');
			const box_mid = cc.find('Canvas/bg/box_mid');
			optionNode.on(cc.Node.EventType.TOUCH_START, (event) => {
				if (optionNode.optionData.selected) {
					return;
				}
				const location = event.getLocation();
				optionNode.startLocation = location;
				optionNode.startPos = {
					x: optionNode.x,
					y: optionNode.y
				}
				const selectedNum = box.children.filter(child => child.optionData.selected == true).length;
				optionNode.zIndex = selectedNum;

				this.optionJump(optionNode);
				this.playAudioByUrl(optionNode.optionData.audio_url);
			});
			optionNode.on(cc.Node.EventType.TOUCH_MOVE, (event) => {
				if (optionNode.optionData.selected) {
					return;
				}
				const location = event.getLocation();
				optionNode.x = optionNode.startPos.x + (location.x - optionNode.startLocation.x);
				optionNode.y = optionNode.startPos.y + (location.y - optionNode.startLocation.y);
			});
			optionNode.on(cc.Node.EventType.TOUCH_END, (event) => {
				if (optionNode.optionData.selected) {
					return;
				}
				// const rectOption = optionNode.getBoundingBox();
				//TODO:copy--start
				const rectBox = new cc.Rect(box_mid.x, box_mid.y, box_mid.width, box_mid.height);
				const rectOption = new cc.Rect(optionNode.x, optionNode.y, optionNode.width, optionNode.height);
				function rect2Rect(rect1, rect2) {
					let width = rect1.width / 2 + rect2.width / 2;
					let spaceX = Math.abs(rect1.x - rect2.x);
					let height = rect1.height / 2 + rect2.height / 2;
					let spaceY = Math.abs(rect1.y - rect2.y);
					return spaceX <= width && spaceY <= height;
				}

				let oPos0 = optionNode.convertToWorldSpaceAR(cc.Vec2.ZERO);//正确位置的坐标
				let oPos1 = box_mid.convertToWorldSpaceAR(cc.Vec2.ZERO);//移动位置坐标

				// 计算两个位置的距离
				let nD = cc.Vec2.distance(oPos0, oPos1);
				if (nD > 550) {
					// if (!rect2Rect(rectBox, rectOption)) {
					//TODO:copy--end

					cc.tween(optionNode)
						.to(0.05, {
							x: optionNode.startPos.x,
							y: optionNode.startPos.y
						}, cc.easing.quadOut)
						.start();

					this.playEffect('flyBack');
					return;
				}

				//copy-start  把物品的父节点换到中间的box上。
				const group1 = cc.find('Canvas/bg/group1');
				const group2 = cc.find('Canvas/bg/group2');
				if (optionNode.x >= 0) {
					cc.tween(optionNode)
						.to(0.2, { x: optionNode.x, y: optionNode.y + 200 }, cc.easing.quadOut)
						.call(() => {
							optionNode.anchorX = 0;
							optionNode.anchorY = 0;
							optionNode.parent = this.showIdx > 1 ? group2 : group1;
							this.showIdx++;
						}).to(0.2, { x: 0, y: 0, scale: 0.7 }, cc.easing.quadOut).start();
				} else {
					cc.tween(optionNode)
						.to(0.2, { x: optionNode.x, y: optionNode.y + 100 }, cc.easing.quadOut)
						.call(() => {
							optionNode.anchorX = 0;
							optionNode.anchorY = 0;
							optionNode.parent = this.showIdx > 1 ? group2 : group1;
							this.showIdx++;
						}).to(0.2, { x: 0, y: 0, scale: 0.7 }, cc.easing.quadOut).start();
				}
				//copy-end


				this.boxJump();

				optionNode.optionData.selected = true;
			});

			return optionNode;
		});
	},

	optionJump(node, time = 0.1) {
		if (node.baseScale) {
			return;
		}
		node.baseScale = node.scaleX;

		cc.tween(node)
			.to(time, { scaleX: node.baseScale * 1.1, scaleY: node.baseScale * 1.1 })
			.to(time, { scaleX: node.baseScale * 1, scaleY: node.baseScale * 1 })
			.call(() => {
				node.baseScale = null;
			})
			.start();
	},

	initListener() {
		const btnSubmit = cc.find('Canvas/bg/btnSubmit');
		btnSubmit.on('click', () => {
			this.optionJump(btnSubmit, 0.05);
			this.playEffect('submit');
			const box = cc.find('Canvas/bg/box');
			//TODO:copy-start  把物品的父节点换到中间的box上。
			const box_mid = cc.find('Canvas/bg/box_mid');
			const group1 = cc.find('Canvas/bg/group1');
			const group2 = cc.find('Canvas/bg/group2');
			let children = box.children.concat(group1.children).concat(group2.children);
			if (children.every(child => child.optionData.selected == child.optionData.is_right)) {
				//copy-end
				this.onAnswerRight();
			} else {
				this.coolCatSpeakWrong(() => {
					this.status.wrongTime++;
					if (this.status.wrongTime < this.data.maxWrongNumber) {
						this.onAnswerWrong();
					} else {
						this.onAnswerWrongTwice();
					}
				});
			}

			this.showIdx = 0;
		});

		const btnNext = cc.find('Canvas/bg/btnNext');
		btnNext.on('click', () => {
			this.optionJump(btnNext, 0.05);
		});

		const btnCoolCat = cc.find('Canvas/bg/catFrame/BtnCoolCat');
		btnCoolCat.on('click', () => {
			const cat = cc.find('Canvas/bg/catFrame/CoolCat');
			const btn = cc.find('Canvas/bg/btnReplay');
			if (btn.active) {
				playDragonBoneAnimation(cat, 'finish', -1);
				this.playAudioByUrl(this.data.endAudio, () => {
					playDragonBoneAnimation(cat, 'normal', -1);
					this.showNextBtn();
				});
			} else {
				// playDragonBoneAnimation(cat, 'begin', -1);
				// this.playAudioByUrl(this.data.startAudio, () => {
				// playDragonBoneAnimation(cat, 'normal', -1);
				// this.showSubmitBtn();
				// this.jumpToQuestion(this.status.currentQuestionIdx);
				// });

				playDragonBoneAnimation(cat, 'normal', -1);
				this.showSubmitBtn();
				let questionIdx = this.status.currentQuestionIdx;
				const questionAudioUrl = this.data.question_arr[questionIdx].audio_url;
				this.playAudioByUrl(questionAudioUrl);
			}
		});
	},

	//TODO:copy---start
	showFlower() {
		const flower = cc.find('Canvas/bg/star_ske');
		flower.active = true;
		let dba = flower.getComponent(dragonBones.ArmatureDisplay)
		dba.playAnimation('normal', 1);
	},
	hideFlower() {
		const flower = cc.find('Canvas/bg/star_ske');
		flower.active = false;
	},
	//TODO:copy---end


	onAnswerRight() {
		//TODO:copy
		this.showFlower();

		this.coolCatSpeakRight(() => {
			//TODO:copy
			setTimeout(() => {
				this.nextQuestion();
			}, 1000);
		});
	},

	onAnswerWrong() {
		//copy---start
		let box_b = cc.find('Canvas/bg/box_behind')
		cc.tween(box_b).by(0.1, { x: 20 }).by(0.2, { x: -40 }).by(0.1, { x: 20 }).start();
		let box_f = cc.find('Canvas/bg/box_front')
		cc.tween(box_f).by(0.1, { x: 20 }).by(0.2, { x: -40 }).by(0.1, { x: 20 }).start();
		setTimeout(() => {
			const box = cc.find('Canvas/bg/box');
			box.children
				.filter(child => child.optionData.selected)
				.forEach(child => {
					child.optionData.selected = false;
					cc.tween(child)
						.to(0.2, { x: child.startPos.x, y: child.startPos.y, scale: child.targetScale })
						.start();
				});

			//copy-start  把物品的父节点换到中间的box上。
			const group1 = cc.find('Canvas/bg/group1');
			const group2 = cc.find('Canvas/bg/group2');
			const box_mid = cc.find('Canvas/bg/box_mid');
			group1.children
				.filter(child => child.optionData.selected)
				.forEach(child => {
					child.optionData.selected = false;
					cc.tween(child)
						.to(0.2, { x: child.startPos.x, y: child.startPos.y, scale: child.targetScale })
						.call(() => {
							child.parent = box;
							child.anchorX = 0.5;
							child.anchorY = 0.5;
						})
						.start();
				});
			group2.children
				.filter(child => child.optionData.selected)
				.forEach(child => {
					child.optionData.selected = false;
					cc.tween(child)
						.to(0.2, { x: child.startPos.x, y: child.startPos.y, scale: child.targetScale })
						.call(() => {
							child.parent = box;
							child.anchorX = 0.5;
							child.anchorY = 0.5;
						})
						.start();
				});
			//copy-end
			this.playEffect('flyBackAll');
		}, 100);
		//copy---end

	},

	onAnswerWrongTwice() {
		this.status.currentQuestionIdx = this.data.question_arr.length;
		this.nextQuestion();
		this.playEffect('jumpAll');
	},

	timeA: null,
	nextQuestion() {
		const box = cc.find('Canvas/bg/box');
		box.children.forEach(child => {
			cc.tween(child)
				.to(0.1, { scaleX: 0, scaleY: 0 })
				.removeSelf()
				.start();
		});
		this.status.currentQuestionIdx++;

		if (this.status.currentQuestionIdx < this.data.question_arr.length) {
			this.timeA = setTimeout(() => {
				this.jumpToQuestion(this.status.currentQuestionIdx);
			}, 0.1 * 1000);
		} else {

			this.hideSubmitBtn();
			this.coolCatSpeakEnd(() => {
				this.showNextBtn();
			});
		}
	},

	boxJump() {
		const boxBehind = cc.find('Canvas/bg/box_behind');
		const boxFront = cc.find('Canvas/bg/box_front');

		this.playEffect('boxJump');

		cc.tween(boxFront)
			.to(0.1, { scaleX: 1.02, scaleY: 1.02 })
			.to(0.1, { scaleX: 1.0, scaleY: 1.0 })
			.start();
		cc.tween(boxBehind)
			.to(0.1, { scaleX: 1.02, scaleY: 1.02 })
			.to(0.1, { scaleX: 1.0, scaleY: 1.0 })
			.start();
	},

	showSubmitBtn() {
		const submitBtn = cc.find('Canvas/bg/btnSubmit');
		if (submitBtn.showed) {
			return;
		}
		submitBtn.showed = true;
		cc.tween(submitBtn)
			.by(1, { y: submitBtn.height })
			.start();
	},

	hideSubmitBtn() {
		const submitBtn = cc.find('Canvas/bg/btnSubmit');
		if (!submitBtn.showed) {
			return;
		}
		submitBtn.showed = false;
		submitBtn.off('click');
		cc.tween(submitBtn)
			.by(1, { y: -submitBtn.height })
			.start();
	},

	showNextBtn() {
		onHomeworkFinish();

		this.showRestartBtn();

		const btnNext = cc.find('Canvas/bg/btnNext');
		btnNext.active = true;
	},

	coolCatSpeakStart(cb) {
		const cat = cc.find('Canvas/bg/catFrame/CoolCat');
		playDragonBoneAnimation(cat, 'begin', -1);
		this.playAudioByUrl(this.data.startAudio, () => {
			playDragonBoneAnimation(cat, 'normal', -1);
			cb();
		});
	},

	coolCatSpeakRight(cb) {
		const cat = cc.find('Canvas/bg/catFrame/CoolCat');
		playDragonBoneAnimation(cat, 'right', -1);
		this.playEffect('CoolCatRight', () => {
			playDragonBoneAnimation(cat, 'normal', -1);
			cb();
		});
	},

	coolCatSpeakWrong(cb) {
		const cat = cc.find('Canvas/bg/catFrame/CoolCat');
		playDragonBoneAnimation(cat, 'wrong', -1);
		this.playEffect('CoolCatWrong', () => {
			playDragonBoneAnimation(cat, 'normal', -1);
			cb();
		});
	},

	coolCatSpeakEnd(cb) {
		const cat = cc.find('Canvas/bg/catFrame/CoolCat');
		playDragonBoneAnimation(cat, 'finish', -1);
		this.playAudioByUrl(this.data.endAudio, () => {
			playDragonBoneAnimation(cat, 'normal', -1);
			cb();
		});
	},

	//TODO:copy
	resetGame() {
		this.initData();
		this.initView();
		this.initListener();
		this.hideRestartBtn();
	},

	showRestartBtn() {
		const btn = cc.find('Canvas/bg/btnReplay');
		btn.active = true;
		btn.off('click');
		btn.on('click', () => {
			const middleLayer = cc.find('middleLayer');
			if (middleLayer) {
				middleLayer.getComponent('middleLayer').reloadBundle();
			} else {
				console.log('没有middleLayer');
				//TODO:copy 重置游戏
				this.resetGame();
			}
		});

		const circle = cc.find('Canvas/bg/btnReplay/bg_circle');
		cc.tween(circle)
			.set({ scale: 0.8, opacity: 255 })
			.to(2, { scale: 1.2, opacity: 0 })
			.union()
			.repeatForever()
			.start();
	},

	hideRestartBtn() {
		console.log('hideRestartBtn');
		const btn = cc.find('Canvas/bg/btnReplay');
		btn.active = false;

		const circle = cc.find('Canvas/bg/btnReplay/bg_circle');
		circle.stopAllActions();
		circle.scale = 0.8;
		circle.opacity = 255;
	},
















	// ------------------------------------------------
	loadSpriteByUrl(node, url, cb) {
		cc.loader.load({ url }, (err, img) => {
			if (!node) cb && cb();
			const spriteFrame = new cc.SpriteFrame(img)
			const spr = node.getComponent(cc.Sprite);
			spr.spriteFrame = spriteFrame;
			if (cb) cb(img);
		});
	},

	currentPlayedAudioId: null,
	stopCurrentPlayedAudio() {
		if (this.currentPlayedAudioId !== null) {
			cc.audioEngine.stop(this.currentPlayedAudioId);
			this.currentPlayedAudioId = null;
		}
	},
	playEffect(name, cb) {
		this.stopCurrentPlayedAudio();
		const audioNode = cc.find(`audios/${name}`);
		const audioClip = audioNode.getComponent(cc.AudioSource).clip;
		const audioId = cc.audioEngine.play(audioClip, false, 0.8);
		this.currentPlayedAudioId = audioId;
		if (cb) {
			cc.audioEngine.setFinishCallback(audioId, cb);
		}
	},
	playAudioByUrl(audio_url, cb = null) {
		if (!audio_url) {
			if (cb) {
				cb();
			}
			return;
		}
		this.stopCurrentPlayedAudio();
		cc.assetManager.loadRemote(audio_url.toLowerCase(), (err, audioClip) => {
			const audioId = cc.audioEngine.play(audioClip, false, 0.8);
			this.currentPlayedAudioId = audioId;
			if (cb) {
				cc.audioEngine.setFinishCallback(audioId, cb);
			}
		});
	},
});
