Image: Swap stb for libpng/libjpeg

This commit is contained in:
Stenzek 2024-03-06 16:24:25 +10:00
parent e9c4416272
commit c854b8f85e
No known key found for this signature in database
19 changed files with 255 additions and 12273 deletions

View file

@ -358,6 +358,78 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
</pre> </pre>
<h3>libjpeg - <a href="https://ijg.org/">https://ijg.org/</a></h3>
<pre>
The authors make NO WARRANTY or representation, either express or implied,
with respect to this software, its quality, accuracy, merchantability, or
fitness for a particular purpose. This software is provided "AS IS", and you,
its user, assume the entire risk as to its quality and accuracy.
This software is copyright (C) 1991-2024, Thomas G. Lane, Guido Vollbeding.
All Rights Reserved except as specified below.
Permission is hereby granted to use, copy, modify, and distribute this
software (or portions thereof) for any purpose, without fee, subject to these
conditions:
(1) If any part of the source code for this software is distributed, then this
README file must be included, with this copyright and no-warranty notice
unaltered; and any additions, deletions, or changes to the original files
must be clearly indicated in accompanying documentation.
(2) If only executable code is distributed, then the accompanying
documentation must state that "this software is based in part on the work of
the Independent JPEG Group".
(3) Permission for use of this software is granted only if the user accepts
full responsibility for any undesirable consequences; the authors accept
NO LIABILITY for damages of any kind.
These conditions apply to any software derived from or based on the IJG code,
not just to the unmodified library. If you use our work, you ought to
acknowledge us.
Permission is NOT granted for the use of any IJG author's name or company name
in advertising or publicity relating to this software or products derived from
it. This software may be referred to only as "the Independent JPEG Group's
software".
We specifically permit and encourage the use of this software as the basis of
commercial products, provided that all warranty or liability claims are
assumed by the product vendor.
</pre>
<h3>libpng - <a href="http://www.libpng.org/pub/png/libpng.html">http://www.libpng.org/pub/png/libpng.html</a></h3>
<pre>
* Copyright (c) 1995-2024 The PNG Reference Library Authors.
* Copyright (c) 2018-2024 Cosmin Truta.
* Copyright (c) 2000-2002, 2004, 2006-2018 Glenn Randers-Pehrson.
* Copyright (c) 1996-1997 Andreas Dilger.
* Copyright (c) 1995-1996 Guy Eric Schalnat, Group 42, Inc.
The software is supplied "as is", without warranty of any kind,
express or implied, including, without limitation, the warranties
of merchantability, fitness for a particular purpose, title, and
non-infringement. In no event shall the Copyright owners, or
anyone distributing the software, be liable for any damages or
other liability, whether in contract, tort or otherwise, arising
from, out of, or in connection with the software, or the use or
other dealings in the software, even if advised of the possibility
of such damage.
Permission is hereby granted to use, copy, modify, and distribute
this software, or portions hereof, for any purpose, without fee,
subject to the following restrictions:
1. The origin of this software must not be misrepresented; you
must not claim that you wrote the original software. If you
use this software in a product, an acknowledgment in the product
documentation would be appreciated, but is not required.
2. Altered source versions must be plainly marked as such, and must
not be misrepresented as being the original software.
3. This Copyright notice may not be removed or altered from any
source or altered source distribution.
</pre>
<h3>LLVM - <a href="https://github.com/llvm/llvm-project">https://github.com/llvm/llvm-project</a></h3> <h3>LLVM - <a href="https://github.com/llvm/llvm-project">https://github.com/llvm/llvm-project</a></h3>
<pre> <pre>
Apache License Apache License
@ -1580,11 +1652,6 @@ ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
</pre> </pre>
<h3>stb libraries - <a href="https://github.com/nothings/stb">https://github.com/nothings/stb</a></h3>
These libraries are in the public domain. You can do anything you want with them. You have no legal obligation to do anything else, although I appreciate attribution.
They are also licensed under the MIT open source license, if you have lawyers who are unhappy with public domain. Every source file includes an explicit dual-license for you to choose from.
<h3>vixl - <a href="https://git.linaro.org/arm/vixl.git">https://git.linaro.org/arm/vixl.git</a></h3> <h3>vixl - <a href="https://git.linaro.org/arm/vixl.git">https://git.linaro.org/arm/vixl.git</a></h3>
<pre> <pre>
LICENCE LICENCE

View file

@ -1,8 +1,6 @@
set(FMT_INSTALL OFF CACHE BOOL "") set(FMT_INSTALL OFF CACHE BOOL "")
add_subdirectory(fmt EXCLUDE_FROM_ALL) add_subdirectory(fmt EXCLUDE_FROM_ALL)
disable_compiler_warnings_for_target(fmt) disable_compiler_warnings_for_target(fmt)
add_subdirectory(stb EXCLUDE_FROM_ALL)
disable_compiler_warnings_for_target(stb)
add_subdirectory(minizip EXCLUDE_FROM_ALL) add_subdirectory(minizip EXCLUDE_FROM_ALL)
disable_compiler_warnings_for_target(minizip) disable_compiler_warnings_for_target(minizip)
add_subdirectory(lzma EXCLUDE_FROM_ALL) add_subdirectory(lzma EXCLUDE_FROM_ALL)

View file

@ -1,13 +0,0 @@
set(SRCS
include/stb_image.h
include/stb_image_resize.h
include/stb_image_write.h
src/stb_image.c
src/stb_image_resize.c
src/stb_image_write.c
)
add_library(stb ${SRCS})
target_include_directories(stb PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/include" "${CMAKE_CURRENT_SOURCE_DIR}/src")
target_include_directories(stb INTERFACE "${CMAKE_CURRENT_SOURCE_DIR}/include")
target_link_libraries(stb ZLIB::ZLIB Threads::Threads "${CMAKE_DL_LIBS}")

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -1,2 +0,0 @@
#define STB_IMAGE_IMPLEMENTATION
#include "stb_image.h"

View file

@ -1,2 +0,0 @@
#define STB_IMAGE_RESIZE_IMPLEMENTATION
#include "stb_image_resize.h"

View file

@ -1,28 +0,0 @@
#include <stdlib.h>
#include "zlib.h"
// https://github.com/nothings/stb/issues/113
static unsigned char* compress_for_stbiw(unsigned char* data, int data_len, int* out_len, int quality)
{
uLongf buf_size = compressBound(data_len);
// note that buf will be free'd by stb_image_write.h
// with STBIW_FREE() (plain free() by default)
unsigned char* buf = malloc(buf_size);
if (buf == NULL)
return NULL;
if (compress2(buf, &buf_size, data, data_len, quality) != Z_OK)
{
free(buf);
return NULL;
}
*out_len = buf_size;
return buf;
}
#define STBIW_ZLIB_COMPRESS compress_for_stbiw
#define STB_IMAGE_WRITE_IMPLEMENTATION
#include "stb_image_write.h"

View file

@ -1,30 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="..\msvc\vsprops\Configurations.props" />
<ItemGroup>
<ClCompile Include="src\stb_image.c" />
<ClCompile Include="src\stb_image_resize.c" />
<ClCompile Include="src\stb_image_write.c" />
</ItemGroup>
<ItemGroup>
<ClInclude Include="include\stb_image.h" />
<ClInclude Include="include\stb_image_resize.h" />
<ClInclude Include="include\stb_image_write.h" />
</ItemGroup>
<PropertyGroup Label="Globals">
<ProjectGuid>{ED601289-AC1A-46B8-A8ED-17DB9EB73423}</ProjectGuid>
</PropertyGroup>
<Import Project="..\msvc\vsprops\StaticLibrary.props" />
<ItemDefinitionGroup>
<ClCompile>
<WarningLevel>TurnOffAllWarnings</WarningLevel>
<AdditionalIncludeDirectories>$(SolutionDir)dep\zlib\include;$(ProjectDir)include;$(ProjectDir)src;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
</ClCompile>
</ItemDefinitionGroup>
<Import Project="..\msvc\vsprops\Targets.props" />
</Project>

View file

@ -1,13 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup>
<ClCompile Include="src\stb_image_write.c" />
<ClCompile Include="src\stb_image_resize.c" />
<ClCompile Include="src\stb_image.c" />
</ItemGroup>
<ItemGroup>
<ClInclude Include="include\stb_image_write.h" />
<ClInclude Include="include\stb_image_resize.h" />
<ClInclude Include="include\stb_image.h" />
</ItemGroup>
</Project>

View file

@ -13,8 +13,6 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "common", "src\common\common
EndProject EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "core", "src\core\core.vcxproj", "{868B98C8-65A1-494B-8346-250A73A48C0A}" Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "core", "src\core\core.vcxproj", "{868B98C8-65A1-494B-8346-250A73A48C0A}"
EndProject EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "stb", "dep\stb\stb.vcxproj", "{ED601289-AC1A-46B8-A8ED-17DB9EB73423}"
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "simpleini", "dep\simpleini\simpleini.vcxproj", "{3773F4CC-614E-4028-8595-22E08CA649E3}" Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "simpleini", "dep\simpleini\simpleini.vcxproj", "{3773F4CC-614E-4028-8595-22E08CA649E3}"
EndProject EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "duckstation-qt", "src\duckstation-qt\duckstation-qt.vcxproj", "{28F14272-0EC4-41BB-849F-182ADB81AF70}" Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "duckstation-qt", "src\duckstation-qt\duckstation-qt.vcxproj", "{28F14272-0EC4-41BB-849F-182ADB81AF70}"
@ -223,38 +221,6 @@ Global
{868B98C8-65A1-494B-8346-250A73A48C0A}.ReleaseLTCG-Clang|ARM64.Build.0 = ReleaseLTCG-Clang|ARM64 {868B98C8-65A1-494B-8346-250A73A48C0A}.ReleaseLTCG-Clang|ARM64.Build.0 = ReleaseLTCG-Clang|ARM64
{868B98C8-65A1-494B-8346-250A73A48C0A}.ReleaseLTCG-Clang|x64.ActiveCfg = ReleaseLTCG-Clang|x64 {868B98C8-65A1-494B-8346-250A73A48C0A}.ReleaseLTCG-Clang|x64.ActiveCfg = ReleaseLTCG-Clang|x64
{868B98C8-65A1-494B-8346-250A73A48C0A}.ReleaseLTCG-Clang|x64.Build.0 = ReleaseLTCG-Clang|x64 {868B98C8-65A1-494B-8346-250A73A48C0A}.ReleaseLTCG-Clang|x64.Build.0 = ReleaseLTCG-Clang|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Debug|ARM64.ActiveCfg = Debug|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Debug|ARM64.Build.0 = Debug|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Debug|x64.ActiveCfg = Debug|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Debug|x64.Build.0 = Debug|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Debug-Clang|ARM64.ActiveCfg = Debug-Clang|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Debug-Clang|ARM64.Build.0 = Debug-Clang|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Debug-Clang|x64.ActiveCfg = Debug-Clang|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Debug-Clang|x64.Build.0 = Debug-Clang|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.DebugFast|ARM64.ActiveCfg = DebugFast|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.DebugFast|ARM64.Build.0 = DebugFast|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.DebugFast|x64.ActiveCfg = DebugFast|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.DebugFast|x64.Build.0 = DebugFast|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.DebugFast-Clang|ARM64.ActiveCfg = DebugFast-Clang|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.DebugFast-Clang|ARM64.Build.0 = DebugFast-Clang|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.DebugFast-Clang|x64.ActiveCfg = DebugFast-Clang|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.DebugFast-Clang|x64.Build.0 = DebugFast-Clang|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Release|ARM64.ActiveCfg = Release|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Release|ARM64.Build.0 = Release|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Release|x64.ActiveCfg = Release|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Release|x64.Build.0 = Release|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Release-Clang|ARM64.ActiveCfg = Release-Clang|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Release-Clang|ARM64.Build.0 = Release-Clang|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Release-Clang|x64.ActiveCfg = Release-Clang|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.Release-Clang|x64.Build.0 = Release-Clang|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.ReleaseLTCG|ARM64.ActiveCfg = ReleaseLTCG|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.ReleaseLTCG|ARM64.Build.0 = ReleaseLTCG|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.ReleaseLTCG|x64.ActiveCfg = ReleaseLTCG|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.ReleaseLTCG|x64.Build.0 = ReleaseLTCG|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.ReleaseLTCG-Clang|ARM64.ActiveCfg = ReleaseLTCG-Clang|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.ReleaseLTCG-Clang|ARM64.Build.0 = ReleaseLTCG-Clang|ARM64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.ReleaseLTCG-Clang|x64.ActiveCfg = ReleaseLTCG-Clang|x64
{ED601289-AC1A-46B8-A8ED-17DB9EB73423}.ReleaseLTCG-Clang|x64.Build.0 = ReleaseLTCG-Clang|x64
{3773F4CC-614E-4028-8595-22E08CA649E3}.Debug|ARM64.ActiveCfg = Debug|ARM64 {3773F4CC-614E-4028-8595-22E08CA649E3}.Debug|ARM64.ActiveCfg = Debug|ARM64
{3773F4CC-614E-4028-8595-22E08CA649E3}.Debug|ARM64.Build.0 = Debug|ARM64 {3773F4CC-614E-4028-8595-22E08CA649E3}.Debug|ARM64.Build.0 = Debug|ARM64
{3773F4CC-614E-4028-8595-22E08CA649E3}.Debug|x64.ActiveCfg = Debug|x64 {3773F4CC-614E-4028-8595-22E08CA649E3}.Debug|x64.ActiveCfg = Debug|x64
@ -1140,7 +1106,6 @@ Global
GlobalSection(NestedProjects) = preSolution GlobalSection(NestedProjects) = preSolution
{43540154-9E1E-409C-834F-B84BE5621388} = {BA490C0E-497D-4634-A21E-E65012006385} {43540154-9E1E-409C-834F-B84BE5621388} = {BA490C0E-497D-4634-A21E-E65012006385}
{BB08260F-6FBC-46AF-8924-090EE71360C6} = {BA490C0E-497D-4634-A21E-E65012006385} {BB08260F-6FBC-46AF-8924-090EE71360C6} = {BA490C0E-497D-4634-A21E-E65012006385}
{ED601289-AC1A-46B8-A8ED-17DB9EB73423} = {BA490C0E-497D-4634-A21E-E65012006385}
{3773F4CC-614E-4028-8595-22E08CA649E3} = {BA490C0E-497D-4634-A21E-E65012006385} {3773F4CC-614E-4028-8595-22E08CA649E3} = {BA490C0E-497D-4634-A21E-E65012006385}
{72F9423C-91EE-4487-AAC6-555ED6F61AA1} = {BA490C0E-497D-4634-A21E-E65012006385} {72F9423C-91EE-4487-AAC6-555ED6F61AA1} = {BA490C0E-497D-4634-A21E-E65012006385}
{8BDA439C-6358-45FB-9994-2FF083BABE06} = {BA490C0E-497D-4634-A21E-E65012006385} {8BDA439C-6358-45FB-9994-2FF083BABE06} = {BA490C0E-497D-4634-A21E-E65012006385}

View file

@ -131,7 +131,7 @@ target_precompile_headers(core PRIVATE "pch.h")
target_include_directories(core PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/..") target_include_directories(core PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/..")
target_include_directories(core PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/..") target_include_directories(core PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/..")
target_link_libraries(core PUBLIC Threads::Threads common util ZLIB::ZLIB) target_link_libraries(core PUBLIC Threads::Threads common util ZLIB::ZLIB)
target_link_libraries(core PRIVATE stb xxhash imgui rapidyaml rcheevos) target_link_libraries(core PRIVATE xxhash imgui rapidyaml rcheevos)
if(CPU_ARCH_X64) if(CPU_ARCH_X64)
target_compile_definitions(core PUBLIC "ENABLE_RECOMPILER=1" "ENABLE_NEWREC=1" "ENABLE_MMAP_FASTMEM=1") target_compile_definitions(core PUBLIC "ENABLE_RECOMPILER=1" "ENABLE_NEWREC=1" "ENABLE_MMAP_FASTMEM=1")

View file

@ -178,9 +178,6 @@
<ProjectReference Include="..\..\dep\rcheevos\rcheevos.vcxproj"> <ProjectReference Include="..\..\dep\rcheevos\rcheevos.vcxproj">
<Project>{4ba0a6d4-3ae1-42b2-9347-096fd023ff64}</Project> <Project>{4ba0a6d4-3ae1-42b2-9347-096fd023ff64}</Project>
</ProjectReference> </ProjectReference>
<ProjectReference Include="..\..\dep\stb\stb.vcxproj">
<Project>{ed601289-ac1a-46b8-a8ed-17db9eb73423}</Project>
</ProjectReference>
<ProjectReference Include="..\..\dep\vixl\vixl.vcxproj" Condition="'$(Platform)'=='ARM64'"> <ProjectReference Include="..\..\dep\vixl\vixl.vcxproj" Condition="'$(Platform)'=='ARM64'">
<Project>{8906836e-f06e-46e8-b11a-74e5e8c7b8fb}</Project> <Project>{8906836e-f06e-46e8-b11a-74e5e8c7b8fb}</Project>
</ProjectReference> </ProjectReference>

View file

@ -77,7 +77,7 @@ target_precompile_headers(util PRIVATE "pch.h")
target_include_directories(util PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/..") target_include_directories(util PRIVATE "${CMAKE_CURRENT_SOURCE_DIR}/..")
target_include_directories(util PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/..") target_include_directories(util PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/..")
target_link_libraries(util PUBLIC common simpleini imgui) target_link_libraries(util PUBLIC common simpleini imgui)
target_link_libraries(util PRIVATE stb libchdr ZLIB::ZLIB soundtouch xxhash Zstd::Zstd reshadefx) target_link_libraries(util PRIVATE libchdr JPEG::JPEG PNG::PNG ZLIB::ZLIB soundtouch xxhash Zstd::Zstd reshadefx)
if(ENABLE_CUBEB) if(ENABLE_CUBEB)
target_sources(util PRIVATE target_sources(util PRIVATE

View file

@ -3,6 +3,7 @@
#include "image.h" #include "image.h"
#include "common/bitutils.h"
#include "common/byte_stream.h" #include "common/byte_stream.h"
#include "common/file_system.h" #include "common/file_system.h"
#include "common/log.h" #include "common/log.h"
@ -10,50 +11,41 @@
#include "common/scoped_guard.h" #include "common/scoped_guard.h"
#include "common/string_util.h" #include "common/string_util.h"
#include "stb_image.h" #include <jpeglib.h>
#include "stb_image_resize.h" #include <png.h>
#include "stb_image_write.h"
// clang-format off
#ifdef _MSC_VER
#pragma warning(disable : 4611) // warning C4611: interaction between '_setjmp' and C++ object destruction is non-portable
#pragma warning(disable : 4324) // warning C4324: '`anonymous-namespace'::JPEGErrorHandler': structure was padded due to alignment specifier
#endif
// clang-format on
Log_SetChannel(Image); Log_SetChannel(Image);
#if 0
static bool PNGBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size); static bool PNGBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size);
static bool PNGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, int quality); static bool PNGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, u8 quality);
static bool PNGFileLoader(RGBA8Image* image, const char* filename, std::FILE* fp); static bool PNGFileLoader(RGBA8Image* image, const char* filename, std::FILE* fp);
static bool PNGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp, int quality); static bool PNGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp, u8 quality);
static bool JPEGBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size); static bool JPEGBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size);
static bool JPEGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, int quality); static bool JPEGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, u8 quality);
static bool JPEGFileLoader(RGBA8Image* image, const char* filename, std::FILE* fp); static bool JPEGFileLoader(RGBA8Image* image, const char* filename, std::FILE* fp);
static bool JPEGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp, int quality); static bool JPEGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp, u8 quality);
#endif
static bool STBBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size);
static bool STBFileLoader(RGBA8Image* image, const char* filename, std::FILE* fp);
static bool STBBufferSaverPNG(const RGBA8Image& image, std::vector<u8>* buffer, int quality);
static bool STBBufferSaverJPEG(const RGBA8Image& image, std::vector<u8>* buffer, int quality);
static bool STBFileSaverPNG(const RGBA8Image& image, const char* filename, std::FILE* fp, int quality);
static bool STBFileSaverJPEG(const RGBA8Image& image, const char* filename, std::FILE* fp, int quality);
struct FormatHandler struct FormatHandler
{ {
const char* extension; const char* extension;
bool (*buffer_loader)(RGBA8Image*, const void*, size_t); bool (*buffer_loader)(RGBA8Image*, const void*, size_t);
bool (*buffer_saver)(const RGBA8Image&, std::vector<u8>*, int); bool (*buffer_saver)(const RGBA8Image&, std::vector<u8>*, u8);
bool (*file_loader)(RGBA8Image*, const char*, std::FILE*); bool (*file_loader)(RGBA8Image*, const char*, std::FILE*);
bool (*file_saver)(const RGBA8Image&, const char*, std::FILE*, int); bool (*file_saver)(const RGBA8Image&, const char*, std::FILE*, u8);
}; };
static constexpr FormatHandler s_format_handlers[] = { static constexpr FormatHandler s_format_handlers[] = {
#if 0
{"png", PNGBufferLoader, PNGBufferSaver, PNGFileLoader, PNGFileSaver}, {"png", PNGBufferLoader, PNGBufferSaver, PNGFileLoader, PNGFileSaver},
{"jpg", JPEGBufferLoader, JPEGBufferSaver, JPEGFileLoader, JPEGFileSaver}, {"jpg", JPEGBufferLoader, JPEGBufferSaver, JPEGFileLoader, JPEGFileSaver},
{"jpeg", JPEGBufferLoader, JPEGBufferSaver, JPEGFileLoader, JPEGFileSaver}, {"jpeg", JPEGBufferLoader, JPEGBufferSaver, JPEGFileLoader, JPEGFileSaver},
#else
{"png", STBBufferLoader, STBBufferSaverPNG, STBFileLoader, STBFileSaverPNG},
{"jpg", STBBufferLoader, STBBufferSaverJPEG, STBFileLoader, STBFileSaverJPEG},
{"jpeg", STBBufferLoader, STBBufferSaverJPEG, STBFileLoader, STBFileSaverJPEG},
#endif
}; };
static const FormatHandler* GetFormatHandler(const std::string_view& extension) static const FormatHandler* GetFormatHandler(const std::string_view& extension)
@ -110,7 +102,7 @@ bool RGBA8Image::LoadFromFile(const char* filename)
return LoadFromFile(filename, fp.get()); return LoadFromFile(filename, fp.get());
} }
bool RGBA8Image::SaveToFile(const char* filename, int quality) const bool RGBA8Image::SaveToFile(const char* filename, u8 quality) const
{ {
auto fp = FileSystem::OpenManagedCFile(filename, "wb"); auto fp = FileSystem::OpenManagedCFile(filename, "wb");
if (!fp) if (!fp)
@ -151,7 +143,7 @@ bool RGBA8Image::LoadFromBuffer(const char* filename, const void* buffer, size_t
return handler->buffer_loader(this, buffer, buffer_size); return handler->buffer_loader(this, buffer, buffer_size);
} }
bool RGBA8Image::SaveToFile(const char* filename, std::FILE* fp, int quality) const bool RGBA8Image::SaveToFile(const char* filename, std::FILE* fp, u8 quality) const
{ {
const std::string_view extension(Path::GetExtension(filename)); const std::string_view extension(Path::GetExtension(filename));
const FormatHandler* handler = GetFormatHandler(extension); const FormatHandler* handler = GetFormatHandler(extension);
@ -167,7 +159,7 @@ bool RGBA8Image::SaveToFile(const char* filename, std::FILE* fp, int quality) co
return (std::fflush(fp) == 0); return (std::fflush(fp) == 0);
} }
std::optional<std::vector<u8>> RGBA8Image::SaveToBuffer(const char* filename, int quality) const std::optional<std::vector<u8>> RGBA8Image::SaveToBuffer(const char* filename, u8 quality) const
{ {
std::optional<std::vector<u8>> ret; std::optional<std::vector<u8>> ret;
@ -186,6 +178,8 @@ std::optional<std::vector<u8>> RGBA8Image::SaveToBuffer(const char* filename, in
return ret; return ret;
} }
#if 0
void RGBA8Image::Resize(u32 new_width, u32 new_height) void RGBA8Image::Resize(u32 new_width, u32 new_height)
{ {
if (m_width == new_width && m_height == new_height) if (m_width == new_width && m_height == new_height)
@ -222,7 +216,7 @@ void RGBA8Image::Resize(const RGBA8Image* src_image, u32 new_width, u32 new_heig
} }
} }
#if 0 #endif
static bool PNGCommonLoader(RGBA8Image* image, png_structp png_ptr, png_infop info_ptr, std::vector<u32>& new_data, static bool PNGCommonLoader(RGBA8Image* image, png_structp png_ptr, png_infop info_ptr, std::vector<u32>& new_data,
std::vector<png_bytep>& row_pointers) std::vector<png_bytep>& row_pointers)
@ -336,7 +330,7 @@ bool PNGBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size)
return PNGCommonLoader(image, png_ptr, info_ptr, new_data, row_pointers); return PNGCommonLoader(image, png_ptr, info_ptr, new_data, row_pointers);
} }
static void PNGSaveCommon(const RGBA8Image& image, png_structp png_ptr, png_infop info_ptr, int quality) static void PNGSaveCommon(const RGBA8Image& image, png_structp png_ptr, png_infop info_ptr, u8 quality)
{ {
png_set_compression_level(png_ptr, std::clamp(quality / 10, 0, 9)); png_set_compression_level(png_ptr, std::clamp(quality / 10, 0, 9));
png_set_IHDR(png_ptr, info_ptr, image.GetWidth(), image.GetHeight(), 8, PNG_COLOR_TYPE_RGBA, PNG_INTERLACE_NONE, png_set_IHDR(png_ptr, info_ptr, image.GetWidth(), image.GetHeight(), 8, PNG_COLOR_TYPE_RGBA, PNG_INTERLACE_NONE,
@ -349,7 +343,7 @@ static void PNGSaveCommon(const RGBA8Image& image, png_structp png_ptr, png_info
png_write_end(png_ptr, nullptr); png_write_end(png_ptr, nullptr);
} }
bool PNGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp, int quality) bool PNGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp, u8 quality)
{ {
png_structp png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, nullptr, nullptr, nullptr); png_structp png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, nullptr, nullptr, nullptr);
png_infop info_ptr = nullptr; png_infop info_ptr = nullptr;
@ -380,7 +374,7 @@ bool PNGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp,
return true; return true;
} }
bool PNGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, int quality) bool PNGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, u8 quality)
{ {
png_structp png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, nullptr, nullptr, nullptr); png_structp png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, nullptr, nullptr, nullptr);
png_infop info_ptr = nullptr; png_infop info_ptr = nullptr;
@ -415,245 +409,200 @@ bool PNGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, int qualit
return true; return true;
} }
bool JPEGBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size) namespace {
struct JPEGErrorHandler
{ {
int width, height, file_comps; jpeg_error_mgr err;
u8* data = jpgd::decompress_jpeg_image_from_memory(static_cast<const u8*>(buffer), static_cast<int>(buffer_size), jmp_buf jbuf;
&width, &height, &file_comps, 4, 0); };
if (!data) } // namespace
{
Console.Error("jpgd::decompress_jpeg_image_from_memory() failed");
return false;
}
image->SetPixels(static_cast<u32>(width), static_cast<u32>(height), reinterpret_cast<const u32*>(data));
std::free(data);
return true;
}
bool JPEGFileLoader(RGBA8Image* image, const char* filename, std::FILE* fp) static bool HandleJPEGError(JPEGErrorHandler* eh)
{ {
class FileStream : public jpgd::jpeg_decoder_stream jpeg_std_error(&eh->err);
{
std::FILE* m_fp;
bool m_error_flag = false;
bool m_eof_flag = false;
public: eh->err.error_exit = [](j_common_ptr cinfo) {
explicit FileStream(std::FILE* fp_) : m_fp(fp_) {} JPEGErrorHandler* eh = (JPEGErrorHandler*)cinfo->err;
char msg[JMSG_LENGTH_MAX];
int read(jpgd::uint8* pBuf, int max_bytes_to_read, bool* pEOF_flag) override eh->err.format_message(cinfo, msg);
{ Log_ErrorFmt("libjpeg fatal error: {}", msg);
if (m_eof_flag) longjmp(eh->jbuf, 1);
{
*pEOF_flag = true;
return 0;
}
if (m_error_flag)
return -1;
int bytes_read = static_cast<int>(std::fread(pBuf, 1, max_bytes_to_read, m_fp));
if (bytes_read < max_bytes_to_read)
{
if (std::ferror(m_fp))
{
m_error_flag = true;
return -1;
}
m_eof_flag = true;
*pEOF_flag = true;
}
return bytes_read;
}
}; };
FileStream stream(fp); if (setjmp(eh->jbuf) == 0)
int width, height, file_comps; return true;
u8* data = jpgd::decompress_jpeg_image_from_stream(&stream, &width, &height, &file_comps, 4, 0);
if (!data)
{
Console.Error("jpgd::decompress_jpeg_image_from_stream() failed");
return false;
}
image->SetPixels(static_cast<u32>(width), static_cast<u32>(height), reinterpret_cast<const u32*>(data)); return false;
std::free(data);
return true;
} }
static bool JPEGCommonSaver(const RGBA8Image& image, jpge::output_stream& stream, int quality) template<typename T>
static bool WrapJPEGDecompress(RGBA8Image* image, T setup_func)
{ {
jpge::params params; std::vector<u8> scanline;
params.m_quality = quality;
jpge::jpeg_encoder dst_image; JPEGErrorHandler err;
if (!dst_image.init(&stream, image.GetWidth(), image.GetHeight(), 3, params)) if (!HandleJPEGError(&err))
return false; return false;
// for RGBA->RGB jpeg_decompress_struct info;
std::vector<u8> row; info.err = &err.err;
row.resize(image.GetWidth() * 3); jpeg_create_decompress(&info);
setup_func(info);
for (uint pass_index = 0; pass_index < dst_image.get_total_passes(); pass_index++) const int herr = jpeg_read_header(&info, TRUE);
if (herr != JPEG_HEADER_OK)
{ {
for (u32 i = 0; i < image.GetHeight(); i++) Log_ErrorFmt("jpeg_read_header() returned {}", herr);
{ return false;
const u8* row_in = reinterpret_cast<const u8*>(image.GetRowPixels(i));
u8* row_out = row.data();
for (u32 j = 0; j < image.GetWidth(); j++)
{
*(row_out++) = *(row_in++);
*(row_out++) = *(row_in++);
*(row_out++) = *(row_in++);
row_in++;
}
if (!dst_image.process_scanline(row.data()))
return false;
}
if (!dst_image.process_scanline(NULL))
return false;
} }
dst_image.deinit(); if (info.image_width == 0 || info.image_height == 0 || info.num_components < 3)
{
Log_ErrorFmt("Invalid image dimensions: {}x{}x{}", info.image_width, info.image_height, info.num_components);
return false;
}
return true; info.out_color_space = JCS_RGB;
} info.out_color_components = 3;
bool JPEGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, int quality) if (!jpeg_start_decompress(&info))
{
class BufferStream : public jpge::output_stream
{ {
std::vector<u8>* buffer; Log_ErrorFmt("jpeg_start_decompress() returned failure");
return false;
}
public: image->SetSize(info.image_width, info.image_height);
explicit BufferStream(std::vector<u8>* buffer_) : buffer(buffer_) {} scanline.resize(info.image_width * 3);
bool put_buf(const void* Pbuf, int len) override u8* scanline_buffer[1] = {scanline.data()};
bool result = true;
for (u32 y = 0; y < info.image_height; y++)
{
if (jpeg_read_scanlines(&info, scanline_buffer, 1) != 1)
{ {
const size_t old_size = buffer->size(); Log_ErrorFmt("jpeg_read_scanlines() failed at row {}", y);
buffer->resize(buffer->size() + static_cast<size_t>(len)); result = false;
std::memcpy(buffer->data() + old_size, Pbuf, static_cast<size_t>(len)); break;
return true;
} }
};
// give enough space to avoid reallocs // RGB -> RGBA
buffer->reserve(image.GetWidth() * image.GetHeight() * 2); const u8* src_ptr = scanline.data();
u32* dst_ptr = image->GetRowPixels(y);
for (u32 x = 0; x < info.image_width; x++)
{
*(dst_ptr) =
(ZeroExtend32(src_ptr[0]) | (ZeroExtend32(src_ptr[1]) << 8) | (ZeroExtend32(src_ptr[2]) << 16) | 0xFF000000u);
}
}
BufferStream stream(buffer); jpeg_finish_decompress(&info);
return JPEGCommonSaver(image, stream, quality); jpeg_destroy_decompress(&info);
return result;
} }
bool JPEGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp, int quality) bool JPEGBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size)
{ {
class FileStream : public jpge::output_stream return WrapJPEGDecompress(image, [buffer, buffer_size](jpeg_decompress_struct& info) {
{ jpeg_mem_src(&info, static_cast<const unsigned char*>(buffer), buffer_size);
std::FILE* m_fp; });
bool m_error_flag = false; }
public: bool JPEGFileLoader(RGBA8Image* image, const char* filename, std::FILE* fp)
explicit FileStream(std::FILE* fp_) : m_fp(fp_) {} {
return WrapJPEGDecompress(image, [fp](jpeg_decompress_struct& info) { jpeg_stdio_src(&info, fp); });
}
bool put_buf(const void* Pbuf, int len) override template<typename T>
{ static bool WrapJPEGCompress(const RGBA8Image& image, u8 quality, T setup_func)
if (m_error_flag) {
return false; std::vector<u8> scanline;
if (std::fwrite(Pbuf, len, 1, m_fp) != 1) JPEGErrorHandler err;
{ if (!HandleJPEGError(&err))
m_error_flag = true; return false;
return false;
}
return true; jpeg_compress_struct info;
} info.err = &err.err;
}; jpeg_create_compress(&info);
setup_func(info);
FileStream stream(fp); info.image_width = image.GetWidth();
return JPEGCommonSaver(image, stream, quality); info.image_height = image.GetHeight();
} info.in_color_space = JCS_RGB;
info.input_components = 3;
#endif jpeg_set_defaults(&info);
jpeg_set_quality(&info, quality, TRUE);
jpeg_start_compress(&info, TRUE);
bool STBBufferLoader(RGBA8Image* image, const void* buffer, size_t buffer_size) scanline.resize(image.GetWidth() * 3);
{ u8* scanline_buffer[1] = {scanline.data()};
int width, height, file_channels; bool result = true;
u8* pixel_data = stbi_load_from_memory(static_cast<const stbi_uc*>(buffer), static_cast<int>(buffer_size), &width, for (u32 y = 0; y < info.image_height; y++)
&height, &file_channels, 4);
if (!pixel_data)
{ {
const char* error_reason = stbi_failure_reason(); // RGBA -> RGB
Log_ErrorPrintf("Failed to load image from memory: %s", error_reason ? error_reason : "unknown error"); u8* dst_ptr = scanline.data();
return false; const u32* src_ptr = image.GetRowPixels(y);
} for (u32 x = 0; x < info.image_width; x++)
{
image->SetPixels(static_cast<u32>(width), static_cast<u32>(height), reinterpret_cast<const u32*>(pixel_data)); const u32 rgba = *(src_ptr++);
stbi_image_free(pixel_data); *(dst_ptr++) = Truncate8(rgba);
return true; *(dst_ptr++) = Truncate8(rgba >> 8);
} *(dst_ptr++) = Truncate8(rgba >> 16);
}
bool STBFileLoader(RGBA8Image* image, const char* filename, std::FILE* fp) if (jpeg_write_scanlines(&info, scanline_buffer, 1) != 1)
{ {
int width, height, file_channels; Log_ErrorFmt("jpeg_write_scanlines() failed at row {}", y);
u8* pixel_data = stbi_load_from_file(fp, &width, &height, &file_channels, 4); result = false;
if (!pixel_data) break;
{ }
const char* error_reason = stbi_failure_reason();
Log_ErrorPrintf("Failed to load image from memory: %s", error_reason ? error_reason : "unknown error");
return false;
} }
image->SetPixels(static_cast<u32>(width), static_cast<u32>(height), reinterpret_cast<const u32*>(pixel_data)); jpeg_finish_compress(&info);
stbi_image_free(pixel_data); jpeg_destroy_compress(&info);
return true; return result;
} }
bool STBBufferSaverPNG(const RGBA8Image& image, std::vector<u8>* buffer, int quality) bool JPEGBufferSaver(const RGBA8Image& image, std::vector<u8>* buffer, u8 quality)
{ {
const auto write_func = [](void* context, void* data, int size) { // give enough space to avoid reallocs
std::vector<u8>* buffer = reinterpret_cast<std::vector<u8>*>(data); buffer->resize(image.GetWidth() * image.GetHeight() * 2);
const u32 len = static_cast<u32>(size);
buffer->resize(buffer->size() + len);
std::memcpy(buffer->data(), data, len);
};
return (stbi_write_png_to_func(write_func, buffer, image.GetWidth(), image.GetHeight(), 4, image.GetPixels(),
image.GetPitch()) != 0);
}
bool STBBufferSaverJPEG(const RGBA8Image& image, std::vector<u8>* buffer, int quality) struct MemCallback
{ {
const auto write_func = [](void* context, void* data, int size) { jpeg_destination_mgr mgr;
std::vector<u8>* buffer = reinterpret_cast<std::vector<u8>*>(data); std::vector<u8>* buffer;
const u32 len = static_cast<u32>(size); size_t buffer_used;
buffer->resize(buffer->size() + len);
std::memcpy(buffer->data(), data, len);
}; };
return (stbi_write_jpg_to_func(write_func, buffer, image.GetWidth(), image.GetHeight(), 4, image.GetPixels(), MemCallback cb;
quality) != 0); cb.buffer = buffer;
} cb.buffer_used = 0;
cb.mgr.next_output_byte = buffer->data();
cb.mgr.free_in_buffer = buffer->size();
cb.mgr.init_destination = [](j_compress_ptr cinfo) {};
cb.mgr.empty_output_buffer = [](j_compress_ptr cinfo) -> boolean {
MemCallback* cb = (MemCallback*)cinfo->dest;
// double size
cb->buffer_used = cb->buffer->size();
cb->buffer->resize(cb->buffer->size() * 2);
cb->mgr.next_output_byte = cb->buffer->data() + cb->buffer_used;
cb->mgr.free_in_buffer = cb->buffer->size() - cb->buffer_used;
return TRUE;
};
cb.mgr.term_destination = [](j_compress_ptr cinfo) {
MemCallback* cb = (MemCallback*)cinfo->dest;
bool STBFileSaverPNG(const RGBA8Image& image, const char* filename, std::FILE* fp, int quality) // get final size
{ cb->buffer->resize(cb->buffer->size() - cb->mgr.free_in_buffer);
const auto write_func = [](void* context, void* data, int size) {
std::fwrite(data, 1, size, static_cast<std::FILE*>(context));
}; };
return (stbi_write_png_to_func(write_func, fp, image.GetWidth(), image.GetHeight(), 4, image.GetPixels(), return WrapJPEGCompress(image, quality, [&cb](jpeg_compress_struct& info) { info.dest = &cb.mgr; });
image.GetPitch()) != 0);
} }
bool STBFileSaverJPEG(const RGBA8Image& image, const char* filename, std::FILE* fp, int quality) bool JPEGFileSaver(const RGBA8Image& image, const char* filename, std::FILE* fp, u8 quality)
{ {
const auto write_func = [](void* context, void* data, int size) { return WrapJPEGCompress(image, quality, [fp](jpeg_compress_struct& info) { jpeg_stdio_dest(&info, fp); });
std::fwrite(data, 1, size, static_cast<std::FILE*>(context)); }
};
return (stbi_write_jpg_to_func(write_func, fp, image.GetWidth(), image.GetHeight(), 4, image.GetPixels(), quality) !=
0);
}

View file

@ -114,7 +114,7 @@ protected:
class RGBA8Image : public Image<u32> class RGBA8Image : public Image<u32>
{ {
public: public:
static constexpr int DEFAULT_SAVE_QUALITY = 85; static constexpr u8 DEFAULT_SAVE_QUALITY = 85;
RGBA8Image(); RGBA8Image();
RGBA8Image(u32 width, u32 height); RGBA8Image(u32 width, u32 height);
@ -130,10 +130,7 @@ public:
bool LoadFromFile(const char* filename, std::FILE* fp); bool LoadFromFile(const char* filename, std::FILE* fp);
bool LoadFromBuffer(const char* filename, const void* buffer, size_t buffer_size); bool LoadFromBuffer(const char* filename, const void* buffer, size_t buffer_size);
bool SaveToFile(const char* filename, int quality = DEFAULT_SAVE_QUALITY) const; bool SaveToFile(const char* filename, u8 quality = DEFAULT_SAVE_QUALITY) const;
bool SaveToFile(const char* filename, std::FILE* fp, int quality = DEFAULT_SAVE_QUALITY) const; bool SaveToFile(const char* filename, std::FILE* fp, u8 quality = DEFAULT_SAVE_QUALITY) const;
std::optional<std::vector<u8>> SaveToBuffer(const char* filename, int quality = DEFAULT_SAVE_QUALITY) const; std::optional<std::vector<u8>> SaveToBuffer(const char* filename, u8 quality = DEFAULT_SAVE_QUALITY) const;
void Resize(u32 new_width, u32 new_height);
void Resize(const RGBA8Image* src_image, u32 new_width, u32 new_height);
}; };

View file

@ -8,7 +8,7 @@
<PreprocessorDefinitions>ENABLE_CUBEB=1;ENABLE_SDL2=1;%(PreprocessorDefinitions)</PreprocessorDefinitions> <PreprocessorDefinitions>ENABLE_CUBEB=1;ENABLE_SDL2=1;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<PreprocessorDefinitions Condition="'$(Platform)'!='ARM64'">%(PreprocessorDefinitions);ENABLE_OPENGL=1;ENABLE_VULKAN=1</PreprocessorDefinitions> <PreprocessorDefinitions Condition="'$(Platform)'!='ARM64'">%(PreprocessorDefinitions);ENABLE_OPENGL=1;ENABLE_VULKAN=1</PreprocessorDefinitions>
<PreprocessorDefinitions Condition="'$(Platform)'=='ARM64'">%(PreprocessorDefinitions);SOUNDTOUCH_USE_NEON</PreprocessorDefinitions> <PreprocessorDefinitions Condition="'$(Platform)'=='ARM64'">%(PreprocessorDefinitions);SOUNDTOUCH_USE_NEON</PreprocessorDefinitions>
<AdditionalIncludeDirectories>%(AdditionalIncludeDirectories);$(SolutionDir)dep\xxhash\include;$(SolutionDir)dep\soundtouch\include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\simpleini\include;$(SolutionDir)dep\libchdr\include;$(SolutionDir)dep\cubeb\include;$(SolutionDir)dep\d3d12ma\include;$(SolutionDir)dep\zstd\lib;$(SolutionDir)dep\stb\include</AdditionalIncludeDirectories> <AdditionalIncludeDirectories>%(AdditionalIncludeDirectories);$(SolutionDir)dep\xxhash\include;$(SolutionDir)dep\soundtouch\include;$(SolutionDir)dep\imgui\include;$(SolutionDir)dep\simpleini\include;$(SolutionDir)dep\libchdr\include;$(SolutionDir)dep\cubeb\include;$(SolutionDir)dep\d3d12ma\include;$(SolutionDir)dep\zstd\lib;$(SolutionDir)dep\libpng\include;$(SolutionDir)dep\libjpeg\include</AdditionalIncludeDirectories>
<AdditionalIncludeDirectories Condition="'$(Platform)'!='ARM64'">%(AdditionalIncludeDirectories);$(SolutionDir)dep\glad\include;$(SolutionDir)dep\vulkan\include;$(SolutionDir)dep\glslang</AdditionalIncludeDirectories> <AdditionalIncludeDirectories Condition="'$(Platform)'!='ARM64'">%(AdditionalIncludeDirectories);$(SolutionDir)dep\glad\include;$(SolutionDir)dep\vulkan\include;$(SolutionDir)dep\glslang</AdditionalIncludeDirectories>
</ClCompile> </ClCompile>
</ItemDefinitionGroup> </ItemDefinitionGroup>

View file

@ -253,6 +253,12 @@
<ProjectReference Include="..\..\dep\libchdr\libchdr.vcxproj"> <ProjectReference Include="..\..\dep\libchdr\libchdr.vcxproj">
<Project>{425d6c99-d1c8-43c2-b8ac-4d7b1d941017}</Project> <Project>{425d6c99-d1c8-43c2-b8ac-4d7b1d941017}</Project>
</ProjectReference> </ProjectReference>
<ProjectReference Include="..\..\dep\libjpeg\libjpeg.vcxproj">
<Project>{ec3b6685-0b6e-4767-84ab-39b75eead2e2}</Project>
</ProjectReference>
<ProjectReference Include="..\..\dep\libpng\libpng.vcxproj">
<Project>{9fd2abcd-2dcd-4302-be5c-df0ba8431fa5}</Project>
</ProjectReference>
<ProjectReference Include="..\..\dep\reshadefx\reshadefx.vcxproj"> <ProjectReference Include="..\..\dep\reshadefx\reshadefx.vcxproj">
<Project>{27b8d4bb-4f01-4432-bc14-9bf6ca458eee}</Project> <Project>{27b8d4bb-4f01-4432-bc14-9bf6ca458eee}</Project>
</ProjectReference> </ProjectReference>
@ -265,9 +271,6 @@
<ProjectReference Include="..\..\dep\glslang\glslang.vcxproj" Condition="'$(Platform)'!='ARM64'"> <ProjectReference Include="..\..\dep\glslang\glslang.vcxproj" Condition="'$(Platform)'!='ARM64'">
<Project>{7f909e29-4808-4bd9-a60c-56c51a3aaec2}</Project> <Project>{7f909e29-4808-4bd9-a60c-56c51a3aaec2}</Project>
</ProjectReference> </ProjectReference>
<ProjectReference Include="..\..\dep\stb\stb.vcxproj">
<Project>{ed601289-ac1a-46b8-a8ed-17db9eb73423}</Project>
</ProjectReference>
<ProjectReference Include="..\..\dep\zstd\zstd.vcxproj"> <ProjectReference Include="..\..\dep\zstd\zstd.vcxproj">
<Project>{73ee0c55-6ffe-44e7-9c12-baa52434a797}</Project> <Project>{73ee0c55-6ffe-44e7-9c12-baa52434a797}</Project>
</ProjectReference> </ProjectReference>