#include static void img_rotate_ip90(img_t img) { if(img.width != img.height) return; img_pixel_t *tl = img.pixels; img_pixel_t *tr = img.pixels + img.width - 1; img_pixel_t *bl = tl + (img.height - 1) * img.stride; img_pixel_t *br = tr + (img.height - 1) * img.stride; for(int y=0; y < img.height >> 1; y++) { for(int x=y, dx=0, dy=0; x < img.width-1 - y; x++, dx++, dy+=img.stride) { int swp = tl[dx]; tl[dx] = bl[-dy]; bl[-dy] = br[-dx]; br[-dx] = tr[dy]; tr[dy] = swp; } tl += img.stride + 1; tr += img.stride - 1; bl -= img.stride - 1; br -= img.stride + 1; } } static void img_rotate_ip180(img_t img) { img_pixel_t *tl = img.pixels; img_pixel_t *br = tl + (img.height - 1) * img.stride + img.width - 1; for(int y = 0; y < (img.height+1) >> 1; y++) { /* If both pointers reach the same line (height is odd), we must stop at half of the width */ int limit = img.width; if(tl+img.stride-1 == br) limit >>= 1; for(int x = 0; x < limit; x++) { int swp = tl[x]; tl[x] = br[-x]; br[-x] = swp; } tl += img.stride; br -= img.stride; } } static void img_rotate_ip270(img_t img) { /* Same as img_rotate_ip90, except for the order of assignments */ if(img.width != img.height) return; img_pixel_t *tl = img.pixels; img_pixel_t *tr = img.pixels + img.width - 1; img_pixel_t *bl = tl + (img.height - 1) * img.stride; img_pixel_t *br = tr + (img.height - 1) * img.stride; for(int y=0; y < img.height >> 1; y++) { for(int x=y, dx=0, dy=0; x < img.width-1 - y; x++, dx++, dy+=img.stride) { /* Only difference with img_rotate_ip90 */ int swp = tl[dx]; tl[dx] = tr[dy]; tr[dy] = br[-dx]; br[-dx] = bl[-dy]; bl[-dy] = swp; } tl += img.stride + 1; tr += img.stride - 1; bl -= img.stride - 1; br -= img.stride + 1; } } void img_rotate_inplace(img_t img, int angle) { if(angle == 90) img_rotate_ip90(img); if(angle == 180) img_rotate_ip180(img); if(angle == 270) img_rotate_ip270(img); }