/**
 * ʒ[Ŕ˂e𔭎˂
 * x傫Aˈʒǔ덷傫Ȃ
 * 
 * @param {Integer} x         exW
 * @param {Integer} y         eyW
 * @param {Integer} speed     x
 * @param {Integer} angle     px
 * @param {Integer} graph     摜
 * @param {Integer} delay     xt[
 * @param {Array}   refflag   EEEEŔ˂邩(zœB1Ŕ)
 * @param {Integer} refnumber ˉ
 */
task ReflectShot(x,y,speed,angle,graph,delay,refflag,refnumber){
	let refnum = refnumber;
	
	let obj = Obj_Create(OBJ_SHOT);
	Obj_SetPosition(obj,x,y);
	Obj_SetSpeed(obj,speed);
	Obj_SetAngle(obj,angle);
	ObjShot_SetGraphic(obj,graph);
	ObjShot_SetDelay(obj,delay);
	
	while( !Obj_BeDeleted(obj) ){
		if( (Obj_GetX(obj) <= GetClipMinX() && refflag[0] == 1 && refnum > 0) || (Obj_GetX(obj) >= GetClipMaxX() && refflag[2] == 1 && refnum > 0) ){
			if(refnum > 1){
				Obj_SetAngle(obj, 180 - Obj_GetAngle(obj) );
				refnum -= 1;
			}else{
				CreateShot01( Obj_GetX(obj),Obj_GetY(obj),speed,180 - Obj_GetAngle(obj),graph,0 );
				Obj_Delete(obj);
			}
		}
		
		if( (Obj_GetY(obj) <= GetClipMinY() && refflag[1] == 1 && refnum > 0) || (Obj_GetY(obj) >= GetClipMaxY() && refflag[3] == 1 && refnum > 0) ){
			if(refnum > 1){
				Obj_SetAngle(obj, -Obj_GetAngle(obj) );
				refnum -= 1;
			}else{
				CreateShot01( Obj_GetX(obj),Obj_GetY(obj),speed,-Obj_GetAngle(obj),graph,0 );
				Obj_Delete(obj);
			}
		}
		
		yield;
	}
}

/**
 * ʒ[Ŕ˂郌[U[𔭎˂
 * x傫Aˈʒǔ덷傫Ȃ
 * 
 * @param {Integer} x         exW
 * @param {Integer} y         eyW
 * @param {Integer} speed     x
 * @param {Integer} angle     px
 * @param {Integer} lng       [U[̒
 * @param {Integer} wid       [U[̕
 * @param {Integer} graph     摜
 * @param {Integer} delay     xt[
 * @param {Array}   refflag   EEEEŔ˂邩(zœB1Ŕ)
 * @param {Integer} refnumber ˉ
 */
task RefrectLaser(x,y,speed,angle,lng,wid,graph,delay,refflag,refnumber){
	let refnum = refnumber;
	
	let vLng = 0;
	
	let mx = speed * cos(angle);
	let my = speed * sin(angle);
	
	let vx = x;
	let vy = y;
	
	let obj = Obj_Create(OBJ_LASER);
	Obj_SetPosition(obj,x,y);
	Obj_SetSpeed(obj,speed);
	Obj_SetAngle(obj,angle);
	ObjShot_SetGraphic(obj,graph);
	ObjShot_SetDelay(obj,delay);
	
	ObjLaser_SetLength(obj,0);
	ObjLaser_SetWidth(obj,wid);
	ObjLaser_SetSource(obj,false);
	
	while( !Obj_BeDeleted(obj) ){
		if( vLng < lng ){
			vLng += speed;
			ObjLaser_SetLength(obj,vLng);
		}else{
			vLng = lng;
			vx += mx;
			vy += my;
		}
		
		Obj_SetPosition(obj,vx,vy);
		
		if( (ObjLaser_GetEndX(obj) <= GetClipMinX() && refflag[0] == 1 && refnum > 0) || (ObjLaser_GetEndX(obj) >= GetClipMaxX() && refflag[2] == 1 && refnum > 0) ){
			RefrectLaser(ObjLaser_GetEndX(obj),ObjLaser_GetEndY(obj),speed,180 - angle,lng,wid,graph,0,refflag,refnumber - 1);
			refnum = 0;
		}
		
		if( (ObjLaser_GetEndY(obj) <= GetClipMinY() && refflag[1] == 1 && refnum > 0) || (ObjLaser_GetEndY(obj) >= GetClipMaxY() && refflag[3] == 1 && refnum > 0) ){
			RefrectLaser(ObjLaser_GetEndX(obj),ObjLaser_GetEndY(obj),speed,-angle,lng,wid,graph,0,refflag,refnumber - 1);
			refnum = 0;
		}
		
		yield;
	}
}

