JavaScriptからバイナリファイルが読めると知った( Handling binary data - XMLHttpRequestの利用 - MDC )ので、色々試しているところです。
flash(flex)のURLLoaderとByteArrayに似せたクラスがあればflashとの相互移植がやりやすくなりそうだなと思い、作ってみたり。
いくつか直面した問題を列挙。
- Google Chromeでローカル・同一ディレクトリ下のファイルにアクセスできない。
どうもセキュリティ上の都合のようです。コマンドラインオプション –allow-file-access-from-files で回避できました。(参考: Maginot-line: Error: NETWORK_ERR: XMLHttpRequest Exception 101)
- IE8のXMLHttpRequestでローカル・同一ディレクトリ下のファイルにアクセスできない。
ActiveXObject("Msxml2.XMLHTTP")ならアクセスできました。
- IEでバイナリが取得できない。
Msxml2.XMLHTTPにはoverrideMimeTypeは無く、responseTextでは正しくバイナリが取得できません。0のところで列が切れてしまうみたいです。responseBodyを使うと取得できるのですが、これはJavaScriptからはアクセスできず、VBScriptを経由してアクセスするものらしいです。(参考: JavaScriptによるLZHの解凍サンプル)
私は以下のようなコードでresponseBodyの中身をJavaScript文字列へ変換しました。かなり遅いです。
execScript("Function vbBinaryToText(bin)n"+ " Dim in"+ " Dim sn"+ " s=""n"+ " For i=1 to LenB(bin)n"+ " s = s & ChrW(AscB(MidB(bin, i, 1)))n"+ " Nextn"+ " vbBinaryToText = sn"+ "End Functionn"+ "n", "VBScript"); str = vbBinaryToText(xhr.responseBody);
- 文字列の文字エンコーディング変換が難しい。
ByteArray.readMultiByte()のようなことをするのは難しそうです。Escape Codec Library: ecl.jsでやっているようなことをすれば実装できるのだとは思いますが、とりあえずUTF-8さえデコードできれば十分なので、readUTFBytes相当だけ実装しました。手元にあったC++の変換コードを移植。JavaScriptの内部エンコーディングはUTF-16っぽいのでサロゲートペアは分割。
- 浮動小数点数バイナリの読み書きが難しい。
NaN(JavaScriptにqNaNとsNaNの区別ってあるの?)、±無限大、±0、非正規数、正規化数をそれぞれ自分で分解・組みたてするしかないんでしょうね。powを使うのかな。