----------------------------------------------------------------------------------
-- Company: 
-- Engineer: 
-- 
-- Create Date: 30.11.2021 10:35:30
-- Design Name: 
-- Module Name: Gene_Snake - Behavioral
-- Project Name: 
-- Target Devices: 
-- Tool Versions: 
-- Description: 
-- 
-- Dependencies: 
-- 
-- Revision:
-- Revision 0.01 - File Created
-- Additional Comments:
-- 
----------------------------------------------------------------------------------
-- a faire:
--  - faire bouger le snake
--  - ajouter une clk

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;

-- Uncomment the following library declaration if using
-- arithmetic functions with Signed or Unsigned values
use IEEE.NUMERIC_STD.ALL;

library ourTypes;
use ourTypes.types.all;

-- Uncomment the following library declaration if instantiating
-- any Xilinx leaf cells in this code.
--library UNISIM;
--use UNISIM.VComponents.all;

entity Gene_Snake is
generic( addressSize : integer:=10);
Port ( X : in unsigned (9 downto 0);
       Y : in unsigned (8 downto 0);
       currentSnake : in pos;
       clk: in std_logic;
       updateOrder : in std_logic;
       reset: in std_logic;
       snakePresent : out std_logic;
       currentAddress : out unsigned(addressSize-1 downto 0));
end Gene_Snake;

architecture Behavioral of Gene_Snake is

-- D???claration des signaux
signal mat: coord; --mat de correspondance "grille d'affichage (x,y)" vers position dans la RAM
signal snakeHere: std_logic; --1 si on doit afficher le pixel 0 sinon
signal dx : signed(1 downto 0);
signal dy : signed(1 downto 0);
signal running : std_logic;

begin


---- Process d'initialisation
--process(mat,snake,reset,current_index)
--variable current_dir : direction;
--begin
--    if(reset='0')
--    then
--        update <= '0';
--        current_index <= to_unsigned(0,11);
--        for x in 0 to 39 loop
--            for y in 0 to 29 loop
--                mat(x,y) <= to_unsigned(snake'length-1,11);
--            end loop;
--        end loop;
        
--        mat(0,0) <= to_unsigned(0,11);
--        mat(1,0) <= to_unsigned(1,11);
        
--        snake(0).X <= to_unsigned(8,10);
--        snake(0).Y <= to_unsigned(8,9);
--        snake(0).dir <= droite;
--        snake(0).isDefined <= '1';
        
--        snake(1).X <= to_unsigned(24,10);
--        snake(1).Y <= to_unsigned(8,9);
--        snake(1).dir <= droite;
--        snake(1).isDefined <= '1';
        
--        for i in 2 to snake'length-1 loop
--            snake(i).X <= to_unsigned(0,10);
--            snake(i).Y <= to_unsigned(0,9);
--            snake(i).dir <= gauche;
--            snake(i).isDefined <= '0';
--        end loop;
--    elsif(clk_rapide'event and clk_rapide = '1')
--    then
--        snake(to_integer(current_index)) <= updatedSnake;
--        current_index <= updatedIndex;
--    end if;
    
--    if (to_integer(current_index) = snake'length) then
--        update <= '0';
--        current_index <= to_unsigned(0,11);
--    end if;
    
--    if(clk_lente'event and clk_lente = '1')
--    then
--        update <= '1';
--    end if;
    
--end process;

-- Process de calcul d'affichage
process(X,Y,clk,mat)
begin
if(reset = '0') then
    dx <= to_signed(0,2);
    dy <= to_signed(0,2);
elsif(clk'event and clk = '1' and running = '1') then
    if(currentSnake.isDefined= '1') then
        if(X>=currentSnake.X-8 and X<=currentSnake.X+8 and Y>=currentSnake.Y-8 and Y<=currentSnake.Y+8) then
            snakeHere <= '1';
        end if;
    end if;
    
    dx <= dx + 1;
    if(dx = 2) then
        dx <= to_signed(-1,2);
        dy <= dy + 1;
    end if;
end if;

if(dy = 2) then
    dy <= to_signed(-1,2);
    running <= '0';
end if;

if(updateOrder'event and updateOrder = '1') then
    running <= '1';
end if;
end process;

currentAddress <= mat(to_integer(X/16)+to_integer(dx),to_integer(Y/16)+to_integer(dy));

snakePresent <= snakeHere;
end Behavioral;
