This backtrack is semi-related to the Zip Backtrack and expands on the dialect principle used for the Zip/Build function.
It's a departure from the Parse-approach to dialecting and one that I took to try to sail a little closer to the way PDFs are structured.
Create
The pdf/create
function takes a block!
and evaluates its contents in a context containing helper functions. The result should be a completely modeled PDF document ready for serialization:
doc: pdf/create [
info [
title "A Document"
author "@rgchris"
]
add-page 640x480 [
; supported colors:
; RGB 0.0.0 - 255.255.255
; Gray 0 - 100
; CMYK 0.0.0.0 - 100.100.100.100
;
set-fill 0.100.100.0
set-pen 0.0.0.0
; several helper functions are available in page context for
; altering the graphics state
;
set-line-width 2
; other helper functions apply graphics to the page
;
draw none non-zero [
rectangle 20x20 600x440
]
draw line none [
rectangle 530x370 50x50
]
set-dash-array [4 5] 2
set-line-cap 'round
draw line none [
move-to 0x0
curve-to
as-pair 0 page/height
as-pair page/width 0
as-pair page/width page/height
]
]
add-page 200x200 [
set-pen 204.0.0
set-fill 10
set-line-width 2
; PUSH creates an isolated graphics state in which changes
; do not affect subsequent graphics operations
;
push [
set-pen 80
draw line none [
repeat offset 21 [
move-to as-pair 0 offset - 1 * 10 0
line-to as-pair 200 offset - 1 * -10 + page/height
]
]
]
; this retains the red pen from before the PUSH
;
draw line even-odd [
rectangle 20x85 30x30
]
]
; fonts/text not yet implemented, this is a no-op
;
add-font /Helvetica [
spec
]
]
Some functions can be used outside the pdf/create
context:
pdf/add-page doc 400x200 [
set-pen 10
draw line non-zero [
move-to reduce [
50 page/height - 50
]
line-to 50x100
line-to 100x100
line-to 100x50
close-path
]
]
The model can be serialized using the pdf/render
function:
probe pdf/render doc
Relevance
The context-sensitive functions give both an appearance of dialecting and the transparency and rigor of being regular functions. I think the function specialization in Ren-C would really make this an efficient and scalable approach.