157 lines
4.5 KiB
VHDL
157 lines
4.5 KiB
VHDL
-- altera vhdl_input_version vhdl_2008
|
|
library ieee;
|
|
use ieee.std_logic_1164.all;
|
|
use ieee.numeric_std.all;
|
|
|
|
|
|
entity PixTrans is
|
|
generic (
|
|
MAX_H : natural;
|
|
MAX_W : natural
|
|
);
|
|
port (
|
|
clk : in std_logic;
|
|
rst_n : in std_logic;
|
|
|
|
lcd_req : in std_logic;
|
|
data : out std_logic_vector(15 downto 0);
|
|
empty : out std_logic;
|
|
|
|
fifo_req : out std_logic;
|
|
fifo_q : in std_logic_vector(31 downto 0);
|
|
fifo_empty : in std_logic;
|
|
|
|
-- Currently configured width/height of the buffer
|
|
w : in natural;
|
|
h : in natural
|
|
);
|
|
end PixTrans;
|
|
|
|
architecture behavioral of PixTrans is
|
|
subtype Pixel is std_logic_vector(15 downto 0);
|
|
|
|
-- Generic constants
|
|
constant BLANK : Pixel := "0000000000000000"; --(others => '0');
|
|
|
|
-- Type definitions
|
|
type PIXEL_SOURCE is (S_BLANK, S_FIFO, S_BUFFER);
|
|
|
|
-- Inferred registers
|
|
signal pixbuf_reg, pixbuf_next : Pixel;
|
|
signal pixbufvalid_reg, pixbufvalid_next : boolean;
|
|
signal pos_x_reg, pos_x_next : integer range 1 to MAX_W;
|
|
signal pos_y_reg, pos_y_next : integer range 1 to MAX_H;
|
|
signal pix_src_reg, pix_src_next : PIXEL_SOURCE;
|
|
signal finished_next, finished_reg : std_logic;
|
|
|
|
-- Convenience signals
|
|
signal inBlankArea_reg, inBlankArea_next : boolean;
|
|
signal lcd_req_delayed_reg : std_logic;
|
|
|
|
begin
|
|
|
|
-- Update cursor
|
|
process(all) begin
|
|
finished_next <= finished_reg;
|
|
pos_y_next <= pos_y_reg;
|
|
pos_x_next <= pos_x_reg;
|
|
|
|
if lcd_req_delayed_reg = '1' then
|
|
if pos_x_reg = MAX_W and pos_y_reg = MAX_H then
|
|
pos_x_next <= 1;
|
|
pos_y_next <= 1;
|
|
|
|
elsif pos_x_reg = MAX_W then
|
|
pos_x_next <= 1;
|
|
pos_y_next <= pos_y_reg + 1;
|
|
else
|
|
pos_x_next <= pos_x_reg + 1;
|
|
end if;
|
|
|
|
if pos_x_reg = MAX_W and pos_y_reg = MAX_H then
|
|
finished_next <= '1' and not finished_reg;
|
|
else
|
|
finished_next <= '0';
|
|
end if;
|
|
end if;
|
|
inBlankArea_next <= pos_y_next > h or pos_x_next > w;
|
|
end process;
|
|
|
|
|
|
-- Data process
|
|
process(all) begin
|
|
pix_src_next <= pix_src_reg;
|
|
pixbufvalid_next <= pixbufvalid_reg;
|
|
|
|
-- FIFO output signals
|
|
fifo_req <= '0';
|
|
|
|
if lcd_req_delayed_reg = '1' then
|
|
if inBlankArea_next then
|
|
pix_src_next <= S_BLANK;
|
|
elsif pixbufvalid_reg then
|
|
-- Has valid pixel in pixel buffer
|
|
pix_src_next <= S_BUFFER;
|
|
pixbufvalid_next <= false;
|
|
else
|
|
|
|
fifo_req <= '1';
|
|
|
|
-- fifo_req should be kept high until pixel is available
|
|
if fifo_empty = '0' then
|
|
-- Must request pixel from FIFO
|
|
pix_src_next <= S_FIFO;
|
|
pixbufvalid_next <= true;
|
|
end if;
|
|
end if;
|
|
end if;
|
|
|
|
end process;
|
|
|
|
-- Data request multiplexer (pixel source)
|
|
with pix_src_reg select data <=
|
|
BLANK when S_BLANK,
|
|
fifo_q(15 downto 0) when S_FIFO,
|
|
pixbuf_reg when S_BUFFER;
|
|
|
|
|
|
-- Fill pixel buffer with the upper half word of the input FIFO word when
|
|
-- reading from the fifo
|
|
pixbuf_next <= fifo_q(31 downto 16) when pix_src_reg = S_FIFO else pixbuf_reg;
|
|
|
|
-- LCD Controller empty signal
|
|
process(all) begin
|
|
if fifo_empty = '1' then
|
|
empty <= '1';
|
|
else
|
|
empty <= finished_reg;
|
|
end if;
|
|
end process;
|
|
|
|
-- Clocking process/register inferrence
|
|
process(clk) begin
|
|
if rising_edge(clk) then
|
|
if rst_n = '0' then
|
|
pos_x_reg <= 1;
|
|
pos_y_reg <= 1;
|
|
pixbuf_reg <= BLANK;
|
|
pixbufvalid_reg <= false;
|
|
pix_src_reg <= S_BLANK;
|
|
inBlankArea_reg <= false;
|
|
finished_reg <= '0';
|
|
lcd_req_delayed_reg <= '0';
|
|
else
|
|
pos_x_reg <= pos_x_next;
|
|
pos_y_reg <= pos_y_next;
|
|
pixbuf_reg <= pixbuf_next;
|
|
pixbufvalid_reg <= pixbufvalid_next;
|
|
pix_src_reg <= pix_src_next;
|
|
inBlankArea_reg <= inBlankArea_next;
|
|
finished_reg <= finished_next;
|
|
lcd_req_delayed_reg <= lcd_req;
|
|
end if;
|
|
end if;
|
|
end process;
|
|
|
|
|
|
end behavioral ; -- behavioral |