前回のWebアプリ版に続いて、今回はデスクトップアプリ版のメッセンジャーアプリを作ってみましょう。
前回のWebアプリ版では、プロデル簡易WebサーバへWebブラウザを使ってメッセージをやりとりしました。今回は、Webブラウザの代わりにデスクトップアプリでメッセージをやりとりしてみようと思います。
19/5/23加筆: 記事投稿当時から1.6.957までで開発版よりも古いバージョンの簡易Webサーバが配布されており、掲載しているプログラムがそのままでは動作しない状態だったことがわかりました。問題は1.6.958で修正済みです。失礼致しました。
概要
全体図
メッセンジャーデスクトップアプリでは、前回作成したWebサーバにあるapi.rdrに対して、クライアントPCからメッセージを受信したり送信したりするための命令を送信します。
今回の題材では、1台のPCにWebサーバを起動しておき、複数のクライアントPCからそのPCのWebサーバにアクセスできるような形にしたいと思います。このようにすれば、私の名前と相手の名前を変えるだけで、メールやDMのように複数人とメッセージをやりとりできます。
※なお今回も複数のPCを用意せずに、1台のPCでサーバとクライアントを実行してテストしてみます。複数PCでテストする場合は、サーバのIPアドレスを調べておき、クライアントPCのプログラム中の「localhost」の部分をそのIPアドレスに置き換えて実行して下さい。
ポイント
今回作る必要がある主な機能は、次のとおりです。
- メッセンジャーAPIを使ってメッセージを送信する
- メッセンジャーAPIを使って受信した新着メッセージを表示する
- キャンバスでチャット画面を作る
APIでメッセージを送信する
まずは、クライアントPCのプロデルから、サーバにあるメッセンジャーAPIを呼び出してメッセージを送信する簡単なプログラムを作ってみます。
メッセンジャーAPIを呼び出すには、「HTTPで送信する」手順を使います。この手順では、WebサーバのPOSTメソッドを呼び出します。パラメータには、フィールド値として、送信する情報を辞書で指定します。
メッセンジャーAPIには、「mode」「sendto」「message」の3つの引数があるので、これらをパラメータとして指定します。
送るテスト.rdr
【私の名前】は、「秋山」
【相手の名前】は、「山中」
パラメータ={
「mode」=「write」,
「sendto」=相手の名前,
「message」=「こんにちは」
}
内容は、「http://localhost/message/api.rdr?myname=[私の名前]」へパラメータをHTTPで送信する
では、実際に実行してみましょう。メッセージを送信するには、Webサーバが起動している必要があります。プロデル簡易Webサーバを起動状態にして前回のapi.rdrが利用できる状態にしてください。
※なお前回のapi.rdrに誤りがありましたので1/5以前に試している方はプログラムの「バインド値」の部分を修正して下さい(現時点では修正済みです)
エラーが表示されなければ無事メッセージが送信されました。Webアプリ版で送信できているか確認してみましょう。
APIでメッセージを受信する
次にメッセージを受信してみましょう。受信の時は「HTTPで取得する」手順を使います。受信の場合には、「myname」と「update」の2つのクエリ引数を指定します。これは、「私の名前で指定した日時以降に届いたメッセージを取得する」ことを意味しています。
受信テスト.rdr
【私の名前】は、「秋山」
【相手の名前】は、「山中」
最終日時=無
引数は、「myname=[私の名前]&update=[最終日時を「yyyy-MM-dd HH:mm:ss」に整えたもの]」
結果は、「http://localhost/message/api.rdr?[引数]」をHTTPで取得する
JSON形式として結果を読み取って投稿一覧とする
投稿一覧を投稿にそれぞれ繰り返す
投稿を報告する
繰り返し終わり
メッセージの取得は一度きりですので、新しいメッセージが届いても再度実行しないと表示されません。新しいメッセージ届いたら、そのメッセージを表示するようなプログラムが必要です。
新着メッセージを受信するには、サーバへ新着メッセージがあるかどうかを、定期的に問い合わせる必要があります。定期的な処理には「タイマー」種類を使います。「update」クエリ引数に最後の受信した日時を指定すると、その日時以降に受信したメッセージがある場合のみ、そのメッセージが得られます。
受信テスト2.rdr
【私の名前】は、「秋山」
【相手の名前】は、「山中」
タイマー1というタイマーを作る
タイマー1の間隔を1000に変える
タイマー1を開始する
最終日時=無
待機する
タイマー1が時間になった時の手順
引数は、「myname=[私の名前]&update=[最終日時を「yyyy-MM-dd HH:mm:ss」に整えたもの]」
結果は、「http://localhost/message/api.rdr?[引数]」へHTTPで取得する
JSON形式として結果を読み取って投稿一覧とする
もし投稿一覧の個数が0より大きいなら
投稿一覧を投稿にそれぞれ繰り返す
投稿を報告する
繰り返し終わり
「-----」を報告する
最終日時は、今
もし終わり
終わり
では、メッセージ受信もテストします。このプログラムを実行した状態で、Webアプリ版にてメッセージを送信してみましょう。送信した直後に「調査ウィンドウ」にメッセージが表示されれば成功です。
アプリUIを作る
メッセンジャーアプリで重要なメッセージの送受信は、完成しました。次にアプリの画面を作っていきます。メッセンジャーデスクトップアプリは、メッセージを古い順に並べて、自分と相手のアイコンに吹き出しをつけて表示します。
吹き出しを作る
まず上の画像のようなメッセージ枠を作りましょう。
吹き出しは、キャンバス部品を使って作ります。吹き出しの図形は、連続線を使って一つ一つ座標を指定していきます。また、名前やメッセージなど内容が変わる部分は、キャンバス文字を使います。またアバター部分も今回は円弧図形で作ります。図形を使うことで線や色を簡単に変えることができます。円弧図形の変わりに画像図形を使ってアイコンを表示させることもできます。
吹き出し.rdr
窓というウィンドウを作る
そのタイトルは、「吹き出し」
窓へキャンバス1というキャンバスを作る
そのドッキング方向を全体に変える
窓を表示する
キャンバス1へ円弧を描く
その位置と大きさは、{5,25,40,40}
その線色を緑に変える
その背景色を水色に変える
その開始角度を180に変える
その扇角度を180に変える
その太さを3に変える
キャンバス1へ円を描く
その位置と大きさは、{10,5,30,30}
その線色を緑に変える
その背景色を水色に変える
その太さを3に変える
キャンバス1へ連続線を描いて吹き出しとする
その線色を緑に変える
その太さを3に変える
その背景色を白色に変える
吹き出しの点は、{{50,30},{60,20},{60,3},{180,3},{180,80},{60,80},{60,40},{50,29}}
キャンバス1へ「プロデル」という文字を描く
その位置は、{65,10}
そのフォントを「メイリオ」に変える
その文字色を緑色に変える
その文字サイズを9に変える
キャンバス1へ「こんにちは」という文字を描く
その位置は、{65,30}
そのフォントを「メイリオ」に変える
その文字サイズを12に変える
キャンバス1を更新する
待機する
カスタムウィンドウ部品
チャット画面では、メッセージごとにキャンバス部品を作り図形を表示させる必要があります。何度も利用する部品は、ボタンやテキストのように「作る」文で作ることができると便利です。標準で用意された部品のように、自分で部品を定義するには、「カスタムウィンドウ部品」種類を使います。
カスタムウィンドウ部品は、プロデルデザイナでアウトラインツリーから追加できます。コンテキストメニューから「項目の追加」←「カスタムウィンドウ部品」を選択します。
名前として「メッセージ枠」と入力すると、タイトルバーやフレームがない「ウィンドウの設計」画面が表示されます。この設計画面にキャンバス部品を貼り付けておきます。
プログラムに戻ると「カスタムウィンドウ部品を継承」した「メッセージ枠」種類の定義プログラムが出力されます。
続けて「はじめの手順」手順の末尾に先ほどの吹き出しを描画するプログラムを貼り付けます。また「本文」「名前」設定項目をそれぞれ定義して部品を作った後に名前や本文を変更しやすいようにします。
メッセージ枠.rdr
メッセージ枠とは
カスタムウィンドウ部品を継承する
はじめの手順
初期化する
ーー貼り付けた部品に対する操作をここに書きます
キャンバス1に子キャンバスを作ってアバターとする
その位置と大きさは、{0,0,50,50}
その線色を白に変える
アバターへ円弧を描く
その位置と大きさは、{5,25,40,40}
その線色を緑に変える
その背景色を水色に変える
その開始角度を180に変える
その扇角度を180に変える
その太さを3に変える
アバターへ円を描く
その位置と大きさは、{10,5,30,30}
その線色を緑に変える
その背景色を水色に変える
その太さを3に変える
キャンバス1へ連続線を描いて吹き出しとする
その線色を緑に変える
その太さを3に変える
その背景色を白色に変える
キャンバス1へ文字を描いて名前ラベルとする
その位置は、{70,10}
そのフォントを「メイリオ」に変える
その文字色を緑色に変える
その文字サイズを9に変える
キャンバス1へ文字を描いて本文ラベルとする
その位置は、{70,30}
そのフォントを「メイリオ」に変える
その文字サイズを12に変える
その大きさ調整を×に変える
キャンバス1を更新する
終わり
初期化する手順
ーー自動生成された手順です。ここにプログラムを書き加えても消える場合があります
この位置と大きさを{15,15,449,100}に変える
この内容を「メッセージ枠」に変える
この実質大きさを{449,100}に変える
キャンバス1というキャンバスを作る
その位置と大きさを{0,0,449,100}に変える
その移動順を3に変える
その実質大きさを{449,100}に変える
そのドッキング方向を「全体」に変える
終わり
本文という属性
取得する手順
本文ラベルの内容を返す
終わり
設定する手順
本文ラベルの内容は、設定値
終わり
終わり
名前という属性
取得する手順
名前ラベルの内容を返す
終わり
設定する手順
名前ラベルの内容は、設定値
終わり
終わり
+方向は、「相手」
自分方向という属性
設定する手順
もし設定値が○なら
方向は、「自分」
そうでなければ
方向は、「相手」
もし終わり
キャンバス1の大きさが変わった
終わり
終わり
キャンバス1の大きさが変わった時の手順
もし本文ラベルが無なら返す
本文ラベルの大きさは、{幅-60,高さ-2}
もし方向が「自分」なら
アバターの横は、幅-53
名前ラベルの横は、10
本文ラベルの横は、10
吹き出しの点を{{3,3},{幅-63,3},{幅-63,20},{幅-53,30},{幅-63,40},{幅-63,高さ-2},{3,高さ-3},{3,3}}に変える
そうでなければ
アバターの横は、0
名前ラベルの横は、70
本文ラベルの横は、70
吹き出しの点を{{50,30},{60,20},{60,3},{幅-3,3},{幅-3,高さ-2},{60,高さ-2},{60,40},{50,29}}に変える
もし終わり
終わり
終わり
「メッセージ枠」の配置
「メッセージ枠」部品を実際にメイン画面に表示させてみます。このとき、
「メッセージ枠」を「自動配置パネル」部品に貼り付けてみます。
自動配置パネルは、その内部にある部品を左上から順番に自動的に整列して配置する部品です。「自動配置パネル」部品では、その内部の部品をHTMLやエクスプローラのアイコンのようにフロートのレイアウトで自動的に配置してくれます。
つまり「メッセージ枠」を「自動配置パネル」に作ることで、チャットのようにメッセージを受信する度に順番にメッセージ枠が増えて表示されるレイアウトを実現します。
自動配置パネルに部品が収まらなくなった時は、スクロールバーが表示されます。通常は自動的にスクロールされませんが、最後に追加した部品が常に表示されるように、スクロール位置を変えるプログラムを加えます。
メッセンジャーアプリ.rdr (冒頭)
メイン画面を表示する
待機する
メイン画面とは
ウィンドウを継承する
はじめの手順
初期化する
ーー貼り付けた部品に対する操作をここに書きます
終わり
初期化する手順
ーー自動生成された手順です。ここにプログラムを書き加えても消える場合があります
この設計スケール比率を{144,144}に変える
この実質大きさを{712,473}に変える
この内容を「チャット画面」に変える
初期化開始する
受信ボタンというボタンを作る
その位置と大きさを{12,12,122,37}に変える
その内容を「受信テスト」に変える
その移動順を4に変える
その実質大きさを{122,37}に変える
送信ボタンというボタンを作る
その位置と大きさを{595,415,105,46}に変える
その内容を「送信」に変える
その移動順を5に変える
その実質大きさを{105,46}に変える
その位置固定方向を「右+下」に変える
送信テキストというテキストを作る
その位置と大きさを{12,426,577,25}に変える
その移動順を3に変える
その実質大きさを{573,21}に変える
その位置固定方向を「右+左+下」に変える
自動配置パネル1という自動配置パネルを作る
その位置と大きさを{12,55,688,354}に変える
そのスクロールバー表示を○に変える
その移動順を2に変える
その実質大きさを{688,354}に変える
その背景色を「白」に変える
その位置固定方向を「右+左+下+上」に変える
初期化終了する
終わり
送信ボタンがクリックされた時の手順
もし送信テキストの内容が「」なら返す
自動配置パネル1にメッセージラベルというメッセージ枠を作る
メッセージラベルの大きさは、{400,120}
メッセージラベルの自分方向は、○
メッセージラベルの名前は、「のぞみ [今]」
メッセージラベルの本文は、送信テキストの内容
自動配置パネル1のスクロール位置を{0,自動配置パネル1のスクロール領域の高さ}に変える
送信テキストの内容は、「」
終わり
受信ボタンがクリックされた時の手順
自動配置パネル1にメッセージラベルというメッセージ枠を作る
メッセージラベルの名前は、「みぞれ [今]」
メッセージラベルの本文は、「こんにちは」
メッセージラベルの大きさは、{400,120}
自動配置パネル1のスクロール位置を{0,自動配置パネル1のスクロール領域の高さ}に変える
終わり
終わり
// 「メッセージ枠とは」の部分を貼り付ける
アプリ画面の設計
「ウィンドウの設計」画面で次のような部品を貼り付けていきます。
「プログラムの編集」画面に戻ると次のようなプログラムが作られます。これに加えて、アプリ起動時に「私の名前」を入力できるようにプログラムを加えておきます。
メッセンジャーアプリ.rdr (冒頭)
【私の名前】は、入力画面で「自分の名前を入力してください」を入力させる
メイン画面を表示する
待機する
メイン画面とは
ウィンドウを継承する
-相手の名前
はじめの手順
初期化する
ーー貼り付けた部品に対する操作をここに書きます
終わり
初期化する手順
ーー自動生成された手順です。ここにプログラムを書き加えても消える場合があります
この設計スケール比率を{144,144}に変える
この実質大きさを{712,473}に変える
この内容を「プロデルメッセンジャーアプリ」に変える
初期化開始する
ラベル1というラベルを作る
その位置と大きさを{12,15,100,23}に変える
その内容を「相手の名前」に変える
その移動順を8に変える
受信ボタンというボタンを作る
その位置と大きさを{322,12,75,25}に変える
その内容を「受信」に変える
その移動順を7に変える
その実質大きさを{75,25}に変える
名前テキストというテキストを作る
その位置と大きさを{118,12,198,25}に変える
その移動順を4に変える
その実質大きさを{194,21}に変える
送信ボタンというボタンを作る
その位置と大きさを{625,436,75,25}に変える
その内容を「送信」に変える
その移動順を6に変える
その実質大きさを{75,25}に変える
送信テキストというテキストを作る
その位置と大きさを{12,436,607,25}に変える
その移動順を3に変える
その実質大きさを{603,21}に変える
その位置固定方向を「右+左+下」に変える
自動配置パネル1という自動配置パネルを作る
その位置と大きさを{12,50,688,380}に変える
そのスクロールバー表示を○に変える
その移動順を2に変える
その実質大きさを{688,380}に変える
その背景色を「白」に変える
その位置固定方向を「右+左+下+上」に変える
初期化終了する
終わり
終わり
受信部分
「メイン画面」種類の定義に次のような3つの手順と2つの変数を定義していきます。
受信は、先ほどの「メッセージの受信」で作ったようにタイマーを使います。タイマーは、はじめの手順で作っておきます。またメッセージ枠を追加する手順として「【投稿】を追加する手順」を定義しておきます。
メッセンジャーアプリ.rdr (「メイン画面」種類の内容)
-相手の名前
はじめの手順
初期化する
ーー貼り付けた部品に対する操作をここに書きます
タイマー1というタイマーを作る
タイマー1の間隔を1000に変える
タイマー1を開始する
終わり
受信ボタンがクリックされた時の手順
最終日時=無
自動配置パネル1をクリアする
相手の名前は、名前テキストの内容
終わり
-最終日時=無
タイマー1が時間になった時の手順
もし相手の名前が空なら返す
引数は、「myname=[私の名前]&update=[最終日時を「yyyy-MM-dd HH:mm:ss」に整えたもの]」
結果は、「http://localhost/api.rdr?[引数]」をHTTPで取得する
JSON形式として結果を読み取って投稿一覧とする
もし投稿一覧の個数が0より大きいなら
投稿一覧を投稿にそれぞれ繰り返す
もし投稿の「名前」が相手の名前または投稿の「相手」が相手の名前なら、投稿を追加する
繰り返し終わり
最終日時は、今
もし終わり
終わり
【投稿】を追加する手順
自動配置パネル1にメッセージラベルというメッセージ枠を作る
メッセージラベルの名前は、「[投稿の「名前」] [投稿の「時刻」]」
メッセージラベルの本文は、投稿の「本文」
メッセージラベルの大きさは、{400,120}
もし投稿の「名前」が私の名前ならメッセージラベルの自分方向は、○
自動配置パネル1のスクロール位置を{0,自動配置パネル1のスクロール領域の高さ}に変える
終わり
送信部分
送信部分も、先ほどの送信プログラムをほぼそのまま「メイン画面」種類の『送信ボタンがクリックされた時の手順』の中で、定義しておきます。
メッセンジャーアプリ.rdr (「メイン画面」種類の内容の続き)
送信ボタンがクリックされた時の手順
もし送信テキストの内容が空なら「メッセージを入力してください」を表示する。返す
もし名前テキストの内容が空なら「相手の名前を入力してください」を表示する。返す
相手の名前は、名前テキストの内容
パラメータは、辞書を作ったもの
パラメータ={
「mode」=「write」,
「sendto」=相手の名前,
「message」=送信テキストの内容
}
結果は、「http://localhost/api.rdr?myname=[私の名前]」へパラメータをHTTPで送信する
送信テキストをクリアする
終わり
アプリ完成!
メッセンジャーアプリが完成しました!プログラムを実行してみましょう。
まずは自分の名前を入力して、メイン画面で「名前テキスト」に相手の名前を入力して[受信]ボタンをクリックします。
そうすると、自分と指定した相手との会話が表示されます。「送信テキスト」にメッセージを入力して[送信]ボタンをクリックすると、相手にメッセージが送信されます。
相手の名前でもアプリを別に起動して、メッセージが届いているかテストしてみましょう。
デスクトップアプリのメリット
一般に、WebアプリはWebブラウザを使って操作します。一方デスクトップアプリでは、Webブラウザを使わずに独立したアプリで操作します。
メッセンジャーアプリのようなアプリでは、Webブラウザだけでも十分な機能を提供できますが、ネットに繋がっていないと何もできません。一方デスクトップアプリは、必要なデータ(すでに受信したメッセージなど)が保存されていれば、ネットに接続されていなくてもメッセージが確認できます。この点はデスクトップアプリの利点です。
また、デスクトップアプリでは、PCに含まれる画像や動画ファイルを大量に扱いたい時に、ネットの通信量を気にせずにアクセスできるのも利点です。さらに以前ブログで紹介したFeliCaを利用した機能やOfficeとの連携などデスクトップアプリでしかできない豊富な機能と組み合わせられることもメリットです。
まとめ
前回と今回の2回に分けて、メッセンジャーアプリを作ってみました。
前回作成したWebAPIをデスクトップアプリから呼び出して、メッセージ送信したり受信したりしました。「HTTP」種類を使うことでWebアプリと連携させることができます。
また、デスクトップ版では、最近のチャット画面のようなUIを作ってみました。カスタムウィンドウ部品を使うことで、再利用可能な部品を自分で定義でき、プロデルでより凝ったアプリを作ることができます。
メッセンジャーアプリは、いろいろな用途に応用できますので、ぜひプロデルで便利なアプリを作ってみて下さい。