From 80ebe5194e912fd1de32489da37a5bd916565672 Mon Sep 17 00:00:00 2001 From: Gregory Nutt Date: Wed, 3 Dec 2014 18:19:10 -0600 Subject: Correct graphics scaling logic --- apps/graphics/traveler/include/trv_graphics.h | 8 +-- apps/graphics/traveler/include/trv_raycntl.h | 9 +++- apps/graphics/traveler/src/trv_graphics.c | 70 ++++++++++++++++----------- 3 files changed, 54 insertions(+), 33 deletions(-) (limited to 'apps/graphics') diff --git a/apps/graphics/traveler/include/trv_graphics.h b/apps/graphics/traveler/include/trv_graphics.h index 69790e627..b51a8d4fc 100644 --- a/apps/graphics/traveler/include/trv_graphics.h +++ b/apps/graphics/traveler/include/trv_graphics.h @@ -86,14 +86,16 @@ struct trv_graphics_info_s NXHANDLE hnx; /* The connection handle */ NXHANDLE bgwnd; /* Background window handle */ #else - trv_coord_t stride; /* Length of a line in bytes */ + trv_coord_t hoffset; /* Horizontal to start of data (in columns) */ + trv_coord_t voffset; /* Offset to start of data (in rows) */ + trv_coord_t stride; /* Length of a line (in bytes) */ #endif trv_coord_t hwwidth; /* Display width (pixels) */ trv_coord_t hwheight; /* Display height (rows) */ trv_coord_t swwidth; /* Software render width (pixels) */ trv_coord_t swheight; /* Software render height height (rows) */ - uint8_t vscale; /* Log2 vertical image scale factor */ - uint8_t hscale; /* Log2 horizontal image scale factor */ + uint8_t vscale; /* Vertical image scale factor */ + uint8_t hscale; /* Horizontal image scale factor */ struct trv_palette_s palette; /* Color palette */ FAR dev_pixel_t *hwbuffer; /* Hardware frame buffer */ FAR trv_pixel_t *swbuffer; /* Software render buffer */ diff --git a/apps/graphics/traveler/include/trv_raycntl.h b/apps/graphics/traveler/include/trv_raycntl.h index ffcf2b6d3..47bc6bf54 100644 --- a/apps/graphics/traveler/include/trv_raycntl.h +++ b/apps/graphics/traveler/include/trv_raycntl.h @@ -41,12 +41,16 @@ ****************************************************************************/ #include "trv_types.h" -#include "trv_graphics.h" /**************************************************************************** * Pre-processor Definitions ****************************************************************************/ +/* This is the size of the buffer supported by the ray caster */ + +#define TRV_SCREEN_WIDTH 320 +#define TRV_SCREEN_HEIGHT 200 + /**************************************************************************** * Public Types ****************************************************************************/ @@ -55,6 +59,9 @@ * Public Function Prototypes ****************************************************************************/ +struct trv_camera_s; +struct trv_graphics_info_s; + void trv_raycaster(FAR struct trv_camera_s *player, FAR struct trv_graphics_info_s *ginfo); diff --git a/apps/graphics/traveler/src/trv_graphics.c b/apps/graphics/traveler/src/trv_graphics.c index 02d9b61b9..19f5b81e5 100644 --- a/apps/graphics/traveler/src/trv_graphics.c +++ b/apps/graphics/traveler/src/trv_graphics.c @@ -41,6 +41,7 @@ #include "trv_main.h" #include "trv_mem.h" #include "trv_color.h" +#include "trv_raycntl.h" #include "trv_debug.h" #include "trv_graphics.h" @@ -329,24 +330,21 @@ void trv_row_update(struct trv_graphics_info_s *ginfo, FAR const trv_pixel_t *src, FAR dev_pixel_t *dest) { - trv_coord_t hexpand; dev_pixel_t pixel; trv_coord_t srccol; int i; /* Loop for each column in the src render buffer */ - hexpand = (1 << ginfo->hscale); - - for (srccol = 0; srccol < ginfo->swwidth; srccol++) + for (srccol = 0; srccol < TRV_SCREEN_WIDTH; srccol++) { /* Map the source pixel */ pixel = ginfo->palette.lut[*src++]; - /* Copy it to the destination, expanding as necessary */ + /* Expand pixels horizontally via pixel replication */ - for (i = 0; i < hexpand; i++) + for (i = 0; i < ginfo->hscale; i++) { *dest++ = pixel; } @@ -383,8 +381,8 @@ void trv_display_update(struct trv_graphics_info_s *ginfo, int trv_graphics_initialize(FAR struct trv_graphics_info_s *ginfo) { - int swwidth; - int swheight; + int width; + int height; int scale; /* Initialize the graphics device and get information about the display */ @@ -397,31 +395,38 @@ int trv_graphics_initialize(FAR struct trv_graphics_info_s *ginfo) trv_nxsu_initialize(ginfo); #endif + /* Check the size of the display */ + + width = ginfo->hwwidth; + height = ginfo->hwheight; + + if (width < TRV_SCREEN_WIDTH || height < TRV_SCREEN_HEIGHT) + { + trv_abort("ERROR: Display is too small\n"); + } + /* Check if we need to scale the image */ - swwidth = ginfo->hwwidth; - scale = 0; + scale = 0; - while (swwidth > MAX_REND_WIDTH) + while (width >= TRV_SCREEN_WIDTH) { - swwidth >>= 1; + width -= TRV_SCREEN_WIDTH; scale++; } - ginfo->swwidth = swwidth; - ginfo->hscale = scale; + ginfo->hscale = scale; + ginfo->hoffset = (width >> 1); - swheight = ginfo->hwheight; - scale = 0; - - while (swheight > MAX_REND_WIDTH) + scale = 0; + while (height >= TRV_SCREEN_HEIGHT) { - swheight >>= 1; + height -= TRV_SCREEN_HEIGHT; scale++; } - ginfo->swheight = swheight; - ginfo->vscale = scale; + ginfo->vscale = scale; + ginfo->voffset = (height >> 1); /* Allocate buffers * @@ -431,7 +436,7 @@ int trv_graphics_initialize(FAR struct trv_graphics_info_s *ginfo) */ ginfo->swbuffer = (trv_pixel_t*) - trv_malloc(swwidth * swheight * sizeof(trv_pixel_t)); + trv_malloc(TRV_SCREEN_WIDTH * TRV_SCREEN_HEIGHT * sizeof(trv_pixel_t)); if (!ginfo->swbuffer) { trv_abort("ERROR: Failed to allocate render buffer\n"); @@ -503,8 +508,8 @@ void trv_graphics_terminate(FAR struct trv_graphics_info_s *ginfo) void trv_display_update(struct trv_graphics_info_s *ginfo) { - FAR const uint8_t *src = (FAR const uint8_t *)ginfo->swbuffer; - FAR uint8_t *dest = (FAR uint8_t *)ginfo->hwbuffer; + FAR const uint8_t *src; + FAR uint8_t *dest; trv_coord_t srcrow; #ifdef CONFIG_NX trv_coord_t destrow; @@ -512,12 +517,19 @@ void trv_display_update(struct trv_graphics_info_s *ginfo) FAR uint8_t *first; trv_coord_t lnwidth; #endif - trv_coord_t vexpand; int i; - /* Loop for each row in the srce render buffer */ + /* Get the star tof the first source row */ + + src = (FAR const uint8_t *)ginfo->swbuffer; + + /* Get the start of the first destination row */ + + dest = (FAR uint8_t *)ginfo->hwbuffer + + (ginfo->hoffset * ginfo->stride) + ginfo->voffset; + + /* Loop for each row in the src render buffer */ - vexpand = (1 << ginfo->vscale); #ifdef CONFIG_NX destrow = 0; #else @@ -543,7 +555,7 @@ void trv_display_update(struct trv_graphics_info_s *ginfo) /* Then replicate as many times as is necessary */ - for (i = 1; i < vexpand; i++) + for (i = 1; i < ginfo->vscale; i++) { #ifdef CONFIG_NX /* Transfer the row buffer to the NX window */ @@ -560,7 +572,7 @@ void trv_display_update(struct trv_graphics_info_s *ginfo) /* Point to the next src row */ - src += ginfo->swwidth; + src += TRV_SCREEN_WIDTH; } } -- cgit v1.2.3