library IEEE; use IEEE.STD_LOGIC_1164.ALL; use IEEE.STD_LOGIC_ARITH.ALL; use IEEE.STD_LOGIC_UNSIGNED.ALL; entity incremental_encoder is Port ( clk : in std_logic; -- Systemtakt A : in std_logic; -- Spur A B : in std_logic; -- Spur B A_OUT : out std_logic; -- Spur A, verlangsamt B_OUT : out std_logic -- Spur B, verlangsamt ); end incremental_encoder; architecture Behavioral of incremental_encoder is constant decoder_A: std_logic_vector(31 downto 0):="00000000111111110000000011111111"; constant decoder_B: std_logic_vector(31 downto 0):="11110000000011111111000000001111"; signal a_in, b_in, a_old, b_old: std_logic; signal ce, up_down, error: std_logic; signal cnt: std_logic_vector(4 downto 0); begin -- Abtastung und Verzoegerung der Quadratursignale process(clk) begin if rising_edge(clk) then a_in <= A; a_old <= a_in; b_in <= B; b_old <= b_in; end if; end process; -- Dekodierung der Eigaenge process(a_in, b_in, a_old, b_old) variable state: std_logic_vector(3 downto 0); begin state := a_in & b_in & a_old & b_old; case state is when "0000" => up_down <= '0'; ce <= '0'; error <= '0'; when "0001" => up_down <= '1'; ce <= '1'; error <= '0'; when "0010" => up_down <= '0'; ce <= '1'; error <= '0'; when "0011" => up_down <= '0'; ce <= '0'; error <= '1'; when "0100" => up_down <= '0'; ce <= '1'; error <= '0'; when "0101" => up_down <= '0'; ce <= '0'; error <= '0'; when "0110" => up_down <= '1'; ce <= '0'; error <= '1'; when "0111" => up_down <= '1'; ce <= '1'; error <= '0'; when "1000" => up_down <= '1'; ce <= '1'; error <= '0'; when "1001" => up_down <= '0'; ce <= '0'; error <= '1'; when "1010" => up_down <= '0'; ce <= '0'; error <= '0'; when "1011" => up_down <= '0'; ce <= '1'; error <= '0'; when "1100" => up_down <= '0'; ce <= '0'; error <= '1'; when "1101" => up_down <= '0'; ce <= '1'; error <= '0'; when "1110" => up_down <= '1'; ce <= '1'; error <= '0'; when "1111" => up_down <= '0'; ce <= '0'; error <= '0'; when others => null; end case; end process; process(clk) variable index: integer; begin if rising_edge(clk) then -- Lokaler Zaehler fuer Taktteilung if ce='1' then if up_down='0' then cnt <= cnt-1; else cnt <= cnt+1; end if; end if; -- Dekodierung der Ausgaenge, ueber Register glitchfrei ausgegeben index := conv_integer(cnt); A_OUT <= decoder_A(index); B_OUT <= decoder_B(index); end if; end process; end Behavioral;