codeconv.htm

戻る

<!DOCTYPE HTML>
<HTML LANG="ja">

<HEAD>
<META CHARSET="Shift_JIS">
<TITLE>文字コード変換</TITLE>
<STYLE TYPE="text/css">
<!--
#opt::-webkit-scrollbar {display:none}
-->
</STYLE>
</HEAD>

<BODY STYLE="background-color:#CCFFFF">
<CENTER>
<B>文字コード変換</B>
<BR><BR>

<FORM ID="form" TARGET="target">
<TABLE>
<TR><TD NOWRAP>
入力文字コード:
<INPUT TYPE=TEXT ID="i_enc" SIZE=30>
<SPAN STYLE="position:relative">
<INPUT TYPE=BUTTON VALUE="選択" onClick="sel_opt(this, elem_i_enc)" STYLE="position:relative">
</SPAN>
<INPUT TYPE=BUTTON ID="in" VALUE="読み込み" onClick="input()" STYLE="margin-left:1em">
</TD></TR>
<TR><TD NOWRAP>
出力文字コード:
<INPUT TYPE=TEXT ID="o_enc" SIZE=30>
<SPAN STYLE="position:relative">
<INPUT TYPE=BUTTON VALUE="選択" onClick="sel_opt(this, elem_o_enc)" STYLE="position:relative">
</SPAN>
<SPAN STYLE="margin-left:1em">改行:</SPAN>
<SELECT ID="le">
<OPTION>LF
<OPTION>CR
<OPTION>CR+LF
</SELECT>
<INPUT TYPE=BUTTON ID="out" VALUE="書き出し" onClick="output()" STYLE="margin-left:1em">
</TD></TR>
<TR><TD>
<TEXTAREA NAME="d" ID="data" ROWS=20 COLS=80 WRAP="OFF"></TEXTAREA>
</TD></TR>
</TABLE>

<SELECT ID="opt" SIZE=9 STYLE="position:absolute; left:0; top:0; z-index:1; display:none; scrollbar-width:none; outline:none">
<OPTION>ISO-8859-1
<OPTION>ISO-2022-JP
<OPTION>Shift_JIS
<OPTION>EUC-JP
<OPTION>UTF-8
<OPTION>UTF-16BE
<OPTION>UTF-16LE
<OPTION>UTF-32BE
<OPTION>UTF-32LE
</SELECT>
</FORM>

</CENTER>

<IFRAME NAME="target" ID="frame" WIDTH=1 HEIGHT=1 SRC="about:blank" STYLE="display:none"></IFRAME>
<A ID="dl" STYLE="display:none"></A>

<SCRIPT TYPE="text/javascript">
<!--

function sel_opt(sel, enc) {
  elem_sel = sel;
  elem_enc = enc;
  elem_opt.selectedIndex = 0;
  elem_sel.parentNode.appendChild(elem_opt);
  elem_opt.style.display = "";
  elem_opt.focus();
}

function opt_click() {
  elem_enc.value = elem_opt.value;
  elem_opt.style.display = "none";
}

function opt_keydown(e) {
  switch(e.keyCode) {
  case 9:  // Tab
    if(e.shiftKey) {
      elem_enc.focus();
    }
    else {
      if(elem_enc === elem_i_enc)
        elem_in.focus();
      else
        elem_le.focus();
    }
    e.preventDefault();
    break;

  case 13:  // Enter
    elem_enc.value = elem_opt.value;
    // fall thru
  case 27:  // Esc
    elem_opt.style.display = "none";
    break;
  }
}

function opt_blur() {
  elem_opt.style.display = "none";
}

// 読み込み
function input() {
  elem_in.disabled = elem_out.disabled = true;
  setTimeout(enable_btn, 100);
  // ファイルを開く
  elem_file = document.createElement("INPUT");
  elem_file.type = "FILE";
  elem_file.onchange = input2;
  elem_file.click();
}

function enable_btn() {
  elem_in.disabled = elem_out.disabled = false;
}

function input2() {
  elem_in.disabled = elem_out.disabled = true;
  file_reader = new FileReader();
  file_reader.onloadend = input4;
  enc_val = elem_i_enc.value.trim();
  switch(enc_val.toUpperCase()) {
  case "UTF-16BE":
  case "UTF-16LE":
  case "UTF-32BE":
  case "UTF-32LE":
    file_reader.onload = input3s;
    file_reader.readAsBinaryString(elem_file.files.item(0));
    return;
  }
  file_reader.onload = input3;
  file_reader.readAsText(elem_file.files.item(0), enc_val);
}

function input3() {
  elem_data.value = file_reader.result;
  elem_data.scrollTop = 0;
}

function input3s() {
  var buff = file_reader.result;
  var data = "";
  var i = 0;
  switch(enc_val.toUpperCase()) {
  case "UTF-16BE":
    for(; i + 1 < buff.length; i += 2)
      data += String.fromCharCode((buff.charCodeAt(i) << 8) | buff.charCodeAt(i + 1));
    break;

  case "UTF-16LE":
    for(; i + 1 < buff.length; i += 2)
      data += String.fromCharCode((buff.charCodeAt(i + 1) << 8) | buff.charCodeAt(i));
    break;

  case "UTF-32BE":
    for(; i + 3 < buff.length; i += 4) {
      if(buff.charCodeAt(i) || buff.charCodeAt(i + 1))  // BMP 以外
        data += String.fromCharCode(0xd800 | (((buff.charCodeAt(i + 1) & 0x1f) - 1) << 6) | (buff.charCodeAt(i + 2) >> 2),
                                    0xdc00 | ((buff.charCodeAt(i + 2) & 0x3) << 8) | buff.charCodeAt(i + 3));
      else
        data += String.fromCharCode((buff.charCodeAt(i + 2) << 8) | buff.charCodeAt(i + 3));
    }
    break;

  case "UTF-32LE":
    for(; i + 3 < buff.length; i += 4) {
      if(buff.charCodeAt(i + 2) || buff.charCodeAt(i + 3))  // BMP 以外
        data += String.fromCharCode(0xd800 | (((buff.charCodeAt(i + 2) & 0x1f) - 1) << 6) | (buff.charCodeAt(i + 1) >> 2),
                                    0xdc00 | ((buff.charCodeAt(i + 1) & 0x3) << 8) | buff.charCodeAt(i));
      else
        data += String.fromCharCode((buff.charCodeAt(i + 1) << 8) | buff.charCodeAt(i));
    }
    break;
  }
  elem_data.value = data;
  elem_data.scrollTop = 0;
}

