Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/72.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
用C语言中的SDL模糊图像_C_Sdl - Fatal编程技术网

用C语言中的SDL模糊图像

用C语言中的SDL模糊图像,c,sdl,C,Sdl,我的算法有问题,应该会模糊我的图像。 这是我的密码: #include <stdlib.h> #include <stdio.h> #include <string.h> #include <SDL/SDL.h> #include <SDL/SDL_image.h> Uint32 getpixel(SDL_Surface *surface, int x, int y) { int bpp = surface->form

我的算法有问题,应该会模糊我的图像。 这是我的密码:

#include <stdlib.h>
#include <stdio.h>
#include <string.h>

#include <SDL/SDL.h>
#include <SDL/SDL_image.h>

Uint32 getpixel(SDL_Surface *surface, int x, int y)
{
    int bpp = surface->format->BytesPerPixel;
    /* Here p is the address to the pixel we want to retrieve */
    Uint8 *p = (Uint8 *)surface->pixels + y * surface->pitch + x * bpp;

    switch(bpp) {
    case 1:
        return *p;
        break;

    case 2:
        return *(Uint16 *)p;
        break;

    case 3:
        if(SDL_BYTEORDER == SDL_BIG_ENDIAN)
            return p[0] << 16 | p[1] << 8 | p[2];
        else
            return p[0] | p[1] << 8 | p[2] << 16;
        break;

    case 4:
        return *(Uint32 *)p;
        break;

    default:
        return 0;       /* shouldn't happen, but avoids warnings */
    }
}

void putpixel(SDL_Surface *surface, int x, int y, Uint32 pixel)
{
    int bpp = surface->format->BytesPerPixel;
    /* Here p is the address to the pixel we want to set */
    Uint8 *p = (Uint8 *)surface->pixels + y * surface->pitch + x * bpp;

    switch(bpp) {
    case 1:
        *p = pixel;
        break;

    case 2:
        *(Uint16 *)p = pixel;
        break;

    case 3:
        if(SDL_BYTEORDER == SDL_BIG_ENDIAN) {
            p[0] = (pixel >> 16) & 0xff;
            p[1] = (pixel >> 8) & 0xff;
            p[2] = pixel & 0xff;
        } else {
            p[0] = pixel & 0xff;
            p[1] = (pixel >> 8) & 0xff;
            p[2] = (pixel >> 16) & 0xff;
        }
        break;

    case 4:
        *(Uint32 *)p = pixel;
        break;
    }
}


SDL_Surface* Filter(SDL_Surface* source)
{
    SDL_Surface *target;
    int x, y;

    if( source->flags & SDL_SRCCOLORKEY )
        {target = SDL_CreateRGBSurface( SDL_SWSURFACE, source->w ,source->h, source->format->BitsPerPixel, source->format->Rmask, source->format->Gmask, source->format->Bmask, 0 );}
    else
        {target = SDL_CreateRGBSurface( SDL_SWSURFACE, source->w ,source->h, source->format->BitsPerPixel, source->format->Rmask, source->format->Gmask, source->format->Bmask, source->format->Amask );}

    for(y=0; y<source->h; ++y){
        for(x=0; x<source->w; ++x)
        {
           int a = getpixel(source,x-1, y-1);
           int b = getpixel(source,x  , y-1);
           int c = getpixel(source,x+1, y-1);

           int d = getpixel(source,x-1, y);
           int z = getpixel(source,x  , y);
           int e = getpixel(source,x+1, y);

           int f = getpixel(source,x-1, y+1);
           int g = getpixel(source,x  , y+1);
           int h = getpixel(source,x+1, y+1);

           int avg = (a+b+c + d+z+e + f+g+h)/9;

           putpixel(target,x, y, avg);
        }
    }
return target;
}
#包括
#包括
#包括
#包括
#包括
Uint32 getpixel(SDL_曲面*曲面,整数x,整数y)
{
int bpp=表面->格式->字节/像素;
/*这里p是我们要检索的像素的地址*/
Uint8*p=(Uint8*)表面->像素+y*表面->基音+x*bpp;
交换机(bpp){
案例1:
返回*p;
打破
案例2:
返回*(Uint16*)p;
打破
案例3:
if(SDL_字节顺序==SDL_大字节)

return p[0]事情比代码假设的要复杂一些。图像中的像素值是使用特定的像素格式编码的,因此您不能简单地对它们进行求和、除法,然后假设一切正常

相反,您必须分离图像的不同通道,分别对每个通道进行操作,然后再次对它们进行分组。为此,您可以使用以下功能和:

注意,所有这些函数调用都会非常慢。如果你事先知道像素格式,你可以自己做RGB转换

PS2:虽然这或多或少会起作用,但请注意,如果考虑伽马,而不是假设颜色空间是线性的,那么许多颜色计算的效果会更好

PS3:如果你做两次传递,这个算法会快一个数量级。第一次将只模糊水平边缘(3个样本),而第二次将模糊垂直边缘(3个样本)。这就是
O(n)
,而不是
O(n^2)
,即
n
模糊内核的大小


PS4:正如其他人所说,你没有检查图像边界,也没有锁定表面。

int avg=(a+b+c+d+z+e+f+g+h)/9;
看起来不对。分开颜色。我应该如何分开颜色?
unsigned r = 0, g = 0, b = 0;
Uint8 rt, gt, bt;

unsigned a = getpixel(source,x-1, y-1);
SDL_GetRGB(a, source->format, &rt, &gt, &bt);
r += rt;
g += gt;
b += bt;
//repeat for each pixel...

r /= 9;
g /= 9;
b /= 9;
unsigned avg = SDL_MapRGB(target->format, r, g, b);