m2

CharsetEncoder

文字列とバイト配列を相互に変換する CharsetEncoder という JavaScript ライブラリを書きました。
GitHub - miya2000/CharsetEncoder: JavaScript charset encode/decode library.

お試し用のスクリプト

(function(){

var later = 0;
if (!window.__testscriptloaded__) {
  var scripts = [
    'http://github.com/miya2000/CharsetEncoder/raw/master/charset_encoder.js',
    'http://github.com/miya2000/CharsetEncoder/raw/master/fileio/charset_encoder_fileio.js',
    'http://github.com/miya2000/CharsetEncoder/raw/master/liveconnect/charset_encoder_liveconnect.js',
    'http://github.com/miya2000/CharsetEncoder/raw/master/applet/charset_encoder_applet.js'
  ];
  for (var i = 0; i < scripts.length; i++) {
    var script = document.createElement('script');
    script.type = 'text/javascript';
    script.src = scripts[i];
    document.body.appendChild(script);
  }
  window.__testscriptloaded__ = true;
  later = 3000;
}

setTimeout(function() {

var enc = 'Shift_JIS';
var str = '日本語00';

try {
  var b = CharsetEncoder.create(enc).encode(str);
  alert(b);
  var s = CharsetEncoder.create(enc).decode(b);
  alert(s);
}
catch(e) { alert(e) }

}, later);

})()

bookmarklet:

何に使うの?

サーバーサイド JavaScript で有効に使えるのではないかと思います。

実装方式

「世に数多くある文字セットすべてを実装」というわけではなく、UTF-8/UTF-16(LE) 以外は JavaOpera Unite の力を借りています。
また、既存の CharsetEncoder に加えて別の実装を追加できる構造になっています。

プログラム構造

(http://github.com/miya2000/CharsetEncoder/blob/master/charset_encoder.js に詳しく書いています。)

CharsetEncoder のインスタンスは以下のメソッドを実装します。

{Array} encode({String} str, {Array} buffer)
str をバイト配列にして返します。buffer が指定された場合は結果を buffer に追加します。
{String} decode({Array} bytes)
bytes を String 型に変換します。

CharsetEncoder のインスタンスはファクトリオブジェクトから生成できるようにします。ファクトリオブジェクトは以下のメソッドを実装します。

{CharsetEncoder} create({String} charset)
指定された文字セット用の CharsetEncoder のインスタンスを返します。
{Boolean} available({String} charset)
指定された文字セットが使用できるかどうかを返します。

CharsetEncoder の以下のメソッドを使用して、前述のファクトリオブジェクトの登録/CharsetEncoder インスタンスの生成を行います。

{void} CharsetEncoder.registerFactory({String} name, {Object} factory, {Number} order, {Boolean} asDefault)
ファクトリオブジェクトを CharsetEncoder に登録します。ファクトリオブジェクトは order の昇順で並べられ、CharsetEncoder のインスタンス生成は最初に見つかったファクトリが使用されます。
{void} CharsetEncoder.unregisterFactory({String} name)
ファクトリオブジェクトを CharsetEncoder から登録解除します。
{CharsetEncoder} CharsetEncoder.create({String} charset)
指定された文字セット用の CharsetEncoder のインスタンスを生成して返します。
{Object} CharsetEncoder.getFactory({String} name)
指定された名前のファクトリオブジェクトを返します。


この構造により、CharsetEncoder の各実装を意識することなく、以下のように使用することができます。

function getBytes(str, charset) {
  return CharsetEncoder.create(charset).encode(str);
}
function toString(bytes, charset) {
  return CharsetEncoder.create(charset).decode(bytes);
}

ファイル構成

構成は以下のようになっています。

スクリプト 説明
charset_encoder.js 本体。必須。(UTF-8/UTF-16 のみ同梱)
charset_encoder_fileio.js Opera Unite の File I/O API を利用した encoder/decoder. 現状では Opera Unite 環境でないと使用できません。
charset_encoder_liveconnect.js LiveConnect を利用した encoder/decoder. Live Connect が使用できる環境でないと使用できません。
charset_encoder_applet.js JavaApplet を利用した encoder/decoder. (要 a.jar) Java Plug-in が無いと使用できません。

UTF-8/UTF-16 のみを使用する場合は charset_encoder.js だけ必要で、他のスクリプトは必要ありません。
すべてのスクリプトを読みこんだとしても、File I/O や Java Plugin-in が利用できない場合は encoder/decoder も使用しないようになっています。

ライセンス

MIT ライセンスとしました。
ただ重要なのは免責だけで、著作権を主張するようなことはたぶんありません。

参考/謝辞

UTF-8, UTF-16 まわりは以下を参考(というかまんま)にさせていただきました。ありがとうございます。