1 // license:BSD-3-Clause
2 // copyright-holders:Mirko Buffoni,Nicola Salmoria,Bryan McPhail,David Haywood,R. Belmont,Alex Marshall,Angelo Salese,Luca Elia
3 // thanks-to:Richard Bush
4 /* notes...
5 
6  drawing sprites in a single pass with pdrawgfx breaks Thunder Dragon 2,
7   which seems to expect the sprite priority values to affect sprite-sprite
8   priority.  Thunder Dragon 2 also breaks if you support sprite flipping,
9   the collectible point score / power up names appear flipped..
10 
11 */
12 
13 #include "emu.h"
14 #include "includes/nmk16.h"
15 
16 // the larger tilemaps on macross2, rapid hero and thunder dragon 2 appear to act like 4 'banks'
17 // of the smaller tilemaps, rather than being able to scroll into each other (not verified on real hw,
18 // but see raphero intro / 1st level cases)
19 
20 
21 /***************************************************************************
22 
23   Callbacks for the TileMap code
24 
25 ***************************************************************************/
26 
27 /*
28 #define TILES_PER_PAGE_X    (0x10)
29 #define TILES_PER_PAGE_Y    (0x10)
30 #define PAGES_PER_TMAP_X    (0x10)
31 #define PAGES_PER_TMAP_Y    (0x02)
32 */
33 
TILEMAP_MAPPER_MEMBER(nmk16_state::tilemap_scan_pages)34 TILEMAP_MAPPER_MEMBER(nmk16_state::tilemap_scan_pages)
35 {
36 	return (row & 0xf) | ((col & 0xff) << 4) | ((row & 0x10) << 8);
37 }
38 
39 template<unsigned Layer, unsigned Gfx>
TILE_GET_INFO_MEMBER(nmk16_state::common_get_bg_tile_info)40 TILE_GET_INFO_MEMBER(nmk16_state::common_get_bg_tile_info)
41 {
42 	const u16 code = m_bgvideoram[Layer][(m_tilerambank << 13) | tile_index];
43 	tileinfo.set(Gfx, (code & 0xfff) | (m_bgbank << 12), code >> 12, 0);
44 }
45 
TILE_GET_INFO_MEMBER(nmk16_state::common_get_tx_tile_info)46 TILE_GET_INFO_MEMBER(nmk16_state::common_get_tx_tile_info)
47 {
48 	const u16 code = m_txvideoram[tile_index];
49 	tileinfo.set(0, code & 0xfff, code >> 12, 0);
50 }
51 
TILE_GET_INFO_MEMBER(nmk16_state::bioship_get_bg_tile_info)52 TILE_GET_INFO_MEMBER(nmk16_state::bioship_get_bg_tile_info)
53 {
54 	const u16 code = m_tilemap_rom[(m_bioship_background_bank << 13) | tile_index]; // ROM Based
55 	tileinfo.set(3, code & 0xfff, code >> 12, 0);
56 }
57 
TILE_GET_INFO_MEMBER(nmk16_state::bjtwin_get_bg_tile_info)58 TILE_GET_INFO_MEMBER(nmk16_state::bjtwin_get_bg_tile_info)
59 {
60 	const u16 code = m_bgvideoram[0][tile_index];
61 	const u8 bank = BIT(code, 11);
62 	tileinfo.set(bank,
63 			(code & 0x7ff) + ((bank) ? (m_bgbank << 11) : 0),
64 			code >> 12,
65 			0);
66 }
67 
68 
69 /***************************************************************************
70 
71   Start the video hardware emulation.
72 
73 ***************************************************************************/
74 
video_init()75 void nmk16_state::video_init()
76 {
77 	m_spriteram_old = make_unique_clear<u16[]>(0x1000/2);
78 	m_spriteram_old2 = make_unique_clear<u16[]>(0x1000/2);
79 
80 	m_tilerambank = 0;
81 
82 	m_dma_timer = machine().scheduler().timer_alloc(timer_expired_delegate(FUNC(nmk16_state::dma_callback),this));
83 	save_pointer(NAME(m_spriteram_old), 0x1000/2);
84 	save_pointer(NAME(m_spriteram_old2), 0x1000/2);
85 	save_item(NAME(m_bgbank));
86 	save_item(NAME(m_mustang_bg_xscroll));
87 	save_item(NAME(m_scroll[0]));
88 	save_item(NAME(m_scroll[1]));
89 	save_item(NAME(m_vscroll));
90 	save_item(NAME(m_tilerambank));
91 }
92 
93 
VIDEO_START_MEMBER(nmk16_state,bioship)94 VIDEO_START_MEMBER(nmk16_state, bioship)
95 {
96 	// ROM Based Tilemap
97 	m_bg_tilemap[0] = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, FUNC(nmk16_state::bioship_get_bg_tile_info)), tilemap_mapper_delegate(*this, FUNC(nmk16_state::tilemap_scan_pages)), 16, 16, 256, 32);
98 	m_bg_tilemap[1] = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, NAME((&nmk16_state::common_get_bg_tile_info<1, 1>))), tilemap_mapper_delegate(*this, FUNC(nmk16_state::tilemap_scan_pages)), 16, 16, 256, 32);
99 	m_tx_tilemap = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, FUNC(nmk16_state::common_get_tx_tile_info)), TILEMAP_SCAN_COLS, 8, 8, 32, 32);
100 
101 	m_bg_tilemap[1]->set_transparent_pen(15);
102 	m_tx_tilemap->set_transparent_pen(15);
103 
104 	video_init();
105 	m_bioship_background_bank=0;
106 	save_item(NAME(m_bioship_background_bank));
107 }
108 
VIDEO_START_MEMBER(nmk16_state,macross)109 VIDEO_START_MEMBER(nmk16_state,macross)
110 {
111 	m_bg_tilemap[0] = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, NAME((&nmk16_state::common_get_bg_tile_info<0, 1>))), tilemap_mapper_delegate(*this, FUNC(nmk16_state::tilemap_scan_pages)), 16, 16, 256, 32);
112 	m_tx_tilemap = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, FUNC(nmk16_state::common_get_tx_tile_info)), TILEMAP_SCAN_COLS, 8, 8, 32, 32);
113 
114 	m_tx_tilemap->set_transparent_pen(15);
115 
116 	video_init();
117 }
118 
VIDEO_START_MEMBER(nmk16_state,strahl)119 VIDEO_START_MEMBER(nmk16_state,strahl)
120 {
121 	VIDEO_START_CALL_MEMBER(macross);
122 	m_bg_tilemap[1] = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, NAME((&nmk16_state::common_get_bg_tile_info<1, 3>))), tilemap_mapper_delegate(*this, FUNC(nmk16_state::tilemap_scan_pages)), 16, 16, 256, 32);
123 	m_bg_tilemap[1]->set_transparent_pen(15);
124 
125 	m_sprdma_base = 0xf000;
126 }
127 
VIDEO_START_MEMBER(nmk16_state,macross2)128 VIDEO_START_MEMBER(nmk16_state,macross2)
129 {
130 	m_bg_tilemap[0] = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, NAME((&nmk16_state::common_get_bg_tile_info<0, 1>))), tilemap_mapper_delegate(*this, FUNC(nmk16_state::tilemap_scan_pages)), 16, 16, 256, 32);
131 	m_tx_tilemap = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, FUNC(nmk16_state::common_get_tx_tile_info)), TILEMAP_SCAN_COLS, 8, 8, 64, 32);
132 
133 	m_tx_tilemap->set_transparent_pen(15);
134 
135 	video_init();
136 	// 384x224 screen, leftmost 64 pixels have to be retrieved from the other side of the tilemap (!)
137 	m_bg_tilemap[0]->set_scrolldx(64,64);
138 	m_tx_tilemap->set_scrolldx(64,64);
139 }
140 
VIDEO_START_MEMBER(nmk16_state,gunnail)141 VIDEO_START_MEMBER(nmk16_state,gunnail)
142 {
143 	VIDEO_START_CALL_MEMBER(macross2);
144 	m_bg_tilemap[0]->set_scroll_rows(512);
145 }
146 
VIDEO_START_MEMBER(nmk16_state,bjtwin)147 VIDEO_START_MEMBER(nmk16_state, bjtwin)
148 {
149 	m_bg_tilemap[0] = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, FUNC(nmk16_state::bjtwin_get_bg_tile_info)), TILEMAP_SCAN_COLS, 8, 8, 64, 32);
150 
151 	video_init();
152 	// 384x224 screen, leftmost 64 pixels have to be retrieved from the other side of the tilemap (!)
153 	m_bg_tilemap[0]->set_scrolldx(64,64);
154 }
155 
mustang_scroll_w(u16 data)156 void nmk16_state::mustang_scroll_w(u16 data)
157 {
158 //  osd_printf_debug("mustang %04x %04x %04x\n",offset,data,mem_mask);
159 
160 	switch (data & 0xff00)
161 	{
162 		case 0x0000:
163 			m_mustang_bg_xscroll = (m_mustang_bg_xscroll & 0x00ff) | ((data & 0x00ff)<<8);
164 			break;
165 
166 		case 0x0100:
167 			m_mustang_bg_xscroll = (m_mustang_bg_xscroll & 0xff00) | (data & 0x00ff);
168 			break;
169 
170 		case 0x0200:
171 			break;
172 
173 		case 0x0300:
174 			break;
175 
176 		default:
177 			break;
178 	}
179 
180 	m_bg_tilemap[0]->set_scrollx(0,m_mustang_bg_xscroll);
181 }
182 
bjtwin_scroll_w(offs_t offset,u8 data)183 void nmk16_state::bjtwin_scroll_w(offs_t offset, u8 data)
184 {
185 	m_bg_tilemap[0]->set_scrolly(0,-data);
186 }
187 
vandyke_scroll_w(offs_t offset,u16 data)188 void nmk16_state::vandyke_scroll_w(offs_t offset, u16 data)
189 {
190 	m_vscroll[offset] = data;
191 
192 	m_bg_tilemap[0]->set_scrollx(0,m_vscroll[0] * 256 + (m_vscroll[1] >> 8));
193 	m_bg_tilemap[0]->set_scrolly(0,m_vscroll[2] * 256 + (m_vscroll[3] >> 8));
194 }
195 
vandykeb_scroll_w(offs_t offset,u16 data,u16 mem_mask)196 void nmk16_state::vandykeb_scroll_w(offs_t offset, u16 data, u16 mem_mask)
197 {
198 	switch (offset)
199 	{
200 	case 0: COMBINE_DATA(&m_vscroll[3]); break;
201 	case 1: COMBINE_DATA(&m_vscroll[2]); break;
202 	case 5: COMBINE_DATA(&m_vscroll[1]); break;
203 	case 6: COMBINE_DATA(&m_vscroll[0]); break;
204 	}
205 
206 	m_bg_tilemap[0]->set_scrollx(0,m_vscroll[0] * 256 + (m_vscroll[1] >> 8));
207 	m_bg_tilemap[0]->set_scrolly(0,m_vscroll[2] * 256 + (m_vscroll[3] >> 8));
208 }
209 
manybloc_scroll_w(offs_t offset,u16 data,u16 mem_mask)210 void nmk16_state::manybloc_scroll_w(offs_t offset, u16 data, u16 mem_mask)
211 {
212 	COMBINE_DATA(&m_gunnail_scrollram[offset]);
213 
214 	m_bg_tilemap[0]->set_scrollx(0,m_gunnail_scrollram[0x82/2]);
215 	m_bg_tilemap[0]->set_scrolly(0,m_gunnail_scrollram[0xc2/2]);
216 }
217 
flipscreen_w(u8 data)218 void nmk16_state::flipscreen_w(u8 data)
219 {
220 	flip_screen_set(data & 0x01);
221 	m_spritegen->set_flip_screen(flip_screen());
222 }
223 
tilebank_w(u8 data)224 void nmk16_state::tilebank_w(u8 data)
225 {
226 	if (m_bgbank != data)
227 	{
228 		m_bgbank = data;
229 		for (int layer = 0; layer < 2; layer++)
230 			if (m_bg_tilemap[layer]) m_bg_tilemap[layer]->mark_all_dirty();
231 
232 	}
233 }
234 
raphero_scroll_w(offs_t offset,u16 data,u16 mem_mask)235 void nmk16_state::raphero_scroll_w(offs_t offset, u16 data, u16 mem_mask)
236 {
237 	COMBINE_DATA(&m_gunnail_scrollram[offset]);
238 	if ((m_bgvideoram[0].bytes() > 0x4000) && (offset == 0))
239 	{
240 		int newbank = (m_gunnail_scrollram[0] >> 12) & ((m_bgvideoram[0].bytes() >> 14) - 1);
241 		if (m_tilerambank != newbank)
242 		{
243 			m_tilerambank = newbank;
244 			for (int layer = 0; layer < 2; layer++)
245 			{
246 				if (m_bg_tilemap[layer])
247 					m_bg_tilemap[layer]->mark_all_dirty();
248 			}
249 		}
250 	}
251 }
252 
bioship_bank_w(u8 data)253 void nmk16_state::bioship_bank_w(u8 data)
254 {
255 	if (m_bioship_background_bank != data)
256 	{
257 		m_bioship_background_bank = data;
258 		m_bg_tilemap[0]->mark_all_dirty();
259 	}
260 }
261 
262 /***************************************************************************
263 
264   Display refresh
265 
266 ***************************************************************************/
267 
268 
get_colour_4bit(u32 & colour,u32 & pri_mask)269 void nmk16_state::get_colour_4bit(u32 &colour, u32 &pri_mask)
270 {
271 	colour &= 0xf;
272 	pri_mask |= GFX_PMASK_2; // under foreground
273 }
274 
get_colour_5bit(u32 & colour,u32 & pri_mask)275 void nmk16_state::get_colour_5bit(u32 &colour, u32 &pri_mask)
276 {
277 	colour &= 0x1f;
278 	pri_mask |= GFX_PMASK_2; // under foreground
279 }
280 
281 // manybloc uses extra flip bits on the sprites, but these break other games
282 
get_sprite_flip(u16 attr,int & flipx,int & flipy,int & code)283 void nmk16_state::get_sprite_flip(u16 attr, int &flipx, int &flipy, int &code)
284 {
285 	flipy = (attr & 0x200) >> 9;
286 	flipx = (attr & 0x100) >> 8;
287 }
288 
draw_sprites(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect,u16 * src)289 void nmk16_state::draw_sprites(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, u16 *src)
290 {
291 	m_spritegen->draw_sprites(screen, bitmap, cliprect, m_gfxdecode->gfx(2), src, 0x1000 / 2);
292 }
293 
294 /***************************************************************************
295 
296 
297                             Generic Screen Updates
298 
299 
300 ***************************************************************************/
301 
bg_update(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect,int layer)302 void nmk16_state::bg_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect, int layer)
303 {
304 	if (m_gunnail_scrollram && m_gunnail_scrollramy)
305 	{
306 		// the hardware supports per-scanline X *and* Y scroll which isn't
307 		// supported by tilemaps so we have to draw the tilemap one line at a time
308 		int i = 16;
309 		rectangle bgclip = cliprect;
310 		int y1 = cliprect.min_y;
311 		while (y1 <= cliprect.max_y)
312 		{
313 			const int yscroll = m_gunnail_scrollramy[0] + m_gunnail_scrollramy[y1];
314 
315 			bgclip.min_y = y1;
316 			bgclip.max_y = y1;
317 
318 			m_bg_tilemap[layer]->set_scroll_rows(512);
319 
320 			m_bg_tilemap[layer]->set_scrolly(0, yscroll);
321 			m_bg_tilemap[layer]->set_scrollx((i + yscroll) & 0x1ff, m_gunnail_scrollram[0] + m_gunnail_scrollram[i]);
322 
323 			m_bg_tilemap[layer]->draw(screen, bitmap, bgclip, 0, 1);
324 
325 			y1++;
326 			i++;
327 		}
328 	}
329 	else
330 	{
331 		m_bg_tilemap[layer]->draw(screen, bitmap, cliprect, 0, 1);
332 	}
333 }
334 
tx_update(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)335 void nmk16_state::tx_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
336 {
337 	m_tx_tilemap->draw(screen, bitmap, cliprect, 0, 2);
338 }
339 
340 /***************************************************************************
341 
342 
343                             Screen update functions
344 
345 
346 ***************************************************************************/
347 
screen_update_macross(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)348 u32 nmk16_state::screen_update_macross(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
349 {
350 	screen.priority().fill(0, cliprect);
351 	bg_update(screen, bitmap, cliprect, 0);
352 	tx_update(screen, bitmap, cliprect);
353 	draw_sprites(screen, bitmap, cliprect, m_spriteram_old2.get());
354 	return 0;
355 }
356 
screen_update_tharrier(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)357 u32 nmk16_state::screen_update_tharrier(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
358 {
359 	screen.priority().fill(0, cliprect);
360 	/* I think the protection device probably copies this to the regs... */
361 	u16 tharrier_scroll = m_mainram[0x9f00/2];
362 
363 	m_bg_tilemap[0]->set_scrollx(0, tharrier_scroll);
364 
365 	bg_update(screen, bitmap, cliprect, 0);
366 	tx_update(screen, bitmap, cliprect);
367 	draw_sprites(screen, bitmap, cliprect, m_spriteram_old2.get());
368 	return 0;
369 }
370 
screen_update_strahl(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)371 u32 nmk16_state::screen_update_strahl(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
372 {
373 	screen.priority().fill(0, cliprect);
374 	bg_update(screen, bitmap, cliprect, 0);
375 	bg_update(screen, bitmap, cliprect, 1);
376 	tx_update(screen, bitmap, cliprect);
377 	draw_sprites(screen, bitmap, cliprect, m_spriteram_old2.get());
378 	return 0;
379 }
380 
screen_update_bjtwin(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)381 u32 nmk16_state::screen_update_bjtwin(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
382 {
383 	screen.priority().fill(0, cliprect);
384 	bg_update(screen, bitmap, cliprect, 0);
385 	draw_sprites(screen, bitmap, cliprect, m_spriteram_old.get()); // only a single buffer, verified
386 	return 0;
387 }
388 
389 
390 /***************************************************************************
391 
392 
393                             Video Hardware Init
394 
395 
396 ***************************************************************************/
397 
TILE_GET_INFO_MEMBER(afega_state::get_bg_tile_info_8bit)398 TILE_GET_INFO_MEMBER(afega_state::get_bg_tile_info_8bit)
399 {
400 	const u16 code = m_bgvideoram[0][tile_index];
401 	tileinfo.set(1, code, 0, 0);
402 }
403 
VIDEO_START_MEMBER(afega_state,grdnstrm)404 VIDEO_START_MEMBER(afega_state,grdnstrm)
405 {
406 	// 8bpp Tilemap
407 	m_bg_tilemap[0] = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, FUNC(afega_state::get_bg_tile_info_8bit)), tilemap_mapper_delegate(*this, FUNC(afega_state::tilemap_scan_pages)), 16, 16, 256, 32);
408 	m_tx_tilemap = &machine().tilemap().create(*m_gfxdecode, tilemap_get_info_delegate(*this, FUNC(afega_state::common_get_tx_tile_info)), TILEMAP_SCAN_COLS, 8, 8, 32, 32);
409 
410 	m_tx_tilemap->set_transparent_pen(15);
411 
412 	video_init();
413 }
414 
415 
416 /***************************************************************************
417 
418 
419                                 Screen Drawing
420 
421 
422 ***************************************************************************/
423 
video_update(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect,int dsw_flipscreen,int xoffset,int yoffset,int attr_mask)424 void afega_state::video_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect,
425 	int dsw_flipscreen,         // 1 = Horizontal and vertical screen flip are hardwired to 2 dip switches
426 	int xoffset, int yoffset,   // bg_tilemap0 offsets
427 	int attr_mask               // "sprite active" mask
428 	)
429 {
430 	screen.priority().fill(0, cliprect);
431 	if (dsw_flipscreen)
432 	{
433 		flip_screen_x_set(~m_dsw_io[0]->read() & 0x0100);
434 		flip_screen_y_set(~m_dsw_io[0]->read() & 0x0200);
435 	}
436 
437 	m_bg_tilemap[0]->set_scrollx(0, m_afega_scroll[0][1] + xoffset);
438 	m_bg_tilemap[0]->set_scrolly(0, m_afega_scroll[0][0] + yoffset);
439 
440 	m_tx_tilemap->set_scrollx(0, m_afega_scroll[1][1]);
441 	m_tx_tilemap->set_scrolly(0, m_afega_scroll[1][0]);
442 
443 	m_bg_tilemap[0]->draw(screen, bitmap, cliprect, 0, 1);
444 
445 	m_tx_tilemap->draw(screen, bitmap, cliprect, 0, 2);
446 
447 	draw_sprites(screen, bitmap, cliprect, m_spriteram_old2.get());
448 }
449 
redhawki_video_update(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)450 void afega_state::redhawki_video_update(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
451 {
452 	screen.priority().fill(0, cliprect);
453 	m_bg_tilemap[0]->set_scrollx(0, m_afega_scroll[1][0]&0xff);
454 	m_bg_tilemap[0]->set_scrolly(0, m_afega_scroll[1][1]&0xff);
455 
456 	m_bg_tilemap[0]->draw(screen, bitmap, cliprect, 0, 1);
457 
458 	draw_sprites(screen, bitmap, cliprect, m_spriteram_old2.get());
459 }
460 
screen_update_afega(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)461 u32 afega_state::screen_update_afega(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)   { video_update(screen, bitmap, cliprect, 1, -0x100, +0x000, 0x0001);  return 0; }
screen_update_bubl2000(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)462 u32 afega_state::screen_update_bubl2000(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect){ video_update(screen, bitmap, cliprect, 0, -0x100, +0x000, 0x0001);  return 0; } // no flipscreen support, I really would confirmation from the schematics
screen_update_redhawkb(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)463 u32 afega_state::screen_update_redhawkb(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect){ video_update(screen, bitmap, cliprect, 0, +0x000, +0x100, 0x0001);  return 0; }
screen_update_redhawki(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)464 u32 afega_state::screen_update_redhawki(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect){ redhawki_video_update(screen, bitmap, cliprect); return 0;} // strange scroll regs
465 
screen_update_firehawk(screen_device & screen,bitmap_ind16 & bitmap,const rectangle & cliprect)466 u32 afega_state::screen_update_firehawk(screen_device &screen, bitmap_ind16 &bitmap, const rectangle &cliprect)
467 {
468 	screen.priority().fill(0, cliprect);
469 	m_bg_tilemap[0]->set_scrolly(0, m_afega_scroll[1][1] + 0x100);
470 	m_bg_tilemap[0]->set_scrollx(0, m_afega_scroll[0][1] - 0x100);
471 
472 	m_bg_tilemap[0]->draw(screen, bitmap, cliprect, 0, 1);
473 
474 	m_tx_tilemap->draw(screen, bitmap, cliprect, 0, 2);
475 
476 	draw_sprites(screen, bitmap, cliprect, m_spriteram_old2.get());
477 	return 0;
478 }
479