Load the image in a separate thread
This commit is contained in:
		
							
								
								
									
										1
									
								
								compile
									
									
									
									
									
								
							
							
						
						
									
										1
									
								
								compile
									
									
									
									
									
								
							@@ -9,6 +9,7 @@ INCLUDES="\
 | 
			
		||||
"
 | 
			
		||||
LIBS="\
 | 
			
		||||
	-lm \
 | 
			
		||||
	-pthread \
 | 
			
		||||
	$(pkg-config --libs sdl2) \
 | 
			
		||||
"
 | 
			
		||||
SRC="\
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										59
									
								
								src/main.c
									
									
									
									
									
								
							
							
						
						
									
										59
									
								
								src/main.c
									
									
									
									
									
								
							@@ -8,6 +8,7 @@
 | 
			
		||||
#include <SDL2/SDL_surface.h>
 | 
			
		||||
#include <SDL2/SDL_video.h>
 | 
			
		||||
#include <netinet/in.h>
 | 
			
		||||
#include <pthread.h>
 | 
			
		||||
#include <stdbool.h>
 | 
			
		||||
#include <stdio.h>
 | 
			
		||||
#include <stdlib.h>
 | 
			
		||||
@@ -32,8 +33,13 @@ struct point {
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
internal void write_debug_ppm6(const Image *img);
 | 
			
		||||
internal SDL_Texture *image_to_texture(SDL_Renderer *renderer,
 | 
			
		||||
                                       const Image *img);
 | 
			
		||||
internal void *load_tiff_image(void *args);
 | 
			
		||||
 | 
			
		||||
typedef struct img_thread_args ImgThreadArgs;
 | 
			
		||||
struct img_thread_args {
 | 
			
		||||
  const char *filename;
 | 
			
		||||
  Arena *arena;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
int main(int argc, char *argv[]) {
 | 
			
		||||
  int exit_code = EXIT_SUCCESS;
 | 
			
		||||
@@ -45,14 +51,13 @@ int main(int argc, char *argv[]) {
 | 
			
		||||
 | 
			
		||||
  const char *file_to_open = argc > 1 ? argv[1] : "./resources/test.tif";
 | 
			
		||||
 | 
			
		||||
  Image *img = read_baseline_tiff(file_to_open, arena);
 | 
			
		||||
  if (!img) {
 | 
			
		||||
  pthread_t img_thread;
 | 
			
		||||
  ImgThreadArgs args = {.filename = file_to_open, .arena = arena};
 | 
			
		||||
  if (pthread_create(&img_thread, NULL, load_tiff_image, &args) != 0) {
 | 
			
		||||
    exit_code = EXIT_FAILURE;
 | 
			
		||||
    goto MAIN_DESTROY_ARENA;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  write_debug_ppm6(img);
 | 
			
		||||
 | 
			
		||||
  if (SDL_Init(SDL_INIT_EVERYTHING) != 0) {
 | 
			
		||||
    exit_code = EXIT_FAILURE;
 | 
			
		||||
    goto MAIN_DESTROY_ARENA;
 | 
			
		||||
@@ -73,17 +78,23 @@ int main(int argc, char *argv[]) {
 | 
			
		||||
    goto MAIN_DESTROY_WINDOW;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  SDL_Texture *texture = image_to_texture(renderer, img);
 | 
			
		||||
  if (!texture) {
 | 
			
		||||
  SDL_Surface *surface = NULL;
 | 
			
		||||
  if (pthread_join(img_thread, (void **)&surface) != 0 || !surface) {
 | 
			
		||||
    exit_code = EXIT_FAILURE;
 | 
			
		||||
    goto MAIN_DESTROY_RENDERER;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  SDL_Texture *texture = SDL_CreateTextureFromSurface(renderer, surface);
 | 
			
		||||
  if (!texture) {
 | 
			
		||||
    exit_code = EXIT_FAILURE;
 | 
			
		||||
    goto MAIN_DESTROY_SURFACE;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  SDL_Rect dest = {
 | 
			
		||||
      .h = img->height,
 | 
			
		||||
      .w = img->width,
 | 
			
		||||
      .x = (WINDOW_WIDTH - img->width) / 2,
 | 
			
		||||
      .y = (WINDOW_HEIGHT - img->height) / 2,
 | 
			
		||||
      .h = surface->h,
 | 
			
		||||
      .w = surface->w,
 | 
			
		||||
      .x = (WINDOW_WIDTH - surface->w) / 2,
 | 
			
		||||
      .y = (WINDOW_HEIGHT - surface->h) / 2,
 | 
			
		||||
  };
 | 
			
		||||
 | 
			
		||||
  bool running = true;
 | 
			
		||||
@@ -110,6 +121,9 @@ int main(int argc, char *argv[]) {
 | 
			
		||||
 | 
			
		||||
  SDL_DestroyTexture(texture);
 | 
			
		||||
 | 
			
		||||
MAIN_DESTROY_SURFACE:
 | 
			
		||||
  SDL_FreeSurface(surface);
 | 
			
		||||
 | 
			
		||||
MAIN_DESTROY_RENDERER:
 | 
			
		||||
  SDL_DestroyRenderer(renderer);
 | 
			
		||||
 | 
			
		||||
@@ -146,17 +160,19 @@ internal void write_debug_ppm6(const Image *img) {
 | 
			
		||||
  fclose(out);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
internal SDL_Texture *image_to_texture(SDL_Renderer *renderer,
 | 
			
		||||
                                       const Image *img) {
 | 
			
		||||
  SDL_Texture *output = NULL;
 | 
			
		||||
  if (!renderer || !img) {
 | 
			
		||||
    goto IMAGE_TO_TEXTURE_RETURN;
 | 
			
		||||
internal void *load_tiff_image(void *args) {
 | 
			
		||||
  ImgThreadArgs *img_args = (ImgThreadArgs *)args;
 | 
			
		||||
  Image *img = read_baseline_tiff(img_args->filename, img_args->arena);
 | 
			
		||||
  if (!img) {
 | 
			
		||||
    return NULL;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  write_debug_ppm6(img);
 | 
			
		||||
 | 
			
		||||
  SDL_Surface *surface = SDL_CreateRGBSurface(0, img->width, img->height, 32,
 | 
			
		||||
                                              RMASK, GMASK, BMASK, AMASK);
 | 
			
		||||
  if (!surface) {
 | 
			
		||||
    goto IMAGE_TO_TEXTURE_RETURN;
 | 
			
		||||
    return NULL;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  SDL_LockSurface(surface);
 | 
			
		||||
@@ -170,10 +186,5 @@ internal SDL_Texture *image_to_texture(SDL_Renderer *renderer,
 | 
			
		||||
  }
 | 
			
		||||
  SDL_UnlockSurface(surface);
 | 
			
		||||
 | 
			
		||||
  output = SDL_CreateTextureFromSurface(renderer, surface);
 | 
			
		||||
 | 
			
		||||
  SDL_FreeSurface(surface);
 | 
			
		||||
 | 
			
		||||
IMAGE_TO_TEXTURE_RETURN:
 | 
			
		||||
  return output;
 | 
			
		||||
  return surface;
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user