Tau

FPS:

Click on the boxes below to start the automatons. (256x256 rule 30 1D CA)

The main thread automatons will quickly bog down the main thread.

Automatons on the tauons will do all work off the main thread.

(note: to try this example, you must enable SharedArrayBuffers via chrome://flags)

main thread:

on tauon:

Example code for automatons running off main thread.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
(ns tau.alpha.example.core
  (:require [tau.alpha.core :refer [on-screen? tauon tau get-id]]
            [tau.alpha.example.automata :refer [get-frame make-initial-conditions]]
            [tau.alpha.example.utils :refer [raf on-click actx]]))

(def local-store (atom {}))

(defn paint-automaton [ctx width height iref]
  (let [idata (.createImageData ctx width height)]
    (.set (.-data idata) @iref)
    (.putImageData ctx idata 0 0 0 0 width height)))

(defn process-results [tau]
  (raf
   #(let [{:keys [ctx width height on?]} (@local-store tau)]
      (paint-automaton ctx width height tau)
      (swap! on? (constantly @on?)))))

(defn swap-on! [tauon tau work-fn]
  (on tauon [tau work-fn]
    (swap! tau work-fn)
    (on "screen" [tau]
      (process-results tau))))

(defn run-loop-once [on? tau]
  (when @on?
    (let [{:keys [tauon]} (@local-store tau)]
      (swap-on! tauon tau get-frame))))

(defn setup-tauon [{:keys [width] :as automaton}]
  (let [tauon (tauon)
        tau (tau (make-initial-conditions width) :ab true :size (* width width 4))]
    (swap! local-store assoc tau
           (merge automaton {:on? (atom false) :tauon tauon :tau tau}))
    (@local-store tau)))

(defn start-automaton [on? tau]
  (swap! on? not)
  (run-loop-once on? tau))

(defn hookup-automaton [astr]
  (let [{:keys [canvas] :as automaton} (actx astr)
        {:keys [tau on?]} (setup-tauon automaton)]
    (on-click canvas #(start-automaton on? tau))
    (add-watch on? tau #(run-loop-once on? tau))))

(when (on-screen?)
  (hookup-automaton "a-div")
  (hookup-automaton "b-div")
  (hookup-automaton "c-div")
  (hookup-automaton "d-div")
  (hookup-automaton "e-div")
  (hookup-automaton "f-div"))