第2回 HelloWorld を作ろう!

今回の講座は?

まず開発環境を用意し、簡単なサンプルプログラム HelloWorld を作成します。

J2SE のインストール

最初は J2SE のインストールです。 僕は Windows XP Home Edition に all languages 版の J2SDK v1.4.0 を入れました。 現時点での最新版です。 v1.3.0 以上であれば OK なので、実績のある v1.3.1 を入れるのも良いでしょう。

ソフトウェア名 Java2 SDK, Standard Edition, v 1.4.0
対象OS Windows (各国語)
ダウンロード先 http://java.sun.com/j2se/1.4/ja/download.html
ファイル名 j2sdk-1_4_0-win.exe
サイズ 37,067,134 バイト
インストール方法 InstallShield

InstallShield による自動インストールなので簡単です。 あとはインストール先の bin ディレクトリ (僕の場合はデフォルトの c:\j2sdk1.4.0\bin) に実行パスを通すだけ。 これだけの説明で不安がある人は 補足2 インストールの様子は? を参考にしてみてください。

英語のドキュメント があり、ローカルにダウンロードも可能です。 Java 2 Platform API Specification のセクションはブックマークする価値あり。 あ、いつのまにか 日本語版 も公開されていますね。 (^-^)

J2ME Wireless Toolkit のインストール

さあこれで通常の Java言語 は使用できるようになりました。 引き続いて J2ME Wireless Toolkit をインストールします。 これは 「CLDC および MIDP に準拠するアプリケーションの開発に必要なエミュレーション環境、マニュアル、 およびサンプルアプリケーションを備えた開発者向けツールセット」 だそうです。 これ1つで J2ME が体験できる、なかなか優れもののセット。 しかも日本語版があります。

ソフトウェア名 Java2 Platform, Micro Edition, Wireless Toolkit v1.0.3 日本語版
対象OS 日本語 Windows 98SE/NT/2000
ダウンロード先 http://java.sun.com/products/j2mewtoolkit/ja_download.html
ファイル名 j2me_wireless_toolkit-1_0_3-ml-win.exe
サイズ 8,519,506 バイト
インストール方法 InstallShield

