Code
Documentation for a library is mostly code. chimera highlights Luwu, Luau and Lua while it builds the page. Readers download no highlighting script, and the colors follow whichever theme they picked. Squiggles and hovers then explain the code the way an editor would.
Code blocks
const function greet(name: string, greeting = "Hello")
print(`{greeting}, {name}!`)
end
const greet = CodeBlock([==[
const function greet(name: string, greeting = "Hello")
print(`{greeting}, {name}!`)
end
]==])
:line_numbers()
:copyable()
copyable() adds the copy button in the corner, and line_numbers() adds the gutter. Selecting the code never picks up the numbers.
Inline code
Call site:build("out") to write every page.
const tip = Paragraph({ "Call ", Code("site:build(\"out\")"), " to write every page." })
Every <code> tag is a Code, highlighted as Luwu unless you name another language.
Languages
The language is the second argument: CodeBlock("cargo build", "bash"). Other languages are highlighted in the browser by highlight.js, and a page only loads it when it has code that needs it. "plaintext" isn't highlighted at all, and plain() turns the colors off for a single block.
Squiggles
A Squiggle underlines a span of code the way an editor marks an error and shows its message when the reader points at it:
local name = "Ada"
print(nmae)
const typo = CodeBlock("local name = \"Ada\"\nprint(nmae)")
:line_numbers()
:squiggle(
Squiggle.error(SourceSpan.on_line(2, 7, 10), "Unknown global 'nmae'"),
Squiggle.info(SourceSpan.on_line(1, 7, 10), "'name' is only used once")
)
Squiggle.error, Squiggle.warning and Squiggle.info use the theme's editor colors. For any other color, use Squiggle(spans, color, message).
Each span is a SourceSpan: a start and an end, both a line and a column. SourceSpan.on_line(2, 7, 10) covers columns 7 to 10 of line 2, and SourceSpan.from_string("2.7-2.10") reads the spans that luwu-analyze --formatter=gnu prints.
Hovers
A Hover shows content when the reader points at part of the code. A dotted underline tells them what to try. On a phone, tap it:
const cat = Cat("Nyla")
cat:feed(2)const cat: Cat
function Cat:feed(amount: number): Cat
Feeds the cat, so it's less hungry.
const hovered = CodeBlock("const cat = Cat(\"Nyla\")\ncat:feed(2)")
:hover(
Hover(SourceSpan.on_line(1, 7, 9), CodeBlock("const cat: Cat")),
Hover(SourceSpan.on_line(2, 5, 8), {
CodeBlock("function Cat:feed(amount: number): Cat"),
Paragraph("Feeds the cat, so it's less hungry."),
})
)
A hover can hold anything, from plain text to code or your own components, and one over a squiggle shows both. The Better Hovers page uses them to show real hovers from Luwu's language server.
Hover A small, opinionated cat.nyla to meet her.Nyla
const nyla = Code("nyla"):hover(Hover(
SourceSpan.on_line(1, 1, 4),
Card("Nyla", Paragraph("A small, opinionated cat."))
))
const fancy = Paragraph({ "Hover ", nyla, " to meet her." })
Your own code elements
To show code your own way, with a file name above it for example, implement SourceCode. Your class gets highlighting, squiggles and hovers too. Call render_source(out) where the code goes:
class FileSnippet implements SourceCode
function tag(): string
return "figure"
end
function __init(self, file: string?, source: string?, language: Language?)
self.source = source or ""
self
:attr("data-file", file)
:attr("data-language", language or "luwu")
end
function render(self, out: Writer)
self:render_open(out)
out:write(`<figcaption>{Text.escape(tostring(self:get_attr("data-file")))}</figcaption>`)
out:write(`<pre><code class="language-{self:language()}">`)
self:render_source(out)
out:write("</code></pre></figure>")
end
end