2014
11
21
11
21
JavaScript: 良質でExifを失わないJPEG縮小ライブラリ
以前に書いたJPEG縮小ライブラリに外部ライブラリ依存している部分があり、その外部ライブラリのライセンスがApache License Ver.2.0で開発や使用が少し手間だったので、外部依存を抜いた新しいライブラリを書いた。たいしたものでもなく使用改変の制限が面倒だったのでMITライセンスにした。
https://github.com/hMatoba/JavaScript-MinifyJpegAsync
MinifyAsync_Demo.html
・このライブラリのそもそもの目的
スマフォのカメラの解像度がやたら高くなっており、画像アップロード機能を持ったサービスをやるときはこの肥大化した画像のやり取りで通信やストレージのコストが膨らみやすくなっている。通信キャリアなどではサーバ側で添付画像などの縮小をおこなってしまう例があるぐらいなので、それならクライアントのブラウザでもポストする画像を送信前に適正サイズに縮小できたらうれしいはずという狙い。
・たぶん他と違うところ
縮小による画質劣化を抑え、Exifが抜け落ちないようにした。
HTML5のCanvasを使うことでJPEGの縮小は容易にできる。それをブログネタにしているところも多い。しかしなんのフィルタ処理もなくそれをやると画質が著しく劣化する。

上の画像で右側がCanvasによる単純な縮小、左側は当ライブラリにて縮小を行った結果である。当ライブラリを使えば極端にサイズが変わる縮小を行わない限りは、画質劣化を抑えることができる。
HTML5のCanvasを使った縮小では加工中にExifが抜け落ちる。スマフォのカメラは高機能化が進んでおりExifに価値のある情報が入っているかもしれないので、リサイズによってExifが抜け落ちるのは望ましくない。当ライブラリのJPEG縮小ではExifを維持したまま縮小を行える。
・使い方例
当ライブラリを使って画像を縮小してポストする例を以下に示す。
https://github.com/hMatoba/JavaScript-MinifyJpegAsync
MinifyAsync_Demo.html
・このライブラリのそもそもの目的
スマフォのカメラの解像度がやたら高くなっており、画像アップロード機能を持ったサービスをやるときはこの肥大化した画像のやり取りで通信やストレージのコストが膨らみやすくなっている。通信キャリアなどではサーバ側で添付画像などの縮小をおこなってしまう例があるぐらいなので、それならクライアントのブラウザでもポストする画像を送信前に適正サイズに縮小できたらうれしいはずという狙い。
・たぶん他と違うところ
縮小による画質劣化を抑え、Exifが抜け落ちないようにした。
HTML5のCanvasを使うことでJPEGの縮小は容易にできる。それをブログネタにしているところも多い。しかしなんのフィルタ処理もなくそれをやると画質が著しく劣化する。
上の画像で右側がCanvasによる単純な縮小、左側は当ライブラリにて縮小を行った結果である。当ライブラリを使えば極端にサイズが変わる縮小を行わない限りは、画質劣化を抑えることができる。
HTML5のCanvasを使った縮小では加工中にExifが抜け落ちる。スマフォのカメラは高機能化が進んでおりExifに価値のある情報が入っているかもしれないので、リサイズによってExifが抜け落ちるのは望ましくない。当ライブラリのJPEG縮小ではExifを維持したまま縮小を行える。
・使い方例
当ライブラリを使って画像を縮小してポストする例を以下に示す。
<input type="file" id="files" name="files[]" multiple />
<script source="/js/MinifyJpegAsync.js" />
<script>
function post(data) {
req.open("POST", "/jpeg", false);
req.setRequestHeader('Content-Type', 'image\/jpeg');
req.send(data.buffer);
}
function handleFileSelect(evt) {
var files = evt.target.files;
for (var i = 0, f; f = files[i]; i++){
var reader = new FileReader();
reader.onloadend = function(e){
MinifyJpegAsync.minify(e.target.result, 1280, post);
};
reader.readAsDataURL(f);
}
}
document.getElementById('files').addEventListener('change', handleFileSelect, false);
</script>