My blog has moved!

You should automatically be redirected in 6 seconds. If not, visit
http://blogs.i2m.dk/allan
and update your bookmarks.

Saturday 29 March 2008

Using my Nokia 6120 for presentations

Today I noticed a cool feature of my new Nokia 6120 mobile phone. From it's download menu I was able to download a presentation tool from Nokia that turns the phone into a remote control for my PC. I've been thinking about getting a separate presentation device as I do a fair share of presentations and hate having to walk back to my PC everytime I want to move to the next slide. So, the way it works is by having a java application on the phone that emulates the mouse and an application on the PC that turns the keypresses on the phone into mouse movesments on the PC. I've tried it out with PowerPoint and works great. The tool also supports other applications out of the box such as Winamp and Media Player. The desktop tool can futhermore configure the remote control for other programs as well by specifying what should happen when each individual key on the phone is pressed.



The application (containing both the desktop application and the Java ME application) can be downloaded from the Nokia Community Portal: Mosh.

Links:

Wednesday 19 March 2008

Shared libraries finally made it to NetBeans

Today I installed NetBeans 6.1 beta. I've always been a great fan of NetBeans and participated in the Community Acceptance Testing programme (NetCAT) for version 4.0 and 6.0.

I haven't had time to go through all the changes yet, but one thing caught my attention immediately, the "Shared Library" functionality. It has always amazed me that this feature was not implemented way sooner. I have never used the built-in library manager for third-party libraries as the information about the libraries were not included with the projects, i.e. when I create a third-party library in the Library manager for say Apache Commons Configuration and use that in my project, it will break the built for not only other developers by also my continuous integration server. The alternative is to simply add the third-party library directly to the project as jars. The downside about that is that you can't attach the source and JavaDocs, so the inline code completion becomes almost useless. A third alternative is to manage dependencies completely outside of the IDE using Ant and Maven build scripts. I use to do this when using Eclipse, however then you have to update the dependencies in both the IDE and the build script = twice the work.

Back to NetBeans 6.1. When creating a project you now get the offer to enable "sharable libraries". When enabling this feature you are asked to specify the location where the libraries should be saved. By default it will suggest ..\libraries, which is a bit strange considering that it is outside the project folder. I guess it depends on the configuration management practices used on the project. Personally I always check in third-party libraries (as long as there are no licensing issues preventing it). In that way I alaways know that I can build the software anywhere on any machine (that includes my CI box).



After having enabled sharable libraries, NetBeans will automatically copy library to the specified folder when you add dependencies to your project. Furthermore, if you find out that you'd rather have your sharable libraries in a different location, you can simply change the location click "Save" and it will re-create the sharable libraries. Very neat!

I can imagine that they will continue working on the feature at NetBeans and this feature will become even better before the next release.

Tuesday 18 March 2008

Example of using custom facelet tags

Rather than using includes when creating templates you can create your own custom facelet tags without the husle of creating a JSF component from scratch. As an example, I'll create a menu tag that can be used to switch a selected menu item on and off.

Here is the menu (save it as /WEB-INF/facelets/tags/menu.xhtml):


<ui:composition xmlns:ui="http://java.sun.com/jsf/facelets" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core">
<h:panelGrid columns="10">
<h:outputText styleClass="menuItem" value="Home" />
<h:outputText styleClass="menuItem" value="Some page" />
<h:outputText styleClass="menuItem" value="Another page" />
<h:outputText styleClass="menuItem" value="Third page" />
</h:panelGrid>
</ui:composition>


Here is the cascanding style sheet:

.menuItem {
border: 1px solid black;
}

.menuItemSelected {
background: red;
color: white;
font-weight: bold;
}


To make the menu into a tag you create a facelets tag library. I'll call it mytags.taglib.xml and place it in /WEB-INF/facelets/:


<?xml version="1.0"?>
<!DOCTYPE facelet-taglib PUBLIC "-//Sun Microsystems, Inc.//DTD Facelet Taglib 1.0//EN" "http://java.sun.com/dtd/facelet-taglib_1_0.dtd">
<facelet-taglib>
<namespace>http://bigallan.blogspot.com/mytags
<tag>
<tag-name>menu</tag-name>
<source>tags/menu.xhtml</source>
</tag>
</facelet-taglib>


To make the web application recognise your tag library you need to update add the following context parameter to web.xml:

<context-param>
<param-name>facelets.LIBRARIES</param-name>
<param-value>/WEB-INF/facelets/mytags.taglib.xml</param-value>
</context-param>


If you have more than one custom tag library you can separate them with semicolons (;)

On your pages you can now include the menu tag:


<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:ui="http://java.sun.com/jsf/facelets" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core" xmlns:mytags="http://bigallan.blogspot.com/mytags">
<head>
<title>My page</title>
<link href="css/styles.css" rel="stylesheet" type="text/css" />
</head>
<body>
<mytags:menu home="true" />
</body>
</html>


All we need to do now is to look out for the attributes of the custom tag. Attributes are automatically turned into variables on the tag pages, so we simply make the following changes to /WEB-INF/facelets/tags/menu.xhtml:


<ui:composition xmlns:ui="http://java.sun.com/jsf/facelets" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core">
<h:panelGrid columns="10">
<h:outputText styleClass="menuItem #{home == 'true' ? 'menuItemSelected' : ''}" value="Home" />
<h:outputText styleClass="menuItem #{somePage == 'true' ? 'menuItemSelected' : ''}" value="Some page" />
<h:outputText styleClass="menuItem #{anotherPage == 'true' ? 'menuItemSelected' : ''}" value="Another page" />
<h:outputText styleClass="menuItem #{thirdPage == 'true' ? 'menuItemSelected' : ''}" value="Third page" />
</h:panelGrid>
</ui:composition>


To turn all menu items on you code do the following:


<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:ui="http://java.sun.com/jsf/facelets" xmlns:h="http://java.sun.com/jsf/html" xmlns:f="http://java.sun.com/jsf/core" xmlns:mytags="http://bigallan.blogspot.com/mytags">
<head>
<title>My page</title>
<link href="css/styles.css" rel="stylesheet" type="text/css" />
</head>
<body>
<mytags:menu home="true" somePage="true" anotherPage="true" thirdPage="true" />
</body>
</html>


Enjoy!

Suggested reading on the subject:

Monday 17 March 2008

Creating timers in EJB3

While the EJB 3.1 expert group is working on the improved timer service using annotations (See New Features in EJB 3.1) I thought that I'd just bring a small entry on using the timer service in EJB 3.

The timer service works by telling the service when it should timeout (i.e. when shall the "alarm" go off). You can add to this by telling it when it should timeout the first time, and how often (in ms) it should timeout after that. You define which methods on the bean that should be invoked upon timeout by annotating them @Timeout. The timer service is initialised by annotating a TimerService object as a @Resource.

Okay, before I show the code, these are the methods that we need:


  • A method for starting the timer

  • A method for stopping the timer

  • One or more listener methods that will be invoked when the timer has timed-out




@Stateless
public class MyTimerBean implements MyTimerLocal {

/** Service used for scheduling tasks. */
@Resource private TimerService timerService;

/**
* Starts the scheduler.
*
* @param startDate
* Start date
* @param interval
* Interval at which the timeout shall repeat
* @param timerName
* Timer to start
*/
public void startTimer(Date startDate, Long interval, String timerName) {
this.timerService.createTimer(startDate, interval, timerName);
}

/**
* Stops a given scheduler.
*
* @param timerName
* Timer to stop
*/
public void stopTimer(String timerName) {
for (Timer timer : (Collection) this.timerService.getTimers()) {
if (timer.getInfo() instanceof String) {
if (((String) timer.getInfo()).equals(timerName)) {
timer.cancel();
return;
}
}
}
}

/**
* {@link Timeout} event handler for generating a report.
*
* @param timer
* Timer that timed out
*/
@Timeout
public void generateReport(Timer timer) {
if (timer.getInfo() instanceof String) {
if (((String) timer.getInfo()).equals("Generate Report")) {
... do some processing ...
}
}
}

/**
* {@link Timeout} event handler for cleaning the cache.
*
* @param timer
* Timer that timed out
*/
@Timeout
public void cleanCache(Timer timer) {
if (timer.getInfo() instanceof String) {
if (((String) timer.getInfo()).equals("Clean Cache")) {
... do some processing ...
}
}
}
}


Right, so we have a method for starting a timer (startTimer). This method needs to be invoked in order to start the timer. This is one of the drawbacks of the TimerService, you cannot tell it to just start when the application is deployed (will be there in EJB3.1). Instead I use a Servlet Context Listener to invoke the startTimer method when the accompaying webapplication is deployed:


