Skip to content

Instantly share code, notes, and snippets.

@muspellsson
Last active December 10, 2015 03:38
Show Gist options
  • Save muspellsson/4375510 to your computer and use it in GitHub Desktop.
Save muspellsson/4375510 to your computer and use it in GitHub Desktop.
Simple example of loading SVG files with J language and bindings to Cairo and librsvg. It still needs more explanations.
NB. pretty stubby librsvg bindings
coclass 'jrsvg'
NB. define unnamed monad and call it in-place
NB. verb wrapping is needed for control structures
NB. as they work only within explicit definitions
monad define''
select. UNAME
case. 'Linux' do.
librsvg=:<'librsvg-2.so.2'
case. 'Win' do.
librsvg=:<'librsvg-2-2.dll'
end.
EMPTY
)
NB. powerful dark magic here, copied from
NB. other bindings.
NB. Verb for massive loading from DLL
cddef=: dyad define
y=. dtb (y i. ':'){.y
if. 0=#y do. '' return. end.
n=. y i. ' '
f=. n {. y
d=. (_2 * (<_2{.f) e. '_1';'_2';'_3') }. f
if. IFUNIX do.
p=. n }. y
else.
p=. (n+1) }. y
if. '>' = {.p do.
p=. ' >+', }.p
else.
p=. ' +', p
end.
end.
(f)=: (x,' ',d,p)&(15!:0)
''
)
NB. load basic functions from librsvg
librsvg cddef each <;._2 [ 0 : 0
rsvg_handle_render_cairo > i x x
rsvg_handle_new_from_data > x *c x *x
rsvg_handle_get_dimensions > n x x
)
NB. class for our application
coclass 'cairodemo'
coinsert 'jgtk'
coinsert 'jrsvg'
create=: monad define
require 'gtk'
gtkinit_jgtk_''
w=: make_main_window''
s=: 0
run''
)
NB. Open SVG file and return its handle
open_svg_file=: monad define
'f'=. y
NB. I choose the way of prereading file into J memory
try.
sd=. 1!:1 <f
catch.
error'You must select some file!'
0
return.
end.
NB. another piece of black magic, without minus this array
NB. would be unwriteable from DLL procedure
gerr=. ,-0
s=. rsvg_handle_new_from_data sd;(#sd);gerr
if. s do.
d=. mema JINT+JINT+JFL+JFL
rsvg_handle_get_dimensions s,d
NB. W64 librsvg bug?
NB. first dimension isn't correct on W64
dims=. (memr d,0,1,JINT),(memr d,JINT,1,JINT)
memf d
else.
error readerror gerr
0
return.
end.
s;dims
)
run=: monad define
gtk_widget_show_all w
gtk_main''
1
)
ask=: monad define
w filechooser 0;'file_new';(<'*.svg';'SVG images');''
)
error=: monad define
msg=. y
mbox 2;'Error';msg
)
destroy=: monad define
gtk_main_quit''
cbfree''
codestroy''
exit 0
)
make_main_window=: monad define
w=. gtk_window_new GTK_WINDOW_TOPLEVEL
gtk_window_set_default_size w,400 400
gtk_window_set_position w,GTK_WIN_POS_CENTER
gtk_window_set_title w;'Cairo SVG demo'
da=. gtk_drawing_area_new''
gtk_widget_set_size_request da, 400 400
b=. gtk_vbox_new 0 0
gtk_container_add w, b
bt=. gtk_button_new_with_label <'Open SVG'
gtk_box_pack_start b, da, 0 0 0
gtk_box_pack_start b, bt, 0 0 0
consig3 w;'delete-event';'window_delete'
consig bt;'clicked';'open_svg'
consig3 da;'expose-event';'expose_event'
w
)
open_svg=: monad define
'widget data'=. y
't dims'=: open_svg_file ask''
smoutput dims
if. t do. s=:t end.
%~s
)
window_delete=: monad define
'widget event data'=. y
destroy''
1 NB. just for good style
)
expose_event=: monad define
'widget event data'=. y
cr=. gdk_cairo_create getGtkWidgetWindow widget
if. s do. rsvg_handle_render_cairo s,cr end.
cairo_destroy cr
1
)
'' conew 'cairodemo'
@muspellsson
Copy link
Author

Sorry, forgot to add class initialization :)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment