70 const size_t after = at +
strlen(name);
74 const char c = (char)s[after];
121 while ((j < len) && (s[j] != (uint8_t)
'>')) {
165 const uint8_t* tag = &s[open];
166 const size_t tlen = close - open;
175 if ((nums[2] > 0) && (nums[3] > 0)) {
184 if ((wv > 0) && (hv > 0)) {
220 const uint8_t* tag = &s[at];
221 const size_t tlen = (close > at) ? (close - at) : 0U;
329 const bool self_close = (close > i) && (s[close - 1U] == (uint8_t)
'/');
372 while ((i < len) && (s[i] != (uint8_t)
'<')) {
379 while ((close < len) && (s[close] != (uint8_t)
'>')) {
383 gsp = (gsp > 0) ? (gsp - 1) : 0;
391 i = (close < len) ? (close + 1U) : len;
474 for (
size_t i = 0U; i < n; ++i) {
475 dst[i] = (char)s[off + i];
545 static const float k_percent = 100.0F;
553 for (
size_t z = 0U; z < ovl; ++z) {
554 if (tag[ooff + z] == (uint8_t)
'%') {
555 return off / k_percent;
635 while ((close < end) && (s[close] != (uint8_t)
'>')) {
638 const uint8_t* tag = &s[sp];
639 const size_t tlen = (close > sp) ? (close - sp) : 0U;
643 at = (close < end) ? (close + 1U) : end;
675 static const float k_half = 0.5F;
682 const bool is_rad = (rad < lin);
683 const size_t at = is_rad ? rad : lin;
688 while ((close < len) && (s[close] != (uint8_t)
'>')) {
691 const uint8_t* tag = &s[at];
692 const size_t tlen = (close > at) ? (close - at) : 0U;
707 const char* endtag = is_rad ?
"</radialGradient" :
"</linearGradient";
709 const size_t stopend = (endpos < len) ? endpos : len;
714 from = (endpos < len) ? (endpos + 1U) : len;
725 if ((bytes ==
nullptr) || (len == 0U)) {
743 if ((svg ==
nullptr) || (out_off ==
nullptr) || (out_len ==
nullptr)) {
751 const uint8_t* tag = &svg[open];
752 const size_t tlen = close - open;
759 *out_off = open + voff;
766 if ((svg ==
nullptr) || (out_w ==
nullptr) || (out_h ==
nullptr)) {
774 const uint8_t* tag = &svg[open];
775 const size_t tlen = close - open;
778 if ((w <= 0) || (h <= 0)) {
791 if ((w <= 0) || (h <= 0)) {
801 if (svg ==
nullptr) {
804 if ((w <= 0) || (h <= 0)) {
Annotation-attribute framework macros for ra8-firmware.
#define RA8_INTERNAL
Marker that a function is intended to be static (file-local).
@ k_ra8_err_invalid_arg
Invalid function argument.
@ k_ra8_ok
Success – operation completed with all postconditions satisfied.
@ k_ra8_err_null_ptr
Pointer was NULL where a valid pointer was required.
@ k_ra8_err_not_found
Requested item not found (lookup / search missed).
ra8_err_codes_t ra8_err_t
Canonical error-return type used by every ra8-firmware API.
size_t strlen(const char *s)
Calculate string length.
uint32_t priv_ra8_svgp_paint(const uint8_t *s, size_t len)
Parse an SVG paint value ('rgb'/'rrggbb'/name/'none') to 0x00RRGGBB.
int32_t priv_ra8_svgp_num(const uint8_t *s, size_t len, size_t *i)
Parse the integer part of one SVG number at s[*i], skipping leading separators (whitespace / commas);...
bool priv_ra8_svgp_ws(char c)
Test whether a character is XML whitespace.
bool priv_ra8_svgp_attr(const uint8_t *s, size_t len, const char *name, size_t *voff, size_t *vlen)
Find attribute name in tag span s[0..len); return its value slice.
size_t priv_ra8_svgp_find_ci(const uint8_t *s, size_t len, size_t from, const char *lit)
Find the first case-insensitive occurrence of a literal in a byte span.
bool priv_ra8_svgp_starts_ci(const uint8_t *s, size_t len, size_t at, const char *lit)
Test whether a byte span starts with a literal at a given offset, case-insensitively.
int32_t priv_ra8_svgp_attr_num(const uint8_t *s, size_t len, const char *name, int32_t def)
Read an SVG attribute as a signed integer, returning a default when absent.
Minimal SVG handling for the reflow ereader (#112).
ra8_err_t ra8_svg_image_href(const uint8_t *svg, size_t len, size_t *out_off, size_t *out_len)
Extract the href of a cover-wrapper <svg><image .../></svg>.
static uint32_t internal_stop_color(const uint8_t *tag, size_t tlen)
Parse a gradient 'stop' element's 'stop-color' attribute.
ra8_err_t ra8_svg_render(const uint8_t *svg, size_t len, int32_t x, int32_t y, int32_t w, int32_t h)
Render an SVG's vector shapes into a box.
static float internal_clamp01(float v)
Clamp a float value to the unit interval [0, 1].
static void internal_xform_with_group(const svg_xform_t *t, svg_utf_t g, svg_xform_t *out)
Copy the base transform t into out and replace the user affine with g.
static void internal_parse_stops(const uint8_t *s, size_t from, size_t end, svg_grad_t *g)
Parse the 'stop' child elements of a gradient definition into g.
static bool internal_elem_at(const uint8_t *s, size_t len, size_t at, const char *name)
Test whether an element keyword begins at s[at] with a valid delimiter.
static int32_t internal_group_open(const uint8_t *s, size_t i, size_t close, const svg_xform_t *t, svg_utf_t *gstk, int32_t gsp)
Handle a 'g' open tag: compose its 'transform=' over the stack top and push.
static void internal_copy_attr_id(const uint8_t *s, size_t len, char *dst)
Copy the 'id' attribute value into dst as a NUL-terminated string.
bool ra8_svg_is_svg(const uint8_t *bytes, size_t len)
Heuristically decide whether bytes are an SVG document.
static bool internal_tag_span(const uint8_t *s, size_t len, size_t from, const char *name, size_t *open, size_t *close)
Locate the tag span [*open, *close) of element name at or after from.
ra8_err_t ra8_svg_size(const uint8_t *svg, size_t len, int32_t *out_w, int32_t *out_h)
Report an SVG's intrinsic size (width/height, else viewBox dimensions).
static void internal_draw_shapes(const uint8_t *s, size_t len, const svg_xform_t *t)
Walk every element in document order and draw the supported shapes.
static float internal_stop_offset(const uint8_t *tag, size_t tlen)
Parse a gradient 'stop' element's 'offset' attribute.
static float internal_attr_numf(const uint8_t *s, size_t len, const char *name, float def)
Read an SVG attribute as a floating-point number, returning a default when absent.
static void internal_read_viewbox(const uint8_t *s, size_t len, svg_xform_t *t)
Fill t's viewBox fields from the SVG root element.
static const float s_svg_unit
Gradient parameter / offset upper clamp.
static void internal_scan_grads(const uint8_t *s, size_t len, svg_grads_t *gs)
Scan the document for gradient definitions and populate gs.
static void internal_dispatch_shape(const uint8_t *s, size_t len, size_t at, size_t close, const svg_xform_t *t)
Dispatch one element tag span to the appropriate shape-drawing function.
Cross-TU surface for the split minimal-SVG subset (#112).
struct svg_grads svg_grads_t
Forward decl: the document's gradient set (defined after svg_xform_t).
void priv_ra8_svgp_draw_circle(const uint8_t *s, size_t len, const svg_xform_t *t)
Draw one SVG 'circle' element using its fill colour or gradient.
void priv_ra8_svgp_draw_polygon(const uint8_t *s, size_t len, const svg_xform_t *t)
Draw one SVG 'polygon' element as a filled polygon.
void priv_ra8_svgp_draw_polyline(const uint8_t *s, size_t len, const svg_xform_t *t)
Draw one SVG 'polyline' element as connected stroke line segments.
float priv_ra8_svgp_numf(const uint8_t *s, size_t len, size_t *i)
Parse one SVG floating-point number at s[*i], skipping separators.
void priv_ra8_svgp_draw_rect(const uint8_t *s, size_t len, const svg_xform_t *t)
Draw one SVG 'rect' element using its fill colour or gradient.
void priv_ra8_svgp_apply_xform(svg_xform_t *t, const uint8_t *tag, size_t tlen)
Compose the 'transform=' attribute from tag onto t's user affine.
void priv_ra8_svgp_draw_line(const uint8_t *s, size_t len, const svg_xform_t *t)
Draw one SVG 'line' element using its stroke colour.
@ k_svg_bom2
UTF-8 BOM byte 2.
@ k_svg_grad_linear
<linearGradient> kind.
@ k_svg_grad_radial
<radialGradient> kind.
@ k_svg_def_fill
SVG default fill is black.
@ k_svg_grad_max
Max gradients defined per document.
@ k_svg_bom0
UTF-8 BOM byte 0.
@ k_svg_no_paint
none / absent paint sentinel.
@ k_svg_viewbox_n
viewBox number count.
@ k_svg_g_depth_max
Max nested <g> transform depth.
@ k_svg_bom_len
UTF-8 BOM length.
@ k_svg_grad_id
Max gradient id length, bytes.
@ k_svg_bom1
UTF-8 BOM byte 1.
@ k_svg_grad_stops
Max colour stops per gradient.
void priv_ra8_svgp_draw_path(const uint8_t *s, size_t len, const svg_xform_t *t)
Draw one SVG 'path' element as a filled polygon.
A parsed linear/radial gradient in objectBoundingBox units.
float x2
Linear end x / radial radius.
char id[k_svg_grad_id]
NUL-terminated gradient id (for url()).
uint8_t kind
k_svg_grad_linear / k_svg_grad_radial.
float y1
Linear start y / radial centre y.
float y2
Linear end y (unused for radial).
uint8_t nstops
Number of valid stops.
float x1
Linear start x / radial centre x.
svg_stop_t stops[k_svg_grad_stops]
Colour stops, in document order.
svg_grad_t g[k_svg_grad_max]
The gradient table.
int32_t n
Number of valid gradients (<= k_svg_grad_max).
float off
Stop offset, clamped to [0,1].
uint32_t col
Stop colour, 0x00RRGGBB.
A user transform= as a full 2x3 affine matrix.
float c
Row0 col1 (x shear).
float a
Row0 col0 (x scale).
float b
Row1 col0 (y shear).
float d
Row1 col1 (y scale).