【问题标题】:Ordered color dither有序颜色抖动
【发布时间】:2016-10-12 19:50:01
【问题描述】:

我目前正在做一个项目,我必须使用 4x4 有序抖动矩阵将 24bpp 图片减少到 3bpp 图像。但是,在进行抖动处理后,我的图像只显示了大约 1/3 的路径。有谁知道我做错了什么?

来源:

#include <stdio.h>
#include <fstream>

/*24 bit per pixel - 3 bit per pixel dither*/
/*Use the 4x4 Ordered Dither Matrix:

    [1 9 3 11]
    [13 5 15 7]
    [4 12 2 10]
    [16 8 14 6]

*/
int checkColor(int a, int b);

unsigned char buf[512][512];
unsigned char out[512][512];
float ratio = 1.0 / 17;


int main(){

    FILE *fp, *output;
    int i, j, k, l;

    /*dither matrix*/
    unsigned int dith[4][4] = {{1, 9, 3, 11}, {13, 5, 15, 7}, {4, 12, 2, 10}, {16, 8, 14, 6}};


    if((fp = fopen("LennaRGB512.data", "rb")) == NULL){
        printf("error opening file\n");
    }

    for (i = 0; i < 512; i++) {
        for (j = 0; j < 512; j++) {
            buf[i][j] = fgetc(fp); /*Put data in buffer*/
        }
    }

    i = 0;
    j = 0;

    int x, y;
    int bd = 64;
    for (k = 0; k < 512; k++){
        for (l = 0; l < 512; l++){
            int oldPixel = buf[k][l];
            int value = (oldPixel + (ratio * dith[k%4][l%4]));

            int r = ((oldPixel >> 16) & 0xff) + value;
            int g = ((oldPixel >> 8) & 0xff) + value;
            int b = (oldPixel & 0xff) + value;

            int newPixel = 0x000000 | checkColor(r, bd) << 16 | checkColor(g, bd) << 8 | checkColor(b, bd);
            out[k][l] = newPixel;
        }
    }


    output = fopen("converted_img.data", "wb");

    for (i = 0; i < 512; i++){
        for (j = 0; j < 512; j++){
            fputc(out[i][j], output);
        }
    }

    fclose(output);
    fclose(fp);

    return 0;
}

int checkColor(int a, int b){
    return a / b * b;
}

我之前的图像是 512x512 图像,但是我的输出图像抖动只是图像的一部分 (512x170)

【问题讨论】:

    标签: c++ dithering


    【解决方案1】:

    您的源图像是 24bpp。这是每个像素三个字节。如果您只读取 512 字节宽和 512 字节高,这正好代表 512x170 (512/3) 的图像。开始时每个像素需要读取 3 个字节。

    此外,您正在使用int newPixel 转换为 32bpp,而不是 3bpp,而是将其存储在一个字符中,这将溢出(截断)该值。

    此外,为什么您的抖动模式是 4bpp? (2^4 = 16 个值)。

    看来你的老师解释得不好。

    【讨论】:

    • 我的老师刚刚告诉我们使用 4 * 4 有序抖动矩阵。他们也没有教我们关于颜色抖动的知识,而是向我们展示了我们可以在灰度图像中抖动 1 或 0。我实际上是白手起家,所以我感谢你的帮助。
    • 查看en.wikipedia.org/wiki/Ordered_dithering 了解该方法的作用的一些细节。但是他们的伪代码算法有一个错误,所以不要使用它。您需要使您的 buf 数组大小为 512x512x3 以容纳每个 rgb 三元组。首先应用您的抖动,然后转换为 3bpp(您需要调色板或颜色图)。请逐字发布您的作业,以便我确切知道您的老师要求什么。
    • 我猜你老师所说的 3bpp 是指红色、绿色和蓝色各一位。否则,它会建议使用 8 种颜色的调色板。了解他的要求将大有帮助。
    • 您需要将 24 位彩色图像量化为仅 3 位彩色图像,无需查找表。将给定的 24 位 RGB Lena 转换为每像素 3 位,而不会完全失去每种颜色的强度(位深度)。为此使用 4X4 有序抖动矩阵。使用有序的 4x4 抖动矩阵,将 lena.data 中 512 x 512 Lena 彩色图像的 R、G、B 的每个 256 强度(在课程网页中给出)转换为(16 + 1)不同强度,使用每通道 1 位 1 位R 1 位 G 1 位 B
    • 我想我知道他在问什么。这里有一个非常相似的问题:stackoverflow.com/questions/36087038/…。要将 888 RGB 转换为 111 RGB,您需要测试 R、G 或 B 值是否大于或等于 128。如果是,请将相应位设置为 1。不过,我不确定他希望您如何存储相应的 3 位。您应该请老师为您澄清作业。他遗漏了一些关键细节。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-04-13
    • 1970-01-01
    • 2021-09-16
    • 1970-01-01
    • 2015-08-28
    • 2020-03-19
    • 1970-01-01
    相关资源
    最近更新 更多