function input4() {
  file_reader = undefined;
  elem_in.disabled = elem_out.disabled = false;
}

// 書き出し
function output() {
  var enc_val = elem_o_enc.value.trim();
  switch(enc_val.toUpperCase()) {
  case "UTF-16BE":
  case "UTF-16LE":
  case "UTF-32BE":
  case "UTF-32LE":
    break;

  default:
    elem_in.disabled = elem_out.disabled = true;
    // フォームの文字エンコーディングをセットして送信
    elem_form.acceptCharset = enc_val;
    addEventListener("message", output2, false);
    elem_form.submit();
    return;
  }

  var data = elem_data.value;
  switch(elem_le.selectedIndex) {  // 改行
  case 1:  // CR
    data = data.replace(/\n/g, "\r");
    break;
  case 2:  // CR+LF
    data = data.replace(/\n/g, "\r\n");
    break;
  }
  var bin = "";
  var c1, c2;
  var i = 0;
  switch(enc_val.toUpperCase()) {
  case "UTF-16BE":
    for(; i < data.length; i++) {
      c1 = data.charCodeAt(i);
      bin += String.fromCharCode(c1 >> 8) + String.fromCharCode(c1 & 0xff);
    }
    break;

  case "UTF-16LE":
    for(; i < data.length; i++) {
      c1 = data.charCodeAt(i);
      bin += String.fromCharCode(c1 & 0xff) + String.fromCharCode(c1 >> 8);
    }
    break;

  case "UTF-32BE":
    for(; i < data.length; i++) {
      c1 = data.charCodeAt(i);
      if((c1 & 0xfc00) == 0xd800) {  // BMP 以外
        if(++i == data.length)
          break;
        c2 = data.charCodeAt(i);
        bin += "\0" + String.fromCharCode(((c1 & 0x3c0) >> 6) + 1)
                 + String.fromCharCode(((c1 & 0x3f) << 2) | ((c2 & 0x300) >> 8))
                 + String.fromCharCode(c2 & 0xff);
      }
      else {
        bin += "\0\0" + String.fromCharCode(c1 >> 8) + String.fromCharCode(c1 & 0xff);
      }
    }
    break;

  case "UTF-32LE":
    for(; i < data.length; i++) {
      c1 = data.charCodeAt(i);
      if((c1 & 0xfc00) == 0xd800) {  // BMP 以外
        if(++i == data.length)
          break;
        c2 = data.charCodeAt(i);
        bin += String.fromCharCode(c2 & 0xff)
                 + String.fromCharCode(((c1 & 0x3f) << 2) | ((c2 & 0x300) >> 8))
                 + String.fromCharCode(((c1 & 0x3c0) >> 6) + 1) + "\0";
      }
      else {
        bin += String.fromCharCode(c1 & 0xff) + String.fromCharCode(c1 >> 8) + "\0\0";
      }
    }
    break;
  }
  // 変換結果をダウンロードする
  elem_dl.href = "data:application/octet-stream;base64," + btoa(bin);
  elem_dl.click();
}

function output2(e) {
  removeEventListener("message", output2, false);

  var str = e.data;  // location.href
  str = str.substring(str.indexOf("?") + 3).replace(/\+/g, "%20");  // ?d= の後ろを取り出し,スペースを %20 に変換
  switch(elem_le.selectedIndex) {  // 改行
  case 0:  // LF
    str = str.replace(/%0[Dd]/g, "");
    break;
  case 1:  // CR
    str = str.replace(/%0[Aa]/g, "");
    break;
  }
  // 変換結果をダウンロードする
  elem_dl.href = "data:application/octet-stream," + str;
  elem_dl.click();
  elem_in.disabled = elem_out.disabled = false;
}

  elem_form = document.getElementById("form");
  elem_i_enc = document.getElementById("i_enc");
  elem_in = document.getElementById("in");
  elem_o_enc = document.getElementById("o_enc");
  elem_le = document.getElementById("le");
  elem_out = document.getElementById("out");
  elem_data = document.getElementById("data");
  elem_opt = document.getElementById("opt");
  elem_dl = document.getElementById("dl");

  // クエリー文字列は location.search で取得できるが,Firefox ではなぜか
  // "data" URL のクエリー文字列を取得できない.
  // Firefox でも location.href にはクエリー文字列が含まれているので,location.href を送る.
  elem_form.action = "data:text/html,"
    + encodeURIComponent("<SCRIPT TYPE='text/javascript'>parent.postMessage(location.href, '*')</SCRIPT>");

  elem_opt.onclick = opt_click;
  elem_opt.onkeydown = opt_keydown;
  elem_opt.onblur = opt_blur;

  elem_i_enc.focus();

  // Firefox でページを再ロードしたときのため
  elem_form.reset();
  elem_in.disabled = elem_out.disabled = false;

//-->
</SCRIPT>

</BODY>

</HTML>