yes yes hahaha yes

This commit is contained in:
Brooke Vibber 2023-03-21 18:34:14 -07:00
parent 2cc9198e2c
commit b4e3394809

View file

@ -407,11 +407,10 @@ let atariRGB = [
* @param {RGB[]} input source scanline data, in linear RGB * @param {RGB[]} input source scanline data, in linear RGB
* @param {number[]} palette - current working palette, as Atari 8-bit color values (low nybble luminance, high nybble hue) * @param {number[]} palette - current working palette, as Atari 8-bit color values (low nybble luminance, high nybble hue)
* @param {number} n - target color count * @param {number} n - target color count
* @param {RGB[]} inputError
* @param {number} y * @param {number} y
* @returns {{output: number[], palette: number[], error: RGB[]}} * @returns {{output: number[], palette: number[], error: RGB[]}}
*/ */
function decimate(input, palette, n, inputError, y) { function decimate(input, palette, n) {
// to brute-force, the possible palettes are: // to brute-force, the possible palettes are:
// 255 * 254 * 253 = 16,386,810 // 255 * 254 * 253 = 16,386,810
// //
@ -433,9 +432,6 @@ function decimate(input, palette, n, inputError, y) {
if (error) { if (error) {
rgb.inc(error.cur[x]); rgb.inc(error.cur[x]);
} }
if (inputError) {
rgb.inc(inputError[x]);
}
rgb.cap(); rgb.cap();
return rgb; return rgb;
}; };
@ -540,9 +536,9 @@ function decimate(input, palette, n, inputError, y) {
// Median cut! // Median cut!
// https://en.wikipedia.org/wiki/Median_cut // https://en.wikipedia.org/wiki/Median_cut
//let buckets = [input.slice()]; let buckets = [input.slice()];
let initial = dither(palette); //let initial = dither(palette);
let buckets = [initial.output.map((i) => atariRGB[palette[i]])]; //let buckets = [initial.output.map((i) => atariRGB[palette[i]])];
let medianCut = (bucket, range) => { let medianCut = (bucket, range) => {
if (bucket.length < 2) { if (bucket.length < 2) {
console.log(bucket); console.log(bucket);
@ -582,19 +578,25 @@ function decimate(input, palette, n, inputError, y) {
} }
decimated = buckets.map((bucket) => { decimated = buckets.map((bucket) => {
// Average the RGB colors in this chunk // Average the RGB colors in this chunk
//let rgb = bucket let rgb = bucket
// .reduce((acc, rgb) => acc.inc(rgb), new RGB(0, 0, 0)) .reduce((acc, rgb) => acc.inc(rgb), new RGB(0, 0, 0))
// .divide(bucket.length); .divide(bucket.length);
// scale to the max luma let avg_luma = rgb.luma();
let lumas = bucket.map((rgb) => rgb.luma());
let brightest = Math.max(...lumas);
if (avg_luma > 0) {
rgb = rgb.multiply(brightest / avg_luma);
}
// pick the luma-brightest color in the bucket
// kinda nice but really aggressive with the colors // kinda nice but really aggressive with the colors
/*
let lumas = bucket.map((rgb) => rgb.luma()); let lumas = bucket.map((rgb) => rgb.luma());
let luma = Math.max(...lumas); let luma = Math.max(...lumas);
let rgb = bucket[lumas.indexOf(luma)]; let rgb = bucket[lumas.indexOf(luma)];
let from = rgb.luma(); */
if (from > 0) {
rgb = rgb.multiply(luma / rgb.luma());
}
// Take the channel-brightest color in the bucket // Take the channel-brightest color in the bucket
// bad // bad
@ -615,6 +617,7 @@ function decimate(input, palette, n, inputError, y) {
Math.max(...bucket.map((rgb) => rgb.b)) Math.max(...bucket.map((rgb) => rgb.b))
); );
*/ */
// combine the median of each channel // combine the median of each channel
// sux // sux
/* /*
@ -734,9 +737,13 @@ async function convert(source) {
let lines = []; let lines = [];
for (let y = 0; y < height; y++) { for (let y = 0; y < height; y++) {
let error = lines[y - 1]?.error; let inputLine = input
let inputLine = input.slice(y * width, (y + 1) * width); .slice(y * width, (y + 1) * width);
let line = decimate(inputLine, allColors, 4, error, y); if (y > 0) {
let error = lines[y - 1].error;
inputLine = inputLine.map((rgb, x) => RGB.add(rgb, error[x]));
}
let line = decimate(inputLine, allColors, 4, y);
lines.push(line); lines.push(line);
} }
return { return {