Why do we need JavaFX when we have Groovy?

The more I learn about Groovy, the less I understand why the world needs JavaFX.

Back around 2002 or 2003 I studied Java, but it seemed heavy to me, verbose, and slow to program with. My attitude has mostly been, life is short, so I’d rather program in light-weight, high level programming languages. I want to be able to go as fast possible. For the last few years I’ve mostly been doing web development, mostly with PHP, though I did one project with Ruby On Rails.

But then the iPhone came out. And then the iPhone app store. So I became intrigued with the idea of programming for cell phones. But I didn’t want to especially learn Objective C just to be able to work with the iPhone. I was relieved to hear that Google was coming out with its Android operating system for cell phones, and programming for Android would be done in Java. That opened the door to using the light-weight languages (derived from Java) for cell phone programming. Very cool.

So I began to delve into the world of Java, something I hadn’t done much in the last few years. At first I was attracted to JavaFX, which Sun was hyping. But then I began to wonder why JavaFX was suffering such a slow uptake, and why programmers seemed less thrilled about it than I.

Now that I’ve started to study Groovy, I realize why JavaFX has so little traction: it isn’t needed. Much of what I liked about JavaFX is already present in Groovy. Lexecorp expresses some of the same hesitation that I feel:

I wonder whether I will be able to like JavaFX! Have I been spoilt already by Groovy (it does, virtually, the same thing)? Maybe, but I managed to accept the long winded Java language well after Perl’s expressive power had spoilt me. I learned to love Java for its platforms and immense libraries, so what can I love about JavaFX?

Consider this tutorial, which showed how to draw a coffee cup, and which showed off the clean, declarative style of JavaFX:

def plateGroup = Group {

translateX: 250
translateY: 300

content: [

// The gray ellipse under the plate
Ellipse{centerX:0 centerY:10 radiusX:160 radiusY:50 fill:Color.DIMGRAY},

// The thin "lip" of the plate (provides a sense of 3D)
Ellipse{centerX:0 centerY:3 radiusX:170 radiusY:50 fill:Color.LAVENDER},

// The large plate ellipse
Ellipse{centerX:0 centerY:0 radiusX:170 radiusY:50
fill:RadialGradient{
centerX:0.5 centerY:0.75
stops:[Stop {offset: 0.0 color: Color.WHITESMOKE},
Stop {offset: 0.5 color: Color.LIGHTGRAY},
Stop {offset: 1.0 color: Color.DARKGRAY}]
}
},

// Recessed plate center
Ellipse{
centerX:0 centerY:5 radiusX:90 radiusY:22
fill:RadialGradient{
centerX:0.5 centerY:0.75
stops:[Stop {offset: 0.0 color: Color.BLACK},
Stop {offset: 0.4 color: Color.LIGHTGRAY},
Stop {offset: 1.0 color: Color.GHOSTWHITE}]
}
}
]
}

def cupGroup = Group {

translateX: 152
translateY: 20
scaleX: 3.0
scaleY: 4.0

content: [
// Cup body
Circle {centerX: 100 centerY: 100 radius: 50
fill: RadialGradient {
centerX: 0.4 centerY: 0.0 focusX: 0.5 focusY:.65, proportional:true
stops: [Stop {offset: 0.0 color: Color.GHOSTWHITE},
Stop {offset: 1.0 color: Color.SILVER}]
}
},

// Cut top of cup
Rectangle{stroke: BGCOLOR fill: BGCOLOR
x:25 y:50 width:150 height:50},

// Outer rim
Ellipse{fill: Color.WHITE centerX:100 centerY:100 radiusX:50 radiusY:8},

// Inner rim
Ellipse{centerX:100 centerY:100 radiusX:48 radiusY:7 //inner rim
fill: RadialGradient {
centerX: 0.4 centerY: 0.0 focusX: 0.5 focusY:.4, proportional:true
stops: [Stop {offset: 0.0 color: Color.GHOSTWHITE},
Stop {offset: 1.0 color: Color.SILVER}]
}
},

// Create “coffee in cup” by intersecting coffee ellipse with inner rim ellipse
ShapeIntersect {

fill:Color.SADDLEBROWN

//Inner Rim
a: Ellipse{centerX:100 centerY:100 radiusX:48 radiusY:7} // inner rim dimensions

//Coffee
b: Ellipse{centerX:100 centerY:102 radiusX:46 radiusY:6} // coffee dimensions
}
]
}