J2SDK と同様、ダウンロードしたファイルを実行するだけで導入は終了します。 せっかくなので 補足2 インストールの様子は? に簡単な流れを書いてみましたが・・・ こちらは読まなくても何の問題もないと思われます。 (あは

日本語ドキュメント のインストール

同じ場所に日本語のドキュメントもあるので、忘れずにダウンロードしておきましょう。

ソフトウェア名 J2ME Wireless Toolkit Japanese Documentation 1.0.3
対象OS 日本語が表示できる Web Browser, Acrobat Reader
ダウンロード先 http://java.sun.com/products/j2mewtoolkit/ja_download.html
ファイル名 j2me_wireless_toolkit-1_0_3-ja-doc.zip
サイズ 1,606,138 バイト
インストール方法 zip ファイルを解凍

zip ファイルなので、適当な解凍ツールで解凍するだけです。 ・・・いやいや、ここは java の講座です。 java の アーカイブツール jar を使って解凍してみましょう。

コマンドプロンプトより 'jar xvf j2me_wireless_toolkit-1_0_3-ja-doc.zip' と入力すれば解凍できます。 jar は unix のコマンド tar とほぼ同じ使い方をします。 'x' が解凍の指定、'v' は詳しいメッセージの出力、f は対象ファイルの指定です。 解凍せずに中を見たい場合は 'x' のかわりに 't' を指定します。

C:\J2mewtk>jar xvf j2me_wireless_toolkit-1_0_3-ja-doc.zip
  docs_ja/ が作成されました。
docs_ja/copyright.html が抽出されました。
docs_ja/UnixReleaseNotes.html が抽出されました。
docs_ja/BinaryLicense.html が抽出されました。
docs_ja/index.html が抽出されました。
docs_ja/BinaryReleaseNotes.html が抽出されました。
docs_ja/Japanese12B.gif が抽出されました。
  docs_ja/docs/ が作成されました。
docs_ja/docs/BasicCustomizationGuide.pdf が抽出されました。
docs_ja/docs/ForteJ2MEGuide.pdf が抽出されました。
docs_ja/docs/UserGuide.pdf が抽出されました。
index.html が抽出されました。

C:\J2mewtk>

解凍先は C:\J2mewtk がお勧めです。 ここ以外だと、Toolkit のドキュメントとのリンクがズレてしまうようです。 index.html をダブルクリックして流し読みしておきましょう。

POSE のインストール

作成したプログラムを試すには、POSE (Palm OS Emulator) があると便利です。

ソフトウェア名 Palm OS Emulator for Windows version 3.5
対象OS Windows
ダウンロード先 http://www.palmos.com/dev/tech/tools/emulator/
ファイル名 emulator-win.zip
サイズ 2,982,752 バイト
インストール方法 zip ファイルを解凍

適当なディレクトリに解凍するだけです。 僕は c:\local\POSE_v35 というディレクトリ (フォルダ) を作って、そこに解凍しました。 c:\local にインストール不要のソフトをまとめるのが、僕の好みです。

まずは PRC-Tools 講座や、Code Warrior講座の第3回を読んでみてください。 (^-^; POSE の実行には ROM イメージが必要なんですよね。 まだ入手できていなくても大丈夫。 実機があれば、POSE が無くとも開発はできます。 って、当然か。 (^-^;;

ちなみに同じ場所に、エミュレータの外観を変えるためのスキンが置いてあります。 こちらはお好みでどうぞ。 (^-^;

とりあえず、作ってみましょう!

開発環境をインストールしたら、とりあえず簡単なサンプルを作成してみる。 やっぱこれが基本ですよね? そして作成するサンプルは慣習に従い、"Hello World!" って文字列を表示するもの。

まずはプロジェクトを作成

スタート -> プログラム -> J2ME Wireless Toolkit 1.0.3 -> KToolbar と起動しましょう。 '新規作成(N)' のボタンを押すと、プロジェクト名とクラス名の入力を求められます。 今回は、プロジェクト名は 'FirstStep'、クラス名は 'HelloWorld' と入力します。 同じ名前にしても良いのですが、最初なのできちんと分けてみました。

クリックすると拡大します

'プロジェクトの作成' ボタンを押すと、アプリケーション属性を設定するためのウィンドウが開きます。 4ページもあるので最初はギョ!っとしますが、今回は特に変更する必要はありません。 '了解' ボタンを押すだけです。

クリックすると拡大します クリックすると拡大します

クリックすると拡大します クリックすると拡大します

せっかくなので簡単に説明します。

最初のタブ '必須項目' は コンフィギュレーションやプロファイル等の基本的な情報を設定します。 MIDlet という言葉については後ほど説明しますね。 ちなみに MIDlet-Vender は作成者の情報を示しますので、自分の名前に変更して OK です。

次のタブ 'オプション項目' もその名の通りですね。 説明文や情報を公開したURLを指定できます。 MIDlet-Data-Size は対象マシン上で使用するローカルストレージの大きさを指定するもので、 データを保存したいソフトウェアを作成する時には指定する必要があります。

次の 'ユーザ定義' では独自のキーを追加することができます。 最初は空ですが '追加' ボタンを押すことで、任意のキーを追加することができます。 画面は、試しに test を入力した後に、test2 を入力中のものです。

最後の 'MIDlets' には、実際のクラス名 'HelloWorld' が表示されています。 また .png 形式でアイコンが指定できるんだな、と想像できますね。 1つのプロジェクトには複数の MIDlet を入れることができ、ここではその順番も変更できます。

更に詳しく知りたい場合は、日本語ドキュメントのユーザーガイドを見てくださいね。

クリックすると拡大します

'了解' ボタンを押して新規プロジェクトが作成されます。 コンソール上のメッセージを読むと、c:\j2mewtk\apps の下に、 プロジェクト名と同じ名前のディレクトリが作られたのがわかります。

プロジェクト の中身

さて、新規にプロジェクトを作成すると、どんなファイルが生成されるのでしょうか? c:\j2mewtk\apps の下をチェックしてみましょう。

 FirstStep
│  ├ bin
│  │  ├ FirstStep.jad
│  │  └ MANIFEST.MF
│  ├ lib
│  ├ res
│  └ src

幾つかのディレクトリと、ファイルが2つ作成されています。

MANIFEST.MF はマニフェストといって、 Java のソフトウェアを jar ファイルにまとめて配布する際に必要となるファイルです。 Java言語による開発ではよく使います。 FirstStep.jad は目新しいですね。 この .jad ファイルは、jar ファイル (ソフトウェア) と同時に配布される定義ファイルです。

これら2つのファイルの中身は、非常に似通っています。 単なるテキストファイルなので、興味があればメモ帳かなにかで中身をチェックしてみてください。 相違点は、この2つのファイルの目的を考えると理解できると思います。

jad ファイルはそのソフトウェアを 入手 する際に必要な情報が記述されています。 実行するかどうかの判断、もしくは実行すると判断した場合に全体のサイズやダウンロード先など。 マニフェストは、実際に 実行 する時に参照されます。 どのクラスから実行が開始されるかなど。 属性がどちらのファイルに格納されるかは、日本語ドキュメントのユーザーガイドに詳しい説明があります。

とりあえず 空のクラス を作成してみる

Java のソースファイルは、src ディレクトリの中に作成します。 とりあえず、MIDlet クラスを継承した 何もしないクラス を記述してみましょう。 HelloWorld.java という名前のテキストファイルを新規作成し、以下のように入力してください。

HelloWorld.java (その1)
import javax.microedition.midlet.MIDlet;

public class HelloWorld extends MIDlet {
  public void startApp() {}
  public void pauseApp() {}
  public void destroyApp(boolean unconditional) {}
}

import 命令で、MIDlet というクラスを使用すると宣言しています。 MIDlet クラスは javax.microedition.midlet というパッケージ (Java におけるクラス等の管理の単位) に含まれています。 この宣言が無いと、MIDlet というクラスを指定するたびに javax.microedition.midlet.MIDlet という長い、パッケージ名を含めた名前を用いなくてはなりません。

次に HelloWorld クラスの定義で、 extends MIDlet と MIDlet クラスを継承することを記述しています。 Palm で動作する Java プログラムは、必ずこの MIDlet を継承していなければなりません。

継承する MIDlet クラスは、abstract なメソッドを3つ 含んだクラスです。 abstract なメソッドは、継承する側で必ず定義しなくてはなりません。 今回は何もしないプログラムなので、全て {} の中身が空な、 何もしないメソッドとして定義しています。

おまけコラム: abstract class

abstractな要素を含むクラスを、アブストラクト・クラス (abstract class) と呼びます。 これらのクラスは直接使用することはできず、 継承して abstract 部分を定義しなければなりません。 定義し忘れるとコンパイル時にエラーになります。 これは一見、面倒な仕組みに思えます。 でも、ちょっとその存在意義を考えてみせんか? (^-^;

初めて見たクラスを再利用する場合を考えてみましょう。 そのクラスを継承し、目的に応じた改変作業が必要だとします。 50個のメソッドがあっても、マニュアルを最初から眺める必要はありません。 とりあえず、abstract 宣言がされた数個を調べれば十分です。 元のクラスの設計者がきちんと利用を想定していれば、 目的に応じて改変すべきポイントを abstract 宣言しておいてくれています。

同じ目的で、中身が空のメソッドを使用する場合もあります。 abstract よりも目立ちませんし、コンパイル時のチェックもありませんが、 クラスを直接利用することが可能になります。 このあたりは case by case でしょうか。 忘れられては困る重要なポイントのみ abstract を指定し、 動作に大きな影響を与えない、 もしくは再定義される可能性が低い部分には、 空のメソッド宣言を使用するのが一般的な気がします。

abstract 宣言は、元のクラスの設計者から再利用者に対する 「これは重要な部分だから、忘れないでね!」 というメッセージだと理解していただけたら幸いです。 (^-^)



これら3つのメソッドがどんな時に呼び出されるか、 その名前からおおよその見当がつくのではないでしょうか? startApp() はプログラムが開始する時。 pauseApp() はプログラムが一時停止される時。 destroyApp() はプログラムが終了する時です。

空のクラス をビルド(コンパイル) してみる

さてここで、開発環境がうまく動作するかちょっと試してみましょう。 KToolbar で 'ビルド (B)' のボタンを押します。 うまくいけば KToolbar のコンソールに「ビルドは完了しました」 というメッセージが表示されます。

さて、プロジェクトの内容はどうなったでしょうか? c:\j2mewtk\apps\FirstStep の中を調べてみましょう。

 FirstStep
│  ├ bin
│  │  ├ FirstStep.jad
│  │  └ MANIFEST.MF
│  ├ classes
│  │  └ HelloWorld.class
│  ├ lib
│  ├ res
│  ├ src
│  │  └ HelloWorld.java
│  ├ tmpclasses
│  │  └ HelloWorld.class
│  └ tmplib

src ディレクトリにある HelloWorld.java は、さきほど作成したもの。 classes, tmpclasses, tmplib という3つのディレクトリが追加され、 HelloWorld.class というファイルが増えていることがわかります。

classes と tmpclasses には同じファイルが置かれています。 tmpclasses はコンパイル時に使用される作業用のディレクトリでしょう。

.class ファイルは Java の実行ファイルですから、ビルドは無事に終了したようですね。 開発環境はうまく動いているようです。

Hello World! と表示させよう!

さて、それでは先ほどの HelloWorld.java ソースファイルに、 処理を追加していきましょう。

今回のプログラムは単に文字を表示することが目的なので、 一時停止時 (pauseApp) や 終了時 (destroyApp) の処理は特にありません。 開始時 (startApp) の処理のみ追加します。

HelloWorld.java (その2)
import javax.microedition.midlet.MIDlet;
import javax.microedition.lcdui.*;

public class HelloWorld extends MIDlet {
  public void startApp() {
    Form form = new Form("Hello World!");
    Display.getDisplay(this).setCurrent(form);
  }
  public void pauseApp() {}
  public void destroyApp(boolean unconditional) {}
}

まずは import 命令で、 javax.microedition.lcdui パッケージを使用すると宣言します。 クラス名のかわりに * というワイルドカード文字を指定すると、 そのパッケージ内の全ての要素を指定したことになります。 ちなみに lcdui は "LCD (液晶ディスプレイ) User Interface" の略でしょうかね。

startApp() の内部では、まず new Form("Hello World!") と new 命令で 部品 Form のインスタンス (オブジェクト) を生成します。 引数として与えた文字列が Form の名前として表示されます。

その Form インスタンスを、 紫色 の部分で実際に表示させています。 this はこのアプリケーション自身を意味しますから Display.getDisplay(this) で、現在の画面を示す Display インスタンスを得ることができます。 得られたインスタンスに対し setCurrent(form) と form インスタンスを指定すれば、form が画面に表示されます。

クリックすると拡大します

さて、実行してみましょう。 ビルドの後にデバイスを "PalmOS_Device" に変更し、 '実行 (R)' ボタンを押せば POSE で実行されます。

POSE Setting

初めての実行の時、POSE の位置を入力する画面になります。 POSE を解凍したディレクトリを指定しましょう。

ここで "取り消し" を押すとキャンセルされますが、 c:\j2mewtk\wtklib\devices\PalmOS_Device のディレクトリに FirstStep.prc というファイルが作成されています。 これを実機に HotSync すれば、POSE が無くても実行することができます。 (^-^)/

HelloWorld MIDlet

これが実行画面です。 左上のタブに、"Hello World!" と表示されていますね。

ちょっと画面が寂しいかな?

無事に Hello World! は表示できたものの、少し画面が寂しいですね。 Form の名前で表示するのは、ちょっと裏技っぽいですし。 ちゃんとしたメッセージを追加してみましょう。 (^-^;

HelloWorld.java (その3)
import javax.microedition.midlet.MIDlet;
import javax.microedition.lcdui.*;

public class HelloWorld extends MIDlet {
  public void startApp() {
    Form form = new Form("Hello World!");
    form.append(new StringItem("Message", "Hello World!"));
    Display.getDisplay(this).setCurrent(form);
  }
  public void pauseApp() {}
  public void destroyApp(boolean unconditional) {}
}

Form は画面のベースとなる部品で、その上に他の部品を追加することができます。 new StringItem("Message", "Hello World!") と部品 StringItem のインスタンスを生成し append() メソッドで form に追加してみます。

HelloWorld MIDlet

と、画面に "Hello World!" という文字列が追加されましたね。 (^-^)

append() で追加できる部品は他にもあるので、いろいろ変更して遊んでみてください。 UIDemo というサンプルがあるので、プロジェクトを選んで実行すると、 いろいろな部品が試せて面白いですよ。

UIDemo MIDlet

次回の講座は?

HelloWorld! 楽しんでいただけましたでしょうか? 次回はこのサンプルを元に、入力を処理したり、グラフィックを描いたりする予定です。

楽しみましょう! (^-^)/



Copyright (c) 2002 Toshio Yamashita
first version 2002/07/21