Nilorea Library
C utilities for networking, threading, graphics
Loading...
Searching...
No Matches
n_gui_md.h File Reference

Lay out and draw n_markdown's block model with Allegro fonts. More...

#include <allegro5/allegro.h>
#include <allegro5/allegro_font.h>
#include <nilorea/n_markdown.h>
#include <stddef.h>
Include dependency graph for n_gui_md.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  N_GUI_MD_FONTS
 The faces a render uses. More...
struct  N_GUI_MD_STYLE
 Colours and metrics. More...

Functions

float n_gui_md_draw (const N_GUI_MD_FONTS *fonts, const N_GUI_MD_STYLE *style, float x, float y, float width, const char *text)
 draw text as markdown at (x, y), wrapped to width
float n_gui_md_height (const N_GUI_MD_FONTS *fonts, const N_GUI_MD_STYLE *style, float width, const char *text)
 height of text laid out as markdown at width, in pixels
int n_gui_md_link_at (const N_GUI_MD_FONTS *fonts, const N_GUI_MD_STYLE *style, float x, float y, float width, const char *text, float px, float py, char *url, size_t url_cap)
 the url of the link under (px, py), if there is one
void n_gui_md_style_default (N_GUI_MD_STYLE *out, ALLEGRO_COLOR text, ALLEGRO_COLOR background, float line_height)
 fill a style from two colours and a line height

Detailed Description

Lay out and draw n_markdown's block model with Allegro fonts.

The renderer half of n_markdown: it takes the text, parses it, and turns the blocks and styled spans into glyph runs at a given width. Bold, italic and code runs get their own face, a link gets its own colour and can be hit-tested, and paragraphs, headings, quotes, code blocks, lists and tables get vertical structure.

n_gui_md_height() and n_gui_md_draw() walk identically – the measure pass is the draw pass with the per-line callback left off – so a caller that caches a height cannot drift from what is painted. n_gui_md_link_at() is the same walk again.

It depends on Allegro and on n_markdown, and deliberately not on n_gui: a caller lays these out inside its own chat bubble, list row or window without the widget system, and N_GUI_TYPE_MARKDOWNVIEW is a thin widget over this for the callers that do want one.

Nothing here is retained: every call parses, lays out and frees. A caller drawing the same long text every frame should be doing it only on the frames it actually redraws.

Author
Castagnier Mickael
Version
1.0

Definition in file n_gui_md.h.


Data Structure Documentation

◆ N_GUI_MD_FONTS

struct N_GUI_MD_FONTS

The faces a render uses.

Any of them may be NULL and falls back towards regular, so a caller that has only one font still gets its text, only without the emphasis; regular itself must be set.

Examples
ex_gui_md.c.

Definition at line 65 of file n_gui_md.h.

Collaboration diagram for N_GUI_MD_FONTS:
Data Fields
ALLEGRO_FONT * bold bold
ALLEGRO_FONT * bolditalic both at once
ALLEGRO_FONT * h1 "# " headings, ideally the bold face at a larger size
ALLEGRO_FONT * h2 "## " headings
ALLEGRO_FONT * h3 "### " and deeper
ALLEGRO_FONT * italic italic
ALLEGRO_FONT * mono code and fenced code blocks
ALLEGRO_FONT * regular body text, and the fallback for every other face.

Must not be NULL.

◆ N_GUI_MD_STYLE

struct N_GUI_MD_STYLE

Colours and metrics.

n_gui_md_style_default() fills one from a text and a background colour; a caller with a palette of its own should set the fields it cares about afterwards.

Examples
ex_gui_md.c.

Definition at line 87 of file n_gui_md.h.

Collaboration diagram for N_GUI_MD_STYLE:
Data Fields
float block_gap vertical space between two blocks, in pixels
float cell_pad padding inside a table cell, left and right
ALLEGRO_COLOR code code and code block text
ALLEGRO_COLOR code_bg the panel behind a fenced code block, and behind inline code
float col_min narrowest a table column may be squeezed to, in pixels
int hard_breaks Non-zero to break a paragraph where its source breaks, which is what a chat message wants: somebody pressed Return there and meant it.

Zero reflows the paragraph to the width it is given and treats a single newline as a space, which is what Markdown says and what a document wants – a manual is hard-wrapped at some column by whoever wrote it, and honouring that column in a pane of a different width breaks every paragraph in the wrong places. A fenced code block keeps its own line breaks either way.

ALLEGRO_COLOR heading heading text
float indent how far a quote, a list item's text and a code block are indented
ALLEGRO_COLOR link link text
unsigned parse_flags n_markdown parse flags.

