The Beginnings Of A RantI don't normally have a desire to start flame wars, go out of my way to troll, nor do I like to make blanket statements - especially about the technology that I've been using for 12 years. I've benefited greatly over that time period by using Java and committing projects such as Purnama XUI, a couple of games in J2ME, a book on creating content management systems in Java, and all of the courses that I've taught throughout those years using Java's list of media APIs.However, I just recently came across a bug "feature" based on the java.awt.Shape interface that caused me to grit my teeth, my left eye to twitch, and spike my blood pressure to an unhealthy and high level. The code was to draw a polygon and then perform a fill of that same polygon (actually this code was someone's test from a forum post - my original code drew a polygon with many more points but this code demonstrated to me that it wasn't the number of the points): 1 @Override
2 public void paintComponent(Graphics g) {
3 super.paintComponent(g);
4 Graphics2D g2 = (Graphics2D) g;
5
6 int w = 200, h = w/2, s2 = 150;
7 g2.setColor(Color.red);
8 g2.drawPolygon(new int[]{0,2*w/5,0},new int[]{h/2,0,-h/2},3);
9 g2.setColor(Color.black);
10 g2.fillPolygon(new int[]{0,2*w/5,0},new int[]{h/2,0,-h/2},3);
11 }
The result should of course be that no red pixels are shown, meaning that the fill, fills the exact same area as the draw with a line. But under JDK 1.6 update 10, it doesn't. The fill polygon is incorrectly offset (by one pixel to the left) and does not draw all the correct pixels to the edges of the polygon on all sides. I tried several other examples. All of which display the same bug "feature". *sigh*Now this seems to be such a minor and small problem. Based on the API documentation, the java.awt.Shape class's description of "insidedness" implies that the above "feature" is working correctly and as it has been documented. Right? It's not like I've never made a bad choice either or a mistake; I know that. But this problem got me thinking. Recalling back to all of the other times I've gritted my teeth, eye twitching, like Chief Inspector Charles Dreyfus I began to realize just how many times show stopping bugs or "features" such as this have either caused me to shake my head in disbelief or watch students or clients do the same thing.JMF - Java Media FoobarI remember teaching with the Java Media Frameworks (JMF) back in 2000. Students were using it to play audio streams, create music players and develop video capture applications such as video-phone applications. The problems we had were too numerous to count but some of the more frustrating issues were:- Video playback only working some of the time (debugging and testing never revealed the rhyme or reason to this)
- Video capture starting several seconds after being prompted to do so
- Video capture not capturing for the time specified
- Very few web cams actually supported
- No support for MP3
- Configuration problems while trying to set up JMF (under Windows 2000 at that time)
Many of these problems were happening to students and just at a time they were expected to either hand in assignments or client projects. Worse was the problem of industry projects requiring JMF support; students were expected to explain why these types of problems weren't their fault.It was an exciting and yet, incredibly frustrating time and I had to listen to irate industry sponsors and students both telling me why we shouldn't be using Java for digital media (at the time called multimedia).But it wasn't just the bugs that killed JMF. It was the lack of usability. It appeared that design patterns and half-baked solutions were more important than ease of use and common feature sets. I came to see this process in action (more on this later).For example, JMF did not include MP3 support. This was a huge shortcoming that limited the usefulness of JMF. At that time MP3 support was pertinent for any digital media API that purported to play, capture, or stream digital audio. Another major flaw in Sun's addressing of features for JMF was the lack of complete support for RTSP/RTCP. Although it was a feature offered for playback, there was no way of serving up content using the RTSP/RTCP protocol on the server. This blind spot could have been the single-most reason why JMF never stood a chance: developers could not serve up media content using this protocol.JMF now seems all but abandoned, although Sun Microsystems insists that JMF is going strong. There is a "plugin" for MP3 support but 10 years later and this feature is too little, too late. Most of us have moved on; once bitten, twice shy as the saying goes.Java Imaging Support - Catch Me If You CanNext, I recall using an API known as Java Image Management Interface (JIMI). This API wasn't actually created by Sun Microsystems, but it was inherited and used to offer (at the time) the important support of being able to encode/decode various types of raster image file formats such as PNG, TIFF, PSD, and a few others. While JIMI filled a void left by Sun's lack of foresight and planning for usability, JIMI had the uncanny ability to crash the Java VM. Once again, I went into damage control and had to help students and industry sponsors work around why a specific image would actually crash the VM. How embarrassing this was.JIMI was quickly replaced by Java Advanced Imaging (JAI) which offered support advanced filtering effects and for encoding/decoding of raster image file formats (although not as many as JIMI had offered). JIMI is still downloadable but Sun Microsystems states that they are only "making it available for developers who have code with dependencies on JIMI" and that users should instead use the Java Advanced Imaging (JAI) API.However, JAI also seems to be abandoned by Sun with it being moved to the Java.net website. Specifically, Sun states that "Java Advanced Imaging (JAI) and the associated Image I/O Tools packages are now community source projects on java.net". This is an indirect way of saying "we've offloaded this project to the open source community because we are no longer interested in directly supporting this API/framework". No direction, no future, just maintenance of existing flaws and the odd answer to a question in the forum. This is the final nail in the coffin. "It's dead Jim."The Java 2D API, which is part of the J2SE bundle, has had its own share of problems. Some of these include: Once again, immense blind spots that appear to fly in the face of usability. After stumbling across these issues (and many more), I find myself asking "why didn't I take the blue pill?"
3D In Java - Affine Mess
Then there's Java3D. Java3D is a scene-graph-based API and was publicly released in March, 1998. Java3D is yet another API that Sun Microsystems has offloaded to the open source community in the hopes that kind-hearted Java aficionados will continue to maintain the failed project. Java3D never really had a chance though. Like so many other digital media APIs and frameworks that Sun Microsystems created, it suffered from a lack of usability. Because Java3D is a scene-graph-based API, many of the low-level control calls that 3D developers require, simply aren't available. Add that to the list of bugs tying Java3D to Direct3D and OpenGL, and Sun Microsystems has created another abandoned API.
There is hope within the Java community when it comes to 3D API support due to a project known as Java OpenGL (JOGL). JOGL was started in the summer of 2002 by former MIT graduate students Ken Russell and Chris Kline. The API is a direct 1:1 mapping to the procedural calls found in the C programming language. This API has even become a JSR and has some handy utility calls bundled in it including the ability to take screen captures, output tiled images of really large images, and a seamless integration between Java 2D and JOGL.
What's interesting is that this API seems to be holding it's own. I strongly believe this is due to non-Sun engineers/developers looking at usability, features and benefits; basically being built for use, not for looking at the pretty UML diagrams. Whereas Java3D was a Sun API tossed down to the open source community after lackluster performance and interest, JOGL is a project started by two grads (most likely out of frustration), which has been promoted to a JSR and enjoys the status of having been one of the few independent projects to steer some sensible direction in Swing's rendering pipeline. Usability, simplicity. What a concept!
Java Sound - Testing 1, 2, 3
This is another API I remember using back in 2000 with students and industry projects. Once again, UML diagrams and design patterns were the main focus of this API instead of usability. Back then, Java Sound was missing two vitally important features in order to be useful:
- Ability to play encode/decode MP3
- Ability to save a sampled stream recording directly to file
At the time I was completely flabbergasted that Sun would take the time to build such an elegant interface and yet forget or ignore something so important such as the ability to save the captured sampled sound as a stream. The upshot of this decision was that any captured sound from an input would have to fit inside of the OS's main memory. Any large recordings requirements would simply not be doable.
The MP3 support and recording sampled sound directly to file were offered by two independent Java developers (Florian Bomers and Matthias Pfisterer) who created the Tritonus project which was meant to be an open source implementation of the Java API. Ironically the support of Tritonus scratched the itch more-so than what Sun provided. Like a repeat of JMF and the imaging APIs, Java sound lost the momentum that would have been required to attract programmers to this API.
Today, Java Sound (finally) supports the ability to record streaming sampled sound directly to file but still lacks MP3 and OGG Vorbis support - two very common sound formats in use today. Without support for those two formats, there's very little chance of any rejuvenated interest in Java Sound. Sun Java software engineers did include the Service Provider Interface (SPI) within Java Sound but that's akin to telling a potential home buyer "Look, here's your dream house and the blueprints, if you can find someone that knows electrical, give them these blueprint and they'll set up the electricity in your dream house." Rather daft logic by my standards.
What's more peculiar is that although Java Sound is still listed as a Sun Microsystems interest (i.e. it's still on their site instead of being given up for adoption to open source developers at java.net), Sun Microsystems has delegated all technical questions and issues pertaining with Java Sound to Florian Bomers and Matthias Pfisterer's web site. Is this another example of Sun Microsystems disinterest and lack of any true vision when it comes to dealing with digital media support within the Java platform? I wonder.
JSR - Java Specification Refuse
Recall earlier on when I was talking about JMF and how UML and half-baked solutions were more important than ease-of-use. In 2001 I joined a Java Specification Request (JSR) known as The Stream Assembly API or JSR 158. The demand that this API was meant to satisfy at the time was to specify "classes and interfaces for the creation, management, and processing of broadcast and interactive stream multiplexes" for MPEG 2. I joined immediately since I had been toying with the idea of creating a media API in Java anyway and so I decided that it was better not to duplicate efforts.
It was an interesting opportunity that allowed a complete group of strangers from all over the world, to teleconference once a week and work together towards a common goal: provide a useful Java API. I found myself feeling very passionate about contributing to this project due to my frustration with JMF and Java Sound and so I looked at this opportunity as a way to help steer media support usability in the Java platform towards the right direction.
Unfortunately about three months into the draft I quickly realized that this was simply another example of Sun engineers' flawed syllogistic reasoning. I was preparing use cases, documenting an example API, preparing suggestions for ease-of-use for JSR 158 until one teleconference. One of the Sun engineers was suggesting that every position on the time line of a media stream had to be represented by an interface.
"What's wrong with a long, man?!" I blurted out.
It was suggested that in order to make all data types polymorphic and in order to ensure that strict design patterns were adhered to, that the position within a stream of media should be an interface. End of discussion. But I persisted and reminded the group that using a long primitive type in Java would support over 170 trillion hours (2^64/30/60/60) of positionable streaming or half that if one decided to ignore the negative values. Another way to look at it is having over 19 billion years of streaming - more than enough for your average streaming application requirements.
But the Sun engineers dug in their heels and refused to budge. However, it wasn't just that one particular design choice. It was everything. As the API was starting to take shape is was starting to look suspiciously like some mutated transmogrification of JMF and the Java Sound API. It was like David Cronenberg's The Fly: a complete aberration. I sent an email to the group and politely removed myself; I left feeling disappointed and frustrated.
The Future
Edward Gibbon once said "I have but one lamp by which my feet are guided, and that is the lamp of experience. I know no way of judging of the future but by the past." Using this outlook, it is easy to see that the current methodology that Sun has adopted is not working. It's leaving a garbage heap-trail of abandoned APIs and it's leaving Java developers less and less trusting with each iteration.
What Sun needs is a vision, a grand unification of digital media support. One framework to serve all forms of content and one that ties into existing standards, be they de facto or committee-based, no matter. No more blatant omissions or show-stopping bugs. But most importantly, one framework that places usability as its most principal goal. Java developers shouldn't feel envious towards their Python, Rails, Flex, or C#/.NET counterparts. Java developers shouldn't have to be embarrassed any more that we can't even fill a polygon correctly or play MP3 files.
As I watch the fanfare of JavaFX I find my default knee-jerk reaction asking "why?" Why create a new language, why go head-to-head with the de facto standard, Adobe's Flex/Flash/Air triple threat? Why assume that the underlying technology is working? Because it is not. Applets freeze and applets freeze the web browser. There are bugs to be fixed. Old bugs, new bugs, regressions, and blatantly missing fundamental features.
So, will JavaFX become yet another casualty and die a slow and painful death, eventually thrown to the open source community in the hopes that a new generation will offer their time and effort looking after maintenance and bug fixes? It's hard to say. I'm personally not very optimistic. From where I stand, desktop and digital media support from Sun's Java is in jeopardy. Sun's commitment appears unclear. In the mean time, I need to go and write a flood-fill algorithm that fills an arbitrary polygon.
- Arron
=========================================
July 23, 2009 Edit
After reading this article about Hans Muller, who was Sun MicroSystems' CTO for Sun's Desktop division, and his defection from Sun (after being assigned to JavaFX), I am now convinced that JavaFX will go nowhere. Flex will continue to be the juggernaut it is, adding to that momentum is Hans working for Adobe and being an engineer for Flex.
It speaks volumes when a top engineer such as Hans Muller leaves to go work for the competition after 21 years - especially after being assigned a framework that was suppose to go head-to-head against Flash/Flex/AIR.
Copyright © 2009, Arron Ferguson