#include "tools.h" #include Uint8 *pixelref(SDL_Surface *surf, unsigned x, unsigned y) { int bpp = surf->format->BytesPerPixel; return (Uint8 *)surf->pixels + y * surf->pitch + x * bpp; } Uint32 getpixel(SDL_Surface *surface, unsigned x, unsigned y) { Uint8 *p = pixelref(surface, x, y); switch (surface->format->BytesPerPixel) { case 1: return *p; case 2: return *(Uint16 *)p; 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; case 4: return *(Uint32 *)p; } return 0; } void putpixel(SDL_Surface *surface, int x, int y, Uint32 pixel) { Uint8 *p = pixelref(surface, x, y); switch (surface->format->BytesPerPixel) { 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; } } void pause1() { int continuer = 1; SDL_Event event; while (continuer) { SDL_WaitEvent(&event); switch (event.type) { case SDL_QUIT: continuer = 0; } } } void array_swap(int array[], size_t i, size_t j) { int element1 = array[i]; int element2 = array[j]; array[i] = element2; array[j] = element1; } void array_select_sort(int array[], size_t len) { size_t i = 0; size_t j; int min_index; while (i < len) { j = i; min_index = j; while (j < len) { if (array[j] < array[min_index]) { min_index = j; } j += 1; } array_swap(array, i, min_index); i++; } } SDL_Surface *copy_image(SDL_Surface *img) { Uint32 pixel; SDL_Surface *copy; copy = SDL_CreateRGBSurface(0, img->w, img->h, img->format->BitsPerPixel, 0, 0, 0, 0); for (int i = 0; i < img->w; i++) { for (int j = 0; j < img->h; j++) { pixel = getpixel(img, i, j); putpixel(copy, i, j, pixel); } } return (copy); } SDL_Surface *resize(SDL_Surface *img, int x, int y) { Uint32 pixel; SDL_Surface *new = SDL_CreateRGBSurface(0, x, y, img->format->BitsPerPixel, 0, 0, 0, 0); int w = img->w; int h = img->h; float ratioX = (float)w / x; float ratioY = (float)h / y; for (int i = 0; i < x; ++i) { for (int j = 0; j < y; ++j) { pixel = getpixel(img, (int)(i * ratioX), (int)(j * ratioY)); putpixel(new, i, j, pixel); } } return new; } SDL_Surface *CreateWhiteSurface(int x, int y, SDL_Surface *img) { Uint32 pixel; SDL_Surface *new = SDL_CreateRGBSurface(0, x, y, img->format->BitsPerPixel, 0, 0, 0, 0); for (int i = 0; i < new->w; i++) { for (int j = 0; j < new->h; j++) { pixel = SDL_MapRGB(img->format, 255, 255, 255); putpixel(new, i, j, pixel); } } return (new); } /*return a new image with a rotation of theta a apply in the image in paramaters*/ SDL_Surface *rotate(double teta, SDL_Surface *img) { double radian = (teta * M_PI) / 180.0; int certerx = round(((img->w + 1) / 2) - 1); int centery = round(((img->h + 1) / 2) - 1); int xprime = 0; int yprime = 0; int h = img->h; int w = img->w; Uint32 pixel = 0; SDL_Surface *new = CreateWhiteSurface(w, h, img); for (int i = 0; i < img->w; i++) { for (int j = 0; j < img->h; j++) { xprime = round((double)(i - certerx) * cos(radian) + (double)(j - centery) * sin(radian)); yprime = round((double)(j - centery) * cos(radian) - (double)(i - certerx) * sin(radian)); xprime += certerx; yprime += centery; if (xprime >= 0 && xprime < img->w && yprime < img->h && yprime >= 0) { pixel = getpixel(img, i, j); putpixel(new, xprime, yprime, pixel); } } } return new; } /*apply hough transformy and return the angle detected*/ double houghtrasformy(SDL_Surface *img) { double maxrow = sqrt((img->w * img->w) + (img->h * img->h)); int maxteta = 180; Uint8 r, g, b; int *tab = calloc((size_t)(maxrow * 181), sizeof(int)); Uint32 pixel = 0; for (int i = 0; i < img->w; i++) { for (int j = 0; j < img->h; j++) { pixel = getpixel(img, i, j); SDL_GetRGB(pixel, img->format, &r, &g, &b); if (r == 0 && g == 0 && b == 0) { int x = i - (img->w / 2); int y = j - (img->h / 2); for (int teta_i = 0; teta_i < maxteta; teta_i++) { double teta = ((double)teta_i / 180.0) * M_PI; double row = x * cos(teta) + y * sin(teta); size_t i_rho = 0.5 + (row / maxrow + 0.5) * (maxrow + 1); tab[teta_i + maxteta * i_rho] += 1; } } } } double resulte = maxhough(tab, maxrow); free(tab); return resulte; } double maxhough(int *tab, size_t maxrow) { double ThetaR; int max = 0; size_t maxteta = 180; for (size_t i = 0; i < maxrow; ++i) { for (size_t j = 0; j < maxteta; ++j) { if (tab[j + i * maxteta] > max) { max = tab[j + i * maxteta]; ThetaR = j; } } } return ThetaR; }