ひだまりソケットは壊れない

ソフトウェア開発に関する話を書きます。 最近は主に Android アプリ、Windows アプリ (UWP アプリ)、Java 関係です。

まじめなことを書くつもりでやっています。 適当なことは 「一角獣は夜に啼く」 に書いています。

Kyoto.js #3 で 『GUI アプリケーションにおける MVC』 という発表をしました

2012 年 12 月 13 日に開催された JavaScript の勉強会 Kyoto.js #3 で 『GUI アプリケーションにおける MVC』 という発表をしました。

内容

最近は GUI アプリケーションの設計についていろいろ考えていたので、GUI アプリケーション設計の典型である MVC について話しました。 MVC の基本的なことと、デモ用に作ってみたオセロ的なゲームについて。

とりあえず基本を振り返って、何か議論できればいいなー、という感じだったので内容的には特に面白いものは何もないのですが、何か気になることなどがあれば是非意見くださいませ。 実際発表後には id:yuku_t さんといろいろ話ができて面白かったです (ありがとうございました)。

JavaScript の勉強会ですがデモ用のコードは TypeScript で書いています。

MVC についてぐだぐだと

Model と View の関係ってわかりやすいし、どの単位でクラス分けしたらいいのかもわかりやすいのだけど、Controller をどういう風に理解すればいいのかが結構悩みどころだった。 役割としては 「ユーザー操作をトリガーにして何らかの処理を行うもの」 って理解でいいと思うんだけど、複数の入力経路 (マウスクリックとキーボード入力とか) で同じ処理をさせたい場合とか、同じ入力でも状況によって違う処理をさせたい場合とか、どういう風に実装するのがいいんだろうなー、とかとか。 まあ場合によりけりだと思うのだけど。

今回のオセロ的ゲームの例だと 「単に Model が 1 個あって、それに結び付けられる View が 2 個あって」 という感じで単純だから特に難しいところはないけど、もっと複雑なアプリケーションになってくるといろいろ考えることが増えてくるので、どこで何を管理するのか明確に意識しないとぐちゃぐちゃになっちゃうなー、と思ったりしてる。 常に必要なわけではない Model をどのタイミングで生成するのかとか、生成した Model を管理するのは誰なのかとか。 そういうの難しい。

さらにサーバーと通信するアプリケーションの場合、どこでサーバーと通信すべきなのかも悩みどころだしなー。 うーん。

Kyoto.js #2 で 『ECMAScript 5 時代のオブジェクト・プロトタイプ継承入門』 という発表を行った

2012 年 11 月 29 日に開催された Kyoto.js #2 で 『ECMAScript 5 時代のオブジェクト・プロトタイプ継承入門』 という発表を行った。

発表の動機

世の中にある JavaScript のプロトタイプ継承の解説には new 演算子コンストラクタが使われることが多い気がしていて、プロトタイプ継承そのものは単純なのに理解するのが難しくなっているように思っていた。 ECMAScript 5 の Object.create 関数を使って説明すればプロトタイプ継承が理解しやすくなって、さらにそれを理解したうえで new 演算子コンストラクタの挙動を見ればそっちはそっちでわかりやすくなるのではないか、ということでそういう方針で説明してみようというのが今回の発表の動機。

しかし、発表資料を作るうちになんだかんだで結局難しくなってしまった気がする。

内容

Kyoto.js #1 で 『TypeScript 言語処理系ことはじめ』 という発表をしました

2012 年 11 月 15 日に開催された Kyoto.js #1 で 『TypeScript 言語処理系ことはじめ』 という発表をしました。

発表内容

資料は SlideShare にアップロードしました。

概要

  • 前半は JavaScript に代わる言語を使用したいという動機の話、あるいは 「JavaScript 最高!!」 という話
  • 後半は TypeScript の言語処理系を (tsc コマンドからではなく) 直接 JavaScript で触る話

TypeScript の言語の基本的な話はしてないです

TypeScript の言語機能だとか構文の話は基本的にしてません。 まあ JavaScript の勉強会ですしね!

