For information about the design and functionality of the MIDlet, see section Design.
To create the MIDlet:
Create the URLWriter.java
class file.
Import the required classes and packages.
// Classes for contactless communication import java.io.IOException; import javax.microedition.contactless.ContactlessException; import javax.microedition.contactless.DiscoveryManager; import javax.microedition.contactless.TargetListener; import javax.microedition.contactless.TargetProperties; import javax.microedition.contactless.TargetType; // Classes for NDEF targets import javax.microedition.contactless.ndef.NDEFMessage; import javax.microedition.contactless.ndef.NDEFRecord; import javax.microedition.contactless.ndef.NDEFRecordType; import javax.microedition.contactless.ndef.NDEFTagConnection; import javax.microedition.io.Connector; // Classes for UI import javax.microedition.lcdui.Alert; import javax.microedition.lcdui.AlertType; import javax.microedition.lcdui.Command; import javax.microedition.lcdui.CommandListener; import javax.microedition.lcdui.Display; import javax.microedition.lcdui.Displayable; import javax.microedition.lcdui.Form; import javax.microedition.midlet.*;
Set URLWriter
to extend MIDlet
and to implement TargetListener
and CommandListener
. Create the required variables.
public class URLWriter extends MIDlet implements TargetListener, CommandListener { // Global variables for the UI private Command exitCommand; private Form form;
Create the URLWriter
class constructor.
public URLWriter() {
Set up the MIDlet UI.
exitCommand = new Command("Exit", Command.EXIT, 1); form = new Form("URLWriter"); form.addCommand(exitCommand); form.setCommandListener(this); form.append("Touch tag to write URL: \"www.developer.nokia.com\"");
Register the MIDlet to receive notifications when NDEF targets are detected.
// Determine the contactless target types supported by the device TargetType[] supportedTargetTypes = DiscoveryManager.getSupportedTargetTypes(); // Check if the NDEF_TAG type is supported by the device, // and, if it is, register TargetListener for it for (int i=0; i<supportedTargetTypes.length; i++) { if (supportedTargetTypes[i].equals(TargetType.NDEF_TAG)) { // Register TargetListener (this) for NDEF targets try { DiscoveryManager dm = DiscoveryManager.getInstance(); dm.addTargetListener(this, TargetType.NDEF_TAG); } catch (SecurityException se) { displayAlert("Unable to register TargetListener: " + se.toString(), AlertType.ERROR); } catch (ContactlessException ce) { displayAlert("Unable to register TargetListener: " + ce.toString(), AlertType.ERROR); } catch (IllegalStateException ise) { displayAlert("Unable to register TargetListener: " + ise.toString(), AlertType.ERROR); } catch (NullPointerException npe) { displayAlert("Unable to register TargetListener: " + npe.toString(), AlertType.ERROR); } // Break the loop, since a matching target type has been found break; } } }
Create the mandatory MIDlet lifecycle methods. The MIDlet uses
the startApp
method to display the UI.
public void startApp() { Display.getDisplay(this).setCurrent(form); } public void pauseApp() { } public void destroyApp(boolean unconditional) { }
The targetDetected
method of the TargetListener
interface is called every time the device detects one or more NDEF
targets. The MIDlet uses the targetProperties
array
returned by the method to open an NDEF connection to the target.
The custom getNDEFTAGConnection
method
is used to retrieve the first applicable connection, an NDEF connection,
from the set of connections returned in the targetProperties
array.
/** * Implements the callback function of TargetListener * @param targetProperties: Array of targets found by the device */ public void targetDetected(TargetProperties[] targetProperties) { // In case no targets are found, exit the method if (targetProperties.length == 0) { return; } // NDEF connection for write operation NDEFTagConnection ndconn = getNDEFTAGConnection(targetProperties); try { // Header byte: open bookmark in browser byte[] headerByte = {0x00}; // Payload text: URL as a byte array byte[] urlBytes = "http://www.developer.nokia.com/".getBytes(); // Create an NDEF record of type urn:nfc:wkt:U (a URI record) // using the NFC Forum Record Type Description syntax NDEFRecord r = new NDEFRecord(new NDEFRecordType(NDEFRecordType.NFC_FORUM_RTD, "urn:nfc:wkt:U"), null, null); // Append payload manually r.appendPayload(headerByte); r.appendPayload(urlBytes); // Create record array and add record NDEFRecord[] myRecArray = new NDEFRecord[]{r}; // Generate a message out of the array NDEFMessage myMessage = new NDEFMessage(myRecArray); // Write message to tag ndconn.writeNDEF(myMessage); displayAlert("Information written", AlertType.INFO); } catch (IOException io) { displayAlert("Writing failed, please try again.", AlertType.ERROR); } catch (ContactlessException io) { displayAlert("ContactlessException during writeNDEF(): " + io.toString(), AlertType.ERROR); } catch (Exception e) { displayAlert("Exception: " + e.toString(), AlertType.ERROR); } // In case of an exception, close connection properly finally { // Close connection again if (ndconn != null) { try { ndconn.close(); } catch (IOException ex) { displayAlert("IOException during close(): " + ex.toString(), AlertType.ERROR); } } } } private NDEFTagConnection getNDEFTAGConnection(TargetProperties[] tProp) { for (int j = 0; j < tProp.length; j++) { Class[] connections = tProp[j].getConnectionNames(); if (connections != null) { for (int i = 0; i < connections.length; i++) { if (connections[i].getName().equals( "javax.microedition.contactless.ndef.NDEFTagConnection")) { try { return (NDEFTagConnection) Connector.open(tProp[j].getUrl(connections[i])); } catch (Exception e) { displayAlert("Error writing NDEF: " + e.toString(), AlertType.ERROR); } } } } } return null; }
Implement command and message handling for the MIDlet UI. The
MIDlet uses the commandAction
method to handle the
exit command, which involves unregistering TargetListener
and closing the MIDlet. The MIDlet uses the displayAlert
method to display error and other messages through the MIDlet UI.
/** * Implements the callback function of CommandListener * @param command: Command given * @param displayable: Associated Displayable object */ public void commandAction(Command command, Displayable displayable) { if (command == exitCommand) { DiscoveryManager dm = DiscoveryManager.getInstance(); dm.removeTargetListener(this, TargetType.NDEF_TAG); destroyApp(false); notifyDestroyed(); } } private void displayAlert(String error, AlertType type) { Alert err = new Alert(form.getTitle(), error, null, type); Display.getDisplay(this).setCurrent(err, form); } }