棚からパルチャギ

日々の雑記、ニュース拾いとか

2007. 11. 18

Android (エミュレータ小ネタ)
Androidのエミュレータは、小さなディスプレイとボタンが並んだ無骨なデザインで、 少しがっかりした人もいるかもしれませんが(実機ではないですけど)、 エミュレータのスキンは全部で4種類あるので、別のデザインに変更することが可能です。

> emulator -skin HVGA-P
起動時の引数に、上記のようにスキン名を指定すると、任意のスキンを適用してエミュレータが起動します。 スキンファイルは <android_sdk(インストールパス)>/tools/lib/images/skins に置かれています。 必要な画像を用意してレイアウトを定義すれば、自作スキンで動かすこともできそうですね。 各スキンのデザインはこんな感じ(↓)。


左から順に…
・HVGA-L
・HVGA-P
・QVGA-L (デフォルト)
・QVGA-P



もう一つ。
デフォルトの壁紙は、オーロラっぽいのとNice boat.っぽいものの2種類しか用意されていないんですが、 どうにも味気ないので自分好みの壁紙に変更する方法。 実機じゃないのであまり意味はないですけど、開発中のモチベーション維持にw

画像(ここではimage.jpg)を用意して、エミュレータが起動している状態で、コマンドラインから以下のコマンドを実行します。 エミュレータを再起動すると壁紙が変更されています。元に戻す場合は、デフォルトの壁紙を選択しなおしてください。
> adb push image.jpg /data/misc/wallpaper

画像形式はJPG/GIF/PNG/BMPあたりなら認識してくれるようです。 サイズは解像度に合わせて自動的に拡大/縮小されますが、横長の壁紙を縦画面のインターフェースで使用すると、 縦に伸ばされてしょんぼりするので、解像度にあったサイズで用意しておくのがよいと思います。
スキンの解像度は、320x240/480x320の縦または横画面。 バッテリー残量や時計表示で上部に20dot分確保されるので、その分を差し引く必要があります。
Android (プリプロセッサ)
携帯Javaの世界では、とにかくファイルサイズを縮小する必要があるので、 プリプロセッサを使って定数やメソッドをマクロで展開したりすることも多かったと思います。 そうでなくても、#ifdef とか enum(これは言語仕様だけど) 使いたいよねー、 ということでC/C++付属のものや私製のプリプロセッサを仲介させる場合は、build.xmlに以下のような記述を追加します。
<!-- Execute preprocessor --> <property name="preprocess.exec" value="C:/Development/Tools/preprocessor.exe" /> <target name="preprocess"> <apply executable="${preprocess.exec}" dest="${srcdir}" parallel="false"> <srcfile/> <targetfile/> <fileset dir="${srcdir}" includes="**/*.j"/> <mapper type="glob" from="*.j" to="*.java"/> </apply> </target>

<!-- Compile this project's .java files into .class files. --> <target name="compile" depends="dirs, resource-src, aidl, preprocess"> ... </target>
preprocessターゲットを新規に追加して、compileターゲットの依存関係に追加します。 ここでは、ソースコードディレクトリに存在する*.jファイルを、プリプロセッサを介して*.javaファイルに変換しています。

赤字のプリプロセッサのファイルパスは使用するプログラムに置き換えてください。 iアプリのときはpp_incというプリプロセッサを使っていたんですが、 Java5以降のアノテーション(@overrideとか)に対応していないので、変数やメソッド名の短縮命令と間違われて正しく処理できなくなってしまいました。残念。 前の会社で社内ツールとして使っていたプリプロセッサは、携帯アプリ開発に特化していたのもあって、 非常に高機能で便利だったんですが、あれをオープンソースとかで公開してくれないかしら。

2007. 11. 17

Android (携帯アプリ互換編)
[android.swf]
iアプリでの定石(なのかも微妙だけど)だと、アプリケーション本体であるIApplicationと描画用のCanvasを継承したクラスを1つずつ用意して、 Canvasのメソッド内でメインループを回すのが一般的だと思います。 メインループはwhile()で回して、System.getCurrentMiils()を見ながらFPSを調整、キー情報はループ毎にポーリングして、 描画はCanvasから取得したGraphicsにlock/unlockして描画みたいな。

AndroidではIApplocationに相当するものがActivity。 描画はCanvasそのものに描くのではなくて、View#OnDraw()で引数として渡されるCanvasに描画。 メインループは、Handlerで定期的に内部処理と描画の更新を行うというのが作法(?)みたいですね。

速度や正確さを求めると結局はwhile()で回すことになるのかもしれないけど、 携帯アプリみたいにほぼシングルスレッドで動作するわけでもなさそうなので、とりあえずは奇麗な方法で。 キー情報はonKeyイベントが発生するまで状態を取得する手段が無いっぽいので、 イベントハンドラでキー状態を保持するようにKeyPadStateクラスを作成しました。 とりあえずメインループとキー情報が取れて、描画対象が1枚だけということになれば携帯アプリと同じような感覚で作れるかなー、 ということで三角形が動くだけのサンプルでも置いておきます。
描画関係だと、あとはスプライトとして使っていたImageはDrawableで代用。 背景なんかは従来通りにBitmapで保持して、BitmapDrawableで描画すればなんとかなりそう。 ダブルバッファリングはonDraw()の最中に表示スクリーンが再描画されることはないので、特に意識する必要はなさそう。 シーン管理を書けばゲームっぽいものなら作れる気がしますね。

あと必要そうなのは、データの読み書きと通信処理、サウンド機能。OpenGLとか3D関連は苦手。 端末機能は当面使わないので保留。公式のサンプルコードはじっくり読むとかなり参考になるので、 ドキュメントと合わせてもう少し勉強します。
Android (デバッグ編)
DDMS(Dalvik Debug Monitor Service) Toolという素敵っぽいツールが付属しているんですが、 いまいち使い方が把握できていないので、とりあえずは原始的にprintデバッグ的な。 Eclipseと統合していれば、この辺もコンソールに表示されたりするんだろうなー、とか思いつつ。

Androidのデバッグ出力はSystem.out.println()ではなく、android.util.Logを使います。 staticなメソッドがあるので、そのままこんな感じで(↓)呼び出します。
private static final String TAG = "APPNAME";

Log.e(TAG, "This is ERROR message."); Log.w(TAG, "This is WARNING message."); Log.i(TAG, "This is INFO message."); Log.d(TAG, "This is DEBUG message."); Log.v(TAG, "This is VERBOSE message.");
「Log.」に続く一文字がエラーレベルを示します。「e」ならば「ERROR」。 ERRORが最も深刻度が高く、順にWARNING→INFO→…と下がっていきます。 第1引数はログメッセージにつけるタグ名で、ログをフィルタリングする際に使用するので、 アプリケーションの名前などを設定しておくと良いと思います。

吐き出されたログメッセージは、adb logcat で閲覧できます。
> adb logcat APPNAME:D
そのまま表示すると大量に流れてしまうので、オプションでタグ名とエラーレベル(優先度)を指定してフィルタリングします。 上記の例では、タグが「APPNAME」でエラーレベルがDEBUG以上のメッセージのみを表示します。 タグ名は「*」にすると、全てのタグを対象にすることができます。
> adb logcat *:W
エラーレベル(優先度)に指定できる文字列は以下の通り。調べるまでもないかもですが…。
> adb logcat --help V Verbose D Debug I Info W Warn E Error F Fatal
Android (インストール編・補足)
書き忘れていたので、補足です。
Androidのアプリケーションはパッケージ単位で認識されているようなので、 たとえば com.example というパッケージでは1つのアプリケーションしか登録することができません。多分。 なので、com.example.Foo と com.example.Bar というアプリケーションを同時にインストールすることはできず、 どちらか一方だけが有効になります。

パッケージ名はアプリケーション名まで含めて com.example.foo.Foo のように命名したほうが良さそうですね。 …って、これJavaでは常識だったりしますか???


あとは、アプリケーションの削除について。 エミュレータのインターフェース上ではアプリケーションを削除することができないので、ここでもadb(Android Debug Bridge)を使用します。
1. エミュレータを起動する
2. adb shellでエミュレータ(が動いている土台のqemu?)にシェルログインする
> adb shell
3. data/app に移動する
# cd data/app
4. インストールした.apkファイルが置いてあるので削除する
# ls ls -rw-r--r-- system system 1325833 2007-11-11 20:59 ApiDemos.apk -rw-rw-rw- root root 118915 2007-11-16 06:19 LunarLander.apk # rm LunarLander.apk

