⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tlc549.vhd

📁 是一些很好的FPGA设计实例
💻 VHD
字号:

--文件名:tlc549.vhd

--功  能:数字电压表

--说  明:学习模数转换芯片(tlc549)的使用

--        通过修改竞赛板上电位器的抽头值可以达到修改当前电压值的目的

--        发光二极管上显示的是模数转换后的数字量

--        数码管上显示的是当前电压值

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;

entity tlc549 is
    Port (clk : in std_logic;						--50m系统时钟
		din : in std_logic;		                    --(tlc549)串行数据输出端
		clk_tlc549 : out std_logic;
          cs_tlc549  : out std_logic;				--tlc549的片选信号输入端
		shift      : out std_logic_vector(3 downto 0);--动态扫描时的位选信号			
		cs_led     : out std_logic_vector(1 downto 0);--竞赛板的发光二极管及数码管的片选信号输入端
		dout_led   : out std_logic_vector(7 downto 0));--竞赛板的发光器件的信号输出端
end tlc549;

architecture Behavioral of tlc549 is

type state is (st1,st2);
signal current_state : state;

type state1 is (st0,st1,st2);
signal current_state1 : state1; 

type state2 is (st0,st1,st2,st3,st4);
signal current_state2 : state2; 

signal reg_datain : std_logic_vector(7 downto 0);
signal reg_dout : std_logic_vector(15 downto 0);
signal dout : std_logic_vector(4 downto 0);
signal reg_din : integer range 0 to 80000;
signal clk1m,clk1k,clk100 : std_logic;
begin
--分频部分
process(clk)						      --产生1MHz的频率
variable cnt : integer range 0 to 50;
begin
   if clk'event and clk='1' then cnt:=cnt+1;
      if cnt<50 then 
	    if cnt<25 then clk1m<='0';
	    else clk1m<='1';
	    end if;
	 else cnt:=0;
	 end if;
   end if;
end process;

process(clk1m)						      --产生1KHz的频率
variable cnt : integer range 0 to 1000;
begin
   if clk1m'event and clk1m='1' then cnt:=cnt+1;
      if cnt<1000 then 
	    if cnt<500 then clk1k<='0';
	    else clk1k<='1';
	    end if;
	 else cnt:=0;
      end if;
   end if;
end process;

process(clk1k)							 --产生100Hz的频率
variable cnt : integer range 0 to 10;
begin
   if clk1k'event and clk1k='1' then cnt:=cnt+1;
      if cnt<10 then 
	    if cnt<5 then clk100<='0';
	    else clk100<='1';
	    end if;
      else cnt:=0;
	 end if;
   end if;
end process;

--tlc549的控制部分
process(clk1k)
variable cnt : integer range 0 to 7;
variable datain : std_logic_vector(7 downto 0);
begin
   if clk1k'event and clk1k='1' then
      case current_state is
      when st1=>									  --将数据进行串并转换
	            cs_tlc549<='0';
			  datain:=datain(6 downto 0)&din;			  --将读取的数据向高位移位
			  clk_tlc549<='1';
			  current_state<=st2;
      when st2=>
	            cs_tlc549<='0';
			  clk_tlc549<='0';
			  current_state<=st1;
			  if cnt<7 then cnt:=cnt+1;				  --读取8位数据
			  else cnt:=0;
			       reg_din<=conv_integer(datain)*195;       --每单位数字量乘以系数=当前电压值;
				  reg_datain<=not(datain);
			  end if;
      when others=>
	            current_state<=st1;
      end case;
   end if;
end process;

--十进制-BCD码转换;
process(clk100)		   
variable reg : integer range 0 to 80000;
variable d1,d2,d3,d4 : std_logic_vector(3 downto 0);
begin
   if clk100'event and clk100='1' then
      case current_state1 is
	 when st0=>
	           reg:=reg_din;
			 d1:="0000";d2:="0000";d3:="0000";d4:="0000";
			 current_state1<=st1;
      when st1=>
	           if reg>9999 then reg:=reg-10000;d1:=d1+1;
			 elsif reg>999 then reg:=reg-1000;d2:=d2+1;
			 elsif reg>99 then reg:=reg-100;d3:=d3+1;
			 elsif reg>9 then reg:=reg-10;d4:=d4+1;
			 else current_state1<=st2;
			 end if;
      when st2=>
			 reg_dout<=d1&d2&d3&d4;
			 current_state1<=st0;
      when others=> 
	           current_state1<=st0;
      end case;
   end if;
end process;

--动态扫描控制;
process(clk1k)
begin
   if clk1k'event and clk1k='1' then
      case current_state2 is
      when st0=>							 --在发光二极管上显示模数转换后的数字量
                cs_led<="01";					 --熄灭数码管
			 shift<="1111";                     
			 dout<="11111";
                current_state2<=st1;
      when st1=>							 --在数码管的最高位显示数据
	           cs_led<="10";					 --熄灭发光二极管
			 shift<="0111";				 --最高位数码管显示
			 dout<='0'&reg_dout(15 downto 12);	 --小数点显示,并且将最高位的数据送给译码器
			 current_state2<=st2;
      when st2=>							 --在数码管的次高位显示数据
	           cs_led<="10";					 --熄灭发光二极管
			 shift<="1011";				 --次高位数码管显示
			 dout<='1'&reg_dout(11 downto 8);	 --小数点不显示,将次高位的数据送给译码器
			 current_state2<=st3;
	 when st3=>							 --在数码管的次低位显示数据
	           cs_led<="10";					 --熄灭发光二极管
			 shift<="1101";				 --次低位数码管显示
			 dout<='1'&reg_dout(7 downto 4);	 --小数点不显示,将次低位的数据送给译码器
			 current_state2<=st4;
      when st4=>							 --在数码管的最低位显示数据
	           cs_led<="10";					 --熄灭发光二极管
			 shift<="1110";				 --最低位数码管显示
			 dout<='1'&reg_dout(3 downto 0);	 --小数点不显示,将最低位的数据送给译码器
			 current_state2<=st0;
      when others=>
	           current_state2<=st0;
	 end case;
   end if;
end process;

--**将BCD码进行8段译码(包括小数点) **--
--**dout(4)代表小数点,低电平点亮  **--
code1: process (dout,reg_datain)                       
begin
   case dout(3 downto 0) is
   when "0000"=>dout_led<=dout(4)&"0000001";
   when "0001"=>dout_led<=dout(4)&"1001111";
   when "0010"=>dout_led<=dout(4)&"0010010";
   when "0011"=>dout_led<=dout(4)&"0000110";
   when "0100"=>dout_led<=dout(4)&"1001100";
   when "0101"=>dout_led<=dout(4)&"0100100";
   when "0110"=>dout_led<=dout(4)&"0100000";
   when "0111"=>dout_led<=dout(4)&"0001111";
   when "1000"=>dout_led<=dout(4)&"0000000";
   when "1001"=>dout_led<=dout(4)&"0000100";
                --"DOUT_LED"送给数码管;
   when others=>dout_led<=reg_datain(7)&reg_datain(0)&reg_datain(1)&reg_datain(2)&reg_datain(3)&reg_datain(4)&reg_datain(5)&reg_datain(6); 
                --"DOUT_LED"送给发光二极管;
   end case;
end process;
end Behavioral;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -