2

我正在尝试将图像(使用 HTML 画布)从 RGB 转换为 YCoCg 颜色空间,并将画布的输出保存为 PNG,可以根据此处的代码无损地转换回来:

https://stackoverflow.com/a/12146329/2399347

该过程是可逆的,但我的尝试目前仅在不使用中间格式时才有效。没有这个,代码的实际应用就会受到限制。

我需要让“提升”过程使用 8 位有符号整数(我相信从 -128 到 127,在伪代码中模 0x100),并转换要在画布上显示的值(从 0 到 255),然后再能够保存。如果成功,当转换后的图像放置在画布中时,重新转换值和反向提升应该会生成原始图像。当前生成的值无法正确显示在画布上(从 -255 到 255)。

上述问题超出了我目前的知识范围,目前我还没有找到基于在线搜索和查看 Javascript 文档的方法。那些知道(或感兴趣)的人,能否请您看一下代码,并建议或提供一种实用的方法或解决方法?

<!DOCTYPE html>
<html>
<head>
    <meta http-equiv="content-type" content="charset=UTF-8" />
    <style>
    img, canvas {
        display: block;
        padding-bottom: 1em;
    }
    </style>
    <script>
function go() {

//  Extract PNG image to Canvas

    var canvas = document.getElementById('ycocg');
    var ctx = canvas.getContext('2d');
    var source = document.querySelector("#original");

    canvas.width = source.width;
    canvas.height = source.height;

    ctx.drawImage(source, 0, 0);

    var canvasData = ctx.getImageData(0, 0, canvas.width, canvas.height);


//  Canvas to convert image to YCoCg and back in one step

    var canvasBack = document.getElementById('back2rgb');
    var ctxBack = canvasBack.getContext('2d');

    canvasBack.width = source.width;
    canvasBack.height = source.height;

    ctxBack.drawImage(canvas, 0, 0);

    var canvasBackData = ctxBack.getImageData(0, 0, canvas.width, canvas.height);


//  Colour space functions

function forward_lift( x1, y1 ) {
    var diff = ( ( y1 - x1 ) ) % 256;
    var average = ( x1 + ( diff >> 1 ) ) % 256;

    return  { c1: average, c2: diff };
}

function reverse_lift( average, diff ) {
    var x2 = ( average - ( diff >> 1 ) ) % 256;
    var y2 = ( ( x2 + diff ) ) % 256;

    return  { c1: x2, c2: y2 };
}

function RGB_to_YCoCg24( red, green, blue ) {
    // Conversion and back

    var lift1 = forward_lift( red, blue );
    var lift2 = forward_lift( green, lift1.c1 );

    var rlift1 = reverse_lift( lift2.c1, lift2.c2 );
    var rlift2 = reverse_lift( rlift1.c2, lift1.c2 );

    canvasBackData.data[idx + 0] = rlift2.c1 % 256; // R
    canvasBackData.data[idx + 1] = rlift1.c1 % 256; // G
    canvasBackData.data[idx + 2] = rlift2.c2 % 256; // B

    // Attempt at conversion only and store

    canvasData.data[idx + 0] = lift2.c1 % 256; // Y
    canvasData.data[idx + 1] = lift2.c2 % 256; // Cg
    canvasData.data[idx + 2] = lift1.c2 % 256; // Co
}

function YCoCg24_to_RGB( Yimg, Cg, Co ) {
    // Attempt at reversing stored image

    var rlift1 = reverse_lift( Yimg, Cg );
    var rlift2 = reverse_lift( rlift1.c2, Co );

    canvasStepData.data[idx + 0] = rlift2.c1 % 256; // R
    canvasStepData.data[idx + 1] = rlift1.c1 % 256; // G
    canvasStepData.data[idx + 2] = rlift2.c2 % 256; // B
}

//  Conversion of RGB image to YCoCg

    for (var x = 0; x < canvasData.width; x++) {
        for (var y = 0; y < canvasData.height; y++) {
            // Index of the pixel in the array
            var idx = (x + y * canvas.width) * 4;

            RGB_to_YCoCg24( canvasData.data[idx + 0], canvasData.data[idx + 1], canvasData.data[idx + 2]  );
        }
    }
    ctxBack.putImageData(canvasBackData, 0, 0);
    ctx.putImageData(canvasData, 0, 0);


//  Convert from YCoCg to RGB, in two steps

    var canvasStep = document.getElementById('twostep');
    var ctxStep = canvasStep.getContext('2d');

    canvasStep.width = source.width;
    canvasStep.height = source.height;

    ctxStep.drawImage(canvas, 0, 0);

    var canvasStepData = ctxStep.getImageData(0, 0, canvas.width, canvas.height);

    for (var x = 0; x < canvasData.width; x++) {
        for (var y = 0; y < canvasData.height; y++) {
            // Index of the pixel in the array
            var idx = (x + y * canvas.width) * 4;

            YCoCg24_to_RGB( canvasStepData.data[idx + 0], canvasStepData.data[idx + 1], canvasStepData.data[idx + 2]  );
        }
    }
    ctxStep.putImageData(canvasStepData, 0, 0);
}
    </script>
</head>

<body onload="go()">

<div id="container">
    Original:
    <img id="original" src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAABAAAAAQACAIAAADwf7zUAAAR00lEQVR4Xu3a0QnDAAxDQTVkAO8/bbdQKTq4Afz7kD9PnuT9Y5/X/e53/59yf5/73e9+97vf/c+bjAAAAH4ZAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAADQWQAAAAAvQAAAgAAAAAAEAAAAIAAAAAABAAAACAAAABAAAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAAEwGUDAABgAQAAAC9AAACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAA0AACAAAAAAAQAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAABAAAAAAAIAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAAAgAAAAAAEAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAAAQAAAAgAAAAAAEAAAAIAAAAAABAAAACAAAAEAAAAAAAgAAABAAAACAAAAAAAQAAAAIAAAAQAAAAAACAAAAEAAAAIAAAAAABAAAACAAAAAAAQAAAAgAAABAAAAAAAIAAAD4Aozry/w+U2+oAAAAAElFTkSuQmCC" />

    Converted and back in one step:
    <canvas id="back2rgb"></canvas>

    Converted and stored (right click, save image as):
    <canvas id="ycocg"></canvas>

    Restored previous image:
    <canvas id="twostep"></canvas>
</div>

</body>
</html>
4

0 回答 0