GameScene = Object.extend(Object)

function GameScene:new()
end

function GameScene:init()
	GameScene:playerChanged(currentPlayer)
	movementDelta = 0

	love.audio.setPosition( windowWidth/2, windowHeight/2,0)

	pSystem = love.graphics.newParticleSystem(boosterParticle,128)
	pSystem:setParticleLifetime(0,0.6)
	pSystem:setLinearAcceleration(0,20,0,25)
	pSystem:setSpeed(40,50)
	pSystem:setRotation(10,20)
	pSystem:setSpin(10,20)
	pSystem:setRadialAcceleration(10,20)
	pSystem:setTangentialAcceleration(10,20)
	pSystem:setSizeVariation(0.3)
	pSystem:setSizes(1,0.9,0.8,0.7,0.5,0.3,0.1,0.05)
	pSystem:setColors(
		1,1,1,1,
		1,1,1,1,
		1,1,1,1,
		1,1,1,0.8,
		1,1,1,0.6,
		1,1,1,0.5,
		1,1,1,0.4,
		1,1,1,0.3
	)

	eSystem = love.graphics.newParticleSystem(explosionParticle,64)
	eSystem:setParticleLifetime(0,0.7)
	eSystem:setLinearAcceleration(-2,-2,2,2)
	eSystem:setSpeed(2,8)
	eSystem:setRotation(1,7)
	eSystem:setSpin(1,2)
	eSystem:setRadialAcceleration(10,20)
	eSystem:setTangentialAcceleration(10,20)
	eSystem:setSizeVariation(0.9)
	eSystem:setSizes(0.1, 0.2, 0.4, 0.6, 0.8, 1.0, 0.6, 0.1)
	eSystem:setColors(
		1,1,1,1,
		1,1,1,1,
		1,1,1,1,
		1,1,1,1,
		1,1,1,0.8,
		1,1,1,0.6,
		1,1,1,0.4,
		1,1,1,0.3
	)

	GameScene.bullets = {}

	GameScene.explosionObj = {angle=100, radius=100}
	GameScene.godsrayObj = {weight=0}

	currentPlanet:init()
	currentPlanet:draw()
end

function GameScene:update(dt)

	local bLen = table.getn(GameScene.bullets)
	if bLen > 0 then
		for y=1, bLen do
			if GameScene.bullets[bLen-(y-1)].finished then
				table.remove(GameScene.bullets, bLen-(y-1))
			end
		end
	end

	if currentPlayer.death == false and currentPlanet.hasGeneratedMap == true then
		pSystem:update(dt)

		GameScene:updateInput(dt)
		GameScene:updateBounds(dt)

		bLen = table.getn(GameScene.bullets)
		if bLen > 0 then
			for y=1, bLen do
				GameScene.bullets[y]:update(dt)
			end
		end

		GameScene:checkCollisions()
	else
		eSystem:update(dt)
	end

	currentPlanet:update(dt)
	self.updateEffects();
end

function GameScene:draw()
	love.graphics.setColor(1,1,1, 1)

	if currentPlanet ~= nil and currentPlanet.canvas ~= nil then
		love.graphics.draw(currentPlanet.canvas,0,0)
	end

	if currentPlayer.death == false then
		love.graphics.setColor(1,1,1, 1)
		love.graphics.draw(pSystem, currentPlayer.px-2, currentPlayer.py)
		love.graphics.draw(pSystem, currentPlayer.px+2, currentPlayer.py)
		love.graphics.draw(
			currentPlayer.ship.image,
			currentPlayer.px,
			currentPlayer.py,
			currentPlayer.rot*(math.pi/180),
			1, 1,
			currentPlayer.ship.image:getWidth()/2,
			currentPlayer.ship.image:getHeight()/2
		)

		local bLen = table.getn(GameScene.bullets)
		if bLen > 0 then
			for y=1, bLen do
				GameScene.bullets[y]:draw()
			end
		end
	else
		love.graphics.draw(eSystem, currentPlayer.px, currentPlayer.py)

		local logoWidth = gameoverLogo:getWidth()
		local logoHeight = gameoverLogo:getHeight()
		love.graphics.setColor(1,1,1,GameScene.logoScale.a)
		love.graphics.draw(
			gameoverLogo,
			(windowWidth - logoWidth) / 2,
			(windowHeight-logoHeight) / 2,
			0,
			GameScene.logoScale.x,
			GameScene.logoScale.y
		)
	end
end

