Skip to content

Instantly share code, notes, and snippets.

@takedasoft
Created February 19, 2009 09:49
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save takedasoft/66829 to your computer and use it in GitHub Desktop.
Save takedasoft/66829 to your computer and use it in GitHub Desktop.
/*
* scala で OpenGLのためし。
* Java OpenGL ライブラリ JOGL を使っています。
*
* scalac -classpath \
* "/jogl/lib/gluegen-rt.jar:/jogl/lib/jogl.jar" JOGLDemo.scala
* java -Djava.library.path="/jogl/lib" -classpath \
* "./classes:scala-library.jar:\
* /jogl/lib/gluegen-rt.jar:/jogl/lib/jogl.jar" takedasoft.JOGLDemo
*
* @see https://jogl.dev.java.net/
*/
package takedasoft
import javax.swing._
import java.util.ArrayList
import java.awt.event._
import javax.media.opengl._
import scala.collection.mutable.Queue
import com.sun.opengl.util._
/******************************
Simple 3D Animation Framework
*******************************/
class WorldConfig(gl:GL) {
val CAMERA = -10.0f
// Light
val LPOSITION = Array( -2.0f, 2.0f, -3.0f, 0.0f )
val LSPECULAR = Array( 0.2f, 0.2f, 0.2f, 1.0f )
val LDIFFUSE = Array( 0.5f, 0.5f, 0.5f, 1.0f )
val LAMBIENT = Array( 0.8f, 0.8f, 0.8f, 1.0f )
// reflection
val MSPECULAR = Array( 0.5f, 0.5f, 0.8f, 1.0f )
val MDIFFUSE = Array( 0.5f, 0.5f, 0.8f, 1.0f )
val MAMBIENT = Array( 0.8f, 0.8f, 1.0f, 1.0f )
val MSHININESS = 10.0f
def base = {
gl.glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
gl.glEnable(GL.GL_DEPTH_TEST);
gl.glEnable(GL.GL_CULL_FACE);
gl.glEnable(GL.GL_LIGHTING);
gl.glEnable(GL.GL_LIGHT0);
gl.glEnable(GL.GL_NORMALIZE);
}
def lighting = {
gl.glLightfv(GL.GL_LIGHT0, GL.GL_POSITION, LPOSITION, 0);
gl.glLightfv(GL.GL_LIGHT0, GL.GL_SPECULAR, LSPECULAR, 0);
gl.glLightfv(GL.GL_LIGHT0, GL.GL_DIFFUSE, LDIFFUSE, 0);
gl.glLightfv(GL.GL_LIGHT0, GL.GL_AMBIENT, LAMBIENT, 0);
}
def refrection = {
gl.glMaterialfv(GL.GL_FRONT, GL.GL_SPECULAR, MSPECULAR, 0);
gl.glMaterialfv(GL.GL_FRONT, GL.GL_DIFFUSE, MDIFFUSE, 0);
gl.glMaterialfv(GL.GL_FRONT, GL.GL_AMBIENT, MAMBIENT, 0);
gl.glMaterialf(GL.GL_FRONT, GL.GL_SHININESS, MSHININESS);
}
def configurate = {
base
lighting
refrection
}
def viewport(width:Int,height:Int) = {
val ratio:Float = height.toFloat / width.toFloat;
gl.glViewport(0, 0, width, height)
gl.glMatrixMode(GL.GL_PROJECTION)
gl.glLoadIdentity
gl.glFrustum(-1.0f, 1.0f, -ratio, ratio, 5.0f, 40.0f)
gl.glMatrixMode(GL.GL_MODELVIEW);
gl.glLoadIdentity
gl.glTranslatef(0.0f, 0.0f, -30.0f)
}
}
trait SimpleSprite{
var gl:GL = _
def setGL(gl:GL) = this.gl = gl
def rotateX(dx:Int) {
//gl.glPushMatrix();
gl.glRotatef(dx, 1.0f, 0.0f, 0.0f)
//gl.glPopMatrix();
}
def rotateY(dy:Int) = gl.glRotatef(dy, 0.0f, 1.0f, 0.0f)
def rotateZ(dz:Int) = gl.glRotatef(dz, 0.0f, 0.0f, 1.0f)
def moveX(dx:Int)={}
def moveY(dy:Int)={}
def moveZ(dz:Int)={}
def rotateXTo(px:Int) {
gl.glPushMatrix();
gl.glRotatef(px, 1.0f, 0.0f, 0.0f)
gl.glPopMatrix();
}
def rotateYTo(py:Int) = gl.glRotatef(py, 0.0f, 1.0f, 0.0f)
def rotateZTo(pz:Int) = gl.glRotatef(pz, 0.0f, 0.0f, 1.0f)
def moveXTo(px:Int)={}
def moveYTo(py:Int)={}
def moveZTo(pz:Int)={}
def update()
val glut:GLUT = new GLUT
def getGLUT:GLUT = glut
}
class World extends GLEventListener {
implicit def config(gl:GL) = new WorldConfig(gl)
var items:Queue[SimpleSprite] = new Queue
var gl:GL = _
def addItem(item:SimpleSprite) = items += item
override def init(drawable:GLAutoDrawable) {
gl = drawable.getGL
items.foreach{ _.setGL(this.gl) }
gl.configurate
}
override def reshape( drawable:GLAutoDrawable,
x:Int, y:Int, width:Int, height:Int) {
// called on windowsize changed.
gl.viewport(width,height)
}
override def display(drawable:GLAutoDrawable) {
gl.glClear(GL.GL_COLOR_BUFFER_BIT | GL.GL_DEPTH_BUFFER_BIT);
items.foreach{ _.update }
}
override def displayChanged( drawable:GLAutoDrawable ,
modeChanged:boolean , deviceChanged:boolean ) {
}
}
class WorldFrame extends JFrame {
val canvas:GLCanvas = new GLCanvas
val world:World = new World
val animator:Animator = new Animator(canvas)
canvas.addGLEventListener(world)
add(canvas)
setSize(500, 500)
addWindowListener(new WindowAdapter{
override def windowClosing( e:WindowEvent ){
animator.stop
System.exit(0)
}
})
def addItem(item:SimpleSprite) = world.addItem(item)
def start = {
animator.start // repeat GLEventListener.display
this.setVisible(true)
}
}
/******************************
Sample
*******************************/
class TeaPot(size:Double) extends SimpleSprite {
override def update(){
rotateZ(-1)
rotateX(-1)
getGLUT.glutSolidTeapot(size)
}
}
object JOGLDemo extends WorldFrame {
def main(args: Array[String]){
addItem(new TeaPot(3.0d) )
addItem(new TeaPot(2.0d) )
addItem(new TeaPot(1.0d) )
start
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment