georaster
georaster copied to clipboard
Save as PNG
Is your feature request related to a problem? Please describe.
Sometimes users might want to save their GeoRaster as a PNG file. For example, this would be useful for displaying results in Observable or Jupyter Notebooks.
Describe the solution you'd like
We should create a new function called savePNG that returns an (array)buffer for a PNG.
Describe alternatives you've considered
I've thought about creating a save method where you pass in the filename and the function auto-detects the file type from the extension of the filename. I don't think this would be a good idea, because we can't easily save files in the browser and I think this would make this package much more complicated. Perhaps, we can explore this after creating the function that creates the arraybuffer because I think this is a pre-requisite to saving a file, anyway.
Additional context
Should users have to manually create a data URI like those found at https://en.wikipedia.org/wiki/Data_URI_scheme or should we have a separate method savePNGDataURI. It might be more maintainable to force the users to construct their own data URIs, but I'm not sure what % of users will know how to do this.
This is something I implemented using pngjs, here is the snippet:
const parse_georaster = require('georaster')
const { PNG } = require('pngjs')
const hexRgb = require('hex-rgb')
const georaster = await parse_georaster(tiffBuffer)
const { width, height } = georaster
const png = new PNG({ width, height })
const band = georaster.values[0]
for(let x = 0; x < band.length; x++) {
for(let y = 0; y < band[x].length; y++) {
if(band[x] && band[x][y]) {
// I need to "translate" values to colors myself, you might as well use the color if it's in the TIFF
const color = pixelValueToColor(band[x][y])
const rgba = color ? hexRgb(color, {format: 'array'}) : [ 0, 0, 0, 0 ]
const idx = (width * x + y) << 2
png.data[idx ] = rgba[0]
png.data[idx+1] = rgba[1]
png.data[idx+2] = rgba[2]
png.data[idx+3] = rgba[3] * 255
}
}
}
const pngBuffer = PNG.sync.write(png)
from there you can write the PNG to a file, produce a data URI, stream it or anything else you can do with a buffer.
Awesome!