mirror of
https://github.com/Gehstock/Mist_FPGA.git
synced 2026-02-03 15:12:39 +00:00
IremM62: some sprite array optimizations (but still consume huge area)
This commit is contained in:
@@ -27,6 +27,7 @@ entity Graphics is
|
||||
sprite_ctl_i : in to_SPRITE_CTL_t;
|
||||
sprite_ctl_o : out from_SPRITE_CTL_t;
|
||||
spr0_hit : out std_logic;
|
||||
sprite_rgb : in RGB_t;
|
||||
|
||||
graphics_i : in to_GRAPHICS_t;
|
||||
graphics_o : out from_GRAPHICS_t;
|
||||
@@ -113,7 +114,7 @@ begin
|
||||
(
|
||||
bitmap_ctl_o => bitmap_ctl_o_s,
|
||||
tilemap_ctl_o => tilemap_ctl_o_s,
|
||||
sprite_rgb => sprite_ctl_i.rgb,
|
||||
sprite_rgb => sprite_rgb,
|
||||
sprite_set => sprite_ctl_o_s.set,
|
||||
sprite_pri => sprite_pri,
|
||||
|
||||
|
||||
@@ -78,6 +78,7 @@ architecture SYN of PACE is
|
||||
signal from_graphics : from_GRAPHICS_t;
|
||||
signal sprite_prom : prom_a(0 to 31);
|
||||
signal sprite_no : integer range 0 to PACE_VIDEO_NUM_SPRITES-1;
|
||||
signal sprite_rgb : RGB_t;
|
||||
|
||||
begin
|
||||
|
||||
@@ -129,6 +130,7 @@ begin
|
||||
sprite_i => from_sprite_ctl,
|
||||
sprite_o => to_sprite_ctl,
|
||||
spr0_hit => spr0_hit,
|
||||
sprite_rgb => sprite_rgb,
|
||||
graphics_i => from_graphics,
|
||||
graphics_o => to_graphics,
|
||||
|
||||
@@ -167,6 +169,7 @@ begin
|
||||
sprite_ctl_i => to_sprite_ctl,
|
||||
sprite_ctl_o => from_sprite_ctl,
|
||||
spr0_hit => spr0_hit,
|
||||
sprite_rgb => sprite_rgb,
|
||||
|
||||
graphics_i => to_graphics,
|
||||
graphics_o => from_graphics,
|
||||
|
||||
@@ -43,6 +43,7 @@ entity platform is
|
||||
sprite_i : in from_SPRITE_CTL_t;
|
||||
sprite_o : out to_SPRITE_CTL_t;
|
||||
spr0_hit : in std_logic;
|
||||
sprite_rgb : out RGB_t;
|
||||
|
||||
-- various graphics information
|
||||
graphics_i : in from_GRAPHICS_t;
|
||||
@@ -124,6 +125,7 @@ architecture SYN of platform is
|
||||
signal sp_pal_r_wr : std_logic;
|
||||
signal sp_pal_g_wr : std_logic;
|
||||
signal sp_pal_b_wr : std_logic;
|
||||
signal sprite_pal_a : std_logic_vector(7 downto 0);
|
||||
|
||||
-- other signals
|
||||
signal rst_platform : std_logic;
|
||||
@@ -737,6 +739,14 @@ begin
|
||||
);
|
||||
pal_b_wr <= '1' when dl_wr = '1' and dl_addr(11 downto 8) = x"5" else '0'; -- 500-5FF
|
||||
|
||||
sprite_pal_a <= '0' & sprite_i.pal_a(6 downto 0) when
|
||||
hwsel = HW_LDRUN or
|
||||
hwsel = HW_LDRUN2 or
|
||||
hwsel = HW_LDRUN3 or
|
||||
hwsel = HW_LDRUN4 or
|
||||
hwsel = HW_BATTROAD
|
||||
else sprite_i.pal_a;
|
||||
|
||||
-- sprite palettes
|
||||
sp_pal_r : entity work.dpram
|
||||
generic map
|
||||
@@ -754,10 +764,10 @@ begin
|
||||
q_b => open,
|
||||
|
||||
clock_a => not clk_video,
|
||||
address_a => sprite_i.pal_a,
|
||||
address_a => sprite_pal_a,
|
||||
wren_a => '0',
|
||||
data_a => (others => '0'),
|
||||
q_a => sprite_o.rgb.r(9 downto 2)
|
||||
q_a => sprite_rgb.r(9 downto 2)
|
||||
);
|
||||
sp_pal_r_wr <= '1' when dl_wr = '1' and dl_addr(11 downto 8) = x"0" else '0'; -- 000-0FF
|
||||
|
||||
@@ -777,10 +787,10 @@ begin
|
||||
q_b => open,
|
||||
|
||||
clock_a => not clk_video,
|
||||
address_a => sprite_i.pal_a,
|
||||
address_a => sprite_pal_a,
|
||||
wren_a => '0',
|
||||
data_a => (others => '0'),
|
||||
q_a => sprite_o.rgb.g(9 downto 2)
|
||||
q_a => sprite_rgb.g(9 downto 2)
|
||||
);
|
||||
sp_pal_g_wr <= '1' when dl_wr = '1' and dl_addr(11 downto 8) = x"1" else '0'; -- 100-1FF
|
||||
|
||||
@@ -800,10 +810,10 @@ begin
|
||||
q_b => open,
|
||||
|
||||
clock_a => not clk_video,
|
||||
address_a => sprite_i.pal_a,
|
||||
address_a => sprite_pal_a,
|
||||
wren_a => '0',
|
||||
data_a => (others => '0'),
|
||||
q_a => sprite_o.rgb.b(9 downto 2)
|
||||
q_a => sprite_rgb.b(9 downto 2)
|
||||
);
|
||||
sp_pal_b_wr <= '1' when dl_wr = '1' and dl_addr(11 downto 8) = x"2" else '0'; -- 200-2FF
|
||||
|
||||
|
||||
@@ -96,7 +96,6 @@ begin
|
||||
ctl_i(i).ld <= ld_r(i);
|
||||
ctl_i(i).height <= sprite_prom(to_integer(unsigned(reg_o(i).n(9 downto 5))));
|
||||
ctl_i(i).d <= row_d;
|
||||
ctl_i(i).rgb <= (others => (others => '0'));
|
||||
end generate GEN_ROW_D;
|
||||
|
||||
-- Sprite Priority Encoder
|
||||
|
||||
@@ -34,14 +34,13 @@ package sprite_pkg is
|
||||
|
||||
function NULL_TO_SPRITE_REG return to_SPRITE_REG_t;
|
||||
|
||||
subtype SPRITE_ROW_D_t is std_logic_vector(63 downto 0);
|
||||
subtype SPRITE_ROW_D_t is std_logic_vector(23 downto 0);
|
||||
subtype SPRITE_ROW_A_t is std_logic_vector(15 downto 0);
|
||||
|
||||
type to_SPRITE_CTL_t is record
|
||||
ld : std_logic;
|
||||
d : SPRITE_ROW_D_t;
|
||||
height : integer range 0 to 3;
|
||||
rgb : RGB_t;
|
||||
end record;
|
||||
|
||||
type from_SPRITE_CTL_t is record
|
||||
|
||||
@@ -11,7 +11,7 @@ package body sprite_pkg is
|
||||
|
||||
function NULL_TO_SPRITE_CTL return to_SPRITE_CTL_t is
|
||||
begin
|
||||
return ('0', (others => '0'), 0, (others => (others => '0')));
|
||||
return ('0', (others => '0'), 0);
|
||||
end function NULL_TO_SPRITE_CTL;
|
||||
|
||||
function flip_row
|
||||
|
||||
@@ -41,35 +41,35 @@ architecture SYN of spritectl is
|
||||
|
||||
signal ld_r : std_logic;
|
||||
signal left_d : std_logic;
|
||||
signal hblank_r : std_logic;
|
||||
signal rowStore : std_logic_vector(47 downto 0); -- saved row of spt to show during visibile period
|
||||
signal rowCount : unsigned(5 downto 0);
|
||||
-- which part of the sprite is being drawn
|
||||
alias segment : unsigned(1 downto 0) is rowCount(5 downto 4);
|
||||
|
||||
begin
|
||||
|
||||
process (clk, clk_ena, left_d, reg_i)
|
||||
process (clk, clk_ena, left_d, rowCount, reg_i)
|
||||
|
||||
variable pel : std_logic_vector(2 downto 0);
|
||||
variable x : unsigned(video_ctl.x'range);
|
||||
variable y : unsigned(video_ctl.y'range);
|
||||
variable yMat : boolean; -- raster is between first and last line of sprite
|
||||
variable xMat : boolean; -- raster in between left edge and end of line
|
||||
variable pel : std_logic_vector(2 downto 0);
|
||||
variable x : unsigned(video_ctl.x'range);
|
||||
variable y : unsigned(video_ctl.y'range);
|
||||
variable xMat : boolean; -- raster in between left edge and end of line
|
||||
variable yMat : boolean; -- raster is between first and last line of sprite
|
||||
|
||||
variable height : unsigned(6 downto 0);
|
||||
variable height : unsigned(1 downto 0);
|
||||
|
||||
variable rowCount : unsigned(height'range);
|
||||
-- which part of the sprite is being drawn
|
||||
alias segment : unsigned(1 downto 0) is rowCount(5 downto 4);
|
||||
|
||||
variable code : std_logic_vector(9 downto 0);
|
||||
variable pal_i : std_logic_vector(7 downto 0);
|
||||
variable code : std_logic_vector(9 downto 0);
|
||||
|
||||
begin
|
||||
|
||||
if rising_edge(clk) then
|
||||
if clk_ena = '1' then
|
||||
ld_r <= ctl_i.ld;
|
||||
hblank_r <= video_ctl.hblank;
|
||||
if video_ctl.hblank = '1' then
|
||||
|
||||
x := unsigned(reg_i.x) - video_ctl.video_h_offset + PACE_VIDEO_PIPELINE_DELAY - 3;
|
||||
x := unsigned(reg_i.x) - video_ctl.video_h_offset + PACE_VIDEO_PIPELINE_DELAY - 2;
|
||||
y := 256 + 128 - 18 - unsigned(reg_i.y);
|
||||
|
||||
-- hande sprite height, placement
|
||||
@@ -77,23 +77,33 @@ begin
|
||||
case ctl_i.height is
|
||||
when 1 =>
|
||||
-- double height
|
||||
height := to_unsigned(2*16,height'length);
|
||||
y := y - 16;
|
||||
when 2 =>
|
||||
-- quadruple height
|
||||
height := to_unsigned(4*16,height'length);
|
||||
y := y - 3*16;
|
||||
when others =>
|
||||
height := to_unsigned(16,height'length);
|
||||
null;
|
||||
end case;
|
||||
|
||||
-- do this 1st because we don't have many clocks
|
||||
if y = unsigned(video_ctl.y) then
|
||||
-- start counting sprite row
|
||||
rowCount := (others => '0');
|
||||
yMat := true;
|
||||
elsif rowCount = height then
|
||||
yMat := false;
|
||||
height := to_unsigned(ctl_i.height,2);
|
||||
height(0) := height (0) or height(1);
|
||||
|
||||
-- count row at start of hblank
|
||||
if hblank_r = '0' then
|
||||
if y = unsigned(video_ctl.y) then
|
||||
-- start counting sprite row
|
||||
rowCount <= (others => '0');
|
||||
yMat := true;
|
||||
elsif rowCount = height & "1111" then
|
||||
yMat := false;
|
||||
else
|
||||
rowCount <= rowCount + 1;
|
||||
end if;
|
||||
|
||||
-- stop sprites wrapping from bottom of screen
|
||||
if y = 0 then
|
||||
yMat := false;
|
||||
end if;
|
||||
end if;
|
||||
|
||||
case ctl_i.height is
|
||||
@@ -115,14 +125,8 @@ begin
|
||||
null;
|
||||
end case;
|
||||
|
||||
xMat := false;
|
||||
-- stop sprites wrapping from bottom of screen
|
||||
if y = 0 then
|
||||
yMat := false;
|
||||
end if;
|
||||
|
||||
-- sprites not visible before row 16
|
||||
if ld_r = '0' and ctl_i.ld = '1' then
|
||||
xMat := false;
|
||||
left_d <= not left_d; -- switch sprite half
|
||||
if yMat then
|
||||
if left_d = '1' then
|
||||
@@ -147,12 +151,7 @@ begin
|
||||
if video_ctl.stb = '1' then
|
||||
|
||||
if x = unsigned(video_ctl.x) then
|
||||
-- count up at left edge of sprite
|
||||
rowCount := rowCount + 1;
|
||||
-- start of sprite
|
||||
--if unsigned(x) /= 0 and unsigned(x) < 240 then
|
||||
xMat := true;
|
||||
--end if;
|
||||
end if;
|
||||
|
||||
if xMat then
|
||||
@@ -172,17 +171,7 @@ begin
|
||||
|
||||
end if;
|
||||
|
||||
if hwsel = HW_LDRUN or
|
||||
hwsel = HW_LDRUN2 or
|
||||
hwsel = HW_LDRUN3 or
|
||||
hwsel = HW_LDRUN4 or
|
||||
hwsel = HW_BATTROAD then
|
||||
pal_i := '0' & reg_i.colour(3 downto 0) & pel;
|
||||
else
|
||||
pal_i := reg_i.colour(4 downto 0) & pel;
|
||||
end if;
|
||||
--pal_i := "000" & std_logic_vector(to_unsigned(INDEX,5));
|
||||
ctl_o.pal_a <= pal_i;
|
||||
ctl_o.pal_a <= reg_i.colour(4 downto 0) & pel;
|
||||
|
||||
-- set pixel transparency based on match
|
||||
ctl_o.set <= '0';
|
||||
|
||||
Reference in New Issue
Block a user