Stage {
title: “Coffee Cup”
width: 500
height: 500
visible: true
scene: Scene {
fill: BGCOLOR
content: [plateGroup,cupGroup]
}
}

That’s impressive! Look how clean the code is! So much simpler than Swing! But then Andres Almiray turned around and demonstrated how to draw a coffee cup with Groovy:

group( id: ‘plategroup’, bc: ‘none’ ) {
// gray ellipse under the plate
ellipse( cx: 0, cy: 10, rx: 160, ry: 50, f: color(’darkGray’).brighter() )

// thin ‘lip’ of the plate (provides a sense of 3D)
ellipse( cx: 0, cy: 3, rx: 170, ry: 50, f: ‘lavender’ )

// large plate
ellipse( cx: 0, cy: 0, rx: 170, ry: 50 ) {
radialGradient( cx: 1, cy: 1, fy: 100, r: 270 ) {
stop( c: ‘whiteSmoke’, s: 0 )
stop( c: ‘lightGray’, s: 0.5 )
stop( c: ‘darkGray’, s: 1 )
}
}

// recessed plate center
ellipse( cx: 0, cy: 5, rx: 90, ry: 22 ) {
radialGradient( cx: 1, cy: 1, fy: 20, r: 180 ) {
stop( c: ‘black’, s: 0 )
stop( c: ‘lightGray’, s: 0.4 )
stop( c: color(’white’).darker(), s: 1 )
}
}

transformations {
translate( x: 250, y: 300 )
}
}

group( id: ‘cupgroup’, bc: ‘none’ ) {
subtract( id: ‘cup’, asShape: yes ) {
circle( cx: 100, cy: 100, r: 50 )
rect( x: 25, y:50, w: 150, h: 50 )
}
draw( cup, keepTrans: yes ) {
radialGradient( cx: 0.4, cy: 0, r: 100 ) {
stop( c: ‘whiteSmoke’, s: 0 )
stop( c: color(’whiteSmoke’).darker(), s: 1 )
}
}

// outer rim
ellipse( cx: 100, cy: 100, rx: 50, ry: 8, f: ‘white’ )

// inner rim
ellipse( cx: 100, cy: 100, rx: 48, ry: 7, id: ‘innerRim’ ) {
linearGradient( y2: 1 ){
stop( c: ‘whiteSmoke’, s: 0 )
stop( c: color(’whiteSmoke’).darker(), s: 1 )
}
}

intersect( f: color(’darkOrange’).darker().darker() ) {
shape( innerRim )
ellipse( cx: 100, cy: 102, rx: 46, ry: 6 )
}

transformations {
scale( x: 3, y: 4 )
translate( x: -16, y: -70 )
}
}

transformations {
translate( x: -50, y: -50 )
}

Damn. Doesn’t that look similar? There are some syntax differences, but both use a declarative style, and both require less work than using Swing.

Groovy offers some solid MVC frameworks. For web development, there is Grails, which is an imitation of Ruby On Rails. For the desktop, there is Griffon. Consider this post on Transentia:

Although it is early days yet for the project, Griffon aims to bring the same “Configuration by Convention” goodness to desktop GUI development that Grails has brought to Web development. In fact, Griffon ‘borrows’ heavily from Grails: many of the build scripts, etc. are straight carry-overs, meaning that anybody familiar with Grails can get started easily.

This is all that is needed to get started:

