Field / Clojure / Incanter

Field has support for other languages and runtimes — Java, Clojure, Processing, Scala. Recently we've been taking a closer look at Clojure, which, in addition to being a very interesting language and runtime in its own right, is also accumulating some very interesting libraries.

One such library is Incanter a statistics and graphics environment. The usual use of such a library is from a command line REPL — either raw or embedded in something like Emacs. What happens if we embed these libraries in Field instead?

  • A Field sheet containing the code for this page can be downloaded here.

Warning: adding Incanter to Field adds it's internal build of Processing to Field. This clashes with the ProcessingPlugin's support for Processing 2.0aX and will cause the ProcessingPlugin to fail to redraw

Hello Incanter

First we need a working Field / Clojure / Incanter installation. Best way to do this for our purposes here is to download Incanter itself (from here) and add the incanter.jar file (it's hiding inside the .app package) to Field. Just drag it into the Plugin manager here and restart Field. While you are in the Plugin manager, also add the "wrap in transform" plugin.

Finally, after a restart of Field, initialize Clojure in the languages tab:

Now we can start working in Incanter:

(use '(incanter core charts datasets pdf))
(def x (function-plot sin (* -2 Math/PI) (* 2 Math/PI)))
(view x)

Using the new drop down box in the toolbar of the text editor we can tell Field that everything in the text editor (for this element) is actually going to be in Clojure. This gives us line by line execution of Clojure. Quickly we get something like this:

Drawing on the canvas directly

This is already great fun — we can interactively fire off bits and pieces of Incanter from inside Field. But the new windows that pop up to visualize the stats are disappointing. We already have a place for graphics — the canvas, can we have Incanter draw their instead?

Yes we can. In the example above we assigned the thing that we were going to (view ... ) to the Clojure variable x. In Field we can grab this part of Clojure's namespace and call methods on it. The latest version of Field comes with a java.awt.Graphics2D -> PLine bridge. So:

from java.awt.geom import Rectangle2D

target = FieldGraphics2D2()
_clojure.x.draw(target, Rectangle2D.Float(0,0,400,400))
_self.lines.clear()

_self.lines.addAll([n(derived=1, offsetFromSource=Vector2(0,0) ) for n in target.geometry])
_self.optimizeLines()

Draws whatever (view ... ) was going to draw in a new window directly into a FLine drawing element (see BasicDrawing).

For the avoidance of doubt, that geometry is just Field FLine objects, and are subject to any kind of post-processing transformation you might be interested in: