Flash CS3 でゼロからはじめよう
AIRアプリケーション作成講座 Vol.2

今月はAdobe AIRのニューバージョン、Beta2がAdobe Labsでリリースされました。HTML、Flash、JavaScriptなどのスキルでデスクトップアプリケーションが開発できる環境は、さらに成熟度を増してきています。そして米国アドビのサイトでは「Adobe AIR Showcase」として、すでにリリースされているAIRアプリケーションが多数紹介されています。このように状況は日々整いつつあるAIR周辺ですが、やはり兎にも角にもクリエイターやデベロッパーの皆さんが、それぞれのアイデアを形にしていくことが、AIRの成長と成熟に欠かせません。今月もそのお手伝いということで、AIRアプリケーション制作講座の2回目として「データベースのハンドリング」を解説しましょう。

Adobe AIR update Beta 2 for Flash CS3 Professional公開

Adobe AIR Beta2がAdobe Labsで公開され、それに併せて Flash CS3 Professional Update もリリースされました。このアップデートは旧バージョンのAIR上ではご利用いただけませんので、まずは以下のリンクからAdobe AIR Beta2のインストールを行ってください。

Download the Adobe AIR Installer

Flash CS3 Professional 日本語版で使うには、このページの中頃にある日本語版向けのものを利用する必要があります。

Adobe AIR update Beta 2 for Flash CS3 Professional

すでに旧バージョンがインストールされている場合は、以下のファイルを削除してからインストールを実行してください。

Macintosh

Windows

AIR Beta2 の公開に伴ってFlash開発環境用のリファレンスやマニュアルも用意されるようになりました。現在ところ英語版のみではありますが、開発の際は以下のドキュメントも併せて参照してください。

 

なお、AIR Beta2によるAPIの変更で動作しなくなった機能や、マニュアルなどの記載内容によっては旧バージョン用のままになっているものもありますので、問題が解決しないような場合は、以下のリリースノートも併せて確認されることをお奨めします。

AIR 1.0 Beta 2 release notes - http://www.adobe.com/go/learn_air_relnotes

Beta2 によって変更されたAPIは数多くあり、Beta2 上で動作させるためにはプログラムを修正させる必要があります。それでは、前回の記事で作成したWebブラウザのアプリケーションをBeta2で再度動作するように修正するところから始めましょう。

Adobe AIR Beta2 の変更点

前回作成したWebブラウザのプログラムで、Beta2に伴う変更点としては、ウィンドウのドラッグ処理や終了処理に使用していた Stage.window を Stage.nativeWindow に修正する必要があります。

//背景(bg)をクリックしてウィンドウを移動できるようにする
bg.addEventListener(MouseEvent.MOUSE_DOWN, windowMove);
function windowMove(event:MouseEvent):void {
	stage.nativeWindow.startMove();
}

//ステージ上のCloseボタンをクリックして終了
close_btn.addEventListener(MouseEvent.CLICK, closeApli);
function closeApli(event:MouseEvent):void {
	stage.nativeWindow.close();
}

本記事で作成したプログラムの修正は上記だけですが、その他のAPIについての変更点はリリースノートの 10 Changes/Updates to AIR APIs をご確認下さい。

次に、Beta2 より パッケージ作成時には電子署名が必要になりました。これを行わない場合、airi という拡張子の中間ファイルが生成されますが、このままでは別途署名作業を行わない限りインストールを行うことはできません。インストール可能なパッケージファイルを作成するためには「コマンド」メニューから "AIR - Application & Installer Settings"をクリックし、表示されるダイアログにある 「Digital Signature」の項の「Change」ボタンをクリックします。

電子証明

すでに電子署名ファイルを作成している場合は「Browse」ボタンをクリックし、その電子署名ファイルを選択するか、まだ作成していない場合は「Create」ボタンをクリックして新たに電子署名ファイルの作成を行います。

デジタル証明書ダイアログ

ここで入力するパスワードはパッケージ作業の際に確認されますので、忘れないようにしてください。これによって、これまで通りインストール作業可能なパッケージファイルの作成をFlash CS3上から直接行うことができるようになります。

それでは実際のアプリケーションの作成に入りましょう。

AIR のローカルデータベースを利用する…その前に

Adobe AIR にはファイルベースのデータベースである SQLite が搭載されており、Flash CS3 からも直接ActionScriptの中にSQL言語を使ってアクセスできます。SQLite 自体はMySQLやPostgreSQLと同じく広く使用されているオープンソースのデータベースであるため、日本語の資料なども入手がしやすいのが利点です。

また、Flash ではデータベースを直接操作することができないため、以下のようなデータベース管理ソフトと併用することをお奨めします。

SourceForge.net: SQLite Database Browser

それではこのローカルデータベースを利用して、アクセスしたページの情報を保存できるブックマーク機能を作成します。その前に、現在のプログラムではURLの直接入力ができないので、ブラウザとしての使い勝手はまだまだです。そこで、Webブラウザのように、ユーザ側から直接URLをクリックしてページへのアクセスが行えるようにしましょう。

テキストツールを使用してステージ上にテキスト入力フィールドを作成し、そのインスタンス名を「URL_txt」という名前にします。

テキスト入力フィールド。インスタンス名を、url_txtにする。
「テキストフィールド」のプロパティ

次に、タイムラインの第1フレームにあるActionScriptに以下のコードを追加します。

//HTMLの表示が完了するとテキストフィールドに現在のURLを表示
html.addEventListener(Event.COMPLETE, completeHandler);
function completeHandler (event:Event):void {
	url_txt.text=html.location;
}

//ENTERキーが押されるとHTML更新
url_txt.addEventListener(KeyboardEvent.KEY_DOWN, openURL);
function openURL (event:KeyboardEvent):void {
	if(event.keyCode==Keyboard.ENTER){
	urlReq = new URLRequest(url_txt.text);
	html.load(urlReq);
	}
}

コードの最初の行では、HTMControlがHTMLの表示が完了したことを検知するとテキストフィールドにそのURLを表示するようにしています。また、テキストフィールドにユーザがURLの情報を直接入力し、入力後にエンターキーが押されるとそのイベントを検知してページが更新されるようにしています。

FlashからSQLiteにアクセスする

それではいよいよFlash上からSQLiteに対してアクセスしてみましょう。

Flash CS3 からデータベースへの接続を行う場合、まずはActionScript の Flash.data パッケージにある flash.data.SQLConnectionクラスを使用してローカルのデータベースファイルを開きます。そこでSQLConnection のインスタンスを作成して open()メソッドでローカルファイルの保存場所を指定し、接続が行えるかどうかイベントを検知します。正常に接続が行えた場合は次の処理、エラーが発生した場合はエラー処理を行います。

接続が無事に行えた場合、flash.data.SQLStatementクラスを使用して、クエリーやコマンドのといったSQLステートメントによる処理を実行させます。ここでまた処理がエラーになったか正常に行えたかどうかをイベントで検知し、正常に行えた場合はその実行結果をflash.data.SQLResultから取得します。

これらのことをふまえて、実際のコードは以下のようになります。まず、読み込むクラスとして以下を追加します。

import flash.data.SQLConnection;
import flash.data.SQLStatement;
import flash.data.SQLResult;
import flash.events.SQLEvent;
import flash.events.SQLErrorEvent;
import flash.filesystem.File;

されらに、これまで作成したコードの最後の行に以下のコードを追加します。

//データベースコネクションの作成
var dbCon:SQLConnection = new SQLConnection();
var SQLState:SQLStatement; 
var dbFile:File = File.applicationStorageDirectory.resolvePath("EdgeBrowser.db");
dbCon.addEventListener(SQLErrorEvent.ERROR, errorHandler);
dbCon.addEventListener(SQLEvent.OPEN, onSQLConnectSuccess);
dbCon.open(dbFile);

//データベースエラーハンドラ
function errorHandler(event:SQLErrorEvent):void {
    trace("Error code:", event.error.code);
    trace("Details:", event.error.message);
}

これによってデータベースの接続コネクションとSQLステートメントのインスタンスを作成し、アプリケーションが実行されると.open()メソッドでデータベースへの接続を行います。AIR は該当する場所にデータベースファイルが存在しない場合は新規にデータベースファイルを作成し、既に存在する場合はそのファイルが開かれます。データベースの接続が正常に行えた場合はonSQLConnectSuccessハンドラが呼び出されて次の処理に移り、接続に失敗した場合はerrorHandler ハンドラが呼び出されエラー内容の表示処理を行います。このtrace()によるメッセージ表示は「デバッグ」メニューにある「ムービーのデバッグ」を行った場合のみ表示されます。

次に、接続が正常に行えた際に呼び出される onSQLConnectSuccess ハンドラの処理内容を作成しましょう。ここでは、該当するデータベーステーブルが存在しない場合はそれを作成し、すでに存在するようであればそのテーブルからデータを取得するようにステートメントを設定します。具体的なコードは以下のようになります。

//接続してテーブルが存在しない場合は作成
function onSQLConnectSuccess(event:SQLEvent):void {
	SQLState= new SQLStatement();
	SQLState.sqlConnection = dbCon;	
	var tblCreateSql:String = 
    "CREATE TABLE IF NOT EXISTS EdgeBookmarks (" + 
    "    linkId INTEGER PRIMARY KEY AUTOINCREMENT, " + 
    "    urlStr TEXT, " + 
    "    pageTitle TEXT" + 
    ")";
	SQLState.text = tblCreateSql;
	
	SQLState.addEventListener(SQLEvent.RESULT, createResult);
	SQLState.addEventListener(SQLErrorEvent.ERROR, errorHandler);
	
	SQLState.execute();
}

function createResult(event:SQLEvent):void {
	getDBData();
}

//データベースからのデータ取得
function getDBData ():void {
	SQLState= new SQLStatement();
	SQLState.sqlConnection = dbCon;	
	var selectSql:String = "SELECT * FROM EdgeBookmarks";
	SQLState.text = selectSql;
	SQLState.addEventListener(SQLEvent.RESULT, selectResult);
	SQLState.addEventListener(SQLErrorEvent.ERROR, errorHandler);
	
	SQLState.execute();
}

今回はブラウザののブックマークのような機能にしようと考えて、自動的に追加されるプライマリキーの役割としてLinkID、ページのURLアドレス urlStr、ページのタイトル pageTitle、これらのフィールドを持つテーブルEdgeBookmarks を作成しました。正常にテーブルが作成されると、createResult ハンドラが呼び出され、そこでデータベースからのデータ取得処理が行われます。

最後に、取得したデータベースの値の表示処理を追加します。Flash CS3 にはデータベースからの値を表示するのに最適なコンポーネントとして「データグリッド」があります。「コンポーネント」パネルからステージ上に「データグリッド」を配置し、そのインスタンス名をつけます。ここではインスタンス名を「dg」としています。

データグリッドのプロパティ。インスタンス名を「dg」にする
ステージ上の「データグリッド」コンポーネントのプロパティ

取得したデータベースからの情報はSQLResult インスタンスから取り出して表示します。具体的なコードは以下です。

//データグリッドの表示設定
var dp:DataProvider= new DataProvider();
dg.columns = [ "linkId","pageTitle", "urlStr"];
dg.getColumnAt(0).sortOptions = Array.NUMERIC;
dg.getColumnAt(0).width = 30;

//取得した値をデータプロバイダに渡す処理
function selectResult(event:SQLEvent):void {	
	var result:SQLResult = SQLState.getResult();
	dp=new DataProvider(result.data);
	dg.dataProvider = dp;
}

//データグリッドの項目をクリックしたときのHTML表示処理
dg.addEventListener(Event.CHANGE, ItemSelect); 
function ItemSelect(e:Event):void {
	urlReq =  new URLRequest(e.target.selectedItem.urlStr);
	html.load(urlReq);
}

まず、データプロバイダのインスタンス dp を作成し、次にデータグリッドdg の表示設定を行います。この前の処理でselectResultハンドラが呼び出されると、データプロバイダとしてSQLResultのdata プロパティの配列データを割り当てて、データグリッドでその配列データを表示させます。

ここでひとまずプレビューを行い、実際にデータグリッドにテーブルの内容が表示されるかどうか確認しましょう。その前に、データベースの保存先として指定している applicationStorageDirectory を、desktopDirectoryに変更してデスクトップにデータベースを保存させるようにしてみましょう。これによってSQLite がどのような構造になっているか確認を行いやすくなると思います。

コードに問題がないようであればムービーのプレビューを行うとデスクトップにSQLite のデータベースファイル(ここではEdgeBrowser.db)が作成されるはずです。このファイルを SQLiteBrowser 等のアプリケーションで開きます。以下のようなテーブル構造ができていれば成功です。

SQLiteBrowser
SQLite Database Browser でデータ構造を確認

SQLiteをGUIで管理できるSQLite Database Browser などのアプリケーションを併用すれば、直接データの編集を行ったり別形式で書き出すなど、データベース利用の幅がさらに広がります。ご自身でアプリケーションを作成される場合はぜひ利用してみてください。なお、最終的なアプリケーション配布の際は、先ほど変更したdesktopDirectoryは元に戻すなどしてユーザーが誤って削除してしまわないようにしましょう。

それでは最後に、このテキストフィールドの右側に現在表示されているURLをブックマークのように登録するボタンを配置しましょう。配置が終わったらそのボタンにインスタンス名をつけます。ここでは「add_btn」としています。

ボタンのインスタンス名をadd_btnにする
配置したボタンのプロパティ

このボタンに対するスクリプトの内容は以下です。

//追加ボタンを押したときのデータベースへの追加処理
add_btn.addEventListener(MouseEvent.CLICK, addData);
function addData(event:MouseEvent):void {
	SQLState= new SQLStatement();
	SQLState.sqlConnection = dbCon;	

	var InsertSql:String = 
		"INSERT INTO EdgeBookmarks (urlStr, pageTitle) "+
		"VALUES (@urlString, @pageTitle)";
		
	SQLState.parameters["@urlString"] = html.location;
	SQLState.parameters["@pageTitle"] = html.window.document.title;
		
	SQLState.text = InsertSql;
	
	SQLState.addEventListener(SQLEvent.RESULT, InsertResult);
	SQLState.addEventListener(SQLErrorEvent.ERROR, errorHandler);
	
	SQLState.execute();
}

function InsertResult(event:SQLEvent):void {
	    trace("Inserted");
			getDBData();
}

ボタンが押されるとaddDataイベントハンドラが呼び出され、URL文字列とページタイトルをそれぞれのパラメータとして取得してデータベースへ追加します。ここでINSERTクエリーのパラメータの記述方法に注目してもらいたいのですが、通常、クエリーパラメータはシングルクォーテーションの間に変数の値を連結する形で記述しますが、ActionScriptではこのように先頭に@(アットマーク)、もしくは : (コロン)で始めて変数を記述することで内部的に変数処理して送信してくれます。もちろん、以下のように変数を連結して渡すことも可能ですが、コードの可視性を高めるためにも有効利用してみてください。

var InsertSql:String = 
		"INSERT INTO EdgeBookmarks (urlStr, pageTitle) "+
		"VALUES ('" + urlString + "', '" + pageTitle + "')";

ここまでで今回の記事は終わりにしたいと思います。今回もソースファイルとインストールプログラムを以下に掲載しておきます。このファイルを叩き台として、みなさんのプログラム作成のお役に立てれば幸いです。なお、ソースファイルの中に電子署名ファイルは含まれておりませんので、インストーラ作成の際はご自身で別途作成して行ってください。

 

今回はデータベースへのアクセスということで、多少敷居が高く感じたかもしれません。とくにFlashでフロントエンドのコンテンツを主に作られていた方にとっては、普段はサーバ側で稼働するデータベースについて、ここまでの操作をするということはなかなかないでしょう。しかし、AIRにSQLiteが搭載されたことで、たとえばオフラインでのWebブラウジングやローカルでデータ処理をするWebアプリケーションなど、デスクトップアプリケーションの可能性を大きく広げてくれる有益なファンクションなのです。

また、SQLiteを活用したアプリケーション環境は格段に増えてきています。GoogleGear、次期FirefoxなどがこれからSQLiteによるオフライン機能を実現してくる予定です。そうした技術を、あなたのAIRアプリケーションでも実装できるので、これを機会にぜひいろいろなアイデアをチャレンジしてみてください。