/**
 * d͂ŉe𔭎˂
 * pxAd͊px͐Ίpxw(SetShotDirectionTypȅԂɂ͊֌WȂ)
 * 
 * @param {Integer} x        exW
 * @param {Integer} y        eyW
 * @param {Integer} speed    x
 * @param {Integer} angle    px
 * @param {Integer} graph    摜
 * @param {Integer} delay    xt[
 * @param {Integer} grvspeed d͉x
 * @param {Integer} grvangle d͊px
 * @param {Integer} maxspeed ő呬x
 */
function GravityShot(x,y,speed,angle,graph,delay,grvspeed,grvangle,maxspeed){
	let xSpeed = speed * cos(angle);
	let ySpeed = speed * sin(angle);
	let accXSpeed = grvspeed * cos(grvangle);
	let accYSpeed = grvspeed * sin(grvangle);
	let maxXSpeed = [maxspeed,-maxspeed][accXSpeed < 0];
	let maxYSpeed = [maxspeed,-maxspeed][accYSpeed < 0];
	
	CreateShot12(x,y,xSpeed,ySpeed,accXSpeed,accYSpeed,maxXSpeed,maxYSpeed,graph,delay);
}

/**
 * d͂ŉe𔭎˂֐Obj
 * pxAd͊px͐Ίpxw(SetShotDirectionTypȅԂɂ͊֌WȂ)
 * 
 * @param {Integer} x        exW
 * @param {Integer} y        eyW
 * @param {Integer} speed    x
 * @param {Integer} angle    px
 * @param {Integer} graph    摜
 * @param {Integer} delay    xt[
 * @param {Integer} grvspeed d͉x
 * @param {Integer} grvangle d͊px
 * @param {Integer} maxspeed ő呬x
 * @returns {Object} 쐬IuWFNgid
 */
function GravityShotObj(x,y,speed,angle,graph,delay,gspeed,gangle,maxspeed){
	let obj = Obj_Create(OBJ_SHOT);
	Obj_SetPosition(obj,x,y);
	Obj_SetSpeed(obj,speed);
	Obj_SetAngle(obj,angle);
	ObjShot_SetGraphic(obj,graph);
	ObjShot_SetDelay(obj,delay);
	
	ObjShot_SetGravity(obj,speed,angle,delay,gspeed,gangle,maxspeed);
	
	return obj;
}

/**
 * Ώۂ̃IuWFNgeɏd͉
 * 
 * @param {Object}  obj      Ώۂ̃IuWFNge
 * @param {Integer} speed    x
 * @param {Integer} angle    px
 * @param {Integer} delay    xt[
 * @param {Integer} grvspeed d͉x
 * @param {Integer} grvangle d͊px
 * @param {Integer} maxspeed ő呬x
 */
task ObjShot_SetGravity(obj,speed,angle,delay,gspeed,gangle,maxspeed){
	let ox = speed * cos(angle);
	let oy = speed * sin(angle);
	let vx = gspeed * cos(gangle);
	let vy = gspeed * sin(gangle);
	
	loop(delay){
		yield;
	}
	
	while( !Obj_BeDeleted(obj) ){
		ox += vx;
		oy += vy;
		
		speed = (ox ^ 2 + oy ^ 2) ^ 0.5;
		
		if( speed > maxspeed ){
			speed = maxspeed;
		}
		
		angle = atan2(oy,ox);
		
		Obj_SetSpeed(obj,speed);
		Obj_SetAngle(obj,angle);
		
		yield;
	}
}
