----------------------------------------------------------------------------- -- This switch debouncer circuit, which can be used for multiple switches, is -- based upon Dr. Andrew Greensted's VHDL code available at -- http://www.labbookpages.co.uk/electronics/debounce.html. The circuit has -- been modified so that the output (a bit of switchesOut) goes high for one -- clock cycle when the switch is determined to have made the open to closed -- transition. This is accomplished with the two-bit shift register process -- below. In the original circuit, the output remained high until the switch -- made the closed to open transition. -- -- Nothing in this module should be modified. ----------------------------------------------------------------------------- library ieee; use ieee.std_logic_1164.all; use ieee.numeric_std.all; entity SwitchDebouncerTrans is generic (CLK_FREQ : positive; NUM_SWITCHES : positive); port ( clk : in std_logic; reset : in std_logic; switchesIn : in std_logic_vector(NUM_SWITCHES-1 downto 0); switchesOut : out std_logic_vector(NUM_SWITCHES-1 downto 0)); end SwitchDebouncerTrans; architecture Structural of SwitchDebouncerTrans is signal sample : std_logic; begin SampleGen : process(clk) constant SAMPLE_COUNT_MAX : integer := (CLK_FREQ / 2000) - 1; -- 500 us variable counter : integer range 0 to SAMPLE_COUNT_MAX; begin if (clk'event and clk='1') then if (reset='1') then sample <= '0'; counter := 0; else if (counter=SAMPLE_COUNT_MAX) then counter := 0; sample <= '1'; else sample <= '0'; counter := counter + 1; end if; end if; end if; end process; DebounceGen : for sw in 0 to NUM_SWITCHES-1 generate constant PULSE_COUNT_MAX : integer := 20; signal sync : std_logic_vector(1 downto 0); signal counter : integer range 0 to PULSE_COUNT_MAX; signal swInternal : std_logic; signal shift : std_logic_vector(1 downto 0); begin switchesOut(sw) <= not shift(1) and shift(0); shiftReg : process(clk) begin if (clk'event and clk='1') then if (reset='1') then shift <= (others => '0'); else shift <= shift(0) & swInternal; end if; end if; end process; Debounce : process(clk) begin if (clk'event and clk='1') then if (reset='1') then sync <= (others => '0'); counter <= 0; swInternal <= '0'; else sync <= sync(0) & switchesIn(sw); if (sync(1)='0') then -- Switch not pressed counter <= 0; swInternal <= '0'; elsif(sample = '1') then -- Switch pressed if (counter=PULSE_COUNT_MAX) then swInternal <= '1'; else counter <= counter + 1; end if; end if; end if; end if; end process; end generate; end Structural;