Jreality with Jruby

A place to discuss advanced projects and high-level topics.
Post Reply
BrunoGardin
Posts: 7
Joined: Sat 31. Jan 2009, 16:52
Location: Guyancourt France

Jreality with Jruby

Post by BrunoGardin » Sun 1. Feb 2009, 19:12

As recommended by Gunn, i share one of my example that runs a viewerApp in jruby.
In addition to java and jreality lib you need to install ruby which is a script language that i find very elegant and jruby which is an implementation ruby on java. You should find installation tips for your platform on the web. In my case i am running jruby 1.1.5 on a linux platform but this should work on other platforms as well.
Now it is quite simple. Move to the JReality tutorial directory.
Like with java, declare your java CLASSPATH including jReality.jar and lib/jtem-beans.jar. Copy the following example in a file names test.rb, place gridSmall.jpg texture file in the same directory and just run jruby test.rb. This example implement the cylinder with a texture.

Code: Select all

require 'java'
import 'java.io.IOException'
import 'java.net.URL'
import 'java.awt.Color'

import 'de.jreality.geometry.Primitives' 
import 'de.jreality.reader.Readers'
import 'de.jreality.ui.viewerapp.ViewerApp'
import 'de.jreality.scene.data.AttributeEntityUtility'

class MainWindow
include_package 'de.jreality.shader'
include_package 'de.jreality.util'
include_package 'de.jreality.scene'
include_package 'de.jreality.math'

def initialize
# Scene, Viewerapp setting
  myscene = SceneGraphUtility.createFullSceneGraphComponent("myscene")
  myscene.setGeometry(Primitives.cylinder(20))
  va = ViewerApp.display(myscene)
  va.setAttachNavigator(true)
  va.setExternalNavigator(false)
  va.update
  CameraUtility.encompass(va.getViewerSwitch)
  ap = myscene.getAppearance
# Geometry setting
  dgs = ShaderUtility.createDefaultGeometryShader(ap, true)
  dgs.setShowLines(false)
  dgs.setShowPoints(false)
  dps = dgs.createPolygonShader("default")
  dps.setDiffuseColor(Color.white)
# Texture setting with matrix scaling
  tex2d = AttributeEntityUtility.createAttributeEntity(Texture2D.java_class, CommonAttributes::POLYGON_SHADER + "." + CommonAttributes::TEXTURE_2D,ap, true)
  is = URL.new("file:///root/workspace/jreality/tutorial/gridSmall.jpg")
  id = ImageData.load(Input.new(is))
  tex2d.setImage(id)
  matrix = Matrix.new
  MatrixBuilder.euclidean.scale(10.0, 5.0, 1.0).assignTo(matrix)
  tex2d.setTextureMatrix(matrix)
end
end
MainWindow.new
Rubyer

User avatar
gunn
Posts: 323
Joined: Thu 14. Dec 2006, 09:56
Location: TU Berlin
Contact:

Post by gunn » Mon 2. Feb 2009, 16:35

I was able to get the code to run quite easily. I changed to URL reference to be a reference to a copy of gridSmall.jpg sitting on the jReality web site so every user doesn't have to edit the filename for his filesystem. And I added what's needed to $CLASSPATH and $JAVA_LIBRARY_PATH to get the JOGL backend to work. Finally, I put the resulting test.rb file into the src-tutorial folder in the de/jreality/tutorial/misc folder, along with directions for use as comments at top of the file. That's now checked into the svn repository. So any jReality users interested in playing with jruby and jReality together can access the example there. And at some point we'll need to add an entry in the Developer's Tutorial pointing to this example.

BTW: I didn't have to download ruby ... are you sure ruby is required?

Thanks again for the contribution. Keep us updated on any news in this direction.
jReality core developer

BrunoGardin
Posts: 7
Joined: Sat 31. Jan 2009, 16:52
Location: Guyancourt France

Post by BrunoGardin » Mon 2. Feb 2009, 19:26

No i am not completely sure that ruby is required but cannot test without it very easily. I am actually converting some other examples and will post them when available. If you need another form, just let me know.
Regards.
Rubyer

BrunoGardin
Posts: 7
Joined: Sat 31. Jan 2009, 16:52
Location: Guyancourt France

Post by BrunoGardin » Mon 2. Feb 2009, 22:02

