diff --git a/SimpleImageViewer.c b/SimpleImageViewer.c index 2d9479d..e1f1e19 100644 --- a/SimpleImageViewer.c +++ b/SimpleImageViewer.c @@ -20,6 +20,8 @@ typedef struct Image{ int y; int channels; unsigned char* pixels; + SDL_Surface* surface; + SDL_Texture* texture; } Image; typedef struct{ @@ -27,13 +29,13 @@ typedef struct{ int h; } window_size_delta; -Image load_image(const char* filepath){ +Image load_image_pixels_from_file(const char* filepath){ Image image; image.pixels = stbi_load(filepath, &image.x, &image.y, &image.channels, DESIRED_IMAGE_CHANNELS); return image; } -void free_image_buffer(Image* image){ +void free_image_pixels_buffer(Image* image){ if(image->pixels) stbi_image_free(image->pixels); image->pixels = NULL; } @@ -66,8 +68,10 @@ SDL_Window* create_window(const char* title, int w, int h){ return window; } -SDL_Surface* create_image_surface(SDL_Surface* surface, Image* image){ - SDL_Surface* image_surface = SDL_CreateSurface(image->x, image->y, SDL_PIXELFORMAT_RGBA32); +void populate_image(SDL_Window* window, Image* image){ + SDL_Surface* surface = SDL_GetWindowSurface(window); + image->surface = SDL_CreateSurface(image->x, image->y, SDL_PIXELFORMAT_RGBA32); + SDL_Rect pixel = { 0, 0, 1, 1 }; int center_x = ((surface->w + 1) / 2 - 1); @@ -82,20 +86,20 @@ SDL_Surface* create_image_surface(SDL_Surface* surface, Image* image){ pixel.y = dst_y + y; const int current_pixel_idx = (y * image->x + x) * DESIRED_IMAGE_CHANNELS; - Uint32 color = SDL_MapSurfaceRGBA(image_surface, + Uint32 color = SDL_MapSurfaceRGBA(image->surface, image->pixels[current_pixel_idx + 0], image->pixels[current_pixel_idx + 1], image->pixels[current_pixel_idx + 2], image->pixels[current_pixel_idx + 3]); - SDL_FillSurfaceRect(image_surface, &pixel, color); + SDL_FillSurfaceRect(image->surface, &pixel, color); } } - return image_surface; + image->texture = SDL_CreateTextureFromSurface(SDL_GetRenderer(window), image->surface); } -void draw_image(SDL_Window* window, SDL_Surface* image_surface, Image* image, float pixel_size_delta, int image_start_x, int image_start_y){ +void draw_image(SDL_Window* window, Image* image, float pixel_size_delta, int image_start_x, int image_start_y){ SDL_Surface* surface = SDL_GetWindowSurface(window); float pixel_size = pixel_size_delta; @@ -105,13 +109,14 @@ void draw_image(SDL_Window* window, SDL_Surface* image_surface, Image* image, fl Uint64 start = SDL_GetTicksNS(); - SDL_Rect dst = { center_x - (image->x * pixel_size / 2) + image_start_x, center_y - (image->y * pixel_size / 2) + image_start_y, image->x * pixel_size, image->y * pixel_size }; - SDL_ClearSurface(surface, 0, 0, 0, 255); - SDL_BlitSurfaceScaled(image_surface, NULL, surface, &dst, SDL_SCALEMODE_LINEAR); - + SDL_FRect dst = { center_x - (image->x * pixel_size / 2) + image_start_x, center_y - (image->y * pixel_size / 2) + image_start_y, image->x * pixel_size, image->y * pixel_size }; + SDL_Renderer* renderer = SDL_GetRenderer(window); + SDL_RenderClear(renderer); + SDL_RenderTexture(renderer, image->texture, NULL, &dst); + SDL_RenderPresent(renderer); + printf("Redraw time: %.3fms\n", (SDL_GetTicksNS() - start) / 1000000.0); - SDL_UpdateWindowSurface(window); } int clamp(const int in, const int low, const int high){ @@ -152,7 +157,7 @@ void on_wheel(SDL_Event* event, SDL_Window* window){ SDL_SetWindowSize(window, new_w, new_h); } -void loop(SDL_Window* window, SDL_Surface* image_surface, Image* image){ +void loop(SDL_Window* window, Image* image){ bool drag_left_mouse = false; bool drag_right_mouse = false; int last_pointer_x = 0; @@ -221,7 +226,7 @@ void loop(SDL_Window* window, SDL_Surface* image_surface, Image* image){ if(redraw){ redraw = false; - draw_image(window, image_surface, image, pixel_size_delta, current_image_start_x, current_image_start_y); + draw_image(window, image, pixel_size_delta, current_image_start_x, current_image_start_y); } } } @@ -239,7 +244,7 @@ int main(int argc, char** argv){ exit(2); } - Image image = load_image(filepath); + Image image = load_image_pixels_from_file(filepath); if(image.pixels == NULL){ printf("Failed to load image!"); exit(3); @@ -257,15 +262,14 @@ int main(int argc, char** argv){ exit(5); } - SDL_Surface* image_surface = create_image_surface(surface, &image); - free_image_buffer(&image); + populate_image(window, &image); + free_image_pixels_buffer(&image); - draw_image(window, image_surface, &image, 1.0f, 0, 0); + draw_image(window, &image, 1.0f, 0, 0); - SDL_UpdateWindowSurface(window); + loop(window, &image); - loop(window, image_surface, &image); - - SDL_DestroySurface(image_surface); + SDL_DestroyTexture(image.texture); + SDL_DestroySurface(image.surface); SDL_DestroyWindow(window); } \ No newline at end of file