public class TimerInitialisationListener implements ServletContextListener {

/** Local interface for {@link MyTimerBean}. */
@EJB private MyTimerLocal myTimer;

/**
* Initialises the timer service.
*
* @param event
* Event that invoked the listener
*/
public void contextInitialized(ServletContextEvent event) {
Calendar now = Calendar.getInstance();
now.set(Calendar.HOUR_OF_DAY, 0);
now.set(Calendar.MINUTE, 0);
now.set(Calendar.SECOND, 0);
int year = now.get(Calendar.YEAR);
int month = now.get(Calendar.MONTH);
int dayOfMonth = now.get(Calendar.DAY_OF_MONTH);
int hourOfDay = now.get(Calendar.HOUR_OF_DAY);
int minute = now.get(Calendar.MINUTE);
Long repeat = 60000L * 60L * 24L;
LogFactory.getLog(TimerInitialisationListener.class).info("Start time: " + now.getTime());
LogFactory.getLog(TimerInitialisationListener.class).info("Repeat every: " + repeat + " ms (" + (repeat / 3600000L) + " hrs)");

myTimer.startTimer(new GregorianCalendar(year, month, dayOfMonth, hourOfDay, minute).getTime(), 60000L * 60L * 24L, "Generate Report");
}

/**
* Context is uninstalled from the servlet container.
*
* @param event
* Event that invoked the listener
*/
public void contextDestroyed(ServletContextEvent event) {
LogFactory.getLog(TimerInitialisationListener.class).info("Stopping timer");
myTimer.stopTimer("Generate Report");
}
}


When you deploy the enterprise application you will see that the timer is set to start at midnight and execute every 86400000 ms (i.e. every 24 hours). What you will notice is that it is only the generateReport method that is executed fully at every timeout as I've put in a check to ensure that it is the correct action being executed. Instead of using a String as the identifier of the Timer you can create create your own custom objects as pass them instead (just remember to make it serializable).

That's all for now. I'll bring another entry when EJB3.1 has been released and the new timer service annotations have been implemented.

On a side note, I've used Quartz before and it's great - I just like to stick to the standards if it can do the job.

Checkout the JavaDocs for the TimerService for more information.

UPDATE: 6. May 2008: Yesterday I was preparing some code using the timer service and I noticed that only the first method annotated with @TimeOut is executed upon timeout. Therefore, use only one @TimeOut method per SessionBean.

Saturday 15 March 2008

Yippiee my new phone arrived

For a long time my old phone has been way past retirement. It was a Qtec 2020 (I believe). I've always loved smartphones and hated the glorified music players (e.g. Sony Ericsson). I don't see the point in the fancy music player phones, but that is probably because I'm perfectly happy with my iPod and have no plans of replacing it for something less cool.

Anyways, the Qtec acted up a long time ago. I used it as my organiser, phone and GPS for the car. When it suddenly started losing all its memory and at the same time I misplaced my stylus, I thought that it was high time to get a new phone. So this time I decided not to get a smartphone (mostly because the complete lack of market for smartphones in Denmark - this makes it very expensive!). Instead I got myself a Nokia 6120 with all the latest services provided on the 3G network (Skype, MSN, MobileTV, etc).

From the End-to-End Web Service Tutorial on NetBeans.org So far I'm loving the phone! It is fully compatible with Java MIDP 2.0 - so I'll have to get cracking with Java ME to make some applications soon. Can anybody recommend a good starting point for Java ME programming? My background in Java is purely enterprise and web. NetBeans got some cool mobile development aids that I'll be trying out - but I'd really like to know the basics before I start all the dragging and dropping. In anycase I think this is a good place to start: NetBeans 6.0 Mobility Documentation. It's got a pretty good tutorial for creating a mobile Dilbert browser.

Ordered the certification books

I've finally ordered the certification books that I mentioned in a previous post (SCJP Sun Certified Programmer for Java 5 Study Guide (Exam 310-055): Study Guide Exam 310-055 and Sun Certified Enterprise Architect for Java EE Study Guide (Exam 310-051): Study Guide Exam 310-051).

It is my personal goal to have taken both certifications before the end of April. I was tempted to also get the Certification Press book about Sun Certified Business Components Developer, but it got such bad reviews on Amazon that I didn't dare to get it. Unfortunately it seem to be the only study guide for Business Components Development.

Anyways, I'm looking forward to the books getting here so that I can get started!