Here is a second example that start the viewerVR with an icosahedron inside. All the viewerVR features seems to work prefectly. Of course youneed to add the lib/vrData.jar and lib/vrExamples.jar in the CLASSPATH. Hereafter are the 26 lines of jruby code. Great result!

Code: Select all

require 'java'
import 'java.io.IOException'
import 'java.net.URL'
 
import 'de.jreality.reader.Readers'
import 'de.jreality.ui.viewerapp.ViewerApp'
import 'de.jreality.geometry.Primitives' 
import 'java.awt.Color'

class MainWindow
include_package 'de.jreality.shader'
include_package 'de.jreality.util'
include_package 'de.jreality.scene'
include_package 'de.jreality.vr'

def initialize
  scp = SceneGraphUtility.createFullSceneGraphComponent("myscene")
  scp.setGeometry(Primitives.icosahedron)
  vvr = ViewerVR.createDefaultViewerVR(nil)
  vvr.setContent(scp)
  va = vvr.display
  va.update
  va.display
end
end
 MainWindow.new
Rubyer

User avatar
gunn
Posts: 323
Joined: Thu 14. Dec 2006, 09:56
Location: TU Berlin
Contact:

Post by gunn » Tue 3. Feb 2009, 21:58

Thanks for the ViewerVR example. I'll include it with the first example in the tutorial package.

I was inspired by the jruby connection to revive some older code that I had written to connect jReality to two other scripting languages, jython and groovy. I've added these to the tutorial package in jReality svn repository (src-tutorial/de/jreality/tutorial/misc) in the same package with the jruby example, and have added usage directions in the Developer Tutorial.

Anyone out there care to offer a brief comparison of the strengths and weaknesses of these three alternative scripting languages? No flaming, of course. :roll:
jReality core developer

olaf
Posts: 16
Joined: Mon 16. Feb 2009, 05:24
Location: Australia
Contact:

Post by olaf » Wed 25. Feb 2009, 07:32

I've used both Python and Ruby in larger projects, and they are pretty much in the same league. Personally, I prefer Python, but that's mostly a matter of taste.

From memory, I found it a bit more difficult to interface with existing Java libraries from JRuby than from Jython. But that might have changed in the meantime. If I find time, I'll dust off some of my old code and look at that issue again.

While we're at it, I'd like to mention Scala as another very useful language based on the JVM. It is a compiled language, but can be used interactively from a command line. The syntax is very clean and concise, and interoperability with Java is very smooth. Basically, Scala has analogues to all the interesting features of Ruby and Python combined while also offering the advantages of a static, compiled language. I've done some experimenting with Scala and JReality lately and found it a quite pleasant experience. I can post some example code if anyone's interested.

User avatar
gunn
Posts: 323
Joined: Thu 14. Dec 2006, 09:56
Location: TU Berlin
Contact:

Post by gunn » Wed 25. Feb 2009, 10:28

Thanks for the feedback on scripting languages. Regarding Scala, I'd be interested to see an example of Scala working with jReality. Eventually it might even find its way into the developer's tutorial.
jReality core developer

olaf
Posts: 16
Joined: Mon 16. Feb 2009, 05:24
Location: Australia
Contact:

Post by olaf » Wed 25. Feb 2009, 14:17

Here's a quick translation of de.jreality.tutorial.too.DragEventTool01:

Code: Select all

package org.gavrog.scratch

import java.awt.Color

import scala.collection.mutable.ArrayBuffer

import de.jreality.geometry.Primitives
import de.jreality.scene.{Appearance, SceneGraphComponent}
import de.jreality.scene.data.{Attribute, StorageModel}
import de.jreality.shader.{DefaultLineShader, DefaultPointShader, ShaderUtility}
import de.jreality.tools.{DragEventTool, PointDragEvent, PointDragListener}
import de.jreality.ui.viewerapp.ViewerApp

