Search code examples
plotclojureclojurescriptvega-lite

Clojure Oz/View! Not Connecting to Browser


I'm trying to do some (simple) plots in Clojure and it seems like Oz would be a great long term solution. However, I'm running into problems just trying to get the example code to run. PS I'm completely new to ClojureScript / Reagent / Hiccup ...

On the website it shows the following example code:

(defn play-data [& names]
  (for [n names
        i (range 20)]
    {:time i :item n :quantity (+ (Math/pow (* i (count n)) 0.8) (rand-int (count n)))}))

(def line-plot
  {:data {:values (play-data "monkey" "slipper" "broom")}
   :encoding {:x {:field "time" :type "quantitative"}
              :y {:field "quantity" :type "quantitative"}
              :color {:field "item" :type "nominal"}}
   :mark "line"})

;; Render the plot
(oz/view! line-plot)

For me, (oz/view! ...) creates a blank page in my browser but no plots actually get outputted. Can someone help me figure out what's going on? How I do check that Oz even connected to the browser directly? How did Oz figure out which browser to use (I'm currently using Brave)?


Solution

  • Try something like the following, which uses my favorite template project.

    (ns tst.demo.core
      (:use tupelo.core tupelo.test)
      (:require
        [oz.core :as oz]
        ))
    
    (defn play-data [& names]
      (for [n names
            i (range 20)]
        {:time i :item n :quantity (+ (Math/pow (* i (count n)) 0.8) (rand-int (count n)))}))
    
    (defn line-plot []
      {:data     {:values (play-data "monkey" "slipper" "broom")}
       :encoding {:x     {:field "time" :type "quantitative"}
                  :y     {:field "quantity" :type "quantitative"}
                  :color {:field "item" :type "nominal"}}
       :mark     "line"})
    
    (dotest
      ; Render the plot
      (println \newline "calling (oz/start-server!)")
      (oz/start-server!) ; this is optional and is implied by oz/view!
    
      (println \newline "calling (oz/view! (line-plot))")
      (oz/view! (line-plot))
    
      (println \newline "sleeping")
      (Thread/sleep 5000)
    )
    

    with result:

     calling (oz/start-server!)
    21-04-14 22:21:15 brandy INFO [oz.server:142] - Web server is running at `http://localhost:10666/`
    Opening in existing browser session.
    21-04-14 22:21:16 brandy INFO [oz.server:50] - Connected uids change: {:ws #{"b75d3026-919f-4927-a43c-ce678167348d"}, :ajax #{}, :any #{"b75d3026-919f-4927-a43c-ce678167348d"}}
    
     calling (oz/view! (line-plot))
    
     sleeping
    

    You need to either sleep a few seconds, read input, or otherwise keep the thread alive. If not, the thread seems to exit before the info is transmitted from the JVM to the browser.

    The result looks like this (using Chrome):

    enter image description here

    Internally, Oz uses clojure.java.browse, which internally uses java.awt.Desktop to open the default browser.