r61524: add a r61524_display_rect() function for small regions

This commit is contained in:
Lephe 2022-07-16 22:30:59 +01:00
parent e8b4bcc9cb
commit 1c3c9727a5
No known key found for this signature in database
GPG key ID: 1BBA026E13FC0495
2 changed files with 39 additions and 7 deletions

View file

@ -35,16 +35,33 @@ enum {
@method Transfer method, see above */
void r61524_display(uint16_t *vram, int start, int height, int method);
/* r61524_display_rect(): Send a rectangular section of VRAM to the display
This function updates the rectangle going from (xmin,ymin) to (xmax,ymax) in
the VRAM to the display (both ends included). This can be faster than a full
dupdate() or a striped r61524_display() depending on the situation. However,
because the source VRAM is not contiguous, the transfer is only possible by
CPU, so this is only interesting for small regions.
@vram Source VRAM with a stride of 396*2 bytes
@xmin @xmax Horizontal range to be updated (both included)
@ymin @ymax Vertical range to be updated (both included) */
void r61524_display_rect(uint16_t *vram, int xmin, int xmax, int ymin,
int ymax);
/* r61524_start_frame(): Prepare the display for a region update
This function sets up the display driver to receive graphics data to update
liens [start] to [start+height-1] (both included) of the current window.
This is the initial step of r61524_display(), which is normally followed by
writing all the data to 0xb4000000.
the rectangle going from (xmin,ymin) to (xmax,ymax) (both included). This is
the initial step of r61524_display(), which is normally followed by writing
all the data to 0xb4000000.
In order to write with the DMA, it is necessary to write the full horizontal
range and select ymin and ymax to be congruent to 0 and 3 modulo 4.
This function can be used to implement additional display driver update
methods or alternate rendering pipelines. */
void r61524_start_frame(int start, int height);
void r61524_start_frame(int xmin, int xmax, int ymin, int ymax);
/* r162524_win_get() and r61524_win_set(): Manipulate the display window

View file

@ -134,10 +134,10 @@ void r61524_win_set(uint16_t HSA, uint16_t HEA, uint16_t VSA, uint16_t VEA)
/* TODO: r61524: update, backlight, brightness, gamma */
void r61524_start_frame(int start, int height)
void r61524_start_frame(int xmin, int xmax, int ymin, int ymax)
{
/* Move the window to the desired region, then select address 0 */
r61524_win_set(0, 395, start, start + height - 1);
r61524_win_set(xmin, xmax, ymin, ymax);
select(ram_address_horizontal);
write(0);
select(ram_address_vertical);
@ -153,7 +153,7 @@ void r61524_display(uint16_t *vram, int start, int height, int method)
the DMA might write data *while* we're sending commands! */
dma_transfer_wait(0);
r61524_start_frame(start, height);
r61524_start_frame(0, 395, start, start + height - 1);
if(method == R61524_CPU)
{
@ -181,6 +181,21 @@ void r61524_display(uint16_t *vram, int start, int height, int method)
}
}
void r61524_display_rect(uint16_t *vram, int xmin, int xmax, int ymin,
int ymax)
{
dma_transfer_wait(0);
r61524_start_frame(xmin, xmax, ymin, xmax);
vram += 396 * ymin + xmin;
for(int y = 0; y < ymax - ymin + 1; y++) {
for(int x = 0; x < xmax - xmin + 1; x++)
write(vram[x]);
vram += 396;
}
}
//---
// State and driver metadata
//---