function GameScene:drawHud()

	love.graphics.setColor(1,1,1, 1)
	love.graphics.draw( gameHud, 0, 600-66 )

	love.graphics.setColor(255,255,255, 0.75)
	love.graphics.draw( currentPlayer.image, 14, 550, 0, 0.5, 0.5 )

	love.graphics.setColor( text.r, text.g, text.b, text.alpha )
	love.graphics.print( currentPlayer.name, 48, 550 )
	love.graphics.print( currentPlayer:getShipname(), 48, 566 )

	love.graphics.print(
		"glbl: " .. currentPlayer.px..","..currentPlayer.py.." s: " .. currentPlayer.ship.speed .. " a: " ..currentPlayer.acc,
		10,10
	)

	local deathval = "0"
	if currentPlayer.death then
		deathval = "1"
	end

	love.graphics.print( "death: " .. deathval, 10, 24 )
	love.graphics.print( "wpnrot: " .. currentPlayer.ship.weaponrot .. " cd: " .. currentPlayer.ship.cooldown, 70, 24 )

	local bLen = table.getn(GameScene.bullets)
	love.graphics.print( "bul: " .. bLen, 10, 38 )
end

function GameScene:keypressed(key,unicode)
	if key == "1" then
		GameScene:playerChanged(CaptainSteve)
	elseif key == "2" then
		GameScene:playerChanged(CaptainRobert)
	elseif key == "3" then
		GameScene:playerChanged(CaptainJohn)
	end
end

function GameScene:playerChanged(to)
	currentPlayer = to
	currentPlayer.px = math.floor(windowWidth/2)
	currentPlayer.py = math.floor(windowHeight/2)
	currentPlayer.rot = 0
	currentPlayer.acc = 0
	currentPlayer.bounds = { x1= 20, y1= 20, x2= windowWidth-20, y2= windowHeight - 86}
	currentPlayer.death = false
end

function GameScene:updateInput(dt)
	movementDelta = movementDelta + dt
	if (movementDelta > 0.02) then
		movementDelta = 0

		local isUp = false
		local isLeft = false
		local isDown = false
		local isRight = false

		local isBUp = false
		local isBLeft = false
		local isBDown = false
		local isBRight = false

		isUp = love.keyboard.isDown( "w" )
		isDown = love.keyboard.isDown( "s" )
		isLeft = love.keyboard.isDown( "a" )
		isRight = love.keyboard.isDown( "d" )

		isBUp = love.keyboard.isDown( "up" )
		isBDown = love.keyboard.isDown( "down" )
		isBLeft = love.keyboard.isDown( "left" )
		isBRight = love.keyboard.isDown( "right" )

		if isUp and isLeft then
			currentPlayer.rot = 315
			particleRot = 45
		elseif isUp and isRight then
			currentPlayer.rot = 45
			particleRot = 135
		elseif isUp then
			currentPlayer.rot = 0
			particleRot = 90
		elseif isDown and isLeft then
			currentPlayer.rot = 225
			particleRot = 315
		elseif isDown and isRight then
			currentPlayer.rot = 135
			particleRot = 225
		elseif isDown then
			currentPlayer.rot = 180
			particleRot = 270
		elseif isLeft then
			currentPlayer.rot = 270
			particleRot = 0
		elseif isRight then
			currentPlayer.rot = 90
			particleRot = 180
		end

		if isUp or isDown or isLeft or isRight then
			currentPlayer.acc = currentPlayer.acc + currentPlayer.ship.accIncr
		elseif currentPlayer.acc > 0 then
			currentPlayer.acc = currentPlayer.acc - currentPlayer.ship.accIncr
		end

		currentPlayer.acc = math.clamp(0, currentPlayer.acc, 1)

		if currentPlayer.acc > 0 then
			pSystem:setDirection(particleRot*(math.pi/180))
			pSystem:emit( 64 * currentPlayer.acc )
		end

		if isUp then
			currentPlayer.py = math.floor(currentPlayer.py - (currentPlayer.ship.speed*currentPlayer.acc))
		end

		if isDown then
			currentPlayer.py = math.floor(currentPlayer.py + (currentPlayer.ship.speed*currentPlayer.acc))
		end

		if isLeft then
			currentPlayer.px = math.floor(currentPlayer.px - (currentPlayer.ship.speed*currentPlayer.acc))
		end

		if isRight then
			currentPlayer.px = math.floor(currentPlayer.px + (currentPlayer.ship.speed*currentPlayer.acc))
		end

		love.audio.setPosition( currentPlayer.px, currentPlayer.py,0)

		if isBUp and isBLeft then
			currentPlayer.ship.weaponrot = 135
		elseif isBUp and isBRight then
			currentPlayer.ship.weaponrot = 45
		elseif isBUp then
			currentPlayer.ship.weaponrot = 90
		elseif isBDown and isBLeft then
			currentPlayer.ship.weaponrot = 225
		elseif isBDown and isBRight then
			currentPlayer.ship.weaponrot = 315
		elseif isBDown then
			currentPlayer.ship.weaponrot = 270
		elseif isBLeft then
			currentPlayer.ship.weaponrot = 180
		elseif isBRight then
			currentPlayer.ship.weaponrot = 0
		end

		if currentPlayer.ship.cooldown == 0 then
			if isBUp or isBDown or isBLeft or isBRight then
				currentPlayer.ship.cooldown = currentPlayer.ship.cooldownPeriod

				local bullet = Bullet( currentPlayer )
				bullet:emit( currentPlayer.px, currentPlayer.py, 0, 0, currentPlayer.ship.weaponrot, 0.5 )
				table.insert(GameScene.bullets, bullet)
			end
		end

		currentPlayer.ship.cooldown = math.clamp( 0, currentPlayer.ship.cooldown-dt, currentPlayer.ship.cooldownPeriod )
	end
