SDL_image: stb_image takes precedence over other libraries when requested

From 86eea9ad1563928f6db216749b1f38a1eb52bffe Mon Sep 17 00:00:00 2001
From: Sam Lantinga <[EMAIL REDACTED]>
Date: Tue, 10 May 2022 09:39:05 -0700
Subject: [PATCH] stb_image takes precedence over other libraries when
 requested

---
 IMG_ImageIO.m |  8 ++++++
 IMG_jpg.c     | 41 +++++++++++++++------------
 IMG_png.c     | 76 +++++++++++++++++++++++++++------------------------
 3 files changed, 73 insertions(+), 52 deletions(-)

diff --git a/IMG_ImageIO.m b/IMG_ImageIO.m
index 5c58f22..0d790f1 100644
--- a/IMG_ImageIO.m
+++ b/IMG_ImageIO.m
@@ -368,6 +368,8 @@ void IMG_QuitJPG()
 
 #endif /* JPG_USES_IMAGEIO */
 
+#ifdef PNG_USES_IMAGEIO
+
 int IMG_InitPNG()
 {
     return 0;
@@ -377,6 +379,8 @@ void IMG_QuitPNG()
 {
 }
 
+#endif /* PNG_USES_IMAGEIO */
+
 int IMG_InitTIF()
 {
     return 0;
@@ -599,11 +603,15 @@ int IMG_isJPG(SDL_RWops *src)
 
 #endif /* JPG_USES_IMAGEIO */
 
+#ifdef PNG_USES_IMAGEIO
+
 int IMG_isPNG(SDL_RWops *src)
 {
     return Internal_isType(src, kUTTypePNG);
 }
 
+#endif /* PNG_USES_IMAGEIO */
+
 // This isn't a public API function. Apple seems to be able to identify tga's.
 int IMG_isTGA(SDL_RWops *src)
 {
diff --git a/IMG_jpg.c b/IMG_jpg.c
index 75b7680..9f5badd 100644
--- a/IMG_jpg.c
+++ b/IMG_jpg.c
@@ -26,7 +26,15 @@
 #include <stdio.h>
 #include <setjmp.h>
 
-#if defined(SDL_IMAGE_USE_COMMON_BACKEND)
+
+/* We'll have JPG save support by default */
+#ifndef SAVE_JPG
+#define SAVE_JPG    1
+#endif
+
+#if defined(USE_STBIMAGE)
+#undef WANT_JPEGLIB
+#elif defined(SDL_IMAGE_USE_COMMON_BACKEND)
 #define WANT_JPEGLIB
 #elif defined(SDL_IMAGE_USE_WIC_BACKEND)
 #undef WANT_JPEGLIB
@@ -36,10 +44,10 @@
 #define WANT_JPEGLIB
 #endif
 
-#ifdef WANT_JPEGLIB
-
 #ifdef LOAD_JPG
 
+#ifdef WANT_JPEGLIB
+
 #define USE_JPEGLIB
 
 #include <jpeglib.h>
@@ -640,6 +648,8 @@ SDL_Surface *IMG_LoadJPG_RW(SDL_RWops *src)
     return IMG_LoadSTB_RW(src);
 }
 
+#endif /* WANT_JPEGLIB */
+
 #else
 #if _MSC_VER >= 1300
 #pragma warning(disable : 4100) /* warning C4100: 'op' : unreferenced formal parameter */
@@ -669,14 +679,7 @@ SDL_Surface *IMG_LoadJPG_RW(SDL_RWops *src)
 
 #endif /* LOAD_JPG */
 
-#endif /* WANT_JPEGLIB */
-
-/* We'll always have JPG save support */
-#define SAVE_JPG
-
-#ifdef SAVE_JPG
-
-#if !defined(USE_JPEGLIB) && defined(USE_TINYJPEG)
+#if SAVE_JPG
 
 #ifdef __WATCOMC__ /* watcom has issues.. */
 #define ceilf ceil
@@ -754,7 +757,7 @@ static int IMG_SaveJPG_RW_tinyjpeg(SDL_Surface *surface, SDL_RWops *dst, int fre
     return result;
 }
 
-#endif /* !defined(USE_JPEGLIB) && defined(USE_TINYJPEG) */
+#endif /* SAVE_JPG */
 
 int IMG_SaveJPG(SDL_Surface *surface, const char *file, int quality)
 {
@@ -768,13 +771,17 @@ int IMG_SaveJPG(SDL_Surface *surface, const char *file, int quality)
 
 int IMG_SaveJPG_RW(SDL_Surface *surface, SDL_RWops *dst, int freedst, int quality)
 {
+#if SAVE_JPG
 #ifdef USE_JPEGLIB
-    return IMG_SaveJPG_RW_jpeglib(surface, dst, freedst, quality);
-#elif USE_TINYJPEG
+    if ((IMG_Init(IMG_INIT_JPG) & IMG_INIT_JPG) != 0) {
+        if (IMG_SaveJPG_RW_jpeglib(surface, dst, freedst, quality) == 0) {
+            return 0;
+        }
+    }
+#endif
     return IMG_SaveJPG_RW_tinyjpeg(surface, dst, freedst, quality);
+
 #else
-    return IMG_SetError("SDL_image not built with jpeglib/tinyjpeg, saving not supported");
+    return IMG_SetError("SDL_image built without JPEG save support");
 #endif
 }
-
-#endif /* SAVE_JPG */
diff --git a/IMG_png.c b/IMG_png.c
index d4a45c4..1ba1c8e 100644
--- a/IMG_png.c
+++ b/IMG_png.c
@@ -23,14 +23,28 @@
 
 #include "SDL_image.h"
 
-#if !defined(SDL_IMAGE_SAVE_PNG)
-#  define SDL_IMAGE_SAVE_PNG 1
+
+/* We'll have PNG save support by default */
+#ifndef SAVE_PNG
+#define SAVE_PNG    1
 #endif
 
-#if !(defined(__APPLE__) || defined(SDL_IMAGE_USE_WIC_BACKEND)) || defined(SDL_IMAGE_USE_COMMON_BACKEND)
+#if defined(USE_STBIMAGE)
+#undef WANT_LIBPNG
+#elif defined(SDL_IMAGE_USE_COMMON_BACKEND)
+#define WANT_LIBPNG
+#elif defined(SDL_IMAGE_USE_WIC_BACKEND)
+#undef WANT_LIBPNG
+#elif defined(__APPLE__) && defined(PNG_USES_IMAGEIO)
+#undef WANT_LIBPNG
+#else
+#define WANT_LIBPNG
+#endif
 
 #ifdef LOAD_PNG
 
+#ifdef WANT_LIBPNG
+
 #define USE_LIBPNG
 
 /* This code was originally written by Philippe Lavoie (2 November 1998) */
@@ -496,6 +510,8 @@ SDL_Surface *IMG_LoadPNG_RW(SDL_RWops *src)
     return IMG_LoadSTB_RW(src);
 }
 
+#endif /* WANT_LIBPNG */
+
 #else
 #if _MSC_VER >= 1300
 #pragma warning(disable : 4100) /* warning C4100: 'op' : unreferenced formal parameter */
@@ -525,19 +541,7 @@ SDL_Surface *IMG_LoadPNG_RW(SDL_RWops *src)
 
 #endif /* LOAD_PNG */
 
-#endif /* !defined(__APPLE__) || defined(SDL_IMAGE_USE_COMMON_BACKEND) */
-
-#if SDL_IMAGE_SAVE_PNG
-
-int IMG_SavePNG(SDL_Surface *surface, const char *file)
-{
-    SDL_RWops *dst = SDL_RWFromFile(file, "wb");
-    if (dst) {
-        return IMG_SavePNG_RW(surface, dst, 1);
-    } else {
-        return -1;
-    }
-}
+#if SAVE_PNG
 
 #if SDL_BYTEORDER == SDL_LIL_ENDIAN
 static const Uint32 png_format = SDL_PIXELFORMAT_ABGR8888;
@@ -727,30 +731,32 @@ static int IMG_SavePNG_RW_miniz(SDL_Surface *surface, SDL_RWops *dst, int freeds
     return result;
 }
 
-int IMG_SavePNG_RW(SDL_Surface *surface, SDL_RWops *dst, int freedst)
-{
-    static int (*rw_func)(SDL_Surface *surface, SDL_RWops *dst, int freedst);
+#endif /* SAVE_PNG */
 
-    if (!rw_func)
-    {
-#ifdef USE_LIBPNG
-        if (IMG_Init(IMG_INIT_PNG)) {
-            rw_func = IMG_SavePNG_RW_libpng;
-        } else
-#endif
-            rw_func = IMG_SavePNG_RW_miniz;
-    }
-
-    return rw_func(surface, dst, freedst);
-}
-#else
 int IMG_SavePNG(SDL_Surface *surface, const char *file)
 {
-    return SDL_Unsupported();
+    SDL_RWops *dst = SDL_RWFromFile(file, "wb");
+    if (dst) {
+        return IMG_SavePNG_RW(surface, dst, 1);
+    } else {
+        return -1;
+    }
 }
 
 int IMG_SavePNG_RW(SDL_Surface *surface, SDL_RWops *dst, int freedst)
 {
-    return SDL_Unsupported();
+#if SAVE_PNG
+#ifdef USE_LIBPNG
+    if ((IMG_Init(IMG_INIT_PNG) & IMG_INIT_PNG) != 0) {
+        if (IMG_SavePNG_RW_libpng(surface, dst, freedst) == 0) {
+            return 0;
+        }
+    }
+#endif
+    return IMG_SavePNG_RW_miniz(surface, dst, freedst);
+
+#else
+    return IMG_SetError("SDL_image built without PNG save support");
+
+#endif /* SAVE_PNG */
 }
-#endif /* SDL_IMAGE_SAVE_PNG */