TypeScript の基本的なことは公式ページをご覧ください。

ECMAScript って何なの?

JavaScript の勉強会に来るような人はみんな知っているかもしれませんが、ECMAScript ってのは JavaScript の言語機能のコア部分を標準化して作られた言語です。 詳細は以下のページを見るとよいでしょう。

2012 年 11 月 27 日現在、ECMAScript の最新のバージョンは 5.1 で、最近のブラウザは基本的に ECMAScript 5.1 をサポートしていると思います。 ECMAScript 5.1 にはクラス定義の構文などはないのですが、現在策定作業が進んでいる ECMAScript の次のバージョン (ES.next とか ECMAScript 6 とか呼ばれてるもの) にはクラス定義の構文などが含まれる予定になっています。 草案は定期的に公開されていて下記ページで見ることができます。

TypeScript と ECMAScript

TypeScript の構文は ECMAScript 5 の構文のスーパーセットになっています。

TypeScript syntax is a superset of Ecmascript 5 (ES5) syntax.

TypeScript Language Specification 0.8 (PDF)

つまり、ECMAScript 5 の構文で書かれた JavaScript のコードは、全て TypeScript (0.8) の構文としても正しい、ということだと思います *1。 また、TypeScript のクラス定義の構文などは ECMAScript 6 の草案をベースにしているようです。

そういった点を考えると、すでに存在している JavaScript のプロジェクトを、少しずつ TypeScript に書き換えていく、というような移行が (他の JavaScript を置き換えるような言語と比べて) やりやすいと思います。

TypeScript 言語処理系を JavaScript から使用する

TypeScript のコンパイルの方法としても最も一般的 *2 なのは tsc コマンドを使用して、node 上で TypeScript 言語処理系を動かしてコンパイルさせることだと思います。 ただ、この方法は実際にやってみるとコンパイルごとに結構時間がかかってしまいます (私の環境だと小さな TypeScript ファイルの 1 回のコンパイルに 3, 4 秒程度かかりました)。 これは、コンパイルの処理そのものに時間がかかっているのではなくて、コンパイラの準備にかかるオーバーヘッドが大きいことが原因でしょう。

こういう問題を回避するために、コンパイラの準備を一度したらそのプロセスをずっと留めておいて毎回同じプロセスを使ってコンパイルさせる、というようなことをしたいわけですが、tsc コマンドを使っているだけではあまり細かな制御ができません *3。 そこで、TypeScript 言語処理系の実体である JavaScript を直接触ってコンパイルしたりしてみましょう、という話。

TypeScript 言語処理系の実体は、TypeScript プロジェクト の中の bin/typescript.js というファイルです *4。 これを読み込むと TypeScript.TypeScriptCompiler というコンストラクタが使えるようになるので、以下のような JavaScript を書いて TypeScript のソースコードをコンパイルできます。

// 出力用オブジェクトの定義
var outfile = {
	source: "",
	Write: function (s) {
		this.source += s;
	},
	WriteLine: function (s) {
		this.source += s + "\n";
	},
	Close: function () {}
}

// コンパイラ生成
var compiler = new TypeScript.TypeScriptCompiler(outfile);

// エラーの扱い
compiler.parser.errorRecovery = true;
compiler.setErrorCallback(function (start, len, message, block) {
	console.log("error : " + message);
});

// TypeScript のソースコード追加 (これがコンパイルされる)
var src1 = "class Test { aaa: string; };\n var ttt = 100;";
compiler.addUnit(src1, 'test1.ts');
var src2 = "///<reference path='test1.ts' />\nvar test = new Test(); test.";
compiler.addUnit(src2, 'test2.ts');

// 型チェック
compiler.typeCheck();

// 実行
// 以下は TypeScript 0.8.0 用に第 1 引数に bool 値を渡していますが
// 0.8.1 では以下の false は消す必要があります
compiler.emit(false, function createFile(fileName) {
	console.log("create file : " + fileName);
	return outfile;
});

console.log('compiled: ' + outfile.source);
console.dir(compiler); // TypeScriptCompiler オブジェクトの中を見ると抽象構文木が見える

コード補完させたい

VimEmacs で TypeScript を書くことを考えると、記述中の TypeScript のソースコードの指定した位置における識別子等のコード補完をさせるための機能が欲しいところです。 そのための機能は TypeScript のプロジェクトの中に含まれています。

詳細は以前記事を書いたのでそちらを参照ください。

そういえば何やら Microsoft の人が TypeScript のサービス用プロジェクトみたいなのを公開してましたが、あれはなんなんでしょうね。 「TypeScript Services Server」 という名前からすると、補完等の言語サービスを提供してくれるのかもしれないですね。 (ちゃんと見てないのでわかんない。)

Node 以外の環境で動かしたい

TypeScript 言語処理系は JavaScript で実装されていますが、現在 (version 0.8.1) のところサポートされているのは Windows の JScript 処理系 (?) と Node だけです。

さまざまな JavaScript 言語処理系で TypeScript コンパイラを動かすための障害として、ファイルの読み書きや標準入出力等の IO 機能が JavaScript 処理系間で統一されていないという問題があります。 TypeScript 言語処理系では、IO というオブジェクトの中に JavaScript 言語処理系固有の IO の機能を隠ぺいすることで、実装間の差異を吸収しています。 そのため、動かしたい JavaScript 処理系に対応した IO の機能を IO オブジェクトの中に記述すれば、その JavaScript 処理系で TypeScript 処理系を動かすことができる可能性があります。

詳細は以前書いた記事をご覧ください。

おわり

JavaScript 最高!!

*1:ただし、構文的には正しくてもコンパイルできるかどうかは別問題。 例えば型チェックが通らなくてコンパイルできない可能性もある。

*2:VisualStudio 上で使う場合を除く

*3:tsc コマンドには watch オプションというものがあって、ファイルの変更を検出して自動的にコンパイルし直したりしてくれるのですが、いまいち使いにくい。

*4:TypeScript 言語処理系自体は TypeScript で書かれていて、それをコンパイルしたものがこの JavaScript ファイルです。

Kyoto.pm Tech Talks 02 で WebSocket のことを話しました

2012 年 8 月 18 日に開催された Kyoto.pm Tech Talks 02 で WebSocket のことを LT してきました。

Plack::Middleware::WebSocket

Plack で WebSocket プロトコルを扱うための Middleware を motemen さんが 2 年ほど前に書かれていた のですが、それから WebSocket プロトコルの仕様も色々変わっていてそのままだと使えなかったので、4 月ごろに RFC 6455 に適合するように書き換えました。

今回の発表では、これを使ったデモも行いました。 急いで作ったのであまり綺麗なコードじゃないですが、下記リポジトリ (20120818-Kyoto.pm-2/master ブランチ) に置いてありますので、興味があれば実行してみてください。

下記コマンドで clone できます。

$ git clone -b 20120818-Kyoto.pm-2/master git://github.com/nobuoka/presentation.git

今は Plack::Middleware::WebSocket の中に、WebSocket プロトコルのパース処理なども書いているのですが、発表後に 「Protocol::WebSocket って CPAN モジュールがあるよ」 って motemen さんに教えてもらって、「確かに Plack::Middleware::WebSocket にパースとかの細かい処理を書くのは微妙だしそれを使って書き直した方が良いかなー」 と思ったりしました。

"鹿駆動勉強会" に参加しました

鹿駆動勉強会」 という勉強会に参加してきました。 鹿駆動ってなんやねん、という感じですが、奈良公園の鹿によって駆動される勉強会なのです。

会場へ

f:id:nobuoka:20120429130142j:plain
鹿かわいいなぁと思いながら会場へ。

f:id:nobuoka:20120429143108j:plain
会場はなんと 新公会堂の能楽ホール です。

学んだこと

今回の勉強会は Java 関係の LT が多くて、Java 周辺の最近の話を聞くことができたのが良かったです。 Java 以外の話も面白いものが多くて良い刺激を受けました。 気になった内容などを簡単にまとめておきます。

発表内容を軽く調べながらまとめたものなので間違いがあるかもしれません。 あと発表者名が間違っていたり足りなかったりするかもしれません。 ご指摘頂けると助かります。

JavaFX - 我々が愛した Swing は死んだ!! なぜだ!!

いくつかの講演で Swing が殺されました。 Swing の代わりに JavaFX がある、と。

JavaFX といえば JavaFX Script で書くもので、なかなか普及しなかったという印象があります (少なくとも私の中では) が、それは Java FX 1 の時代の話。 2010 年の JavaOne において、JavaFX は、Java 言語だけでなく JavaScriptScala、Groovy のような JVM (Java 仮想マシン) 上で動く言語からも利用できる RIA (Rich Internet Application) 用の Java API として生まれ変わる事になり、2011 年には JavaFX 2.0 がリリースされました (参考 : 生まれ変わった JavaFX 2.0)。 JavaFX 2 には以下のような特徴があります。

  • JavaFX Script は廃止され、Java から API を叩く形になっている
    • Groovy や Scala などの JVM 上で動く言語からも使える
  • ロジックは Java で、UI 構造設計は FXML で、UI 表示デザインは CSS
  • WebKit ベースの組み込み web ブラウザが導入された
  • メディア再生エンジン
  • などなど

とりあえず FXML で UI 構造を書けるようになったのは良いですね。 現時点の最新版である Java FX 2.2 だと Windows と Mac OS のみのサポートで Linux は Developer Preview っていう段階みたいですが、これから使えるようになっていきそうですので、今後 JavaGUI アプリケーションを書くときには JavaFX を使っていくと良さそうですね。 JDK 8 では JavaFX が組み込まれる予定のようですし。

今のところ JavaFX の開発をするなら NetBeans + Scene Builder という組み合わせがオススメとの事。

ちなみに GUI 描画用のスレッド周りは Swing と似た感じになっていて、描画やイベントを処理するための JavaFX Application Thread が 1 つあって、他の処理をするスレッドとやりとりしながら処理を進める、という感じの模様。 あと、JavaFX には組み込み web ブラウザがあるから、それを使えば JavaScript のテストもできるはずだよね、という話も。

ここら辺の話は主に以下の方々によるものです。

JVM の invokedynamic の話

JDK 7 の新機能として JVM における動的型付け言語のサポートがあります。 このサポートの重要な点は、JVM に invokedynamic ニーモニックが追加されたことです。

これまで、JVM 上でのメソッド呼び出しは静的型付け言語を想定した命令しか存在せず、動的型付け言語のメソッド呼び出しは最適化された状態とはいえない形で実装されていました。 動的型付け言語により適した形でメソッド呼び出しを行えるように追加された命令が invokedynamic です。 詳細は以下。

たんご238さん (@tan_go238) の発表。

奈良時代から伝わる技と術

こしばさん (id:bash0C7 / @bash0C7) の発表。 上記発言が面白かったので大事なところを聞き漏らしてしまった気がするけど、確か核心を見定めることが重要、って話だった気がします。

JavaScript で WebRTC

WebRTC なる規格で JavaScript からも WebCam が使える、という話。 デモでは、WebCam でとった画像をブラウザ上に表示して、さらに顔認識により顔の部分に能面画像をかぶらせる、というものを見せてもらいました。 WebRTC なんてのもあるのですね。

Kazuyuki Honda さん (id:scalar / @hakobera) の発表。

JavaScript のテンプレートエンジン
  • jQuery Templates があるけど beta 版のまま開発終了ぽい
  • 後継っぽいのは JsRender

おださん (id:odashinsuke / @shinsukeoda) の発表。

などなど

ほかにもいろいろ面白い話がありましたが多いので特に気になったものを挙げてみました。 後で勉強できたらいいな...。 勉強会中の TL は以下。

ありがとうございました

企画のはくらいさんはじめとする運営の皆様、参加者の皆様、ありがとうございました。