I have a small FFI Helper demo using cairo. I used my ffi-helper, all written in Guile Scheme, to generate a (ffi cairo) module, in Scheme, from cairo.h.
Now compare the program below to the demo at https://www.cairographics.org/samples/text_extents/ Some notes: 1) The FFI Helper uses the bytestructures package to deal with C structs. The bs-ref macro defined below is used to save typing. 2) The FFI Helper uses Guile structs to wrap types: scheme@(guile-user)> extents $1 = #<cairo_text_extents_t 0x1079aaa70> scheme@(guile-user)> te $2 = #<bytestructure 0x108709930> scheme@(guile-user)> 3) The procecure fh-object-val gets the object value (often a bytestructure) from the FFI-helper type. 4) You can use quoted symbols where enums are used in C code. 5) You can use strings in Scheme and the unwrapper within (ffi cairo) will apply string->pointer for you. 6) For reference, cairo.h contains typedef struct { double ascent; double descent; double height; double max_x_advance; double max_y_advance; } cairo_font_extents_t; 7) Below is a full script. If saved as demo.scm, `guile demo.scm' will generate the expected .png file. (use-modules (ffi cairo)) (use-modules (system ffi-help-rt)) (use-modules (bytestructures guile)) (define-syntax-rule (bs-ref bs ix ...) (bytestructure-ref bs ix ...)) (define pngfile "te.png") (define srf (cairo_image_surface_create 'CAIRO_FORMAT_ARGB32 600 400)) (define cr (cairo_create srf)) ;; ------------------------------------------------------- ;; Go look at ;; https://www.cairographics.org/samples/text_extents/ ;; and compare to the following. (define extents (make-cairo_text_extents_t)) (define utf8 "cairo") (define x) (define y) (cairo_select_font_face cr "Sans" 'CAIRO_FONT_SLANT_NORMAL 'CAIRO_FONT_WEIGHT_NORMAL) (cairo_set_font_size cr 100.0) (cairo_text_extents cr utf8 (pointer-to extents)) (define te (fh-object-val extents)) (set! x 25.0) (set! y 150.0) (cairo_move_to cr x y) (cairo_show_text cr utf8) ;; draw helping lines (cairo_set_source_rgba cr 1 0.2 0.2 0.6) (cairo_set_line_width cr 6.0) (cairo_arc cr x y 10.0 0 (* 2 3.15)) (cairo_fill cr) (cairo_move_to cr x y) (cairo_rel_line_to cr 0 (- (bs-ref te 'height))) (cairo_rel_line_to cr (bs-ref te 'width) 0) (cairo_rel_line_to cr (bs-ref te 'x_bearing) (- (bs-ref te 'y_bearing))) (cairo_stroke cr) ;; ------------------------------------------------------- (cairo_surface_write_to_png srf pngfile) (cairo_destroy cr) (cairo_surface_destroy srf)