object DragEventTool01 {
  def main(args: Array[String]) {
    ViewerApp.display(new SceneGraphComponent {
      setGeometry(Primitives.icosahedron)
      
      setAppearance(new Appearance {
        val dgs = ShaderUtility.createDefaultGeometryShader(this, true)
        val dls =
          dgs.createLineShader("default").asInstanceOf[DefaultLineShader]
        dls.setDiffuseColor(Color.yellow)
        dls.setTubeRadius(.03)
        val dpts =
          dgs.createPointShader("default").asInstanceOf[DefaultPointShader]
        dpts.setDiffuseColor(Color.red)
        dpts.setPointRadius(.05)
      })

      addTool(new DragEventTool {
        addPointDragListener(new PointDragListener {
          def pointDragStart(e: PointDragEvent) =
            println("drag start of vertex no " + e.getIndex)		
          
          def pointDragged(e: PointDragEvent) {
            val pointSet = e.getPointSet
            val points = new Array[Array[Double]](pointSet.getNumPoints)
            pointSet.getVertexAttributes(
              Attribute.COORDINATES).toDoubleArrayArray(points)
            points(e.getIndex) = e.getPosition
            pointSet.setVertexAttributes(
              Attribute.COORDINATES,
              StorageModel.DOUBLE_ARRAY.array(3).createReadOnly(points))
          }	
	
          def pointDragEnd(e: PointDragEvent) {}
        })
      })
    })
  }
}

olaf
Posts: 16
Joined: Mon 16. Feb 2009, 05:24
Location: Australia
Contact:

Post by olaf » Wed 25. Feb 2009, 15:01

Here's the transcript of an interactive session, with some slight editing to make it more readable. As you see somewhere in the middle, I didn't quite manage to get the jogl backend to work in this case, but I imagine that's only a matter of finding the right incantations.

Code: Select all

olaf@olaf-laptop:~/scratch$ ./jrscala 
Welcome to Scala version 2.7.3.RC1 (Java HotSpot(TM) Server VM, Java 1.6.0_07).
Type in expressions to have them evaluated.
Type :help for more information.

scala> import de.jreality._
import de.jreality._

scala> import scene._
import scene._

scala> val cmp = new SceneGraphComponent
cmp: de.jreality.scene.SceneGraphComponent = [...]

scala> import ui.viewerapp.ViewerApp
import ui.viewerapp.ViewerApp

scala> ViewerApp.display(cmp)
Possibly no jogl libraries in java.library.path!
scene root is root
res0: de.jreality.ui.viewerapp.ViewerApp = de.jreality.ui.viewerapp.ViewerApp@aea5cd

scala> import geometry._
import geometry._

scala> cmp.setGeometry(Primitives.icosahedron)

scala> val ap = new Appearance
ap: de.jreality.scene.Appearance = [...] 

scala> import shader.CommonAttributes._
import shader.CommonAttributes._

scala> import java.awt.Color._
import java.awt.Color._

scala> ap.setAttribute("lineShader.diffuseColor", YELLOW) 

scala> cmp.setAppearance(ap)

User avatar
steffen
Posts: 186
Joined: Fri 16. Jun 2006, 13:30
Location: TU Berlin
Contact:

Post by steffen » Wed 25. Feb 2009, 18:59

Possibly no jogl libraries in java.library.path!
Maybe that is the problem? pass -Djava.library.path=... to the jvm, see Documentation->Getting Started.

olaf
Posts: 16
Joined: Mon 16. Feb 2009, 05:24
Location: Australia
Contact:

Post by olaf » Thu 26. Feb 2009, 01:07

Okay, problem identified. In the interactive example above, I had used a little script that populates the CLASSPATH and then calls the scala command, which is also a script. According to the documentation, it should accept -D arguments, but apparently it doesn't pass them to the JVM correctly. So I changed my script to call java directly, and now jReality gives me a JOGL viewer instead of just the software one.

Here's the script I'm using in case anyone would like to try. If a class argument is given, its main method is executed, otherwise Scala comes up in interactive mode. Obviously, the two lines near the top have to be adjusted to point to wherever your jReality and your Scala installations live.

Code: Select all

#!/bin/sh

SCALA=$HOME/Software/scala-2.7.3.RC1
JREALITY=$HOME/eclipse-workspace/jreality

CLASSPATH=.:$JREALITY/bin

for file in $JREALITY/lib/*.jar
do
  CLASSPATH=$CLASSPATH:$file
done

for file in $SCALA/lib/*.jar
do
  CLASSPATH=$CLASSPATH:$file
done

java -Djava.library.path="$JREALITY/jni" -cp $CLASSPATH \
     scala.tools.nsc.MainGenericRunner $*

Post Reply