ra8-firmware 0.1.0
Bare-metal firmware for the Renesas RA8 family (RA8D2 / RA8P1)
Loading...
Searching...
No Matches
zoom_render.c
Go to the documentation of this file.
1
42
43#include <stdint.h>
44#include <string.h>
45
46#include "ra8_attributes.h"
47#include "ra8_check.h"
48#include "ra8_err.h"
49#include "ra8_gfx.h"
50#include "ra8_gfx_dither.h"
51#include "zoom.h"
52#include "zoom_internal.h"
53
55static const char* const s_tag = "zoom_render";
56
79typedef enum : uint8_t {
83
109static void internal_expand_row(const zoom_view_t* v, const zoom_axis_t* ax, uint8_t* drow)
110{
111 const int32_t scale = (int32_t)v->scale;
112 /* The whole index calculation stays signed and the only conversion is of the
113 * axis' own simple `s0` -- a cast of the composite `(anchor + d) / scale` to
114 * an unsigned type would change essential type mid-expression (MISRA 10.8)
115 * for no benefit: every value here is non-negative by construction. */
116 const int32_t base = (int32_t)ax->s0;
117 for (int32_t d = ax->d0; d < ax->d1; ++d) {
118 const int32_t si = ((v->anchor_x + d) / scale) - base;
119 drow[d] = v->scratch.row[si];
120 }
121}
122
155 const zoom_axis_t* ax,
156 int32_t plane_y,
157 uint8_t* drow,
158 int32_t* cached_sy)
159{
160 const int32_t scale = (int32_t)v->scale;
161 const int32_t height = (int32_t)v->src.height;
162 const int32_t sy = (plane_y >= 0) ? (plane_y / scale) : -1;
163 /* Decision: this destination row shows image only if the plane row lies
164 * inside the image. The horizontal span is NOT re-tested here -- it is
165 * constant across the frame and ::internal_fill_strip settles it once, which
166 * keeps this decision to two conditions that are each independently
167 * reachable rather than three where one never varies. */
168 const bool covered = (sy >= 0) && (sy < height);
169 if (!covered) {
170 return k_ra8_ok;
171 }
172 if (sy != *cached_sy) {
173 const ra8_err_t rc =
174 v->src.read(v->src.ctx, ax->s0, (uint32_t)sy, ax->count, 1U, v->scratch.row, ax->count);
175 if (rc != k_ra8_ok) {
176 /* Name the row. The caller only learns that the frame was abandoned, and
177 * on a paged source which source row faulted IS the diagnostic. */
178 ra8_log_error_val(s_tag, "source read failed at row", (uint32_t)sy);
179 *cached_sy = -1;
180 return rc;
181 }
182 *cached_sy = sy;
183 }
184 internal_expand_row(v, ax, drow);
185 return k_ra8_ok;
186}
187
220 const zoom_axis_t* ax,
221 int32_t top,
222 int32_t rows,
223 int32_t* cached_sy)
224{
225 const size_t stride = (size_t)v->dst.w;
226 (void)memset(v->scratch.strip, (int)k_zoom_bg_gray, (size_t)rows * stride);
227 if (ax->count == 0U) {
228 /* The image misses the viewport horizontally, so every row is letterbox and
229 * the background fill above is the whole answer. */
230 return k_ra8_ok;
231 }
232 for (int32_t r = 0; r < rows; ++r) {
233 uint8_t* drow = &v->scratch.strip[(size_t)r * stride];
234 RA8_RETURN_ON_ERROR(internal_fill_row(v, ax, v->anchor_y + top + r, drow, cached_sy),
235 s_tag,
236 "strip row");
237 }
238 return k_ra8_ok;
239}
240
270 const zoom_axis_t* ax,
271 int32_t top,
272 int32_t rows,
273 int32_t* cached_sy)
274{
275 RA8_RETURN_ON_ERROR(internal_fill_strip(v, ax, top, rows, cached_sy), s_tag, "strip fill");
276 uint32_t packed_len = 0U;
278 v->dst.w,
279 rows,
280 v->anchor_x,
281 v->anchor_y + top,
282 v->scratch.packed,
284 &packed_len),
285 s_tag,
286 "strip dither");
288 v->dst.w,
289 rows,
290 (int32_t)k_zoom_blit_origin,
291 (int32_t)k_zoom_blit_origin,
292 v->dst.w,
293 rows,
294 (int32_t)k_zoom_blit_native,
295 v->dst.x,
296 v->dst.y + top);
297}
298
325{
326 RA8_CHECK_NULL_PTR(v, s_tag, "view must not be nullptr");
327 RA8_CHECK_NULL_PTR(v->src.read, s_tag, "view source seam must not be nullptr");
328 if (!v->active) {
329 ra8_log_error(s_tag, "render on a closed view");
331 }
332 if (v->strip_rows == 0U) {
333 ra8_log_error(s_tag, "view has no strip height; it was not opened properly");
335 }
336 return k_ra8_ok;
337}
338
340{
341 RA8_RETURN_ON_ERROR(internal_render_ready(v), s_tag, "render preconditions");
342
343 zoom_axis_t ax = {};
344 priv_zoom_axis(v->anchor_x, v->dst.w, (int32_t)v->scale, (int32_t)v->src.width, &ax);
345
346 const int32_t rows_max = (int32_t)v->strip_rows;
347 int32_t cached_sy = -1;
348 for (int32_t top = 0; top < v->dst.h; top += rows_max) {
349 int32_t rows = v->dst.h - top;
350 if (rows > rows_max) {
351 rows = rows_max;
352 }
353 RA8_RETURN_ON_ERROR(internal_emit_strip(v, &ax, top, rows, &cached_sy), s_tag, "strip emit");
354 }
355 return k_ra8_ok;
356}
static const char * s_tag
Logging / check tag.
Definition ra8_app.c:17
Annotation-attribute framework macros for ra8-firmware.
#define RA8_INTERNAL
Marker that a function is intended to be static (file-local).
Validation and Error-Checking Macros for ra8-firmware.
#define RA8_RETURN_ON_ERROR(err, tag, message)
Early return on error, propagating the code upward.
Definition ra8_check.h:184
#define RA8_CHECK_NULL_PTR(ptr, tag, message)
Reject nullptr pointer, returning k_ra8_err_null_ptr.
Definition ra8_check.h:243
Error Code Definitions for ra8-firmware.
@ k_ra8_err_invalid_state
Module in wrong state for requested operation.
Definition ra8_err.h:161
@ k_ra8_ok
Success – operation completed with all postconditions satisfied.
Definition ra8_err.h:119
ra8_err_codes_t ra8_err_t
Canonical error-return type used by every ra8-firmware API.
Definition ra8_err.h:546
void * memset(void *dst, int value, size_t n)
Fill memory with a constant byte value.
Software 2D graphics primitives layered on top of a caller-ownedframebuffer (DRW / D/AVE 2D / GLCDC r...
ra8_err_t ra8_gfx_blit_gray4_zoom(const uint8_t *src, int32_t src_w, int32_t src_h, int32_t sx, int32_t sy, int32_t sw, int32_t sh, int32_t zoom, int32_t dst_x, int32_t dst_y)
Nearest-neighbour integer-zoom blit of a sub-rectangle of a packed 4-bit grayscale image into the fra...
Void-and-cluster blue-noise dithering: continuous-tone gray8 -> 16-level panel (#477).
ra8_err_t ra8_gfx_dither_gray8_to_gray4(const uint8_t *src, int32_t w, int32_t h, int32_t origin_x, int32_t origin_y, uint8_t *out, uint32_t out_cap, uint32_t *out_size)
Dither a gray8 tile to packed 4-bpp nibbles (panel-native), seamlessly.
#define ra8_log_error_val(tag, message, value)
RA8 log error val.
Definition ra8_log.h:337
#define ra8_log_error(tag, message)
RA8 log error.
Definition ra8_log.h:335
int32_t w
Width (pixels, >= 0).
Definition ra8_ui.h:75
int32_t h
Height (pixels, >= 0).
Definition ra8_ui.h:76
int32_t x
Left edge (pixels).
Definition ra8_ui.h:73
int32_t y
Top edge (pixels).
Definition ra8_ui.h:74
One axis of the viewport resolved against the image: coverage + source span.
uint32_t count
Source indices feeding the covered span (0 if none).
uint32_t s0
First source index feeding the covered span.
int32_t d0
First covered destination offset inside the viewport.
uint8_t * packed
The strip packed to 4 bpp (2 px/byte).
Definition zoom.h:340
uint8_t * row
One source row, >= dst.w bytes.
Definition zoom.h:336
uint32_t packed_cap
Capacity of packed, bytes.
Definition zoom.h:341
uint8_t * strip
gray8 destination strip, dst.w * strip_rows.
Definition zoom.h:338
uint32_t height
Full-resolution source height, pixels.
Definition zoom.h:300
uint32_t width
Full-resolution source width, pixels.
Definition zoom.h:299
zoom_read_fn read
gray8 sub-rectangle reader (never NULL once bound).
Definition zoom.h:297
void * ctx
Opaque context handed back to read.
Definition zoom.h:298
Live viewport: where it is looking, how magnified, and what it owes the panel.
Definition zoom.h:472
uint8_t scale
Current integer magnification.
Definition zoom.h:481
zoom_source_t src
Bound source.
Definition zoom.h:473
zoom_scratch_t scratch
Caller-owned composite buffers.
Definition zoom.h:474
ra8_ui_rect_t dst
Viewport in framebuffer pixels.
Definition zoom.h:475
uint16_t strip_rows
Destination rows per composite strip.
Definition zoom.h:480
int32_t anchor_y
Plane row shown at dst.y.
Definition zoom.h:477
bool active
The view is open.
Definition zoom.h:487
int32_t anchor_x
Plane column shown at dst.x.
Definition zoom.h:476
void priv_zoom_axis(int32_t anchor, int32_t extent, int32_t scale, int32_t src_dim, zoom_axis_t *out)
Resolve one viewport axis against the image at the current magnification.
Definition zoom.c:60
Tap-to-zoom image viewer: viewport state machine + tiled magnifying render (#478).
@ k_zoom_bg_gray
Letterbox fill level (on-palette white).
Definition zoom.h:121
Module-private seam shared by the zoom state machine and its render.
static ra8_err_t internal_emit_strip(zoom_view_t *v, const zoom_axis_t *ax, int32_t top, int32_t rows, int32_t *cached_sy)
One strip, end to end: magnify, re-dither at plane phase, blit.
static ra8_err_t internal_fill_row(zoom_view_t *v, const zoom_axis_t *ax, int32_t plane_y, uint8_t *drow, int32_t *cached_sy)
Composite one destination row: decide coverage, fault, replicate.
static ra8_err_t internal_fill_strip(zoom_view_t *v, const zoom_axis_t *ax, int32_t top, int32_t rows, int32_t *cached_sy)
Build one gray8 destination strip: background fill, then per-row composite.
static ra8_err_t internal_render_ready(const zoom_view_t *v)
Whether a view is in a state that can be composited at all.
static void internal_expand_row(const zoom_view_t *v, const zoom_axis_t *ax, uint8_t *drow)
Replicate one source row across the covered destination columns.
ra8_err_t zoom_view_render(zoom_view_t *v)
Composite the visible window into the bound ra8_gfx framebuffer.
zoom_blit_t
Fixed arguments of the per-strip packed-gray4 blit.
Definition zoom_render.c:79
@ k_zoom_blit_origin
Sub-rect origin inside the packed strip.
Definition zoom_render.c:80
@ k_zoom_blit_native
Blit magnification (the strip is already sized).
Definition zoom_render.c:81