griffon create-app GT
cd GT
griffon run-app

These three shell commands give a simple immediately runnable application.

As with Grails, Griffon imposes a clear MVC structure for the code and also creates a standard project filesystem heirarchy.

I haven’t yet worked with Griffon, but the setup described on Transentia looks very clean. Certainly, everything I’ve learned so far about Groovy has left me impressed. And since Groovy integrates with regular Java far more smoothly than JavaFX, why do we need JavaFX? Can anyone name one thing that JavaFX gives us that Groovy hasn’t already given us?

8 Responses to “Why do we need JavaFX when we have Groovy?”

  1. Andres Almiray Says:

    JavaFX Script’s marquee feature, Binding, is indeed more powerful that what we currently have in Groovy, mainly because every statement is an expression, which means you can bind to almost any language construct. This is a very powerful feature that can be easily abused as well.

    Other than that pretty much everything else can be replicated via libraries, even with other alternate JVM languages like Scala and JRuby, the real power of the JavaFX movement is in its libraries (the platform) not the language.

    Cheers,
    Andres

  2. Richard Osbaldeston Says:

    I was going to make the point about not confusing JavaFX Script with JavaFX but Andres does that succinctly with ‘the real power of the JavaFX movement is in its libraries not the language.’ Tiz a shame that it’s so awkward to leverage these libraries from anywhere but JavaFX Script. AFAIK we can’t distribute the JavaFX lib jars with our own applications. Despite being GPL we can’t see any of the source repositories and even if we did they keep changing so radically with every release it’d be unwise if not impractical (thinking 1.2 internal scenario changes). Accessing the libs from Java/Groovy/Whatever seems overly painful and relies on fragile ‘hacks’. Finally we have no roadmap, no guidance, no communication/consultation as to what to expect when from the dev team, it’s like the blind, deaf and dumb leading the blind.

    Mind you, just to play my devils advocate joker for a moment. I dont see any more uptake for Groovy, Griffon, Grails in the current job market than I do for JavaFX. Sure bloggers talk up all-of-the-above to huge degrees, but where are all the jobs? how do the Groovy guys pay their bills? (yeah I’ve seen grailsjobs, but it suffers the same problems as the various rails jobs sites – badly maintained sourly dated content thats simply not kept updated ie not agent driven).

    hmm Should I even be asking where are the jobs? before asking where are the designer tools?

  3. Rebolian Says:

    Well, I agree with you life is short :) I’m interested in Groovy, I think I will look at it but I don’t think it can be easier than Rebol.

  4. Steven Reynolds Says:

    OK, I’ll bite. One thing: parts of JavaFX use graphics shader code running directly on the video card. They’re also using other acceleration techniques on platforms where they can’t run shaders.

  5. sboulay Says:

    if you make a mistake in the first example the compiler will catch it. If you make a mistake in the second example it will be a runtime error. The better question would have been why fx script when you have Scala.

    Other than that I think fx script is pretty sweat – I think we’ll start to see some serious uptake with 2.0.

  6. sboulay Says:

    sweet

  7. lawrence Says:

    Richard, you wrote:

    I dont see any more uptake for Groovy, Griffon, Grails in the current job market than I do for JavaFX. Sure bloggers talk up all-of-the-above to huge degrees, but where are all the jobs? how do the Groovy guys pay their bills?

    I think, historically, light-weight, high level languages tend to start off as tools that get snuck into work environments. Back in the 80s/90s, Perl got snuck in by sysadmins. In the 90s, PHP started off as a tool that no one took seriously. There were no PHP jobs. That came years later. Right now, I would assume the uptake for Groovy is the same – there are no official Groovy jobs, only programming jobs that some programmers decide to use Groovy for.

    My thanks to everyone who posted a comment – these were informative.

  8. Tbee Says:

    In theory there is not reason why Groovy can’t compile the drawing statements to JavaFX compatible byte code. Or use the bind logic.

Leave a Reply