IMG_svg.c
author Ozkan Sezer <sezeroz@gmail.com>
Thu, 18 Oct 2018 11:57:19 +0300
changeset 612 ca95d0e31aec
parent 584 8fee51506499
child 638 e3e9d7430674
permissions -rw-r--r--
use less ancient versions of autofoo scripts
     1 /*
     2   SDL_image:  An example image loading library for use with SDL
     3   Copyright (C) 1997-2018 Sam Lantinga <slouken@libsdl.org>
     4 
     5   This software is provided 'as-is', without any express or implied
     6   warranty.  In no event will the authors be held liable for any damages
     7   arising from the use of this software.
     8 
     9   Permission is granted to anyone to use this software for any purpose,
    10   including commercial applications, and to alter it and redistribute it
    11   freely, subject to the following restrictions:
    12 
    13   1. The origin of this software must not be misrepresented; you must not
    14      claim that you wrote the original software. If you use this software
    15      in a product, an acknowledgment in the product documentation would be
    16      appreciated but is not required.
    17   2. Altered source versions must be plainly marked as such, and must not be
    18      misrepresented as being the original software.
    19   3. This notice may not be removed or altered from any source distribution.
    20 */
    21 
    22 /* This is an SVG image file loading framework, based on Nano SVG:
    23  * https://github.com/memononen/nanosvg
    24  */
    25 
    26 #include "SDL_image.h"
    27 
    28 #ifdef LOAD_SVG
    29 
    30 /* Replace C runtime functions with SDL C runtime functions for building on Windows */
    31 #define acosf   SDL_acosf
    32 #define atan2f  SDL_atan2f
    33 #define cosf    SDL_cosf
    34 #define ceilf   SDL_ceilf
    35 #define fabs    SDL_fabs
    36 #define fabsf   SDL_fabsf
    37 #define floorf  SDL_floorf
    38 #define fmodf   SDL_fmodf
    39 #define free    SDL_free
    40 #define malloc  SDL_malloc
    41 #undef memcpy
    42 #define memcpy  SDL_memcpy
    43 #undef memset
    44 #define memset  SDL_memset
    45 #define pow     SDL_pow
    46 #define qsort   SDL_qsort
    47 #define realloc SDL_realloc
    48 #define sinf    SDL_sinf
    49 #define sqrt    SDL_sqrt
    50 #define sqrtf   SDL_sqrtf
    51 #define sscanf  SDL_sscanf
    52 #undef strchr
    53 #define strchr  SDL_strchr
    54 #undef strcmp
    55 #define strcmp  SDL_strcmp
    56 #undef strncmp
    57 #define strncmp SDL_strncmp
    58 #undef strncpy
    59 #define strncpy SDL_strlcpy
    60 #define strlen  SDL_strlen
    61 #define strstr  SDL_strstr
    62 #define strtol  SDL_strtol
    63 #define strtoll SDL_strtoll
    64 #define tanf    SDL_tanf
    65 #ifndef FLT_MAX
    66 #define FLT_MAX     3.402823466e+38F
    67 #endif
    68 #undef HAVE_STDIO_H
    69 
    70 #define NANOSVG_IMPLEMENTATION
    71 #include "nanosvg.h"
    72 #define NANOSVGRAST_IMPLEMENTATION
    73 #include "nanosvgrast.h"
    74 
    75 /* See if an image is contained in a data source */
    76 int IMG_isSVG(SDL_RWops *src)
    77 {
    78     Sint64 start;
    79     int is_SVG;
    80     char magic[4096];
    81     size_t magic_len;
    82 
    83     if ( !src )
    84         return 0;
    85     start = SDL_RWtell(src);
    86     is_SVG = 0;
    87     magic_len = SDL_RWread(src, magic, 1, sizeof(magic) - 1);
    88     magic[magic_len] = '\0';
    89     if ( SDL_strstr(magic, "<svg") ) {
    90         is_SVG = 1;
    91     }
    92     SDL_RWseek(src, start, RW_SEEK_SET);
    93     return(is_SVG);
    94 }
    95 
    96 /* Load a SVG type image from an SDL datasource */
    97 SDL_Surface *IMG_LoadSVG_RW(SDL_RWops *src)
    98 {
    99     char *data;
   100     struct NSVGimage *image;
   101     struct NSVGrasterizer *rasterizer;
   102     SDL_Surface *surface = NULL;
   103     float scale = 1.0f;
   104 
   105     data = (char *)SDL_LoadFile_RW(src, NULL, SDL_FALSE);
   106     if ( !data ) {
   107         return NULL;
   108     }
   109 
   110     /* For now just use default units of pixels at 96 DPI */
   111     image = nsvgParse(data, "px", 96.0f);
   112     SDL_free(data);
   113     if ( !image ) {
   114         IMG_SetError("Couldn't parse SVG image");
   115         return NULL;
   116     }
   117 
   118     rasterizer = nsvgCreateRasterizer();
   119     if ( !rasterizer ) {
   120         IMG_SetError("Couldn't create SVG rasterizer");
   121         nsvgDelete( image );
   122         return NULL;
   123     }
   124 
   125     surface = SDL_CreateRGBSurface(SDL_SWSURFACE,
   126                                    (int)(image->width * scale),
   127                                    (int)(image->height * scale),
   128                                    32,
   129                                    0x000000FF,
   130                                    0x0000FF00,
   131                                    0x00FF0000,
   132                                    0xFF000000);
   133     if ( !surface ) {
   134         nsvgDeleteRasterizer( rasterizer );
   135         nsvgDelete( image );
   136         return NULL;
   137     }
   138 
   139     nsvgRasterize(rasterizer, image, 0.0f, 0.0f, scale, (unsigned char *)surface->pixels, surface->w, surface->h, surface->pitch);
   140     nsvgDeleteRasterizer( rasterizer );
   141     nsvgDelete( image );
   142 
   143     return surface;
   144 }
   145 
   146 #else
   147 
   148 /* See if an image is contained in a data source */
   149 int IMG_isSVG(SDL_RWops *src)
   150 {
   151     return(0);
   152 }
   153 
   154 /* Load a SVG type image from an SDL datasource */
   155 SDL_Surface *IMG_LoadSVG_RW(SDL_RWops *src)
   156 {
   157     return(NULL);
   158 }
   159 
   160 #endif /* LOAD_SVG */