N_MARKDOWN_ALL is what a document wants; zero is the safe chat subset, with a heading line and a table row left as the text they are.

ALLEGRO_COLOR quote a blockquote's text, and its bar
ALLEGRO_COLOR rule the rule under a heading and under a table's header row
ALLEGRO_COLOR text body text

Function Documentation

◆ n_gui_md_draw()

float n_gui_md_draw ( const N_GUI_MD_FONTS * fonts,
const N_GUI_MD_STYLE * style,
float x,
float y,
float width,
const char * text )

draw text as markdown at (x, y), wrapped to width

Draws into the current Allegro target with the current transform and clipping rectangle; a caller wanting the overflow clipped sets one.

Parameters
fontsthe faces. Must not be NULL, nor fonts->regular.
stylecolours and metrics. Must not be NULL.
xleft edge
ytop edge
widththe width to wrap to, in pixels
textthe markdown source. NULL is treated as empty.
Returns
the height used, equal to n_gui_md_height() for the same inputs

Definition at line 657 of file n_gui_md.c.

References MD_DRAW, md_run(), and N_GUI_MD_FONTS::regular.

Referenced by _draw_markdownview(), and main().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ n_gui_md_height()

float n_gui_md_height ( const N_GUI_MD_FONTS * fonts,
const N_GUI_MD_STYLE * style,
float width,
const char * text )

height of text laid out as markdown at width, in pixels

The same walk n_gui_md_draw() makes, with nothing drawn, so the two agree to the pixel. Independent of any y: measuring at the origin gives the height a draw anywhere will use.

Parameters
fontsthe faces. Must not be NULL, nor fonts->regular.
stylecolours and metrics. Must not be NULL.
widththe width to wrap to, in pixels
textthe markdown source. NULL is treated as empty.
Returns
the height in pixels, never negative

Definition at line 651 of file n_gui_md.c.

References MD_MEASURE, md_run(), and N_GUI_MD_FONTS::regular.

Referenced by _markdownview_measure(), and main().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ n_gui_md_link_at()

int n_gui_md_link_at ( const N_GUI_MD_FONTS * fonts,
const N_GUI_MD_STYLE * style,
float x,
float y,
float width,
const char * text,
float px,
float py,
char * url,
size_t url_cap )

the url of the link under (px, py), if there is one

Lays the text out exactly as n_gui_md_draw() would at the same position and width, and reports the link whose glyph cell the point falls in.

Parameters
fontsthe faces. Must not be NULL, nor fonts->regular.
stylecolours and metrics. Must not be NULL.
xleft edge the text would be drawn at
ytop edge
widththe width it would wrap to
textthe markdown source. NULL is treated as empty.
pxthe point to test
pythe point to test
urlreceives the url, NUL-terminated and bounded by url_cap
url_capsize of url
Returns
1 when a link was under the point and url was written, else 0

Definition at line 663 of file n_gui_md.c.

References md_hit::cap, md_hit::found, MD_HIT, md_run(), md_hit::out, md_hit::px, md_hit::py, and N_GUI_MD_FONTS::regular.

Referenced by main(), and n_gui_process_event().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ n_gui_md_style_default()

void n_gui_md_style_default ( N_GUI_MD_STYLE * out,
ALLEGRO_COLOR text,
ALLEGRO_COLOR background,
float line_height )

fill a style from two colours and a line height

The derived colours are the obvious ones: a heading and body text share a colour, a link is blue, code sits on a panel lifted or dropped from the background depending on which is darker. The metrics are fractions of line_height, so they follow the font.

Parameters
outthe style to fill. Must not be NULL.
textbody text colour
backgroundwhat the text is drawn on, used to derive the code panel
line_heightthe regular face's line height, in pixels

Definition at line 622 of file n_gui_md.c.

References background(), N_GUI_MD_STYLE::block_gap, N_GUI_MD_STYLE::cell_pad, N_GUI_MD_STYLE::code, N_GUI_MD_STYLE::code_bg, N_GUI_MD_STYLE::col_min, N_GUI_MD_STYLE::hard_breaks, N_GUI_MD_STYLE::heading, N_GUI_MD_STYLE::indent, N_GUI_MD_STYLE::link, md_fade(), N_MARKDOWN_ALL, N_GUI_MD_STYLE::parse_flags, N_GUI_MD_STYLE::quote, N_GUI_MD_STYLE::rule, and N_GUI_MD_STYLE::text.

Referenced by _markdownview_follow_theme(), and main().

Here is the call graph for this function:
Here is the caller graph for this function: