//
//  Layer.h
//  PixelKit
//
//  Copyright (c) 2014 César Parent. All rights reserved.
//
#ifndef _LAYER_H
#define _LAYER_H

#include <vector>
#include "includes.h"
#include "Node.h"
#include "Color.h"
#include "Collision.h"

namespace PixelKit
{
	class Game;
	
	/*!
	 * @class PixelKit::Layer
	 * @brief Layer is a node that draws its children node on a texture before
	 * rendering the texture on the current scene.
	 * @namespace PixelKit
	 */
	class Layer : public Node
	{
	public:
		
		/*!
		 * @brief Layer Constructor. The newly created Layer uses the games
		 * renderer to create a target texture to draw in, with the given size.
		 *
		 * @param game Game director object.
		 * @param xSize Width of the new Layer.
		 * @param ySize Height of the new Layer.
		 */
		Layer(Game &game, int xSize, int ySize);
		
		/*!
		 * @brief Layer destructor.
		 */
		virtual ~Layer();
		
		/*!
		 * @brief Adds a Node to the layer's children tree
		 * @param child Node to add to the Layer
		 */
		virtual void addChild(Node* child);
		
		/*!
		 * @brief Removes a node from the Layer.
		 * @param child Node to remove from the Layer.
		 */
		virtual void removeChild(Node *child);
		
		/*!
		 * @brief Commits the changes made to the children tree during a
		 * frame. Added and deleted Nodes are stored in buffer vectors, and
		 * updateTree() is called after the node has finished rendering.
		 */
		virtual void updateTree();
		
		/*!
		 * @brief Returns the texture used as a drawing target by the Layer.
		 */
		virtual SDL_Texture *getTarget();
		
		/*!
		 * @brief Method called before rendering each frame. Any game logic
		 * is added here.
		 *
		 * @param timeInterval time elapsed since last frame in milliseconds.
		 */
		virtual void update(int timeInterval);
		
		/*!
		 * @brief Set the Layer's background color.
		 * @param color Layer's new background color.
		 */
		virtual void setBackgroundColor(Color color);
		
		/*!
		 * @brief Layer's background color getter.
		 */
		const Color &backgroundColor;
		
		/*!
		 * @brief Wether Layer should attempt to collide nodes.
		 */
		virtual void collideChildren(bool collide)
		{
			_collideChildren = collide;
		}
		
	protected:
		
		/*!
		 * @brief Layer's background color.
		 */
		Color _backgroundColor;
		
		/*!
		 * @brief Layer's texture to render to.
		 */
		SDL_Texture *_target;
		
		/*!
		 * @brief Game director reference.
		 */
		Game &_game;
		
		/*!
		 * @brief Layer's children.
		 */
		std::vector<Node*> _children;
		
	protected:
		/*!
		 * @brief Draw Layer to its target texture.
		 * @param renderer Renderer used to draw to the screen.
		 */
		virtual void draw(SDL_Renderer *renderer);
		
		/*!
		 * @brief Collision delegate method called when two nodes have collided.
		 * @param collision Object holding the collision's data.
		 */
		virtual void didCollide(Collision collision){};
		
		/*!
		 * @brief Loop through collidable children and check for collisions.
		 */
		virtual void simulateCollisions();
		
		bool _collideChildren;
		
	private:
		std::vector<Node*> _addBuffer;
		std::vector<Node*> _deleteBuffer;
		
	};
}

#endif