Home Pictures of 3D objects
Using GlowScript
as a JavaScript library

By far the *easiest* way to embed a glowscript program in your web page is to edit it at glowscript.org and then use the "Share" feature to get HTML source, which can be inserted into your own web page. This is easiest because the glowscript.org environment applies a number of transformations of GlowScript programs to add operator overloading for vectors and the ability to write infinite loops and yet update the window.

A knowledgable JavaScript programmer should be able to make use of the 'glow' JavaScript library directly, and this could make sense for some purposes.  One would have to write a tiny bit of initialization boilerplate to create a canvas, and one would have to write in pure JavaScript, without operator overloading and with function callbacks. The program must not include options such as rate or waitfor, and the following vector operations must be rewritten as shown, where A and B are vectors and k is an ordinary number:

A+B -> A.add(B)
A-B -> A.sub(B)
k*A -> A.multiply(k)
A/k -> A.divide(k)

Here is a minimal working example HTML file. If you copy the program from here, be sure to delete the new line and extra spaces in the http strings.

<div id="glowscript" class="glowscript">
<script type="text/javascript"        src="https://s3.amazonaws.com/glowscript/lib/
            jquery/2.1/jquery.min.js"></script>

<script type="text/javascript"        src="https://s3.amazonaws.com/glowscript/lib/
            jquery/2.1/jquery-ui.custom.min.js"></script>
<script type="text/javascript"        src="https://s3.amazonaws.com/glowscript/package/
            glow.2.7.min.js"></script>

<script type="text/javascript">
       window.__context = { glowscript_container:        $("#glowscript").removeAttr("id") }

var scene = canvas()
var b = box()

function spin() {
   b.rotate({angle:0.01, axis:vec(0,1,0)})
   rate(100, spin) // make spin a callback
}

spin()

</script>
</div>

Additional considerations

As in the use of the rate function in the example above, you need to use your own callback function to be called when the condition is met. For example, scene.waitfor('click) blocks, waiting for the user to click before executing the following statement. You can instead establish a callback function to be executed when the user clicks, as is illustrated by the use of scene.bind for handling keyboard and mouse events.

The function read_local_file() can be used in two ways, as shown below. The first form blocks, waiting for the user to choose a file before the following statement is executed. This blocking form is not available without using the preprocessing available at glowscript.org.

The second form establishes a callback function which will be executed when the user has chosen a file. If there are no errors, the callback function will receive two arguments, with the first argument ("err") equal to null. If there is an error, the callback function will receive one argument, the error code. In the case of the read_local_file() function, an error would presumably occur only in case of a disk error.

// Blocking; not available:
var g = read_local_file()
print(g.text)

// Nonblocking:
function get(err, f) {
    // First argument ("err") is always
    // null for read_local_file().
    print(f.text)
}
read_local_file(get) // establish callback

The function get_library() times out if the library cannot be loaded and posts an alert to the user, asking whether the user wants to attempt the operation again. Here is one way to use this function:

var loaded = false
var load = function() { loaded = true }

get_library(file, load)

var wait_for_load = function() {
  if (loaded) {
    print('Got library')
    // use the library
  } else {
    rate(30,wait_for_load)
  }
}

wait_for_load()
while (!loaded) {
  rate(30)
}
print('Library is loaded')

The same structure can be used with scene.waitfor('textures',load), with the difference that there is no timeout; if any of the textures requested for objects cannot be found, the load() function will never be called. This structure can also be used with scene.pause('Click to see something',load).

 

Top of page