end

function GameScene:updateBounds(dt)
	currentPlayer.px = math.floor(math.clamp( currentPlayer.bounds.x1,  currentPlayer.px, currentPlayer.bounds.x2 ))
	currentPlayer.py = math.floor(math.clamp( currentPlayer.bounds.y1,  currentPlayer.py, currentPlayer.bounds.y2 ))
end

function GameScene:checkCollisions()
	-- Get basic alpha blended collision
	local cp = currentPlanet.canvas:newImageData( nil, nil, currentPlayer.px, currentPlayer.py, 1, 1):getPixel( 0,0 )
	if cp == 0 then
		currentPlayer.death = true
		self:generateExplosion( currentPlayer.px, currentPlayer.py )
		self:generateLogoEffect()
	end
end

function GameScene:generateLogoEffect()
	GameScene.logoScale = {x= 0.6, y= 0.6, a= 0}
	flux.to(GameScene.logoScale, 0.5, {x= 1, y= 1, a= 1}):ease("quintout"):delay(0.5)
end

function GameScene:generateExplosion(px,py)
	GameScene:generateExplosionSound(px,py)
	GameScene.explosionObj = {angle=100, radius=100}
	GameScene.godsrayObj = {weight=0}

	flux.to(GameScene.explosionObj, 0.5, {
		angle= math.variance(100,90),
		radius=math.variance(1600, 150)
	}):ease("quintout"):after( GameScene.explosionObj, 0.5, { angle= 100, radius= 100 })

	flux.to(GameScene.godsrayObj, 0.5, {
		weight=math.variance(100,50)
	}):ease("quintout"):after( GameScene.godsrayObj, 0.5, { weight=1 })

	eSystem:emit(32)
end

function GameScene:updateEffects()
	effect.chromasep.angle= math.floor(GameScene.explosionObj.angle/100)
	effect.chromasep.radius= math.floor(GameScene.explosionObj.radius/100)
	effect.godsray.weight= GameScene.godsrayObj.weight/100
end

function GameScene:generateExplosionSound(px,py)
	local sound = sfxr.newSound()
	sound:resetParameters()
	sound.waveform = sfxr.WAVEFORM.NOISE
	sound.frequency.start = math.variance(0.19907648104897,150)
	sound.frequency.slide = -0.057634852747835
	sound.repeatspeed = 0
	sound.envelope.attack = 0
	sound.envelope.sustain = math.variance(0.30484231377123, 150)
	sound.envelope.punch = math.variance(0.7393770288859, 150)
	sound.envelope.decay = 0.43495283918775
	sound.phaser.offset = math.variance(0.53418301267674, 150)
	sound.phaser.sweep = -0.26648187020582
	sound.vibrato.depth = math.variance(0.24860915303688, 150)
	sound.vibrato.speed = 0.44703997451237
	sound.change.speed = 0.83105037145914
	sound.change.amount = -0.66873272021076

	local soundData = sound:generateSoundData()
	local source = love.audio.newSource(soundData)
	source:setVolume(1)
	source:setPosition(px,py)
	source:play()
end
