A JavaScript Encoder of Guetzli.
Guetzli is a JPEG encoder that aims for excellent compression density at high visual quality. Guetzli-generated images are typically 20-30% smaller than images of equivalent quality generated by libjpeg. Guetzli generates only sequential (nonprogressive) JPEGs due to faster decompression speeds they offer. Guetzli Github
View a Live Demo:
http://dominikhlbg.github.io/Guetzli.js/web/jsDemo.html
http://dominikhlbg.github.io/Guetzli.js/web/wasmDemo.html (WebAssembly => webassembly.org)
This javascript solution of Google Guetzli Encoder for Images is compiled with Emscripten to JavaScript & WebAssembly. The source code of Guetzli has some changes else compile would not work.
Install and configure Emscripten (https://github.com/kripken/emscripten)
The current version of Guetzli.js was built with emscripten 1.37.8, but works with 1.35.0, too.
The code for the demo you can found in this git, to build use follow code lines:
JavaScript:
$ ./emcc guetzli_emscripten.cc -I. -I./third_party/butteraugli/ -I./third_party -o ./web/guetzli.js -std=c++14 -s EXPORTED_FUNCTIONS="['_Guetzli_encodeRGBA','_Guetzli_encode']" -s TOTAL_MEMORY=167772160 -s ALLOW_MEMORY_GROWTH=1 -s INVOKE_RUN=0 -O3
WebAssembly:
$ ./emcc guetzli_emscripten.cc -I. -I./third_party/butteraugli/ -I./third_party -o ./web/guetzli_wasm.js -Wno-format -std=c++14 -s EXPORTED_FUNCTIONS="['_Guetzli_encodeRGBA','_Guetzli_encode']" -s TOTAL_MEMORY=167772160 -s ALLOW_MEMORY_GROWTH=1 -s INVOKE_RUN=0 -s WASM=1 -s BINARYEN_METHOD='native-wasm' -O3
The Guetzli source code has an own decoder for jpeg images for better analysing of optimising. Another images Gif/WebP must be load as rgba array for encoding. In the the folder "web" you found two html files with example code, but here a shorter version:
JavaScript Version (Init):
<script src="guetzli.js"></script>
<script>
function init() {
var Guetzli_encodeRGBA = Module.cwrap('Guetzli_encodeRGBA', 'int', ['array', 'number', 'number', 'number', 'number']);
var Guetzli_encode = Module.cwrap('Guetzli_encode', 'int', ['number','number']);
}
</script>
<body onload="init()">
Encode JPEG/PNG Image:
var quality=95;
FS.writeFile('in.ext', new Uint8Array(input), { encoding: "binary" });
Guetzli_encode(quality, verbose);
output=FS.readFile('out.jpg');//output: Uint8Array()
or RGBA data:
Guetzli_encodeRGBA(rgbaData, width, height, quality, verbose);
output=FS.readFile('out.jpg');//output: Uint8Array()
rgbadata => new Array(r,g,b,a, r,g,b,a, r,g,b,a, ...); width => Image width height => Image height quality => [0...100] verbose => true/false - print encoding steps into console functions => return false if successful encoded and true if error
- implement javascript instance
This is my first emscripten release!