2007. 11. 16

Android (インストール・実行編)
続き。プロジェクトのビルド。
activityCreatorで生成するとbuild.xmlが自動的に用意されるので、antでビルド可能です。 プロジェクトのディレクトリに移動して、ant [Enter] すればおけ。
> cd C:\Development\Projects\android\sample > ant
特に問題がなければ、新規に作成されたbinディレクトリの中に Sample.apk ができているはずです。 ちなみに.dexファイルはコンパイル済みのクラスファイルをまとめたもの、それにマニフェストファイルや各種リソースを含めて一纏めにしたものが.apkファイル。 インストールに必要なのは、この.apkファイルだけ。

ビルドの際にこんなエラーが出る場合は、複数JDKが混在していて、正しいjavacを参照していない可能性があります。 JAVA_HOMEが1.5以降に設定されていれば問題ないんですが…普通に間違ってましたorz。
[javac] javac: 1.5 は無効な VM バージョンです。


で、アプリのインストール編。(参考:Running an Android Application)
付属ツールのadb(Android Debug Bridge)を使用して、アプリケーションを転送します。
1. エミュレータを起動する
> cd C:\Development\android_sdk\tools > emulator.exe
2. しばらくエミュレータで遊ぶw
3. 堪能したらカーソルキーの右側にある家ボタンを押して、メインメニュー(?)に戻っておく
4. プロジェクトのディレクトリに移動して、adb install .apk でインストール実行
> cd C:\Development\Projects\android\sample > adb install bin/Sample.apk
初回起動時なのか、起動後にまだ準備ができていないのか、インスト-ル時に以下のようなエラーメッセージが表示されることがあるけど、 めげずにもう一回実行すればおけ。
* daemon not running. starting it now * * daemon still not running * error: no device
5. エミュレータのメニューの一番左にある「Applications」を開くと、アプリケーションが追加されています…が、何もない雛型アプリなので Hello, World! すら表示されません(>_<)

※Android SDKにはサンプルゲームも付属しているので、上記の手順で <Android_SDK>\samples\LunarLander とかをインストールしてみると、ちょっと楽しいかもしれません

続く。
Android (開発環境編)
Googleさんの携帯プラットホーム「Android」で遊んでみたので、覚書き諸々。 基本はプラグイン入れてEclipseで開発するみたいですけど、使い慣れたエディタで書きたいよーとか、 プリプロセッサ使わないと開発できないとか、ダメな旧人類古きよき開発者のために非Eclipse環境での開発をば。 WindowsXP SP2+JDK(1.5.0_14)+Ant(1.7.0)でのメモです。


まずは開発環境の用意。(参考:System and Software Requirements)
1. JDK(1.5以降)Apache-Ant(Windowsは1.7以降/Mac・Linuxは1.6.5以降)をインストール
2. 環境変数 JAVA_HOMEANT_HOME に、それぞれインストールしたディレクトリを設定
3. 環境変数 PATH%JAVA_HOME%\bin%ANT_HOME%\bin を追加する
4. Android SDKをインストール
5. 環境変数 PATH<Android_SDK(インストールしたパス)>\tools を追加

準備ができたら、アプリケーションの雛型を作成。
1. 適当なディレクトリに移動する
> cd C:\Development\Projects\android
2. 雛型作成用のスクリプトを実行する。「--out」オプションに出力先のディレクトリ名、引数にアプリケーションクラスのパッケージ名を指定します。
> activityCreator --out samplecom.example.sample.Sample
3. こんなプロジェクト一式が生成されます。
sample /res /src AndroidManifest.xml build.xml


こんなエラーが出る場合は、パッケージ名が短すぎるので、2階層(?)以上指定してあげます。
Traceback (most recent call last):
File "activityCreator.py", line 200, in <module>
File "activityCreator.py", line 197, in main
File "activityCreator.py", line 133, in Setup
AttributeError: 'NoneType' object has no attribute 'group'
helpメッセージ出すと書いてありました。ちゃんと嫁。
packageName is a fully qualified java Package in the format .... (with at least two components).

ちなみに、Eclipseプラグインを使わない開発については、公式のドキュメントにも載っているんですが、 全然親切じゃないので分かりづらい気がします…。

  [ 1 ]