Tag Archives: time

30 Lines of JavaFX Coding Challenge Theme – Time

Space Time (updated!)

My entry is called ‘Space Time‘. A 3D cube clock. The full source code that is readable is below the article.

Wow, it is amazing at what you can you do in 30 lines of JavaFX code or 3000 characters.   JFXStudio is running a contest and the theme has to do with “TIME”. Although I posted my entry very last minute, there will be other chances for you to enter. Please visit http://jfxstudio.wordpress.com/2009/08/31/jfxstudio-challenge-small-is-the-new-big/

Space Time

Space Time

My entry including the import statements are just at 30 lines with each line containing less than or equal to 100 characters.  Click on the image to launch the demo.

Instructions:

  • Observe the cube rotating as each tick a second.
  • Observe the Space Time Title’s Distant lighting effect as seconds go by
  • Use mouse drag to rotate 3D cube
  • import javafx.animation.*;import javafx.scene.*;import javafx.scene.paint.Color;import javafx.scene
    .effect.*;import javafx.scene.text.*;import javafx.scene.shape.*;import javafx.scene.input.
    MouseEvent;import javafx.util.Math;class P{var x:Number;var y:Number;var z:Number;var sX:Number;var
    sY:Number;}class E{var a:Integer;var b:Integer;}var w:Number=800;var h:Number=600;var a:Number=30;
    var e:Number=30;var vs:P[]=[];function av(x:Integer,y:Integer,z:Integer){insert P{x:x,y:y,z:z}into
    vs;}av(-1,-1,-1);av(-1,-1,1);av(-1,1,-1);av(-1,1,1);av(1,-1,-1);av(1,-1,1);av(1,1,-1);av(1,1,1);var
    es:E[]=[];function aE(a:Integer,b:Integer){insert E{a:a,b:b}into es;}aE(0,1);aE(0,2);aE(0,4);aE(1,3
    );aE(1,5);aE(2,3);aE(2,6);aE(3,7);aE(4,5);aE(4,6);aE(5,7);aE(6,7);var ps:Circle[]=[];var ls:Line[]=
    [];function mps(c:Boolean):Void{var th:Number=bind 0.017453*a;var ph=0.017453*e;var cT=Math.cos(th)
    ;var sT=Math.sin(th);var cP=Math.cos(ph);var sP=Math.sin(ph);var cTcP=cT*cP;var cTsP=cT*sP;var sTcP
    =sT*cP;var sTsP=sT*sP;var sf=bind w/4;for(i in[0..sizeof vs-1]){var x0=vs[i].x;var y0=vs[i].y;var
    z0=vs[i].z;var x1=cT*x0+sT*z0;var y1=-sTsP*x0+cP*y0+cTsP*z0;var z1=cTcP*z0-sTcP*x0-sP*y0;x1=x1*3/(
    z1+4.5);y1=y1*3/(z1+4.5);vs[i].sX=x1;vs[i].sY=y1;if(c)insert Circle{centerX:bind w/2+sf*vs[i].sX+.5
    ,centerY: bind h/2-sf*vs[i].sY+.5,radius:2 fill:Color.BLUE}into ps;}if(c)for(e in es){insert Line{
    startX:bind ps[e.a].centerX startY:bind ps[e.a].centerY endX:bind ps[e.b].centerX endY:bind ps[e.b]
    .centerY strokeWidth:2,stroke:Color.BLUE}into ls;}}mps(true);var mx:Number;var my:Number;var g:
    Rectangle=Rectangle{x:0,y:0 width:bind w,height:bind h fill:Color.BLACK onMousePressed:function(me:
    MouseEvent):Void{mx=me.x;my=me.y;}onMouseDragged:function(me:MouseEvent):Void{var new_mx=me.x;a-=
    new_mx-mx;var new_my=me.y;e+=new_my-my;mx=new_mx;my=new_my;mps(false);}}var ct:String=new java.util
    .Date().toString();var tz:Integer=-125;var t=Group{content:[Text{effect:Lighting{light:javafx.scene
    .effect.light.DistantLight{azimuth:bind tz elevation:40}surfaceScale:5} x:10 y:50 content:"Space "
    "Time" fill:Color.RED font:Font{name:"Arial Bold" letterSpacing:0.20 size:50}},Text{x:10 y:80
    content:bind ct fill:Color.BLUE font:Font{name:"Arial Bold" letterSpacing:0.20 size:20}}]}var bc=
    Group{content:[Rectangle{x:10,y:bind h-85,arcHeight:5,arcWidth:5,width:bind w-30,height:30,fill:
    Color.RED,opacity:.5},Text{effect:DropShadow{offsetX:10,offsetY:10,color:Color.BLACK,radius:10}
    opacity:.5 x:15,y:bind h-65,content:"by Carl Dea - carlfx.wordpress.com"fill:Color.WHITE font:Font{
    name:"Arial Bold"letterSpacing:.20 size:20}}]}var scene:Scene=Scene{content:bind[g,ps,ls,t,bc]};var
    anim=Timeline{keyFrames:[KeyFrame{time:1s action:function():Void{a-=1;mps(false);ct=new java.util.
    Date().toString();if(tz>125){tz=-125;}tz+=2;}}]repeatCount:Timeline.INDEFINITE};anim.play();javafx.
    stage.Stage{width:bind w with inverse height:bind h with inverse scene:scene}

    Enjoy!
    Please vote for me…
    Let me know what you think. 🙂

    Here is the readable source code below:

    /**
     * Main.fx
     * 
     * Check out http://www.comp.brad.ac.uk/research/GIP/tutorials/project1.html 
     * for all the math.
     * Created on Dec 20, 2009, 11:06:15 PM
     */
    
    package bigsmall.part8;
    
    import javafx.animation.*;
    import javafx.scene.*;
    import javafx.scene.paint.Color;
    import javafx.scene.effect.*;
    import javafx.scene.effect.light.DistantLight;
    import javafx.scene.text.*;
    import javafx.scene.shape.*;
    import javafx.scene.input.MouseEvent;
    import javafx.stage.*;
    import java.util.Date;
    import javafx.util.Math;
    
    class Point3D {
       var x: Number;
       var y: Number;
       var z: Number;
       var screenX: Number;
       var screenY: Number;
    }
    
    class Edge {
       var a: Integer;
       var b: Integer;
    }
    var width: Number = 800;
    var height: Number = 600;
    var azimuth: Number = 30;
    var elevation: Number = 30;
    var vertices: Point3D[] = [];
    
    function addVertex(x: Integer, y: Integer, z: Integer) {
       insert 
          Point3D {
             x: x, 
             y: y, 
             z: z
          } 
       into vertices;
    }
    
    addVertex(-1, -1, -1);
    addVertex(-1, -1, 1);
    addVertex(-1, 1, -1);
    addVertex(-1, 1, 1);
    addVertex(1, -1, -1);
    addVertex(1, -1, 1);
    addVertex(1, 1, -1);
    addVertex(1, 1, 1);
    
    var edges: Edge[] = [];
    
    function addEdge(a: Integer, b: Integer) {
       insert 
          Edge {
             a: a, 
             b: b
          } 
       into edges;
    }
    
    addEdge(0, 1);
    addEdge(0, 2);
    addEdge(0, 4);
    addEdge(1, 3);
    addEdge(1, 5);
    addEdge(2, 3);
    addEdge(2, 6);
    addEdge(3, 7);
    addEdge(4, 5);
    addEdge(4, 6);
    addEdge(5, 7);
    addEdge(6, 7);
    
    var points: Circle[] = [];
    var lines: Line[] = [];
    
    function movePoints(createFirstTime: Boolean): Void {
       var theta: Number = bind 0.017453 * azimuth;
       var phi = 0.017453 * elevation;
       var cosTheta = Math.cos(theta);
       var sinTheta = Math.sin(theta);
       var cosPhi = Math.cos(phi);
       var sinPhi = Math.sin(phi);
       var cosThetaCosPhi = cosTheta * cosPhi;
       var cosThetaSinPhi = cosTheta * sinPhi;
       var sinThetaCosPhi = sinTheta * cosPhi;
       var sinThetaSinPhi = sinTheta * sinPhi;
       var scaleFactor = bind width / 4;
       for (i in [0..sizeof vertices - 1]) {
          var x0 = vertices[i].x;
          var y0 = vertices[i].y;
          var z0 = vertices[i].z;
          var x1 = cosTheta * x0 + sinTheta * z0;
          var y1 = -sinThetaSinPhi * x0 + cosPhi * y0 + cosThetaSinPhi * z0;
          var z1 = cosThetaCosPhi * z0 - sinThetaCosPhi * x0 - sinPhi * y0;
          x1 = x1 * 3 / (z1 + 4.5);
          y1 = y1 * 3 / (z1 + 4.5);
          vertices[i].screenX = x1;
          vertices[i].screenY = y1;
          if (createFirstTime) {
             insert 
                Circle { 
                   centerX: bind width / 2 + scaleFactor * vertices[i].screenX + 0.5,
                   centerY: bind height / 2 - scaleFactor * vertices[i].screenY + 0.5,
                   radius: 2 
                   fill: Color.BLUE
                } 
             into points;
          }
       }
    
       if (createFirstTime) {
          for (edge in edges) {
             insert 
             Line {   
                startX: bind points[edge.a].centerX
                startY: bind points[edge.a].centerY
                endX: bind points[edge.b].centerX
                endY: bind points[edge.b].centerY
                strokeWidth: 2,
                stroke: Color.BLUE
             } 
             into lines;
          }
       }
    }
    
    // create the first time; draw cube.
    movePoints(true);
    
    var mouseX: Number;
    var mouseY: Number;
    
    // Space region that changes the azimuth and recalculates the cube 
    var galaxy: Rectangle = Rectangle { 
       x: 0,
       y: 0
       width: bind width,
       height: bind height
       fill: Color.BLACK
       onMousePressed: function (me: MouseEvent): Void {
          mouseX = me.x;
          mouseY = me.y;
       }
       onMouseDragged: function (me: MouseEvent): Void {
          var new_mx = me.x;
          azimuth -= new_mx - mouseX;
          var new_my = me.y;
          elevation += new_my - mouseY;
          mouseX = new_mx;
          mouseY = new_my;
          movePoints(false);
       }
    } // galaxy
    
    var currentTime: String = new Date().toString();
    var initialAzimuth: Integer = -125;
    
    // Title with current time seconds.
    var titleDisplay = Group { 
       content: [
          Text {    
             effect: Lighting {  
                light: DistantLight {
                   azimuth: bind initialAzimuth
                   elevation: 40
                }
                surfaceScale: 5
             }
             x: 10
             y: 50
             content: "Space Time"
             fill: Color.RED
             font: Font {    
                name: "Arial Bold"
                letterSpacing: 0.20
                size: 50
             }
          },
          Text {    
             x: 10
             y: 80
             content: bind currentTime
             fill: Color.BLUE
             font: Font {    
                name: "Arial Bold"
                letterSpacing: 0.20
                size: 20
             }
          }
       ]
    }; // titleDisplay Group
    
    
    // This is the bottom display credits
    var byCarl = Group {    
       content: [
          Rectangle {   
             x: 10,
             y: bind height - 85,
             arcHeight: 5,
             arcWidth: 5,
             width: bind width - 30,
             height: 30,
             fill: Color.RED,
             opacity: .5
          },
          Text {    
             effect: DropShadow {    
                offsetX: 10,
                offsetY: 10,
                color: Color.BLACK,
                radius: 10
             }
             opacity: .5
             x: 15,
             y: bind height - 65,
             content: "by Carl Dea - carlfx.wordpress.com"
             fill: Color.WHITE
             font: Font {
                name: "Arial Bold"
                letterSpacing: .20
                size: 20
             }
          }
       ] // byCarl contents Group
    }; // by Carl
    
    var scene: Scene = Scene {  
       content: bind [
          galaxy, 
          points, 
          lines, 
          titleDisplay, 
          byCarl]
    };
    
    // this is the ticking motion of the cube.
    var anim = Timeline {   
       keyFrames: [
          KeyFrame {
             time: 1s
             action: function (): Void {
                azimuth -= 1;
                movePoints(false);
                currentTime = new Date().toString();
                if (initialAzimuth > 125) {
                  initialAzimuth = -125;
                }
                initialAzimuth += 2;
             }
          }
       ] // keyFrames
       repeatCount: Timeline.INDEFINITE
    }; // animation
    
    anim.play();
    
    Stage { 
       title: "Space Time"
       width: bind width with inverse
       height: bind height with inverse
       scene: scene
    }