textures_image_processing.c 6.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184
  1. /*******************************************************************************************
  2. *
  3. * raylib [textures] example - Image processing
  4. *
  5. * NOTE: Images are loaded in CPU memory (RAM); textures are loaded in GPU memory (VRAM)
  6. *
  7. * This example has been created using raylib 1.4 (www.raylib.com)
  8. * raylib is licensed under an unmodified zlib/libpng license (View raylib.h for details)
  9. *
  10. * Copyright (c) 2016 Ramon Santamaria (@raysan5)
  11. *
  12. ********************************************************************************************/
  13. #include "raylib.h"
  14. #include <stdlib.h> // Required for: free()
  15. #if defined(PLATFORM_WEB)
  16. #include <emscripten/emscripten.h>
  17. #endif
  18. #define NUM_PROCESSES 8
  19. //----------------------------------------------------------------------------------
  20. // Global Variables Definition
  21. //----------------------------------------------------------------------------------
  22. int screenWidth = 800;
  23. int screenHeight = 450;
  24. typedef enum {
  25. NONE = 0,
  26. COLOR_GRAYSCALE,
  27. COLOR_TINT,
  28. COLOR_INVERT,
  29. COLOR_CONTRAST,
  30. COLOR_BRIGHTNESS,
  31. FLIP_VERTICAL,
  32. FLIP_HORIZONTAL
  33. } ImageProcess;
  34. static const char *processText[] = {
  35. "NO PROCESSING",
  36. "COLOR GRAYSCALE",
  37. "COLOR TINT",
  38. "COLOR INVERT",
  39. "COLOR CONTRAST",
  40. "COLOR BRIGHTNESS",
  41. "FLIP VERTICAL",
  42. "FLIP HORIZONTAL"
  43. };
  44. Image image;
  45. Texture2D texture;
  46. int currentProcess = NONE;
  47. bool textureReload = false;
  48. Rectangle selectRecs[NUM_PROCESSES];
  49. //----------------------------------------------------------------------------------
  50. // Module Functions Declaration
  51. //----------------------------------------------------------------------------------
  52. void UpdateDrawFrame(void); // Update and Draw one frame
  53. //----------------------------------------------------------------------------------
  54. // Main Enry Point
  55. //----------------------------------------------------------------------------------
  56. int main()
  57. {
  58. // Initialization
  59. //--------------------------------------------------------------------------------------
  60. InitWindow(screenWidth, screenHeight, "raylib [textures] example - image processing");
  61. // NOTE: Textures MUST be loaded after Window initialization (OpenGL context is required)
  62. image = LoadImage("resources/parrots.png"); // Loaded in CPU memory (RAM)
  63. ImageFormat(&image, UNCOMPRESSED_R8G8B8A8); // Format image to RGBA 32bit (required for texture update)
  64. texture = LoadTextureFromImage(image); // Image converted to texture, GPU memory (VRAM)
  65. for (int i = 0; i < NUM_PROCESSES; i++) selectRecs[i] = (Rectangle){ 40, 50 + 32*i, 150, 30 };
  66. #if defined(PLATFORM_WEB)
  67. emscripten_set_main_loop(UpdateDrawFrame, 0, 1);
  68. #else
  69. SetTargetFPS(60); // Set our game to run at 60 frames-per-second
  70. //--------------------------------------------------------------------------------------
  71. // Main game loop
  72. while (!WindowShouldClose()) // Detect window close button or ESC key
  73. {
  74. UpdateDrawFrame();
  75. }
  76. #endif
  77. // De-Initialization
  78. //--------------------------------------------------------------------------------------
  79. UnloadTexture(texture); // Unload texture from VRAM
  80. UnloadImage(image); // Unload image from RAM
  81. CloseWindow(); // Close window and OpenGL context
  82. //--------------------------------------------------------------------------------------
  83. return 0;
  84. }
  85. //----------------------------------------------------------------------------------
  86. // Module Functions Definition
  87. //----------------------------------------------------------------------------------
  88. void UpdateDrawFrame(void)
  89. {
  90. // Update
  91. //----------------------------------------------------------------------------------
  92. if (IsKeyPressed(KEY_DOWN))
  93. {
  94. currentProcess++;
  95. if (currentProcess > 7) currentProcess = 0;
  96. textureReload = true;
  97. }
  98. else if (IsKeyPressed(KEY_UP))
  99. {
  100. currentProcess--;
  101. if (currentProcess < 0) currentProcess = 7;
  102. textureReload = true;
  103. }
  104. if (textureReload)
  105. {
  106. UnloadImage(image); // Unload current image data
  107. image = LoadImage("resources/parrots.png"); // Re-load image data
  108. // NOTE: Image processing is a costly CPU process to be done every frame,
  109. // If image processing is required in a frame-basis, it should be done
  110. // with a texture and by shaders
  111. switch (currentProcess)
  112. {
  113. case COLOR_GRAYSCALE: ImageColorGrayscale(&image); break;
  114. case COLOR_TINT: ImageColorTint(&image, GREEN); break;
  115. case COLOR_INVERT: ImageColorInvert(&image); break;
  116. case COLOR_CONTRAST: ImageColorContrast(&image, -40); break;
  117. case COLOR_BRIGHTNESS: ImageColorBrightness(&image, -80); break;
  118. case FLIP_VERTICAL: ImageFlipVertical(&image); break;
  119. case FLIP_HORIZONTAL: ImageFlipHorizontal(&image); break;
  120. default: break;
  121. }
  122. Color *pixels = GetImageData(image); // Get pixel data from image (RGBA 32bit)
  123. UpdateTexture(texture, pixels); // Update texture with new image data
  124. free(pixels); // Unload pixels data from RAM
  125. textureReload = false;
  126. }
  127. //----------------------------------------------------------------------------------
  128. // Draw
  129. //----------------------------------------------------------------------------------
  130. BeginDrawing();
  131. ClearBackground(RAYWHITE);
  132. DrawText("IMAGE PROCESSING:", 40, 30, 10, DARKGRAY);
  133. // Draw rectangles
  134. for (int i = 0; i < NUM_PROCESSES; i++)
  135. {
  136. if (i == currentProcess)
  137. {
  138. DrawRectangleRec(selectRecs[i], SKYBLUE);
  139. DrawRectangleLines(selectRecs[i].x, selectRecs[i].y, selectRecs[i].width, selectRecs[i].height, BLUE);
  140. DrawText(processText[i], selectRecs[i].x + selectRecs[i].width/2 - MeasureText(processText[i], 10)/2, selectRecs[i].y + 11, 10, DARKBLUE);
  141. }
  142. else
  143. {
  144. DrawRectangleRec(selectRecs[i], LIGHTGRAY);
  145. DrawRectangleLines(selectRecs[i].x, selectRecs[i].y, selectRecs[i].width, selectRecs[i].height, GRAY);
  146. DrawText(processText[i], selectRecs[i].x + selectRecs[i].width/2 - MeasureText(processText[i], 10)/2, selectRecs[i].y + 11, 10, DARKGRAY);
  147. }
  148. }
  149. DrawTexture(texture, screenWidth - texture.width - 60, screenHeight/2 - texture.height/2, WHITE);
  150. DrawRectangleLines(screenWidth - texture.width - 60, screenHeight/2 - texture.height/2, texture.width, texture.height, BLACK);
  151. EndDrawing();
  152. //----------------------------------------------------------------------------------
  153. }