From 735c4f149a8e6a00aceeb557c3b60c884d911d3f Mon Sep 17 00:00:00 2001 From: Andrii Danylchenko Date: Tue, 20 Sep 2022 11:50:47 +0300 Subject: [PATCH 001/131] Update vcpkg, fix QT paths --- CI/msvc/before_install.sh | 5 +++- CMakeLists.txt | 1 + osx/CMakeLists.txt | 58 +-------------------------------------- win/CMakeLists.txt | 43 +++++++++++++++++++++++++++++ 4 files changed, 49 insertions(+), 58 deletions(-) create mode 100644 win/CMakeLists.txt diff --git a/CI/msvc/before_install.sh b/CI/msvc/before_install.sh index 9ee5d77e8..c80aaf4d7 100644 --- a/CI/msvc/before_install.sh +++ b/CI/msvc/before_install.sh @@ -1,7 +1,10 @@ curl -LfsS -o "vcpkg-export-${VCMI_BUILD_PLATFORM}-windows-v140.7z" \ - "https://github.com/vcmi/vcmi-deps-windows/releases/download/v1.4/vcpkg-export-${VCMI_BUILD_PLATFORM}-windows-v140.7z" + "https://github.com/vcmi/vcmi-deps-windows/releases/download/v1.5/vcpkg-export-${VCMI_BUILD_PLATFORM}-windows-v140.7z" 7z x "vcpkg-export-${VCMI_BUILD_PLATFORM}-windows-v140.7z" rm -r -f vcpkg/installed/${VCMI_BUILD_PLATFORM}-windows/debug mkdir -p vcpkg/installed/${VCMI_BUILD_PLATFORM}-windows/debug/bin cp vcpkg/installed/${VCMI_BUILD_PLATFORM}-windows/bin/* vcpkg/installed/${VCMI_BUILD_PLATFORM}-windows/debug/bin + +DUMPBIN_DIR=$(vswhere -latest -find **/dumpbin.exe | head -n 1) +dirname "$DUMPBIN_DIR" > $GITHUB_PATH \ No newline at end of file diff --git a/CMakeLists.txt b/CMakeLists.txt index 9d7e99df3..472a65cef 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -488,6 +488,7 @@ if(WIN32) # Use BundleUtilities to fix build when Vcpkg is used and disable it for MXE if(NOT (${CMAKE_CROSSCOMPILING})) add_subdirectory(osx) + add_subdirectory(win) endif() elseif(APPLE AND NOT ENABLE_MONOLITHIC_INSTALL) set(CPACK_MONOLITHIC_INSTALL 1) diff --git a/osx/CMakeLists.txt b/osx/CMakeLists.txt index 9c0057da9..91d343074 100644 --- a/osx/CMakeLists.txt +++ b/osx/CMakeLists.txt @@ -58,60 +58,4 @@ if(APPLE) ) endforeach() ") -endif(APPLE) - -# This will likely only work for Vcpkg -if(WIN32) - if(ENABLE_LAUNCHER) - # Temporary ugly fix for Qt deployment since windeployqt broken in Vcpkg - - #there are some weird issues with variables used in path not evaluated properly when trying to remove code duplication from below lines - if(EXISTS ${CMAKE_BINARY_DIR}/../../vcpkg) #current path to vcpkg main folder on appveyor CI - if(CMAKE_SIZEOF_VOID_P EQUAL 8) #64 bit build - install(CODE " - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x64-windows/plugins/bearer DESTINATION \${CMAKE_INSTALL_PREFIX}) - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x64-windows/plugins/iconengines DESTINATION \${CMAKE_INSTALL_PREFIX}) - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x64-windows/plugins/imageformats DESTINATION \${CMAKE_INSTALL_PREFIX}) - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x64-windows/plugins/platforminputcontexts DESTINATION \${CMAKE_INSTALL_PREFIX}) - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x64-windows/plugins/platforms DESTINATION \${CMAKE_INSTALL_PREFIX}) - ") - else() - install(CODE " - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x86-windows/plugins/bearer DESTINATION \${CMAKE_INSTALL_PREFIX}) - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x86-windows/plugins/iconengines DESTINATION \${CMAKE_INSTALL_PREFIX}) - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x86-windows/plugins/imageformats DESTINATION \${CMAKE_INSTALL_PREFIX}) - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x86-windows/plugins/platforminputcontexts DESTINATION \${CMAKE_INSTALL_PREFIX}) - file(COPY ${CMAKE_BINARY_DIR}/../../vcpkg/installed/x86-windows/plugins/platforms DESTINATION \${CMAKE_INSTALL_PREFIX}) - ") - endif() - else() #not appveyor build - lines below do not work properly - install(CODE " - execute_process( - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_BINARY_DIR}/bin/\${BUILD_TYPE}/bearer \${CMAKE_INSTALL_PREFIX}/bearer - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_BINARY_DIR}/bin/\${BUILD_TYPE}/iconengines \${CMAKE_INSTALL_PREFIX}/iconengines - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_BINARY_DIR}/bin/\${BUILD_TYPE}/imageformats \${CMAKE_INSTALL_PREFIX}/imageformats - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_BINARY_DIR}/bin/\${BUILD_TYPE}/platforminputcontexts \${CMAKE_INSTALL_PREFIX}/platforminputcontexts - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_BINARY_DIR}/bin/\${BUILD_TYPE}/platforms \${CMAKE_INSTALL_PREFIX}/platforms) - ") - endif() - endif() - - - #TODO: check if some equivalent of block below can be used for above block (easy qt dependencies copy) - if(ENABLE_LUA) - install_vcpkg_imported_tgt(luajit::luajit) - endif() - - #LuaJIT will not be copied automatically by not meeting criteria for this block of code - install(CODE " - if(\"\${BUILD_TYPE}\" STREQUAL \"Debug\") - set(dirs \"${CMAKE_PREFIX_PATH}/debug/bin/\") - else() - set(dirs \"${CMAKE_PREFIX_PATH}/bin/\") - endif() - set(BU_CHMOD_BUNDLE_ITEMS ON) - include(BundleUtilities) - fixup_bundle(\"\${CMAKE_INSTALL_PREFIX}/VCMI_Client.exe\" \"\" \"\${dirs}\") - - " COMPONENT Runtime) -endif(WIN32) +endif(APPLE) \ No newline at end of file diff --git a/win/CMakeLists.txt b/win/CMakeLists.txt new file mode 100644 index 000000000..bf3ab9922 --- /dev/null +++ b/win/CMakeLists.txt @@ -0,0 +1,43 @@ +# We need to keep this code into separate directory so CMake will execute it after all other subdirectories install code +# Otherwise we can't fix win bundle dependencies since binaries wouldn't be there when this code executed +# This will likely only work for Vcpkg +if(WIN32) + #there are some weird issues with variables used in path not evaluated properly when trying to remove code duplication from below lines + + if(ENABLE_LAUNCHER) + install(CODE " + file(WRITE \"\${CMAKE_INSTALL_PREFIX}/qt.conf\" + \"[Paths]\nPlugins = .\" + ) + ") + endif() + + + #TODO: check if some equivalent of block below can be used for above block (easy qt dependencies copy) + #LuaJIT will not be copied automatically by not meeting criteria for this block of code + if(ENABLE_LUA) + install_vcpkg_imported_tgt(luajit::luajit) + endif() + + if(MSVC) + set(gp_tool "dumpbin") + endif() + + install(CODE " + set(dirs \"${CMAKE_PREFIX_PATH}\") + if(\"\${CMAKE_INSTALL_CONFIG_NAME}\" STREQUAL \"Debug\") + list(TRANSFORM dirs APPEND \"/debug/bin\") + else() + list(TRANSFORM dirs APPEND \"/bin\") + list(FILTER dirs EXCLUDE REGEX \".*debug.*\") + endif() + + set(BU_CHMOD_BUNDLE_ITEMS ON) + set(gp_tool \"${gp_tool}\") + + include(BundleUtilities) + + fixup_bundle(\"\${CMAKE_INSTALL_PREFIX}/VCMI_Client.exe\" \"\" \"\${dirs}\") + + " COMPONENT Runtime) +endif(WIN32) From b824a90295d475e3fdb6ea6b5d28bb0e3630bc0b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 1 Mar 2021 11:38:21 +0300 Subject: [PATCH 002/131] initial iOS support to fix building tested with Xcode and Unix Makefiles --- CMakeLists.txt | 33 +- Global.h | 4 - client/CMakeLists.txt | 7 + client/CServerHandler.cpp | 2 +- client/main_ios.m | 8 + cmake_modules/FindSDL2.cmake | 8 +- cmake_modules/Findminizip.cmake | 2 +- configure_ios.sh | 20 + ios.toolchain.cmake | 747 ++++++++++++++++++++++++++++++++ osx/CMakeLists.txt | 4 +- 10 files changed, 818 insertions(+), 17 deletions(-) create mode 100644 client/main_ios.m create mode 100755 configure_ios.sh create mode 100644 ios.toolchain.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 472a65cef..f44d6e632 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -26,6 +26,14 @@ project(VCMI) # It's used currently to make sure that 3rd-party dependencies in git submodules get proper FOLDER property # - Make FindFuzzyLite check for the right version and disable FORCE_BUNDLED_FL by default +if(APPLE) + if(${CMAKE_SYSTEM_NAME} STREQUAL "Darwin") + set(APPLE_MACOS 1) + else() + set(APPLE_IOS 1) + endif() +endif(APPLE) + ############################################ # User-provided options # ############################################ @@ -43,7 +51,9 @@ set(VCMI_VERSION_PATCH 0) option(ENABLE_ERM "Enable compilation of ERM scripting module" OFF) option(ENABLE_LUA "Enable compilation of LUA scripting module" OFF) -option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) +if(NOT APPLE_IOS) + option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) +endif() option(ENABLE_TEST "Enable compilation of unit tests" ON) if(NOT ${CMAKE_VERSION} VERSION_LESS "3.16.0") option(ENABLE_PCH "Enable compilation using precompiled headers" ON) @@ -53,7 +63,9 @@ option(ENABLE_DEBUG_CONSOLE "Enable debug console for Windows builds" ON) option(ENABLE_MULTI_PROCESS_BUILDS "Enable /MP flag for MSVS solution" ON) # Used for Snap packages and also useful for debugging -option(ENABLE_MONOLITHIC_INSTALL "Install everything in single directory on Linux and Mac" OFF) +if(NOT APPLE_IOS) + option(ENABLE_MONOLITHIC_INSTALL "Install everything in single directory on Linux and Mac" OFF) +endif() # Allow to pass package name from Travis CI set(PACKAGE_NAME_SUFFIX "" CACHE STRING "Suffix for CPack package name") @@ -133,6 +145,10 @@ set(CMAKE_MAP_IMPORTED_CONFIG_MINSIZEREL MinSizeRel Release RelWithDebInfo "") # Release falls back to RelWithDebInfo, then MinSizeRel set(CMAKE_MAP_IMPORTED_CONFIG_RELEASE Release RelWithDebInfo MinSizeRel "") +if(APPLE_IOS) + set(SYSTEM_LIBS ${SYSTEM_LIBS} iconv) # boost.locale +endif(APPLE_IOS) + if(MINGW OR MSVC) # Windows Vista or newer for FuzzyLite 6 to compile add_definitions(-D_WIN32_WINNT=0x0600) @@ -209,7 +225,7 @@ if(CMAKE_COMPILER_IS_GNUCXX OR NOT WIN32) #so far all *nix compilers support suc endif() # Check if some platform-specific libraries are needed for linking -if(NOT WIN32) +if(NOT WIN32 AND NOT ${CMAKE_SYSTEM_NAME} STREQUAL "iOS") include(CheckLibraryExists) # Shared memory functions used by Boost.Interprocess @@ -307,8 +323,13 @@ elseif(APPLE) set(DATA_DIR "." CACHE STRING "Where to install data files") else() set(APP_BUNDLE_DIR "${CMAKE_PROJECT_NAME}.app") - set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}/Contents") - set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_CONTENTS_DIR}/MacOS") + if(APPLE_MACOS) + set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}/Contents") + set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_CONTENTS_DIR}/MacOS") + else() + set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}") + set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_DIR}") + endif(APPLE_MACOS) set(APP_BUNDLE_RESOURCES_DIR "${APP_BUNDLE_CONTENTS_DIR}/Resources") set(BIN_DIR "${APP_BUNDLE_BINARY_DIR}" CACHE STRING "Where to install binaries") @@ -490,7 +511,7 @@ if(WIN32) add_subdirectory(osx) add_subdirectory(win) endif() -elseif(APPLE AND NOT ENABLE_MONOLITHIC_INSTALL) +elseif(APPLE_MACOS AND NOT ENABLE_MONOLITHIC_INSTALL) set(CPACK_MONOLITHIC_INSTALL 1) set(CPACK_GENERATOR "DragNDrop") set(CPACK_DMG_BACKGROUND_IMAGE "${CMAKE_SOURCE_DIR}/osx/dmg_background.png") diff --git a/Global.h b/Global.h index 5bce068d7..254e06437 100644 --- a/Global.h +++ b/Global.h @@ -82,10 +82,6 @@ static_assert(sizeof(bool) == 1, "Bool needs to be 1 byte in size."); # error "VCMI supports only Windows, OSX, Linux and Android targets" #endif -#ifdef VCMI_IOS -# error "iOS system isn't yet supported." -#endif - // Each compiler uses own way to supress fall through warning. Try to find it. #ifdef __has_cpp_attribute # if __has_cpp_attribute(fallthrough) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 1274bab4e..5719be336 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -153,6 +153,8 @@ endif() if(WIN32) set(client_ICON "VCMI_client.rc") +elseif(APPLE_IOS) + set(client_SRCS ${client_SRCS} main_ios.m) endif() if(ENABLE_DEBUG_CONSOLE) @@ -173,6 +175,11 @@ if(WIN32) target_link_libraries(vcmiclient SDL2::SDL2main) endif() target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) +elseif(APPLE_IOS) + target_link_libraries(vcmiclient PRIVATE + "-framework UIKit" + "-framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image + ) endif() target_link_libraries(vcmiclient PRIVATE diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index 46495145c..d24903da6 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -698,7 +698,7 @@ void CServerHandler::threadHandleConnection() void CServerHandler::threadRunServer() { -#ifndef VCMI_ANDROID +#if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) setThreadName("CServerHandler::threadRunServer"); const std::string logName = (VCMIDirs::get().userLogsPath() / "server_log.txt").string(); std::string comm = VCMIDirs::get().serverPath().string() diff --git a/client/main_ios.m b/client/main_ios.m new file mode 100644 index 000000000..f66680475 --- /dev/null +++ b/client/main_ios.m @@ -0,0 +1,8 @@ +#import +int main (int argc, char const *argv[]) +{ + @autoreleasepool + { + return UIApplicationMain(argc, argv, nil, nil); + } +} diff --git a/cmake_modules/FindSDL2.cmake b/cmake_modules/FindSDL2.cmake index c74890eb2..fde86e409 100644 --- a/cmake_modules/FindSDL2.cmake +++ b/cmake_modules/FindSDL2.cmake @@ -273,7 +273,7 @@ if(SDL2_LIBRARY) # I think it has something to do with the CACHE STRING. # So I use a temporary variable until the end so I can set the # "real" variable in one-shot. - if(APPLE) + if(APPLE_MACOS) set(SDL2_LIBRARIES ${SDL2_LIBRARIES} -framework Cocoa) endif() @@ -342,8 +342,10 @@ if(SDL2_FOUND) if(APPLE) # For OS X, SDL2 uses Cocoa as a backend so it must link to Cocoa. # For more details, please see above. - set_property(TARGET SDL2::SDL2 APPEND PROPERTY - INTERFACE_LINK_OPTIONS -framework Cocoa) + if (APPLE_MACOS) + set_property(TARGET SDL2::SDL2 APPEND PROPERTY + INTERFACE_LINK_OPTIONS -framework Cocoa) + endif() else() # For threads, as mentioned Apple doesn't need this. # For more details, please see above. diff --git a/cmake_modules/Findminizip.cmake b/cmake_modules/Findminizip.cmake index e5cf684b3..13b81b73c 100644 --- a/cmake_modules/Findminizip.cmake +++ b/cmake_modules/Findminizip.cmake @@ -33,7 +33,7 @@ else() set(VC_LIB_PATH_SUFFIX lib/x86) endif() -if (NOT WIN32) +if (NOT WIN32 AND NOT APPLE_IOS) find_package(PkgConfig) if (PKG_CONFIG_FOUND) pkg_check_modules(_MINIZIP minizip) diff --git a/configure_ios.sh b/configure_ios.sh new file mode 100755 index 000000000..af0eb8297 --- /dev/null +++ b/configure_ios.sh @@ -0,0 +1,20 @@ +#!/usr/bin/env bash + +boostPrefix=~/dev/ios/vcmi-ios-deps/Apple-Boost-BuildScript-master/build/boost/1.75.0/ios/release/prefix +ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal +sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib + +srcDir="../vcmi" +"${2:-cmake}" "$srcDir" -G "$1" \ + -DENABLE_LAUNCHER=0 \ + -Wno-dev \ + -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ + -DPLATFORM=OS64 \ + -DENABLE_BITCODE=0 \ + -DCMAKE_BINARY_DIR=$(pwd) \ + -DCMAKE_PREFIX_PATH="$boostPrefix;$ffmpegDir;$sdlLibsDir" \ + -DSDL2_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL/include \ + -DSDL2_IMAGE_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_image-release-2.0.5 \ + -DSDL2_MIXER_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_mixer-release-2.0.4 \ + -DSDL2_TTF_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_ttf-release-2.0.15 \ + -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED=NO diff --git a/ios.toolchain.cmake b/ios.toolchain.cmake new file mode 100644 index 000000000..94db9fc25 --- /dev/null +++ b/ios.toolchain.cmake @@ -0,0 +1,747 @@ +# This file is part of the ios-cmake project. It was retrieved from +# https://github.com/gerstrong/ios-cmake.git which is a fork of +# https://github.com/cristeab/ios-cmake.git, which again is a fork of +# https://code.google.com/p/ios-cmake/. Which in turn is based off of +# the Platform/Darwin.cmake and Platform/UnixPaths.cmake files which +# are included with CMake 2.8.4 +# +# The ios-cmake project is licensed under the new BSD license. +# +# Copyright (c) 2014, Bogdan Cristea and LTE Engineering Software, +# Kitware, Inc., Insight Software Consortium. All rights reserved. +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# 3. Neither the name of the copyright holder nor the names of its +# contributors may be used to endorse or promote products derived from +# this software without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS +# FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE +# COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, +# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, +# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN +# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +# POSSIBILITY OF SUCH DAMAGE. +# +# This file is based off of the Platform/Darwin.cmake and +# Platform/UnixPaths.cmake files which are included with CMake 2.8.4 +# It has been altered for iOS development. +# +# Updated by Alex Stewart (alexs.mac@gmail.com) +# +# ***************************************************************************** +# Now maintained by Alexander Widerberg (widerbergaren [at] gmail.com) +# under the BSD-3-Clause license +# https://github.com/leetal/ios-cmake +# ***************************************************************************** +# +# INFORMATION / HELP +# +# The following arguments control the behaviour of this toolchain: +# +# PLATFORM: (default "OS") +# OS = Build for iPhoneOS. +# OS64 = Build for arm64 iphoneOS. +# OS64COMBINED = Build for arm64 x86_64 iphoneOS. Combined into FAT STATIC lib (supported on 3.14+ of CMakewith "-G Xcode" argument ONLY) +# SIMULATOR = Build for x86 i386 iphoneOS Simulator. +# SIMULATOR64 = Build for x86_64 iphoneOS Simulator. +# SIMULATORARM64 = Build for arm64 iphoneOS Simulator. +# TVOS = Build for arm64 tvOS. +# TVOSCOMBINED = Build for arm64 x86_64 tvOS. Combined into FAT STATIC lib (supported on 3.14+ of CMake with "-G Xcode" argument ONLY) +# SIMULATOR_TVOS = Build for x86_64 tvOS Simulator. +# WATCHOS = Build for armv7k arm64_32 for watchOS. +# WATCHOSCOMBINED = Build for armv7k arm64_32 x86_64 watchOS. Combined into FAT STATIC lib (supported on 3.14+ of CMake with "-G Xcode" argument ONLY) +# SIMULATOR_WATCHOS = Build for x86_64 for watchOS Simulator. +# +# CMAKE_OSX_SYSROOT: Path to the SDK to use. By default this is +# automatically determined from PLATFORM and xcodebuild, but +# can also be manually specified (although this should not be required). +# +# CMAKE_DEVELOPER_ROOT: Path to the Developer directory for the platform +# being compiled for. By default this is automatically determined from +# CMAKE_OSX_SYSROOT, but can also be manually specified (although this should +# not be required). +# +# DEPLOYMENT_TARGET: Minimum SDK version to target. Default 2.0 on watchOS and 9.0 on tvOS+iOS +# +# ENABLE_BITCODE: (1|0) Enables or disables bitcode support. Default 1 (true) +# +# ENABLE_ARC: (1|0) Enables or disables ARC support. Default 1 (true, ARC enabled by default) +# +# ENABLE_VISIBILITY: (1|0) Enables or disables symbol visibility support. Default 0 (false, visibility hidden by default) +# +# ENABLE_STRICT_TRY_COMPILE: (1|0) Enables or disables strict try_compile() on all Check* directives (will run linker +# to actually check if linking is possible). Default 0 (false, will set CMAKE_TRY_COMPILE_TARGET_TYPE to STATIC_LIBRARY) +# +# ARCHS: (armv7 armv7s armv7k arm64 arm64_32 i386 x86_64) If specified, will override the default architectures for the given PLATFORM +# OS = armv7 armv7s arm64 (if applicable) +# OS64 = arm64 (if applicable) +# SIMULATOR = i386 +# SIMULATOR64 = x86_64 +# SIMULATORARM64 = arm64 +# TVOS = arm64 +# SIMULATOR_TVOS = x86_64 (i386 has since long been deprecated) +# WATCHOS = armv7k arm64_32 (if applicable) +# SIMULATOR_WATCHOS = x86_64 (i386 has since long been deprecated) +# +# This toolchain defines the following variables for use externally: +# +# XCODE_VERSION: Version number (not including Build version) of Xcode detected. +# SDK_VERSION: Version of SDK being used. +# CMAKE_OSX_ARCHITECTURES: Architectures being compiled for (generated from PLATFORM). +# APPLE_TARGET_TRIPLE: Used by autoconf build systems. NOTE: If "ARCHS" are overridden, this will *NOT* be set! +# +# This toolchain defines the following macros for use externally: +# +# set_xcode_property (TARGET XCODE_PROPERTY XCODE_VALUE XCODE_VARIANT) +# A convenience macro for setting xcode specific properties on targets. +# Available variants are: All, Release, RelWithDebInfo, Debug, MinSizeRel +# example: set_xcode_property (myioslib IPHONEOS_DEPLOYMENT_TARGET "3.1" "all"). +# +# find_host_package (PROGRAM ARGS) +# A macro used to find executable programs on the host system, not within the +# environment. Thanks to the android-cmake project for providing the +# command. +# +# ******************************** DEPRECATIONS ******************************* +# +# IOS_DEPLOYMENT_TARGET: (Deprecated) Alias to DEPLOYMENT_TARGET +# CMAKE_IOS_DEVELOPER_ROOT: (Deprecated) Alias to CMAKE_DEVELOPER_ROOT +# IOS_PLATFORM: (Deprecated) Alias to PLATFORM +# IOS_ARCH: (Deprecated) Alias to ARCHS +# +# ***************************************************************************** +# + +# Fix for PThread library not in path +set(CMAKE_THREAD_LIBS_INIT "-lpthread") +set(CMAKE_HAVE_THREADS_LIBRARY 1) +set(CMAKE_USE_WIN32_THREADS_INIT 0) +set(CMAKE_USE_PTHREADS_INIT 1) + +# Cache what generator is used +set(USED_CMAKE_GENERATOR "${CMAKE_GENERATOR}" CACHE STRING "Expose CMAKE_GENERATOR" FORCE) + +if(${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.14") + set(MODERN_CMAKE YES) +endif() + +# Get the Xcode version being used. +execute_process(COMMAND xcodebuild -version + OUTPUT_VARIABLE XCODE_VERSION + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) +string(REGEX MATCH "Xcode [0-9\\.]+" XCODE_VERSION "${XCODE_VERSION}") +string(REGEX REPLACE "Xcode ([0-9\\.]+)" "\\1" XCODE_VERSION "${XCODE_VERSION}") + +# Assuming that xcode 12.0 is installed you most probably have ios sdk 14.2 or later installed (tested on Big Sur) +# if you don't set a deployment target it will be set the way you only get 64-bit builds +if(NOT DEFINED DEPLOYMENT_TARGET AND XCODE_VERSION VERSION_GREATER 12.0) + option(DROP_32_BIT "Will make drop 32-bit support universally. On later sdks you won't be able to build 32-bit apps" yes) + # Temporarily fix the arm64 issues in CMake install-combined by excluding arm64 for simulator builds (needed for Apple Silicon...) + set(CMAKE_XCODE_ATTRIBUTE_EXCLUDED_ARCHS[sdk=iphonesimulator*] "arm64") +endif() + +######## ALIASES (DEPRECATION WARNINGS) + +if(DEFINED IOS_PLATFORM) + set(PLATFORM ${IOS_PLATFORM}) + message(DEPRECATION "IOS_PLATFORM argument is DEPRECATED. Consider using the new PLATFORM argument instead.") +endif() + +if(DEFINED IOS_DEPLOYMENT_TARGET) + set(DEPLOYMENT_TARGET ${IOS_DEPLOYMENT_TARGET}) + message(DEPRECATION "IOS_DEPLOYMENT_TARGET argument is DEPRECATED. Consider using the new DEPLOYMENT_TARGET argument instead.") +endif() + +if(DEFINED CMAKE_IOS_DEVELOPER_ROOT) + set(CMAKE_DEVELOPER_ROOT ${CMAKE_IOS_DEVELOPER_ROOT}) + message(DEPRECATION "CMAKE_IOS_DEVELOPER_ROOT argument is DEPRECATED. Consider using the new CMAKE_DEVELOPER_ROOT argument instead.") +endif() + +if(DEFINED IOS_ARCH) + set(ARCHS ${IOS_ARCH}) + message(DEPRECATION "IOS_ARCH argument is DEPRECATED. Consider using the new ARCHS argument instead.") +endif() + +######## END ALIASES + +# Unset the FORCE on cache variables if in try_compile() +set(FORCE_CACHE FORCE) +get_property(_CMAKE_IN_TRY_COMPILE GLOBAL PROPERTY IN_TRY_COMPILE) +if(_CMAKE_IN_TRY_COMPILE) + unset(FORCE_CACHE) +endif() + +# Default to building for iPhoneOS if not specified otherwise, and we cannot +# determine the platform from the CMAKE_OSX_ARCHITECTURES variable. The use +# of CMAKE_OSX_ARCHITECTURES is such that try_compile() projects can correctly +# determine the value of PLATFORM from the root project, as +# CMAKE_OSX_ARCHITECTURES is propagated to them by CMake. +if(NOT DEFINED PLATFORM) + if (CMAKE_OSX_ARCHITECTURES) + if(CMAKE_OSX_ARCHITECTURES MATCHES "arm64" AND CMAKE_OSX_SYSROOT MATCHES ".*iphoneos.*") + set(PLATFORM "OS64") + elseif(CMAKE_OSX_ARCHITECTURES MATCHES ".*arm.*" AND CMAKE_OSX_SYSROOT MATCHES ".*iphoneos.*") + set(PLATFORM "OS") + elseif(CMAKE_OSX_ARCHITECTURES MATCHES "i386" AND CMAKE_OSX_SYSROOT MATCHES ".*iphonesimulator.*") + set(PLATFORM "SIMULATOR") + elseif(CMAKE_OSX_ARCHITECTURES MATCHES "x86_64" AND CMAKE_OSX_SYSROOT MATCHES ".*iphonesimulator.*") + set(PLATFORM "SIMULATOR64") + elseif(CMAKE_OSX_ARCHITECTURES MATCHES "arm64" AND CMAKE_OSX_SYSROOT MATCHES ".*iphonesimulator.*") + set(PLATFORM "SIMULATORARM64") + elseif(CMAKE_OSX_ARCHITECTURES MATCHES "arm64" AND CMAKE_OSX_SYSROOT MATCHES ".*appletvos.*") + set(PLATFORM "TVOS") + elseif(CMAKE_OSX_ARCHITECTURES MATCHES "x86_64" AND CMAKE_OSX_SYSROOT MATCHES ".*appletvsimulator.*") + set(PLATFORM "SIMULATOR_TVOS") + elseif(CMAKE_OSX_ARCHITECTURES MATCHES ".*armv7k.*" AND CMAKE_OSX_SYSROOT MATCHES ".*watchos.*") + set(PLATFORM "WATCHOS") + elseif(CMAKE_OSX_ARCHITECTURES MATCHES "i386" AND CMAKE_OSX_SYSROOT MATCHES ".*watchsimulator.*") + set(PLATFORM "SIMULATOR_WATCHOS") + endif() + endif() + if (NOT PLATFORM) + if(DROP_32_BIT) + set(PLATFORM "OS64") + else() + set(PLATFORM "OS") + endif() + endif() +endif() + +set(PLATFORM_INT "${PLATFORM}" CACHE STRING "Type of platform for which the build targets.") + +# Handle the case where we are targeting iOS and a version above 10.3.4 (32-bit support dropped officially) +if(PLATFORM_INT STREQUAL "OS" AND DEPLOYMENT_TARGET VERSION_GREATER_EQUAL 10.3.4) + set(PLATFORM_INT "OS64") + message(STATUS "Targeting minimum SDK version ${DEPLOYMENT_TARGET}. Dropping 32-bit support.") +elseif(PLATFORM_INT STREQUAL "SIMULATOR" AND DEPLOYMENT_TARGET VERSION_GREATER_EQUAL 10.3.4) + set(PLATFORM_INT "SIMULATOR64") + message(STATUS "Targeting minimum SDK version ${DEPLOYMENT_TARGET}. Dropping 32-bit support.") +endif() + +# Determine the platform name and architectures for use in xcodebuild commands +# from the specified PLATFORM name. +if(PLATFORM_INT STREQUAL "OS") + set(SDK_NAME iphoneos) + if(NOT ARCHS) + set(ARCHS armv7 armv7s arm64) + set(APPLE_TARGET_TRIPLE_INT arm-apple-ios) + endif() +elseif(PLATFORM_INT STREQUAL "OS64") + set(SDK_NAME iphoneos) + if(NOT ARCHS) + if (XCODE_VERSION VERSION_GREATER 10.0) + set(ARCHS arm64) # Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example + else() + set(ARCHS arm64) + endif() + set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios) + endif() +elseif(PLATFORM_INT STREQUAL "OS64COMBINED") + set(SDK_NAME iphoneos) + if(MODERN_CMAKE) + if(NOT ARCHS) + if (XCODE_VERSION VERSION_GREATER 10.0) + set(ARCHS arm64 x86_64) # Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example + else() + set(ARCHS arm64 x86_64) + endif() + set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-ios) + endif() + else() + message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the OS64COMBINED setting work") + endif() +elseif(PLATFORM_INT STREQUAL "SIMULATOR") + set(SDK_NAME iphonesimulator) + if(NOT ARCHS) + set(ARCHS i386) + set(APPLE_TARGET_TRIPLE_INT i386-apple-ios) + endif() + message(DEPRECATION "SIMULATOR IS DEPRECATED. Consider using SIMULATOR64 instead.") +elseif(PLATFORM_INT STREQUAL "SIMULATOR64") + set(SDK_NAME iphonesimulator) + if(NOT ARCHS) + set(ARCHS x86_64) + set(APPLE_TARGET_TRIPLE_INT x86_64-apple-ios) + endif() +elseif(PLATFORM_INT STREQUAL "SIMULATORARM64") + set(SDK_NAME iphonesimulator) + if(NOT ARCHS) + set(ARCHS arm64) + set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios) + endif() +elseif(PLATFORM_INT STREQUAL "TVOS") + set(SDK_NAME appletvos) + if(NOT ARCHS) + set(ARCHS arm64) + set(APPLE_TARGET_TRIPLE_INT aarch64-apple-tvos) + endif() +elseif (PLATFORM_INT STREQUAL "TVOSCOMBINED") + set(SDK_NAME appletvos) + if(MODERN_CMAKE) + if(NOT ARCHS) + set(ARCHS arm64 x86_64) + set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-tvos) + endif() + else() + message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the TVOSCOMBINED setting work") + endif() +elseif(PLATFORM_INT STREQUAL "SIMULATOR_TVOS") + set(SDK_NAME appletvsimulator) + if(NOT ARCHS) + set(ARCHS x86_64) + set(APPLE_TARGET_TRIPLE_INT x86_64-apple-tvos) + endif() +elseif(PLATFORM_INT STREQUAL "WATCHOS") + set(SDK_NAME watchos) + if(NOT ARCHS) + if (XCODE_VERSION VERSION_GREATER 10.0) + set(ARCHS armv7k arm64_32) + set(APPLE_TARGET_TRIPLE_INT aarch64_32-apple-watchos) + else() + set(ARCHS armv7k) + set(APPLE_TARGET_TRIPLE_INT arm-apple-watchos) + endif() + endif() +elseif(PLATFORM_INT STREQUAL "WATCHOSCOMBINED") + set(SDK_NAME watchos) + if(MODERN_CMAKE) + if(NOT ARCHS) + if (XCODE_VERSION VERSION_GREATER 10.0) + set(ARCHS armv7k arm64_32 i386) + set(APPLE_TARGET_TRIPLE_INT aarch64_32-i386-apple-watchos) + else() + set(ARCHS armv7k i386) + set(APPLE_TARGET_TRIPLE_INT arm-i386-apple-watchos) + endif() + endif() + else() + message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the WATCHOSCOMBINED setting work") + endif() +elseif(PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") + set(SDK_NAME watchsimulator) + if(NOT ARCHS) + set(ARCHS i386) + set(APPLE_TARGET_TRIPLE_INT i386-apple-watchos) + endif() +else() + message(FATAL_ERROR "Invalid PLATFORM: ${PLATFORM_INT}") +endif() + +if(MODERN_CMAKE AND PLATFORM_INT MATCHES ".*COMBINED" AND NOT USED_CMAKE_GENERATOR MATCHES "Xcode") + message(FATAL_ERROR "The COMBINED options only work with Xcode generator, -G Xcode") +endif() + +# If user did not specify the SDK root to use, then query xcodebuild for it. +execute_process(COMMAND xcodebuild -version -sdk ${SDK_NAME} Path + OUTPUT_VARIABLE CMAKE_OSX_SYSROOT_INT + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) +if (NOT DEFINED CMAKE_OSX_SYSROOT_INT AND NOT DEFINED CMAKE_OSX_SYSROOT) + message(SEND_ERROR "Please make sure that Xcode is installed and that the toolchain" + "is pointing to the correct path. Please run:" + "sudo xcode-select -s /Applications/Xcode.app/Contents/Developer" + "and see if that fixes the problem for you.") + message(FATAL_ERROR "Invalid CMAKE_OSX_SYSROOT: ${CMAKE_OSX_SYSROOT} " + "does not exist.") +elseif(DEFINED CMAKE_OSX_SYSROOT_INT) + set(CMAKE_OSX_SYSROOT "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") +endif() + +# Set Xcode property for SDKROOT as well if Xcode generator is used +if(USED_CMAKE_GENERATOR MATCHES "Xcode") + set(CMAKE_OSX_SYSROOT "${SDK_NAME}" CACHE INTERNAL "") +endif() + +# Specify minimum version of deployment target. +if(NOT DEFINED DEPLOYMENT_TARGET) + if (PLATFORM_INT STREQUAL "WATCHOS" OR PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") + # Unless specified, SDK version 2.0 is used by default as minimum target version (watchOS). + set(DEPLOYMENT_TARGET "2.0" + CACHE STRING "Minimum SDK version to build for." ) + else() + # Unless specified, SDK version 9.0 is used by default as minimum target version (iOS, tvOS). + set(DEPLOYMENT_TARGET "9.0" + CACHE STRING "Minimum SDK version to build for." ) + endif() + message(STATUS "Using the default min-version since DEPLOYMENT_TARGET not provided!") +endif() + +# Use bitcode or not +if(NOT DEFINED ENABLE_BITCODE AND NOT ARCHS MATCHES "((^|;|, )(i386|x86_64))+") + # Unless specified, enable bitcode support by default + message(STATUS "Enabling bitcode support by default. ENABLE_BITCODE not provided!") + set(ENABLE_BITCODE TRUE) +elseif(NOT DEFINED ENABLE_BITCODE) + message(STATUS "Disabling bitcode support by default on simulators. ENABLE_BITCODE not provided for override!") + set(ENABLE_BITCODE FALSE) +endif() +set(ENABLE_BITCODE_INT ${ENABLE_BITCODE} CACHE BOOL "Whether or not to enable bitcode" ${FORCE_CACHE}) +# Use ARC or not +if(NOT DEFINED ENABLE_ARC) + # Unless specified, enable ARC support by default + set(ENABLE_ARC TRUE) + message(STATUS "Enabling ARC support by default. ENABLE_ARC not provided!") +endif() +set(ENABLE_ARC_INT ${ENABLE_ARC} CACHE BOOL "Whether or not to enable ARC" ${FORCE_CACHE}) +# Use hidden visibility or not +if(NOT DEFINED ENABLE_VISIBILITY) + # Unless specified, disable symbols visibility by default + set(ENABLE_VISIBILITY FALSE) + message(STATUS "Hiding symbols visibility by default. ENABLE_VISIBILITY not provided!") +endif() +set(ENABLE_VISIBILITY_INT ${ENABLE_VISIBILITY} CACHE BOOL "Whether or not to hide symbols (-fvisibility=hidden)" ${FORCE_CACHE}) +# Set strict compiler checks or not +if(NOT DEFINED ENABLE_STRICT_TRY_COMPILE) + # Unless specified, disable strict try_compile() + set(ENABLE_STRICT_TRY_COMPILE FALSE) + message(STATUS "Using NON-strict compiler checks by default. ENABLE_STRICT_TRY_COMPILE not provided!") +endif() +set(ENABLE_STRICT_TRY_COMPILE_INT ${ENABLE_STRICT_TRY_COMPILE} CACHE BOOL "Whether or not to use strict compiler checks" ${FORCE_CACHE}) +# Get the SDK version information. +execute_process(COMMAND xcodebuild -sdk ${CMAKE_OSX_SYSROOT} -version SDKVersion + OUTPUT_VARIABLE SDK_VERSION + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) + +# Find the Developer root for the specific iOS platform being compiled for +# from CMAKE_OSX_SYSROOT. Should be ../../ from SDK specified in +# CMAKE_OSX_SYSROOT. There does not appear to be a direct way to obtain +# this information from xcrun or xcodebuild. +if (NOT DEFINED CMAKE_DEVELOPER_ROOT AND NOT USED_CMAKE_GENERATOR MATCHES "Xcode") + get_filename_component(PLATFORM_SDK_DIR ${CMAKE_OSX_SYSROOT} PATH) + get_filename_component(CMAKE_DEVELOPER_ROOT ${PLATFORM_SDK_DIR} PATH) + if (NOT DEFINED CMAKE_DEVELOPER_ROOT) + message(FATAL_ERROR "Invalid CMAKE_DEVELOPER_ROOT: " + "${CMAKE_DEVELOPER_ROOT} does not exist.") + endif() +endif() +# Find the C & C++ compilers for the specified SDK. +if(NOT CMAKE_C_COMPILER) + execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT} -find clang + OUTPUT_VARIABLE CMAKE_C_COMPILER + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) + message(STATUS "Using C compiler: ${CMAKE_C_COMPILER}") +endif() +if(NOT CMAKE_CXX_COMPILER) + execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT} -find clang++ + OUTPUT_VARIABLE CMAKE_CXX_COMPILER + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) + message(STATUS "Using CXX compiler: ${CMAKE_CXX_COMPILER}") +endif() +# Find (Apple's) libtool. +execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT} -find libtool + OUTPUT_VARIABLE BUILD_LIBTOOL + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) +message(STATUS "Using libtool: ${BUILD_LIBTOOL}") +# Configure libtool to be used instead of ar + ranlib to build static libraries. +# This is required on Xcode 7+, but should also work on previous versions of +# Xcode. +set(CMAKE_C_CREATE_STATIC_LIBRARY + "${BUILD_LIBTOOL} -static -o ") +set(CMAKE_CXX_CREATE_STATIC_LIBRARY + "${BUILD_LIBTOOL} -static -o ") +# Find the toolchain's provided install_name_tool if none is found on the host +if(NOT CMAKE_INSTALL_NAME_TOOL) + execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT} -find install_name_tool + OUTPUT_VARIABLE CMAKE_INSTALL_NAME_TOOL_INT + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) + set(CMAKE_INSTALL_NAME_TOOL ${CMAKE_INSTALL_NAME_TOOL_INT} CACHE STRING "" ${FORCE_CACHE}) +endif() +# Get the version of Darwin (OS X) of the host. +execute_process(COMMAND uname -r + OUTPUT_VARIABLE CMAKE_HOST_SYSTEM_VERSION + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) +if(SDK_NAME MATCHES "iphone") + set(CMAKE_SYSTEM_NAME iOS CACHE INTERNAL "" ${FORCE_CACHE}) +endif() +# CMake 3.14+ support building for iOS, watchOS and tvOS out of the box. +if(MODERN_CMAKE) + if(SDK_NAME MATCHES "appletv") + set(CMAKE_SYSTEM_NAME tvOS CACHE INTERNAL "" ${FORCE_CACHE}) + elseif(SDK_NAME MATCHES "watch") + set(CMAKE_SYSTEM_NAME watchOS CACHE INTERNAL "" ${FORCE_CACHE}) + endif() + # Provide flags for a combined FAT library build on newer CMake versions + if(PLATFORM_INT MATCHES ".*COMBINED") + set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH "NO") + set(CMAKE_IOS_INSTALL_COMBINED YES CACHE INTERNAL "" ${FORCE_CACHE}) + message(STATUS "Will combine built (static) artifacts into FAT lib...") + endif() +elseif(${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.10") + # Legacy code path prior to CMake 3.14 or fallback if no SDK_NAME specified + set(CMAKE_SYSTEM_NAME iOS CACHE INTERNAL "" ${FORCE_CACHE}) +else() + # Legacy code path prior to CMake 3.14 or fallback if no SDK_NAME specified + set(CMAKE_SYSTEM_NAME Darwin CACHE INTERNAL "" ${FORCE_CACHE}) +endif() +# Standard settings. +set(CMAKE_SYSTEM_VERSION ${SDK_VERSION} CACHE INTERNAL "") +set(UNIX TRUE CACHE BOOL "") +set(APPLE TRUE CACHE BOOL "") +set(IOS TRUE CACHE BOOL "") +set(CMAKE_AR ar CACHE FILEPATH "" FORCE) +set(CMAKE_RANLIB ranlib CACHE FILEPATH "" FORCE) +set(CMAKE_STRIP strip CACHE FILEPATH "" FORCE) +# Set the architectures for which to build. +set(CMAKE_OSX_ARCHITECTURES ${ARCHS} CACHE STRING "Build architecture for iOS") +# Change the type of target generated for try_compile() so it'll work when cross-compiling, weak compiler checks +if(ENABLE_STRICT_TRY_COMPILE_INT) + message(STATUS "Using strict compiler checks (default in CMake).") +else() + set(CMAKE_TRY_COMPILE_TARGET_TYPE STATIC_LIBRARY) +endif() +# All iOS/Darwin specific settings - some may be redundant. +set(CMAKE_MACOSX_BUNDLE YES) +set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_REQUIRED "NO") +set(CMAKE_SHARED_LIBRARY_PREFIX "lib") +set(CMAKE_SHARED_LIBRARY_SUFFIX ".dylib") +set(CMAKE_SHARED_MODULE_PREFIX "lib") +set(CMAKE_SHARED_MODULE_SUFFIX ".so") +set(CMAKE_C_COMPILER_ABI ELF) +set(CMAKE_CXX_COMPILER_ABI ELF) +set(CMAKE_C_HAS_ISYSROOT 1) +set(CMAKE_CXX_HAS_ISYSROOT 1) +set(CMAKE_MODULE_EXISTS 1) +set(CMAKE_DL_LIBS "") +set(CMAKE_C_OSX_COMPATIBILITY_VERSION_FLAG "-compatibility_version ") +set(CMAKE_C_OSX_CURRENT_VERSION_FLAG "-current_version ") +set(CMAKE_CXX_OSX_COMPATIBILITY_VERSION_FLAG "${CMAKE_C_OSX_COMPATIBILITY_VERSION_FLAG}") +set(CMAKE_CXX_OSX_CURRENT_VERSION_FLAG "${CMAKE_C_OSX_CURRENT_VERSION_FLAG}") + +if(ARCHS MATCHES "((^|;|, )(arm64|arm64e|x86_64))+") + set(CMAKE_C_SIZEOF_DATA_PTR 8) + set(CMAKE_CXX_SIZEOF_DATA_PTR 8) + if(ARCHS MATCHES "((^|;|, )(arm64|arm64e))+") + set(CMAKE_SYSTEM_PROCESSOR "aarch64") + else() + set(CMAKE_SYSTEM_PROCESSOR "x86_64") + endif() +else() + set(CMAKE_C_SIZEOF_DATA_PTR 4) + set(CMAKE_CXX_SIZEOF_DATA_PTR 4) + set(CMAKE_SYSTEM_PROCESSOR "arm") +endif() + +# Note that only Xcode 7+ supports the newer more specific: +# -m${SDK_NAME}-version-min flags, older versions of Xcode use: +# -m(ios/ios-simulator)-version-min instead. +if(${CMAKE_VERSION} VERSION_LESS "3.11") + if(PLATFORM_INT STREQUAL "OS" OR PLATFORM_INT STREQUAL "OS64") + if(XCODE_VERSION VERSION_LESS 7.0) + set(SDK_NAME_VERSION_FLAGS + "-mios-version-min=${DEPLOYMENT_TARGET}") + else() + # Xcode 7.0+ uses flags we can build directly from SDK_NAME. + set(SDK_NAME_VERSION_FLAGS + "-m${SDK_NAME}-version-min=${DEPLOYMENT_TARGET}") + endif() + elseif(PLATFORM_INT STREQUAL "TVOS") + set(SDK_NAME_VERSION_FLAGS + "-mtvos-version-min=${DEPLOYMENT_TARGET}") + elseif(PLATFORM_INT STREQUAL "SIMULATOR_TVOS") + set(SDK_NAME_VERSION_FLAGS + "-mtvos-simulator-version-min=${DEPLOYMENT_TARGET}") + elseif(PLATFORM_INT STREQUAL "WATCHOS") + set(SDK_NAME_VERSION_FLAGS + "-mwatchos-version-min=${DEPLOYMENT_TARGET}") + elseif(PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") + set(SDK_NAME_VERSION_FLAGS + "-mwatchos-simulator-version-min=${DEPLOYMENT_TARGET}") + else() + # SIMULATOR or SIMULATOR64 both use -mios-simulator-version-min. + set(SDK_NAME_VERSION_FLAGS + "-mios-simulator-version-min=${DEPLOYMENT_TARGET}") + endif() +else() + # Newer versions of CMake sets the version min flags correctly + set(CMAKE_OSX_DEPLOYMENT_TARGET ${DEPLOYMENT_TARGET} CACHE STRING + "Set CMake deployment target" ${FORCE_CACHE}) +endif() + +if(DEFINED APPLE_TARGET_TRIPLE_INT) + set(APPLE_TARGET_TRIPLE ${APPLE_TARGET_TRIPLE_INT} CACHE STRING + "Autoconf target triple compatible variable" ${FORCE_CACHE}) +endif() + +if(ENABLE_BITCODE_INT) + set(BITCODE "-fembed-bitcode") + set(CMAKE_XCODE_ATTRIBUTE_BITCODE_GENERATION_MODE "bitcode") + set(CMAKE_XCODE_ATTRIBUTE_ENABLE_BITCODE "YES") +else() + set(BITCODE "") + set(CMAKE_XCODE_ATTRIBUTE_ENABLE_BITCODE "NO") +endif() + +if(ENABLE_ARC_INT) + set(FOBJC_ARC "-fobjc-arc") + set(CMAKE_XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC "YES") +else() + set(FOBJC_ARC "-fno-objc-arc") + set(CMAKE_XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC "NO") +endif() + +if(NOT ENABLE_VISIBILITY_INT) + set(VISIBILITY "-fvisibility=hidden") + set(CMAKE_XCODE_ATTRIBUTE_GCC_SYMBOLS_PRIVATE_EXTERN "YES") +else() + set(VISIBILITY "") + set(CMAKE_XCODE_ATTRIBUTE_GCC_SYMBOLS_PRIVATE_EXTERN "NO") +endif() + +if(NOT IOS_TOOLCHAIN_HAS_RUN) + #Check if Xcode generator is used, since that will handle these flags automagically + if(USED_CMAKE_GENERATOR MATCHES "Xcode") + message(STATUS "Not setting any manual command-line buildflags, since Xcode is selected as generator.") + else() + set(CMAKE_C_FLAGS + "${SDK_NAME_VERSION_FLAGS} ${BITCODE} -fobjc-abi-version=2 ${FOBJC_ARC} ${CMAKE_C_FLAGS}") + # Hidden visibilty is required for C++ on iOS. + set(CMAKE_CXX_FLAGS + "${SDK_NAME_VERSION_FLAGS} ${BITCODE} ${VISIBILITY} -fvisibility-inlines-hidden -fobjc-abi-version=2 ${FOBJC_ARC} ${CMAKE_CXX_FLAGS}") + set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS} -O0 -g ${CMAKE_CXX_FLAGS_DEBUG}") + set(CMAKE_CXX_FLAGS_MINSIZEREL "${CMAKE_CXX_FLAGS} -DNDEBUG -Os -ffast-math ${CMAKE_CXX_FLAGS_MINSIZEREL}") + set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS} -DNDEBUG -O2 -g -ffast-math ${CMAKE_CXX_FLAGS_RELWITHDEBINFO}") + set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS} -DNDEBUG -O3 -ffast-math ${CMAKE_CXX_FLAGS_RELEASE}") + set(CMAKE_C_LINK_FLAGS "${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_C_LINK_FLAGS}") + set(CMAKE_CXX_LINK_FLAGS "${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_CXX_LINK_FLAGS}") + set(CMAKE_ASM_FLAGS "${CFLAGS} -x assembler-with-cpp -arch ${CMAKE_OSX_ARCHITECTURES}") + + # In order to ensure that the updated compiler flags are used in try_compile() + # tests, we have to forcibly set them in the CMake cache, not merely set them + # in the local scope. + set(VARS_TO_FORCE_IN_CACHE + CMAKE_C_FLAGS + CMAKE_CXX_FLAGS + CMAKE_CXX_FLAGS_DEBUG + CMAKE_CXX_FLAGS_RELWITHDEBINFO + CMAKE_CXX_FLAGS_MINSIZEREL + CMAKE_CXX_FLAGS_RELEASE + CMAKE_C_LINK_FLAGS + CMAKE_CXX_LINK_FLAGS) + foreach(VAR_TO_FORCE ${VARS_TO_FORCE_IN_CACHE}) + set(${VAR_TO_FORCE} "${${VAR_TO_FORCE}}" CACHE STRING "" ${FORCE_CACHE}) + endforeach() + endif() + + ## Print status messages to inform of the current state + message(STATUS "Configuring ${SDK_NAME} build for platform: ${PLATFORM_INT}, architecture(s): ${ARCHS}") + message(STATUS "Using SDK: ${CMAKE_OSX_SYSROOT_INT}") + if(DEFINED APPLE_TARGET_TRIPLE) + message(STATUS "Autoconf target triple: ${APPLE_TARGET_TRIPLE}") + endif() + message(STATUS "Using minimum deployment version: ${DEPLOYMENT_TARGET}" + " (SDK version: ${SDK_VERSION})") + if(MODERN_CMAKE) + message(STATUS "Merging integrated CMake 3.14+ iOS,tvOS,watchOS,macOS toolchain(s) with this toolchain!") + endif() + if(USED_CMAKE_GENERATOR MATCHES "Xcode") + message(STATUS "Using Xcode version: ${XCODE_VERSION}") + endif() + if(DEFINED SDK_NAME_VERSION_FLAGS) + message(STATUS "Using version flags: ${SDK_NAME_VERSION_FLAGS}") + endif() + message(STATUS "Using a data_ptr size of: ${CMAKE_CXX_SIZEOF_DATA_PTR}") + message(STATUS "Using install_name_tool: ${CMAKE_INSTALL_NAME_TOOL}") + if(ENABLE_BITCODE_INT) + message(STATUS "Enabling bitcode support.") + else() + message(STATUS "Disabling bitcode support.") + endif() + + if(ENABLE_ARC_INT) + message(STATUS "Enabling ARC support.") + else() + message(STATUS "Disabling ARC support.") + endif() + + if(NOT ENABLE_VISIBILITY_INT) + message(STATUS "Hiding symbols (-fvisibility=hidden).") + endif() +endif() + +set(CMAKE_PLATFORM_HAS_INSTALLNAME 1) +set(CMAKE_SHARED_LINKER_FLAGS "-rpath @executable_path/Frameworks -rpath @loader_path/Frameworks") +set(CMAKE_SHARED_LIBRARY_CREATE_C_FLAGS "-dynamiclib -Wl,-headerpad_max_install_names") +set(CMAKE_SHARED_MODULE_CREATE_C_FLAGS "-bundle -Wl,-headerpad_max_install_names") +set(CMAKE_SHARED_MODULE_LOADER_C_FLAG "-Wl,-bundle_loader,") +set(CMAKE_SHARED_MODULE_LOADER_CXX_FLAG "-Wl,-bundle_loader,") +set(CMAKE_FIND_LIBRARY_SUFFIXES ".tbd" ".dylib" ".so" ".a") +set(CMAKE_SHARED_LIBRARY_SONAME_C_FLAG "-install_name") + +# Set the find root to the iOS developer roots and to user defined paths. +set(CMAKE_FIND_ROOT_PATH ${CMAKE_OSX_SYSROOT_INT} ${CMAKE_PREFIX_PATH} CACHE STRING "Root path that will be prepended + to all search paths") +# Default to searching for frameworks first. +set(CMAKE_FIND_FRAMEWORK FIRST) +# Set up the default search directories for frameworks. +set(CMAKE_FRAMEWORK_PATH + ${CMAKE_DEVELOPER_ROOT}/Library/PrivateFrameworks + ${CMAKE_OSX_SYSROOT_INT}/System/Library/Frameworks + ${CMAKE_FRAMEWORK_PATH} CACHE STRING "Frameworks search paths" ${FORCE_CACHE}) + +set(IOS_TOOLCHAIN_HAS_RUN TRUE CACHE BOOL "Has the CMake toolchain run already?" ${FORCE_CACHE}) + +# By default, search both the specified iOS SDK and the remainder of the host filesystem. +if(NOT CMAKE_FIND_ROOT_PATH_MODE_PROGRAM) + set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH CACHE STRING "" ${FORCE_CACHE}) +endif() +if(NOT CMAKE_FIND_ROOT_PATH_MODE_LIBRARY) + set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH CACHE STRING "" ${FORCE_CACHE}) +endif() +if(NOT CMAKE_FIND_ROOT_PATH_MODE_INCLUDE) + set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH CACHE STRING "" ${FORCE_CACHE}) +endif() +if(NOT CMAKE_FIND_ROOT_PATH_MODE_PACKAGE) + set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE BOTH CACHE STRING "" ${FORCE_CACHE}) +endif() + +# +# Some helper-macros below to simplify and beautify the CMakeFile +# + +# This little macro lets you set any Xcode specific property. +macro(set_xcode_property TARGET XCODE_PROPERTY XCODE_VALUE XCODE_RELVERSION) + set(XCODE_RELVERSION_I "${XCODE_RELVERSION}") + if(XCODE_RELVERSION_I STREQUAL "All") + set_property(TARGET ${TARGET} PROPERTY + XCODE_ATTRIBUTE_${XCODE_PROPERTY} "${XCODE_VALUE}") + else() + set_property(TARGET ${TARGET} PROPERTY + XCODE_ATTRIBUTE_${XCODE_PROPERTY}[variant=${XCODE_RELVERSION_I}] "${XCODE_VALUE}") + endif() +endmacro(set_xcode_property) + +# This macro lets you find executable programs on the host system. +macro(find_host_package) + set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) + set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY NEVER) + set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE NEVER) + set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE NEVER) + set(IOS FALSE) + find_package(${ARGN}) + set(IOS TRUE) + set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH) + set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH) + set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH) + set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE BOTH) +endmacro(find_host_package) diff --git a/osx/CMakeLists.txt b/osx/CMakeLists.txt index 91d343074..6fbcb041b 100644 --- a/osx/CMakeLists.txt +++ b/osx/CMakeLists.txt @@ -1,6 +1,6 @@ # We need to keep this code into separate directory so CMake will execute it after all other subdirectories install code # Otherwise we can't fix Mac bundle dependencies since binaries wouldn't be there when this code executed -if(APPLE) +if(APPLE_MACOS) set(bundleDir "\${CMAKE_INSTALL_PREFIX}/${APP_BUNDLE_DIR}") set(bundleContentsDir "${bundleDir}/Contents") @@ -58,4 +58,4 @@ if(APPLE) ) endforeach() ") -endif(APPLE) \ No newline at end of file +endif() From 7a50620e6158590efdea66c728a3493891e95a27 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 2 Mar 2021 03:50:54 +0300 Subject: [PATCH 003/131] enable clang modules and framework auto-linking --- CMakeLists.txt | 6 ++++++ client/CMakeLists.txt | 1 - client/main_ios.m | 5 +++-- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index f44d6e632..03c4df80a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -224,6 +224,12 @@ if(CMAKE_COMPILER_IS_GNUCXX OR NOT WIN32) #so far all *nix compilers support suc endif() endif() +# TODO: also enable for macOS +if(APPLE_IOS) + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fmodules") + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fmodules") +endif(APPLE_IOS) + # Check if some platform-specific libraries are needed for linking if(NOT WIN32 AND NOT ${CMAKE_SYSTEM_NAME} STREQUAL "iOS") include(CheckLibraryExists) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 5719be336..53fbb1028 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -177,7 +177,6 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - "-framework UIKit" "-framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image ) endif() diff --git a/client/main_ios.m b/client/main_ios.m index f66680475..346defb21 100644 --- a/client/main_ios.m +++ b/client/main_ios.m @@ -1,5 +1,6 @@ -#import -int main (int argc, char const *argv[]) +@import UIKit; + +int main (int argc, char *argv[]) { @autoreleasepool { From d6a92f23aaf7806bd09e2c3a6cb73c9dc586c05c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 2 Mar 2021 03:56:54 +0300 Subject: [PATCH 004/131] fix leading whitespace --- CMakeLists.txt | 28 ++++++++++++++-------------- client/CMakeLists.txt | 4 ++-- 2 files changed, 16 insertions(+), 16 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 03c4df80a..448b879de 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -27,11 +27,11 @@ project(VCMI) # - Make FindFuzzyLite check for the right version and disable FORCE_BUNDLED_FL by default if(APPLE) - if(${CMAKE_SYSTEM_NAME} STREQUAL "Darwin") - set(APPLE_MACOS 1) - else() - set(APPLE_IOS 1) - endif() + if(${CMAKE_SYSTEM_NAME} STREQUAL "Darwin") + set(APPLE_MACOS 1) + else() + set(APPLE_IOS 1) + endif() endif(APPLE) ############################################ @@ -52,7 +52,7 @@ set(VCMI_VERSION_PATCH 0) option(ENABLE_ERM "Enable compilation of ERM scripting module" OFF) option(ENABLE_LUA "Enable compilation of LUA scripting module" OFF) if(NOT APPLE_IOS) - option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) + option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) endif() option(ENABLE_TEST "Enable compilation of unit tests" ON) if(NOT ${CMAKE_VERSION} VERSION_LESS "3.16.0") @@ -64,7 +64,7 @@ option(ENABLE_MULTI_PROCESS_BUILDS "Enable /MP flag for MSVS solution" ON) # Used for Snap packages and also useful for debugging if(NOT APPLE_IOS) - option(ENABLE_MONOLITHIC_INSTALL "Install everything in single directory on Linux and Mac" OFF) + option(ENABLE_MONOLITHIC_INSTALL "Install everything in single directory on Linux and Mac" OFF) endif() # Allow to pass package name from Travis CI @@ -329,13 +329,13 @@ elseif(APPLE) set(DATA_DIR "." CACHE STRING "Where to install data files") else() set(APP_BUNDLE_DIR "${CMAKE_PROJECT_NAME}.app") - if(APPLE_MACOS) - set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}/Contents") - set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_CONTENTS_DIR}/MacOS") - else() - set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}") - set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_DIR}") - endif(APPLE_MACOS) + if(APPLE_MACOS) + set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}/Contents") + set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_CONTENTS_DIR}/MacOS") + else() + set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}") + set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_DIR}") + endif(APPLE_MACOS) set(APP_BUNDLE_RESOURCES_DIR "${APP_BUNDLE_CONTENTS_DIR}/Resources") set(BIN_DIR "${APP_BUNDLE_BINARY_DIR}" CACHE STRING "Where to install binaries") diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 53fbb1028..f96d12cfb 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -177,8 +177,8 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - "-framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image - ) + "-framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image + ) endif() target_link_libraries(vcmiclient PRIVATE From 8249171066711141b4c5884012c7fa48fa59dbc0 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 2 Mar 2021 06:23:00 +0300 Subject: [PATCH 005/131] implement VCMIDirs --- lib/CIOSUtils.h | 15 ++++++++++++ lib/CIOSUtils.m | 24 +++++++++++++++++++ lib/CMakeLists.txt | 5 ++++ lib/VCMIDirs.cpp | 60 ++++++++++++++++++++++++++++++++++++++-------- 4 files changed, 94 insertions(+), 10 deletions(-) create mode 100644 lib/CIOSUtils.h create mode 100644 lib/CIOSUtils.m diff --git a/lib/CIOSUtils.h b/lib/CIOSUtils.h new file mode 100644 index 000000000..0e5ac20cc --- /dev/null +++ b/lib/CIOSUtils.h @@ -0,0 +1,15 @@ +/* + * CIOSUtils.h, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ + +extern const char *ios_documentsPath(); +extern const char *ios_cachesPath(); + +extern const char *ios_bundlePath(); +extern const char *ios_frameworksPath(); diff --git a/lib/CIOSUtils.m b/lib/CIOSUtils.m new file mode 100644 index 000000000..f3f765352 --- /dev/null +++ b/lib/CIOSUtils.m @@ -0,0 +1,24 @@ +/* + * CIOSUtils.m, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ + +#import "CIOSUtils.h" + +@import Foundation; + +static const char *standardPath(NSSearchPathDirectory directory) +{ + return [NSFileManager.defaultManager URLForDirectory:directory inDomain:NSUserDomainMask appropriateForURL:nil create:NO error:NULL].path.UTF8String; +} + +const char *ios_documentsPath() { return standardPath(NSDocumentDirectory); } +const char *ios_cachesPath() { return standardPath(NSCachesDirectory); } + +const char *ios_bundlePath() { return NSBundle.mainBundle.bundlePath.UTF8String; } +const char *ios_frameworksPath() { return [NSBundle.mainBundle.bundlePath stringByAppendingPathComponent:@"Frameworks"].UTF8String; } // TODO: sharedFrameworksPath? diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt index c816b6331..76f4cc4a5 100644 --- a/lib/CMakeLists.txt +++ b/lib/CMakeLists.txt @@ -439,6 +439,11 @@ set(lib_HEADERS VCMI_Lib.h ) +if(APPLE_IOS) + set(lib_SRCS ${lib_SRCS} CIOSUtils.m) + set(lib_HEADERS ${lib_HEADERS} CIOSUtils.h) +endif(APPLE_IOS) + assign_source_group(${lib_SRCS} ${lib_HEADERS}) add_library(vcmi SHARED ${lib_SRCS} ${lib_HEADERS}) diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index ee42f02b5..ecac91b86 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -349,7 +349,7 @@ class IVCMIDirsUNIX : public IVCMIDirs boost::filesystem::path clientPath() const override; boost::filesystem::path serverPath() const override; - bool developmentMode() const; + virtual bool developmentMode() const; }; bool IVCMIDirsUNIX::developmentMode() const @@ -362,12 +362,54 @@ bfs::path IVCMIDirsUNIX::clientPath() const { return binaryPath() / "vcmiclient" bfs::path IVCMIDirsUNIX::serverPath() const { return binaryPath() / "vcmiserver"; } #ifdef VCMI_APPLE -class VCMIDirsOSX final : public IVCMIDirsUNIX +class VCMIDirsApple : public IVCMIDirsUNIX +{ + public: + bfs::path userConfigPath() const override; + + std::string libraryName(const std::string& basename) const override; +}; + +bfs::path VCMIDirsApple::userConfigPath() const { return userDataPath() / "config"; } + +std::string VCMIDirsApple::libraryName(const std::string& basename) const { return "lib" + basename + ".dylib"; } + +#ifdef VCMI_IOS +extern "C" { +#import "CIOSUtils.h" +} + +class VCMIDirsIOS final : public VCMIDirsApple +{ + public: + bfs::path userDataPath() const override; + bfs::path userCachePath() const override; + bfs::path userLogsPath() const override; + + std::vector dataPaths() const override; + + bfs::path libraryPath() const override; + bfs::path binaryPath() const override; + + bool developmentMode() const override; +}; + +bfs::path VCMIDirsIOS::userDataPath() const { return {ios_documentsPath()}; } +bfs::path VCMIDirsIOS::userCachePath() const { return {ios_cachesPath()}; } +bfs::path VCMIDirsIOS::userLogsPath() const { return {ios_documentsPath()}; } + +std::vector VCMIDirsIOS::dataPaths() const { return {userDataPath()}; } + +bfs::path VCMIDirsIOS::libraryPath() const { return {ios_frameworksPath()}; } +bfs::path VCMIDirsIOS::binaryPath() const { return {ios_bundlePath()}; } + +bool VCMIDirsIOS::developmentMode() const { return false; } +#elif defined(VCMI_MAC) +class VCMIDirsOSX final : public VCMIDirsApple { public: boost::filesystem::path userDataPath() const override; boost::filesystem::path userCachePath() const override; - boost::filesystem::path userConfigPath() const override; boost::filesystem::path userLogsPath() const override; std::vector dataPaths() const override; @@ -375,8 +417,6 @@ class VCMIDirsOSX final : public IVCMIDirsUNIX boost::filesystem::path libraryPath() const override; boost::filesystem::path binaryPath() const override; - std::string libraryName(const std::string& basename) const override; - void init() override; }; @@ -436,7 +476,6 @@ bfs::path VCMIDirsOSX::userDataPath() const return bfs::path(homeDir) / "Library" / "Application Support" / "vcmi"; } bfs::path VCMIDirsOSX::userCachePath() const { return userDataPath(); } -bfs::path VCMIDirsOSX::userConfigPath() const { return userDataPath() / "config"; } bfs::path VCMIDirsOSX::userLogsPath() const { @@ -463,8 +502,7 @@ std::vector VCMIDirsOSX::dataPaths() const bfs::path VCMIDirsOSX::libraryPath() const { return "."; } bfs::path VCMIDirsOSX::binaryPath() const { return "."; } - -std::string VCMIDirsOSX::libraryName(const std::string& basename) const { return "lib" + basename + ".dylib"; } +#endif // VCMI_IOS, VCMI_MAC #elif defined(VCMI_XDG) class VCMIDirsXDG : public IVCMIDirsUNIX { @@ -635,9 +673,11 @@ namespace VCMIDirs static VCMIDirsAndroid singleton; #elif defined(VCMI_XDG) static VCMIDirsXDG singleton; - #elif defined(VCMI_APPLE) + #elif defined(VCMI_MAC) static VCMIDirsOSX singleton; - #endif + #elif defined(VCMI_IOS) + static VCMIDirsIOS singleton; + #endif static bool initialized = false; if (!initialized) From c4233ad7064da72f63cc7fa2c28183c0d4b94e29 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 2 Mar 2021 06:56:57 +0300 Subject: [PATCH 006/131] exclude some code similar to android --- client/CMT.cpp | 2 +- client/CServerHandler.cpp | 24 +++++++++++++++--------- server/CVCMIServer.cpp | 18 +++++++++--------- 3 files changed, 25 insertions(+), 19 deletions(-) diff --git a/client/CMT.cpp b/client/CMT.cpp index 5754814b8..ffeea5d7a 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -170,7 +170,7 @@ int main(int argc, char * argv[]) setenv("LANG", "C", 1); #endif -#ifndef VCMI_ANDROID +#if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) // Correct working dir executable folder (not bundle folder) so we can use executable relative paths boost::filesystem::current_path(boost::filesystem::system_complete(argv[0]).parent_path()); #endif diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index d24903da6..93d44cefa 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -21,10 +21,12 @@ #include "mainmenu/CMainMenu.h" -#ifndef VCMI_ANDROID -#include "../lib/Interprocess.h" -#else +#ifdef VCMI_ANDROID #include "../lib/CAndroidVMHelper.h" +#elif defined(VCMI_IOS) +//TODO +#else +#include "../lib/Interprocess.h" #endif #include "../lib/CConfigHandler.h" #include "../lib/CGeneralTextHandler.h" @@ -132,7 +134,7 @@ void CServerHandler::resetStateForLobby(const StartInfo::EMode mode, const std:: else myNames.push_back(settings["general"]["playerName"].String()); -#ifndef VCMI_ANDROID +#if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) shm.reset(); if(!settings["session"]["disable-shm"].Bool()) @@ -181,6 +183,8 @@ void CServerHandler::startLocalServerAndConnect() CAndroidVMHelper envHelper; envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true); } +#elif defined(VCMI_IOS) + // TODO #else threadRunLocalServer = std::make_shared(&CServerHandler::threadRunServer, this); //runs server executable; #endif @@ -188,10 +192,7 @@ void CServerHandler::startLocalServerAndConnect() th->update(); -#ifndef VCMI_ANDROID - if(shm) - shm->sr->waitTillReady(); -#else +#ifdef VCMI_ANDROID logNetwork->info("waiting for server"); while(!androidTestServerReadyFlag.load()) { @@ -200,12 +201,17 @@ void CServerHandler::startLocalServerAndConnect() } logNetwork->info("waiting for server finished..."); androidTestServerReadyFlag = false; +#elif defined(VCMI_IOS) + //TODO +#else + if(shm) + shm->sr->waitTillReady(); #endif logNetwork->trace("Waiting for server: %d ms", th->getDiff()); th->update(); //put breakpoint here to attach to server before it does something stupid -#ifndef VCMI_ANDROID +#if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) justConnectToServer(settings["server"]["server"].String(), shm ? shm->sr->port : 0); #else justConnectToServer(settings["server"]["server"].String()); diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index 5cef5f553..71b78b153 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -29,6 +29,8 @@ #include "../lib/rmg/CMapGenOptions.h" #ifdef VCMI_ANDROID #include "lib/CAndroidVMHelper.h" +#elif defined(VCMI_IOS) + //TODO #else #include "../lib/Interprocess.h" #endif @@ -55,7 +57,7 @@ #include "../lib/CGameState.h" -#if defined(__GNUC__) && !defined(__MINGW32__) && !defined(VCMI_ANDROID) +#if defined(__GNUC__) && !defined(__MINGW32__) && !defined(VCMI_ANDROID) && !defined(VCMI_IOS) #include #endif @@ -157,7 +159,7 @@ void CVCMIServer::run() if(!restartGameplay) { this->announceLobbyThread = vstd::make_unique(&CVCMIServer::threadAnnounceLobby, this); -#ifndef VCMI_ANDROID +#if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) if(cmdLineOptions.count("enable-shm")) { std::string sharedMemoryName = "vcmi_memory"; @@ -171,14 +173,11 @@ void CVCMIServer::run() startAsyncAccept(); -#ifndef VCMI_ANDROID +#if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) if(shm) { shm->sr->setToReadyAndNotify(port); } -#else - CAndroidVMHelper vmHelper; - vmHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "onServerReady"); #endif } @@ -829,7 +828,7 @@ ui8 CVCMIServer::getIdOfFirstUnallocatedPlayer() const return 0; } -#if defined(__GNUC__) && !defined(__MINGW32__) && !defined(VCMI_ANDROID) +#if defined(__GNUC__) && !defined(__MINGW32__) && !defined(VCMI_ANDROID) && !defined(VCMI_IOS) void handleLinuxSignal(int sig) { const int STACKTRACE_SIZE = 100; @@ -904,13 +903,13 @@ static void handleCommandOptions(int argc, char * argv[], boost::program_options int main(int argc, char * argv[]) { -#ifndef VCMI_ANDROID +#if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) // Correct working dir executable folder (not bundle folder) so we can use executable relative paths boost::filesystem::current_path(boost::filesystem::system_complete(argv[0]).parent_path()); #endif // Installs a sig sev segmentation violation handler // to log stacktrace -#if defined(__GNUC__) && !defined(__MINGW32__) && !defined(VCMI_ANDROID) +#if defined(__GNUC__) && !defined(__MINGW32__) && !defined(VCMI_ANDROID) && !defined(VCMI_IOS) signal(SIGSEGV, handleLinuxSignal); #endif @@ -966,6 +965,7 @@ int main(int argc, char * argv[]) return 0; } +// TODO iOS #ifdef VCMI_ANDROID void CVCMIServer::create() { From fe86ac97b6b02d593bb537627e58ab4cd7e834ef Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 2 Mar 2021 15:39:44 +0300 Subject: [PATCH 007/131] make app launch although it crashes on start because of boost.filesystem --- Info.plist | 59 +++++++++++++++++++++++++++++++++++++++++ client/CMakeLists.txt | 4 +-- client/SDL_uikit_main.c | 19 +++++++++++++ client/main_ios.m | 9 ------- package_ios.sh | 27 +++++++++++++++++++ 5 files changed, 107 insertions(+), 11 deletions(-) create mode 100644 Info.plist create mode 100644 client/SDL_uikit_main.c delete mode 100644 client/main_ios.m create mode 100755 package_ios.sh diff --git a/Info.plist b/Info.plist new file mode 100644 index 000000000..90891f2df --- /dev/null +++ b/Info.plist @@ -0,0 +1,59 @@ + + + + + BuildMachineOSBuild + 19H524 + CFBundleDevelopmentRegion + English + CFBundleExecutable + vcmiclient + CFBundleIdentifier + eu.vcmi.client + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + VCMI + CFBundlePackageType + APPL + CFBundleShortVersionString + 1.0 + CFBundleSignature + ???? + CFBundleSupportedPlatforms + + iPhoneOS + + CFBundleVersion + 1 + DTCompiler + com.apple.compilers.llvm.clang.1_0 + DTPlatformBuild + 17H22 + DTPlatformName + iphoneos + DTPlatformVersion + 13.7 + DTSDKBuild + 17H22 + DTSDKName + iphoneos13.7 + DTXcode + 1170 + DTXcodeBuild + 11E801a + MinimumOSVersion + 9.0 + UIDeviceFamily + + 1 + 2 + + UIFileSharingEnabled + + UIRequiredDeviceCapabilities + + arm64 + + + diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index f96d12cfb..914f43d6a 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -154,7 +154,7 @@ endif() if(WIN32) set(client_ICON "VCMI_client.rc") elseif(APPLE_IOS) - set(client_SRCS ${client_SRCS} main_ios.m) + set(client_SRCS ${client_SRCS} SDL_uikit_main.c) endif() if(ENABLE_DEBUG_CONSOLE) @@ -177,7 +177,7 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - "-framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image + "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image ) endif() diff --git a/client/SDL_uikit_main.c b/client/SDL_uikit_main.c new file mode 100644 index 000000000..966009afe --- /dev/null +++ b/client/SDL_uikit_main.c @@ -0,0 +1,19 @@ +/* + SDL_uikit_main.c, placed in the public domain by Sam Lantinga 3/18/2019 +*/ +// #include "../../SDL_internal.h" + +/* Include the SDL main definition header */ +#include "SDL_main.h" + +#ifdef main +#undef main +#endif + +int +main(int argc, char *argv[]) +{ + return SDL_UIKitRunApp(argc, argv, SDL_main); +} + +/* vi: set ts=4 sw=4 expandtab: */ diff --git a/client/main_ios.m b/client/main_ios.m deleted file mode 100644 index 346defb21..000000000 --- a/client/main_ios.m +++ /dev/null @@ -1,9 +0,0 @@ -@import UIKit; - -int main (int argc, char *argv[]) -{ - @autoreleasepool - { - return UIApplicationMain(argc, argv, nil, nil); - } -} diff --git a/package_ios.sh b/package_ios.sh new file mode 100755 index 000000000..849d4dc3a --- /dev/null +++ b/package_ios.sh @@ -0,0 +1,27 @@ +#!/usr/bin/env bash + +pushd bin/Debug +mkdir -p vcmiclient.app/Frameworks +cp *.dylib AI/*.dylib vcmiclient.app +badInstallNamePrefix=$(pwd) +cd vcmiclient.app + +sdl2Path=~/dev/ios/vcmi-ios-deps/SDL2-lib/lib +cp "$sdl2Path/libSDL2.dylib" . +install_name_tool -rpath "$sdl2Path" '@executable_path/Frameworks' vcmiclient + +for b in vcmiclient *.dylib; do + for l in minizip vcmi; do + libName="lib${l}.dylib" + install_name_tool -change "$badInstallNamePrefix/$libName" "@rpath/$libName" "$b" + done + if [ "$b" != vcmiclient ]; then + install_name_tool -id "@rpath/$b" "$b" + fi +done + +mv -f *.dylib Frameworks +popd + +cp -f ../vcmi/Info.plist "$badInstallNamePrefix/vcmiclient.app" +cp -R bin/Debug-iphoneos/* "$badInstallNamePrefix/vcmiclient.app" From fa90fc0aa46d9c4b40165f18f50a3c17c2458dcf Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 4 Mar 2021 17:21:45 +0300 Subject: [PATCH 008/131] cosmetics --- CMakeLists.txt | 2 +- configure_ios.sh | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 448b879de..a0355d928 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -231,7 +231,7 @@ if(APPLE_IOS) endif(APPLE_IOS) # Check if some platform-specific libraries are needed for linking -if(NOT WIN32 AND NOT ${CMAKE_SYSTEM_NAME} STREQUAL "iOS") +if(NOT WIN32 AND NOT APPLE_IOS) include(CheckLibraryExists) # Shared memory functions used by Boost.Interprocess diff --git a/configure_ios.sh b/configure_ios.sh index af0eb8297..30dc6ba8e 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -1,6 +1,6 @@ #!/usr/bin/env bash -boostPrefix=~/dev/ios/vcmi-ios-deps/Apple-Boost-BuildScript-master/build/boost/1.75.0/ios/release/prefix +boostPrefix=~/dev/other/Apple-Boost-BuildScript/build/boost/1.75.0/ios/debug/prefix ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib From 0078040c8ef599e29f4c79f7c341f8c8b70e3eaa Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 4 Mar 2021 17:22:59 +0300 Subject: [PATCH 009/131] set some common Info.plist keys --- Info.plist | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/Info.plist b/Info.plist index 90891f2df..27539813e 100644 --- a/Info.plist +++ b/Info.plist @@ -44,6 +44,11 @@ 11E801a MinimumOSVersion 9.0 + NSAppTransportSecurity + + NSAllowsArbitraryLoads + + UIDeviceFamily 1 @@ -53,7 +58,11 @@ UIRequiredDeviceCapabilities - arm64 + armv7 + UIRequiresFullScreen + + UIUserInterfaceStyle + Light From a33db4f03b9fd674a7b9463873a6bfa006913060 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 4 Mar 2021 18:10:42 +0300 Subject: [PATCH 010/131] fix creating SDL window, enforce landscape --- Info.plist | 7 +++++++ client/CMT.cpp | 21 ++++++++++++++++++++- client/CMakeLists.txt | 3 +++ client/LaunchScreen.storyboard | 27 +++++++++++++++++++++++++++ 4 files changed, 57 insertions(+), 1 deletion(-) create mode 100644 client/LaunchScreen.storyboard diff --git a/Info.plist b/Info.plist index 27539813e..f82ec6a6a 100644 --- a/Info.plist +++ b/Info.plist @@ -56,12 +56,19 @@ UIFileSharingEnabled + UILaunchStoryboardName + LaunchScreen UIRequiredDeviceCapabilities armv7 UIRequiresFullScreen + UISupportedInterfaceOrientations + + UIInterfaceOrientationLandscapeLeft + UIInterfaceOrientationLandscapeRight + UIUserInterfaceStyle Light diff --git a/client/CMT.cpp b/client/CMT.cpp index ffeea5d7a..2c52a3c28 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -1027,11 +1027,13 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn if (displayIndex < 0) displayIndex = 0; } +#ifndef VCMI_IOS if(!checkVideoMode(displayIndex, w, h)) { logGlobal->error("Error: SDL says that %dx%d resolution is not available!", w, h); return false; } +#endif bool bufOnScreen = (screenBuf == screen); bool realFullscreen = settings["video"]["realFullscreen"].Bool(); @@ -1124,6 +1126,23 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn { logGlobal->error("Can't fix aspect ratio for screen"); } + #elif defined(VCMI_IOS) + auto createWindow = [displayIndex](Uint32 extraFlags = 0) { + mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN/*_DESKTOP*/ | SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI | extraFlags); + return mainWindow != nullptr; + }; + if (!createWindow(SDL_WINDOW_METAL)) + { + logGlobal->warn("Metal unavailable, using OpenGL ES"); + createWindow(); + } + SDL_SetHint(SDL_HINT_ORIENTATIONS, "LandscapeLeft LandscapeRight"); // TODO: isn't setting in Info.plist not enough? + SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); + //SDL_HINT_RETURN_KEY_HIDES_IME + + logGlobal->info("before SDL_GetWindowSize %dx%d", w, h); + SDL_GetWindowSize(mainWindow, &w, &h); + logGlobal->info("after SDL_GetWindowSize %dx%d", w, h); #else if(fullscreen) @@ -1161,7 +1180,7 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn } else { -#ifndef VCMI_ANDROID +#if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) if(fullscreen) { diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 914f43d6a..20b19af97 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -179,6 +179,9 @@ elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image ) + + target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) + set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") endif() target_link_libraries(vcmiclient PRIVATE diff --git a/client/LaunchScreen.storyboard b/client/LaunchScreen.storyboard new file mode 100644 index 000000000..ea997175d --- /dev/null +++ b/client/LaunchScreen.storyboard @@ -0,0 +1,27 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + From d6f8e4328c3a4ebca4825800bd0af5d80656a7fe Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 5 Mar 2021 19:22:10 +0300 Subject: [PATCH 011/131] implement setting thread name on macOS/iOS --- lib/CThreadHelper.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/lib/CThreadHelper.cpp b/lib/CThreadHelper.cpp index 6e0c32e82..d388807e6 100644 --- a/lib/CThreadHelper.cpp +++ b/lib/CThreadHelper.cpp @@ -84,5 +84,7 @@ void setThreadName(const std::string &name) #elif defined(__linux__) prctl(PR_SET_NAME, name.c_str(), 0, 0, 0); +#elif defined(VCMI_APPLE) + pthread_setname_np(name.c_str()); #endif } From 2e18299897b110bf3a9781b059252e6e9ef2a14c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 5 Mar 2021 19:26:35 +0300 Subject: [PATCH 012/131] make server a static lib, run it in a separate thread issues to solve: - dynamic_cast error 2: One or more of the following type_info's has hidden visibility or is defined in more than one translation unit. They should all have public visibility. 13CPackForLobby, 20LobbyClientConnected, 20LobbyClientConnected. - error setting socket option: set_option: No buffer space available --- client/CMT.cpp | 6 ++++-- client/CMakeLists.txt | 4 +++- client/CPlayerInterface.cpp | 1 + client/CServerHandler.cpp | 25 +++++++++++++++++++--- client/windows/CAdvmapInterface.cpp | 5 +++++ configure_ios.sh | 5 +++-- lib/VCMIDirs.cpp | 7 ++++++- lib/filesystem/AdapterLoaders.cpp | 4 +++- lib/serializer/Connection.cpp | 11 ++++++++-- server/CMakeLists.txt | 6 +++++- server/CVCMIServer.cpp | 32 ++++++++++++++++++++++------- server/CVCMIServer.h | 2 ++ 12 files changed, 88 insertions(+), 20 deletions(-) diff --git a/client/CMT.cpp b/client/CMT.cpp index 2c52a3c28..a2aa4c467 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -433,6 +433,7 @@ int main(int argc, char * argv[]) #ifndef VCMI_NO_THREADED_LOAD + // todo ios #ifdef VCMI_ANDROID // android loads the data quite slowly so we display native progressbar to prevent having only black screen for few seconds { CAndroidVMHelper vmHelper; @@ -1136,9 +1137,9 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn logGlobal->warn("Metal unavailable, using OpenGL ES"); createWindow(); } - SDL_SetHint(SDL_HINT_ORIENTATIONS, "LandscapeLeft LandscapeRight"); // TODO: isn't setting in Info.plist not enough? +// SDL_SetHint(SDL_HINT_ORIENTATIONS, "LandscapeLeft LandscapeRight"); // TODO: isn't setting in Info.plist not enough? SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); - //SDL_HINT_RETURN_KEY_HIDES_IME + SDL_SetHint(SDL_HINT_RETURN_KEY_HIDES_IME, "1"); logGlobal->info("before SDL_GetWindowSize %dx%d", w, h); SDL_GetWindowSize(mainWindow, &w, &h); @@ -1315,6 +1316,7 @@ static void handleEvent(SDL_Event & ev) { if((ev.type==SDL_QUIT) ||(ev.type == SDL_KEYDOWN && ev.key.keysym.sym==SDLK_F4 && (ev.key.keysym.mod & KMOD_ALT))) { + // todo ios #ifdef VCMI_ANDROID handleQuit(false); #else diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 20b19af97..cf8efef1a 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -177,7 +177,9 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image + vcmiserver + # SDL2_image: + "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" ) target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) diff --git a/client/CPlayerInterface.cpp b/client/CPlayerInterface.cpp index 62463f048..481893bb1 100644 --- a/client/CPlayerInterface.cpp +++ b/client/CPlayerInterface.cpp @@ -364,6 +364,7 @@ void CPlayerInterface::heroMoved(const TryMoveHero & details, bool verbose) for(int i = 1; i < 32; i += 2 * speed) { movementPxStep(details, i, hp, hero); + // todo ios #ifndef VCMI_ANDROID // currently android doesn't seem to be able to handle all these full redraws here, so let's disable it so at least it looks less choppy; // most likely this is connected with the way that this manual animation+framerate handling is solved diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index 93d44cefa..39024dc1b 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -24,7 +24,8 @@ #ifdef VCMI_ANDROID #include "../lib/CAndroidVMHelper.h" #elif defined(VCMI_IOS) -//TODO +#include "../server/CVCMIServer.h" +// todo ios #else #include "../lib/Interprocess.h" #endif @@ -184,7 +185,18 @@ void CServerHandler::startLocalServerAndConnect() envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true); } #elif defined(VCMI_IOS) - // TODO + // todo ios: hide keyboard + logNetwork->info("[ios] create server thread"); + boost::condition_variable cond; + threadRunLocalServer = std::make_shared([&cond, this] { + setThreadName("CVCMIServer"); + CVCMIServer::create(&cond); + // todo ios copypaste + threadRunLocalServer.reset(); + CSH->campaignServerRestartLock.setn(false); + }); +// threadRunLocalServer->detach(); + logNetwork->info("[ios] detach server thread"); #else threadRunLocalServer = std::make_shared(&CServerHandler::threadRunServer, this); //runs server executable; #endif @@ -202,7 +214,14 @@ void CServerHandler::startLocalServerAndConnect() logNetwork->info("waiting for server finished..."); androidTestServerReadyFlag = false; #elif defined(VCMI_IOS) - //TODO + // todo ios + { + boost::mutex m; + boost::unique_lock lock{m}; + logNetwork->info("[ios] wait for server"); + cond.wait(lock); + logNetwork->info("[ios] server ready"); + } #else if(shm) shm->sr->waitTillReady(); diff --git a/client/windows/CAdvmapInterface.cpp b/client/windows/CAdvmapInterface.cpp index c42fc9019..2c5a9dfb7 100644 --- a/client/windows/CAdvmapInterface.cpp +++ b/client/windows/CAdvmapInterface.cpp @@ -126,6 +126,7 @@ void CTerrainRect::clickLeft(tribool down, bool previousState) return; #ifdef VCMI_ANDROID + // todo ios if(adventureInt->swipeEnabled) { if(handleSwipeStateChange((bool)down == true)) @@ -151,6 +152,7 @@ void CTerrainRect::clickLeft(tribool down, bool previousState) void CTerrainRect::clickRight(tribool down, bool previousState) { #ifdef VCMI_ANDROID + // todo ios if(adventureInt->swipeEnabled && isSwiping) return; #endif @@ -180,6 +182,7 @@ void CTerrainRect::mouseMoved(const SDL_MouseMotionEvent & sEvent) void CTerrainRect::handleSwipeMove(const SDL_MouseMotionEvent & sEvent) { #ifdef VCMI_ANDROID + // todo ios if(sEvent.state == 0) // any "button" is enough on android #else //!VCMI_ANDROID if((sEvent.state & SDL_BUTTON_MMASK) == 0) // swipe only works with middle mouse on other platforms @@ -1050,6 +1053,7 @@ void CAdvMapInt::show(SDL_Surface * to) handleSwipeUpdate(); } #ifdef VCMI_ANDROID // on android, map-moving mode is exclusive (TODO technically it might work with both enabled; to be checked) + // todo ios else #endif // VCMI_ANDROID { @@ -1452,6 +1456,7 @@ void CAdvMapInt::select(const CArmedInstance *sel, bool centerView) void CAdvMapInt::mouseMoved( const SDL_MouseMotionEvent & sEvent ) { #ifdef VCMI_ANDROID + // todo ios if(swipeEnabled) return; #endif diff --git a/configure_ios.sh b/configure_ios.sh index 30dc6ba8e..1a0bc58ae 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -5,11 +5,12 @@ ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib srcDir="../vcmi" -"${2:-cmake}" "$srcDir" -G "$1" \ +/Users/Shared/xbmc-depends/x86_64-darwin19.6.0-native/bin/cmake "$srcDir" -G Xcode \ -DENABLE_LAUNCHER=0 \ -Wno-dev \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ - -DPLATFORM=OS64 \ + -DPLATFORM=${1:-OS64} \ + -DDEPLOYMENT_TARGET=9.0 \ -DENABLE_BITCODE=0 \ -DCMAKE_BINARY_DIR=$(pwd) \ -DCMAKE_PREFIX_PATH="$boostPrefix;$ffmpegDir;$sdlLibsDir" \ diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index ecac91b86..fd6c744e1 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -389,7 +389,9 @@ class VCMIDirsIOS final : public VCMIDirsApple std::vector dataPaths() const override; bfs::path libraryPath() const override; + boost::filesystem::path fullLibraryPath(const std::string & desiredFolder, const std::string & baseLibName) const override; bfs::path binaryPath() const override; + bfs::path serverPath() const override; bool developmentMode() const override; }; @@ -398,10 +400,13 @@ bfs::path VCMIDirsIOS::userDataPath() const { return {ios_documentsPath()}; } bfs::path VCMIDirsIOS::userCachePath() const { return {ios_cachesPath()}; } bfs::path VCMIDirsIOS::userLogsPath() const { return {ios_documentsPath()}; } -std::vector VCMIDirsIOS::dataPaths() const { return {userDataPath()}; } +std::vector VCMIDirsIOS::dataPaths() const { return {binaryPath(), userDataPath()}; } bfs::path VCMIDirsIOS::libraryPath() const { return {ios_frameworksPath()}; } +// todo ios: place AI libs in subdir? +boost::filesystem::path VCMIDirsIOS::fullLibraryPath(const std::string & desiredFolder, const std::string & baseLibName) const { return libraryPath() / libraryName(baseLibName); } bfs::path VCMIDirsIOS::binaryPath() const { return {ios_bundlePath()}; } +bfs::path VCMIDirsIOS::serverPath() const { return clientPath(); } bool VCMIDirsIOS::developmentMode() const { return false; } #elif defined(VCMI_MAC) diff --git a/lib/filesystem/AdapterLoaders.cpp b/lib/filesystem/AdapterLoaders.cpp index 000f44fdd..dd483d2ae 100644 --- a/lib/filesystem/AdapterLoaders.cpp +++ b/lib/filesystem/AdapterLoaders.cpp @@ -154,7 +154,9 @@ std::vector CFilesystemList::getResourcesWithName std::vector ret; for (auto & loader : loaders) - boost::range::copy(loader->getResourcesWithName(resourceName), std::back_inserter(ret)); + // todo ios + if (loader) + boost::range::copy(loader->getResourcesWithName(resourceName), std::back_inserter(ret)); return ret; } diff --git a/lib/serializer/Connection.cpp b/lib/serializer/Connection.cpp index 5d799d666..30bc4e83b 100644 --- a/lib/serializer/Connection.cpp +++ b/lib/serializer/Connection.cpp @@ -33,8 +33,15 @@ using namespace boost::asio::ip; void CConnection::init() { socket->set_option(boost::asio::ip::tcp::no_delay(true)); - socket->set_option(boost::asio::socket_base::send_buffer_size(4194304)); - socket->set_option(boost::asio::socket_base::receive_buffer_size(4194304)); + try + { + socket->set_option(boost::asio::socket_base::send_buffer_size(4194304)); + socket->set_option(boost::asio::socket_base::receive_buffer_size(4194304)); + } + catch (const boost::system::system_error & e) + { + logNetwork->error("error setting socket option: %s", e.what()); + } enableSmartPointerSerialization(); disableStackSendingByID(); diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 653703d11..8fae51ed1 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -22,7 +22,11 @@ if(ANDROID) # android needs client/server to be libraries, not executables, so w return() endif() -add_executable(vcmiserver ${server_SRCS} ${server_HEADERS}) +if(APPLE_IOS) + add_library(vcmiserver STATIC ${server_SRCS} ${server_HEADERS}) +else() + add_executable(vcmiserver ${server_SRCS} ${server_HEADERS}) +endif() set(server_LIBS vcmi) if(CMAKE_SYSTEM_NAME MATCHES FreeBSD) diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index 71b78b153..c918743e5 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -30,7 +30,7 @@ #ifdef VCMI_ANDROID #include "lib/CAndroidVMHelper.h" #elif defined(VCMI_IOS) - //TODO +// todo ios #else #include "../lib/Interprocess.h" #endif @@ -114,8 +114,8 @@ public: } }; -std::string NAME_AFFIX = "server"; -std::string NAME = GameConstants::VCMI_VERSION + std::string(" (") + NAME_AFFIX + ')'; +std::string SERVER_NAME_AFFIX = "server"; +std::string SERVER_NAME = GameConstants::VCMI_VERSION + std::string(" (") + SERVER_NAME_AFFIX + ')'; CVCMIServer::CVCMIServer(boost::program_options::variables_map & opts) : port(3030), io(std::make_shared()), state(EServerState::LOBBY), cmdLineOptions(opts), currentClientId(1), currentPlayerId(1), restartGameplay(false) @@ -293,7 +293,7 @@ void CVCMIServer::connectionAccepted(const boost::system::error_code & ec) try { logNetwork->info("We got a new connection! :)"); - auto c = std::make_shared(upcomingConnection, NAME, uuid); + auto c = std::make_shared(upcomingConnection, SERVER_NAME, uuid); upcomingConnection.reset(); connections.insert(c); c->handler = std::make_shared(&CVCMIServer::threadHandleClient, this, c); @@ -901,6 +901,9 @@ static void handleCommandOptions(int argc, char * argv[], boost::program_options } } +#ifdef VCMI_IOS +#define main server_main +#endif int main(int argc, char * argv[]) { #if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) @@ -913,12 +916,19 @@ int main(int argc, char * argv[]) signal(SIGSEGV, handleLinuxSignal); #endif + // todo ios: double console log console = new CConsoleHandler(); CBasicLogConfigurator logConfig(VCMIDirs::get().userLogsPath() / "VCMI_Server_log.txt", console); logConfig.configureDefault(); - logGlobal->info(NAME); + logGlobal->info(SERVER_NAME); - boost::program_options::variables_map opts; + boost::program_options::variables_map opts; +#ifdef VCMI_IOS + argc = 1; + boost::condition_variable * cond = reinterpret_cast(argv[1]); + cond->notify_one(); +//#endif +#else handleCommandOptions(argc, argv, opts); preinitDLL(console); settings.init(); @@ -926,6 +936,8 @@ int main(int argc, char * argv[]) loadDLLClasses(); srand((ui32)time(nullptr)); +//#ifdef VCMI_IOS +#endif try { boost::asio::io_service io_service; @@ -965,11 +977,17 @@ int main(int argc, char * argv[]) return 0; } -// TODO iOS #ifdef VCMI_ANDROID void CVCMIServer::create() { const char * foo[1] = {"android-server"}; main(1, const_cast(foo)); } +#elif defined(VCMI_IOS) +void CVCMIServer::create(boost::condition_variable * cond) +{ + const auto executablePath = VCMIDirs::get().serverPath(); + void *argv[] = {const_cast(executablePath.c_str()), cond}; + main(2, reinterpret_cast(argv)); +} #endif diff --git a/server/CVCMIServer.h b/server/CVCMIServer.h index 111ded751..5e68c62eb 100644 --- a/server/CVCMIServer.h +++ b/server/CVCMIServer.h @@ -103,5 +103,7 @@ public: #ifdef VCMI_ANDROID static void create(); +#elif defined(VCMI_IOS) + static void create(boost::condition_variable * cond); #endif }; From b8fa692bda41e22798218debd7d4d53779e543e3 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 7 Mar 2021 17:21:32 +0300 Subject: [PATCH 013/131] simulator reads data from the macOS directory --- Global.h | 2 +- lib/VCMIDirs.cpp | 31 ++++++++++++++++++++++++++++--- 2 files changed, 29 insertions(+), 4 deletions(-) diff --git a/Global.h b/Global.h index 254e06437..146897238 100644 --- a/Global.h +++ b/Global.h @@ -68,7 +68,7 @@ static_assert(sizeof(bool) == 1, "Bool needs to be 1 byte in size."); # define VCMI_UNIX # define VCMI_APPLE # include "TargetConditionals.h" -# if TARGET_IPHONE_SIMULATOR +# if TARGET_OS_SIMULATOR || TARGET_IPHONE_SIMULATOR # define VCMI_IOS # define VCMI_IOS_SIM # elif TARGET_OS_IPHONE diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index fd6c744e1..c8c523fb8 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -400,11 +400,36 @@ bfs::path VCMIDirsIOS::userDataPath() const { return {ios_documentsPath()}; } bfs::path VCMIDirsIOS::userCachePath() const { return {ios_cachesPath()}; } bfs::path VCMIDirsIOS::userLogsPath() const { return {ios_documentsPath()}; } -std::vector VCMIDirsIOS::dataPaths() const { return {binaryPath(), userDataPath()}; } +std::vector VCMIDirsIOS::dataPaths() const +{ + return { +#ifdef VCMI_IOS_SIM + // fixme ios + {"/Users/kambala/Library/Application Support/vcmi"}, +#endif + binaryPath(), + userDataPath(), + }; +} -bfs::path VCMIDirsIOS::libraryPath() const { return {ios_frameworksPath()}; } +bfs::path VCMIDirsIOS::libraryPath() const +{ +#ifdef VCMI_IOS_SIM +// fixme ios + return {"/Users/kambala/dev/vcmi/build-sim64/bin/Debug"}; +#else + return {ios_frameworksPath()}; +#endif +} // todo ios: place AI libs in subdir? -boost::filesystem::path VCMIDirsIOS::fullLibraryPath(const std::string & desiredFolder, const std::string & baseLibName) const { return libraryPath() / libraryName(baseLibName); } +boost::filesystem::path VCMIDirsIOS::fullLibraryPath(const std::string & desiredFolder, const std::string & baseLibName) const +{ +#ifdef VCMI_IOS_SIM + return VCMIDirsApple::fullLibraryPath(desiredFolder, baseLibName); +#else + return libraryPath() / libraryName(baseLibName); +#endif +} bfs::path VCMIDirsIOS::binaryPath() const { return {ios_bundlePath()}; } bfs::path VCMIDirsIOS::serverPath() const { return clientPath(); } From 98d507d0a57dcd9deee73e2d9cf143a368fecbe7 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 7 Mar 2021 18:20:53 +0300 Subject: [PATCH 014/131] disable console colors as Xcode doesn't render them --- lib/CConsoleHandler.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/lib/CConsoleHandler.cpp b/lib/CConsoleHandler.cpp index b5489b984..ebff37841 100644 --- a/lib/CConsoleHandler.cpp +++ b/lib/CConsoleHandler.cpp @@ -165,6 +165,7 @@ LONG WINAPI onUnhandledException(EXCEPTION_POINTERS* exception) void CConsoleHandler::setColor(EConsoleTextColor::EConsoleTextColor color) { +#ifndef VCMI_IOS TColor colorCode; switch(color) { @@ -204,6 +205,7 @@ void CConsoleHandler::setColor(EConsoleTextColor::EConsoleTextColor color) #else std::cout << colorCode; #endif +#endif } int CConsoleHandler::run() From 26a1cc5b73e225e85f3333ffe697aadeca361096 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 7 Mar 2021 19:18:26 +0300 Subject: [PATCH 015/131] todos --- lib/CStopWatch.h | 2 +- server/CVCMIServer.cpp | 4 +--- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/lib/CStopWatch.h b/lib/CStopWatch.h index 0431e9c1a..b2821130c 100644 --- a/lib/CStopWatch.h +++ b/lib/CStopWatch.h @@ -53,7 +53,7 @@ public: private: si64 clock() { - #ifdef __FreeBSD__ + #ifdef __FreeBSD__ // TODO: enable also for Apple? struct rusage usage; getrusage(RUSAGE_SELF, &usage); return static_cast(usage.ru_utime.tv_sec + usage.ru_stime.tv_sec) * 1000000 + usage.ru_utime.tv_usec + usage.ru_stime.tv_usec; diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index c918743e5..902d1a8e2 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -916,7 +916,7 @@ int main(int argc, char * argv[]) signal(SIGSEGV, handleLinuxSignal); #endif - // todo ios: double console log + // todo ios: double console log in single-process mode. Why removing the lines below breaks connecting to local server?! console = new CConsoleHandler(); CBasicLogConfigurator logConfig(VCMIDirs::get().userLogsPath() / "VCMI_Server_log.txt", console); logConfig.configureDefault(); @@ -927,7 +927,6 @@ int main(int argc, char * argv[]) argc = 1; boost::condition_variable * cond = reinterpret_cast(argv[1]); cond->notify_one(); -//#endif #else handleCommandOptions(argc, argv, opts); preinitDLL(console); @@ -936,7 +935,6 @@ int main(int argc, char * argv[]) loadDLLClasses(); srand((ui32)time(nullptr)); -//#ifdef VCMI_IOS #endif try { From e72e5cea6f8a11e72d3bd561628cc461d0e2a48e Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 7 Mar 2021 15:18:40 +0300 Subject: [PATCH 016/131] attempt to run server in a separate app partially reverts 3258f8bb40487e3731bf452dbda1add6294ff4b2 --- Info.plist | 4 +++ client/CMakeLists.txt | 4 +-- client/CServerHandler.cpp | 25 ++-------------- lib/VCMIDirs.cpp | 2 -- package_ios.sh | 28 ++++++++++++----- server/CMakeLists.txt | 16 ++++++---- server/CVCMIServer.cpp | 25 ++++------------ server/CVCMIServer.h | 4 +-- server/main_ios.mm | 63 +++++++++++++++++++++++++++++++++++++++ 9 files changed, 109 insertions(+), 62 deletions(-) create mode 100644 server/main_ios.mm diff --git a/Info.plist b/Info.plist index f82ec6a6a..14c1b198d 100644 --- a/Info.plist +++ b/Info.plist @@ -49,6 +49,10 @@ NSAllowsArbitraryLoads + UIBackgroundModes + + audio + UIDeviceFamily 1 diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index cf8efef1a..20b19af97 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -177,9 +177,7 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - vcmiserver - # SDL2_image: - "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" + "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image ) target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index 39024dc1b..93d44cefa 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -24,8 +24,7 @@ #ifdef VCMI_ANDROID #include "../lib/CAndroidVMHelper.h" #elif defined(VCMI_IOS) -#include "../server/CVCMIServer.h" -// todo ios +//TODO #else #include "../lib/Interprocess.h" #endif @@ -185,18 +184,7 @@ void CServerHandler::startLocalServerAndConnect() envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true); } #elif defined(VCMI_IOS) - // todo ios: hide keyboard - logNetwork->info("[ios] create server thread"); - boost::condition_variable cond; - threadRunLocalServer = std::make_shared([&cond, this] { - setThreadName("CVCMIServer"); - CVCMIServer::create(&cond); - // todo ios copypaste - threadRunLocalServer.reset(); - CSH->campaignServerRestartLock.setn(false); - }); -// threadRunLocalServer->detach(); - logNetwork->info("[ios] detach server thread"); + // TODO #else threadRunLocalServer = std::make_shared(&CServerHandler::threadRunServer, this); //runs server executable; #endif @@ -214,14 +202,7 @@ void CServerHandler::startLocalServerAndConnect() logNetwork->info("waiting for server finished..."); androidTestServerReadyFlag = false; #elif defined(VCMI_IOS) - // todo ios - { - boost::mutex m; - boost::unique_lock lock{m}; - logNetwork->info("[ios] wait for server"); - cond.wait(lock); - logNetwork->info("[ios] server ready"); - } + //TODO #else if(shm) shm->sr->waitTillReady(); diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index c8c523fb8..5a59ff03e 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -391,7 +391,6 @@ class VCMIDirsIOS final : public VCMIDirsApple bfs::path libraryPath() const override; boost::filesystem::path fullLibraryPath(const std::string & desiredFolder, const std::string & baseLibName) const override; bfs::path binaryPath() const override; - bfs::path serverPath() const override; bool developmentMode() const override; }; @@ -431,7 +430,6 @@ boost::filesystem::path VCMIDirsIOS::fullLibraryPath(const std::string & desired #endif } bfs::path VCMIDirsIOS::binaryPath() const { return {ios_bundlePath()}; } -bfs::path VCMIDirsIOS::serverPath() const { return clientPath(); } bool VCMIDirsIOS::developmentMode() const { return false; } #elif defined(VCMI_MAC) diff --git a/package_ios.sh b/package_ios.sh index 849d4dc3a..5240b74a1 100755 --- a/package_ios.sh +++ b/package_ios.sh @@ -2,18 +2,20 @@ pushd bin/Debug mkdir -p vcmiclient.app/Frameworks -cp *.dylib AI/*.dylib vcmiclient.app -badInstallNamePrefix=$(pwd) -cd vcmiclient.app +productsDir=$(pwd) sdl2Path=~/dev/ios/vcmi-ios-deps/SDL2-lib/lib -cp "$sdl2Path/libSDL2.dylib" . -install_name_tool -rpath "$sdl2Path" '@executable_path/Frameworks' vcmiclient +for app in vcmiclient vcmiserver; do + install_name_tool -rpath "$sdl2Path" '@executable_path/Frameworks' "$productsDir/$app.app/$app" +done + +cp *.dylib AI/*.dylib "$sdl2Path/libSDL2.dylib" vcmiclient.app +cd vcmiclient.app for b in vcmiclient *.dylib; do for l in minizip vcmi; do libName="lib${l}.dylib" - install_name_tool -change "$badInstallNamePrefix/$libName" "@rpath/$libName" "$b" + install_name_tool -change "$productsDir/$libName" "@rpath/$libName" "$b" done if [ "$b" != vcmiclient ]; then install_name_tool -id "@rpath/$b" "$b" @@ -23,5 +25,15 @@ done mv -f *.dylib Frameworks popd -cp -f ../vcmi/Info.plist "$badInstallNamePrefix/vcmiclient.app" -cp -R bin/Debug-iphoneos/* "$badInstallNamePrefix/vcmiclient.app" +for app in vcmiclient vcmiserver; do + cp -f ../vcmi/Info.plist "$productsDir/$app.app" +done +sed -i '' -e 's/client/server/g' -e 's/>VCMIVCMI server()), state(EServerState::LOBBY), cmdLineOptions(opts), currentClientId(1), currentPlayerId(1), restartGameplay(false) @@ -293,7 +293,7 @@ void CVCMIServer::connectionAccepted(const boost::system::error_code & ec) try { logNetwork->info("We got a new connection! :)"); - auto c = std::make_shared(upcomingConnection, SERVER_NAME, uuid); + auto c = std::make_shared(upcomingConnection, NAME, uuid); upcomingConnection.reset(); connections.insert(c); c->handler = std::make_shared(&CVCMIServer::threadHandleClient, this, c); @@ -920,14 +920,9 @@ int main(int argc, char * argv[]) console = new CConsoleHandler(); CBasicLogConfigurator logConfig(VCMIDirs::get().userLogsPath() / "VCMI_Server_log.txt", console); logConfig.configureDefault(); - logGlobal->info(SERVER_NAME); + logGlobal->info(NAME); - boost::program_options::variables_map opts; -#ifdef VCMI_IOS - argc = 1; - boost::condition_variable * cond = reinterpret_cast(argv[1]); - cond->notify_one(); -#else + boost::program_options::variables_map opts; handleCommandOptions(argc, argv, opts); preinitDLL(console); settings.init(); @@ -935,7 +930,6 @@ int main(int argc, char * argv[]) loadDLLClasses(); srand((ui32)time(nullptr)); -#endif try { boost::asio::io_service io_service; @@ -975,17 +969,10 @@ int main(int argc, char * argv[]) return 0; } -#ifdef VCMI_ANDROID +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) void CVCMIServer::create() { const char * foo[1] = {"android-server"}; main(1, const_cast(foo)); } -#elif defined(VCMI_IOS) -void CVCMIServer::create(boost::condition_variable * cond) -{ - const auto executablePath = VCMIDirs::get().serverPath(); - void *argv[] = {const_cast(executablePath.c_str()), cond}; - main(2, reinterpret_cast(argv)); -} #endif diff --git a/server/CVCMIServer.h b/server/CVCMIServer.h index 5e68c62eb..7cd84eb46 100644 --- a/server/CVCMIServer.h +++ b/server/CVCMIServer.h @@ -101,9 +101,7 @@ public: ui8 getIdOfFirstUnallocatedPlayer() const; -#ifdef VCMI_ANDROID +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) static void create(); -#elif defined(VCMI_IOS) - static void create(boost::condition_variable * cond); #endif }; diff --git a/server/main_ios.mm b/server/main_ios.mm new file mode 100644 index 000000000..ec28d8c64 --- /dev/null +++ b/server/main_ios.mm @@ -0,0 +1,63 @@ +/* + * main_ios.mm, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#import +#import + +//#include "StdInc.h" +#include "../Global.h" +#include "CVCMIServer.h" + +@interface ViewController : UIViewController +@end + +@implementation ViewController +@end + + +@interface AppDelegate : UIResponder +@property (nonatomic, strong) UIWindow *window; +@property (nonatomic, strong) AVPlayerLooper *looper; +@end + +@implementation AppDelegate + +- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions +{ + self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds]; + self.window.rootViewController = [ViewController new]; + [self.window makeKeyAndVisible]; + + [AVAudioSession.sharedInstance setCategory:AVAudioSessionCategoryPlayback mode:AVAudioSessionModeDefault options:AVAudioSessionCategoryOptionMixWithOthers error:nullptr]; + + auto item = [AVPlayerItem playerItemWithURL:[NSBundle.mainBundle URLForResource:@"silence" withExtension:@"wav"]]; + auto player = [AVQueuePlayer new]; + player.allowsExternalPlayback = NO; + [player play]; + self.looper = [AVPlayerLooper playerLooperWithPlayer:player templateItem:item]; + + [NSThread detachNewThreadWithBlock:^ + { + NSThread.currentThread.name = @"CVCMIServer"; + NSLog(@"starting server from thread %@", NSThread.currentThread); + CVCMIServer::create(); + }]; + return YES; +} + +@end + + +int main(int argc, char * argv[]) +{ + @autoreleasepool + { + return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class])); + } +} From 93e9bc4e51a9ee8800d050fc350e1455e8b736ae Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 9 Mar 2021 10:10:11 +0300 Subject: [PATCH 017/131] restrict both apps to 64-bit iPad with multitasking and Metal --- Info.plist | 14 +++++--------- client/CMT.cpp | 12 ++---------- configure_ios.sh | 2 +- 3 files changed, 8 insertions(+), 20 deletions(-) diff --git a/Info.plist b/Info.plist index 14c1b198d..fd7ef47e7 100644 --- a/Info.plist +++ b/Info.plist @@ -43,19 +43,14 @@ DTXcodeBuild 11E801a MinimumOSVersion - 9.0 + 11.0 NSAppTransportSecurity NSAllowsArbitraryLoads - UIBackgroundModes - - audio - UIDeviceFamily - 1 2 UIFileSharingEnabled @@ -64,14 +59,15 @@ LaunchScreen UIRequiredDeviceCapabilities - armv7 + arm64 + metal - UIRequiresFullScreen - UISupportedInterfaceOrientations UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight + UIInterfaceOrientationPortrait + UIInterfaceOrientationPortraitUpsideDown UIUserInterfaceStyle Light diff --git a/client/CMT.cpp b/client/CMT.cpp index a2aa4c467..cdd1408de 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -1128,16 +1128,8 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn logGlobal->error("Can't fix aspect ratio for screen"); } #elif defined(VCMI_IOS) - auto createWindow = [displayIndex](Uint32 extraFlags = 0) { - mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN/*_DESKTOP*/ | SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI | extraFlags); - return mainWindow != nullptr; - }; - if (!createWindow(SDL_WINDOW_METAL)) - { - logGlobal->warn("Metal unavailable, using OpenGL ES"); - createWindow(); - } -// SDL_SetHint(SDL_HINT_ORIENTATIONS, "LandscapeLeft LandscapeRight"); // TODO: isn't setting in Info.plist not enough? + mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN | SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI | SDL_WINDOW_METAL); + SDL_SetHint(SDL_HINT_ORIENTATIONS, "LandscapeLeft LandscapeRight"); SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); SDL_SetHint(SDL_HINT_RETURN_KEY_HIDES_IME, "1"); diff --git a/configure_ios.sh b/configure_ios.sh index 1a0bc58ae..93153f630 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -10,7 +10,7 @@ srcDir="../vcmi" -Wno-dev \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ -DPLATFORM=${1:-OS64} \ - -DDEPLOYMENT_TARGET=9.0 \ + -DDEPLOYMENT_TARGET=11.0 \ -DENABLE_BITCODE=0 \ -DCMAKE_BINARY_DIR=$(pwd) \ -DCMAKE_PREFIX_PATH="$boostPrefix;$ffmpegDir;$sdlLibsDir" \ From 09f5ea52f2c9e9cd8c4475d505c77ff340b02235 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 9 Mar 2021 11:12:17 +0300 Subject: [PATCH 018/131] remove background audio hack --- server/CMakeLists.txt | 2 +- server/main_ios.mm | 11 ----------- 2 files changed, 1 insertion(+), 12 deletions(-) diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 61d06ded4..c6eb684e3 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -32,7 +32,7 @@ set(server_LIBS vcmi) if(CMAKE_SYSTEM_NAME MATCHES FreeBSD) set(server_LIBS execinfo ${server_LIBS}) elseif(APPLE_IOS) - set(server_LIBS ${server_LIBS} "-framework UIKit -framework AVFoundation") + set(server_LIBS ${server_LIBS} "-framework UIKit") endif() target_link_libraries(vcmiserver PRIVATE ${server_LIBS} minizip::minizip) diff --git a/server/main_ios.mm b/server/main_ios.mm index ec28d8c64..4576ed683 100644 --- a/server/main_ios.mm +++ b/server/main_ios.mm @@ -8,9 +8,7 @@ * */ #import -#import -//#include "StdInc.h" #include "../Global.h" #include "CVCMIServer.h" @@ -23,7 +21,6 @@ @interface AppDelegate : UIResponder @property (nonatomic, strong) UIWindow *window; -@property (nonatomic, strong) AVPlayerLooper *looper; @end @implementation AppDelegate @@ -34,14 +31,6 @@ self.window.rootViewController = [ViewController new]; [self.window makeKeyAndVisible]; - [AVAudioSession.sharedInstance setCategory:AVAudioSessionCategoryPlayback mode:AVAudioSessionModeDefault options:AVAudioSessionCategoryOptionMixWithOthers error:nullptr]; - - auto item = [AVPlayerItem playerItemWithURL:[NSBundle.mainBundle URLForResource:@"silence" withExtension:@"wav"]]; - auto player = [AVQueuePlayer new]; - player.allowsExternalPlayback = NO; - [player play]; - self.looper = [AVPlayerLooper playerLooperWithPlayer:player templateItem:item]; - [NSThread detachNewThreadWithBlock:^ { NSThread.currentThread.name = @"CVCMIServer"; From 92a7936202106d2e5ff0406cba7db8ba96925f06 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 10 Mar 2021 10:57:07 +0300 Subject: [PATCH 019/131] add Info.plist to sources --- CMakeLists.txt | 10 ++++- client/CMakeLists.txt | 2 + Info.plist => client/ios/Info.plist.in | 45 ++++++---------------- configure_ios.sh | 2 +- package_ios.sh | 5 --- server/CMakeLists.txt | 5 ++- server/ios/Info.plist.in | 52 ++++++++++++++++++++++++++ server/{main_ios.mm => ios/main.mm} | 0 8 files changed, 79 insertions(+), 42 deletions(-) rename Info.plist => client/ios/Info.plist.in (60%) create mode 100644 server/ios/Info.plist.in rename server/{main_ios.mm => ios/main.mm} (100%) diff --git a/CMakeLists.txt b/CMakeLists.txt index a0355d928..968f76536 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -48,10 +48,18 @@ endif() set(VCMI_VERSION_MAJOR 1) set(VCMI_VERSION_MINOR 0) set(VCMI_VERSION_PATCH 0) +if(APPLE_IOS) + set(APP_SHORT_VERSION "${VCMI_VERSION_MAJOR}.${VCMI_VERSION_MINOR}") + if(NOT VCMI_VERSION_PATCH EQUAL 0) + string(APPEND APP_SHORT_VERSION ".${VCMI_VERSION_PATCH}") + endif() +endif() option(ENABLE_ERM "Enable compilation of ERM scripting module" OFF) option(ENABLE_LUA "Enable compilation of LUA scripting module" OFF) -if(NOT APPLE_IOS) +if(APPLE_IOS) + set(BUNDLE_IDENTIFIER_PREFIX "eu.vcmi" CACHE STRING "Bundle identifier prefix") +else() option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) endif() option(ENABLE_TEST "Enable compilation of unit tests" ON) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 20b19af97..3c031e6ee 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -180,6 +180,8 @@ elseif(APPLE_IOS) "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image ) + set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in") + target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") endif() diff --git a/Info.plist b/client/ios/Info.plist.in similarity index 60% rename from Info.plist rename to client/ios/Info.plist.in index fd7ef47e7..e50e209ff 100644 --- a/Info.plist +++ b/client/ios/Info.plist.in @@ -2,14 +2,12 @@ - BuildMachineOSBuild - 19H524 CFBundleDevelopmentRegion - English + en CFBundleExecutable vcmiclient CFBundleIdentifier - eu.vcmi.client + @BUNDLE_IDENTIFIER_PREFIX@.vcmiclient CFBundleInfoDictionaryVersion 6.0 CFBundleName @@ -17,52 +15,33 @@ CFBundlePackageType APPL CFBundleShortVersionString - 1.0 + @APP_SHORT_VERSION@ CFBundleSignature ???? - CFBundleSupportedPlatforms - - iPhoneOS - CFBundleVersion 1 - DTCompiler - com.apple.compilers.llvm.clang.1_0 - DTPlatformBuild - 17H22 - DTPlatformName - iphoneos - DTPlatformVersion - 13.7 - DTSDKBuild - 17H22 - DTSDKName - iphoneos13.7 - DTXcode - 1170 - DTXcodeBuild - 11E801a - MinimumOSVersion - 11.0 + LSRequiresIPhoneOS + NSAppTransportSecurity NSAllowsArbitraryLoads - UIDeviceFamily - - 2 - UIFileSharingEnabled UILaunchStoryboardName LaunchScreen UIRequiredDeviceCapabilities - arm64 - metal + armv7 + opengles-2 UISupportedInterfaceOrientations + + UIInterfaceOrientationLandscapeLeft + UIInterfaceOrientationLandscapeRight + + UISupportedInterfaceOrientations~ipad UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight diff --git a/configure_ios.sh b/configure_ios.sh index 93153f630..f8f8049a6 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -6,7 +6,7 @@ sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib srcDir="../vcmi" /Users/Shared/xbmc-depends/x86_64-darwin19.6.0-native/bin/cmake "$srcDir" -G Xcode \ - -DENABLE_LAUNCHER=0 \ + -DBUNDLE_IDENTIFIER_PREFIX=com.kambala \ -Wno-dev \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ -DPLATFORM=${1:-OS64} \ diff --git a/package_ios.sh b/package_ios.sh index 5240b74a1..ec3dadf1b 100755 --- a/package_ios.sh +++ b/package_ios.sh @@ -25,11 +25,6 @@ done mv -f *.dylib Frameworks popd -for app in vcmiclient vcmiserver; do - cp -f ../vcmi/Info.plist "$productsDir/$app.app" -done -sed -i '' -e 's/client/server/g' -e 's/>VCMIVCMI server + + + + CFBundleDevelopmentRegion + en + CFBundleExecutable + vcmiserver + CFBundleIdentifier + @BUNDLE_IDENTIFIER_PREFIX@.vcmiserver + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + VCMI server + CFBundlePackageType + APPL + CFBundleShortVersionString + @APP_SHORT_VERSION@ + CFBundleSignature + ???? + CFBundleVersion + 1 + LSRequiresIPhoneOS + + NSAppTransportSecurity + + NSAllowsArbitraryLoads + + + UIFileSharingEnabled + + UILaunchStoryboardName + LaunchScreen + UIRequiredDeviceCapabilities + + armv7 + + UISupportedInterfaceOrientations + + UIInterfaceOrientationLandscapeLeft + UIInterfaceOrientationLandscapeRight + UIInterfaceOrientationPortrait + + UISupportedInterfaceOrientations~ipad + + UIInterfaceOrientationLandscapeLeft + UIInterfaceOrientationLandscapeRight + UIInterfaceOrientationPortrait + UIInterfaceOrientationPortraitUpsideDown + + + diff --git a/server/main_ios.mm b/server/ios/main.mm similarity index 100% rename from server/main_ios.mm rename to server/ios/main.mm From b6c4126bedee0f9bb1441c188259f65faa7484b1 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 11 Mar 2021 11:52:09 +0300 Subject: [PATCH 020/131] install files after building server/client package required files inside app bundle --- CMakeLists.txt | 27 +++++++++++++++------------ client/CMakeLists.txt | 10 ++++++++-- lib/VCMIDirs.cpp | 10 ---------- server/CMakeLists.txt | 8 +++++++- 4 files changed, 30 insertions(+), 25 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 968f76536..85d5139dd 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -61,8 +61,8 @@ if(APPLE_IOS) set(BUNDLE_IDENTIFIER_PREFIX "eu.vcmi" CACHE STRING "Bundle identifier prefix") else() option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) + option(ENABLE_TEST "Enable compilation of unit tests" ON) endif() -option(ENABLE_TEST "Enable compilation of unit tests" ON) if(NOT ${CMAKE_VERSION} VERSION_LESS "3.16.0") option(ENABLE_PCH "Enable compilation using precompiled headers" ON) endif(NOT ${CMAKE_VERSION} VERSION_LESS "3.16.0") @@ -232,8 +232,11 @@ if(CMAKE_COMPILER_IS_GNUCXX OR NOT WIN32) #so far all *nix compilers support suc endif() endif() -# TODO: also enable for macOS if(APPLE_IOS) + set(CMAKE_XCODE_ATTRIBUTE_TARGETED_DEVICE_FAMILY "1,2") # iPhone + iPad + set(CMAKE_XCODE_ATTRIBUTE_GCC_WARN_64_TO_32_BIT_CONVERSION "NO") + + # TODO: also enable for macOS set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fmodules") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fmodules") endif(APPLE_IOS) @@ -336,19 +339,19 @@ elseif(APPLE) set(LIB_DIR "." CACHE STRING "Where to install main library") set(DATA_DIR "." CACHE STRING "Where to install data files") else() - set(APP_BUNDLE_DIR "${CMAKE_PROJECT_NAME}.app") if(APPLE_MACOS) + set(APP_BUNDLE_DIR "${CMAKE_PROJECT_NAME}.app") set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}/Contents") set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_CONTENTS_DIR}/MacOS") - else() - set(APP_BUNDLE_CONTENTS_DIR "${APP_BUNDLE_DIR}") - set(APP_BUNDLE_BINARY_DIR "${APP_BUNDLE_DIR}") - endif(APPLE_MACOS) - set(APP_BUNDLE_RESOURCES_DIR "${APP_BUNDLE_CONTENTS_DIR}/Resources") + set(APP_BUNDLE_RESOURCES_DIR "${APP_BUNDLE_CONTENTS_DIR}/Resources") - set(BIN_DIR "${APP_BUNDLE_BINARY_DIR}" CACHE STRING "Where to install binaries") - set(LIB_DIR "${APP_BUNDLE_CONTENTS_DIR}/Frameworks" CACHE STRING "Where to install main library") - set(DATA_DIR "${APP_BUNDLE_RESOURCES_DIR}/Data" CACHE STRING "Where to install data files") + set(BIN_DIR "${APP_BUNDLE_BINARY_DIR}" CACHE STRING "Where to install binaries") + set(LIB_DIR "${APP_BUNDLE_CONTENTS_DIR}/Frameworks" CACHE STRING "Where to install main library") + set(DATA_DIR "${APP_BUNDLE_RESOURCES_DIR}/Data" CACHE STRING "Where to install data files") + else() + set(LIB_DIR "Frameworks") + set(DATA_DIR ".") + endif(APPLE_MACOS) endif() else() # includes lib path which determines where to install shared libraries (either /lib or /lib64) @@ -415,7 +418,7 @@ install(DIRECTORY scripts DESTINATION ${DATA_DIR}) install(DIRECTORY Mods DESTINATION ${DATA_DIR}) # that script is useless for Windows -if(NOT WIN32) +if(NOT WIN32 AND NOT APPLE_IOS) install(FILES vcmibuilder DESTINATION ${BIN_DIR} PERMISSIONS OWNER_WRITE OWNER_READ OWNER_EXECUTE GROUP_READ GROUP_EXECUTE diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 3c031e6ee..3e78ac9f5 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -177,7 +177,7 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO" # SDL2_image + "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO -framework Metal -framework OpenGLES -framework AVFoundation -framework GameController -framework CoreMotion" # SDL2_image ) set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in") @@ -204,7 +204,13 @@ target_include_directories(vcmiclient vcmi_set_output_dir(vcmiclient "") enable_pch(vcmiclient) -install(TARGETS vcmiclient DESTINATION ${BIN_DIR}) +if(APPLE_IOS) + add_custom_command(TARGET vcmiclient POST_BUILD + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" + ) +else() + install(TARGETS vcmiclient DESTINATION ${BIN_DIR}) +endif() #install icons and desktop file on Linux if(NOT WIN32 AND NOT APPLE) diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index 5a59ff03e..f78601c70 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -389,7 +389,6 @@ class VCMIDirsIOS final : public VCMIDirsApple std::vector dataPaths() const override; bfs::path libraryPath() const override; - boost::filesystem::path fullLibraryPath(const std::string & desiredFolder, const std::string & baseLibName) const override; bfs::path binaryPath() const override; bool developmentMode() const override; @@ -420,15 +419,6 @@ bfs::path VCMIDirsIOS::libraryPath() const return {ios_frameworksPath()}; #endif } -// todo ios: place AI libs in subdir? -boost::filesystem::path VCMIDirsIOS::fullLibraryPath(const std::string & desiredFolder, const std::string & baseLibName) const -{ -#ifdef VCMI_IOS_SIM - return VCMIDirsApple::fullLibraryPath(desiredFolder, baseLibName); -#else - return libraryPath() / libraryName(baseLibName); -#endif -} bfs::path VCMIDirsIOS::binaryPath() const { return {ios_bundlePath()}; } bool VCMIDirsIOS::developmentMode() const { return false; } diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 2026c0a4f..e0bf6a36e 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -56,4 +56,10 @@ endif() vcmi_set_output_dir(vcmiserver "") enable_pch(vcmiserver) -install(TARGETS vcmiserver DESTINATION ${BIN_DIR}) +if(APPLE_IOS) + add_custom_command(TARGET vcmiserver POST_BUILD + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" + ) +else() + install(TARGETS vcmiserver DESTINATION ${BIN_DIR}) +endif() From cfa22c33ad9f76d14791950a9ec36657e6d9042f Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 12 Mar 2021 13:31:05 +0300 Subject: [PATCH 021/131] use rpath properly --- AI/EmptyAI/CMakeLists.txt | 2 +- CMakeLists.txt | 6 + client/CMakeLists.txt | 6 +- ios.toolchain.cmake | 803 +++++++++++++++++++++++--------------- lib/CMakeLists.txt | 14 +- server/CMakeLists.txt | 7 +- 6 files changed, 517 insertions(+), 321 deletions(-) diff --git a/AI/EmptyAI/CMakeLists.txt b/AI/EmptyAI/CMakeLists.txt index 7d2c38377..e6b962fb5 100644 --- a/AI/EmptyAI/CMakeLists.txt +++ b/AI/EmptyAI/CMakeLists.txt @@ -20,4 +20,4 @@ target_link_libraries(EmptyAI PRIVATE vcmi) vcmi_set_output_dir(EmptyAI "AI") enable_pch(EmptyAI) -install(TARGETS EmptyAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) +install(TARGETS EmptyAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} OPTIONAL) diff --git a/CMakeLists.txt b/CMakeLists.txt index 85d5139dd..306419f18 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -154,6 +154,7 @@ set(CMAKE_MAP_IMPORTED_CONFIG_MINSIZEREL MinSizeRel Release RelWithDebInfo "") set(CMAKE_MAP_IMPORTED_CONFIG_RELEASE Release RelWithDebInfo MinSizeRel "") if(APPLE_IOS) + set(CMAKE_MACOSX_RPATH 1) set(SYSTEM_LIBS ${SYSTEM_LIBS} iconv) # boost.locale endif(APPLE_IOS) @@ -269,6 +270,11 @@ if(TARGET zlib::zlib) add_library(ZLIB::ZLIB ALIAS zlib::zlib) endif() +# TODO: needed only for device+simulator +# if(APPLE_IOS) +# set(ZLIB_LIBRARIES "-lz") +# endif() + find_package(ffmpeg COMPONENTS avutil swscale avformat avcodec) option(FORCE_BUNDLED_MINIZIP "Force bundled Minizip library" OFF) if(NOT FORCE_BUNDLED_MINIZIP) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 3e78ac9f5..0b7390023 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -180,7 +180,10 @@ elseif(APPLE_IOS) "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO -framework Metal -framework OpenGLES -framework AVFoundation -framework GameController -framework CoreMotion" # SDL2_image ) - set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in") + set_target_properties(vcmiclient PROPERTIES + MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in" + SKIP_BUILD_RPATH 1 + ) target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") @@ -207,6 +210,7 @@ enable_pch(vcmiclient) if(APPLE_IOS) add_custom_command(TARGET vcmiclient POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" + COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true ) else() install(TARGETS vcmiclient DESTINATION ${BIN_DIR}) diff --git a/ios.toolchain.cmake b/ios.toolchain.cmake index 94db9fc25..d6fae99c2 100644 --- a/ios.toolchain.cmake +++ b/ios.toolchain.cmake @@ -50,9 +50,9 @@ # # INFORMATION / HELP # -# The following arguments control the behaviour of this toolchain: +# The following options control the behaviour of this toolchain: # -# PLATFORM: (default "OS") +# PLATFORM: (default "OS64") # OS = Build for iPhoneOS. # OS64 = Build for arm64 iphoneOS. # OS64COMBINED = Build for arm64 x86_64 iphoneOS. Combined into FAT STATIC lib (supported on 3.14+ of CMakewith "-G Xcode" argument ONLY) @@ -65,6 +65,12 @@ # WATCHOS = Build for armv7k arm64_32 for watchOS. # WATCHOSCOMBINED = Build for armv7k arm64_32 x86_64 watchOS. Combined into FAT STATIC lib (supported on 3.14+ of CMake with "-G Xcode" argument ONLY) # SIMULATOR_WATCHOS = Build for x86_64 for watchOS Simulator. +# MAC = Build for x86_64 macOS. +# MAC_ARM64 = Build for Apple Silicon macOS. +# MAC_CATALYST = Build for x86_64 macOS with Catalyst support (iOS toolchain on macOS). +# Note: The build argument "MACOSX_DEPLOYMENT_TARGET" can be used to control min-version of macOS +# MAC_CATALYST_ARM64 = Build for Apple Silicon macOS with Catalyst support (iOS toolchain on macOS). +# Note: The build argument "MACOSX_DEPLOYMENT_TARGET" can be used to control min-version of macOS # # CMAKE_OSX_SYSROOT: Path to the SDK to use. By default this is # automatically determined from PLATFORM and xcodebuild, but @@ -96,12 +102,17 @@ # SIMULATOR_TVOS = x86_64 (i386 has since long been deprecated) # WATCHOS = armv7k arm64_32 (if applicable) # SIMULATOR_WATCHOS = x86_64 (i386 has since long been deprecated) +# MAC = x86_64 +# MAC_ARM64 = arm64 +# MAC_CATALYST = x86_64 +# MAC_CATALYST_ARM64 = arm64 # -# This toolchain defines the following variables for use externally: +# This toolchain defines the following properties (available via get_property()) for use externally: # +# PLATFORM: The currently targeted platform. # XCODE_VERSION: Version number (not including Build version) of Xcode detected. # SDK_VERSION: Version of SDK being used. -# CMAKE_OSX_ARCHITECTURES: Architectures being compiled for (generated from PLATFORM). +# OSX_ARCHITECTURES: Architectures being compiled for (generated from PLATFORM). # APPLE_TARGET_TRIPLE: Used by autoconf build systems. NOTE: If "ARCHS" are overridden, this will *NOT* be set! # # This toolchain defines the following macros for use externally: @@ -113,18 +124,102 @@ # # find_host_package (PROGRAM ARGS) # A macro used to find executable programs on the host system, not within the -# environment. Thanks to the android-cmake project for providing the +# environment. Thanks to the android-cmake project for providing the # command. # -# ******************************** DEPRECATIONS ******************************* -# -# IOS_DEPLOYMENT_TARGET: (Deprecated) Alias to DEPLOYMENT_TARGET -# CMAKE_IOS_DEVELOPER_ROOT: (Deprecated) Alias to CMAKE_DEVELOPER_ROOT -# IOS_PLATFORM: (Deprecated) Alias to PLATFORM -# IOS_ARCH: (Deprecated) Alias to ARCHS -# -# ***************************************************************************** + +cmake_minimum_required(VERSION 3.8.0) + +# CMake invokes the toolchain file twice during the first build, but only once during subsequent rebuilds. +if(IOS_TOOLCHAIN_HAS_RUN) + return() +endif(IOS_TOOLCHAIN_HAS_RUN) +set(IOS_TOOLCHAIN_HAS_RUN true) + +############################################################################### +# OPTIONS # +############################################################################### + +option(DROP_32_BIT "Drops the 32-bit targets universally." YES) + +############################################################################### +# END OPTIONS # +############################################################################### + +# List of supported platform values +list(APPEND _supported_platforms + "OS" "OS64" "OS64COMBINED" "SIMULATOR" "SIMULATOR64" "SIMULATORARM64" + "TVOS" "TVOSCOMBINED" "SIMULATOR_TVOS" + "WATCHOS" "WATCHOSCOMBINED" "SIMULATOR_WATCHOS" + "MAC" "MAC_ARM64" + "MAC_CATALYST" "MAC_CATALYST_ARM64") + +# Cache what generator is used +set(USED_CMAKE_GENERATOR "${CMAKE_GENERATOR}") + +# Check if using a CMake version capable of building combined FAT builds (simulator and target slices combined in one static lib) +if(${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.14") + set(MODERN_CMAKE YES) +endif() + +# Get the Xcode version being used. +# Problem: CMake runs toolchain files multiple times, but can't read cache variables on some runs. +# Workaround: On first run (in which cache variables are always accessible), set an intermediary environment variable. # +# NOTE: This pattern is used i many places in this toolchain to speed up checks of all sorts +if(DEFINED XCODE_VERSION_INT) + # Environment variables are always preserved. + set(ENV{_XCODE_VERSION_INT} "${XCODE_VERSION_INT}") +elseif(DEFINED ENV{_XCODE_VERSION_INT}) + set(XCODE_VERSION_INT "$ENV{_XCODE_VERSION_INT}") +elseif(NOT DEFINED XCODE_VERSION_INT) + find_program(XCODEBUILD_EXECUTABLE xcodebuild) + if(NOT XCODEBUILD_EXECUTABLE) + message(FATAL_ERROR "xcodebuild not found. Please install either the standalone commandline tools or Xcode.") + endif() + execute_process(COMMAND ${XCODEBUILD_EXECUTABLE} -version + OUTPUT_VARIABLE XCODE_VERSION_INT + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) + string(REGEX MATCH "Xcode [0-9\\.]+" XCODE_VERSION_INT "${XCODE_VERSION_INT}") + string(REGEX REPLACE "Xcode ([0-9\\.]+)" "\\1" XCODE_VERSION_INT "${XCODE_VERSION_INT}") + set(XCODE_VERSION_INT "${XCODE_VERSION_INT}" CACHE INTERNAL "") +endif() + +# Assuming that xcode 12.0 is installed you most probably have ios sdk 14.0 or later installed (tested on Big Sur) +# if you don't set a deployment target it will be set the way you only get 64-bit builds +if(NOT DEFINED DEPLOYMENT_TARGET AND XCODE_VERSION_INT VERSION_GREATER 12.0) + # Temporarily fix the arm64 issues in CMake install-combined by excluding arm64 for simulator builds (needed for Apple Silicon...) + set(CMAKE_XCODE_ATTRIBUTE_EXCLUDED_ARCHS[sdk=iphonesimulator*] "arm64") +endif() + +# Check if the platform variable is set +if(DEFINED PLATFORM) + # Environment variables are always preserved. + set(ENV{_PLATFORM} "${PLATFORM}") +elseif(DEFINED ENV{_PLATFORM}) + set(PLATFORM "$ENV{_PLATFORM}") +elseif(NOT DEFINED PLATFORM) + message(FATAL_ERROR "PLATFORM argument not set. Bailing configure since I don't know what target you want to build for!") +endif () + +# Safeguard that the platform value is set and is one of the supported values +list(FIND _supported_platforms ${PLATFORM} contains_PLATFORM) +if("${contains_PLATFORM}" EQUAL "-1") + string(REPLACE ";" "\n * " _supported_platforms_formatted "${_supported_platforms}") + message(FATAL_ERROR " Invalid PLATFORM specified! Current value: ${PLATFORM}.\n" + " Supported PLATFORM values: \n * ${_supported_platforms_formatted}") +endif() + +# Check if Apple Silicon is supported +if(PLATFORM MATCHES "^(MAC_ARM64)$|^(MAC_CATALYST_ARM64)$" AND ${CMAKE_VERSION} VERSION_LESS "3.19.5") + message(FATAL_ERROR "Apple Silicon builds requires a minimum of CMake 3.19.5") +endif() + +# Touch toolchain variable to suppress "unused variable" warning. +# This happens if CMake is invoked with the same command line the second time. +if(CMAKE_TOOLCHAIN_FILE) +endif() # Fix for PThread library not in path set(CMAKE_THREAD_LIBS_INIT "-lpthread") @@ -132,109 +227,49 @@ set(CMAKE_HAVE_THREADS_LIBRARY 1) set(CMAKE_USE_WIN32_THREADS_INIT 0) set(CMAKE_USE_PTHREADS_INIT 1) -# Cache what generator is used -set(USED_CMAKE_GENERATOR "${CMAKE_GENERATOR}" CACHE STRING "Expose CMAKE_GENERATOR" FORCE) - -if(${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.14") - set(MODERN_CMAKE YES) -endif() - -# Get the Xcode version being used. -execute_process(COMMAND xcodebuild -version - OUTPUT_VARIABLE XCODE_VERSION - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) -string(REGEX MATCH "Xcode [0-9\\.]+" XCODE_VERSION "${XCODE_VERSION}") -string(REGEX REPLACE "Xcode ([0-9\\.]+)" "\\1" XCODE_VERSION "${XCODE_VERSION}") - -# Assuming that xcode 12.0 is installed you most probably have ios sdk 14.2 or later installed (tested on Big Sur) -# if you don't set a deployment target it will be set the way you only get 64-bit builds -if(NOT DEFINED DEPLOYMENT_TARGET AND XCODE_VERSION VERSION_GREATER 12.0) - option(DROP_32_BIT "Will make drop 32-bit support universally. On later sdks you won't be able to build 32-bit apps" yes) - # Temporarily fix the arm64 issues in CMake install-combined by excluding arm64 for simulator builds (needed for Apple Silicon...) - set(CMAKE_XCODE_ATTRIBUTE_EXCLUDED_ARCHS[sdk=iphonesimulator*] "arm64") -endif() - -######## ALIASES (DEPRECATION WARNINGS) - -if(DEFINED IOS_PLATFORM) - set(PLATFORM ${IOS_PLATFORM}) - message(DEPRECATION "IOS_PLATFORM argument is DEPRECATED. Consider using the new PLATFORM argument instead.") -endif() - -if(DEFINED IOS_DEPLOYMENT_TARGET) - set(DEPLOYMENT_TARGET ${IOS_DEPLOYMENT_TARGET}) - message(DEPRECATION "IOS_DEPLOYMENT_TARGET argument is DEPRECATED. Consider using the new DEPLOYMENT_TARGET argument instead.") -endif() - -if(DEFINED CMAKE_IOS_DEVELOPER_ROOT) - set(CMAKE_DEVELOPER_ROOT ${CMAKE_IOS_DEVELOPER_ROOT}) - message(DEPRECATION "CMAKE_IOS_DEVELOPER_ROOT argument is DEPRECATED. Consider using the new CMAKE_DEVELOPER_ROOT argument instead.") -endif() - -if(DEFINED IOS_ARCH) - set(ARCHS ${IOS_ARCH}) - message(DEPRECATION "IOS_ARCH argument is DEPRECATED. Consider using the new ARCHS argument instead.") -endif() - -######## END ALIASES - -# Unset the FORCE on cache variables if in try_compile() -set(FORCE_CACHE FORCE) -get_property(_CMAKE_IN_TRY_COMPILE GLOBAL PROPERTY IN_TRY_COMPILE) -if(_CMAKE_IN_TRY_COMPILE) - unset(FORCE_CACHE) -endif() - -# Default to building for iPhoneOS if not specified otherwise, and we cannot -# determine the platform from the CMAKE_OSX_ARCHITECTURES variable. The use -# of CMAKE_OSX_ARCHITECTURES is such that try_compile() projects can correctly -# determine the value of PLATFORM from the root project, as -# CMAKE_OSX_ARCHITECTURES is propagated to them by CMake. -if(NOT DEFINED PLATFORM) - if (CMAKE_OSX_ARCHITECTURES) - if(CMAKE_OSX_ARCHITECTURES MATCHES "arm64" AND CMAKE_OSX_SYSROOT MATCHES ".*iphoneos.*") - set(PLATFORM "OS64") - elseif(CMAKE_OSX_ARCHITECTURES MATCHES ".*arm.*" AND CMAKE_OSX_SYSROOT MATCHES ".*iphoneos.*") - set(PLATFORM "OS") - elseif(CMAKE_OSX_ARCHITECTURES MATCHES "i386" AND CMAKE_OSX_SYSROOT MATCHES ".*iphonesimulator.*") - set(PLATFORM "SIMULATOR") - elseif(CMAKE_OSX_ARCHITECTURES MATCHES "x86_64" AND CMAKE_OSX_SYSROOT MATCHES ".*iphonesimulator.*") - set(PLATFORM "SIMULATOR64") - elseif(CMAKE_OSX_ARCHITECTURES MATCHES "arm64" AND CMAKE_OSX_SYSROOT MATCHES ".*iphonesimulator.*") - set(PLATFORM "SIMULATORARM64") - elseif(CMAKE_OSX_ARCHITECTURES MATCHES "arm64" AND CMAKE_OSX_SYSROOT MATCHES ".*appletvos.*") - set(PLATFORM "TVOS") - elseif(CMAKE_OSX_ARCHITECTURES MATCHES "x86_64" AND CMAKE_OSX_SYSROOT MATCHES ".*appletvsimulator.*") - set(PLATFORM "SIMULATOR_TVOS") - elseif(CMAKE_OSX_ARCHITECTURES MATCHES ".*armv7k.*" AND CMAKE_OSX_SYSROOT MATCHES ".*watchos.*") - set(PLATFORM "WATCHOS") - elseif(CMAKE_OSX_ARCHITECTURES MATCHES "i386" AND CMAKE_OSX_SYSROOT MATCHES ".*watchsimulator.*") - set(PLATFORM "SIMULATOR_WATCHOS") - endif() - endif() - if (NOT PLATFORM) - if(DROP_32_BIT) - set(PLATFORM "OS64") - else() - set(PLATFORM "OS") - endif() +# Specify minimum version of deployment target. +if(NOT DEFINED DEPLOYMENT_TARGET) + if (PLATFORM MATCHES "WATCHOS") + # Unless specified, SDK version 4.0 is used by default as minimum target version (watchOS). + set(DEPLOYMENT_TARGET "4.0") + elseif(PLATFORM STREQUAL "MAC") + # Unless specified, SDK version 10.13 (High sierra) is used by default as minimum target version (macos). + set(DEPLOYMENT_TARGET "10.13") + elseif(PLATFORM STREQUAL "MAC_ARM64") + # Unless specified, SDK version 11.0 (Big Sur) is used by default as minimum target version (macos on arm). + set(DEPLOYMENT_TARGET "11.0") + elseif(PLATFORM STREQUAL "MAC_CATALYST" OR PLATFORM STREQUAL "MAC_CATALYST_ARM64") + # Unless specified, SDK version 13.0 is used by default as minimum target version (mac catalyst minimum requirement). + set(DEPLOYMENT_TARGET "13.0") + else() + # Unless specified, SDK version 11.0 is used by default as minimum target version (iOS, tvOS). + set(DEPLOYMENT_TARGET "11.0") endif() + message(STATUS "[DEFAULTS] Using the default min-version since DEPLOYMENT_TARGET not provided!") +elseif(DEFINED DEPLOYMENT_TARGET AND PLATFORM STREQUAL "MAC_CATALYST" AND ${DEPLOYMENT_TARGET} VERSION_LESS "13.0") + message(FATAL_ERROR "Mac Catalyst builds requires a minimum deployment target of 13.0!") endif() -set(PLATFORM_INT "${PLATFORM}" CACHE STRING "Type of platform for which the build targets.") +# Store the DEPLOYMENT_TARGET in the cache +set(DEPLOYMENT_TARGET "${DEPLOYMENT_TARGET}" CACHE INTERNAL "") # Handle the case where we are targeting iOS and a version above 10.3.4 (32-bit support dropped officially) -if(PLATFORM_INT STREQUAL "OS" AND DEPLOYMENT_TARGET VERSION_GREATER_EQUAL 10.3.4) - set(PLATFORM_INT "OS64") +if(PLATFORM STREQUAL "OS" AND DEPLOYMENT_TARGET VERSION_GREATER_EQUAL 10.3.4) + set(PLATFORM "OS64") message(STATUS "Targeting minimum SDK version ${DEPLOYMENT_TARGET}. Dropping 32-bit support.") -elseif(PLATFORM_INT STREQUAL "SIMULATOR" AND DEPLOYMENT_TARGET VERSION_GREATER_EQUAL 10.3.4) - set(PLATFORM_INT "SIMULATOR64") +elseif(PLATFORM STREQUAL "SIMULATOR" AND DEPLOYMENT_TARGET VERSION_GREATER_EQUAL 10.3.4) + set(PLATFORM "SIMULATOR64") message(STATUS "Targeting minimum SDK version ${DEPLOYMENT_TARGET}. Dropping 32-bit support.") endif() +set(PLATFORM_INT "${PLATFORM}") + +if(DEFINED ARCHS) + string(REPLACE ";" "-" ARCHS_SPLIT "${ARCHS}") +endif() + # Determine the platform name and architectures for use in xcodebuild commands -# from the specified PLATFORM name. +# from the specified PLATFORM_INT name. if(PLATFORM_INT STREQUAL "OS") set(SDK_NAME iphoneos) if(NOT ARCHS) @@ -244,23 +279,35 @@ if(PLATFORM_INT STREQUAL "OS") elseif(PLATFORM_INT STREQUAL "OS64") set(SDK_NAME iphoneos) if(NOT ARCHS) - if (XCODE_VERSION VERSION_GREATER 10.0) + if (XCODE_VERSION_INT VERSION_GREATER 10.0) set(ARCHS arm64) # Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example else() set(ARCHS arm64) endif() set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) endif() elseif(PLATFORM_INT STREQUAL "OS64COMBINED") set(SDK_NAME iphoneos) if(MODERN_CMAKE) if(NOT ARCHS) - if (XCODE_VERSION VERSION_GREATER 10.0) + if (XCODE_VERSION_INT VERSION_GREATER 10.0) set(ARCHS arm64 x86_64) # Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphoneos*] "arm64") + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphonesimulator*] "x86_64") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphoneos*] "arm64") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphonesimulator*] "x86_64") else() set(ARCHS arm64 x86_64) + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphoneos*] "arm64") + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphonesimulator*] "x86_64") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphoneos*] "arm64") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphonesimulator*] "x86_64") endif() set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-ios) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) endif() else() message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the OS64COMBINED setting work") @@ -270,6 +317,8 @@ elseif(PLATFORM_INT STREQUAL "SIMULATOR") if(NOT ARCHS) set(ARCHS i386) set(APPLE_TARGET_TRIPLE_INT i386-apple-ios) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) endif() message(DEPRECATION "SIMULATOR IS DEPRECATED. Consider using SIMULATOR64 instead.") elseif(PLATFORM_INT STREQUAL "SIMULATOR64") @@ -277,18 +326,24 @@ elseif(PLATFORM_INT STREQUAL "SIMULATOR64") if(NOT ARCHS) set(ARCHS x86_64) set(APPLE_TARGET_TRIPLE_INT x86_64-apple-ios) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) endif() elseif(PLATFORM_INT STREQUAL "SIMULATORARM64") set(SDK_NAME iphonesimulator) if(NOT ARCHS) set(ARCHS arm64) set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) endif() elseif(PLATFORM_INT STREQUAL "TVOS") set(SDK_NAME appletvos) if(NOT ARCHS) set(ARCHS arm64) set(APPLE_TARGET_TRIPLE_INT aarch64-apple-tvos) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos) endif() elseif (PLATFORM_INT STREQUAL "TVOSCOMBINED") set(SDK_NAME appletvos) @@ -296,6 +351,12 @@ elseif (PLATFORM_INT STREQUAL "TVOSCOMBINED") if(NOT ARCHS) set(ARCHS arm64 x86_64) set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-tvos) + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=appletvos*] "arm64") + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=appletvsimulator*] "x86_64") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=appletvos*] "arm64") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=appletvsimulator*] "x86_64") + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos) endif() else() message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the TVOSCOMBINED setting work") @@ -305,29 +366,43 @@ elseif(PLATFORM_INT STREQUAL "SIMULATOR_TVOS") if(NOT ARCHS) set(ARCHS x86_64) set(APPLE_TARGET_TRIPLE_INT x86_64-apple-tvos) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos) endif() elseif(PLATFORM_INT STREQUAL "WATCHOS") set(SDK_NAME watchos) if(NOT ARCHS) - if (XCODE_VERSION VERSION_GREATER 10.0) + if (XCODE_VERSION_INT VERSION_GREATER 10.0) set(ARCHS armv7k arm64_32) set(APPLE_TARGET_TRIPLE_INT aarch64_32-apple-watchos) else() set(ARCHS armv7k) set(APPLE_TARGET_TRIPLE_INT arm-apple-watchos) endif() + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos) endif() elseif(PLATFORM_INT STREQUAL "WATCHOSCOMBINED") set(SDK_NAME watchos) if(MODERN_CMAKE) if(NOT ARCHS) - if (XCODE_VERSION VERSION_GREATER 10.0) + if (XCODE_VERSION_INT VERSION_GREATER 10.0) set(ARCHS armv7k arm64_32 i386) set(APPLE_TARGET_TRIPLE_INT aarch64_32-i386-apple-watchos) + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchos*] "armv7k arm64_32") + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchsimulator*] "i386") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchos*] "armv7k arm64_32") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchsimulator*] "i386") else() set(ARCHS armv7k i386) set(APPLE_TARGET_TRIPLE_INT arm-i386-apple-watchos) + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchos*] "armv7k") + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchsimulator*] "i386") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchos*] "armv7k") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchsimulator*] "i386") endif() + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos) endif() else() message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the WATCHOSCOMBINED setting work") @@ -337,177 +412,242 @@ elseif(PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") if(NOT ARCHS) set(ARCHS i386) set(APPLE_TARGET_TRIPLE_INT i386-apple-watchos) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos) + endif() +elseif(PLATFORM_INT STREQUAL "MAC" OR PLATFORM_INT STREQUAL "MAC_CATALYST") + set(SDK_NAME macosx) + if(NOT ARCHS) + set(ARCHS x86_64) + endif() + string(REPLACE ";" "-" ARCHS_SPLIT "${ARCHS}") + if(PLATFORM_INT STREQUAL "MAC") + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-macosx) + elseif(PLATFORM_INT STREQUAL "MAC_CATALYST") + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-macabi) + endif() +elseif(PLATFORM_INT MATCHES "^(MAC_ARM64)$|^(MAC_CATALYST_ARM64)$") + set(SDK_NAME macosx) + if(NOT ARCHS) + set(ARCHS arm64) + endif() + string(REPLACE ";" "-" ARCHS_SPLIT "${ARCHS}") + if(PLATFORM_INT STREQUAL "MAC_ARM64") + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-macosx) + elseif(PLATFORM_INT STREQUAL "MAC_CATALYST_ARM64") + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-macabi) endif() else() message(FATAL_ERROR "Invalid PLATFORM: ${PLATFORM_INT}") endif() -if(MODERN_CMAKE AND PLATFORM_INT MATCHES ".*COMBINED" AND NOT USED_CMAKE_GENERATOR MATCHES "Xcode") +if(MODERN_CMAKE AND PLATFORM_INT MATCHES ".*COMBINED" AND NOT CMAKE_GENERATOR MATCHES "Xcode") message(FATAL_ERROR "The COMBINED options only work with Xcode generator, -G Xcode") endif() +if(CMAKE_GENERATOR MATCHES "Xcode" AND PLATFORM_INT MATCHES "MAC_CATALYST_.*") + set(CMAKE_XCODE_ATTRIBUTE_CLANG_CXX_LIBRARY "libc++") + set(CMAKE_XCODE_ATTRIBUTE_SUPPORTED_PLATFORMS "macosx") + set(CMAKE_XCODE_EFFECTIVE_PLATFORMS "-maccatalyst") + if(NOT DEFINED MACOSX_DEPLOYMENT_TARGET) + set(CMAKE_XCODE_ATTRIBUTE_MACOSX_DEPLOYMENT_TARGET "10.15") + else() + set(CMAKE_XCODE_ATTRIBUTE_MACOSX_DEPLOYMENT_TARGET "${MACOSX_DEPLOYMENT_TARGET}") + endif() +elseif(CMAKE_GENERATOR MATCHES "Xcode") + set(CMAKE_XCODE_ATTRIBUTE_IPHONEOS_DEPLOYMENT_TARGET "${DEPLOYMENT_TARGET}") + if(NOT PLATFORM_INT MATCHES ".*COMBINED") + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=${SDK_NAME}*] "${ARCHS}") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=${SDK_NAME}*] "${ARCHS}") + endif() +endif() + # If user did not specify the SDK root to use, then query xcodebuild for it. -execute_process(COMMAND xcodebuild -version -sdk ${SDK_NAME} Path - OUTPUT_VARIABLE CMAKE_OSX_SYSROOT_INT - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) +if(DEFINED CMAKE_OSX_SYSROOT_INT) + # Environment variables are always preserved. + set(ENV{_CMAKE_OSX_SYSROOT_INT} "${CMAKE_OSX_SYSROOT_INT}") +elseif(DEFINED ENV{_CMAKE_OSX_SYSROOT_INT}) + set(CMAKE_OSX_SYSROOT_INT "$ENV{_CMAKE_OSX_SYSROOT_INT}") +elseif(NOT DEFINED CMAKE_OSX_SYSROOT_INT) + execute_process(COMMAND ${XCODEBUILD_EXECUTABLE} -version -sdk ${SDK_NAME} Path + OUTPUT_VARIABLE CMAKE_OSX_SYSROOT_INT + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) +endif() + if (NOT DEFINED CMAKE_OSX_SYSROOT_INT AND NOT DEFINED CMAKE_OSX_SYSROOT) message(SEND_ERROR "Please make sure that Xcode is installed and that the toolchain" - "is pointing to the correct path. Please run:" - "sudo xcode-select -s /Applications/Xcode.app/Contents/Developer" - "and see if that fixes the problem for you.") + "is pointing to the correct path. Please run:" + "sudo xcode-select -s /Applications/Xcode.app/Contents/Developer" + "and see if that fixes the problem for you.") message(FATAL_ERROR "Invalid CMAKE_OSX_SYSROOT: ${CMAKE_OSX_SYSROOT} " - "does not exist.") + "does not exist.") elseif(DEFINED CMAKE_OSX_SYSROOT_INT) - set(CMAKE_OSX_SYSROOT "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") -endif() - -# Set Xcode property for SDKROOT as well if Xcode generator is used -if(USED_CMAKE_GENERATOR MATCHES "Xcode") - set(CMAKE_OSX_SYSROOT "${SDK_NAME}" CACHE INTERNAL "") -endif() - -# Specify minimum version of deployment target. -if(NOT DEFINED DEPLOYMENT_TARGET) - if (PLATFORM_INT STREQUAL "WATCHOS" OR PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") - # Unless specified, SDK version 2.0 is used by default as minimum target version (watchOS). - set(DEPLOYMENT_TARGET "2.0" - CACHE STRING "Minimum SDK version to build for." ) - else() - # Unless specified, SDK version 9.0 is used by default as minimum target version (iOS, tvOS). - set(DEPLOYMENT_TARGET "9.0" - CACHE STRING "Minimum SDK version to build for." ) - endif() - message(STATUS "Using the default min-version since DEPLOYMENT_TARGET not provided!") + set(CMAKE_OSX_SYSROOT_INT "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") + # Specify the location or name of the platform SDK to be used in CMAKE_OSX_SYSROOT. + set(CMAKE_OSX_SYSROOT "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") endif() # Use bitcode or not if(NOT DEFINED ENABLE_BITCODE AND NOT ARCHS MATCHES "((^|;|, )(i386|x86_64))+") # Unless specified, enable bitcode support by default - message(STATUS "Enabling bitcode support by default. ENABLE_BITCODE not provided!") + message(STATUS "[DEFAULTS] Enabling bitcode support by default. ENABLE_BITCODE not provided!") set(ENABLE_BITCODE TRUE) elseif(NOT DEFINED ENABLE_BITCODE) - message(STATUS "Disabling bitcode support by default on simulators. ENABLE_BITCODE not provided for override!") + message(STATUS "[DEFAULTS] Disabling bitcode support by default on simulators. ENABLE_BITCODE not provided for override!") set(ENABLE_BITCODE FALSE) endif() -set(ENABLE_BITCODE_INT ${ENABLE_BITCODE} CACHE BOOL "Whether or not to enable bitcode" ${FORCE_CACHE}) +set(ENABLE_BITCODE_INT ${ENABLE_BITCODE} CACHE BOOL + "Whether or not to enable bitcode" FORCE) # Use ARC or not if(NOT DEFINED ENABLE_ARC) # Unless specified, enable ARC support by default set(ENABLE_ARC TRUE) - message(STATUS "Enabling ARC support by default. ENABLE_ARC not provided!") + message(STATUS "[DEFAULTS] Enabling ARC support by default. ENABLE_ARC not provided!") endif() -set(ENABLE_ARC_INT ${ENABLE_ARC} CACHE BOOL "Whether or not to enable ARC" ${FORCE_CACHE}) +set(ENABLE_ARC_INT ${ENABLE_ARC} CACHE BOOL "Whether or not to enable ARC" FORCE) # Use hidden visibility or not if(NOT DEFINED ENABLE_VISIBILITY) # Unless specified, disable symbols visibility by default set(ENABLE_VISIBILITY FALSE) - message(STATUS "Hiding symbols visibility by default. ENABLE_VISIBILITY not provided!") + message(STATUS "[DEFAULTS] Hiding symbols visibility by default. ENABLE_VISIBILITY not provided!") endif() -set(ENABLE_VISIBILITY_INT ${ENABLE_VISIBILITY} CACHE BOOL "Whether or not to hide symbols (-fvisibility=hidden)" ${FORCE_CACHE}) +set(ENABLE_VISIBILITY_INT ${ENABLE_VISIBILITY} CACHE BOOL "Whether or not to hide symbols from the dynamic linker (-fvisibility=hidden)" FORCE) # Set strict compiler checks or not if(NOT DEFINED ENABLE_STRICT_TRY_COMPILE) # Unless specified, disable strict try_compile() set(ENABLE_STRICT_TRY_COMPILE FALSE) - message(STATUS "Using NON-strict compiler checks by default. ENABLE_STRICT_TRY_COMPILE not provided!") + message(STATUS "[DEFAULTS] Using NON-strict compiler checks by default. ENABLE_STRICT_TRY_COMPILE not provided!") endif() -set(ENABLE_STRICT_TRY_COMPILE_INT ${ENABLE_STRICT_TRY_COMPILE} CACHE BOOL "Whether or not to use strict compiler checks" ${FORCE_CACHE}) +set(ENABLE_STRICT_TRY_COMPILE_INT ${ENABLE_STRICT_TRY_COMPILE} CACHE BOOL + "Whether or not to use strict compiler checks" FORCE) + # Get the SDK version information. -execute_process(COMMAND xcodebuild -sdk ${CMAKE_OSX_SYSROOT} -version SDKVersion - OUTPUT_VARIABLE SDK_VERSION - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) +if(DEFINED SDK_VERSION) + # Environment variables are always preserved. + set(ENV{_SDK_VERSION} "${SDK_VERSION}") +elseif(DEFINED ENV{_SDK_VERSION}) + set(SDK_VERSION "$ENV{_SDK_VERSION}") +elseif(NOT DEFINED SDK_VERSION) + execute_process(COMMAND ${XCODEBUILD_EXECUTABLE} -sdk ${CMAKE_OSX_SYSROOT_INT} -version SDKVersion + OUTPUT_VARIABLE SDK_VERSION + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) +endif() # Find the Developer root for the specific iOS platform being compiled for # from CMAKE_OSX_SYSROOT. Should be ../../ from SDK specified in # CMAKE_OSX_SYSROOT. There does not appear to be a direct way to obtain # this information from xcrun or xcodebuild. -if (NOT DEFINED CMAKE_DEVELOPER_ROOT AND NOT USED_CMAKE_GENERATOR MATCHES "Xcode") - get_filename_component(PLATFORM_SDK_DIR ${CMAKE_OSX_SYSROOT} PATH) +if (NOT DEFINED CMAKE_DEVELOPER_ROOT AND NOT CMAKE_GENERATOR MATCHES "Xcode") + get_filename_component(PLATFORM_SDK_DIR ${CMAKE_OSX_SYSROOT_INT} PATH) get_filename_component(CMAKE_DEVELOPER_ROOT ${PLATFORM_SDK_DIR} PATH) - if (NOT DEFINED CMAKE_DEVELOPER_ROOT) - message(FATAL_ERROR "Invalid CMAKE_DEVELOPER_ROOT: " - "${CMAKE_DEVELOPER_ROOT} does not exist.") + if (NOT EXISTS "${CMAKE_DEVELOPER_ROOT}") + message(FATAL_ERROR "Invalid CMAKE_DEVELOPER_ROOT: ${CMAKE_DEVELOPER_ROOT} does not exist.") endif() endif() + # Find the C & C++ compilers for the specified SDK. -if(NOT CMAKE_C_COMPILER) - execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT} -find clang - OUTPUT_VARIABLE CMAKE_C_COMPILER - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) - message(STATUS "Using C compiler: ${CMAKE_C_COMPILER}") +if(DEFINED CMAKE_C_COMPILER) + # Environment variables are always preserved. + set(ENV{_CMAKE_C_COMPILER} "${CMAKE_C_COMPILER}") +elseif(DEFINED ENV{_CMAKE_C_COMPILER}) + set(CMAKE_C_COMPILER "$ENV{_CMAKE_C_COMPILER}") +elseif(NOT DEFINED CMAKE_C_COMPILER) + execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find clang + OUTPUT_VARIABLE CMAKE_C_COMPILER + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) endif() -if(NOT CMAKE_CXX_COMPILER) - execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT} -find clang++ - OUTPUT_VARIABLE CMAKE_CXX_COMPILER - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) - message(STATUS "Using CXX compiler: ${CMAKE_CXX_COMPILER}") +if(DEFINED CMAKE_CXX_COMPILER) + # Environment variables are always preserved. + set(ENV{_CMAKE_CXX_COMPILER} "${CMAKE_CXX_COMPILER}") +elseif(DEFINED ENV{_CMAKE_CXX_COMPILER}) + set(CMAKE_CXX_COMPILER "$ENV{_CMAKE_CXX_COMPILER}") +elseif(NOT DEFINED CMAKE_CXX_COMPILER) + execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find clang++ + OUTPUT_VARIABLE CMAKE_CXX_COMPILER + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) endif() # Find (Apple's) libtool. -execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT} -find libtool - OUTPUT_VARIABLE BUILD_LIBTOOL - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) -message(STATUS "Using libtool: ${BUILD_LIBTOOL}") +if(DEFINED BUILD_LIBTOOL) + # Environment variables are always preserved. + set(ENV{_BUILD_LIBTOOL} "${BUILD_LIBTOOL}") +elseif(DEFINED ENV{_BUILD_LIBTOOL}) + set(BUILD_LIBTOOL "$ENV{_BUILD_LIBTOOL}") +elseif(NOT DEFINED BUILD_LIBTOOL) + execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find libtool + OUTPUT_VARIABLE BUILD_LIBTOOL + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) +endif() +# Find the toolchain's provided install_name_tool if none is found on the host +if(DEFINED CMAKE_INSTALL_NAME_TOOL) + # Environment variables are always preserved. + set(ENV{_CMAKE_INSTALL_NAME_TOOL} "${CMAKE_INSTALL_NAME_TOOL}") +elseif(DEFINED ENV{_CMAKE_INSTALL_NAME_TOOL}) + set(CMAKE_INSTALL_NAME_TOOL "$ENV{_CMAKE_INSTALL_NAME_TOOL}") +elseif(NOT DEFINED CMAKE_INSTALL_NAME_TOOL) + execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find install_name_tool + OUTPUT_VARIABLE CMAKE_INSTALL_NAME_TOOL_INT + ERROR_QUIET + OUTPUT_STRIP_TRAILING_WHITESPACE) + set(CMAKE_INSTALL_NAME_TOOL ${CMAKE_INSTALL_NAME_TOOL_INT} CACHE INTERNAL "") +endif() + # Configure libtool to be used instead of ar + ranlib to build static libraries. # This is required on Xcode 7+, but should also work on previous versions of # Xcode. -set(CMAKE_C_CREATE_STATIC_LIBRARY - "${BUILD_LIBTOOL} -static -o ") -set(CMAKE_CXX_CREATE_STATIC_LIBRARY - "${BUILD_LIBTOOL} -static -o ") -# Find the toolchain's provided install_name_tool if none is found on the host -if(NOT CMAKE_INSTALL_NAME_TOOL) - execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT} -find install_name_tool - OUTPUT_VARIABLE CMAKE_INSTALL_NAME_TOOL_INT - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) - set(CMAKE_INSTALL_NAME_TOOL ${CMAKE_INSTALL_NAME_TOOL_INT} CACHE STRING "" ${FORCE_CACHE}) -endif() -# Get the version of Darwin (OS X) of the host. -execute_process(COMMAND uname -r - OUTPUT_VARIABLE CMAKE_HOST_SYSTEM_VERSION - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) -if(SDK_NAME MATCHES "iphone") - set(CMAKE_SYSTEM_NAME iOS CACHE INTERNAL "" ${FORCE_CACHE}) -endif() +get_property(languages GLOBAL PROPERTY ENABLED_LANGUAGES) +foreach(lang ${languages}) + set(CMAKE_${lang}_CREATE_STATIC_LIBRARY "${BUILD_LIBTOOL} -static -o " CACHE INTERNAL "") +endforeach() + # CMake 3.14+ support building for iOS, watchOS and tvOS out of the box. if(MODERN_CMAKE) - if(SDK_NAME MATCHES "appletv") - set(CMAKE_SYSTEM_NAME tvOS CACHE INTERNAL "" ${FORCE_CACHE}) + if(SDK_NAME MATCHES "iphone") + set(CMAKE_SYSTEM_NAME iOS) + elseif(SDK_NAME MATCHES "macosx") + set(CMAKE_SYSTEM_NAME Darwin) + elseif(SDK_NAME MATCHES "appletv") + set(CMAKE_SYSTEM_NAME tvOS) elseif(SDK_NAME MATCHES "watch") - set(CMAKE_SYSTEM_NAME watchOS CACHE INTERNAL "" ${FORCE_CACHE}) + set(CMAKE_SYSTEM_NAME watchOS) endif() # Provide flags for a combined FAT library build on newer CMake versions if(PLATFORM_INT MATCHES ".*COMBINED") set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH "NO") - set(CMAKE_IOS_INSTALL_COMBINED YES CACHE INTERNAL "" ${FORCE_CACHE}) + set(CMAKE_IOS_INSTALL_COMBINED YES) message(STATUS "Will combine built (static) artifacts into FAT lib...") endif() -elseif(${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.10") - # Legacy code path prior to CMake 3.14 or fallback if no SDK_NAME specified - set(CMAKE_SYSTEM_NAME iOS CACHE INTERNAL "" ${FORCE_CACHE}) -else() - # Legacy code path prior to CMake 3.14 or fallback if no SDK_NAME specified - set(CMAKE_SYSTEM_NAME Darwin CACHE INTERNAL "" ${FORCE_CACHE}) +elseif(NOT DEFINED CMAKE_SYSTEM_NAME AND ${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.10") + # Legacy code path prior to CMake 3.14 or fallback if no CMAKE_SYSTEM_NAME specified + set(CMAKE_SYSTEM_NAME iOS) +elseif(NOT DEFINED CMAKE_SYSTEM_NAME) + # Legacy code path prior to CMake 3.14 or fallback if no CMAKE_SYSTEM_NAME specified + set(CMAKE_SYSTEM_NAME Darwin) endif() # Standard settings. set(CMAKE_SYSTEM_VERSION ${SDK_VERSION} CACHE INTERNAL "") set(UNIX TRUE CACHE BOOL "") set(APPLE TRUE CACHE BOOL "") -set(IOS TRUE CACHE BOOL "") +if(PLATFORM STREQUAL "MAC" OR PLATFORM STREQUAL "MAC_ARM64") + set(IOS FALSE CACHE BOOL "") + set(MACOS TRUE CACHE BOOL "") +elseif(PLATFORM STREQUAL "MAC_CATALYST" OR PLATFORM STREQUAL "MAC_CATALYST_ARM64") + set(IOS TRUE CACHE BOOL "") + set(MACOS TRUE CACHE BOOL "") +else() + set(IOS TRUE CACHE BOOL "") +endif() set(CMAKE_AR ar CACHE FILEPATH "" FORCE) set(CMAKE_RANLIB ranlib CACHE FILEPATH "" FORCE) set(CMAKE_STRIP strip CACHE FILEPATH "" FORCE) # Set the architectures for which to build. -set(CMAKE_OSX_ARCHITECTURES ${ARCHS} CACHE STRING "Build architecture for iOS") +set(CMAKE_OSX_ARCHITECTURES ${ARCHS} CACHE INTERNAL "") # Change the type of target generated for try_compile() so it'll work when cross-compiling, weak compiler checks -if(ENABLE_STRICT_TRY_COMPILE_INT) - message(STATUS "Using strict compiler checks (default in CMake).") -else() +if(NOT ENABLE_STRICT_TRY_COMPILE_INT) set(CMAKE_TRY_COMPILE_TARGET_TYPE STATIC_LIBRARY) endif() # All iOS/Darwin specific settings - some may be redundant. @@ -547,40 +687,45 @@ endif() # -m(ios/ios-simulator)-version-min instead. if(${CMAKE_VERSION} VERSION_LESS "3.11") if(PLATFORM_INT STREQUAL "OS" OR PLATFORM_INT STREQUAL "OS64") - if(XCODE_VERSION VERSION_LESS 7.0) + if(XCODE_VERSION_INT VERSION_LESS 7.0) set(SDK_NAME_VERSION_FLAGS - "-mios-version-min=${DEPLOYMENT_TARGET}") + "-mios-version-min=${DEPLOYMENT_TARGET}") else() # Xcode 7.0+ uses flags we can build directly from SDK_NAME. set(SDK_NAME_VERSION_FLAGS - "-m${SDK_NAME}-version-min=${DEPLOYMENT_TARGET}") + "-m${SDK_NAME}-version-min=${DEPLOYMENT_TARGET}") endif() elseif(PLATFORM_INT STREQUAL "TVOS") set(SDK_NAME_VERSION_FLAGS - "-mtvos-version-min=${DEPLOYMENT_TARGET}") + "-mtvos-version-min=${DEPLOYMENT_TARGET}") elseif(PLATFORM_INT STREQUAL "SIMULATOR_TVOS") set(SDK_NAME_VERSION_FLAGS - "-mtvos-simulator-version-min=${DEPLOYMENT_TARGET}") + "-mtvos-simulator-version-min=${DEPLOYMENT_TARGET}") elseif(PLATFORM_INT STREQUAL "WATCHOS") set(SDK_NAME_VERSION_FLAGS - "-mwatchos-version-min=${DEPLOYMENT_TARGET}") + "-mwatchos-version-min=${DEPLOYMENT_TARGET}") elseif(PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") set(SDK_NAME_VERSION_FLAGS - "-mwatchos-simulator-version-min=${DEPLOYMENT_TARGET}") + "-mwatchos-simulator-version-min=${DEPLOYMENT_TARGET}") + elseif(PLATFORM_INT STREQUAL "MAC") + set(SDK_NAME_VERSION_FLAGS + "-mmacosx-version-min=${DEPLOYMENT_TARGET}") else() # SIMULATOR or SIMULATOR64 both use -mios-simulator-version-min. set(SDK_NAME_VERSION_FLAGS - "-mios-simulator-version-min=${DEPLOYMENT_TARGET}") + "-mios-simulator-version-min=${DEPLOYMENT_TARGET}") endif() -else() - # Newer versions of CMake sets the version min flags correctly - set(CMAKE_OSX_DEPLOYMENT_TARGET ${DEPLOYMENT_TARGET} CACHE STRING - "Set CMake deployment target" ${FORCE_CACHE}) +elseif(NOT PLATFORM_INT STREQUAL "MAC_CATALYST") + # Newer versions of CMake sets the version min flags correctly, skip this for Mac Catalyst targets + set(CMAKE_OSX_DEPLOYMENT_TARGET ${DEPLOYMENT_TARGET}) endif() if(DEFINED APPLE_TARGET_TRIPLE_INT) - set(APPLE_TARGET_TRIPLE ${APPLE_TARGET_TRIPLE_INT} CACHE STRING - "Autoconf target triple compatible variable" ${FORCE_CACHE}) + set(APPLE_TARGET_TRIPLE ${APPLE_TARGET_TRIPLE_INT} CACHE INTERNAL "") +endif() + +if(PLATFORM_INT STREQUAL "MAC_CATALYST") + set(C_TARGET_FLAGS "-target ${APPLE_TARGET_TRIPLE_INT} -isystem ${CMAKE_OSX_SYSROOT_INT}/System/iOSSupport/usr/include") endif() if(ENABLE_BITCODE_INT) @@ -601,84 +746,108 @@ else() endif() if(NOT ENABLE_VISIBILITY_INT) - set(VISIBILITY "-fvisibility=hidden") + foreach(lang ${languages}) + set(CMAKE_${lang}_VISIBILITY_PRESET "hidden" CACHE INTERNAL "") + endforeach() set(CMAKE_XCODE_ATTRIBUTE_GCC_SYMBOLS_PRIVATE_EXTERN "YES") + set(VISIBILITY "-fvisibility=hidden -fvisibility-inlines-hidden") else() - set(VISIBILITY "") + foreach(lang ${languages}) + set(CMAKE_${lang}_VISIBILITY_PRESET "default" CACHE INTERNAL "") + endforeach() set(CMAKE_XCODE_ATTRIBUTE_GCC_SYMBOLS_PRIVATE_EXTERN "NO") + set(VISIBILITY "-fvisibility=default") endif() -if(NOT IOS_TOOLCHAIN_HAS_RUN) - #Check if Xcode generator is used, since that will handle these flags automagically - if(USED_CMAKE_GENERATOR MATCHES "Xcode") - message(STATUS "Not setting any manual command-line buildflags, since Xcode is selected as generator.") - else() - set(CMAKE_C_FLAGS - "${SDK_NAME_VERSION_FLAGS} ${BITCODE} -fobjc-abi-version=2 ${FOBJC_ARC} ${CMAKE_C_FLAGS}") - # Hidden visibilty is required for C++ on iOS. - set(CMAKE_CXX_FLAGS - "${SDK_NAME_VERSION_FLAGS} ${BITCODE} ${VISIBILITY} -fvisibility-inlines-hidden -fobjc-abi-version=2 ${FOBJC_ARC} ${CMAKE_CXX_FLAGS}") - set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS} -O0 -g ${CMAKE_CXX_FLAGS_DEBUG}") - set(CMAKE_CXX_FLAGS_MINSIZEREL "${CMAKE_CXX_FLAGS} -DNDEBUG -Os -ffast-math ${CMAKE_CXX_FLAGS_MINSIZEREL}") - set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS} -DNDEBUG -O2 -g -ffast-math ${CMAKE_CXX_FLAGS_RELWITHDEBINFO}") - set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS} -DNDEBUG -O3 -ffast-math ${CMAKE_CXX_FLAGS_RELEASE}") - set(CMAKE_C_LINK_FLAGS "${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_C_LINK_FLAGS}") - set(CMAKE_CXX_LINK_FLAGS "${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_CXX_LINK_FLAGS}") - set(CMAKE_ASM_FLAGS "${CFLAGS} -x assembler-with-cpp -arch ${CMAKE_OSX_ARCHITECTURES}") - - # In order to ensure that the updated compiler flags are used in try_compile() - # tests, we have to forcibly set them in the CMake cache, not merely set them - # in the local scope. - set(VARS_TO_FORCE_IN_CACHE - CMAKE_C_FLAGS - CMAKE_CXX_FLAGS - CMAKE_CXX_FLAGS_DEBUG - CMAKE_CXX_FLAGS_RELWITHDEBINFO - CMAKE_CXX_FLAGS_MINSIZEREL - CMAKE_CXX_FLAGS_RELEASE - CMAKE_C_LINK_FLAGS - CMAKE_CXX_LINK_FLAGS) - foreach(VAR_TO_FORCE ${VARS_TO_FORCE_IN_CACHE}) - set(${VAR_TO_FORCE} "${${VAR_TO_FORCE}}" CACHE STRING "" ${FORCE_CACHE}) - endforeach() - endif() - - ## Print status messages to inform of the current state - message(STATUS "Configuring ${SDK_NAME} build for platform: ${PLATFORM_INT}, architecture(s): ${ARCHS}") - message(STATUS "Using SDK: ${CMAKE_OSX_SYSROOT_INT}") - if(DEFINED APPLE_TARGET_TRIPLE) - message(STATUS "Autoconf target triple: ${APPLE_TARGET_TRIPLE}") - endif() - message(STATUS "Using minimum deployment version: ${DEPLOYMENT_TARGET}" - " (SDK version: ${SDK_VERSION})") - if(MODERN_CMAKE) - message(STATUS "Merging integrated CMake 3.14+ iOS,tvOS,watchOS,macOS toolchain(s) with this toolchain!") - endif() - if(USED_CMAKE_GENERATOR MATCHES "Xcode") - message(STATUS "Using Xcode version: ${XCODE_VERSION}") - endif() - if(DEFINED SDK_NAME_VERSION_FLAGS) - message(STATUS "Using version flags: ${SDK_NAME_VERSION_FLAGS}") - endif() - message(STATUS "Using a data_ptr size of: ${CMAKE_CXX_SIZEOF_DATA_PTR}") - message(STATUS "Using install_name_tool: ${CMAKE_INSTALL_NAME_TOOL}") - if(ENABLE_BITCODE_INT) - message(STATUS "Enabling bitcode support.") - else() - message(STATUS "Disabling bitcode support.") - endif() - - if(ENABLE_ARC_INT) - message(STATUS "Enabling ARC support.") - else() - message(STATUS "Disabling ARC support.") - endif() - - if(NOT ENABLE_VISIBILITY_INT) - message(STATUS "Hiding symbols (-fvisibility=hidden).") - endif() +#Check if Xcode generator is used, since that will handle these flags automagically +if(CMAKE_GENERATOR MATCHES "Xcode") + message(STATUS "Not setting any manual command-line buildflags, since Xcode is selected as generator.") +else() + # Hidden visibility is required for C++ on iOS. + set(CMAKE_C_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} ${BITCODE} -fobjc-abi-version=2 ${FOBJC_ARC} ${CMAKE_C_FLAGS}") + set(CMAKE_CXX_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} ${BITCODE} ${VISIBILITY} -fobjc-abi-version=2 ${FOBJC_ARC} ${CMAKE_CXX_FLAGS}") + set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS} -O0 -g ${CMAKE_CXX_FLAGS_DEBUG}") + set(CMAKE_CXX_FLAGS_MINSIZEREL "${CMAKE_CXX_FLAGS} -DNDEBUG -Os -ffast-math ${CMAKE_CXX_FLAGS_MINSIZEREL}") + set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS} -DNDEBUG -O2 -g -ffast-math ${CMAKE_CXX_FLAGS_RELWITHDEBINFO}") + set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS} -DNDEBUG -O3 -ffast-math ${CMAKE_CXX_FLAGS_RELEASE}") + set(CMAKE_C_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_C_LINK_FLAGS}") + set(CMAKE_CXX_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_CXX_LINK_FLAGS}") + set(CMAKE_ASM_FLAGS "${CMAKE_C_FLAGS} -x assembler-with-cpp -arch ${CMAKE_OSX_ARCHITECTURES}") endif() +## Print status messages to inform of the current state +message(STATUS "Configuring ${SDK_NAME} build for platform: ${PLATFORM_INT}, architecture(s): ${ARCHS}") +message(STATUS "Using SDK: ${CMAKE_OSX_SYSROOT_INT}") +message(STATUS "Using C compiler: ${CMAKE_C_COMPILER}") +message(STATUS "Using CXX compiler: ${CMAKE_CXX_COMPILER}") +message(STATUS "Using libtool: ${BUILD_LIBTOOL}") +message(STATUS "Using install name tool: ${CMAKE_INSTALL_NAME_TOOL}") +if(DEFINED APPLE_TARGET_TRIPLE) + message(STATUS "Autoconf target triple: ${APPLE_TARGET_TRIPLE}") +endif() +message(STATUS "Using minimum deployment version: ${DEPLOYMENT_TARGET}" + " (SDK version: ${SDK_VERSION})") +if(MODERN_CMAKE) + message(STATUS "Merging integrated CMake 3.14+ iOS,tvOS,watchOS,macOS toolchain(s) with this toolchain!") +endif() +if(CMAKE_GENERATOR MATCHES "Xcode") + message(STATUS "Using Xcode version: ${XCODE_VERSION_INT}") +endif() +message(STATUS "CMake version: ${CMAKE_VERSION}") +if(DEFINED SDK_NAME_VERSION_FLAGS) + message(STATUS "Using version flags: ${SDK_NAME_VERSION_FLAGS}") +endif() +message(STATUS "Using a data_ptr size of: ${CMAKE_CXX_SIZEOF_DATA_PTR}") +if(ENABLE_BITCODE_INT) + message(STATUS "Bitcode: Enabled") +else() + message(STATUS "Bitcode: Disabled") +endif() + +if(ENABLE_ARC_INT) + message(STATUS "ARC: Enabled") +else() + message(STATUS "ARC: Disabled") +endif() + +if(ENABLE_VISIBILITY_INT) + message(STATUS "Hiding symbols: Disabled") +else() + message(STATUS "Hiding symbols: Enabled") +endif() + +# Set global properties +set_property(GLOBAL PROPERTY PLATFORM "${PLATFORM}") +set_property(GLOBAL PROPERTY APPLE_TARGET_TRIPLE "${APPLE_TARGET_TRIPLE_INT}") +set_property(GLOBAL PROPERTY SDK_VERSION "${SDK_VERSION}") +set_property(GLOBAL PROPERTY XCODE_VERSION "${XCODE_VERSION_INT}") +set_property(GLOBAL PROPERTY OSX_ARCHITECTURES "${CMAKE_OSX_ARCHITECTURES}") + +# Export configurable variables for the try_compile() command. +set(CMAKE_TRY_COMPILE_PLATFORM_VARIABLES + PLATFORM + XCODE_VERSION_INT + SDK_VERSION + DEPLOYMENT_TARGET + CMAKE_DEVELOPER_ROOT + CMAKE_OSX_SYSROOT_INT + ENABLE_BITCODE + ENABLE_ARC + CMAKE_C_COMPILER + CMAKE_CXX_COMPILER + BUILD_LIBTOOL + CMAKE_INSTALL_NAME_TOOL + CMAKE_C_FLAGS + CMAKE_CXX_FLAGS + CMAKE_CXX_FLAGS_DEBUG + CMAKE_CXX_FLAGS_MINSIZEREL + CMAKE_CXX_FLAGS_RELWITHDEBINFO + CMAKE_CXX_FLAGS_RELEASE + CMAKE_C_LINK_FLAGS + CMAKE_CXX_LINK_FLAGS + CMAKE_ASM_FLAGS + ) + set(CMAKE_PLATFORM_HAS_INSTALLNAME 1) set(CMAKE_SHARED_LINKER_FLAGS "-rpath @executable_path/Frameworks -rpath @loader_path/Frameworks") set(CMAKE_SHARED_LIBRARY_CREATE_C_FLAGS "-dynamiclib -Wl,-headerpad_max_install_names") @@ -688,31 +857,42 @@ set(CMAKE_SHARED_MODULE_LOADER_CXX_FLAG "-Wl,-bundle_loader,") set(CMAKE_FIND_LIBRARY_SUFFIXES ".tbd" ".dylib" ".so" ".a") set(CMAKE_SHARED_LIBRARY_SONAME_C_FLAG "-install_name") -# Set the find root to the iOS developer roots and to user defined paths. -set(CMAKE_FIND_ROOT_PATH ${CMAKE_OSX_SYSROOT_INT} ${CMAKE_PREFIX_PATH} CACHE STRING "Root path that will be prepended - to all search paths") +# Set the find root to the SDK developer roots. +# Note: CMAKE_FIND_ROOT_PATH is only useful when cross-compiling. Thus, do not set on macOS builds. +if(NOT PLATFORM_INT STREQUAL "MAC" AND NOT PLATFORM_INT STREQUAL "MAC_ARM64") + list(APPEND CMAKE_FIND_ROOT_PATH "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") + set(CMAKE_IGNORE_PATH "/System/Library/Frameworks;/usr/local/lib" CACHE INTERNAL "") +endif() + # Default to searching for frameworks first. set(CMAKE_FIND_FRAMEWORK FIRST) -# Set up the default search directories for frameworks. -set(CMAKE_FRAMEWORK_PATH - ${CMAKE_DEVELOPER_ROOT}/Library/PrivateFrameworks - ${CMAKE_OSX_SYSROOT_INT}/System/Library/Frameworks - ${CMAKE_FRAMEWORK_PATH} CACHE STRING "Frameworks search paths" ${FORCE_CACHE}) -set(IOS_TOOLCHAIN_HAS_RUN TRUE CACHE BOOL "Has the CMake toolchain run already?" ${FORCE_CACHE}) +# Set up the default search directories for frameworks. +if(PLATFORM_INT MATCHES "MAC_CATALYST.*") + set(CMAKE_FRAMEWORK_PATH + ${CMAKE_DEVELOPER_ROOT}/Library/PrivateFrameworks + ${CMAKE_OSX_SYSROOT_INT}/System/Library/Frameworks + ${CMAKE_OSX_SYSROOT_INT}/System/iOSSupport/System/Library/Frameworks + ${CMAKE_FRAMEWORK_PATH} CACHE INTERNAL "") +else() + set(CMAKE_FRAMEWORK_PATH + ${CMAKE_DEVELOPER_ROOT}/Library/PrivateFrameworks + ${CMAKE_OSX_SYSROOT_INT}/System/Library/Frameworks + ${CMAKE_FRAMEWORK_PATH} CACHE INTERNAL "") +endif() # By default, search both the specified iOS SDK and the remainder of the host filesystem. if(NOT CMAKE_FIND_ROOT_PATH_MODE_PROGRAM) - set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH CACHE STRING "" ${FORCE_CACHE}) + set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH CACHE INTERNAL "") endif() if(NOT CMAKE_FIND_ROOT_PATH_MODE_LIBRARY) - set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH CACHE STRING "" ${FORCE_CACHE}) + set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH CACHE INTERNAL "") endif() if(NOT CMAKE_FIND_ROOT_PATH_MODE_INCLUDE) - set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH CACHE STRING "" ${FORCE_CACHE}) + set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH CACHE INTERNAL "") endif() if(NOT CMAKE_FIND_ROOT_PATH_MODE_PACKAGE) - set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE BOTH CACHE STRING "" ${FORCE_CACHE}) + set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE BOTH CACHE INTERNAL "") endif() # @@ -723,11 +903,9 @@ endif() macro(set_xcode_property TARGET XCODE_PROPERTY XCODE_VALUE XCODE_RELVERSION) set(XCODE_RELVERSION_I "${XCODE_RELVERSION}") if(XCODE_RELVERSION_I STREQUAL "All") - set_property(TARGET ${TARGET} PROPERTY - XCODE_ATTRIBUTE_${XCODE_PROPERTY} "${XCODE_VALUE}") + set_property(TARGET ${TARGET} PROPERTY XCODE_ATTRIBUTE_${XCODE_PROPERTY} "${XCODE_VALUE}") else() - set_property(TARGET ${TARGET} PROPERTY - XCODE_ATTRIBUTE_${XCODE_PROPERTY}[variant=${XCODE_RELVERSION_I}] "${XCODE_VALUE}") + set_property(TARGET ${TARGET} PROPERTY XCODE_ATTRIBUTE_${XCODE_PROPERTY}[variant=${XCODE_RELVERSION_I}] "${XCODE_VALUE}") endif() endmacro(set_xcode_property) @@ -738,8 +916,9 @@ macro(find_host_package) set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE NEVER) set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE NEVER) set(IOS FALSE) + set(_TOOLCHAIN_IOS ${IOS}) find_package(${ARGN}) - set(IOS TRUE) + set(IOS ${_TOOLCHAIN_IOS}) set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH) set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH) set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH) diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt index 76f4cc4a5..35d7d3d38 100644 --- a/lib/CMakeLists.txt +++ b/lib/CMakeLists.txt @@ -477,12 +477,14 @@ vcmi_set_output_dir(vcmi "") enable_pch(vcmi) # We want to deploy assets into build directory for easier debugging without install -add_custom_command(TARGET vcmi POST_BUILD - COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config - COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/config ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/Mods ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods -) +if(NOT APPLE_IOS) + add_custom_command(TARGET vcmi POST_BUILD + COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config + COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods + COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/config ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config + COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/Mods ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods + ) +endif() # Update version before vcmi compiling if(TARGET update_version) diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index e0bf6a36e..9d5c7bce6 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -33,6 +33,7 @@ if(CMAKE_SYSTEM_NAME MATCHES FreeBSD) set(server_LIBS execinfo ${server_LIBS}) elseif(APPLE_IOS) set(server_LIBS ${server_LIBS} "-framework UIKit") + add_dependencies(vcmiserver BattleAI StupidAI VCAI) endif() target_link_libraries(vcmiserver PRIVATE ${server_LIBS} minizip::minizip) @@ -47,7 +48,10 @@ if(WIN32) PROJECT_LABEL "VCMI_server" ) elseif(APPLE_IOS) - set_target_properties(vcmiserver PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in") + set_target_properties(vcmiserver PROPERTIES + MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in" + SKIP_BUILD_RPATH 1 + ) # TODO: move to a common dir / add macro? target_sources(vcmiserver PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") @@ -59,6 +63,7 @@ enable_pch(vcmiserver) if(APPLE_IOS) add_custom_command(TARGET vcmiserver POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" + COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true ) else() install(TARGETS vcmiserver DESTINATION ${BIN_DIR}) From 6e41e3154ca731df72a8e5e274e60c6b1e3ba15d Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 12 Mar 2021 14:01:00 +0300 Subject: [PATCH 022/131] fix running on device from Xcode proper codesigning --- CMakeLists.txt | 1 + apple_codesign.sh | 10 ++++++++++ client/CMakeLists.txt | 2 ++ configure_ios.sh | 6 ++++-- server/CMakeLists.txt | 2 ++ 5 files changed, 19 insertions(+), 2 deletions(-) create mode 100755 apple_codesign.sh diff --git a/CMakeLists.txt b/CMakeLists.txt index 306419f18..7f87f9daf 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -155,6 +155,7 @@ set(CMAKE_MAP_IMPORTED_CONFIG_RELEASE Release RelWithDebInfo MinSizeRel "") if(APPLE_IOS) set(CMAKE_MACOSX_RPATH 1) + set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED NO) set(SYSTEM_LIBS ${SYSTEM_LIBS} iconv) # boost.locale endif(APPLE_IOS) diff --git a/apple_codesign.sh b/apple_codesign.sh new file mode 100755 index 000000000..7dd8a64a3 --- /dev/null +++ b/apple_codesign.sh @@ -0,0 +1,10 @@ +#!/usr/bin/env bash + +if [[ "$PLATFORM_NAME" != "iphoneos" ]]; then + exit 0 +fi + +echo 'codesign dylibs' +for lib in $(find "$CODESIGNING_FOLDER_PATH/Frameworks" -iname '*.dylib'); do + codesign --force --timestamp=none --sign "$EXPANDED_CODE_SIGN_IDENTITY" "$lib" +done diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 0b7390023..e57fad386 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -183,6 +183,7 @@ elseif(APPLE_IOS) set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in" SKIP_BUILD_RPATH 1 + XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES ) target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) @@ -211,6 +212,7 @@ if(APPLE_IOS) add_custom_command(TARGET vcmiclient POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true + COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() install(TARGETS vcmiclient DESTINATION ${BIN_DIR}) diff --git a/configure_ios.sh b/configure_ios.sh index f8f8049a6..e2168edd6 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -5,7 +5,7 @@ ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib srcDir="../vcmi" -/Users/Shared/xbmc-depends/x86_64-darwin19.6.0-native/bin/cmake "$srcDir" -G Xcode \ +cmake "$srcDir" -G Xcode \ -DBUNDLE_IDENTIFIER_PREFIX=com.kambala \ -Wno-dev \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ @@ -18,4 +18,6 @@ srcDir="../vcmi" -DSDL2_IMAGE_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_image-release-2.0.5 \ -DSDL2_MIXER_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_mixer-release-2.0.4 \ -DSDL2_TTF_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_ttf-release-2.0.15 \ - -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED=NO + -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY='Apple Development' \ + -DCMAKE_XCODE_ATTRIBUTE_DEVELOPMENT_TEAM='4XHN44TEVG' + # -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED=NO diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 9d5c7bce6..2218f9e46 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -51,6 +51,7 @@ elseif(APPLE_IOS) set_target_properties(vcmiserver PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in" SKIP_BUILD_RPATH 1 + XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES ) # TODO: move to a common dir / add macro? target_sources(vcmiserver PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) @@ -64,6 +65,7 @@ if(APPLE_IOS) add_custom_command(TARGET vcmiserver POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true + COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() install(TARGETS vcmiserver DESTINATION ${BIN_DIR}) From 75282366c00b013376d1c5f586c25898086eb5d8 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 13 Mar 2021 13:47:06 +0300 Subject: [PATCH 023/131] log messages with os_log --- lib/CConsoleHandler.cpp | 2 -- lib/CIOSUtils.h | 2 ++ lib/CIOSUtils.m | 2 ++ lib/logging/CLogger.cpp | 40 ++++++++++++++++++++++++++++++++++++++++ 4 files changed, 44 insertions(+), 2 deletions(-) diff --git a/lib/CConsoleHandler.cpp b/lib/CConsoleHandler.cpp index ebff37841..b5489b984 100644 --- a/lib/CConsoleHandler.cpp +++ b/lib/CConsoleHandler.cpp @@ -165,7 +165,6 @@ LONG WINAPI onUnhandledException(EXCEPTION_POINTERS* exception) void CConsoleHandler::setColor(EConsoleTextColor::EConsoleTextColor color) { -#ifndef VCMI_IOS TColor colorCode; switch(color) { @@ -205,7 +204,6 @@ void CConsoleHandler::setColor(EConsoleTextColor::EConsoleTextColor color) #else std::cout << colorCode; #endif -#endif } int CConsoleHandler::run() diff --git a/lib/CIOSUtils.h b/lib/CIOSUtils.h index 0e5ac20cc..682429747 100644 --- a/lib/CIOSUtils.h +++ b/lib/CIOSUtils.h @@ -13,3 +13,5 @@ extern const char *ios_cachesPath(); extern const char *ios_bundlePath(); extern const char *ios_frameworksPath(); + +extern const char *ios_bundleIdentifier(); diff --git a/lib/CIOSUtils.m b/lib/CIOSUtils.m index f3f765352..0621f1230 100644 --- a/lib/CIOSUtils.m +++ b/lib/CIOSUtils.m @@ -22,3 +22,5 @@ const char *ios_cachesPath() { return standardPath(NSCachesDirectory); } const char *ios_bundlePath() { return NSBundle.mainBundle.bundlePath.UTF8String; } const char *ios_frameworksPath() { return [NSBundle.mainBundle.bundlePath stringByAppendingPathComponent:@"Frameworks"].UTF8String; } // TODO: sharedFrameworksPath? + +const char *ios_bundleIdentifier() { return NSBundle.mainBundle.bundleIdentifier.UTF8String; } diff --git a/lib/logging/CLogger.cpp b/lib/logging/CLogger.cpp index fc6e57cfe..651cf5d91 100644 --- a/lib/logging/CLogger.cpp +++ b/lib/logging/CLogger.cpp @@ -30,6 +30,11 @@ namespace ELogLevel return ANDROID_LOG_UNKNOWN; } } +#elif defined(VCMI_IOS) +extern "C" { +#import "../CIOSUtils.h" +#include +} #endif namespace vstd @@ -353,6 +358,41 @@ void CLogConsoleTarget::write(const LogRecord & record) #ifdef VCMI_ANDROID __android_log_write(ELogLevel::toAndroid(record.level), ("VCMI-" + record.domain.getName()).c_str(), message.c_str()); +#elif defined(VCMI_IOS) + os_log_type_t type; + switch (record.level) + { + case ELogLevel::TRACE: + type = OS_LOG_TYPE_DEBUG; + break; + case ELogLevel::DEBUG: + type = OS_LOG_TYPE_DEFAULT; + break; + case ELogLevel::INFO: + type = OS_LOG_TYPE_INFO; + break; + case ELogLevel::WARN: + type = OS_LOG_TYPE_ERROR; + break; + case ELogLevel::ERROR: + type = OS_LOG_TYPE_FAULT; + break; + default: + return; + } + + os_log_t currentLog; + static std::unordered_map logs; + const auto& domainName = record.domain.getName(); + auto logIt = logs.find(domainName); + if (logIt != logs.end()) + currentLog = logIt->second; + else + { + currentLog = os_log_create(ios_bundleIdentifier(), domainName.c_str()); + logs.insert({domainName, currentLog}); + } + os_log_with_type(currentLog, type, "%s", message.c_str()); #else const bool printToStdErr = record.level >= ELogLevel::WARN; From d2b1cc00e8010c418f3b5324813c14f26405997c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 13 Mar 2021 14:08:13 +0300 Subject: [PATCH 024/131] enable same adventure map tweaks as on android --- client/windows/CAdvmapInterface.cpp | 25 ++++++++++--------------- 1 file changed, 10 insertions(+), 15 deletions(-) diff --git a/client/windows/CAdvmapInterface.cpp b/client/windows/CAdvmapInterface.cpp index 2c5a9dfb7..7de5234f3 100644 --- a/client/windows/CAdvmapInterface.cpp +++ b/client/windows/CAdvmapInterface.cpp @@ -125,8 +125,7 @@ void CTerrainRect::clickLeft(tribool down, bool previousState) if(indeterminate(down)) return; -#ifdef VCMI_ANDROID - // todo ios +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) if(adventureInt->swipeEnabled) { if(handleSwipeStateChange((bool)down == true)) @@ -139,7 +138,7 @@ void CTerrainRect::clickLeft(tribool down, bool previousState) #endif if(down == false) return; -#ifdef VCMI_ANDROID +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) } #endif int3 mp = whichTileIsIt(); @@ -151,8 +150,7 @@ void CTerrainRect::clickLeft(tribool down, bool previousState) void CTerrainRect::clickRight(tribool down, bool previousState) { -#ifdef VCMI_ANDROID - // todo ios +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) if(adventureInt->swipeEnabled && isSwiping) return; #endif @@ -181,12 +179,11 @@ void CTerrainRect::mouseMoved(const SDL_MouseMotionEvent & sEvent) void CTerrainRect::handleSwipeMove(const SDL_MouseMotionEvent & sEvent) { -#ifdef VCMI_ANDROID - // todo ios - if(sEvent.state == 0) // any "button" is enough on android -#else //!VCMI_ANDROID +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) + if(sEvent.state == 0) // any "button" is enough on mobile +#else if((sEvent.state & SDL_BUTTON_MMASK) == 0) // swipe only works with middle mouse on other platforms -#endif //!VCMI_ANDROID +#endif { return; } @@ -1052,10 +1049,9 @@ void CAdvMapInt::show(SDL_Surface * to) { handleSwipeUpdate(); } -#ifdef VCMI_ANDROID // on android, map-moving mode is exclusive (TODO technically it might work with both enabled; to be checked) - // todo ios +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) // on mobile, map-moving mode is exclusive (TODO technically it might work with both enabled; to be checked) else -#endif // VCMI_ANDROID +#endif { handleMapScrollingUpdate(); } @@ -1455,8 +1451,7 @@ void CAdvMapInt::select(const CArmedInstance *sel, bool centerView) void CAdvMapInt::mouseMoved( const SDL_MouseMotionEvent & sEvent ) { -#ifdef VCMI_ANDROID - // todo ios +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) if(swipeEnabled) return; #endif From dde9a5d5d2a7cf9221b6e53891651fd7472214d8 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 13 Mar 2021 14:13:16 +0300 Subject: [PATCH 025/131] todo updates --- client/CServerHandler.cpp | 8 +++----- lib/serializer/Connection.cpp | 3 ++- server/CVCMIServer.cpp | 4 +--- 3 files changed, 6 insertions(+), 9 deletions(-) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index 93d44cefa..f4904c26c 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -23,9 +23,7 @@ #ifdef VCMI_ANDROID #include "../lib/CAndroidVMHelper.h" -#elif defined(VCMI_IOS) -//TODO -#else +#elif !defined(VCMI_IOS) #include "../lib/Interprocess.h" #endif #include "../lib/CConfigHandler.h" @@ -184,7 +182,7 @@ void CServerHandler::startLocalServerAndConnect() envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true); } #elif defined(VCMI_IOS) - // TODO + // todo ios #else threadRunLocalServer = std::make_shared(&CServerHandler::threadRunServer, this); //runs server executable; #endif @@ -202,7 +200,7 @@ void CServerHandler::startLocalServerAndConnect() logNetwork->info("waiting for server finished..."); androidTestServerReadyFlag = false; #elif defined(VCMI_IOS) - //TODO + // todo ios #else if(shm) shm->sr->waitTillReady(); diff --git a/lib/serializer/Connection.cpp b/lib/serializer/Connection.cpp index 30bc4e83b..cd98406b4 100644 --- a/lib/serializer/Connection.cpp +++ b/lib/serializer/Connection.cpp @@ -71,7 +71,8 @@ CConnection::CConnection(std::string host, ui16 port, std::string Name, std::str boost::system::error_code error = asio::error::host_not_found; socket = std::make_shared(*io_service); tcp::resolver resolver(*io_service); - tcp::resolver::iterator end, pom, endpoint_iterator = resolver.resolve(tcp::resolver::query(host, std::to_string(port)),error); + // todo ios: is new param really needed? + tcp::resolver::iterator end, pom, endpoint_iterator = resolver.resolve(tcp::resolver::query(host, std::to_string(port), resolver_query_base::numeric_service), error); if(error) { logNetwork->error("Problem with resolving: \n%s", error.message()); diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index aa6f5ed82..142bac68c 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -29,9 +29,7 @@ #include "../lib/rmg/CMapGenOptions.h" #ifdef VCMI_ANDROID #include "lib/CAndroidVMHelper.h" -#elif defined(VCMI_IOS) -// todo ios -#else +#elif !defined(VCMI_IOS) #include "../lib/Interprocess.h" #endif #include "../lib/VCMI_Lib.h" From 13dd451ff55394f5fa93c4358cfc1cc65ac38caf Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 13 Mar 2021 16:53:31 +0300 Subject: [PATCH 026/131] add simple app icons --- client/CMakeLists.txt | 4 + .../AppIcon.appiconset/Contents.json | 121 ++++++++++++++++++ .../AppIcon.appiconset/Icon-App-20x20@1x.png | Bin 0 -> 517 bytes .../AppIcon.appiconset/Icon-App-20x20@2x.png | Bin 0 -> 811 bytes .../AppIcon.appiconset/Icon-App-20x20@3x.png | Bin 0 -> 1132 bytes .../AppIcon.appiconset/Icon-App-29x29@1x.png | Bin 0 -> 636 bytes .../AppIcon.appiconset/Icon-App-29x29@2x.png | Bin 0 -> 1101 bytes .../AppIcon.appiconset/Icon-App-29x29@3x.png | Bin 0 -> 1600 bytes .../AppIcon.appiconset/Icon-App-40x40@1x.png | Bin 0 -> 811 bytes .../AppIcon.appiconset/Icon-App-40x40@2x.png | Bin 0 -> 1450 bytes .../AppIcon.appiconset/Icon-App-40x40@3x.png | Bin 0 -> 2234 bytes .../AppIcon.appiconset/Icon-App-60x60@2x.png | Bin 0 -> 2234 bytes .../AppIcon.appiconset/Icon-App-60x60@3x.png | Bin 0 -> 3679 bytes .../AppIcon.appiconset/Icon-App-76x76@1x.png | Bin 0 -> 1396 bytes .../AppIcon.appiconset/Icon-App-76x76@2x.png | Bin 0 -> 3017 bytes .../Icon-App-83.5x83.5@2x.png | Bin 0 -> 3325 bytes client/ios/Images.xcassets/Contents.json | 6 + server/CMakeLists.txt | 4 + .../AppIcon.appiconset/Contents.json | 121 ++++++++++++++++++ .../AppIcon.appiconset/Icon-App-20x20@1x.png | Bin 0 -> 513 bytes .../AppIcon.appiconset/Icon-App-20x20@2x.png | Bin 0 -> 798 bytes .../AppIcon.appiconset/Icon-App-20x20@3x.png | Bin 0 -> 1128 bytes .../AppIcon.appiconset/Icon-App-29x29@1x.png | Bin 0 -> 634 bytes .../AppIcon.appiconset/Icon-App-29x29@2x.png | Bin 0 -> 1088 bytes .../AppIcon.appiconset/Icon-App-29x29@3x.png | Bin 0 -> 1589 bytes .../AppIcon.appiconset/Icon-App-40x40@1x.png | Bin 0 -> 798 bytes .../AppIcon.appiconset/Icon-App-40x40@2x.png | Bin 0 -> 1434 bytes .../AppIcon.appiconset/Icon-App-40x40@3x.png | Bin 0 -> 2235 bytes .../AppIcon.appiconset/Icon-App-60x60@2x.png | Bin 0 -> 2235 bytes .../AppIcon.appiconset/Icon-App-60x60@3x.png | Bin 0 -> 3758 bytes .../AppIcon.appiconset/Icon-App-76x76@1x.png | Bin 0 -> 1393 bytes .../AppIcon.appiconset/Icon-App-76x76@2x.png | Bin 0 -> 3053 bytes .../Icon-App-83.5x83.5@2x.png | Bin 0 -> 3401 bytes server/ios/Images.xcassets/Contents.json | 6 + 34 files changed, 262 insertions(+) create mode 100755 client/ios/Images.xcassets/AppIcon.appiconset/Contents.json create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png create mode 100644 client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png create mode 100644 client/ios/Images.xcassets/Contents.json create mode 100755 server/ios/Images.xcassets/AppIcon.appiconset/Contents.json create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png create mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png create mode 100644 server/ios/Images.xcassets/Contents.json diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index e57fad386..ee120af8c 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -184,10 +184,14 @@ elseif(APPLE_IOS) MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in" SKIP_BUILD_RPATH 1 XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES + XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon ) target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") + + target_sources(vcmiclient PRIVATE ios/Images.xcassets) + set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") endif() target_link_libraries(vcmiclient PRIVATE diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Contents.json b/client/ios/Images.xcassets/AppIcon.appiconset/Contents.json new file mode 100755 index 000000000..8122b0a0c --- /dev/null +++ b/client/ios/Images.xcassets/AppIcon.appiconset/Contents.json @@ -0,0 +1,121 @@ +{ + "images" : [ + { + "filename" : "Icon-App-20x20@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-20x20@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-29x29@1x.png", + "idiom" : "iphone", + "scale" : "1x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-40x40@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-40x40@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-60x60@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "60x60" + }, + { + "filename" : "Icon-App-60x60@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "60x60" + }, + { + "filename" : "Icon-App-20x20@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-20x20@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-29x29@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-40x40@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-40x40@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-76x76@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "76x76" + }, + { + "filename" : "Icon-App-76x76@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "76x76" + }, + { + "filename" : "Icon-App-83.5x83.5@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "83.5x83.5" + }, + { + "idiom" : "ios-marketing", + "scale" : "1x", + "size" : "1024x1024" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..cf9b70eb3ab38e6f413d8c1dd5b888fa43fcf971 GIT binary patch literal 517 zcmV+g0{Z=lP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0PaadK~#90b&$wEol=e=!-(Z{T`Uy6NO?uCn;jUa|Y-;wZ+c;sfd`5@=-N|CI;)r0J=>DcYj>DK-< zGOBdxHuDsIV5}6&tY5X7BnE>>U$-l3Q!)nsd9vGZJW=@#0Ow#@e>2&b00000NkvXX Hu0mjfn(^m$ literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..d4ff894857686b080cf2dcf19a5999fa56326a2a GIT binary patch literal 811 zcmV+`1JwM9P)uk0002eX+uL$Nkc;* zP;zf(X>4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0u)I^K~#90)sjDGQ&AMgzjN=4iHTUX5F@dOAlCZdwpItN1*xE*Xp4iBAgGg~ z2o5?rxrm5Ea1fn@j-sLUfN|1I2R@0w}*M$F@nKKi(?Y0kwKr zbU=3kKpoFTT*mMQUQR=^S5oh*uuMOn;e>+$moT^*H*5y>odyElqVjI zqw*N}o$_Io5mAs*bMG~I(xm}`c;XSqI&~-B5FFWiRPjLL2uxiXVW(i z5GRv`fT+y$QYU)o@P1f91g(%46w}xpTjH9|E61LupMPTNt$lh!+gRq^R3?{pynz#W zD+)2H|JCwMJ0_E6cjViO%uuK;pKa&}&$pQ>{RUYX&k&;ELW4qsS$93V{?>o25;?Pv z8P$4pb=`_Jpi$#PdR-{uFX{Ja)Wb_fCvi?pts}2ozF9L$+SkkU$=BMkPPl!x){~0@ zbGOzQTu-GD@pFEVu*xKA4Ay`KM;@sFRKfOxK99tY?)J;!j}u)=<^(}0-x_b)xM%*& pum-8?5fD0tb%yze|MAa*KLM&p1p%)r2`2ym002ovPDHLkV1lptcUk}d literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..c5aa51fca527896abd19ae0844532eaa350ed040 GIT binary patch literal 1132 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 literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..c9d55a80a3fd303a6a089e77df9682e0cfb3005e GIT binary patch literal 1450 zcmV;b1y%ZqP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$1d~ZbK~#90?U-9^R8U$znil9cnDUXGmfiHF6 z{m!w<3mCM(B;5B^xLKpe?>pS$@PP>Tx|zE+6Dgb#SpxtnmDlD% zL?8x`wDn4e&G5t92+6RnBu|^8k&)v%rF2b z7s}c{4P`}f&(;7y(cZ6OZOm=kIfn`~d(tiW4gic4KY6xPOx?k^IxO^C67fpEs{Q!R zog|K+cZgThBNT)eVD(j5Id+%?0vgSm>8+P7C9Z{FNRFIIj}XvlBTnpW{dOS{Fha}? zReX7F1_YwHllVR3d!1-&5&*DS^RZ#suram++^s;v{G!JB1q0Opz~XS#*T%D|R`iQY zh5&`L?yvl8F_et!TH>>#2-VETwOPCgUlv<az%D%(XOLEZGL+TZKVFG!KZInt?5%nFLHJ|vZ|V+O}oQ*xh|4I zxK$6;Ebl*C+ePa1#y!pb?i)69q?)69f3XjZn*fwg>VxBZPr(kzpYX$>3l4`CJ({ed zzX>dvG6OY0i`UbE2JSs~R%|F8015+u8W(#Ni8l!`@xIWB7Jzs~2bKRoz|Pv;(C9P3 z4DjCvy8bQzs1O?IxRWF;$X-sIfC6b)0H7ND@#8riI4ax$@Dj(PMj@ z*q(D{`fzpp{OM!LQ)9BLNb>T#Sk9QAzaLQb$|xM5=UI;|dCwo{muJeyhvyc=9LG48 zOT>SfeR4?CxK5_VhjlR8!Z(FJQ}(zO_twM@*1^oTv}&bqul9)sC|Y0Od1i&%zXWK1 zzQ7P#WB!;<03Sx<)%L0W^C=4oyEh+3;vy1Yqxt|1AA6n~0R^DY9c}(0`c#4CiCnBE zRY@){_b(vdy==K>0G8B~Jo)~Lv|HWn%|9z@PA@I%HFS^{E}0hK)*MU^&mU{(G5GOr zL2lte6kBf|LAy$^0gz1m9nm$wPS}6HFK2)m;9Uv)3zrI}ntSBSUH||907*qoM6N<$ Ef((tK3IG5A literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..90981f0f9419513b849f5208d48e493e7b376422 GIT binary patch literal 2234 zcmV;r2u1gaP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$2ctF%Q+>3bATrAmwDat2$&MPZUGepLYb*vrU?McpOO_j%`QVI`!}Dq3?N^cu&BM^ z@T+I(3KT7Uf&vPT)NJz>q?sF;6Q`8^Hsb}W=0L-(6#tkP)7Yt4&Ay-cjh2;8DcgRy z;g(B61?3MtlfoD@yGZMSAEyGCvF}p2;rjlSz=T~_Nh(`c56YNRRo{4g&)SO8$8uKD zYCg8w09k*h)u}^6-vjXUhZowcmXCj#3KVWS+p3Ha#5VAGxXq@h>tlK4CrMIyaz2Wy z!i45EZmc9p>q(P}c0tN#?@cYC0p+i2WyrJa7+^HxJL!G^VikYegLgg=4J$xZ>k1FrolPJT$A{yA zAsGD>Zf*&5tlf^51pp|4*KcuLxkUO4Ck$@}0SP`m2B)@!)l)8Qd}?f4Jk*`Qnl>j5 zI}Zv0P<&NmM?pXwtP^>ZQK3i*m*+qL2^G%=ww`I9DN%jq*>tr5hT!q9;nG$J0OCLO z^HNnHc>f}^9_kWq%vZueMrRI_qubFwQ|}vJAMfiyP>Ta*-nSq%4WgiMOaI9bP^=R` zVZW|DJM1qwa4vQ8WupLO_rYau%N7{K)S*0H0|BM6wz7}{z<&wI_QXsvGGfmCa;O>r zC9r^-_L97$600PoF2 zTKMo3`ZoHE9DaB4fZl*p=4E2{hr+k-e4SlmgkW_q%$9$AAbc}pL84XZ0T_bu z<8ZYK$97isqW}eRu8sD>KMYN9}2BRsL3A?OlT2fB{SzfitgcnfPG1gJ8sD%Fa{L8Ivfx_D7~Ae6oTqtJhB* z8Q<`G3Ko{k0$(|_2pyrHuIEa4{AF~IX-VCmiy{lp5Ts& zS;e^i$hauYqgH3~jdd_oRaJ2vdU?)$3Nmn02?(Ympq(5F0-<>D1Yp6i z=}eiKqmhLZE?JXt?FTQO7h{Yup_&(_Kc+@Rny;z|gaZ~JeQ_EEA~ymia7_##qSuV^ zO5A7>Uo7tS3_jf@m11b)NZ`RAR{!gxT^klmuBDRxmTkFs>0+Bwd3w;J*HvlVY*-GU z^2Cjh`Yykg4wU@qqQ6_tl_;;Kv^_Iq9ivT!f|GxI_sESeu;bSUev&`Eh^dDsoi|I^(_juElU_o(t zF4O?L67;yCZOC^6uwVr6wYoe4z!%E#T(LYZ0G2N$FV@(Tt0X#CfIW4aL~6v*a16W2kd|yumisLVE3K7Born%!s?OO&bbsO^4o`C zH2~UALef(&2$$Wj4tkaD9MAB7ZxD*4;`2OHOTlkLwx}bei!D~ zv@BJshN#Q1yDz}X4K7o0E%GYBVnhB`29pLSYZNMHe{SiD&Z7duA#*R-@TcUhapwss zdL+sh$l19zz)6Non&1}UhzFuhH4MHHv@!o=!P0nuD05q`sK(UPq_H-Z`dk~3A3L4T zA52`lB`An_rgrwIr0@7D4YF*2dJRqk;O%>`punxTZ0o7^5?r1~d=~Rm`@pz>Awva+ znoTq-`OP?auxQFWnokZO>RlS;qLp~WT>?WeYq*Bi1v(Q5mAcn#r7=m0#kbSoew7+h zlGG5-EUxRDL_mKE^#46cRaNrH>dk98ZZsQ>@~07*qo IM6N<$f>28+ZvX%Q literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..90981f0f9419513b849f5208d48e493e7b376422 GIT binary patch literal 2234 zcmV;r2u1gaP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$2ctF%Q+>3bATrAmwDat2$&MPZUGepLYb*vrU?McpOO_j%`QVI`!}Dq3?N^cu&BM^ z@T+I(3KT7Uf&vPT)NJz>q?sF;6Q`8^Hsb}W=0L-(6#tkP)7Yt4&Ay-cjh2;8DcgRy z;g(B61?3MtlfoD@yGZMSAEyGCvF}p2;rjlSz=T~_Nh(`c56YNRRo{4g&)SO8$8uKD zYCg8w09k*h)u}^6-vjXUhZowcmXCj#3KVWS+p3Ha#5VAGxXq@h>tlK4CrMIyaz2Wy z!i45EZmc9p>q(P}c0tN#?@cYC0p+i2WyrJa7+^HxJL!G^VikYegLgg=4J$xZ>k1FrolPJT$A{yA zAsGD>Zf*&5tlf^51pp|4*KcuLxkUO4Ck$@}0SP`m2B)@!)l)8Qd}?f4Jk*`Qnl>j5 zI}Zv0P<&NmM?pXwtP^>ZQK3i*m*+qL2^G%=ww`I9DN%jq*>tr5hT!q9;nG$J0OCLO z^HNnHc>f}^9_kWq%vZueMrRI_qubFwQ|}vJAMfiyP>Ta*-nSq%4WgiMOaI9bP^=R` zVZW|DJM1qwa4vQ8WupLO_rYau%N7{K)S*0H0|BM6wz7}{z<&wI_QXsvGGfmCa;O>r zC9r^-_L97$600PoF2 zTKMo3`ZoHE9DaB4fZl*p=4E2{hr+k-e4SlmgkW_q%$9$AAbc}pL84XZ0T_bu z<8ZYK$97isqW}eRu8sD>KMYN9}2BRsL3A?OlT2fB{SzfitgcnfPG1gJ8sD%Fa{L8Ivfx_D7~Ae6oTqtJhB* z8Q<`G3Ko{k0$(|_2pyrHuIEa4{AF~IX-VCmiy{lp5Ts& zS;e^i$hauYqgH3~jdd_oRaJ2vdU?)$3Nmn02?(Ympq(5F0-<>D1Yp6i z=}eiKqmhLZE?JXt?FTQO7h{Yup_&(_Kc+@Rny;z|gaZ~JeQ_EEA~ymia7_##qSuV^ zO5A7>Uo7tS3_jf@m11b)NZ`RAR{!gxT^klmuBDRxmTkFs>0+Bwd3w;J*HvlVY*-GU z^2Cjh`Yykg4wU@qqQ6_tl_;;Kv^_Iq9ivT!f|GxI_sESeu;bSUev&`Eh^dDsoi|I^(_juElU_o(t zF4O?L67;yCZOC^6uwVr6wYoe4z!%E#T(LYZ0G2N$FV@(Tt0X#CfIW4aL~6v*a16W2kd|yumisLVE3K7Born%!s?OO&bbsO^4o`C zH2~UALef(&2$$Wj4tkaD9MAB7ZxD*4;`2OHOTlkLwx}bei!D~ zv@BJshN#Q1yDz}X4K7o0E%GYBVnhB`29pLSYZNMHe{SiD&Z7duA#*R-@TcUhapwss zdL+sh$l19zz)6Non&1}UhzFuhH4MHHv@!o=!P0nuD05q`sK(UPq_H-Z`dk~3A3L4T zA52`lB`An_rgrwIr0@7D4YF*2dJRqk;O%>`punxTZ0o7^5?r1~d=~Rm`@pz>Awva+ znoTq-`OP?auxQFWnokZO>RlS;qLp~WT>?WeYq*Bi1v(Q5mAcn#r7=m0#kbSoew7+h zlGG5-EUxRDL_mKE^#46cRaNrH>dk98ZZsQ>@~07*qo IM6N<$f>28+ZvX%Q literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..4d22e1617b22451ef0b34de942311ae31eebd8a2 GIT binary patch literal 3679 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 literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..37f8228413e95e31262dcdc2ffad15f287fcb4d1 GIT binary patch literal 1396 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 G?Ee5tdbp4P literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..1058d3a700aeda626fe1564e2b39597aa3785b58 GIT binary patch literal 3325 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 Ge*7N{uw1GD literal 0 HcmV?d00001 diff --git a/client/ios/Images.xcassets/Contents.json b/client/ios/Images.xcassets/Contents.json new file mode 100644 index 000000000..73c00596a --- /dev/null +++ b/client/ios/Images.xcassets/Contents.json @@ -0,0 +1,6 @@ +{ + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 2218f9e46..a5c424ddf 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -52,10 +52,14 @@ elseif(APPLE_IOS) MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in" SKIP_BUILD_RPATH 1 XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES + XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon ) # TODO: move to a common dir / add macro? target_sources(vcmiserver PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") + + target_sources(vcmiserver PRIVATE ios/Images.xcassets) + set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") endif() vcmi_set_output_dir(vcmiserver "") diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Contents.json b/server/ios/Images.xcassets/AppIcon.appiconset/Contents.json new file mode 100755 index 000000000..8122b0a0c --- /dev/null +++ b/server/ios/Images.xcassets/AppIcon.appiconset/Contents.json @@ -0,0 +1,121 @@ +{ + "images" : [ + { + "filename" : "Icon-App-20x20@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-20x20@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-29x29@1x.png", + "idiom" : "iphone", + "scale" : "1x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-40x40@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-40x40@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-60x60@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "60x60" + }, + { + "filename" : "Icon-App-60x60@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "60x60" + }, + { + "filename" : "Icon-App-20x20@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-20x20@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-29x29@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-40x40@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-40x40@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-76x76@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "76x76" + }, + { + "filename" : "Icon-App-76x76@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "76x76" + }, + { + "filename" : "Icon-App-83.5x83.5@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "83.5x83.5" + }, + { + "idiom" : "ios-marketing", + "scale" : "1x", + "size" : "1024x1024" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..3eba4d478f83f8480b0ed275579d4d4966a2a60a GIT binary patch literal 513 zcmV+c0{;DpP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0P0CZK~#90ZICfbLU9zu&%J*`tf)v39&SP=34MWhW3;%sx;VA^#?N3hGTo_L00000NkvXXu0mjf Duk0002eX+uL$Nkc;* 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 Ub21BU#sB~S07*qoM6N<$g27o4I{*Lx literal 0 HcmV?d00001 diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..e38db8555716e5656df227e61a0e75b80391d3ac GIT binary patch literal 1088 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 JPDHLkV1iX@HF*F4 literal 0 HcmV?d00001 diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..1c2b0039bed8277d6225ce1792f66b6462b22cab GIT binary patch literal 2235 zcmV;s2t@aZP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$2c$_vK~#90?U{RU)YTQozvu2FFOtBJNQeP~nTCgrDOjqK0ePs%J0%7*gboOH zN}0}d`uM|XYe$^vbZYHT#*ShuI+aHQreHE+kx;9`D6aEcT-UHy_Mu-ESv0`N;}Xuy{MNT(wS z2%gb%;oPOPoRMk31Ao>Cqh zIQqwPbohrXdxQcCKC7 zT7TUkfsFk7=D8S!W`wjH`lTDd{C!QKfolg>0#jdVJhD`3Fisk?QU!1n;m*nhD@H~;%LZXk2xxfa7HLG%EB0jJv7d7}A)*KmRqF0Yf#?7^$ue`wA5*&MTdeVKiW<1{yPjrnd`6gBA1V13NvA zu0T;chCV?NAn@W&wRDa#N{J|CuyWdYK!lFG32fTL?(nOxm@)*)r34UhH~_cwj;3B< zp)4GP+7Ck^NNIR~b`BLN@4hPcJj1R9$|Qd`$p=7m_IDET&gWu63Q*CqA`!u06Nto! z;aFe@?tcvJTl`(N+tFMGfZ~7SIw$5!c)oDTy_Z2iI%iD4sVyP(l%@@jJ=75kbu+L@ zC{4hw!$JTQZ^c97As`NaDl&;ZQjugXPlEsw$bJggdN#OIqU!83NyY*gf@$AG(^d!o z;*;7%ZX*zU(8vMzMWh?`^-z*A#bf2zHUxL-dGo=^-Z+w43@`^h38}6Z0}8j?H4_4g zJ^^H=N6zf>zs{ixX*OL_27v57{IpYB0)v=6nswC>P|oZu$)o`AH36xKQCkeJC>@uaBN{b82j`Vs0^5c~uBhwU-7D=KBIjO^WTHBBP(6e{-vl*!$74^tkTYSaT>P znR0L!jB49jR1nNDG=L`hxXaX{A+ondjOg`QCGp*NvB1K@$LZbbQ`mcKaVV3x1_7S- zzO-=MEP6M1l^lI4wyd?x_g0S|;T#uy`xBWp{C8<75XLqITV95J&s^Dq#=FHl>_l&V~3&P>0y(u8AIJ(zZ^ix ziMD|8UiwoKkn`6@U$2_0uezGjG4Gyr?CB~LoP7Je&)NbRS)G}4i}Q?#-gxxb7Z^Bx z_>#ed{C4m%BT`p+=8zW3{ke0#w()rFWd)sm?}U=*D)R;f{ehIRQIjd~)LppJnUS48 z5JmyK(wXRl>A+wo01YL8x5bet0K9>;#49?{0YH0QgQA_if1O0P1sHGG^d&a{$J8AP zk8mf`rKZP%?zD0Xd#76`cV2&NgKe-4w!t>o2HW5}80@_Hl-NQr{JPwVSSnCyz@lU^_Bw^tZm$wPTV@WC@5lbS3!mlg2U;XuK< zx|a6FJ@fFb1J?3&{~eOjSn}i*g%mgKe-4w!t>o2H#2G{{rnj^c4K(LYe>o002ov JPDHLkV1iX@HF*F4 literal 0 HcmV?d00001 diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..5d35d682f25d53c9224e2323ba235d69c6068388 GIT binary patch literal 3758 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 MYWk|B%C@2Z1^c91`Tzg` literal 0 HcmV?d00001 diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..902615d4d43322a4b38b6b8e253be0598c9fd099 GIT binary patch literal 1393 zcmV-%1&;cOP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$1X@W%K~#90?U!3@RYeqr|24apgOnoWmltMZ5X6ZR+&-#5hy=+R` zU4@W7od4xavS+^eXJ*Zsb%eNaGB=PFhs9xW*f519^t6-!#B?`}0HBJYia@B{9|3?0 z81amVNd`+n+Q&C#aA&=+?~jd;=(vReN@VZ3r0C<52?>?`p^4+42!2<3{BTrf=EP`3 zT?G>EnRei`15BJVvUd)4Nl&c>9{wdl(mj%k51Z9;>!gxzem=CRIO|DXEKkSu4pox0 zT#2M@4V|^?fVamjvC26^86>0e{-XTf0%$Z4YCFD!GB(2ttHMyj+IXJqJ z+7FCT-H)j)R4PMxzu5>Y@EEOYZIq`TxuW*9S!QljNm{PSa~_PU)yCkMdiB71x7fi$ zxhMBSq1c;o7ZM_GVFl?JlfWs(Au$~#c|ZOj7Ak)qctv3ZB3*~xtzMXD(o$@;hK664 z!pfoQ;0%%2AuS3L(e#zvKm*Fh_s?Lz@oBux!iiOf#l_K<1vIGE+k=SBD=A5Yxl%N) zyjon-x^IQse`t6^PRA~`pFrgE`6Cpl$C#v^BL^Uzfu-S%fRv5DyUiB{V9}^uwa$g= z=O92h#)!=W0ESD_zBuWG%Uy|B znPREg)?E242p~t!{HZYuJt4j<@M*)27Y0D}ff?q_u6@o4o3bRV*r}S)T9~jYO)4M_yYH;>s z``D}us0p>Fy8i@60)%v42qdE|G3|o61y|hk#NKThG&#nuQ`e8bu7MHWkxGaNx+ATp zk7uZ-`=HMLtA_7W7l*}RHv^X7--Rlmx#|)QApg7RS4Vl|>x^Q{PDC?{!sj38TdrLr zzweaB{ExDx*E~A!DEt!)2bC%dr$$ItC2ycRcwhEkfOw5H>@H61w9$F1JA8flhepVh zUk*TY;b?!D?=su(#oQyL+j7=#k>1L&e_2+fAoY!Uf6@?OR90mJlRpT1U)%o+qsz`|yZ$&E@olT)(#0K` z<)1hFmU$ip=SbF$F0|Hf&wNr4<@AfABH0;@`*Pn;^>yZ(&qB?aXAYlF&CVV|VjDu? z5=&#e5t)_{<<)<9ugBTYHGH4CI4lmk8L)o=yO?E30+r(~00000NkvXXu0mjf0QH*t literal 0 HcmV?d00001 diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..fc3411d970bc49b2034bd5758177b4571493d0a5 GIT binary patch literal 3053 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 I+(JhD3oO3#|DyhDfLX*%iN7)R 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 ON7C0ee)L)s8uLG(nwgOR literal 0 HcmV?d00001 diff --git a/server/ios/Images.xcassets/Contents.json b/server/ios/Images.xcassets/Contents.json new file mode 100644 index 000000000..73c00596a --- /dev/null +++ b/server/ios/Images.xcassets/Contents.json @@ -0,0 +1,6 @@ +{ + "info" : { + "author" : "xcode", + "version" : 1 + } +} From 7def214740348ed3ca7ad1333e2672a49a2a7979 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 13 Mar 2021 23:23:20 +0300 Subject: [PATCH 027/131] more Xcode-compatible Info.plist --- CMakeLists.txt | 2 ++ client/CMakeLists.txt | 2 +- client/ios/{Info.plist.in => Info.plist} | 6 +++--- server/CMakeLists.txt | 2 +- server/ios/{Info.plist.in => Info.plist} | 6 +++--- 5 files changed, 10 insertions(+), 8 deletions(-) rename client/ios/{Info.plist.in => Info.plist} (92%) rename server/ios/{Info.plist.in => Info.plist} (92%) diff --git a/CMakeLists.txt b/CMakeLists.txt index 7f87f9daf..3ba91a18c 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -156,6 +156,8 @@ set(CMAKE_MAP_IMPORTED_CONFIG_RELEASE Release RelWithDebInfo MinSizeRel "") if(APPLE_IOS) set(CMAKE_MACOSX_RPATH 1) set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED NO) + set(CMAKE_XCODE_ATTRIBUTE_MARKETING_VERSION ${APP_SHORT_VERSION}) + set(CMAKE_XCODE_ATTRIBUTE_PRODUCT_BUNDLE_IDENTIFIER "${BUNDLE_IDENTIFIER_PREFIX}.$(PRODUCT_NAME)") set(SYSTEM_LIBS ${SYSTEM_LIBS} iconv) # boost.locale endif(APPLE_IOS) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index ee120af8c..2324cd88d 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -181,7 +181,7 @@ elseif(APPLE_IOS) ) set_target_properties(vcmiclient PROPERTIES - MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in" + MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" SKIP_BUILD_RPATH 1 XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon diff --git a/client/ios/Info.plist.in b/client/ios/Info.plist similarity index 92% rename from client/ios/Info.plist.in rename to client/ios/Info.plist index e50e209ff..6fa803087 100644 --- a/client/ios/Info.plist.in +++ b/client/ios/Info.plist @@ -5,9 +5,9 @@ CFBundleDevelopmentRegion en CFBundleExecutable - vcmiclient + $(PRODUCT_NAME) CFBundleIdentifier - @BUNDLE_IDENTIFIER_PREFIX@.vcmiclient + $(PRODUCT_BUNDLE_IDENTIFIER) CFBundleInfoDictionaryVersion 6.0 CFBundleName @@ -15,7 +15,7 @@ CFBundlePackageType APPL CFBundleShortVersionString - @APP_SHORT_VERSION@ + $(MARKETING_VERSION) CFBundleSignature ???? CFBundleVersion diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index a5c424ddf..30c448a81 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -49,7 +49,7 @@ if(WIN32) ) elseif(APPLE_IOS) set_target_properties(vcmiserver PROPERTIES - MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist.in" + MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" SKIP_BUILD_RPATH 1 XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon diff --git a/server/ios/Info.plist.in b/server/ios/Info.plist similarity index 92% rename from server/ios/Info.plist.in rename to server/ios/Info.plist index e80d25667..9b31b63a2 100644 --- a/server/ios/Info.plist.in +++ b/server/ios/Info.plist @@ -5,9 +5,9 @@ CFBundleDevelopmentRegion en CFBundleExecutable - vcmiserver + $(PRODUCT_NAME) CFBundleIdentifier - @BUNDLE_IDENTIFIER_PREFIX@.vcmiserver + $(PRODUCT_BUNDLE_IDENTIFIER) CFBundleInfoDictionaryVersion 6.0 CFBundleName @@ -15,7 +15,7 @@ CFBundlePackageType APPL CFBundleShortVersionString - @APP_SHORT_VERSION@ + $(MARKETING_VERSION) CFBundleSignature ???? CFBundleVersion From 568e7446b985124908041d5b701ced50f7c18e82 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 14 Mar 2021 07:53:03 +0300 Subject: [PATCH 028/131] show logs without debugger attached --- lib/logging/CLogger.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/logging/CLogger.cpp b/lib/logging/CLogger.cpp index 651cf5d91..184f92773 100644 --- a/lib/logging/CLogger.cpp +++ b/lib/logging/CLogger.cpp @@ -392,7 +392,7 @@ void CLogConsoleTarget::write(const LogRecord & record) currentLog = os_log_create(ios_bundleIdentifier(), domainName.c_str()); logs.insert({domainName, currentLog}); } - os_log_with_type(currentLog, type, "%s", message.c_str()); + os_log_with_type(currentLog, type, "%{public}s", message.c_str()); #else const bool printToStdErr = record.level >= ELogLevel::WARN; From 2b1e6ca3427d1735175c9434315ba239be18278f Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 16 Mar 2021 19:40:56 +0300 Subject: [PATCH 029/131] prevent showing keyboard automatically in main menu closes kambala-decapitator/vcmi#10 --- client/mainmenu/CMainMenu.cpp | 4 ++++ client/widgets/TextControls.cpp | 6 +++--- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/client/mainmenu/CMainMenu.cpp b/client/mainmenu/CMainMenu.cpp index b04bd8034..4066f2d18 100644 --- a/client/mainmenu/CMainMenu.cpp +++ b/client/mainmenu/CMainMenu.cpp @@ -428,7 +428,9 @@ CMultiPlayers::CMultiPlayers(const std::string & firstPlayer, ESelectionScreen S statusBar = CGStatusBar::create(std::make_shared(Rect(7, 381, 348, 18), 0)); //226, 472 inputNames[0]->setText(firstPlayer, true); +#ifndef VCMI_IOS inputNames[0]->giveFocus(); +#endif } void CMultiPlayers::onChange(std::string newText) @@ -477,7 +479,9 @@ CSimpleJoinScreen::CSimpleJoinScreen(bool host) inputPort->filters += std::bind(&CTextInput::numberFilter, _1, _2, 0, 65535); buttonOk = std::make_shared(Point(26, 142), "MUBCHCK.DEF", CGI->generaltexth->zelp[560], std::bind(&CSimpleJoinScreen::connectToServer, this), SDLK_RETURN); + #ifndef VCMI_IOS inputAddress->giveFocus(); + #endif } inputAddress->setText(settings["server"]["server"].String(), true); inputPort->setText(CServerHandler::getDefaultPortStr(), true); diff --git a/client/widgets/TextControls.cpp b/client/widgets/TextControls.cpp index ba38207ed..b7854f127 100644 --- a/client/widgets/TextControls.cpp +++ b/client/widgets/TextControls.cpp @@ -420,7 +420,7 @@ CTextInput::CTextInput(const Rect & Pos, EFonts font, const CFunctionList(bgName, bgOffset.x, bgOffset.y); addUsedEvents(LCLICK | KEYBOARD | TEXTINPUT); -#ifndef VCMI_ANDROID +#if !(defined(VCMI_ANDROID) || defined(VCMI_IOS)) giveFocus(); #endif } @@ -459,7 +459,7 @@ CTextInput::CTextInput(const Rect & Pos, SDL_Surface * srf) background->pos = pos; addUsedEvents(LCLICK | KEYBOARD | TEXTINPUT); -#ifndef VCMI_ANDROID +#if !(defined(VCMI_ANDROID) || defined(VCMI_IOS)) giveFocus(); #endif } From e3539049cdc142315d01d3a1859b555eeeee592b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 16 Mar 2021 23:32:07 +0300 Subject: [PATCH 030/131] implement RMB click as long press kambala-decapitator/vcmi#1 --- client/CMakeLists.txt | 2 +- client/SDL_uikit_main.c | 19 ------------ client/SDL_uikit_main.m | 68 +++++++++++++++++++++++++++++++++++++++++ 3 files changed, 69 insertions(+), 20 deletions(-) delete mode 100644 client/SDL_uikit_main.c create mode 100644 client/SDL_uikit_main.m diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 2324cd88d..f826605d2 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -154,7 +154,7 @@ endif() if(WIN32) set(client_ICON "VCMI_client.rc") elseif(APPLE_IOS) - set(client_SRCS ${client_SRCS} SDL_uikit_main.c) + set(client_SRCS ${client_SRCS} SDL_uikit_main.m) endif() if(ENABLE_DEBUG_CONSOLE) diff --git a/client/SDL_uikit_main.c b/client/SDL_uikit_main.c deleted file mode 100644 index 966009afe..000000000 --- a/client/SDL_uikit_main.c +++ /dev/null @@ -1,19 +0,0 @@ -/* - SDL_uikit_main.c, placed in the public domain by Sam Lantinga 3/18/2019 -*/ -// #include "../../SDL_internal.h" - -/* Include the SDL main definition header */ -#include "SDL_main.h" - -#ifdef main -#undef main -#endif - -int -main(int argc, char *argv[]) -{ - return SDL_UIKitRunApp(argc, argv, SDL_main); -} - -/* vi: set ts=4 sw=4 expandtab: */ diff --git a/client/SDL_uikit_main.m b/client/SDL_uikit_main.m new file mode 100644 index 000000000..6969a2012 --- /dev/null +++ b/client/SDL_uikit_main.m @@ -0,0 +1,68 @@ +/* + SDL_uikit_main.c, placed in the public domain by Sam Lantinga 3/18/2019 +*/ + +/* Include the SDL main definition header */ +#include "SDL_main.h" + +#include "SDL_events.h" + +@import UIKit; + + +@interface SDLViewObserver : NSObject +@end + +@implementation SDLViewObserver + +- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { + __auto_type longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)]; + longPress.minimumPressDuration = 0.1; + [(UIView *)[object valueForKey:keyPath] addGestureRecognizer:longPress]; +} + +- (void)handleLongPress:(UIGestureRecognizer *)gesture { + SDL_EventType mouseButtonType; + switch (gesture.state) + { + case UIGestureRecognizerStateBegan: + mouseButtonType = SDL_MOUSEBUTTONDOWN; + break; + case UIGestureRecognizerStateEnded: + mouseButtonType = SDL_MOUSEBUTTONUP; + break; + default: + return; + } + + __auto_type touchedPoint = [gesture locationInView:gesture.view]; + SDL_Event event; + event.button = (SDL_MouseButtonEvent){ + .type = mouseButtonType, + .button = SDL_BUTTON_RIGHT, + .clicks = 1, + .x = touchedPoint.x, + .y = touchedPoint.y, + }; + SDL_PushEvent(&event); +} + +@end + + +#ifdef main +#undef main +#endif + +int +main(int argc, char *argv[]) +{ + @autoreleasepool + { + __auto_type observer = [SDLViewObserver new]; + [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + [UIApplication.sharedApplication.keyWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; + }]; + return SDL_UIKitRunApp(argc, argv, SDL_main); + } +} From 59fe73e454f3e7d23c1fb45726e513ec8dbb772b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 16 Mar 2021 23:32:58 +0300 Subject: [PATCH 031/131] some random cleanup --- .gitignore | 1 + CMakeLists.txt | 2 +- client/CMT.cpp | 2 +- 3 files changed, 3 insertions(+), 2 deletions(-) diff --git a/.gitignore b/.gitignore index fb947fc5c..3cc5ecc37 100644 --- a/.gitignore +++ b/.gitignore @@ -39,6 +39,7 @@ doc/* VCMI_VS11.sdf *.ipch VCMI_VS11.opensdf +.DS_Store # Visual Studio *.suo diff --git a/CMakeLists.txt b/CMakeLists.txt index 3ba91a18c..9217ccf22 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -58,7 +58,7 @@ endif() option(ENABLE_ERM "Enable compilation of ERM scripting module" OFF) option(ENABLE_LUA "Enable compilation of LUA scripting module" OFF) if(APPLE_IOS) - set(BUNDLE_IDENTIFIER_PREFIX "eu.vcmi" CACHE STRING "Bundle identifier prefix") + set(BUNDLE_IDENTIFIER_PREFIX "" CACHE STRING "Bundle identifier prefix") else() option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) option(ENABLE_TEST "Enable compilation of unit tests" ON) diff --git a/client/CMT.cpp b/client/CMT.cpp index cdd1408de..117985985 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -410,7 +410,7 @@ int main(int argc, char * argv[]) CCS->musich->setVolume((ui32)settings["general"]["music"].Float()); logGlobal->info("Initializing screen and sound handling: %d ms", pomtime.getDiff()); } -#ifdef __APPLE__ +#ifdef VCMI_MAC // Ctrl+click should be treated as a right click on Mac OS X SDL_SetHint(SDL_HINT_MAC_CTRL_CLICK_EMULATE_RIGHT_CLICK, "1"); #endif From 5823a384bd3b37a673904114d9552d69b64c7ba2 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 17 Mar 2021 20:14:03 +0300 Subject: [PATCH 032/131] show keyboard automatically when joining multiplayer kambala-decapitator/vcmi#10 --- client/mainmenu/CMainMenu.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/client/mainmenu/CMainMenu.cpp b/client/mainmenu/CMainMenu.cpp index 4066f2d18..85f4a9be4 100644 --- a/client/mainmenu/CMainMenu.cpp +++ b/client/mainmenu/CMainMenu.cpp @@ -479,9 +479,7 @@ CSimpleJoinScreen::CSimpleJoinScreen(bool host) inputPort->filters += std::bind(&CTextInput::numberFilter, _1, _2, 0, 65535); buttonOk = std::make_shared(Point(26, 142), "MUBCHCK.DEF", CGI->generaltexth->zelp[560], std::bind(&CSimpleJoinScreen::connectToServer, this), SDLK_RETURN); - #ifndef VCMI_IOS inputAddress->giveFocus(); - #endif } inputAddress->setText(settings["server"]["server"].String(), true); inputPort->setText(CServerHandler::getDefaultPortStr(), true); From d716db942cea4d9f5c1a9da3d5ca065e1689736a Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 17 Mar 2021 20:14:35 +0300 Subject: [PATCH 033/131] fall back to OpenGLES if Metal is unavailable --- client/CMT.cpp | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/client/CMT.cpp b/client/CMT.cpp index 117985985..103cd2868 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -1128,8 +1128,15 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn logGlobal->error("Can't fix aspect ratio for screen"); } #elif defined(VCMI_IOS) - mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN | SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI | SDL_WINDOW_METAL); - SDL_SetHint(SDL_HINT_ORIENTATIONS, "LandscapeLeft LandscapeRight"); + auto createWindow = [displayIndex](Uint32 extraFlags = 0) { + mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN_DESKTOP | SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI | extraFlags); + return mainWindow != nullptr; + }; + if (!createWindow(SDL_WINDOW_METAL)) + { + logGlobal->warn("Metal unavailable, using OpenGLES"); + createWindow(); + } SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); SDL_SetHint(SDL_HINT_RETURN_KEY_HIDES_IME, "1"); From 4647bd89817f2be6b40419d92dfe1f92f5c6ad0d Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 17 Mar 2021 20:15:48 +0300 Subject: [PATCH 034/131] add App Group entitlement kambala-decapitator/vcmi#9 --- client/CMakeLists.txt | 4 ++++ client/ios/Entitlements.in | 10 ++++++++++ server/CMakeLists.txt | 4 ++++ server/ios/Entitlements.in | 10 ++++++++++ 4 files changed, 28 insertions(+) create mode 100644 client/ios/Entitlements.in create mode 100644 server/ios/Entitlements.in diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index f826605d2..4004e814e 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -180,11 +180,15 @@ elseif(APPLE_IOS) "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO -framework Metal -framework OpenGLES -framework AVFoundation -framework GameController -framework CoreMotion" # SDL2_image ) + set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) + configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) + set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" SKIP_BUILD_RPATH 1 XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon + XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} ) target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) diff --git a/client/ios/Entitlements.in b/client/ios/Entitlements.in new file mode 100644 index 000000000..73367ec6b --- /dev/null +++ b/client/ios/Entitlements.in @@ -0,0 +1,10 @@ + + + + + com.apple.security.application-groups + + group.@BUNDLE_IDENTIFIER_PREFIX@.vcmi + + + diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 30c448a81..f526bb41c 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -48,11 +48,15 @@ if(WIN32) PROJECT_LABEL "VCMI_server" ) elseif(APPLE_IOS) + set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) + configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) + set_target_properties(vcmiserver PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" SKIP_BUILD_RPATH 1 XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon + XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} ) # TODO: move to a common dir / add macro? target_sources(vcmiserver PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) diff --git a/server/ios/Entitlements.in b/server/ios/Entitlements.in new file mode 100644 index 000000000..73367ec6b --- /dev/null +++ b/server/ios/Entitlements.in @@ -0,0 +1,10 @@ + + + + + com.apple.security.application-groups + + group.@BUNDLE_IDENTIFIER_PREFIX@.vcmi + + + From 9b3c2f2a821cf8ba28d4763c62c24523588f9ab2 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 17 Mar 2021 20:16:48 +0300 Subject: [PATCH 035/131] some cleanup --- configure_ios.sh | 15 ++++++++++++--- lib/VCMIDirs.cpp | 10 +--------- 2 files changed, 13 insertions(+), 12 deletions(-) diff --git a/configure_ios.sh b/configure_ios.sh index e2168edd6..de85bd5ac 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -1,11 +1,20 @@ #!/usr/bin/env bash boostPrefix=~/dev/other/Apple-Boost-BuildScript/build/boost/1.75.0/ios/debug/prefix -ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal +ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal-4.4 sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib +prefixPath="$boostPrefix;$ffmpegDir;$sdlLibsDir" + +# prefixPath="$boostPrefix;$sdlLibsDir" +# xcodeMajorVersion=$(xcodebuild -version | fgrep Xcode | cut -d ' ' -f 2 | cut -d . -f 1) +# if [[ $xcodeMajorVersion -ge 12 ]]; then +# extraVars=-DCMAKE_FRAMEWORK_PATH=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-gpl-4.4-xc12-frameworks +# else +# prefixPath+=;~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal +# fi srcDir="../vcmi" -cmake "$srcDir" -G Xcode \ +cmake "$srcDir" -G Xcode -T buildsystem=1 \ -DBUNDLE_IDENTIFIER_PREFIX=com.kambala \ -Wno-dev \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ @@ -13,7 +22,7 @@ cmake "$srcDir" -G Xcode \ -DDEPLOYMENT_TARGET=11.0 \ -DENABLE_BITCODE=0 \ -DCMAKE_BINARY_DIR=$(pwd) \ - -DCMAKE_PREFIX_PATH="$boostPrefix;$ffmpegDir;$sdlLibsDir" \ + -DCMAKE_PREFIX_PATH="$prefixPath" \ -DSDL2_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL/include \ -DSDL2_IMAGE_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_image-release-2.0.5 \ -DSDL2_MIXER_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_mixer-release-2.0.4 \ diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index f78601c70..adb33a468 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -410,15 +410,7 @@ std::vector VCMIDirsIOS::dataPaths() const }; } -bfs::path VCMIDirsIOS::libraryPath() const -{ -#ifdef VCMI_IOS_SIM -// fixme ios - return {"/Users/kambala/dev/vcmi/build-sim64/bin/Debug"}; -#else - return {ios_frameworksPath()}; -#endif -} +bfs::path VCMIDirsIOS::libraryPath() const { return {ios_frameworksPath()}; } bfs::path VCMIDirsIOS::binaryPath() const { return {ios_bundlePath()}; } bool VCMIDirsIOS::developmentMode() const { return false; } From e20a6c36707665ed5b739b01fac76cf0c6555a0f Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 18 Mar 2021 10:06:10 +0300 Subject: [PATCH 036/131] server: add buttons to start server and to move data to shared directory kambala-decapitator/vcmi#9 kambala-decapitator/vcmi#15 --- server/ios/main.mm | 104 ++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 98 insertions(+), 6 deletions(-) diff --git a/server/ios/main.mm b/server/ios/main.mm index 4576ed683..fe0e3c8a1 100644 --- a/server/ios/main.mm +++ b/server/ios/main.mm @@ -12,10 +12,108 @@ #include "../Global.h" #include "CVCMIServer.h" +#define SHARED_DATA_DIR @"GameData" + @interface ViewController : UIViewController +@property (nonatomic, copy) NSURL *sharedPathURL; +@property (nonatomic, copy) NSArray *dataDirsInDocuments; @end @implementation ViewController + +- (void)viewDidLoad +{ + [super viewDidLoad]; + + auto startServerButton = [UIButton buttonWithType:UIButtonTypeSystem]; + [startServerButton setTitle:@"Start Server" forState:UIControlStateNormal]; + [startServerButton addTarget:self action:@selector(startServer:) forControlEvents:UIControlEventTouchUpInside]; + [self.view addSubview:startServerButton]; + startServerButton.translatesAutoresizingMaskIntoConstraints = NO; + [NSLayoutConstraint activateConstraints:@[ + [startServerButton.centerXAnchor constraintEqualToAnchor:self.view.centerXAnchor], + [startServerButton.centerYAnchor constraintEqualToAnchor:self.view.centerYAnchor], + ]]; + + auto bundleID = NSBundle.mainBundle.bundleIdentifier; + auto lastDotPos = [bundleID rangeOfString:@"." options:NSBackwardsSearch].location; + auto groupID = [NSString stringWithFormat:@"group.%@.vcmi", [bundleID substringToIndex:lastDotPos]]; + auto fm = NSFileManager.defaultManager; + self.sharedPathURL = [fm containerURLForSecurityApplicationGroupIdentifier:groupID]; + if (!self.sharedPathURL) + { + NSLog(@"shared path for group '%@' not available", groupID); + return; + } + + auto dirEnumerator = [fm enumeratorAtURL:self.sharedPathURL includingPropertiesForKeys:@[NSURLNameKey] options:NSDirectoryEnumerationSkipsSubdirectoryDescendants errorHandler:nil]; + for (NSURL *fileURL in dirEnumerator) + { + NSString *filename; + if ([fileURL getResourceValue:&filename forKey:NSURLNameKey error:nullptr] && [filename caseInsensitiveCompare:SHARED_DATA_DIR] == NSOrderedSame) { + NSLog(SHARED_DATA_DIR @" dir already exists in the shared path"); + return; + } + } + + auto documentsURL = [fm URLForDirectory:NSDocumentDirectory inDomain:NSUserDomainMask appropriateForURL:nil create:YES error:nullptr]; + dirEnumerator = [fm enumeratorAtURL:documentsURL includingPropertiesForKeys:@[NSURLNameKey] options:NSDirectoryEnumerationSkipsSubdirectoryDescendants errorHandler:nil]; + auto dataDirs = [NSMutableArray arrayWithCapacity:3]; + for (NSURL *fileURL in dirEnumerator) + { + NSString *filename; + if (![fileURL getResourceValue:&filename forKey:NSURLNameKey error:nullptr]) + continue; + if ([filename caseInsensitiveCompare:@"data"] == NSOrderedSame || [filename caseInsensitiveCompare:@"maps"] == NSOrderedSame || [filename caseInsensitiveCompare:@"mp3"] == NSOrderedSame) + [dataDirs addObject:fileURL]; + } + if (dataDirs.count < 3) + { + NSLog(@"not all required dirs are present, found only: %@", dataDirs); + return; + } + self.dataDirsInDocuments = dataDirs; + + auto moveDataButton = [UIButton buttonWithType:UIButtonTypeSystem]; + [moveDataButton setTitle:@"Move data to shared dir" forState:UIControlStateNormal]; + [moveDataButton addTarget:self action:@selector(moveDataToSharedDir:) forControlEvents:UIControlEventTouchUpInside]; + [self.view addSubview:moveDataButton]; + + moveDataButton.translatesAutoresizingMaskIntoConstraints = NO; + [NSLayoutConstraint activateConstraints:@[ + [moveDataButton.centerXAnchor constraintEqualToAnchor:self.view.centerXAnchor], + [moveDataButton.topAnchor constraintEqualToAnchor:startServerButton.bottomAnchor constant:10], + ]]; +} + +- (void)startServer:(UIButton *)button +{ + button.enabled = NO; + [NSThread detachNewThreadWithBlock:^{ + NSThread.currentThread.name = @"CVCMIServer"; + CVCMIServer::create(); + dispatch_sync(dispatch_get_main_queue(), ^{ + button.enabled = YES; + }); + }]; +} + +- (void)moveDataToSharedDir:(UIButton *)button +{ + button.enabled = NO; + dispatch_async(dispatch_get_global_queue(QOS_CLASS_USER_INITIATED, 0), ^{ + auto fm = NSFileManager.defaultManager; + auto destinationURL = [self.sharedPathURL URLByAppendingPathComponent:SHARED_DATA_DIR]; + [fm createDirectoryAtURL:destinationURL withIntermediateDirectories:YES attributes:nil error:nullptr]; + for (NSURL *dirURL in self.dataDirsInDocuments) + [fm moveItemAtURL:dirURL toURL:[destinationURL URLByAppendingPathComponent:dirURL.lastPathComponent] error:nullptr]; + + dispatch_sync(dispatch_get_main_queue(), ^{ + [button removeFromSuperview]; + }); + }); +} + @end @@ -31,12 +129,6 @@ self.window.rootViewController = [ViewController new]; [self.window makeKeyAndVisible]; - [NSThread detachNewThreadWithBlock:^ - { - NSThread.currentThread.name = @"CVCMIServer"; - NSLog(@"starting server from thread %@", NSThread.currentThread); - CVCMIServer::create(); - }]; return YES; } From 5f97bf0be840cfb42cbd00e944a33d6c1b8ae729 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 18 Mar 2021 10:06:34 +0300 Subject: [PATCH 037/131] debug config in Xcode shouldn't produce dSYM files --- CMakeLists.txt | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 9217ccf22..6e30fa95c 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -161,6 +161,10 @@ if(APPLE_IOS) set(SYSTEM_LIBS ${SYSTEM_LIBS} iconv) # boost.locale endif(APPLE_IOS) +if(CMAKE_GENERATOR STREQUAL Xcode) + set(CMAKE_XCODE_ATTRIBUTE_DEBUG_INFORMATION_FORMAT[variant=Debug] dwarf) +endif() + if(MINGW OR MSVC) # Windows Vista or newer for FuzzyLite 6 to compile add_definitions(-D_WIN32_WINNT=0x0600) From 2fc4d4821584dc22a31944c8c65af0346fc3d7a9 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 18 Mar 2021 17:02:02 +0300 Subject: [PATCH 038/131] load game data from shared dir kambala-decapitator/vcmi#15 --- lib/CIOSUtils.h | 15 +++++++++++++++ lib/CIOSUtils.m | 39 +++++++++++++++++++++++++++++++++++---- lib/VCMIDirs.cpp | 4 ++-- server/ios/main.mm | 39 ++++++++------------------------------- 4 files changed, 60 insertions(+), 37 deletions(-) diff --git a/lib/CIOSUtils.h b/lib/CIOSUtils.h index 682429747..d3beaa0ce 100644 --- a/lib/CIOSUtils.h +++ b/lib/CIOSUtils.h @@ -7,10 +7,25 @@ * Full text of license available in license.txt file, in main folder * */ +#include + +#ifdef __OBJC__ +@class NSURL; +#endif extern const char *ios_documentsPath(); extern const char *ios_cachesPath(); +#ifdef __OBJC__ +NSURL *sharedContainerURL(); +NSURL *sharedGameDataURL(); +#endif +extern const char *ios_sharedDataPath(); + +#if TARGET_OS_SIMULATOR +extern const char *ios_hostApplicationSupportPath(); +#endif + extern const char *ios_bundlePath(); extern const char *ios_frameworksPath(); diff --git a/lib/CIOSUtils.m b/lib/CIOSUtils.m index 0621f1230..ee1db12c0 100644 --- a/lib/CIOSUtils.m +++ b/lib/CIOSUtils.m @@ -12,15 +12,46 @@ @import Foundation; -static const char *standardPath(NSSearchPathDirectory directory) +static NSString *standardPathNative(NSSearchPathDirectory directory) { - return [NSFileManager.defaultManager URLForDirectory:directory inDomain:NSUserDomainMask appropriateForURL:nil create:NO error:NULL].path.UTF8String; + return [NSFileManager.defaultManager URLForDirectory:directory inDomain:NSUserDomainMask appropriateForURL:nil create:NO error:NULL].path; } +static const char *standardPath(NSSearchPathDirectory directory) { return standardPathNative(directory).fileSystemRepresentation; } const char *ios_documentsPath() { return standardPath(NSDocumentDirectory); } const char *ios_cachesPath() { return standardPath(NSCachesDirectory); } -const char *ios_bundlePath() { return NSBundle.mainBundle.bundlePath.UTF8String; } -const char *ios_frameworksPath() { return [NSBundle.mainBundle.bundlePath stringByAppendingPathComponent:@"Frameworks"].UTF8String; } // TODO: sharedFrameworksPath? +NSURL *sharedContainerURL() +{ + static NSURL *sharedPathURL; + static dispatch_once_t onceToken; + dispatch_once(&onceToken, ^{ + __auto_type bundleID = NSBundle.mainBundle.bundleIdentifier; + __auto_type lastDotPos = [bundleID rangeOfString:@"." options:NSBackwardsSearch].location; + __auto_type groupID = [NSString stringWithFormat:@"group.%@.vcmi", [bundleID substringToIndex:lastDotPos]]; + sharedPathURL = [NSFileManager.defaultManager containerURLForSecurityApplicationGroupIdentifier:groupID]; + }); + return sharedPathURL; +} +NSURL *sharedGameDataURL() { return [sharedContainerURL() URLByAppendingPathComponent:@"GameData"]; } +const char *ios_sharedDataPath() { return sharedGameDataURL().fileSystemRepresentation; } + +#if TARGET_OS_SIMULATOR +const char *ios_hostApplicationSupportPath() +{ + static NSString *applicationSupportPath; + static dispatch_once_t onceToken; + dispatch_once(&onceToken, ^{ + __auto_type cachesPath = standardPathNative(NSCachesDirectory); + __auto_type afterMacOsHomeDirPos = [cachesPath rangeOfString:@"Library/Developer"].location; + NSCAssert(afterMacOsHomeDirPos != NSNotFound, @"simulator directory location is not under user's home directory: %@", cachesPath); + applicationSupportPath = [[cachesPath substringToIndex:afterMacOsHomeDirPos] stringByAppendingPathComponent:@"Library/Application Support/vcmi"].stringByResolvingSymlinksInPath; + }); + return applicationSupportPath.fileSystemRepresentation; +} +#endif + +const char *ios_bundlePath() { return NSBundle.mainBundle.bundlePath.fileSystemRepresentation; } +const char *ios_frameworksPath() { return NSBundle.mainBundle.privateFrameworksPath.fileSystemRepresentation; } const char *ios_bundleIdentifier() { return NSBundle.mainBundle.bundleIdentifier.UTF8String; } diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index adb33a468..45cac44d4 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -402,9 +402,9 @@ std::vector VCMIDirsIOS::dataPaths() const { return { #ifdef VCMI_IOS_SIM - // fixme ios - {"/Users/kambala/Library/Application Support/vcmi"}, + {ios_hostApplicationSupportPath()}, #endif + {ios_sharedDataPath()}, binaryPath(), userDataPath(), }; diff --git a/server/ios/main.mm b/server/ios/main.mm index fe0e3c8a1..c8fa6537c 100644 --- a/server/ios/main.mm +++ b/server/ios/main.mm @@ -11,11 +11,11 @@ #include "../Global.h" #include "CVCMIServer.h" - -#define SHARED_DATA_DIR @"GameData" +extern "C" { +#import "../lib/CIOSUtils.h" +} @interface ViewController : UIViewController -@property (nonatomic, copy) NSURL *sharedPathURL; @property (nonatomic, copy) NSArray *dataDirsInDocuments; @end @@ -35,29 +35,13 @@ [startServerButton.centerYAnchor constraintEqualToAnchor:self.view.centerYAnchor], ]]; - auto bundleID = NSBundle.mainBundle.bundleIdentifier; - auto lastDotPos = [bundleID rangeOfString:@"." options:NSBackwardsSearch].location; - auto groupID = [NSString stringWithFormat:@"group.%@.vcmi", [bundleID substringToIndex:lastDotPos]]; auto fm = NSFileManager.defaultManager; - self.sharedPathURL = [fm containerURLForSecurityApplicationGroupIdentifier:groupID]; - if (!self.sharedPathURL) - { - NSLog(@"shared path for group '%@' not available", groupID); + auto sharedGameDataUrl = sharedGameDataURL(); + if (!sharedGameDataUrl || [fm fileExistsAtPath:sharedGameDataUrl.path]) return; - } - - auto dirEnumerator = [fm enumeratorAtURL:self.sharedPathURL includingPropertiesForKeys:@[NSURLNameKey] options:NSDirectoryEnumerationSkipsSubdirectoryDescendants errorHandler:nil]; - for (NSURL *fileURL in dirEnumerator) - { - NSString *filename; - if ([fileURL getResourceValue:&filename forKey:NSURLNameKey error:nullptr] && [filename caseInsensitiveCompare:SHARED_DATA_DIR] == NSOrderedSame) { - NSLog(SHARED_DATA_DIR @" dir already exists in the shared path"); - return; - } - } auto documentsURL = [fm URLForDirectory:NSDocumentDirectory inDomain:NSUserDomainMask appropriateForURL:nil create:YES error:nullptr]; - dirEnumerator = [fm enumeratorAtURL:documentsURL includingPropertiesForKeys:@[NSURLNameKey] options:NSDirectoryEnumerationSkipsSubdirectoryDescendants errorHandler:nil]; + auto dirEnumerator = [fm enumeratorAtURL:documentsURL includingPropertiesForKeys:@[NSURLNameKey] options:NSDirectoryEnumerationSkipsSubdirectoryDescendants errorHandler:nil]; auto dataDirs = [NSMutableArray arrayWithCapacity:3]; for (NSURL *fileURL in dirEnumerator) { @@ -68,10 +52,7 @@ [dataDirs addObject:fileURL]; } if (dataDirs.count < 3) - { - NSLog(@"not all required dirs are present, found only: %@", dataDirs); return; - } self.dataDirsInDocuments = dataDirs; auto moveDataButton = [UIButton buttonWithType:UIButtonTypeSystem]; @@ -100,17 +81,13 @@ - (void)moveDataToSharedDir:(UIButton *)button { - button.enabled = NO; + [button removeFromSuperview]; dispatch_async(dispatch_get_global_queue(QOS_CLASS_USER_INITIATED, 0), ^{ auto fm = NSFileManager.defaultManager; - auto destinationURL = [self.sharedPathURL URLByAppendingPathComponent:SHARED_DATA_DIR]; + auto destinationURL = sharedGameDataURL(); [fm createDirectoryAtURL:destinationURL withIntermediateDirectories:YES attributes:nil error:nullptr]; for (NSURL *dirURL in self.dataDirsInDocuments) [fm moveItemAtURL:dirURL toURL:[destinationURL URLByAppendingPathComponent:dirURL.lastPathComponent] error:nullptr]; - - dispatch_sync(dispatch_get_main_queue(), ^{ - [button removeFromSuperview]; - }); }); } From 01c17d856fc8725478ecc8167ee8408c10907246 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 20 Mar 2021 14:58:10 +0300 Subject: [PATCH 039/131] support restarting server thread kambala-decapitator/vcmi#27 --- lib/filesystem/Filesystem.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/filesystem/Filesystem.cpp b/lib/filesystem/Filesystem.cpp index d478d136e..7afe29345 100644 --- a/lib/filesystem/Filesystem.cpp +++ b/lib/filesystem/Filesystem.cpp @@ -171,6 +171,7 @@ void CResourceHandler::initialize() // |-config globalResourceHandler.rootLoader = vstd::make_unique(); + knownLoaders.clear(); knownLoaders["root"] = globalResourceHandler.rootLoader.get(); knownLoaders["saves"] = new CFilesystemLoader("SAVES/", VCMIDirs::get().userSavePath()); knownLoaders["config"] = new CFilesystemLoader("CONFIG/", VCMIDirs::get().userConfigPath()); From 23540237315a5c61bf473b640894f37f754e8c90 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 20 Mar 2021 17:05:32 +0300 Subject: [PATCH 040/131] move extern "C" to header --- lib/CIOSUtils.h | 10 ++++++++++ lib/VCMIDirs.cpp | 2 -- lib/logging/CLogger.cpp | 2 +- server/ios/main.mm | 2 -- 4 files changed, 11 insertions(+), 5 deletions(-) diff --git a/lib/CIOSUtils.h b/lib/CIOSUtils.h index d3beaa0ce..3b5bd3e80 100644 --- a/lib/CIOSUtils.h +++ b/lib/CIOSUtils.h @@ -7,6 +7,12 @@ * Full text of license available in license.txt file, in main folder * */ +#pragma once + +#ifdef __cplusplus +extern "C" { +#endif + #include #ifdef __OBJC__ @@ -30,3 +36,7 @@ extern const char *ios_bundlePath(); extern const char *ios_frameworksPath(); extern const char *ios_bundleIdentifier(); + +#ifdef __cplusplus +} +#endif diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index 45cac44d4..c9f4e3b67 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -375,9 +375,7 @@ bfs::path VCMIDirsApple::userConfigPath() const { return userDataPath() / "confi std::string VCMIDirsApple::libraryName(const std::string& basename) const { return "lib" + basename + ".dylib"; } #ifdef VCMI_IOS -extern "C" { #import "CIOSUtils.h" -} class VCMIDirsIOS final : public VCMIDirsApple { diff --git a/lib/logging/CLogger.cpp b/lib/logging/CLogger.cpp index 184f92773..fa30eea09 100644 --- a/lib/logging/CLogger.cpp +++ b/lib/logging/CLogger.cpp @@ -31,8 +31,8 @@ namespace ELogLevel } } #elif defined(VCMI_IOS) -extern "C" { #import "../CIOSUtils.h" +extern "C" { #include } #endif diff --git a/server/ios/main.mm b/server/ios/main.mm index c8fa6537c..7b457a8d6 100644 --- a/server/ios/main.mm +++ b/server/ios/main.mm @@ -11,9 +11,7 @@ #include "../Global.h" #include "CVCMIServer.h" -extern "C" { #import "../lib/CIOSUtils.h" -} @interface ViewController : UIViewController @property (nonatomic, copy) NSArray *dataDirsInDocuments; From fd92150566be3dbc61ab68d988c76e49c17aa200 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 21 Mar 2021 13:15:27 +0300 Subject: [PATCH 041/131] use same aspect ratio fix as on android kambala-decapitator/vcmi#26 --- client/CMT.cpp | 61 +++++++++++++++++++++++++------------------------- 1 file changed, 30 insertions(+), 31 deletions(-) diff --git a/client/CMT.cpp b/client/CMT.cpp index 103cd2868..0e792dc62 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -1091,26 +1091,41 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn if(nullptr == mainWindow) { + #if defined(VCMI_ANDROID) || defined(VCMI_IOS) + auto createWindow = [displayIndex](Uint32 extraFlags) -> bool { + mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN | extraFlags); + return mainWindow != nullptr; + }; - #ifdef VCMI_ANDROID - mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex),SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN); +#ifdef VCMI_IOS + SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); + SDL_SetHint(SDL_HINT_RETURN_KEY_HIDES_IME, "1"); - // SDL on Android doesn't do proper letterboxing, and will show an annoying flickering in the blank space in case you're not using the full screen estate + Uint32 windowFlags = SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI; + if(!createWindow(windowFlags | SDL_WINDOW_METAL)) + { + logGlobal->warn("Metal unavailable, using OpenGLES"); + createWindow(windowFlags); + } + + // TODO: can android use this too? + auto shouldFixAspectRatio = true; + int screenWidth, screenHeight; + SDL_GetWindowSize(mainWindow, &screenWidth, &screenHeight); +#else + createWindow(0); + + SDL_Rect screenRect; + auto shouldFixAspectRatio = SDL_GetDisplayBounds(0, &screenRect) == 0; + int screenWidth = screenRect.w, screenHeight = screenRect.h; +#endif + // SDL on mobile doesn't do proper letterboxing, and will show an annoying flickering in the blank space in case you're not using the full screen estate // That's why we need to make sure our width and height we'll use below have the same aspect ratio as the screen itself to ensure we fill the full screen estate - - SDL_Rect screenRect; - - if(SDL_GetDisplayBounds(0, &screenRect) == 0) + if(shouldFixAspectRatio) { - int screenWidth, screenHeight; - double aspect; + auto aspect = static_cast(screenWidth) / screenHeight; - screenWidth = screenRect.w; - screenHeight = screenRect.h; - - aspect = (double)screenWidth / (double)screenHeight; - - logGlobal->info("Screen size and aspect ration: %dx%d (%lf)", screenWidth, screenHeight, aspect); + logGlobal->info("Screen size and aspect ratio: %dx%d (%lf)", screenWidth, screenHeight, aspect); if((double)w / aspect > (double)h) { @@ -1127,22 +1142,6 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn { logGlobal->error("Can't fix aspect ratio for screen"); } - #elif defined(VCMI_IOS) - auto createWindow = [displayIndex](Uint32 extraFlags = 0) { - mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN_DESKTOP | SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI | extraFlags); - return mainWindow != nullptr; - }; - if (!createWindow(SDL_WINDOW_METAL)) - { - logGlobal->warn("Metal unavailable, using OpenGLES"); - createWindow(); - } - SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); - SDL_SetHint(SDL_HINT_RETURN_KEY_HIDES_IME, "1"); - - logGlobal->info("before SDL_GetWindowSize %dx%d", w, h); - SDL_GetWindowSize(mainWindow, &w, &h); - logGlobal->info("after SDL_GetWindowSize %dx%d", w, h); #else if(fullscreen) From 783c0eab26312942415156c7e332c81433b0d93b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 21 Mar 2021 13:15:43 +0300 Subject: [PATCH 042/131] fix coordinates of long press (right click) kambala-decapitator/vcmi#1 kambala-decapitator/vcmi#26 --- client/SDL_uikit_main.m | 40 +++++++++++++++++++++++++++++++++------- 1 file changed, 33 insertions(+), 7 deletions(-) diff --git a/client/SDL_uikit_main.m b/client/SDL_uikit_main.m index 6969a2012..cb3eb0e99 100644 --- a/client/SDL_uikit_main.m +++ b/client/SDL_uikit_main.m @@ -3,12 +3,15 @@ */ /* Include the SDL main definition header */ -#include "SDL_main.h" +#include -#include "SDL_events.h" +#include +#include @import UIKit; +extern SDL_Window * mainWindow; + @interface SDLViewObserver : NSObject @end @@ -18,6 +21,7 @@ - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { __auto_type longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)]; longPress.minimumPressDuration = 0.1; + longPress.delaysTouchesBegan = YES; // prevent normal clicks by SDL [(UIView *)[object valueForKey:keyPath] addGestureRecognizer:longPress]; } @@ -35,16 +39,38 @@ return; } + __auto_type renderer = SDL_GetRenderer(mainWindow); + float scaleX, scaleY; + SDL_Rect viewport; + SDL_RenderGetScale(renderer, &scaleX, &scaleY); + SDL_RenderGetViewport(renderer, &viewport); + __auto_type touchedPoint = [gesture locationInView:gesture.view]; - SDL_Event event; - event.button = (SDL_MouseButtonEvent){ + __auto_type screenScale = UIScreen.mainScreen.nativeScale; + Sint32 x = (int)touchedPoint.x * screenScale / scaleX - viewport.x; + Sint32 y = (int)touchedPoint.y * screenScale / scaleY - viewport.y; + + SDL_Event rmbEvent; + rmbEvent.button = (SDL_MouseButtonEvent){ .type = mouseButtonType, .button = SDL_BUTTON_RIGHT, .clicks = 1, - .x = touchedPoint.x, - .y = touchedPoint.y, + .x = x, + .y = y, }; - SDL_PushEvent(&event); + SDL_PushEvent(&rmbEvent); + + // small hack to prevent cursor jumping + if (mouseButtonType == SDL_MOUSEBUTTONUP) + dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.025 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ + SDL_Event motionEvent; + motionEvent.motion = (SDL_MouseMotionEvent){ + .type = SDL_MOUSEMOTION, + .x = x, + .y = y, + }; + SDL_PushEvent(&motionEvent); + }); } @end From 27b7cb8f1feb0856a42b415b21ab8deedb2ffcbc Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 21 Mar 2021 13:43:01 +0300 Subject: [PATCH 043/131] show long press hints higher kambala-decapitator/vcmi#29 --- client/windows/InfoWindows.cpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/client/windows/InfoWindows.cpp b/client/windows/InfoWindows.cpp index 7f3ee26d3..25e6432e5 100644 --- a/client/windows/InfoWindows.cpp +++ b/client/windows/InfoWindows.cpp @@ -308,6 +308,10 @@ void CRClickPopup::createAndPush(const std::string &txt, const CInfoWindow::TCom auto temp = std::make_shared(txt, player, comps); temp->center(Point(GH.current->motion)); //center on mouse +#ifdef VCMI_IOS + // TODO: enable also for android? + temp->moveBy({0, -temp->pos.h / 2}); +#endif temp->fitToScreen(10); GH.pushIntT(temp); From 44d0e19c715e45a7763c245a063878fe1f6a8671 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 21 Mar 2021 17:30:34 +0300 Subject: [PATCH 044/131] remove focus from active text input after keyboard is closed allows focusing same text input again kambala-decapitator/vcmi#4 kambala-decapitator/vcmi#10 --- client/CFocusableHelper.cpp | 21 +++++++++++++++++++ client/CFocusableHelper.h | 11 ++++++++++ client/CMakeLists.txt | 12 +++++++++-- .../{SDL_uikit_main.m => SDL_uikit_main.mm} | 9 ++++++-- 4 files changed, 49 insertions(+), 4 deletions(-) create mode 100644 client/CFocusableHelper.cpp create mode 100644 client/CFocusableHelper.h rename client/{SDL_uikit_main.m => SDL_uikit_main.mm} (90%) diff --git a/client/CFocusableHelper.cpp b/client/CFocusableHelper.cpp new file mode 100644 index 000000000..e4e3c6cfe --- /dev/null +++ b/client/CFocusableHelper.cpp @@ -0,0 +1,21 @@ +/* + * CFocusableHelper.cpp, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#include "CFocusableHelper.h" +#include "../Global.h" +#include "widgets/TextControls.h" + +void removeFocusFromActiveInput() +{ + if(CFocusable::inputWithFocus == nullptr) + return; + CFocusable::inputWithFocus->focus = false; + CFocusable::inputWithFocus->redraw(); + CFocusable::inputWithFocus = nullptr; +} diff --git a/client/CFocusableHelper.h b/client/CFocusableHelper.h new file mode 100644 index 000000000..6ee0927a3 --- /dev/null +++ b/client/CFocusableHelper.h @@ -0,0 +1,11 @@ +/* + * CFocusableHelper.h, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ + +void removeFocusFromActiveInput(); diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 4004e814e..62d47278e 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -145,6 +145,16 @@ set(client_HEADERS SDLRWwrapper.h ) +if(APPLE_IOS) + set(client_SRCS ${client_SRCS} + SDL_uikit_main.mm + CFocusableHelper.cpp + ) + set(client_HEADERS ${client_HEADERS} + CFocusableHelper.h + ) +endif() + assign_source_group(${client_SRCS} ${client_HEADERS} VCMI_client.rc) if(ANDROID) # android needs client/server to be libraries, not executables, so we can't reuse the build part of this script @@ -153,8 +163,6 @@ endif() if(WIN32) set(client_ICON "VCMI_client.rc") -elseif(APPLE_IOS) - set(client_SRCS ${client_SRCS} SDL_uikit_main.m) endif() if(ENABLE_DEBUG_CONSOLE) diff --git a/client/SDL_uikit_main.m b/client/SDL_uikit_main.mm similarity index 90% rename from client/SDL_uikit_main.m rename to client/SDL_uikit_main.mm index cb3eb0e99..c1f94a796 100644 --- a/client/SDL_uikit_main.m +++ b/client/SDL_uikit_main.mm @@ -8,9 +8,11 @@ #include #include -@import UIKit; +#include "../Global.h" +#include "CMT.h" +#include "CFocusableHelper.h" -extern SDL_Window * mainWindow; +#import @interface SDLViewObserver : NSObject @@ -89,6 +91,9 @@ main(int argc, char *argv[]) [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { [UIApplication.sharedApplication.keyWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; }]; + [NSNotificationCenter.defaultCenter addObserverForName:UIKeyboardDidHideNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + removeFocusFromActiveInput(); + }]; return SDL_UIKitRunApp(argc, argv, SDL_main); } } From 497bf58d3272bd0e67914ad91ee32d256cab8c26 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 21 Mar 2021 17:30:46 +0300 Subject: [PATCH 045/131] disable modules --- CMakeLists.txt | 4 ---- lib/CIOSUtils.m | 2 +- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 6e30fa95c..3e33acdf4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -243,10 +243,6 @@ endif() if(APPLE_IOS) set(CMAKE_XCODE_ATTRIBUTE_TARGETED_DEVICE_FAMILY "1,2") # iPhone + iPad set(CMAKE_XCODE_ATTRIBUTE_GCC_WARN_64_TO_32_BIT_CONVERSION "NO") - - # TODO: also enable for macOS - set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fmodules") - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fmodules") endif(APPLE_IOS) # Check if some platform-specific libraries are needed for linking diff --git a/lib/CIOSUtils.m b/lib/CIOSUtils.m index ee1db12c0..27e291642 100644 --- a/lib/CIOSUtils.m +++ b/lib/CIOSUtils.m @@ -10,7 +10,7 @@ #import "CIOSUtils.h" -@import Foundation; +#import static NSString *standardPathNative(NSSearchPathDirectory directory) { From 123fd5933ee3db7067c40d0f59f3effebbdb58bb Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 22 Mar 2021 22:40:19 +0300 Subject: [PATCH 046/131] trigger chat message with pinch gesture kambala-decapitator/vcmi#4 --- client/SDL_uikit_main.mm | 83 ++++++++++++++++++++++++++++++++++++---- 1 file changed, 75 insertions(+), 8 deletions(-) diff --git a/client/SDL_uikit_main.mm b/client/SDL_uikit_main.mm index c1f94a796..920648b72 100644 --- a/client/SDL_uikit_main.mm +++ b/client/SDL_uikit_main.mm @@ -10,24 +10,46 @@ #include "../Global.h" #include "CMT.h" +#include "CServerHandler.h" #include "CFocusableHelper.h" #import -@interface SDLViewObserver : NSObject +static int watchReturnKey(void * userdata, SDL_Event * event); + +static void sendKeyEvent(SDL_KeyCode keyCode) +{ + SDL_Event keyEvent; + keyEvent.key = (SDL_KeyboardEvent){ + .type = SDL_KEYDOWN, + .keysym.sym = keyCode, + }; + SDL_PushEvent(&keyEvent); +} + + +@interface SDLViewObserver : NSObject +@property (nonatomic) bool wasChatMessageSent; @end @implementation SDLViewObserver - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { - __auto_type longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)]; + UIView * view = [object valueForKey:keyPath]; + + auto longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)]; longPress.minimumPressDuration = 0.1; - longPress.delaysTouchesBegan = YES; // prevent normal clicks by SDL - [(UIView *)[object valueForKey:keyPath] addGestureRecognizer:longPress]; + [view addGestureRecognizer:longPress]; + + auto pinch = [[UIPinchGestureRecognizer alloc] initWithTarget:self action:@selector(handlePinch:)]; + [view addGestureRecognizer:pinch]; } +#pragma mark - Gestures + - (void)handleLongPress:(UIGestureRecognizer *)gesture { + // send RMB click SDL_EventType mouseButtonType; switch (gesture.state) { @@ -41,14 +63,14 @@ return; } - __auto_type renderer = SDL_GetRenderer(mainWindow); + auto renderer = SDL_GetRenderer(mainWindow); float scaleX, scaleY; SDL_Rect viewport; SDL_RenderGetScale(renderer, &scaleX, &scaleY); SDL_RenderGetViewport(renderer, &viewport); - __auto_type touchedPoint = [gesture locationInView:gesture.view]; - __auto_type screenScale = UIScreen.mainScreen.nativeScale; + auto touchedPoint = [gesture locationInView:gesture.view]; + auto screenScale = UIScreen.mainScreen.nativeScale; Sint32 x = (int)touchedPoint.x * screenScale / scaleX - viewport.x; Sint32 y = (int)touchedPoint.y * screenScale / scaleY - viewport.y; @@ -75,6 +97,40 @@ }); } +- (void)handlePinch:(UIGestureRecognizer *)gesture { + if(gesture.state != UIGestureRecognizerStateBegan || CSH->state != EClientState::GAMEPLAY) + return; + + // Tab triggers chat message input + self.wasChatMessageSent = false; + [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(handleKeyboardDidShowForGameChat:) name:UIKeyboardDidShowNotification object:nil]; + sendKeyEvent(SDLK_TAB); +} + +#pragma mark - Notifications + +- (void)handleKeyboardDidShowForGameChat:(NSNotification *)n { + [NSNotificationCenter.defaultCenter removeObserver:self name:n.name object:nil]; + + // watch for pressing Return to ignore sending Escape key after keyboard is closed + SDL_AddEventWatch(watchReturnKey, (__bridge void *)self); + [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(handleKeyboardDidHideForGameChat:) name:UIKeyboardDidHideNotification object:nil]; +} + +- (void)handleKeyboardDidHideForGameChat:(NSNotification *)n { + [NSNotificationCenter.defaultCenter removeObserver:self name:n.name object:nil]; + + // discard chat message + if(!self.wasChatMessageSent) + sendKeyEvent(SDLK_ESCAPE); +} + +#pragma mark - UIGestureRecognizerDelegate + +- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldBeRequiredToFailByGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer { + return [gestureRecognizer isKindOfClass:[UIPinchGestureRecognizer class]]; +} + @end @@ -87,7 +143,7 @@ main(int argc, char *argv[]) { @autoreleasepool { - __auto_type observer = [SDLViewObserver new]; + auto observer = [SDLViewObserver new]; [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { [UIApplication.sharedApplication.keyWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; }]; @@ -97,3 +153,14 @@ main(int argc, char *argv[]) return SDL_UIKitRunApp(argc, argv, SDL_main); } } + +static int watchReturnKey(void * userdata, SDL_Event * event) +{ + if(event->type == SDL_KEYDOWN && event->key.keysym.scancode == SDL_SCANCODE_RETURN) + { + auto self = (__bridge SDLViewObserver *)userdata; + self.wasChatMessageSent = true; + SDL_DelEventWatch(watchReturnKey, userdata); + } + return 1; +} From bca46d9560a8a21fd27a123ad3dbddc5922e458b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 24 Mar 2021 21:02:12 +0300 Subject: [PATCH 047/131] fix focusing input on Save screen --- client/lobby/SelectionTab.cpp | 9 +++++++-- client/lobby/SelectionTab.h | 1 + 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/client/lobby/SelectionTab.cpp b/client/lobby/SelectionTab.cpp index 0d135a915..e1d6226c3 100644 --- a/client/lobby/SelectionTab.cpp +++ b/client/lobby/SelectionTab.cpp @@ -129,7 +129,7 @@ static ESortBy getSortBySelectionScreen(ESelectionScreen Type) } SelectionTab::SelectionTab(ESelectionScreen Type) - : CIntObject(LCLICK | WHEEL | KEYBOARD | DOUBLECLICK), callOnSelect(nullptr), tabType(Type), selectionPos(0), sortModeAscending(true) + : CIntObject(LCLICK | WHEEL | KEYBOARD | DOUBLECLICK), callOnSelect(nullptr), tabType(Type), selectionPos(0), sortModeAscending(true), inputNameRect{32, 539, 350, 20} { OBJ_CONSTRUCTION; @@ -140,7 +140,7 @@ SelectionTab::SelectionTab(ESelectionScreen Type) sortingBy = _format; background = std::make_shared("SCSELBCK.bmp", 0, 6); pos = background->pos; - inputName = std::make_shared(Rect(32, 539, 350, 20), Point(-32, -25), "GSSTRIP.bmp", 0); + inputName = std::make_shared(inputNameRect, Point(-32, -25), "GSSTRIP.bmp", 0); inputName->filters += CTextInput::filenameFilter; labelMapSizes = std::make_shared(87, 62, FONT_SMALL, EAlignment::CENTER, Colors::YELLOW, CGI->generaltexth->allTexts[510]); @@ -273,6 +273,11 @@ void SelectionTab::clickLeft(tribool down, bool previousState) { select(line); } +#ifdef VCMI_IOS + // focus input field if clicked inside it + else if(inputName->active && inputNameRect.isIn(GH.current->button.x, GH.current->button.y)) + inputName->giveFocus(); +#endif } } diff --git a/client/lobby/SelectionTab.h b/client/lobby/SelectionTab.h index a6a974796..ebcdec668 100644 --- a/client/lobby/SelectionTab.h +++ b/client/lobby/SelectionTab.h @@ -90,6 +90,7 @@ private: std::shared_ptr labelTabTitle; std::shared_ptr labelMapSizes; ESelectionScreen tabType; + Rect inputNameRect; void parseMaps(const std::unordered_set & files); void parseSaves(const std::unordered_set & files); From 1a45b97f5e38b418ef439159dd885de2fbe5110b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 19 Apr 2021 01:43:34 +0300 Subject: [PATCH 048/131] improve keyboard hide detection --- client/SDL_uikit_main.mm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/SDL_uikit_main.mm b/client/SDL_uikit_main.mm index 920648b72..033d59615 100644 --- a/client/SDL_uikit_main.mm +++ b/client/SDL_uikit_main.mm @@ -147,7 +147,7 @@ main(int argc, char *argv[]) [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { [UIApplication.sharedApplication.keyWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; }]; - [NSNotificationCenter.defaultCenter addObserverForName:UIKeyboardDidHideNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + [NSNotificationCenter.defaultCenter addObserverForName:UITextFieldTextDidEndEditingNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { removeFocusFromActiveInput(); }]; return SDL_UIKitRunApp(argc, argv, SDL_main); From 217c83a7e761b858ffb7c9282abf0855c38063b5 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 19 Apr 2021 01:58:14 +0300 Subject: [PATCH 049/131] convert text input rect to screen coordinates workarounds SDL bug related to moving window ensuring that the input is always above the native keyboard kambala-decapitator/vcmi#31 --- client/SDL_uikit_main.mm | 2 ++ client/gui/SDL_Extensions.cpp | 34 +++++++++++++++++++++++++++++----- 2 files changed, 31 insertions(+), 5 deletions(-) diff --git a/client/SDL_uikit_main.mm b/client/SDL_uikit_main.mm index 033d59615..edcf28cc1 100644 --- a/client/SDL_uikit_main.mm +++ b/client/SDL_uikit_main.mm @@ -15,6 +15,8 @@ #import +double ios_screenScale() { return UIScreen.mainScreen.nativeScale; } + static int watchReturnKey(void * userdata, SDL_Event * event); diff --git a/client/gui/SDL_Extensions.cpp b/client/gui/SDL_Extensions.cpp index e41b09f0c..69ddb72d2 100644 --- a/client/gui/SDL_Extensions.cpp +++ b/client/gui/SDL_Extensions.cpp @@ -18,6 +18,8 @@ #ifdef VCMI_APPLE #include + +extern double ios_screenScale(); // TODO ios: move to appropriate file #endif const SDL_Color Colors::YELLOW = { 229, 215, 123, 0 }; @@ -790,15 +792,37 @@ SDL_Color CSDL_Ext::makeColor(ui8 r, ui8 g, ui8 b, ui8 a) void CSDL_Ext::startTextInput(SDL_Rect * where) { + auto impl = [](SDL_Rect * where) + { + if (SDL_IsTextInputActive() == SDL_FALSE) + { + SDL_StartTextInput(); + } + SDL_SetTextInputRect(where); + }; + #ifdef VCMI_APPLE dispatch_async(dispatch_get_main_queue(), ^{ #endif - if (SDL_IsTextInputActive() == SDL_FALSE) - { - SDL_StartTextInput(); - } - SDL_SetTextInputRect(where); +#ifdef VCMI_IOS + // TODO ios: looks like SDL bug actually, try fixing there + auto renderer = SDL_GetRenderer(mainWindow); + float scaleX, scaleY; + SDL_Rect viewport; + SDL_RenderGetScale(renderer, &scaleX, &scaleY); + SDL_RenderGetViewport(renderer, &viewport); + + auto nativeScale = ios_screenScale(); + auto rectInScreenCoordinates = *where; + rectInScreenCoordinates.x = (viewport.x + rectInScreenCoordinates.x) * scaleX / nativeScale; + rectInScreenCoordinates.y = (viewport.y + rectInScreenCoordinates.y) * scaleY / nativeScale; + rectInScreenCoordinates.w = rectInScreenCoordinates.w * scaleX / nativeScale; + rectInScreenCoordinates.h = rectInScreenCoordinates.h * scaleY / nativeScale; + impl(&rectInScreenCoordinates); +#else + impl(where); +#endif #ifdef VCMI_APPLE }); From f97ff108a7fc601617e412aeb00a269307f6e6b7 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 19 Apr 2021 02:28:29 +0300 Subject: [PATCH 050/131] show SDL's textfield above the keyboard for game chat, extract handling to separate class kambala-decapitator/vcmi#4 kambala-decapitator/vcmi#31 --- client/CMakeLists.txt | 4 +- client/ios/GameChatKeyboardHanlder.h | 23 ++++++ client/ios/GameChatKeyboardHanlder.m | 107 +++++++++++++++++++++++++++ client/{ => ios}/SDL_uikit_main.mm | 71 ++++++------------ 4 files changed, 154 insertions(+), 51 deletions(-) create mode 100644 client/ios/GameChatKeyboardHanlder.h create mode 100644 client/ios/GameChatKeyboardHanlder.m rename client/{ => ios}/SDL_uikit_main.mm (68%) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 62d47278e..42253f6d2 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -147,11 +147,13 @@ set(client_HEADERS if(APPLE_IOS) set(client_SRCS ${client_SRCS} - SDL_uikit_main.mm CFocusableHelper.cpp + ios/GameChatKeyboardHanlder.m + ios/SDL_uikit_main.mm ) set(client_HEADERS ${client_HEADERS} CFocusableHelper.h + ios/GameChatKeyboardHanlder.h ) endif() diff --git a/client/ios/GameChatKeyboardHanlder.h b/client/ios/GameChatKeyboardHanlder.h new file mode 100644 index 000000000..8f4f8e9c2 --- /dev/null +++ b/client/ios/GameChatKeyboardHanlder.h @@ -0,0 +1,23 @@ +/* + * GameChatKeyboardHanlder.h, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ + +#import + +NS_ASSUME_NONNULL_BEGIN + +@interface GameChatKeyboardHanlder : NSObject + +@property (nonatomic, weak) UITextField * textFieldSDL; + +- (void)triggerInput; + +@end + +NS_ASSUME_NONNULL_END diff --git a/client/ios/GameChatKeyboardHanlder.m b/client/ios/GameChatKeyboardHanlder.m new file mode 100644 index 000000000..24336f592 --- /dev/null +++ b/client/ios/GameChatKeyboardHanlder.m @@ -0,0 +1,107 @@ +/* + * GameChatKeyboardHanlder.m, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ + +#import "GameChatKeyboardHanlder.h" + +#include + +static int watchReturnKey(void * userdata, SDL_Event * event); + +static void sendKeyEvent(SDL_KeyCode keyCode) +{ + SDL_Event keyEvent; + keyEvent.key = (SDL_KeyboardEvent){ + .type = SDL_KEYDOWN, + .keysym.sym = keyCode, + }; + SDL_PushEvent(&keyEvent); +} + +static CGRect keyboardFrame(NSNotification * n, NSString * userInfoKey) +{ + return [n.userInfo[userInfoKey] CGRectValue]; +} +static CGRect keyboardFrameBegin(NSNotification * n) { return keyboardFrame(n, UIKeyboardFrameBeginUserInfoKey); } +static CGRect keyboardFrameEnd (NSNotification * n) { return keyboardFrame(n, UIKeyboardFrameEndUserInfoKey); } + + +@interface GameChatKeyboardHanlder () +@property (nonatomic) BOOL wasChatMessageSent; +@end + +@implementation GameChatKeyboardHanlder + +- (void)triggerInput { + __auto_type notificationCenter = NSNotificationCenter.defaultCenter; + [notificationCenter addObserver:self selector:@selector(textDidBeginEditing:) name:UITextFieldTextDidBeginEditingNotification object:nil]; + [notificationCenter addObserver:self selector:@selector(textDidEndEditing:) name:UITextFieldTextDidEndEditingNotification object:nil]; + [notificationCenter addObserver:self selector:@selector(keyboardWillChangeFrame:) name:UIKeyboardWillChangeFrameNotification object:nil]; + [notificationCenter addObserver:self selector:@selector(keyboardDidChangeFrame:) name:UIKeyboardDidChangeFrameNotification object:nil]; + + self.wasChatMessageSent = NO; + sendKeyEvent(SDLK_TAB); +} + +- (void)positionTextFieldAboveKeyboardRect:(CGRect)kbFrame { + __auto_type r = kbFrame; + r.size.height = CGRectGetHeight(self.textFieldSDL.frame); + r.origin.y -= r.size.height; + self.textFieldSDL.frame = r; +} + +#pragma mark - Notifications + +- (void)textDidBeginEditing:(NSNotification *)n { + self.textFieldSDL.hidden = NO; + self.textFieldSDL.text = nil; + + // watch for pressing Return to ignore sending Escape key after keyboard is closed + SDL_AddEventWatch(watchReturnKey, (__bridge void *)self); +} + +- (void)textDidEndEditing:(NSNotification *)n { + [NSNotificationCenter.defaultCenter removeObserver:self]; + self.textFieldSDL.hidden = YES; + + // discard chat message + if(!self.wasChatMessageSent) + sendKeyEvent(SDLK_ESCAPE); +} + +- (void)keyboardWillChangeFrame:(NSNotification *)n { + // animate textfield together with keyboard + [UIView performWithoutAnimation:^{ + [self positionTextFieldAboveKeyboardRect:keyboardFrameBegin(n)]; + }]; + + NSTimeInterval kbAnimationDuration = [n.userInfo[UIKeyboardAnimationDurationUserInfoKey] doubleValue]; + NSUInteger kbAnimationCurve = [n.userInfo[UIKeyboardAnimationCurveUserInfoKey] unsignedIntegerValue]; + [UIView animateWithDuration:kbAnimationDuration delay:0 options:(kbAnimationCurve << 16) animations:^{ + [self positionTextFieldAboveKeyboardRect:keyboardFrameEnd(n)]; + } completion:nil]; +} + +- (void)keyboardDidChangeFrame:(NSNotification *)n { + [self positionTextFieldAboveKeyboardRect:keyboardFrameEnd(n)]; +} + +@end + + +static int watchReturnKey(void * userdata, SDL_Event * event) +{ + if(event->type == SDL_KEYDOWN && event->key.keysym.scancode == SDL_SCANCODE_RETURN) + { + __auto_type self = (__bridge GameChatKeyboardHanlder *)userdata; + self.wasChatMessageSent = YES; + SDL_DelEventWatch(watchReturnKey, userdata); + } + return 1; +} diff --git a/client/SDL_uikit_main.mm b/client/ios/SDL_uikit_main.mm similarity index 68% rename from client/SDL_uikit_main.mm rename to client/ios/SDL_uikit_main.mm index edcf28cc1..b1faee21b 100644 --- a/client/SDL_uikit_main.mm +++ b/client/ios/SDL_uikit_main.mm @@ -13,35 +13,38 @@ #include "CServerHandler.h" #include "CFocusableHelper.h" +#import "GameChatKeyboardHanlder.h" + #import double ios_screenScale() { return UIScreen.mainScreen.nativeScale; } -static int watchReturnKey(void * userdata, SDL_Event * event); - -static void sendKeyEvent(SDL_KeyCode keyCode) -{ - SDL_Event keyEvent; - keyEvent.key = (SDL_KeyboardEvent){ - .type = SDL_KEYDOWN, - .keysym.sym = keyCode, - }; - SDL_PushEvent(&keyEvent); -} - - @interface SDLViewObserver : NSObject -@property (nonatomic) bool wasChatMessageSent; +@property (nonatomic, strong) GameChatKeyboardHanlder * gameChatHandler; @end @implementation SDLViewObserver - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { - UIView * view = [object valueForKey:keyPath]; + UIView * view = [object valueForKeyPath:keyPath]; + + UITextField * textField; + for (UIView * v in view.subviews) { + if ([v isKindOfClass:[UITextField class]]) { + textField = (UITextField *)v; + break; + } + } + + auto r = textField.frame; + r.size.height = 40; + textField.frame = r; + textField.backgroundColor = UIColor.whiteColor; + self.gameChatHandler.textFieldSDL = textField; auto longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)]; - longPress.minimumPressDuration = 0.1; + longPress.minimumPressDuration = 0.2; [view addGestureRecognizer:longPress]; auto pinch = [[UIPinchGestureRecognizer alloc] initWithTarget:self action:@selector(handlePinch:)]; @@ -102,29 +105,7 @@ static void sendKeyEvent(SDL_KeyCode keyCode) - (void)handlePinch:(UIGestureRecognizer *)gesture { if(gesture.state != UIGestureRecognizerStateBegan || CSH->state != EClientState::GAMEPLAY) return; - - // Tab triggers chat message input - self.wasChatMessageSent = false; - [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(handleKeyboardDidShowForGameChat:) name:UIKeyboardDidShowNotification object:nil]; - sendKeyEvent(SDLK_TAB); -} - -#pragma mark - Notifications - -- (void)handleKeyboardDidShowForGameChat:(NSNotification *)n { - [NSNotificationCenter.defaultCenter removeObserver:self name:n.name object:nil]; - - // watch for pressing Return to ignore sending Escape key after keyboard is closed - SDL_AddEventWatch(watchReturnKey, (__bridge void *)self); - [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(handleKeyboardDidHideForGameChat:) name:UIKeyboardDidHideNotification object:nil]; -} - -- (void)handleKeyboardDidHideForGameChat:(NSNotification *)n { - [NSNotificationCenter.defaultCenter removeObserver:self name:n.name object:nil]; - - // discard chat message - if(!self.wasChatMessageSent) - sendKeyEvent(SDLK_ESCAPE); + [self.gameChatHandler triggerInput]; } #pragma mark - UIGestureRecognizerDelegate @@ -146,6 +127,7 @@ main(int argc, char *argv[]) @autoreleasepool { auto observer = [SDLViewObserver new]; + observer.gameChatHandler = [GameChatKeyboardHanlder new]; [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { [UIApplication.sharedApplication.keyWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; }]; @@ -155,14 +137,3 @@ main(int argc, char *argv[]) return SDL_UIKitRunApp(argc, argv, SDL_main); } } - -static int watchReturnKey(void * userdata, SDL_Event * event) -{ - if(event->type == SDL_KEYDOWN && event->key.keysym.scancode == SDL_SCANCODE_RETURN) - { - auto self = (__bridge SDLViewObserver *)userdata; - self.wasChatMessageSent = true; - SDL_DelEventWatch(watchReturnKey, userdata); - } - return 1; -} From bb9d19deeec0524784da8b23b8301520ea739984 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 19 Apr 2021 03:06:24 +0300 Subject: [PATCH 051/131] fix whitespace --- client/CMakeLists.txt | 4 ++-- server/CMakeLists.txt | 5 +++-- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 42253f6d2..c855476c5 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -190,8 +190,8 @@ elseif(APPLE_IOS) "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO -framework Metal -framework OpenGLES -framework AVFoundation -framework GameController -framework CoreMotion" # SDL2_image ) - set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) - configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) + set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) + configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index f526bb41c..ae3de1a98 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -48,8 +48,8 @@ if(WIN32) PROJECT_LABEL "VCMI_server" ) elseif(APPLE_IOS) - set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) - configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) + set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) + configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) set_target_properties(vcmiserver PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" @@ -70,6 +70,7 @@ vcmi_set_output_dir(vcmiserver "") enable_pch(vcmiserver) if(APPLE_IOS) + # TODO: move to a common dir / add macro? add_custom_command(TARGET vcmiserver POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true From 821672a1a4c10b5715bccefffaf473c955b0687d Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 19 Apr 2021 03:34:13 +0300 Subject: [PATCH 052/131] refactor VCMIDirsIOS::dataPaths() --- lib/VCMIDirs.cpp | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index c9f4e3b67..31b4b5dda 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -398,14 +398,16 @@ bfs::path VCMIDirsIOS::userLogsPath() const { return {ios_documentsPath()}; } std::vector VCMIDirsIOS::dataPaths() const { - return { + std::vector paths; + paths.reserve(4); #ifdef VCMI_IOS_SIM - {ios_hostApplicationSupportPath()}, + paths.emplace_back(ios_hostApplicationSupportPath()); #endif - {ios_sharedDataPath()}, - binaryPath(), - userDataPath(), - }; + if (auto sharedDataPath = ios_sharedDataPath()) + paths.emplace_back(sharedDataPath); + paths.emplace_back(binaryPath()); + paths.emplace_back(userDataPath()); + return paths; } bfs::path VCMIDirsIOS::libraryPath() const { return {ios_frameworksPath()}; } From 67ef0c234d3f645e2c63e56f3035f27677aefe50 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 19 Apr 2021 03:38:20 +0300 Subject: [PATCH 053/131] build Qt launcher, launch Client with it kambala-decapitator/vcmi#17 --- CMakeLists.txt | 2 +- client/ios/Info.plist | 9 ++ configure_ios.sh | 5 +- launcher/CMakeLists.txt | 46 ++++++- launcher/ios/Entitlements.in | 10 ++ .../AppIcon.appiconset/Contents.json | 121 ++++++++++++++++++ .../AppIcon.appiconset/Icon-App-20x20@1x.png | Bin 0 -> 507 bytes .../AppIcon.appiconset/Icon-App-20x20@2x.png | Bin 0 -> 783 bytes .../AppIcon.appiconset/Icon-App-20x20@3x.png | Bin 0 -> 1063 bytes .../AppIcon.appiconset/Icon-App-29x29@1x.png | Bin 0 -> 620 bytes .../AppIcon.appiconset/Icon-App-29x29@2x.png | Bin 0 -> 1047 bytes .../AppIcon.appiconset/Icon-App-29x29@3x.png | Bin 0 -> 1462 bytes .../AppIcon.appiconset/Icon-App-40x40@1x.png | Bin 0 -> 783 bytes .../AppIcon.appiconset/Icon-App-40x40@2x.png | Bin 0 -> 1349 bytes .../AppIcon.appiconset/Icon-App-40x40@3x.png | Bin 0 -> 2058 bytes .../AppIcon.appiconset/Icon-App-60x60@2x.png | Bin 0 -> 2058 bytes .../AppIcon.appiconset/Icon-App-60x60@3x.png | Bin 0 -> 3243 bytes .../AppIcon.appiconset/Icon-App-76x76@1x.png | Bin 0 -> 1283 bytes .../AppIcon.appiconset/Icon-App-76x76@2x.png | Bin 0 -> 2788 bytes .../Icon-App-83.5x83.5@2x.png | Bin 0 -> 3159 bytes launcher/ios/Images.xcassets/Contents.json | 6 + launcher/ios/Info.plist | 55 ++++++++ launcher/ios/mainwindow_moc.mm | 25 ++++ launcher/mainwindow_moc.cpp | 3 +- 24 files changed, 271 insertions(+), 11 deletions(-) create mode 100644 launcher/ios/Entitlements.in create mode 100755 launcher/ios/Images.xcassets/AppIcon.appiconset/Contents.json create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png create mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png create mode 100644 launcher/ios/Images.xcassets/Contents.json create mode 100644 launcher/ios/Info.plist create mode 100644 launcher/ios/mainwindow_moc.mm diff --git a/CMakeLists.txt b/CMakeLists.txt index 3e33acdf4..9fe40f525 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -57,10 +57,10 @@ endif() option(ENABLE_ERM "Enable compilation of ERM scripting module" OFF) option(ENABLE_LUA "Enable compilation of LUA scripting module" OFF) +option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) if(APPLE_IOS) set(BUNDLE_IDENTIFIER_PREFIX "" CACHE STRING "Bundle identifier prefix") else() - option(ENABLE_LAUNCHER "Enable compilation of launcher" ON) option(ENABLE_TEST "Enable compilation of unit tests" ON) endif() if(NOT ${CMAKE_VERSION} VERSION_LESS "3.16.0") diff --git a/client/ios/Info.plist b/client/ios/Info.plist index 6fa803087..c81867289 100644 --- a/client/ios/Info.plist +++ b/client/ios/Info.plist @@ -18,6 +18,15 @@ $(MARKETING_VERSION) CFBundleSignature ???? + CFBundleURLTypes + + + CFBundleURLSchemes + + vcmi + + + CFBundleVersion 1 LSRequiresIPhoneOS diff --git a/configure_ios.sh b/configure_ios.sh index de85bd5ac..efa253cd1 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -1,9 +1,10 @@ #!/usr/bin/env bash -boostPrefix=~/dev/other/Apple-Boost-BuildScript/build/boost/1.75.0/ios/debug/prefix +boostPrefix=~/dev/other/Apple-Boost-BuildScript/build-static/boost/1.75.0/ios/debug/prefix ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal-4.4 sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib -prefixPath="$boostPrefix;$ffmpegDir;$sdlLibsDir" +qtDir=~/dev/Qt-libs/5.15.2/ios +prefixPath="$boostPrefix;$ffmpegDir;$sdlLibsDir;$qtDir" # prefixPath="$boostPrefix;$sdlLibsDir" # xcodeMajorVersion=$(xcodebuild -version | fgrep Xcode | cut -d ' ' -f 2 | cut -d . -f 1) diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index e9fd1ec00..4abdb9e97 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -53,6 +53,10 @@ set(launcher_FORMS updatedialog_moc.ui ) +if(APPLE_IOS) + set(launcher_SRCS ${launcher_SRCS} ios/mainwindow_moc.mm) +endif() + assign_source_group(${launcher_SRCS} ${launcher_HEADERS} VCMI_launcher.rc) # Tell CMake to run moc when necessary: @@ -98,6 +102,26 @@ if(APPLE) # This makes Xcode project prettier by moving vcmilauncher_autogen directory into vcmiclient subfolder set_property(GLOBAL PROPERTY AUTOGEN_TARGETS_FOLDER vcmilauncher) endif() +if(APPLE_IOS) + set(CMAKE_EXE_LINKER_FLAGS ${CMAKE_EXE_LINKER_FLAGS} "-Wl,-e,_qt_main_wrapper") + + set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) + configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) + + set_target_properties(vcmilauncher PROPERTIES + MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" + SKIP_BUILD_RPATH 1 + XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES + XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon + XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} + ) + + target_sources(vcmilauncher PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) + set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") + + target_sources(vcmilauncher PRIVATE ios/Images.xcassets) + set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") +endif() target_link_libraries(vcmilauncher vcmi Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network) target_include_directories(vcmilauncher @@ -112,11 +136,19 @@ add_custom_command(TARGET vcmilauncher POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/launcher/icons ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/launcher/icons ) -install(TARGETS vcmilauncher DESTINATION ${BIN_DIR}) -# copy whole directory -install(DIRECTORY icons DESTINATION ${DATA_DIR}/launcher) -# Install icons and desktop file on Linux -if(NOT WIN32 AND NOT APPLE) - install(FILES "vcmilauncher.desktop" DESTINATION share/applications) - install(FILES "eu.vcmi.VCMI.metainfo.xml" DESTINATION share/metainfo) +if(APPLE_IOS) + add_custom_command(TARGET vcmilauncher POST_BUILD + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" + COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true + COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh + ) +else() + install(TARGETS vcmilauncher DESTINATION ${BIN_DIR}) + # copy whole directory + install(DIRECTORY icons DESTINATION ${DATA_DIR}/launcher) + # Install icons and desktop file on Linux + if(NOT WIN32 AND NOT APPLE) + install(FILES "vcmilauncher.desktop" DESTINATION share/applications) + install(FILES "eu.vcmi.VCMI.metainfo.xml" DESTINATION share/metainfo) + endif() endif() diff --git a/launcher/ios/Entitlements.in b/launcher/ios/Entitlements.in new file mode 100644 index 000000000..73367ec6b --- /dev/null +++ b/launcher/ios/Entitlements.in @@ -0,0 +1,10 @@ + + + + + com.apple.security.application-groups + + group.@BUNDLE_IDENTIFIER_PREFIX@.vcmi + + + diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Contents.json b/launcher/ios/Images.xcassets/AppIcon.appiconset/Contents.json new file mode 100755 index 000000000..8122b0a0c --- /dev/null +++ b/launcher/ios/Images.xcassets/AppIcon.appiconset/Contents.json @@ -0,0 +1,121 @@ +{ + "images" : [ + { + "filename" : "Icon-App-20x20@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-20x20@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-29x29@1x.png", + "idiom" : "iphone", + "scale" : "1x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-40x40@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-40x40@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-60x60@2x.png", + "idiom" : "iphone", + "scale" : "2x", + "size" : "60x60" + }, + { + "filename" : "Icon-App-60x60@3x.png", + "idiom" : "iphone", + "scale" : "3x", + "size" : "60x60" + }, + { + "filename" : "Icon-App-20x20@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-20x20@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "20x20" + }, + { + "filename" : "Icon-App-29x29@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-29x29@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "29x29" + }, + { + "filename" : "Icon-App-40x40@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-40x40@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "40x40" + }, + { + "filename" : "Icon-App-76x76@1x.png", + "idiom" : "ipad", + "scale" : "1x", + "size" : "76x76" + }, + { + "filename" : "Icon-App-76x76@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "76x76" + }, + { + "filename" : "Icon-App-83.5x83.5@2x.png", + "idiom" : "ipad", + "scale" : "2x", + "size" : "83.5x83.5" + }, + { + "idiom" : "ios-marketing", + "scale" : "1x", + "size" : "1024x1024" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..488b4844e8063214c8a44f86bac66cb922272761 GIT binary patch literal 507 zcmV4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0OUzTK~#90ZIHb#L{Sulzq9WMgCI!!m3|}Q1%yt#fLf#SKso4vF0?X%X|LHsW((J;Ufj^xO3AP7)^Ea`TDire+o!TD0% zJ8JATPj)W$EtqMs_BnQcxv@HZn%>@wJ}1KPq0PgUmvLt1c8~hkvJt>AwjYPL9_|{o z^{>I!d((5Hb~U^{EqAi1v_8?APrBl-@1O7@$dQmM<}AYbH=W}%ydaA2#8nWXuWFI3 x^oEagU~(aUHyXXQeYQu0vLnZJLCjQ2{s7MATpsM_v@-wz002ovPDHLkV1hb|<%IwM literal 0 HcmV?d00001 diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..fd9e120456cba1cca6e5c222e1a1aea99208e2cb GIT binary patch literal 783 zcmV+q1MvKbP)uk0002eX+uL$Nkc;* zP;zf(X>4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0r*KoK~#90)sjzW6HyR{fAe-XDNU4Wu_diiFenu*+7hW=nuCbwp%M@TFCqv% z_0Xf>&3mC2Q3TPGV6Q^KfX8Z}Q9+GDn>7B35Gqz8((PvV{X8tnCcBlOAUcPIw|sBj z%r_%MXQ4Xe{tM6q0BDK=wf_NxH2mL+6hD`=>e0a$D1n0zfW7GSACY=tU`(w(Rl9q3 zJu@Z%p!g~C@%{F(Zi-){w!WPH44t@Xt9w@m4_Bw+tJ%kFvOb0 z;4B`Xc2t&AT9gvCu|IcB7P3kpkf0vVymV{uKny!8s;Ou|HD*SNjp2rXU{JWhsnXmj zjf;i4C92%q=JlPKJOML~xYZQ|MfaXeCAFTol3RF{Ut#gNb9p$kzEZNwm6972PSnhP zh*nPuJ4QyoE$ZXR_1@)|U71>?XFNgq^<-M&CrH0NO^AY~0SYy?ob}f67Z#VU7YTM; zquG{E-pnT_(=96-`LyWte0j(XbD4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0}x3>K~#90?N(c8R96&Td*69<@-o7V$ZU=geRvJ{0jpdzIrHKmF{^g~S}D3L&Qnu;}=U}kh;lJTCs`jMH5lDSEv z?T4Dhg>&vbcinZ)+Up#y5YG>N0q!XIH6e#GEdfCKI|2YCL@3$Y{&xh#Qx7D6JPiuK zdH+tiOJaTLGT=#~xVtE7iogDjzFU-vb%i4__Diw1I}&;{h7U_(8B+h6$(A)$E1F35 z9GbB!W!hT1rk+rDJW=T!&A01z9df8Cy}pFQW)Lu98*lBDAmETqx#`m8RpvGgmF zsk--!-(zaRjE=uUZjh{~WDXfJeJ&q!*Uaa>19TnbH8kHR>+ac4)%cb^9k@&ZOyeG&N$Gka&G)2 z!^!A7Du8l&8LVL2&7Z~ONKN6O!eq%}-sbo(f|E<3k8h7Hf&dT_np!krj|;WM7bFIi zN(VYMNC1=&pjcD-&7;*%qveZNIt(@zMvwL_WZjl zGni`w@GRM~7SN!i3TRLPAuv)@%%GZ|JVLyr2jELe4h0R+0O&|U^4};^;w@ocD<=*a z(4aM2$^C_Og@waNGe3;!$l8Fh90J{DkHGw)g#*bV9M0@lE@2svwD5?PNl}_nf9*t2 z3WMDarxOxZJ=0KbL8b@A6Y=^t&VLqjiPHzw1q$S!66JnJu}cwJI63&Q=Kt7L0JC2m hqL`!S_9%H+`~!Pd#=_5Hdc^<$002ovPDHLkV1i*6^;!S` literal 0 HcmV?d00001 diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..b51dd2368c497cdba356989701c5bd00e83885bd GIT binary patch literal 620 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 Q-T(jq07*qoM6N<$g6$Nh<^TWy literal 0 HcmV?d00001 diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png new file mode 100644 index 0000000000000000000000000000000000000000..fd9e120456cba1cca6e5c222e1a1aea99208e2cb GIT binary patch literal 783 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 literal 0 HcmV?d00001 diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..5496a82ea6de2b33990f93bd46ed463629fe3dff GIT binary patch literal 2058 zcmV+l2=(`gP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$2J=ZoK~#90?U`$A6xS8U|L4v=yz3VR+Zc?M4VV^CWEvVl;#!4LAi|^$4-+0v zl|s@qZNF5JDphJDNLr~?qDt+DHmD6v)e_9h36Da;qbQ+iL|tKw+8|=tI4LsNV1w7bNXQ)-W~6f-8Gflbk3L6+_`gqbIv{Y%>Ujc!Q_~lB(4p%!8X_i+h7}PgKe-4 z{w#wXmg|_>rGy5G>mWh|0t6K8K6X3tp)u`j?E%V6S93H(EHtrTS->Nq90))mDhxLS zf;kX1s^tP<9|x~@-7F~gO#yBU%##5#hafIz;-C^@U{ud@_alb{WComtR+ke(E!5K3 zX*fh^*0P3h!#`iU#>yz&_EjOU!sR1x`itE(l(&5KoL_i%m?th=9d-p5|HvzGlR@Wy zI!avWtDSx9Qs=M(dTHgtHEyw>CBg2r>~sOBYwn3O3|@E+SbF-7h_Lkkc$W8xeJvli zz5i;BZ)yJX!nfL9R6zcp#fS~TtUm|f(dO=e*?Z+>H&FV=Yj;>I25W=70H=B*?)pl} z{0R8^vU1)13Cg&(H_3iTl~06RpJ25r6~NmEoGo1|Y1aFc*tC zK7}n{a^Q1ofm8ijq^nZLXKoTjAmf#j>Zw|Wrj*h&mTxV;4v-=>dkMPta%}lg$G)W% z&|FFZq%;k15sh0-;|qvTeKA_jMV25_*Qv+Kp&)epRhqM1q6<>7_nSFE05HqH?x7%A~mj&@X!hjAJC)g?8NOY5D1OFJ|fj~#|i<-vIlwr0Q#!M(z!o! zN2q7ds_Nlns80j4yWWGd7fAq!3hsaSAt4A_|3<1ti$xTQN}etN0Mg6ql{9@Ec3E)j zU(b5jI%*nVkSt$}?gJnIg7X)ia54cn+l_+x36)QKpdjp|v35RvcsSy)|MyF3g5#$& zEpSo2hT|Q?5W@cHwNMacwnL^BCiaZxpI*LEWbaMIfY6zXPdoIizyQ{K9#@WmAk_JG zeF+nQU=NU&Yk9@k&qg1$9t9wz@1DPA{1+iTuoBrexG~rbEsp0Odl?_Dymk_T5x z;9!98!R0NEa3Z@30sk;k49bgYCD1scaOv$Q%gp3`(f~son{w&hX5z;CR)pgwULSDV zpK26wY|W#yet^xblImD&l`PtskJoo8#mvl1TI(-2`h-M6 zL#7CT)r%O*YoGwp8D>ZTh!_SCzMmeLu%K3)j~8;BlzQsL+=1`!xS^C%N{t@bQMXJ$ ziu(GA6i8-lro09h1B!-1YIKMcK*aq@`AJLWTXHkyjCW3l#7QM)W6u|Wc|UyXT=S{j zTUWm$rbw{&U;$pfF~VX>XGM*lSh2)IkEbDG&sVk`pISY&K>0do?G1`!AlQ*RQ93B|okTtT~cd#8J6|9|^q8*GDZ zuno4sHrNJFKG=F*{prTBL+S~=^rUI73_TY5q;WXt6d2?x-&~aL)-Z`>=&{gX`>mbl z0nZPNv${9XC?tA|IWtn5M5CY`D(ObYPBPE(djJ3c literal 0 HcmV?d00001 diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png new file mode 100644 index 0000000000000000000000000000000000000000..5d009effd356290dfa8b89196fa77b50a741f317 GIT binary patch literal 3243 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 literal 0 HcmV?d00001 diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..2e61bb999de08fe13d95c304f70ad4646bb4e378 GIT binary patch literal 2788 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 literal 0 HcmV?d00001 diff --git a/launcher/ios/Images.xcassets/Contents.json b/launcher/ios/Images.xcassets/Contents.json new file mode 100644 index 000000000..73c00596a --- /dev/null +++ b/launcher/ios/Images.xcassets/Contents.json @@ -0,0 +1,6 @@ +{ + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/launcher/ios/Info.plist b/launcher/ios/Info.plist new file mode 100644 index 000000000..01c769d73 --- /dev/null +++ b/launcher/ios/Info.plist @@ -0,0 +1,55 @@ + + + + + CFBundleDevelopmentRegion + en + CFBundleExecutable + $(PRODUCT_NAME) + CFBundleIdentifier + $(PRODUCT_BUNDLE_IDENTIFIER) + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + VCMI laucher + CFBundlePackageType + APPL + CFBundleShortVersionString + $(MARKETING_VERSION) + CFBundleSignature + ???? + CFBundleVersion + 1 + LSApplicationQueriesSchemes + + vcmi + + LSRequiresIPhoneOS + + NSAppTransportSecurity + + NSAllowsArbitraryLoads + + + UIFileSharingEnabled + + UILaunchStoryboardName + LaunchScreen + UIRequiredDeviceCapabilities + + armv7 + + UISupportedInterfaceOrientations + + UIInterfaceOrientationLandscapeLeft + UIInterfaceOrientationLandscapeRight + + UISupportedInterfaceOrientations~ipad + + UIInterfaceOrientationLandscapeLeft + UIInterfaceOrientationLandscapeRight + UIInterfaceOrientationPortrait + UIInterfaceOrientationPortraitUpsideDown + + + diff --git a/launcher/ios/mainwindow_moc.mm b/launcher/ios/mainwindow_moc.mm new file mode 100644 index 000000000..7dd80c9fb --- /dev/null +++ b/launcher/ios/mainwindow_moc.mm @@ -0,0 +1,25 @@ +/* + * mainwindow_moc.mm, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ + +#include "../mainwindow_moc.h" + +#import + +void MainWindow::startExecutable(QString /*name*/) +{ + NSString * vcmiScheme = NSBundle.mainBundle.infoDictionary[@"LSApplicationQueriesSchemes"][0]; + [UIApplication.sharedApplication openURL:[NSURL URLWithString:[vcmiScheme stringByAppendingString:@":"]] options:@{} completionHandler:^(BOOL success) { + if (success) + return; + auto alert = [UIAlertController alertControllerWithTitle:@"Can't open VCMI client" message:nil preferredStyle:UIAlertControllerStyleAlert]; + [alert addAction:[UIAlertAction actionWithTitle:@"OK" style:UIAlertActionStyleDefault handler:nil]]; + [UIApplication.sharedApplication.keyWindow.rootViewController presentViewController:alert animated:YES completion:nil]; + }]; +} diff --git a/launcher/mainwindow_moc.cpp b/launcher/mainwindow_moc.cpp index 4aca35f9a..5da5133f2 100644 --- a/launcher/mainwindow_moc.cpp +++ b/launcher/mainwindow_moc.cpp @@ -102,6 +102,7 @@ void MainWindow::on_startGameButton_clicked() startExecutable(pathToQString(VCMIDirs::get().clientPath())); } +#ifndef Q_OS_IOS void MainWindow::startExecutable(QString name) { QProcess process; @@ -119,6 +120,6 @@ void MainWindow::startExecutable(QString name) "Reason: " + process.errorString(), QMessageBox::Ok, QMessageBox::Ok); - return; } } +#endif From 4c848b8f0000f67cb33a03d30c25d5c5b6d53a9b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 20 Apr 2021 00:23:44 +0300 Subject: [PATCH 054/131] fix showing icons in the launcher kambala-decapitator/vcmi#17 --- launcher/CMakeLists.txt | 13 +++++++------ launcher/mainwindow_moc.cpp | 4 ++++ 2 files changed, 11 insertions(+), 6 deletions(-) diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index 4abdb9e97..c8eab5a2e 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -130,19 +130,20 @@ target_include_directories(vcmilauncher vcmi_set_output_dir(vcmilauncher "") enable_pch(vcmilauncher) -# Copy to build directory for easier debugging -add_custom_command(TARGET vcmilauncher POST_BUILD - COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/launcher/icons - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/launcher/icons ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/launcher/icons -) - if(APPLE_IOS) + install(DIRECTORY icons DESTINATION ${DATA_DIR}) add_custom_command(TARGET vcmilauncher POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() + # Copy to build directory for easier debugging + add_custom_command(TARGET vcmilauncher POST_BUILD + COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/launcher/icons + COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/launcher/icons ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/launcher/icons + ) + install(TARGETS vcmilauncher DESTINATION ${BIN_DIR}) # copy whole directory install(DIRECTORY icons DESTINATION ${DATA_DIR}/launcher) diff --git a/launcher/mainwindow_moc.cpp b/launcher/mainwindow_moc.cpp index 5da5133f2..84edd9c52 100644 --- a/launcher/mainwindow_moc.cpp +++ b/launcher/mainwindow_moc.cpp @@ -34,9 +34,13 @@ void MainWindow::load() CResourceHandler::initialize(); CResourceHandler::load("config/filesystem.json"); +#ifdef Q_OS_IOS + QDir::addSearchPath("icons", pathToQString(VCMIDirs::get().binaryPath() / "icons")); +#else for(auto & string : VCMIDirs::get().dataPaths()) QDir::addSearchPath("icons", pathToQString(string / "launcher" / "icons")); QDir::addSearchPath("icons", pathToQString(VCMIDirs::get().userDataPath() / "launcher" / "icons")); +#endif settings.init(); } From 13d0de17cd9d49db58bbad58362c175e9a68dcc0 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 21 Apr 2021 09:54:37 +0300 Subject: [PATCH 055/131] use shared path as user data when available --- lib/VCMIDirs.cpp | 11 +++-------- 1 file changed, 3 insertions(+), 8 deletions(-) diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index 31b4b5dda..7037bf72f 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -388,11 +388,9 @@ class VCMIDirsIOS final : public VCMIDirsApple bfs::path libraryPath() const override; bfs::path binaryPath() const override; - - bool developmentMode() const override; }; -bfs::path VCMIDirsIOS::userDataPath() const { return {ios_documentsPath()}; } +bfs::path VCMIDirsIOS::userDataPath() const { return {ios_sharedDataPath() ?: ios_documentsPath()}; } bfs::path VCMIDirsIOS::userCachePath() const { return {ios_cachesPath()}; } bfs::path VCMIDirsIOS::userLogsPath() const { return {ios_documentsPath()}; } @@ -403,17 +401,14 @@ std::vector VCMIDirsIOS::dataPaths() const #ifdef VCMI_IOS_SIM paths.emplace_back(ios_hostApplicationSupportPath()); #endif - if (auto sharedDataPath = ios_sharedDataPath()) - paths.emplace_back(sharedDataPath); - paths.emplace_back(binaryPath()); paths.emplace_back(userDataPath()); + paths.emplace_back(ios_documentsPath()); + paths.emplace_back(binaryPath()); return paths; } bfs::path VCMIDirsIOS::libraryPath() const { return {ios_frameworksPath()}; } bfs::path VCMIDirsIOS::binaryPath() const { return {ios_bundlePath()}; } - -bool VCMIDirsIOS::developmentMode() const { return false; } #elif defined(VCMI_MAC) class VCMIDirsOSX final : public VCMIDirsApple { From 6652e656c36b38928e0a971cf84a45a682e0162f Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 21 Apr 2021 09:55:13 +0300 Subject: [PATCH 056/131] disable some launcher settings that are useless on iOS kambala-decapitator/vcmi#17 --- launcher/settingsView/csettingsview_moc.cpp | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/launcher/settingsView/csettingsview_moc.cpp b/launcher/settingsView/csettingsview_moc.cpp index 106666988..95c2a872a 100644 --- a/launcher/settingsView/csettingsview_moc.cpp +++ b/launcher/settingsView/csettingsview_moc.cpp @@ -67,9 +67,17 @@ void CSettingsView::loadSettings() int resIndex = ui->comboBoxResolution->findText(QString("%1x%2").arg(resX).arg(resY)); ui->comboBoxResolution->setCurrentIndex(resIndex); - ui->comboBoxFullScreen->setCurrentIndex(settings["video"]["fullscreen"].Bool()); ui->comboBoxShowIntro->setCurrentIndex(settings["video"]["showIntro"].Bool()); + +#ifdef Q_OS_IOS + ui->comboBoxFullScreen->setCurrentIndex(true); + ui->checkBoxFullScreen->setChecked(false); + for (auto widget : std::initializer_list{ui->comboBoxFullScreen, ui->checkBoxFullScreen}) + widget->setDisabled(true); +#else + ui->comboBoxFullScreen->setCurrentIndex(settings["video"]["fullscreen"].Bool()); ui->checkBoxFullScreen->setChecked(settings["video"]["realFullscreen"].Bool()); +#endif int friendlyAIIndex = ui->comboBoxFriendlyAI->findText(QString::fromUtf8(settings["server"]["friendlyAI"].String().c_str())); int neutralAIIndex = ui->comboBoxNeutralAI->findText(QString::fromUtf8(settings["server"]["neutralAI"].String().c_str())); From d0f1275e6133acbb5363fadcf86c4e7445ba32c8 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 23 Nov 2021 10:22:42 +0300 Subject: [PATCH 057/131] add TBB and LuaJIT dependencies --- configure_ios.sh | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/configure_ios.sh b/configure_ios.sh index efa253cd1..f981d49d0 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -4,7 +4,13 @@ boostPrefix=~/dev/other/Apple-Boost-BuildScript/build-static/boost/1.75.0/ios/de ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal-4.4 sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib qtDir=~/dev/Qt-libs/5.15.2/ios -prefixPath="$boostPrefix;$ffmpegDir;$sdlLibsDir;$qtDir" +tbbDir=~/dev/ios/vcmi-ios-deps/oneTBB-2021.4.0/build/install +luajitDir=~/dev/ios/vcmi-ios-deps/LuaJIT-2.1/ios64 +if [[ "$1" ]]; then + tbbDir=~/dev/ios/vcmi-ios-deps/oneTBB-2021.4.0/build-sim/install + luajitDir=~/dev/ios/vcmi-ios-deps/LuaJIT-2.1/sim64 +fi +prefixPath="$boostPrefix;$ffmpegDir;$sdlLibsDir;$qtDir;$tbbDir;$luajitDir" # prefixPath="$boostPrefix;$sdlLibsDir" # xcodeMajorVersion=$(xcodebuild -version | fgrep Xcode | cut -d ' ' -f 2 | cut -d . -f 1) From 9dc5f3ed8bd8f876136a0070ebd308d18fcc8ea8 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 26 Nov 2021 15:49:02 +0300 Subject: [PATCH 058/131] improve RPATH handling, apply RPATH when installing dylibs --- AI/Nullkiller/CMakeLists.txt | 2 +- client/CMakeLists.txt | 3 +-- configure_ios.sh | 5 ++++- launcher/CMakeLists.txt | 3 +-- scripting/erm/CMakeLists.txt | 2 +- scripting/lua/CMakeLists.txt | 2 +- server/CMakeLists.txt | 3 +-- 7 files changed, 10 insertions(+), 10 deletions(-) diff --git a/AI/Nullkiller/CMakeLists.txt b/AI/Nullkiller/CMakeLists.txt index e35e92af2..ddf408ec5 100644 --- a/AI/Nullkiller/CMakeLists.txt +++ b/AI/Nullkiller/CMakeLists.txt @@ -137,4 +137,4 @@ target_link_libraries(Nullkiller PRIVATE TBB::tbb) vcmi_set_output_dir(Nullkiller "AI") enable_pch(Nullkiller) -install(TARGETS Nullkiller RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) +install(TARGETS Nullkiller RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} OPTIONAL) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index c855476c5..f0c76a984 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -195,7 +195,7 @@ elseif(APPLE_IOS) set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" - SKIP_BUILD_RPATH 1 + XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} @@ -229,7 +229,6 @@ enable_pch(vcmiclient) if(APPLE_IOS) add_custom_command(TARGET vcmiclient POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" - COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() diff --git a/configure_ios.sh b/configure_ios.sh index f981d49d0..b9da18092 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -21,9 +21,12 @@ prefixPath="$boostPrefix;$ffmpegDir;$sdlLibsDir;$qtDir;$tbbDir;$luajitDir" # fi srcDir="../vcmi" -cmake "$srcDir" -G Xcode -T buildsystem=1 \ +# cmake "$srcDir" -G Xcode -T buildsystem=1 \ +cmake "$srcDir" -G Xcode \ -DBUNDLE_IDENTIFIER_PREFIX=com.kambala \ + -DENABLE_PCH=OFF \ -Wno-dev \ + -DCMAKE_CXX_COMPILER_LAUNCHER=ccache \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ -DPLATFORM=${1:-OS64} \ -DDEPLOYMENT_TARGET=11.0 \ diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index c8eab5a2e..1ffe3ae9c 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -110,7 +110,7 @@ if(APPLE_IOS) set_target_properties(vcmilauncher PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" - SKIP_BUILD_RPATH 1 + XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} @@ -134,7 +134,6 @@ if(APPLE_IOS) install(DIRECTORY icons DESTINATION ${DATA_DIR}) add_custom_command(TARGET vcmilauncher POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" - COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() diff --git a/scripting/erm/CMakeLists.txt b/scripting/erm/CMakeLists.txt index c691094b7..cb501c2a6 100644 --- a/scripting/erm/CMakeLists.txt +++ b/scripting/erm/CMakeLists.txt @@ -20,4 +20,4 @@ target_link_libraries(vcmiERM Boost::boost vcmi) vcmi_set_output_dir(vcmiERM "scripting") enable_pch(vcmiERM) -install(TARGETS vcmiERM DESTINATION ${SCRIPTING_LIB_DIR}) +install(TARGETS vcmiERM LIBRARY DESTINATION ${SCRIPTING_LIB_DIR} OPTIONAL) diff --git a/scripting/lua/CMakeLists.txt b/scripting/lua/CMakeLists.txt index 1d43aca7a..13c927c8c 100644 --- a/scripting/lua/CMakeLists.txt +++ b/scripting/lua/CMakeLists.txt @@ -45,7 +45,7 @@ target_link_libraries(vcmiLua Boost::boost luajit::luajit vcmi) vcmi_set_output_dir(vcmiLua "scripting") enable_pch(vcmiLua) -install(TARGETS vcmiLua DESTINATION ${SCRIPTING_LIB_DIR}) +install(TARGETS vcmiLua LIBRARY DESTINATION ${SCRIPTING_LIB_DIR} OPTIONAL) #manually copy lua dll from vcpkg folder to build directory on windows since vcpkg deps copy feature has flaws, using hardcoded paths based on vcmi windows deps package 1.1 from github if(MSVC) diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index ae3de1a98..cf6d56e6f 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -53,7 +53,7 @@ elseif(APPLE_IOS) set_target_properties(vcmiserver PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" - SKIP_BUILD_RPATH 1 + XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} @@ -73,7 +73,6 @@ if(APPLE_IOS) # TODO: move to a common dir / add macro? add_custom_command(TARGET vcmiserver POST_BUILD COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" - COMMAND ${CMAKE_INSTALL_NAME_TOOL} -add_rpath @executable_path/Frameworks $ || true COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() From fb32dd0ffcb4fadead4858428b066f3e0087bc43 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 28 Nov 2021 20:46:40 +0300 Subject: [PATCH 059/131] adapt config to new dependencies --- client/CMakeLists.txt | 2 +- configure_ios.sh | 19 ++++++------------- 2 files changed, 7 insertions(+), 14 deletions(-) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index f0c76a984..608f8cf7d 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -187,7 +187,7 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO -framework Metal -framework OpenGLES -framework AVFoundation -framework GameController -framework CoreMotion" # SDL2_image + "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO -framework Metal -framework OpenGLES -framework AVFoundation -framework GameController -framework CoreMotion -weak_framework CoreHaptics" ) set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) diff --git a/configure_ios.sh b/configure_ios.sh index b9da18092..6de2a72e8 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -1,16 +1,13 @@ #!/usr/bin/env bash -boostPrefix=~/dev/other/Apple-Boost-BuildScript/build-static/boost/1.75.0/ios/debug/prefix -ffmpegDir=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal-4.4 -sdlLibsDir=~/dev/ios/vcmi-ios-deps/SDL2-lib +platform=OS64 +globalPrefix=~/dev/vcmi/vcmi-ios-depends/build/iphoneos qtDir=~/dev/Qt-libs/5.15.2/ios -tbbDir=~/dev/ios/vcmi-ios-deps/oneTBB-2021.4.0/build/install -luajitDir=~/dev/ios/vcmi-ios-deps/LuaJIT-2.1/ios64 if [[ "$1" ]]; then - tbbDir=~/dev/ios/vcmi-ios-deps/oneTBB-2021.4.0/build-sim/install - luajitDir=~/dev/ios/vcmi-ios-deps/LuaJIT-2.1/sim64 + platform=SIMULATOR64 + globalPrefix=~/dev/vcmi/vcmi-ios-depends/build/iphonesimulator fi -prefixPath="$boostPrefix;$ffmpegDir;$sdlLibsDir;$qtDir;$tbbDir;$luajitDir" +prefixPath="$globalPrefix;$qtDir" # prefixPath="$boostPrefix;$sdlLibsDir" # xcodeMajorVersion=$(xcodebuild -version | fgrep Xcode | cut -d ' ' -f 2 | cut -d . -f 1) @@ -28,15 +25,11 @@ cmake "$srcDir" -G Xcode \ -Wno-dev \ -DCMAKE_CXX_COMPILER_LAUNCHER=ccache \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ - -DPLATFORM=${1:-OS64} \ + -DPLATFORM=$platform \ -DDEPLOYMENT_TARGET=11.0 \ -DENABLE_BITCODE=0 \ -DCMAKE_BINARY_DIR=$(pwd) \ -DCMAKE_PREFIX_PATH="$prefixPath" \ - -DSDL2_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL/include \ - -DSDL2_IMAGE_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_image-release-2.0.5 \ - -DSDL2_MIXER_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_mixer-release-2.0.4 \ - -DSDL2_TTF_INCLUDE_DIR=~/dev/ios/vcmi-ios-deps/SDL_ttf-release-2.0.15 \ -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY='Apple Development' \ -DCMAKE_XCODE_ATTRIBUTE_DEVELOPMENT_TEAM='4XHN44TEVG' # -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED=NO From 8319c306957dde7373c6ba1bde72fa0554302372 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 2 Dec 2021 13:53:54 +0300 Subject: [PATCH 060/131] copy external TBB dylib to app package --- AI/Nullkiller/CMakeLists.txt | 3 +++ apple_codesign.sh | 6 +++--- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/AI/Nullkiller/CMakeLists.txt b/AI/Nullkiller/CMakeLists.txt index ddf408ec5..43036e7a6 100644 --- a/AI/Nullkiller/CMakeLists.txt +++ b/AI/Nullkiller/CMakeLists.txt @@ -138,3 +138,6 @@ vcmi_set_output_dir(Nullkiller "AI") enable_pch(Nullkiller) install(TARGETS Nullkiller RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} OPTIONAL) +if(APPLE_IOS) + install(IMPORTED_RUNTIME_ARTIFACTS TBB::tbb LIBRARY DESTINATION ${LIB_DIR} OPTIONAL) # CMake 3.21+ +endif() diff --git a/apple_codesign.sh b/apple_codesign.sh index 7dd8a64a3..aa3ba5d8f 100755 --- a/apple_codesign.sh +++ b/apple_codesign.sh @@ -1,10 +1,10 @@ #!/usr/bin/env bash -if [[ "$PLATFORM_NAME" != "iphoneos" ]]; then +if [[ "$PLATFORM_NAME" == *simulator* || -z "$EXPANDED_CODE_SIGN_IDENTITY" ]]; then exit 0 fi echo 'codesign dylibs' -for lib in $(find "$CODESIGNING_FOLDER_PATH/Frameworks" -iname '*.dylib'); do - codesign --force --timestamp=none --sign "$EXPANDED_CODE_SIGN_IDENTITY" "$lib" +for lib in $(find "$CODESIGNING_FOLDER_PATH/Frameworks" -type f -iname '*.dylib'); do + codesign --verbose=4 --force --timestamp=none --sign "$EXPANDED_CODE_SIGN_IDENTITY" "$lib" done From fae295da88d560eb08248e2838997dbc272a8ff0 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 2 Dec 2021 15:02:34 +0300 Subject: [PATCH 061/131] allow building without codesigning --- CMakeLists.txt | 1 + apple_codesign.sh | 2 +- client/CMakeLists.txt | 2 +- launcher/CMakeLists.txt | 2 +- server/CMakeLists.txt | 2 +- 5 files changed, 5 insertions(+), 4 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 9fe40f525..2d853e8d7 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -156,6 +156,7 @@ set(CMAKE_MAP_IMPORTED_CONFIG_RELEASE Release RelWithDebInfo MinSizeRel "") if(APPLE_IOS) set(CMAKE_MACOSX_RPATH 1) set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED NO) + set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED_FOR_APPS YES) set(CMAKE_XCODE_ATTRIBUTE_MARKETING_VERSION ${APP_SHORT_VERSION}) set(CMAKE_XCODE_ATTRIBUTE_PRODUCT_BUNDLE_IDENTIFIER "${BUNDLE_IDENTIFIER_PREFIX}.$(PRODUCT_NAME)") set(SYSTEM_LIBS ${SYSTEM_LIBS} iconv) # boost.locale diff --git a/apple_codesign.sh b/apple_codesign.sh index aa3ba5d8f..9c85eaf68 100755 --- a/apple_codesign.sh +++ b/apple_codesign.sh @@ -1,6 +1,6 @@ #!/usr/bin/env bash -if [[ "$PLATFORM_NAME" == *simulator* || -z "$EXPANDED_CODE_SIGN_IDENTITY" ]]; then +if [[ "$PLATFORM_NAME" == *simulator* || "$CODE_SIGNING_ALLOWED_FOR_APPS" == 'NO' || -z "$EXPANDED_CODE_SIGN_IDENTITY" ]]; then exit 0 fi diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 608f8cf7d..9898da1e8 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -196,7 +196,7 @@ elseif(APPLE_IOS) set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" - XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES + XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED "$(CODE_SIGNING_ALLOWED_FOR_APPS)" XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} ) diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index 1ffe3ae9c..681dbd6e7 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -111,7 +111,7 @@ if(APPLE_IOS) set_target_properties(vcmilauncher PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" - XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES + XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED "$(CODE_SIGNING_ALLOWED_FOR_APPS)" XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} ) diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index cf6d56e6f..4d1c7cab8 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -54,7 +54,7 @@ elseif(APPLE_IOS) set_target_properties(vcmiserver PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" - XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED YES + XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED "$(CODE_SIGNING_ALLOWED_FOR_APPS)" XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} ) From 338858308982a886e7b9804708b538a32eabc4a3 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 12 Dec 2021 23:37:57 +0300 Subject: [PATCH 062/131] use component-based install to copy only what's needed for every app --- AI/BattleAI/CMakeLists.txt | 2 +- AI/Nullkiller/CMakeLists.txt | 4 ++-- AI/StupidAI/CMakeLists.txt | 2 +- AI/VCAI/CMakeLists.txt | 2 +- CMakeLists.txt | 6 +++--- client/CMakeLists.txt | 3 ++- launcher/CMakeLists.txt | 5 +++-- lib/CMakeLists.txt | 17 ++++++++++++++++- server/CMakeLists.txt | 3 +-- 9 files changed, 30 insertions(+), 14 deletions(-) diff --git a/AI/BattleAI/CMakeLists.txt b/AI/BattleAI/CMakeLists.txt index 527ccdcd3..1c0754b4c 100644 --- a/AI/BattleAI/CMakeLists.txt +++ b/AI/BattleAI/CMakeLists.txt @@ -38,4 +38,4 @@ target_link_libraries(BattleAI PRIVATE vcmi) vcmi_set_output_dir(BattleAI "AI") enable_pch(BattleAI) -install(TARGETS BattleAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) +install(TARGETS BattleAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} COMPONENT AI) diff --git a/AI/Nullkiller/CMakeLists.txt b/AI/Nullkiller/CMakeLists.txt index 43036e7a6..beb4ccd0b 100644 --- a/AI/Nullkiller/CMakeLists.txt +++ b/AI/Nullkiller/CMakeLists.txt @@ -137,7 +137,7 @@ target_link_libraries(Nullkiller PRIVATE TBB::tbb) vcmi_set_output_dir(Nullkiller "AI") enable_pch(Nullkiller) -install(TARGETS Nullkiller RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} OPTIONAL) +install(TARGETS Nullkiller RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} COMPONENT AI OPTIONAL) if(APPLE_IOS) - install(IMPORTED_RUNTIME_ARTIFACTS TBB::tbb LIBRARY DESTINATION ${LIB_DIR} OPTIONAL) # CMake 3.21+ + install(IMPORTED_RUNTIME_ARTIFACTS TBB::tbb LIBRARY DESTINATION ${LIB_DIR} COMPONENT AI OPTIONAL) # CMake 3.21+ endif() diff --git a/AI/StupidAI/CMakeLists.txt b/AI/StupidAI/CMakeLists.txt index 1943fa2ff..f99948995 100644 --- a/AI/StupidAI/CMakeLists.txt +++ b/AI/StupidAI/CMakeLists.txt @@ -20,4 +20,4 @@ target_include_directories(StupidAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) vcmi_set_output_dir(StupidAI "AI") enable_pch(StupidAI) -install(TARGETS StupidAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) +install(TARGETS StupidAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} COMPONENT AI) diff --git a/AI/VCAI/CMakeLists.txt b/AI/VCAI/CMakeLists.txt index e96423834..7f16361ba 100644 --- a/AI/VCAI/CMakeLists.txt +++ b/AI/VCAI/CMakeLists.txt @@ -112,4 +112,4 @@ target_link_libraries(VCAI PRIVATE vcmi fuzzylite::fuzzylite) vcmi_set_output_dir(VCAI "AI") enable_pch(VCAI) -install(TARGETS VCAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) +install(TARGETS VCAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} COMPONENT AI) diff --git a/CMakeLists.txt b/CMakeLists.txt index 2d853e8d7..f395b505f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -423,9 +423,9 @@ endif() # Installation section # ####################################### -install(DIRECTORY config DESTINATION ${DATA_DIR}) -install(DIRECTORY scripts DESTINATION ${DATA_DIR}) -install(DIRECTORY Mods DESTINATION ${DATA_DIR}) +install(DIRECTORY config DESTINATION ${DATA_DIR} COMPONENT core) +install(DIRECTORY scripts DESTINATION ${DATA_DIR} COMPONENT core) +install(DIRECTORY Mods DESTINATION ${DATA_DIR} COMPONENT core) # that script is useless for Windows if(NOT WIN32 AND NOT APPLE_IOS) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 9898da1e8..5264233a5 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -228,7 +228,8 @@ enable_pch(vcmiclient) if(APPLE_IOS) add_custom_command(TARGET vcmiclient POST_BUILD - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component core --prefix "$" + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component AI --prefix "$" COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index 681dbd6e7..0d3bcebbb 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -131,9 +131,10 @@ vcmi_set_output_dir(vcmilauncher "") enable_pch(vcmilauncher) if(APPLE_IOS) - install(DIRECTORY icons DESTINATION ${DATA_DIR}) + install(DIRECTORY icons DESTINATION ${DATA_DIR} COMPONENT launcher) add_custom_command(TARGET vcmilauncher POST_BUILD - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component core --prefix "$" + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component launcher --prefix "$" COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt index 35d7d3d38..d21408085 100644 --- a/lib/CMakeLists.txt +++ b/lib/CMakeLists.txt @@ -491,4 +491,19 @@ if(TARGET update_version) add_dependencies(vcmi update_version) endif() -install(TARGETS vcmi RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR}) +install(TARGETS vcmi RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) +if(APPLE_IOS) + get_target_property(LINKED_LIBS vcmi LINK_LIBRARIES) + foreach(LINKED_LIB IN LISTS LINKED_LIBS) + if(TARGET ${LINKED_LIB}) + get_target_property(LIB_TYPE ${LINKED_LIB} TYPE) + if(LIB_TYPE STREQUAL "SHARED_LIBRARY") + install(TARGETS ${LINKED_LIB} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + endif() + else() + if(LINKED_LIB MATCHES "\\${CMAKE_SHARED_LIBRARY_SUFFIX}$") + install(FILES ${LINKED_LIB} DESTINATION ${LIB_DIR} COMPONENT core) + endif() + endif() + endforeach() +endif() diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 4d1c7cab8..95cd7f135 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -33,7 +33,6 @@ if(CMAKE_SYSTEM_NAME MATCHES FreeBSD) set(server_LIBS execinfo ${server_LIBS}) elseif(APPLE_IOS) set(server_LIBS ${server_LIBS} "-framework UIKit") - add_dependencies(vcmiserver BattleAI StupidAI VCAI) endif() target_link_libraries(vcmiserver PRIVATE ${server_LIBS} minizip::minizip) @@ -72,7 +71,7 @@ enable_pch(vcmiserver) if(APPLE_IOS) # TODO: move to a common dir / add macro? add_custom_command(TARGET vcmiserver POST_BUILD - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component core --prefix "$" COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() From d69d2c705fc8804dae991b72ff8d62dc2b79d9d9 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 26 Jun 2022 16:02:01 +0300 Subject: [PATCH 063/131] update cmake iOS toolchain --- configure_ios.sh | 2 +- ios.toolchain.cmake | 258 +++++++++++++++++++++++++++++--------------- 2 files changed, 174 insertions(+), 86 deletions(-) diff --git a/configure_ios.sh b/configure_ios.sh index 6de2a72e8..abcbf70a2 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -27,7 +27,7 @@ cmake "$srcDir" -G Xcode \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ -DPLATFORM=$platform \ -DDEPLOYMENT_TARGET=11.0 \ - -DENABLE_BITCODE=0 \ + -DENABLE_BITCODE=OFF \ -DCMAKE_BINARY_DIR=$(pwd) \ -DCMAKE_PREFIX_PATH="$prefixPath" \ -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY='Apple Development' \ diff --git a/ios.toolchain.cmake b/ios.toolchain.cmake index d6fae99c2..5b6ee87a6 100644 --- a/ios.toolchain.cmake +++ b/ios.toolchain.cmake @@ -1,6 +1,7 @@ # This file is part of the ios-cmake project. It was retrieved from -# https://github.com/gerstrong/ios-cmake.git which is a fork of -# https://github.com/cristeab/ios-cmake.git, which again is a fork of +# https://github.com/leetal/ios-cmake.git, which is a fork of +# https://github.com/gerstrong/ios-cmake.git, which is a fork of +# https://github.com/cristeab/ios-cmake.git, which is a fork of # https://code.google.com/p/ios-cmake/. Which in turn is based off of # the Platform/Darwin.cmake and Platform/UnixPaths.cmake files which # are included with CMake 2.8.4 @@ -50,7 +51,9 @@ # # INFORMATION / HELP # -# The following options control the behaviour of this toolchain: +############################################################################### +# OPTIONS # +############################################################################### # # PLATFORM: (default "OS64") # OS = Build for iPhoneOS. @@ -83,14 +86,18 @@ # # DEPLOYMENT_TARGET: Minimum SDK version to target. Default 2.0 on watchOS and 9.0 on tvOS+iOS # -# ENABLE_BITCODE: (1|0) Enables or disables bitcode support. Default 1 (true) +# NAMED_LANGUAGE_SUPPORT: +# ON (default) = Will require "enable_language(OBJC) and/or enable_language(OBJCXX)" for full OBJC|OBJCXX support +# OFF = Will embed the OBJC and OBJCXX flags into the CMAKE_C_FLAGS and CMAKE_CXX_FLAGS (legacy behaviour, CMake version < 3.16) # -# ENABLE_ARC: (1|0) Enables or disables ARC support. Default 1 (true, ARC enabled by default) +# ENABLE_BITCODE: (ON|OFF) Enables or disables bitcode support. Default ON # -# ENABLE_VISIBILITY: (1|0) Enables or disables symbol visibility support. Default 0 (false, visibility hidden by default) +# ENABLE_ARC: (ON|OFF) Enables or disables ARC support. Default ON (ARC enabled by default) # -# ENABLE_STRICT_TRY_COMPILE: (1|0) Enables or disables strict try_compile() on all Check* directives (will run linker -# to actually check if linking is possible). Default 0 (false, will set CMAKE_TRY_COMPILE_TARGET_TYPE to STATIC_LIBRARY) +# ENABLE_VISIBILITY: (ON|OFF) Enables or disables symbol visibility support. Default OFF (visibility hidden by default) +# +# ENABLE_STRICT_TRY_COMPILE: (ON|OFF) Enables or disables strict try_compile() on all Check* directives (will run linker +# to actually check if linking is possible). Default OFF (will set CMAKE_TRY_COMPILE_TARGET_TYPE to STATIC_LIBRARY) # # ARCHS: (armv7 armv7s armv7k arm64 arm64_32 i386 x86_64) If specified, will override the default architectures for the given PLATFORM # OS = armv7 armv7s arm64 (if applicable) @@ -107,6 +114,12 @@ # MAC_CATALYST = x86_64 # MAC_CATALYST_ARM64 = arm64 # +# NOTE: When manually specifying ARCHS, put a semi-colon between the entries. E.g., -DARCHS="armv7;arm64" +# +############################################################################### +# END OPTIONS # +############################################################################### +# # This toolchain defines the following properties (available via get_property()) for use externally: # # PLATFORM: The currently targeted platform. @@ -131,20 +144,10 @@ cmake_minimum_required(VERSION 3.8.0) # CMake invokes the toolchain file twice during the first build, but only once during subsequent rebuilds. -if(IOS_TOOLCHAIN_HAS_RUN) +if(DEFINED ENV{_IOS_TOOLCHAIN_HAS_RUN}) return() -endif(IOS_TOOLCHAIN_HAS_RUN) -set(IOS_TOOLCHAIN_HAS_RUN true) - -############################################################################### -# OPTIONS # -############################################################################### - -option(DROP_32_BIT "Drops the 32-bit targets universally." YES) - -############################################################################### -# END OPTIONS # -############################################################################### +endif() +set(ENV{_IOS_TOOLCHAIN_HAS_RUN} true) # List of supported platform values list(APPEND _supported_platforms @@ -203,6 +206,10 @@ elseif(NOT DEFINED PLATFORM) message(FATAL_ERROR "PLATFORM argument not set. Bailing configure since I don't know what target you want to build for!") endif () +if(PLATFORM MATCHES ".*COMBINED" AND NOT CMAKE_GENERATOR MATCHES "Xcode") + message(FATAL_ERROR "The combined builds support requires Xcode to be used as generator via '-G Xcode' command-line argument in CMake") +endif() + # Safeguard that the platform value is set and is one of the supported values list(FIND _supported_platforms ${PLATFORM} contains_PLATFORM) if("${contains_PLATFORM}" EQUAL "-1") @@ -227,6 +234,19 @@ set(CMAKE_HAVE_THREADS_LIBRARY 1) set(CMAKE_USE_WIN32_THREADS_INIT 0) set(CMAKE_USE_PTHREADS_INIT 1) +# Specify named language support defaults. +if(NOT DEFINED NAMED_LANGUAGE_SUPPORT AND ${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.16") + set(NAMED_LANGUAGE_SUPPORT ON) + message(STATUS "[DEFAULTS] Using explicit named language support! E.g., enable_language(CXX) is needed in the project files.") +elseif(NOT DEFINED NAMED_LANGUAGE_SUPPORT AND ${CMAKE_VERSION} VERSION_LESS "3.16") + set(NAMED_LANGUAGE_SUPPORT OFF) + message(STATUS "[DEFAULTS] Disabling explicit named language support. Falling back to legacy behaviour.") +elseif(DEFINED NAMED_LANGUAGE_SUPPORT AND ${CMAKE_VERSION} VERSION_LESS "3.16") + message(FATAL_ERROR "CMake named language support for OBJC and OBJCXX was added in CMake 3.16.") +endif() +set(NAMED_LANGUAGE_SUPPORT_INT ${NAMED_LANGUAGE_SUPPORT} CACHE BOOL + "Whether or not to enable explicit named language support" FORCE) + # Specify minimum version of deployment target. if(NOT DEFINED DEPLOYMENT_TARGET) if (PLATFORM MATCHES "WATCHOS") @@ -240,14 +260,14 @@ if(NOT DEFINED DEPLOYMENT_TARGET) set(DEPLOYMENT_TARGET "11.0") elseif(PLATFORM STREQUAL "MAC_CATALYST" OR PLATFORM STREQUAL "MAC_CATALYST_ARM64") # Unless specified, SDK version 13.0 is used by default as minimum target version (mac catalyst minimum requirement). - set(DEPLOYMENT_TARGET "13.0") + set(DEPLOYMENT_TARGET "13.1") else() # Unless specified, SDK version 11.0 is used by default as minimum target version (iOS, tvOS). set(DEPLOYMENT_TARGET "11.0") endif() message(STATUS "[DEFAULTS] Using the default min-version since DEPLOYMENT_TARGET not provided!") -elseif(DEFINED DEPLOYMENT_TARGET AND PLATFORM STREQUAL "MAC_CATALYST" AND ${DEPLOYMENT_TARGET} VERSION_LESS "13.0") - message(FATAL_ERROR "Mac Catalyst builds requires a minimum deployment target of 13.0!") +elseif(DEFINED DEPLOYMENT_TARGET AND PLATFORM MATCHES "^MAC_CATALYST" AND ${DEPLOYMENT_TARGET} VERSION_LESS "13.1") + message(FATAL_ERROR "Mac Catalyst builds requires a minimum deployment target of 13.1!") endif() # Store the DEPLOYMENT_TARGET in the cache @@ -274,26 +294,28 @@ if(PLATFORM_INT STREQUAL "OS") set(SDK_NAME iphoneos) if(NOT ARCHS) set(ARCHS armv7 armv7s arm64) - set(APPLE_TARGET_TRIPLE_INT arm-apple-ios) + set(APPLE_TARGET_TRIPLE_INT arm-apple-ios${DEPLOYMENT_TARGET}) + else() + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}) endif() elseif(PLATFORM_INT STREQUAL "OS64") set(SDK_NAME iphoneos) if(NOT ARCHS) if (XCODE_VERSION_INT VERSION_GREATER 10.0) - set(ARCHS arm64) # Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example + set(ARCHS arm64) # FIXME: Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example else() set(ARCHS arm64) endif() - set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios) + set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios${DEPLOYMENT_TARGET}) else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}) endif() elseif(PLATFORM_INT STREQUAL "OS64COMBINED") set(SDK_NAME iphoneos) if(MODERN_CMAKE) if(NOT ARCHS) if (XCODE_VERSION_INT VERSION_GREATER 10.0) - set(ARCHS arm64 x86_64) # Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example + set(ARCHS arm64 x86_64) # FIXME: Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphoneos*] "arm64") set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphonesimulator*] "x86_64") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphoneos*] "arm64") @@ -305,9 +327,9 @@ elseif(PLATFORM_INT STREQUAL "OS64COMBINED") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphoneos*] "arm64") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphonesimulator*] "x86_64") endif() - set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-ios) + set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-ios${DEPLOYMENT_TARGET}) else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}) endif() else() message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the OS64COMBINED setting work") @@ -316,47 +338,47 @@ elseif(PLATFORM_INT STREQUAL "SIMULATOR") set(SDK_NAME iphonesimulator) if(NOT ARCHS) set(ARCHS i386) - set(APPLE_TARGET_TRIPLE_INT i386-apple-ios) + set(APPLE_TARGET_TRIPLE_INT i386-apple-ios${DEPLOYMENT_TARGET}-simulator) else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-simulator) endif() message(DEPRECATION "SIMULATOR IS DEPRECATED. Consider using SIMULATOR64 instead.") elseif(PLATFORM_INT STREQUAL "SIMULATOR64") set(SDK_NAME iphonesimulator) if(NOT ARCHS) set(ARCHS x86_64) - set(APPLE_TARGET_TRIPLE_INT x86_64-apple-ios) + set(APPLE_TARGET_TRIPLE_INT x86_64-apple-ios${DEPLOYMENT_TARGET}-simulator) else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-simulator) endif() elseif(PLATFORM_INT STREQUAL "SIMULATORARM64") set(SDK_NAME iphonesimulator) if(NOT ARCHS) set(ARCHS arm64) - set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios) + set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios${DEPLOYMENT_TARGET}-simulator) else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-simulator) endif() elseif(PLATFORM_INT STREQUAL "TVOS") set(SDK_NAME appletvos) if(NOT ARCHS) set(ARCHS arm64) - set(APPLE_TARGET_TRIPLE_INT aarch64-apple-tvos) + set(APPLE_TARGET_TRIPLE_INT aarch64-apple-tvos${DEPLOYMENT_TARGET}) else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos${DEPLOYMENT_TARGET}) endif() elseif (PLATFORM_INT STREQUAL "TVOSCOMBINED") set(SDK_NAME appletvos) if(MODERN_CMAKE) if(NOT ARCHS) set(ARCHS arm64 x86_64) - set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-tvos) + set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-tvos${DEPLOYMENT_TARGET}) set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=appletvos*] "arm64") set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=appletvsimulator*] "x86_64") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=appletvos*] "arm64") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=appletvsimulator*] "x86_64") else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos${DEPLOYMENT_TARGET}) endif() else() message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the TVOSCOMBINED setting work") @@ -365,22 +387,22 @@ elseif(PLATFORM_INT STREQUAL "SIMULATOR_TVOS") set(SDK_NAME appletvsimulator) if(NOT ARCHS) set(ARCHS x86_64) - set(APPLE_TARGET_TRIPLE_INT x86_64-apple-tvos) + set(APPLE_TARGET_TRIPLE_INT x86_64-apple-tvos${DEPLOYMENT_TARGET}-simulator) else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos${DEPLOYMENT_TARGET}-simulator) endif() elseif(PLATFORM_INT STREQUAL "WATCHOS") set(SDK_NAME watchos) if(NOT ARCHS) if (XCODE_VERSION_INT VERSION_GREATER 10.0) set(ARCHS armv7k arm64_32) - set(APPLE_TARGET_TRIPLE_INT aarch64_32-apple-watchos) + set(APPLE_TARGET_TRIPLE_INT aarch64_32-apple-watchos${DEPLOYMENT_TARGET}) else() set(ARCHS armv7k) - set(APPLE_TARGET_TRIPLE_INT arm-apple-watchos) + set(APPLE_TARGET_TRIPLE_INT arm-apple-watchos${DEPLOYMENT_TARGET}) endif() else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos${DEPLOYMENT_TARGET}) endif() elseif(PLATFORM_INT STREQUAL "WATCHOSCOMBINED") set(SDK_NAME watchos) @@ -388,21 +410,21 @@ elseif(PLATFORM_INT STREQUAL "WATCHOSCOMBINED") if(NOT ARCHS) if (XCODE_VERSION_INT VERSION_GREATER 10.0) set(ARCHS armv7k arm64_32 i386) - set(APPLE_TARGET_TRIPLE_INT aarch64_32-i386-apple-watchos) + set(APPLE_TARGET_TRIPLE_INT aarch64_32-i386-apple-watchos${DEPLOYMENT_TARGET}) set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchos*] "armv7k arm64_32") set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchsimulator*] "i386") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchos*] "armv7k arm64_32") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchsimulator*] "i386") else() set(ARCHS armv7k i386) - set(APPLE_TARGET_TRIPLE_INT arm-i386-apple-watchos) + set(APPLE_TARGET_TRIPLE_INT arm-i386-apple-watchos${DEPLOYMENT_TARGET}) set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchos*] "armv7k") set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchsimulator*] "i386") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchos*] "armv7k") set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchsimulator*] "i386") endif() else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos${DEPLOYMENT_TARGET}) endif() else() message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the WATCHOSCOMBINED setting work") @@ -411,9 +433,9 @@ elseif(PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") set(SDK_NAME watchsimulator) if(NOT ARCHS) set(ARCHS i386) - set(APPLE_TARGET_TRIPLE_INT i386-apple-watchos) + set(APPLE_TARGET_TRIPLE_INT i386-apple-watchos${DEPLOYMENT_TARGET}-simulator) else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos${DEPLOYMENT_TARGET}-simulator) endif() elseif(PLATFORM_INT STREQUAL "MAC" OR PLATFORM_INT STREQUAL "MAC_CATALYST") set(SDK_NAME macosx) @@ -422,7 +444,7 @@ elseif(PLATFORM_INT STREQUAL "MAC" OR PLATFORM_INT STREQUAL "MAC_CATALYST") endif() string(REPLACE ";" "-" ARCHS_SPLIT "${ARCHS}") if(PLATFORM_INT STREQUAL "MAC") - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-macosx) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-macosx${DEPLOYMENT_TARGET}) elseif(PLATFORM_INT STREQUAL "MAC_CATALYST") set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-macabi) endif() @@ -433,7 +455,7 @@ elseif(PLATFORM_INT MATCHES "^(MAC_ARM64)$|^(MAC_CATALYST_ARM64)$") endif() string(REPLACE ";" "-" ARCHS_SPLIT "${ARCHS}") if(PLATFORM_INT STREQUAL "MAC_ARM64") - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-macosx) + set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-macosx${DEPLOYMENT_TARGET}) elseif(PLATFORM_INT STREQUAL "MAC_CATALYST_ARM64") set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-macabi) endif() @@ -441,11 +463,13 @@ else() message(FATAL_ERROR "Invalid PLATFORM: ${PLATFORM_INT}") endif() +string(REPLACE ";" " " ARCHS_SPACED "${ARCHS}") + if(MODERN_CMAKE AND PLATFORM_INT MATCHES ".*COMBINED" AND NOT CMAKE_GENERATOR MATCHES "Xcode") message(FATAL_ERROR "The COMBINED options only work with Xcode generator, -G Xcode") endif() -if(CMAKE_GENERATOR MATCHES "Xcode" AND PLATFORM_INT MATCHES "MAC_CATALYST_.*") +if(CMAKE_GENERATOR MATCHES "Xcode" AND PLATFORM_INT MATCHES "^MAC_CATALYST") set(CMAKE_XCODE_ATTRIBUTE_CLANG_CXX_LIBRARY "libc++") set(CMAKE_XCODE_ATTRIBUTE_SUPPORTED_PLATFORMS "macosx") set(CMAKE_XCODE_EFFECTIVE_PLATFORMS "-maccatalyst") @@ -455,10 +479,11 @@ if(CMAKE_GENERATOR MATCHES "Xcode" AND PLATFORM_INT MATCHES "MAC_CATALYST_.*") set(CMAKE_XCODE_ATTRIBUTE_MACOSX_DEPLOYMENT_TARGET "${MACOSX_DEPLOYMENT_TARGET}") endif() elseif(CMAKE_GENERATOR MATCHES "Xcode") + set(CMAKE_XCODE_ATTRIBUTE_CLANG_CXX_LIBRARY "libc++") set(CMAKE_XCODE_ATTRIBUTE_IPHONEOS_DEPLOYMENT_TARGET "${DEPLOYMENT_TARGET}") if(NOT PLATFORM_INT MATCHES ".*COMBINED") - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=${SDK_NAME}*] "${ARCHS}") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=${SDK_NAME}*] "${ARCHS}") + set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=${SDK_NAME}*] "${ARCHS_SPACED}") + set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=${SDK_NAME}*] "${ARCHS_SPACED}") endif() endif() @@ -492,31 +517,31 @@ endif() if(NOT DEFINED ENABLE_BITCODE AND NOT ARCHS MATCHES "((^|;|, )(i386|x86_64))+") # Unless specified, enable bitcode support by default message(STATUS "[DEFAULTS] Enabling bitcode support by default. ENABLE_BITCODE not provided!") - set(ENABLE_BITCODE TRUE) + set(ENABLE_BITCODE ON) elseif(NOT DEFINED ENABLE_BITCODE) message(STATUS "[DEFAULTS] Disabling bitcode support by default on simulators. ENABLE_BITCODE not provided for override!") - set(ENABLE_BITCODE FALSE) + set(ENABLE_BITCODE OFF) endif() set(ENABLE_BITCODE_INT ${ENABLE_BITCODE} CACHE BOOL "Whether or not to enable bitcode" FORCE) # Use ARC or not if(NOT DEFINED ENABLE_ARC) # Unless specified, enable ARC support by default - set(ENABLE_ARC TRUE) + set(ENABLE_ARC ON) message(STATUS "[DEFAULTS] Enabling ARC support by default. ENABLE_ARC not provided!") endif() set(ENABLE_ARC_INT ${ENABLE_ARC} CACHE BOOL "Whether or not to enable ARC" FORCE) # Use hidden visibility or not if(NOT DEFINED ENABLE_VISIBILITY) # Unless specified, disable symbols visibility by default - set(ENABLE_VISIBILITY FALSE) + set(ENABLE_VISIBILITY OFF) message(STATUS "[DEFAULTS] Hiding symbols visibility by default. ENABLE_VISIBILITY not provided!") endif() set(ENABLE_VISIBILITY_INT ${ENABLE_VISIBILITY} CACHE BOOL "Whether or not to hide symbols from the dynamic linker (-fvisibility=hidden)" FORCE) # Set strict compiler checks or not if(NOT DEFINED ENABLE_STRICT_TRY_COMPILE) # Unless specified, disable strict try_compile() - set(ENABLE_STRICT_TRY_COMPILE FALSE) + set(ENABLE_STRICT_TRY_COMPILE OFF) message(STATUS "[DEFAULTS] Using NON-strict compiler checks by default. ENABLE_STRICT_TRY_COMPILE not provided!") endif() set(ENABLE_STRICT_TRY_COMPILE_INT ${ENABLE_STRICT_TRY_COMPILE} CACHE BOOL @@ -553,11 +578,13 @@ if(DEFINED CMAKE_C_COMPILER) set(ENV{_CMAKE_C_COMPILER} "${CMAKE_C_COMPILER}") elseif(DEFINED ENV{_CMAKE_C_COMPILER}) set(CMAKE_C_COMPILER "$ENV{_CMAKE_C_COMPILER}") + set(CMAKE_ASM_COMPILER ${CMAKE_C_COMPILER}) elseif(NOT DEFINED CMAKE_C_COMPILER) execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find clang OUTPUT_VARIABLE CMAKE_C_COMPILER ERROR_QUIET OUTPUT_STRIP_TRAILING_WHITESPACE) + set(CMAKE_ASM_COMPILER ${CMAKE_C_COMPILER}) endif() if(DEFINED CMAKE_CXX_COMPILER) # Environment variables are always preserved. @@ -619,7 +646,6 @@ if(MODERN_CMAKE) if(PLATFORM_INT MATCHES ".*COMBINED") set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH "NO") set(CMAKE_IOS_INSTALL_COMBINED YES) - message(STATUS "Will combine built (static) artifacts into FAT lib...") endif() elseif(NOT DEFINED CMAKE_SYSTEM_NAME AND ${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.10") # Legacy code path prior to CMake 3.14 or fallback if no CMAKE_SYSTEM_NAME specified @@ -630,16 +656,16 @@ elseif(NOT DEFINED CMAKE_SYSTEM_NAME) endif() # Standard settings. set(CMAKE_SYSTEM_VERSION ${SDK_VERSION} CACHE INTERNAL "") -set(UNIX TRUE CACHE BOOL "") -set(APPLE TRUE CACHE BOOL "") +set(UNIX ON CACHE BOOL "") +set(APPLE ON CACHE BOOL "") if(PLATFORM STREQUAL "MAC" OR PLATFORM STREQUAL "MAC_ARM64") - set(IOS FALSE CACHE BOOL "") - set(MACOS TRUE CACHE BOOL "") + set(IOS OFF CACHE BOOL "") + set(MACOS ON CACHE BOOL "") elseif(PLATFORM STREQUAL "MAC_CATALYST" OR PLATFORM STREQUAL "MAC_CATALYST_ARM64") - set(IOS TRUE CACHE BOOL "") - set(MACOS TRUE CACHE BOOL "") + set(IOS ON CACHE BOOL "") + set(MACOS ON CACHE BOOL "") else() - set(IOS TRUE CACHE BOOL "") + set(IOS ON CACHE BOOL "") endif() set(CMAKE_AR ar CACHE FILEPATH "" FORCE) set(CMAKE_RANLIB ranlib CACHE FILEPATH "" FORCE) @@ -715,17 +741,20 @@ if(${CMAKE_VERSION} VERSION_LESS "3.11") set(SDK_NAME_VERSION_FLAGS "-mios-simulator-version-min=${DEPLOYMENT_TARGET}") endif() -elseif(NOT PLATFORM_INT STREQUAL "MAC_CATALYST") +elseif(NOT PLATFORM_INT MATCHES "^MAC_CATALYST") # Newer versions of CMake sets the version min flags correctly, skip this for Mac Catalyst targets set(CMAKE_OSX_DEPLOYMENT_TARGET ${DEPLOYMENT_TARGET}) endif() if(DEFINED APPLE_TARGET_TRIPLE_INT) set(APPLE_TARGET_TRIPLE ${APPLE_TARGET_TRIPLE_INT} CACHE INTERNAL "") + set(CMAKE_C_COMPILER_TARGET ${APPLE_TARGET_TRIPLE}) + set(CMAKE_CXX_COMPILER_TARGET ${APPLE_TARGET_TRIPLE}) + set(CMAKE_ASM_COMPILER_TARGET ${APPLE_TARGET_TRIPLE}) endif() -if(PLATFORM_INT STREQUAL "MAC_CATALYST") - set(C_TARGET_FLAGS "-target ${APPLE_TARGET_TRIPLE_INT} -isystem ${CMAKE_OSX_SYSROOT_INT}/System/iOSSupport/usr/include") +if(PLATFORM_INT MATCHES "^MAC_CATALYST") + set(C_TARGET_FLAGS "-isystem ${CMAKE_OSX_SYSROOT_INT}/System/iOSSupport/usr/include -iframework ${CMAKE_OSX_SYSROOT_INT}/System/iOSSupport/System/Library/Frameworks") endif() if(ENABLE_BITCODE_INT) @@ -745,6 +774,14 @@ else() set(CMAKE_XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC "NO") endif() +if(NAMED_LANGUAGE_SUPPORT_INT) + set(OBJC_VARS "-fobjc-abi-version=2 -DOBJC_OLD_DISPATCH_PROTOTYPES=0") + set(OBJC_LEGACY_VARS "") +else() + set(OBJC_VARS "") + set(OBJC_LEGACY_VARS "-fobjc-abi-version=2 -DOBJC_OLD_DISPATCH_PROTOTYPES=0") +endif() + if(NOT ENABLE_VISIBILITY_INT) foreach(lang ${languages}) set(CMAKE_${lang}_VISIBILITY_PRESET "hidden" CACHE INTERNAL "") @@ -759,20 +796,43 @@ else() set(VISIBILITY "-fvisibility=default") endif() +if(DEFINED APPLE_TARGET_TRIPLE) + set(APPLE_TARGET_TRIPLE_FLAG "-target ${APPLE_TARGET_TRIPLE}") +endif() + #Check if Xcode generator is used, since that will handle these flags automagically if(CMAKE_GENERATOR MATCHES "Xcode") - message(STATUS "Not setting any manual command-line buildflags, since Xcode is selected as generator.") + message(STATUS "Not setting any manual command-line buildflags, since Xcode is selected as generator. Modifying the Xcode build-settings directly instead.") else() - # Hidden visibility is required for C++ on iOS. - set(CMAKE_C_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} ${BITCODE} -fobjc-abi-version=2 ${FOBJC_ARC} ${CMAKE_C_FLAGS}") - set(CMAKE_CXX_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} ${BITCODE} ${VISIBILITY} -fobjc-abi-version=2 ${FOBJC_ARC} ${CMAKE_CXX_FLAGS}") - set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS} -O0 -g ${CMAKE_CXX_FLAGS_DEBUG}") - set(CMAKE_CXX_FLAGS_MINSIZEREL "${CMAKE_CXX_FLAGS} -DNDEBUG -Os -ffast-math ${CMAKE_CXX_FLAGS_MINSIZEREL}") - set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS} -DNDEBUG -O2 -g -ffast-math ${CMAKE_CXX_FLAGS_RELWITHDEBINFO}") - set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS} -DNDEBUG -O3 -ffast-math ${CMAKE_CXX_FLAGS_RELEASE}") + set(CMAKE_C_FLAGS "${C_TARGET_FLAGS} ${APPLE_TARGET_TRIPLE_FLAG} ${SDK_NAME_VERSION_FLAGS} ${OBJC_LEGACY_VARS} ${BITCODE} ${VISIBILITY} ${CMAKE_C_FLAGS}") + set(CMAKE_C_FLAGS_DEBUG "-O0 -g ${CMAKE_C_FLAGS_DEBUG}") + set(CMAKE_C_FLAGS_MINSIZEREL "-DNDEBUG -Os ${CMAKE_C_FLAGS_MINSIZEREL}") + set(CMAKE_C_FLAGS_RELWITHDEBINFO "-DNDEBUG -O2 -g ${CMAKE_C_FLAGS_RELWITHDEBINFO}") + set(CMAKE_C_FLAGS_RELEASE "-DNDEBUG -O3 ${CMAKE_C_FLAGS_RELEASE}") + set(CMAKE_CXX_FLAGS "${C_TARGET_FLAGS} ${APPLE_TARGET_TRIPLE_FLAG} ${SDK_NAME_VERSION_FLAGS} ${OBJC_LEGACY_VARS} ${BITCODE} ${VISIBILITY} ${CMAKE_CXX_FLAGS}") + set(CMAKE_CXX_FLAGS_DEBUG "-O0 -g ${CMAKE_CXX_FLAGS_DEBUG}") + set(CMAKE_CXX_FLAGS_MINSIZEREL "-DNDEBUG -Os ${CMAKE_CXX_FLAGS_MINSIZEREL}") + set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "-DNDEBUG -O2 -g ${CMAKE_CXX_FLAGS_RELWITHDEBINFO}") + set(CMAKE_CXX_FLAGS_RELEASE "-DNDEBUG -O3 ${CMAKE_CXX_FLAGS_RELEASE}") + if(NAMED_LANGUAGE_SUPPORT_INT) + set(CMAKE_OBJC_FLAGS "${C_TARGET_FLAGS} ${APPLE_TARGET_TRIPLE_FLAG} ${SDK_NAME_VERSION_FLAGS} ${BITCODE} ${VISIBILITY} ${FOBJC_ARC} ${OBJC_VARS} ${CMAKE_OBJC_FLAGS}") + set(CMAKE_OBJC_FLAGS_DEBUG "-O0 -g ${CMAKE_OBJC_FLAGS_DEBUG}") + set(CMAKE_OBJC_FLAGS_MINSIZEREL "-DNDEBUG -Os ${CMAKE_OBJC_FLAGS_MINSIZEREL}") + set(CMAKE_OBJC_FLAGS_RELWITHDEBINFO "-DNDEBUG -O2 -g ${CMAKE_OBJC_FLAGS_RELWITHDEBINFO}") + set(CMAKE_OBJC_FLAGS_RELEASE "-DNDEBUG -O3 ${CMAKE_OBJC_FLAGS_RELEASE}") + set(CMAKE_OBJCXX_FLAGS "${C_TARGET_FLAGS} ${APPLE_TARGET_TRIPLE_FLAG} ${SDK_NAME_VERSION_FLAGS} ${BITCODE} ${VISIBILITY} ${FOBJC_ARC} ${OBJC_VARS} ${CMAKE_OBJCXX_FLAGS}") + set(CMAKE_OBJCXX_FLAGS_DEBUG "-O0 -g ${CMAKE_OBJCXX_FLAGS_DEBUG}") + set(CMAKE_OBJCXX_FLAGS_MINSIZEREL "-DNDEBUG -Os ${CMAKE_OBJCXX_FLAGS_MINSIZEREL}") + set(CMAKE_OBJCXX_FLAGS_RELWITHDEBINFO "-DNDEBUG -O2 -g ${CMAKE_OBJCXX_FLAGS_RELWITHDEBINFO}") + set(CMAKE_OBJCXX_FLAGS_RELEASE "-DNDEBUG -O3 ${CMAKE_OBJCXX_FLAGS_RELEASE}") + endif() set(CMAKE_C_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_C_LINK_FLAGS}") set(CMAKE_CXX_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_CXX_LINK_FLAGS}") - set(CMAKE_ASM_FLAGS "${CMAKE_C_FLAGS} -x assembler-with-cpp -arch ${CMAKE_OSX_ARCHITECTURES}") + if(NAMED_LANGUAGE_SUPPORT_INT) + set(CMAKE_OBJC_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_OBJC_LINK_FLAGS}") + set(CMAKE_OBJCXX_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_OBJCXX_LINK_FLAGS}") + endif() + set(CMAKE_ASM_FLAGS "${CMAKE_C_FLAGS} -x assembler-with-cpp -arch ${CMAKE_OSX_ARCHITECTURES} ${APPLE_TARGET_TRIPLE_FLAG}") endif() ## Print status messages to inform of the current state @@ -789,6 +849,9 @@ message(STATUS "Using minimum deployment version: ${DEPLOYMENT_TARGET}" " (SDK version: ${SDK_VERSION})") if(MODERN_CMAKE) message(STATUS "Merging integrated CMake 3.14+ iOS,tvOS,watchOS,macOS toolchain(s) with this toolchain!") + if(PLATFORM_INT MATCHES ".*COMBINED") + message(STATUS "Will combine built (static) artifacts into FAT lib...") + endif() endif() if(CMAKE_GENERATOR MATCHES "Xcode") message(STATUS "Using Xcode version: ${XCODE_VERSION_INT}") @@ -828,16 +891,24 @@ set(CMAKE_TRY_COMPILE_PLATFORM_VARIABLES PLATFORM XCODE_VERSION_INT SDK_VERSION + NAMED_LANGUAGE_SUPPORT DEPLOYMENT_TARGET CMAKE_DEVELOPER_ROOT CMAKE_OSX_SYSROOT_INT ENABLE_BITCODE ENABLE_ARC + CMAKE_ASM_COMPILER CMAKE_C_COMPILER + CMAKE_C_COMPILER_TARGET CMAKE_CXX_COMPILER + CMAKE_CXX_COMPILER_TARGET BUILD_LIBTOOL CMAKE_INSTALL_NAME_TOOL CMAKE_C_FLAGS + CMAKE_C_DEBUG + CMAKE_C_MINSIZEREL + CMAKE_C_RELWITHDEBINFO + CMAKE_C_RELEASE CMAKE_CXX_FLAGS CMAKE_CXX_FLAGS_DEBUG CMAKE_CXX_FLAGS_MINSIZEREL @@ -846,7 +917,24 @@ set(CMAKE_TRY_COMPILE_PLATFORM_VARIABLES CMAKE_C_LINK_FLAGS CMAKE_CXX_LINK_FLAGS CMAKE_ASM_FLAGS - ) +) + +if(NAMED_LANGUAGE_SUPPORT_INT) + list(APPEND CMAKE_TRY_COMPILE_PLATFORM_VARIABLES + CMAKE_OBJC_FLAGS + CMAKE_OBJC_DEBUG + CMAKE_OBJC_MINSIZEREL + CMAKE_OBJC_RELWITHDEBINFO + CMAKE_OBJC_RELEASE + CMAKE_OBJCXX_FLAGS + CMAKE_OBJCXX_DEBUG + CMAKE_OBJCXX_MINSIZEREL + CMAKE_OBJCXX_RELWITHDEBINFO + CMAKE_OBJCXX_RELEASE + CMAKE_OBJC_LINK_FLAGS + CMAKE_OBJCXX_LINK_FLAGS + ) +endif() set(CMAKE_PLATFORM_HAS_INSTALLNAME 1) set(CMAKE_SHARED_LINKER_FLAGS "-rpath @executable_path/Frameworks -rpath @loader_path/Frameworks") @@ -859,7 +947,7 @@ set(CMAKE_SHARED_LIBRARY_SONAME_C_FLAG "-install_name") # Set the find root to the SDK developer roots. # Note: CMAKE_FIND_ROOT_PATH is only useful when cross-compiling. Thus, do not set on macOS builds. -if(NOT PLATFORM_INT STREQUAL "MAC" AND NOT PLATFORM_INT STREQUAL "MAC_ARM64") +if(NOT PLATFORM_INT MATCHES "^MAC.*$") list(APPEND CMAKE_FIND_ROOT_PATH "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") set(CMAKE_IGNORE_PATH "/System/Library/Frameworks;/usr/local/lib" CACHE INTERNAL "") endif() @@ -868,7 +956,7 @@ endif() set(CMAKE_FIND_FRAMEWORK FIRST) # Set up the default search directories for frameworks. -if(PLATFORM_INT MATCHES "MAC_CATALYST.*") +if(PLATFORM_INT MATCHES "^MAC_CATALYST") set(CMAKE_FRAMEWORK_PATH ${CMAKE_DEVELOPER_ROOT}/Library/PrivateFrameworks ${CMAKE_OSX_SYSROOT_INT}/System/Library/Frameworks @@ -915,8 +1003,8 @@ macro(find_host_package) set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY NEVER) set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE NEVER) set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE NEVER) - set(IOS FALSE) set(_TOOLCHAIN_IOS ${IOS}) + set(IOS OFF) find_package(${ARGN}) set(IOS ${_TOOLCHAIN_IOS}) set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH) From 27551a9eaef9b1646cf7abd4f28785096700c94a Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 26 Jun 2022 16:02:50 +0300 Subject: [PATCH 064/131] fix using local minizip after rebase --- configure_ios.sh | 2 +- lib/CMakeLists.txt | 8 +++++++- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/configure_ios.sh b/configure_ios.sh index abcbf70a2..c6b56c25f 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -20,8 +20,8 @@ prefixPath="$globalPrefix;$qtDir" srcDir="../vcmi" # cmake "$srcDir" -G Xcode -T buildsystem=1 \ cmake "$srcDir" -G Xcode \ + -DFORCE_BUNDLED_MINIZIP=ON \ -DBUNDLE_IDENTIFIER_PREFIX=com.kambala \ - -DENABLE_PCH=OFF \ -Wno-dev \ -DCMAKE_CXX_COMPILER_LAUNCHER=ccache \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt index d21408085..62da10ae9 100644 --- a/lib/CMakeLists.txt +++ b/lib/CMakeLists.txt @@ -498,7 +498,13 @@ if(APPLE_IOS) if(TARGET ${LINKED_LIB}) get_target_property(LIB_TYPE ${LINKED_LIB} TYPE) if(LIB_TYPE STREQUAL "SHARED_LIBRARY") - install(TARGETS ${LINKED_LIB} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + get_target_property(_aliased ${LINKED_LIB} ALIASED_TARGET) + if(_aliased) + set(LINKED_LIB_REAL ${_aliased}) + else() + set(LINKED_LIB_REAL ${LINKED_LIB}) + endif() + install(TARGETS ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) endif() else() if(LINKED_LIB MATCHES "\\${CMAKE_SHARED_LIBRARY_SUFFIX}$") From ede9f33328566227aaca08546cf06eaad87d984f Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 27 Jun 2022 13:01:23 +0300 Subject: [PATCH 065/131] fix linking with FFmpeg --- CMakeLists.txt | 7 ++++++- client/CMakeLists.txt | 20 ++++++++++++++++++-- 2 files changed, 24 insertions(+), 3 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index f395b505f..885cabff9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -279,7 +279,12 @@ endif() # set(ZLIB_LIBRARIES "-lz") # endif() -find_package(ffmpeg COMPONENTS avutil swscale avformat avcodec) +set(FFMPEG_COMPONENTS avutil swscale avformat avcodec) +if(APPLE_IOS) + list(APPEND FFMPEG_COMPONENTS swresample) +endif() +find_package(ffmpeg COMPONENTS ${FFMPEG_COMPONENTS}) + option(FORCE_BUNDLED_MINIZIP "Force bundled Minizip library" OFF) if(NOT FORCE_BUNDLED_MINIZIP) find_package(minizip) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 5264233a5..95f05c45d 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -187,7 +187,23 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - "-framework Foundation -framework UIKit -framework QuartzCore -framework CoreGraphics -framework CoreServices -framework ImageIO -framework Metal -framework OpenGLES -framework AVFoundation -framework GameController -framework CoreMotion -weak_framework CoreHaptics" + "-lbz2" + "-framework AudioToolbox" + "-framework AVFoundation" + "-framework CoreGraphics" + "-framework CoreMedia" + "-framework CoreMotion" + "-framework CoreServices" + "-framework CoreVideo" + "-framework Foundation" + "-framework GameController" + "-framework ImageIO" + "-framework Metal" + "-framework OpenGLES" + "-framework QuartzCore" + "-framework UIKit" + "-framework VideoToolbox" + "-weak_framework CoreHaptics" ) set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) @@ -214,7 +230,7 @@ target_link_libraries(vcmiclient PRIVATE if(ffmpeg_LIBRARIES) target_link_libraries(vcmiclient PRIVATE - ffmpeg::swscale ffmpeg::avutil ffmpeg::avcodec ffmpeg::avformat + ${ffmpeg_LIBRARIES} ) else() target_compile_definitions(vcmiclient PRIVATE DISABLE_VIDEO) From 1319c8f19764351cfb8f598af4494d6999eb1caa Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 27 Jun 2022 13:02:39 +0300 Subject: [PATCH 066/131] fix building Client with the latest cmake for some reason cmake injects compile flag to Client's resources which breaks ibtool call --- client/LaunchScreen.storyboard | 2 +- configure_ios.sh | 8 +++++++- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/client/LaunchScreen.storyboard b/client/LaunchScreen.storyboard index ea997175d..14b2fa354 100644 --- a/client/LaunchScreen.storyboard +++ b/client/LaunchScreen.storyboard @@ -2,7 +2,7 @@ - + diff --git a/configure_ios.sh b/configure_ios.sh index c6b56c25f..c57500617 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -26,10 +26,16 @@ cmake "$srcDir" -G Xcode \ -DCMAKE_CXX_COMPILER_LAUNCHER=ccache \ -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ -DPLATFORM=$platform \ - -DDEPLOYMENT_TARGET=11.0 \ + -DDEPLOYMENT_TARGET=12.0 \ -DENABLE_BITCODE=OFF \ -DCMAKE_BINARY_DIR=$(pwd) \ -DCMAKE_PREFIX_PATH="$prefixPath" \ -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY='Apple Development' \ -DCMAKE_XCODE_ATTRIBUTE_DEVELOPMENT_TEAM='4XHN44TEVG' # -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED=NO + +# workaround strange cmake bug that adds compile flag to resources +sed -i '' \ + -e 's|\.storyboard \*/; settings = {COMPILER_FLAGS = "-DCMAKE_SKIP_PRECOMPILE_HEADERS "; };|.storyboard */;|g' \ + -e 's|\.xcassets \*/; settings = {COMPILER_FLAGS = "-DCMAKE_SKIP_PRECOMPILE_HEADERS "; };|.xcassets */;|g' \ + VCMI.xcodeproj/project.pbxproj From ff635edc0b6f48e1a829b8326487d0a32f999197 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 26 Jul 2022 16:07:42 +0300 Subject: [PATCH 067/131] wrap all library code into namespace if VCMI_LIB_NAMESPACE is defined preparation for having client and server in a single process --- AI/BattleAI/BattleAI.h | 5 ++ AI/BattleAI/EnemyInfo.h | 4 ++ AI/BattleAI/PossibleSpellcast.h | 4 ++ AI/BattleAI/StackWithBonuses.h | 7 ++- AI/BattleAI/StdInc.h | 2 + AI/Nullkiller/AIGateway.h | 4 ++ AI/Nullkiller/Engine/FuzzyEngines.h | 4 ++ AI/Nullkiller/Engine/FuzzyHelper.h | 5 ++ AI/Nullkiller/Engine/PriorityEvaluator.h | 7 ++- AI/Nullkiller/Pathfinding/Actors.cpp | 2 + AI/Nullkiller/StdInc.h | 1 + AI/StupidAI/StdInc.h | 4 +- AI/VCAI/FuzzyEngines.h | 4 ++ AI/VCAI/FuzzyHelper.h | 4 ++ AI/VCAI/StdInc.h | 2 + AI/VCAI/VCAI.cpp | 4 ++ AI/VCAI/VCAI.h | 4 ++ CCallback.h | 12 ++-- Global.h | 17 ++++++ Version.cpp.in | 4 ++ Version.h | 4 ++ client/CGameInfo.h | 16 ++++-- client/CPlayerInterface.h | 31 ++++++----- client/CServerHandler.h | 11 +++- client/Client.h | 16 ++++-- client/Graphics.h | 11 +++- client/SDLRWwrapper.h | 7 ++- client/StdInc.h | 2 + client/battle/CBattleAnimations.h | 7 ++- client/battle/CBattleInterface.h | 27 +++++---- client/battle/CBattleInterfaceClasses.h | 20 ++++--- client/gui/CAnimation.h | 7 ++- client/gui/CGuiHandler.h | 7 ++- client/gui/Fonts.h | 4 ++ client/lobby/CBonusSelection.h | 9 ++- client/lobby/CSavingScreen.h | 7 ++- client/lobby/CSelectionBase.h | 11 +++- client/lobby/RandomMapTab.h | 5 ++ client/mainmenu/CCampaignScreen.h | 7 ++- client/mainmenu/CMainMenu.h | 5 ++ client/mapHandler.h | 7 ++- client/widgets/AdventureMapClasses.h | 17 ++++-- client/widgets/Buttons.h | 14 +++-- client/widgets/CArtifactHolder.h | 8 ++- client/widgets/CComponent.h | 5 ++ client/widgets/CGarrisonInt.h | 11 +++- client/widgets/MiscWidgets.h | 11 +++- client/windows/CAdvmapInterface.h | 11 +++- client/windows/CCastleInterface.h | 17 ++++-- client/windows/CCreatureWindow.h | 7 ++- client/windows/CHeroWindow.h | 7 ++- client/windows/CQuestLog.cpp | 5 ++ client/windows/CQuestLog.h | 9 ++- client/windows/CSpellWindow.h | 9 ++- client/windows/CTradeWindow.h | 5 ++ client/windows/GUIClasses.h | 7 ++- client/windows/InfoWindows.h | 7 ++- include/vcmi/Artifact.h | 4 ++ include/vcmi/ArtifactService.h | 4 ++ include/vcmi/Creature.h | 4 ++ include/vcmi/CreatureService.h | 4 ++ include/vcmi/Entity.h | 4 ++ include/vcmi/EntityService.h | 4 ++ include/vcmi/Environment.h | 8 ++- include/vcmi/Faction.h | 4 ++ include/vcmi/FactionService.h | 4 ++ include/vcmi/HeroClass.h | 4 ++ include/vcmi/HeroClassService.h | 4 ++ include/vcmi/HeroType.h | 4 ++ include/vcmi/HeroTypeService.h | 4 ++ include/vcmi/Metatype.h | 4 ++ include/vcmi/Player.h | 7 +-- include/vcmi/ServerCallback.h | 4 ++ include/vcmi/Services.h | 4 ++ include/vcmi/Skill.h | 4 ++ include/vcmi/SkillService.h | 4 ++ include/vcmi/events/ApplyDamage.h | 4 ++ include/vcmi/events/Event.h | 4 ++ include/vcmi/events/EventBus.h | 4 ++ include/vcmi/events/GameResumed.h | 4 ++ include/vcmi/events/ObjectVisitEnded.h | 4 ++ include/vcmi/events/ObjectVisitStarted.h | 4 ++ include/vcmi/events/PlayerGotTurn.h | 4 ++ include/vcmi/events/SubscriptionRegistry.h | 4 ++ include/vcmi/events/TurnStarted.h | 4 ++ include/vcmi/scripting/Service.h | 8 ++- include/vcmi/spells/Caster.h | 4 ++ include/vcmi/spells/Magic.h | 6 +- include/vcmi/spells/Service.h | 4 ++ include/vcmi/spells/Spell.h | 4 ++ include/vstd/CLoggerBase.h | 4 ++ include/vstd/ContainerUtils.h | 5 +- include/vstd/RNG.h | 4 ++ include/vstd/StringUtils.h | 4 ++ launcher/updatedialog_moc.h | 4 ++ lib/BattleFieldHandler.cpp | 6 +- lib/BattleFieldHandler.h | 4 ++ lib/CArtHandler.cpp | 4 ++ lib/CArtHandler.h | 4 ++ lib/CBonusTypeHandler.cpp | 6 +- lib/CBonusTypeHandler.h | 6 +- lib/CBuildingHandler.cpp | 4 ++ lib/CBuildingHandler.h | 4 ++ lib/CConfigHandler.cpp | 4 ++ lib/CConfigHandler.h | 4 ++ lib/CConsoleHandler.cpp | 4 ++ lib/CConsoleHandler.h | 4 ++ lib/CCreatureHandler.cpp | 4 ++ lib/CCreatureHandler.h | 4 ++ lib/CCreatureSet.cpp | 4 ++ lib/CCreatureSet.h | 4 ++ lib/CGameInfoCallback.cpp | 4 ++ lib/CGameInfoCallback.h | 5 ++ lib/CGameInterface.cpp | 4 ++ lib/CGameInterface.h | 9 ++- lib/CGameState.cpp | 4 ++ lib/CGameState.h | 18 +++--- lib/CGameStateFwd.h | 4 ++ lib/CGeneralTextHandler.cpp | 4 ++ lib/CGeneralTextHandler.h | 4 ++ lib/CHeroHandler.cpp | 4 ++ lib/CHeroHandler.h | 5 +- lib/CModHandler.cpp | 4 ++ lib/CModHandler.h | 4 ++ lib/CPathfinder.cpp | 4 ++ lib/CPathfinder.h | 4 ++ lib/CPlayerState.cpp | 4 ++ lib/CPlayerState.h | 4 ++ lib/CRandomGenerator.cpp | 4 ++ lib/CRandomGenerator.h | 4 ++ lib/CScriptingModule.cpp | 4 ++ lib/CScriptingModule.h | 4 ++ lib/CSkillHandler.cpp | 4 ++ lib/CSkillHandler.h | 4 ++ lib/CSoundBase.h | 4 ++ lib/CStack.cpp | 4 ++ lib/CStack.h | 4 ++ lib/CStopWatch.h | 4 ++ lib/CThreadHelper.cpp | 4 ++ lib/CThreadHelper.h | 4 ++ lib/CTownHandler.cpp | 4 ++ lib/CTownHandler.h | 4 ++ lib/CondSh.h | 4 ++ lib/ConstTransitivePtr.h | 6 +- lib/FunctionList.h | 4 ++ lib/GameConstants.cpp | 4 ++ lib/GameConstants.h | 4 ++ lib/HeroBonus.cpp | 4 ++ lib/HeroBonus.h | 4 ++ lib/IBonusTypeHandler.h | 4 ++ lib/IGameCallback.cpp | 4 ++ lib/IGameCallback.h | 4 ++ lib/IGameEventsReceiver.h | 8 ++- lib/IHandlerBase.cpp | 4 ++ lib/IHandlerBase.h | 4 ++ lib/Interprocess.h | 4 ++ lib/JsonDetail.cpp | 4 ++ lib/JsonDetail.h | 4 ++ lib/JsonNode.cpp | 65 ++++++++++++---------- lib/JsonNode.h | 4 ++ lib/LogicalExpression.cpp | 4 ++ lib/LogicalExpression.h | 4 ++ lib/NetPacks.h | 7 ++- lib/NetPacksBase.h | 19 ++++--- lib/NetPacksLib.cpp | 4 ++ lib/NetPacksLobby.h | 9 ++- lib/ObstacleHandler.cpp | 4 ++ lib/ObstacleHandler.h | 4 ++ lib/PathfinderUtil.h | 4 ++ lib/ResourceSet.cpp | 10 +++- lib/ResourceSet.h | 4 ++ lib/ScopeGuard.h | 4 ++ lib/ScriptHandler.cpp | 6 +- lib/ScriptHandler.h | 8 ++- lib/StartInfo.cpp | 4 ++ lib/StartInfo.h | 7 +++ lib/StringConstants.h | 4 ++ lib/Terrain.cpp | 4 ++ lib/Terrain.h | 3 + lib/UnlockGuard.h | 4 ++ lib/VCMIDirs.cpp | 4 ++ lib/VCMIDirs.h | 4 ++ lib/VCMI_Lib.cpp | 4 ++ lib/VCMI_Lib.h | 4 ++ lib/abilities/Ability.h | 5 ++ lib/battle/AccessibilityInfo.cpp | 4 ++ lib/battle/AccessibilityInfo.h | 4 ++ lib/battle/BattleAction.cpp | 4 ++ lib/battle/BattleAction.h | 4 ++ lib/battle/BattleAttackInfo.cpp | 4 ++ lib/battle/BattleAttackInfo.h | 8 ++- lib/battle/BattleHex.cpp | 4 ++ lib/battle/BattleHex.h | 4 ++ lib/battle/BattleInfo.cpp | 4 ++ lib/battle/BattleInfo.h | 4 ++ lib/battle/BattleProxy.cpp | 4 ++ lib/battle/BattleProxy.h | 4 ++ lib/battle/CBattleInfoCallback.cpp | 4 ++ lib/battle/CBattleInfoCallback.h | 4 ++ lib/battle/CBattleInfoEssentials.cpp | 4 ++ lib/battle/CBattleInfoEssentials.h | 4 ++ lib/battle/CCallbackBase.cpp | 4 ++ lib/battle/CCallbackBase.h | 4 ++ lib/battle/CObstacleInstance.cpp | 4 ++ lib/battle/CObstacleInstance.h | 4 ++ lib/battle/CPlayerBattleCallback.cpp | 4 ++ lib/battle/CPlayerBattleCallback.h | 4 ++ lib/battle/CUnitState.cpp | 4 ++ lib/battle/CUnitState.h | 4 ++ lib/battle/Destination.cpp | 4 ++ lib/battle/Destination.h | 4 ++ lib/battle/IBattleInfoCallback.h | 4 ++ lib/battle/IBattleState.h | 4 ++ lib/battle/IUnitInfo.h | 4 ++ lib/battle/ReachabilityInfo.cpp | 4 ++ lib/battle/ReachabilityInfo.h | 4 ++ lib/battle/SideInBattle.cpp | 4 ++ lib/battle/SideInBattle.h | 4 ++ lib/battle/SiegeInfo.cpp | 4 ++ lib/battle/SiegeInfo.h | 4 ++ lib/battle/Unit.cpp | 4 ++ lib/battle/Unit.h | 4 ++ lib/events/ApplyDamage.cpp | 4 ++ lib/events/ApplyDamage.h | 4 ++ lib/events/GameResumed.cpp | 4 ++ lib/events/GameResumed.h | 4 ++ lib/events/ObjectVisitEnded.cpp | 4 ++ lib/events/ObjectVisitEnded.h | 4 ++ lib/events/ObjectVisitStarted.cpp | 4 ++ lib/events/ObjectVisitStarted.h | 4 ++ lib/events/PlayerGotTurn.cpp | 4 ++ lib/events/PlayerGotTurn.h | 4 ++ lib/events/TurnStarted.cpp | 4 ++ lib/events/TurnStarted.h | 4 ++ lib/filesystem/AdapterLoaders.cpp | 4 ++ lib/filesystem/AdapterLoaders.h | 4 ++ lib/filesystem/CArchiveLoader.cpp | 4 ++ lib/filesystem/CArchiveLoader.h | 4 ++ lib/filesystem/CBinaryReader.cpp | 4 ++ lib/filesystem/CBinaryReader.h | 4 ++ lib/filesystem/CCompressedStream.cpp | 4 ++ lib/filesystem/CCompressedStream.h | 4 ++ lib/filesystem/CFileInputStream.cpp | 4 ++ lib/filesystem/CFileInputStream.h | 4 ++ lib/filesystem/CFilesystemLoader.cpp | 4 ++ lib/filesystem/CFilesystemLoader.h | 4 ++ lib/filesystem/CInputOutputStream.h | 4 ++ lib/filesystem/CInputStream.h | 4 ++ lib/filesystem/CMemoryBuffer.cpp | 4 ++ lib/filesystem/CMemoryBuffer.h | 4 ++ lib/filesystem/CMemoryStream.cpp | 4 ++ lib/filesystem/CMemoryStream.h | 4 ++ lib/filesystem/COutputStream.h | 4 ++ lib/filesystem/CStream.h | 4 ++ lib/filesystem/CZipLoader.cpp | 4 ++ lib/filesystem/CZipLoader.h | 4 ++ lib/filesystem/CZipSaver.cpp | 4 ++ lib/filesystem/CZipSaver.h | 4 ++ lib/filesystem/FileInfo.cpp | 4 ++ lib/filesystem/FileInfo.h | 4 ++ lib/filesystem/FileStream.cpp | 8 ++- lib/filesystem/FileStream.h | 10 +++- lib/filesystem/Filesystem.cpp | 4 ++ lib/filesystem/Filesystem.h | 4 ++ lib/filesystem/ISimpleResourceLoader.h | 4 ++ lib/filesystem/MinizipExtensions.cpp | 4 ++ lib/filesystem/MinizipExtensions.h | 5 ++ lib/filesystem/ResourceID.cpp | 4 ++ lib/filesystem/ResourceID.h | 28 +++++----- lib/int3.h | 4 ++ lib/logging/CBasicLogConfigurator.cpp | 4 ++ lib/logging/CBasicLogConfigurator.h | 4 ++ lib/logging/CLogger.cpp | 4 ++ lib/logging/CLogger.h | 4 ++ lib/mapObjects/CArmedInstance.cpp | 4 ++ lib/mapObjects/CArmedInstance.h | 6 +- lib/mapObjects/CBank.cpp | 6 +- lib/mapObjects/CBank.h | 6 +- lib/mapObjects/CGHeroInstance.cpp | 4 ++ lib/mapObjects/CGHeroInstance.h | 4 ++ lib/mapObjects/CGMarket.cpp | 4 ++ lib/mapObjects/CGMarket.h | 6 +- lib/mapObjects/CGPandoraBox.cpp | 6 +- lib/mapObjects/CGPandoraBox.h | 6 +- lib/mapObjects/CGTownInstance.cpp | 4 ++ lib/mapObjects/CGTownInstance.h | 4 ++ lib/mapObjects/CObjectClassesHandler.cpp | 4 ++ lib/mapObjects/CObjectClassesHandler.h | 4 ++ lib/mapObjects/CObjectHandler.cpp | 4 ++ lib/mapObjects/CObjectHandler.h | 4 ++ lib/mapObjects/CQuest.cpp | 4 ++ lib/mapObjects/CQuest.h | 4 ++ lib/mapObjects/CRewardableConstructor.cpp | 4 ++ lib/mapObjects/CRewardableConstructor.h | 4 ++ lib/mapObjects/CRewardableObject.cpp | 4 ++ lib/mapObjects/CRewardableObject.h | 4 ++ lib/mapObjects/CommonConstructors.cpp | 4 ++ lib/mapObjects/CommonConstructors.h | 4 ++ lib/mapObjects/JsonRandom.cpp | 4 ++ lib/mapObjects/JsonRandom.h | 4 ++ lib/mapObjects/MiscObjects.cpp | 6 +- lib/mapObjects/MiscObjects.h | 4 ++ lib/mapObjects/ObjectTemplate.cpp | 3 + lib/mapObjects/ObjectTemplate.h | 4 ++ lib/mapping/CCampaignHandler.cpp | 4 ++ lib/mapping/CCampaignHandler.h | 4 ++ lib/mapping/CDrawRoadsOperation.cpp | 4 ++ lib/mapping/CDrawRoadsOperation.h | 4 ++ lib/mapping/CMap.cpp | 4 ++ lib/mapping/CMap.h | 4 ++ lib/mapping/CMapDefines.h | 4 ++ lib/mapping/CMapEditManager.cpp | 4 ++ lib/mapping/CMapEditManager.h | 4 ++ lib/mapping/CMapInfo.cpp | 4 ++ lib/mapping/CMapInfo.h | 4 ++ lib/mapping/CMapOperation.cpp | 6 +- lib/mapping/CMapOperation.h | 6 +- lib/mapping/CMapService.cpp | 4 ++ lib/mapping/CMapService.h | 4 ++ lib/mapping/MapEditUtils.cpp | 4 ++ lib/mapping/MapEditUtils.h | 4 ++ lib/mapping/MapFormatH3M.cpp | 4 ++ lib/mapping/MapFormatH3M.h | 4 ++ lib/mapping/MapFormatJson.cpp | 4 ++ lib/mapping/MapFormatJson.h | 4 ++ lib/registerTypes/RegisterTypes.cpp | 4 ++ lib/registerTypes/RegisterTypes.h | 4 ++ lib/registerTypes/TypesClientPacks1.cpp | 4 ++ lib/registerTypes/TypesClientPacks2.cpp | 4 ++ lib/registerTypes/TypesLobbyPacks.cpp | 4 ++ lib/registerTypes/TypesMapObjects1.cpp | 4 ++ lib/registerTypes/TypesMapObjects2.cpp | 4 ++ lib/registerTypes/TypesMapObjects3.cpp | 4 ++ lib/registerTypes/TypesServerPacks.cpp | 4 ++ lib/rmg/CMapGenOptions.cpp | 4 ++ lib/rmg/CMapGenOptions.h | 4 ++ lib/rmg/CMapGenerator.cpp | 4 ++ lib/rmg/CMapGenerator.h | 4 ++ lib/rmg/CRmgTemplate.cpp | 4 ++ lib/rmg/CRmgTemplate.h | 4 ++ lib/rmg/CRmgTemplateStorage.cpp | 4 ++ lib/rmg/CRmgTemplateStorage.h | 4 ++ lib/rmg/CZonePlacer.cpp | 4 ++ lib/rmg/CZonePlacer.h | 4 ++ lib/rmg/ConnectionsPlacer.cpp | 4 ++ lib/rmg/ConnectionsPlacer.h | 4 ++ lib/rmg/Functions.cpp | 4 ++ lib/rmg/Functions.h | 4 ++ lib/rmg/ObjectManager.cpp | 4 ++ lib/rmg/ObjectManager.h | 4 ++ lib/rmg/ObstaclePlacer.cpp | 4 ++ lib/rmg/ObstaclePlacer.h | 5 ++ lib/rmg/RiverPlacer.cpp | 4 ++ lib/rmg/RiverPlacer.h | 4 ++ lib/rmg/RmgArea.cpp | 4 ++ lib/rmg/RmgArea.h | 4 ++ lib/rmg/RmgMap.cpp | 4 ++ lib/rmg/RmgMap.h | 4 ++ lib/rmg/RmgObject.cpp | 4 ++ lib/rmg/RmgObject.h | 4 ++ lib/rmg/RmgPath.cpp | 4 ++ lib/rmg/RmgPath.h | 4 ++ lib/rmg/RoadPlacer.cpp | 4 ++ lib/rmg/RoadPlacer.h | 4 ++ lib/rmg/RockPlacer.cpp | 4 ++ lib/rmg/RockPlacer.h | 4 ++ lib/rmg/TerrainPainter.cpp | 4 ++ lib/rmg/TerrainPainter.h | 4 ++ lib/rmg/TileInfo.cpp | 4 ++ lib/rmg/TileInfo.h | 4 ++ lib/rmg/TownPlacer.cpp | 4 ++ lib/rmg/TownPlacer.h | 4 ++ lib/rmg/TreasurePlacer.cpp | 4 ++ lib/rmg/TreasurePlacer.h | 4 ++ lib/rmg/WaterAdopter.cpp | 4 ++ lib/rmg/WaterAdopter.h | 4 ++ lib/rmg/WaterProxy.cpp | 4 ++ lib/rmg/WaterProxy.h | 4 ++ lib/rmg/WaterRoutes.cpp | 4 ++ lib/rmg/WaterRoutes.h | 4 ++ lib/rmg/Zone.cpp | 4 ++ lib/rmg/Zone.h | 4 ++ lib/rmg/float3.h | 4 ++ lib/serializer/BinaryDeserializer.cpp | 4 ++ lib/serializer/BinaryDeserializer.h | 4 ++ lib/serializer/BinarySerializer.cpp | 4 ++ lib/serializer/BinarySerializer.h | 4 ++ lib/serializer/CLoadIntegrityValidator.cpp | 4 ++ lib/serializer/CLoadIntegrityValidator.h | 4 ++ lib/serializer/CMemorySerializer.cpp | 4 ++ lib/serializer/CMemorySerializer.h | 4 ++ lib/serializer/CSerializer.cpp | 4 ++ lib/serializer/CSerializer.h | 4 ++ lib/serializer/CTypeList.cpp | 4 ++ lib/serializer/CTypeList.h | 4 ++ lib/serializer/Cast.h | 4 ++ lib/serializer/Connection.cpp | 4 ++ lib/serializer/Connection.h | 8 ++- lib/serializer/JsonDeserializer.cpp | 4 ++ lib/serializer/JsonDeserializer.h | 4 ++ lib/serializer/JsonSerializeFormat.cpp | 4 ++ lib/serializer/JsonSerializeFormat.h | 4 ++ lib/serializer/JsonSerializer.cpp | 4 ++ lib/serializer/JsonSerializer.h | 4 ++ lib/serializer/JsonTreeSerializer.h | 4 ++ lib/serializer/JsonUpdater.cpp | 4 ++ lib/serializer/JsonUpdater.h | 4 ++ lib/spells/AbilityCaster.cpp | 4 ++ lib/spells/AbilityCaster.h | 4 ++ lib/spells/AdventureSpellMechanics.cpp | 4 ++ lib/spells/AdventureSpellMechanics.h | 4 ++ lib/spells/BattleSpellMechanics.cpp | 4 ++ lib/spells/BattleSpellMechanics.h | 4 ++ lib/spells/BonusCaster.cpp | 4 ++ lib/spells/BonusCaster.h | 4 ++ lib/spells/CSpellHandler.cpp | 6 +- lib/spells/CSpellHandler.h | 4 ++ lib/spells/ISpellMechanics.cpp | 4 ++ lib/spells/ISpellMechanics.h | 4 ++ lib/spells/Problem.cpp | 4 ++ lib/spells/Problem.h | 4 ++ lib/spells/ProxyCaster.cpp | 4 ++ lib/spells/ProxyCaster.h | 4 ++ lib/spells/TargetCondition.cpp | 4 ++ lib/spells/TargetCondition.h | 4 ++ lib/spells/ViewSpellInt.cpp | 4 ++ lib/spells/ViewSpellInt.h | 4 ++ lib/spells/effects/Catapult.cpp | 4 ++ lib/spells/effects/Catapult.h | 4 ++ lib/spells/effects/Clone.cpp | 4 ++ lib/spells/effects/Clone.h | 4 ++ lib/spells/effects/Damage.cpp | 4 ++ lib/spells/effects/Damage.h | 4 ++ lib/spells/effects/Dispel.cpp | 4 ++ lib/spells/effects/Dispel.h | 4 ++ lib/spells/effects/Effect.cpp | 4 ++ lib/spells/effects/Effect.h | 8 ++- lib/spells/effects/Effects.cpp | 4 ++ lib/spells/effects/Effects.h | 4 ++ lib/spells/effects/EffectsFwd.h | 4 ++ lib/spells/effects/Heal.cpp | 4 ++ lib/spells/effects/Heal.h | 4 ++ lib/spells/effects/LocationEffect.cpp | 4 ++ lib/spells/effects/LocationEffect.h | 4 ++ lib/spells/effects/Obstacle.cpp | 4 ++ lib/spells/effects/Obstacle.h | 4 ++ lib/spells/effects/Registry.cpp | 4 ++ lib/spells/effects/Registry.h | 4 ++ lib/spells/effects/RemoveObstacle.cpp | 4 ++ lib/spells/effects/RemoveObstacle.h | 4 ++ lib/spells/effects/Sacrifice.cpp | 4 ++ lib/spells/effects/Sacrifice.h | 4 ++ lib/spells/effects/Summon.cpp | 4 ++ lib/spells/effects/Summon.h | 4 ++ lib/spells/effects/Teleport.cpp | 4 ++ lib/spells/effects/Teleport.h | 4 ++ lib/spells/effects/Timed.cpp | 4 ++ lib/spells/effects/Timed.h | 4 ++ lib/spells/effects/UnitEffect.cpp | 4 ++ lib/spells/effects/UnitEffect.h | 4 ++ lib/vcmi_endian.h | 4 ++ lib/vstd/StringUtils.cpp | 4 ++ server/CGameHandler.cpp | 2 + server/CGameHandler.h | 9 ++- server/CQuery.h | 5 ++ server/CVCMIServer.h | 7 ++- server/StdInc.h | 1 + 467 files changed, 2117 insertions(+), 211 deletions(-) diff --git a/AI/BattleAI/BattleAI.h b/AI/BattleAI/BattleAI.h index 47dc84c47..82cecacc8 100644 --- a/AI/BattleAI/BattleAI.h +++ b/AI/BattleAI/BattleAI.h @@ -13,7 +13,12 @@ #include "PossibleSpellcast.h" #include "PotentialTargets.h" +VCMI_LIB_NAMESPACE_BEGIN + class CSpell; + +VCMI_LIB_NAMESPACE_END + class EnemyInfo; /* diff --git a/AI/BattleAI/EnemyInfo.h b/AI/BattleAI/EnemyInfo.h index 874e9e2b6..e9cb803de 100644 --- a/AI/BattleAI/EnemyInfo.h +++ b/AI/BattleAI/EnemyInfo.h @@ -9,11 +9,15 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace battle { class Unit; } +VCMI_LIB_NAMESPACE_END + class EnemyInfo { public: diff --git a/AI/BattleAI/PossibleSpellcast.h b/AI/BattleAI/PossibleSpellcast.h index 806832ad5..a4e0021c7 100644 --- a/AI/BattleAI/PossibleSpellcast.h +++ b/AI/BattleAI/PossibleSpellcast.h @@ -14,8 +14,12 @@ #include "../../lib/battle/Destination.h" +VCMI_LIB_NAMESPACE_BEGIN + class CSpell; +VCMI_LIB_NAMESPACE_END + class PossibleSpellcast { public: diff --git a/AI/BattleAI/StackWithBonuses.h b/AI/BattleAI/StackWithBonuses.h index eb8d57db5..75015503f 100644 --- a/AI/BattleAI/StackWithBonuses.h +++ b/AI/BattleAI/StackWithBonuses.h @@ -18,9 +18,14 @@ #include "../../lib/battle/BattleProxy.h" #include "../../lib/battle/CUnitState.h" -class HypotheticBattle; +VCMI_LIB_NAMESPACE_BEGIN + class CStack; +VCMI_LIB_NAMESPACE_END + +class HypotheticBattle; + ///Fake random generator, used by AI to evaluate random server behavior class RNGStub : public vstd::RNG { diff --git a/AI/BattleAI/StdInc.h b/AI/BattleAI/StdInc.h index 1e6eda607..ba1e8b9ee 100644 --- a/AI/BattleAI/StdInc.h +++ b/AI/BattleAI/StdInc.h @@ -13,3 +13,5 @@ // This header should be treated as a pre compiled header file(PCH) in the compiler building settings. // Here you can add specific libraries and macros which are specific to this project. + +VCMI_LIB_USING_NAMESPACE diff --git a/AI/Nullkiller/AIGateway.h b/AI/Nullkiller/AIGateway.h index f940853f1..29066be81 100644 --- a/AI/Nullkiller/AIGateway.h +++ b/AI/Nullkiller/AIGateway.h @@ -25,8 +25,12 @@ #include "Pathfinding/AIPathfinder.h" #include "Engine/Nullkiller.h" +VCMI_LIB_NAMESPACE_BEGIN + struct QuestInfo; +VCMI_LIB_NAMESPACE_END + class AIStatus { boost::mutex mx; diff --git a/AI/Nullkiller/Engine/FuzzyEngines.h b/AI/Nullkiller/Engine/FuzzyEngines.h index c0fbba89a..0e0c533da 100644 --- a/AI/Nullkiller/Engine/FuzzyEngines.h +++ b/AI/Nullkiller/Engine/FuzzyEngines.h @@ -11,8 +11,12 @@ #include #include "../Goals/AbstractGoal.h" +VCMI_LIB_NAMESPACE_BEGIN + class CArmedInstance; +VCMI_LIB_NAMESPACE_END + class engineBase //subclasses create fuzzylite variables with "new" that are not freed - this is desired as fl::Engine wants to destroy these... { protected: diff --git a/AI/Nullkiller/Engine/FuzzyHelper.h b/AI/Nullkiller/Engine/FuzzyHelper.h index f9bfcf23a..760b34279 100644 --- a/AI/Nullkiller/Engine/FuzzyHelper.h +++ b/AI/Nullkiller/Engine/FuzzyHelper.h @@ -10,7 +10,12 @@ #pragma once #include "FuzzyEngines.h" +VCMI_LIB_NAMESPACE_BEGIN + class CBank; + +VCMI_LIB_NAMESPACE_END + class Nullkiller; class DLL_EXPORT FuzzyHelper diff --git a/AI/Nullkiller/Engine/PriorityEvaluator.h b/AI/Nullkiller/Engine/PriorityEvaluator.h index 6bcd09c32..6156c08c2 100644 --- a/AI/Nullkiller/Engine/PriorityEvaluator.h +++ b/AI/Nullkiller/Engine/PriorityEvaluator.h @@ -12,9 +12,14 @@ #include "../Goals/CGoal.h" #include "../Pathfinding/AIPathfinder.h" +VCMI_LIB_NAMESPACE_BEGIN + +class CGWitchHut; + +VCMI_LIB_NAMESPACE_END + class BuildingInfo; class Nullkiller; -class CGWitchHut; class RewardEvaluator { diff --git a/AI/Nullkiller/Pathfinding/Actors.cpp b/AI/Nullkiller/Pathfinding/Actors.cpp index e6806a0b2..d4905d462 100644 --- a/AI/Nullkiller/Pathfinding/Actors.cpp +++ b/AI/Nullkiller/Pathfinding/Actors.cpp @@ -164,6 +164,7 @@ ExchangeResult ChainActor::tryExchangeNoLock(const ChainActor * specialActor, co return baseActor->tryExchangeNoLock(specialActor, other); } +VCMI_LIB_NAMESPACE_BEGIN namespace vstd { template @@ -180,6 +181,7 @@ namespace vstd return v; } } +VCMI_LIB_NAMESPACE_END ExchangeResult HeroActor::tryExchangeNoLock(const ChainActor * specialActor, const ChainActor * other) const { diff --git a/AI/Nullkiller/StdInc.h b/AI/Nullkiller/StdInc.h index 2e1a36a05..50855f6e5 100644 --- a/AI/Nullkiller/StdInc.h +++ b/AI/Nullkiller/StdInc.h @@ -1,3 +1,4 @@ #pragma once #include "../../Global.h" +VCMI_LIB_USING_NAMESPACE #include "../../CCallback.h" diff --git a/AI/StupidAI/StdInc.h b/AI/StupidAI/StdInc.h index 81a6cb308..02b2c08f3 100644 --- a/AI/StupidAI/StdInc.h +++ b/AI/StupidAI/StdInc.h @@ -4,4 +4,6 @@ // This header should be treated as a pre compiled header file(PCH) in the compiler building settings. -// Here you can add specific libraries and macros which are specific to this project. \ No newline at end of file +// Here you can add specific libraries and macros which are specific to this project. + +VCMI_LIB_USING_NAMESPACE diff --git a/AI/VCAI/FuzzyEngines.h b/AI/VCAI/FuzzyEngines.h index 95a58c482..f09920da7 100644 --- a/AI/VCAI/FuzzyEngines.h +++ b/AI/VCAI/FuzzyEngines.h @@ -11,8 +11,12 @@ #include #include "Goals/AbstractGoal.h" +VCMI_LIB_NAMESPACE_BEGIN + class CArmedInstance; +VCMI_LIB_NAMESPACE_END + class engineBase //subclasses create fuzzylite variables with "new" that are not freed - this is desired as fl::Engine wants to destroy these... { protected: diff --git a/AI/VCAI/FuzzyHelper.h b/AI/VCAI/FuzzyHelper.h index 036374acb..6973df463 100644 --- a/AI/VCAI/FuzzyHelper.h +++ b/AI/VCAI/FuzzyHelper.h @@ -10,8 +10,12 @@ #pragma once #include "FuzzyEngines.h" +VCMI_LIB_NAMESPACE_BEGIN + class CBank; +VCMI_LIB_NAMESPACE_END + class DLL_EXPORT FuzzyHelper { public: diff --git a/AI/VCAI/StdInc.h b/AI/VCAI/StdInc.h index 2bc4c254b..0c0f05a6b 100644 --- a/AI/VCAI/StdInc.h +++ b/AI/VCAI/StdInc.h @@ -1,2 +1,4 @@ #pragma once #include "../../Global.h" + +VCMI_LIB_USING_NAMESPACE diff --git a/AI/VCAI/VCAI.cpp b/AI/VCAI/VCAI.cpp index d24f171be..7f42b8d70 100644 --- a/AI/VCAI/VCAI.cpp +++ b/AI/VCAI/VCAI.cpp @@ -29,8 +29,12 @@ extern FuzzyHelper * fh; +VCMI_LIB_NAMESPACE_BEGIN + class CGVisitableOPW; +VCMI_LIB_NAMESPACE_END + const double SAFE_ATTACK_CONSTANT = 1.5; //one thread may be turn of AI and another will be handling a side effect for AI2 diff --git a/AI/VCAI/VCAI.h b/AI/VCAI/VCAI.h index f19fed2ba..acb6e5f5d 100644 --- a/AI/VCAI/VCAI.h +++ b/AI/VCAI/VCAI.h @@ -26,8 +26,12 @@ #include "../../lib/CondSh.h" #include "Pathfinding/AIPathfinder.h" +VCMI_LIB_NAMESPACE_BEGIN + struct QuestInfo; +VCMI_LIB_NAMESPACE_END + class AIhelper; class AIStatus diff --git a/CCallback.h b/CCallback.h index 36d93898a..6986153f1 100644 --- a/CCallback.h +++ b/CCallback.h @@ -13,6 +13,8 @@ #include "lib/battle/CPlayerBattleCallback.h" #include "lib/int3.h" // for int3 +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class CGameState; struct CPath; @@ -20,18 +22,22 @@ class CGObjectInstance; class CArmedInstance; class BattleAction; class CGTownInstance; -struct lua_State; -class CClient; class IShipyard; struct CGPathNode; struct CGPath; struct CPathsInfo; class PathfinderConfig; struct CPack; +struct CPackForServer; class IBattleEventsReceiver; class IGameEventsReceiver; struct ArtifactLocation; +VCMI_LIB_NAMESPACE_END + +class CClient; +struct lua_State; + class IBattleCallback { public: @@ -88,8 +94,6 @@ public: virtual int bulkMergeStacks(ObjectInstanceID armyId, SlotID srcSlot) = 0; }; -struct CPackForServer; - class CBattleCallback : public IBattleCallback, public CPlayerBattleCallback { protected: diff --git a/Global.h b/Global.h index 146897238..965c24d8f 100644 --- a/Global.h +++ b/Global.h @@ -264,11 +264,26 @@ template char (&_ArrayCountObj(const T (&)[N]))[N]; // should be used for variables that becomes unused in release builds (e.g. only used for assert checks) #define UNUSED(VAR) ((void)VAR) +// single-process build makes 2 copies of the main lib by wrapping it in a namespace +#ifdef VCMI_LIB_NAMESPACE +#define VCMI_LIB_NAMESPACE_BEGIN namespace VCMI_LIB_NAMESPACE { +#define VCMI_LIB_NAMESPACE_END } +#define VCMI_LIB_USING_NAMESPACE using namespace VCMI_LIB_NAMESPACE; +#define VCMI_LIB_WRAP_NAMESPACE(x) VCMI_LIB_NAMESPACE::x +#else +#define VCMI_LIB_NAMESPACE_BEGIN +#define VCMI_LIB_NAMESPACE_END +#define VCMI_LIB_USING_NAMESPACE +#define VCMI_LIB_WRAP_NAMESPACE(x) x +#endif + /* ---------------------------------------------------------------------------- */ /* VCMI standard library */ /* ---------------------------------------------------------------------------- */ #include +VCMI_LIB_NAMESPACE_BEGIN + void inline handleException() { try @@ -739,3 +754,5 @@ namespace std } } #endif // NO_STD_TOSTRING + +VCMI_LIB_NAMESPACE_END diff --git a/Version.cpp.in b/Version.cpp.in index 3198034f1..3efea1c74 100644 --- a/Version.cpp.in +++ b/Version.cpp.in @@ -9,7 +9,11 @@ */ #include "Version.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace GameConstants { const char GIT_SHA1[] = "@GIT_SHA1@"; } + +VCMI_LIB_NAMESPACE_END diff --git a/Version.h b/Version.h index 93adced57..3d929696c 100644 --- a/Version.h +++ b/Version.h @@ -1,6 +1,10 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace GameConstants { extern const char GIT_SHA1[]; } + +VCMI_LIB_NAMESPACE_END diff --git a/client/CGameInfo.h b/client/CGameInfo.h index 442be449d..3e6a31dfa 100644 --- a/client/CGameInfo.h +++ b/client/CGameInfo.h @@ -13,29 +13,33 @@ #include "../lib/ConstTransitivePtr.h" +VCMI_LIB_NAMESPACE_BEGIN + class CModHandler; -class CMapHandler; class CHeroHandler; class CCreatureHandler; class CSpellHandler; class CSkillHandler; class CBuildingHandler; class CObjectHandler; -class CSoundHandler; -class CMusicHandler; class CObjectClassesHandler; class CTownHandler; class CGeneralTextHandler; class CConsoleHandler; -class CCursorHandler; class CGameState; -class IMainVideoPlayer; -class CServerHandler; class BattleFieldHandler; class ObstacleHandler; class CMap; +VCMI_LIB_NAMESPACE_END + +class CMapHandler; +class CSoundHandler; +class CMusicHandler; +class CCursorHandler; +class IMainVideoPlayer; +class CServerHandler; //a class for non-mechanical client GUI classes class CClientState diff --git a/client/CPlayerInterface.h b/client/CPlayerInterface.h index 9a5d5408b..f7907594c 100644 --- a/client/CPlayerInterface.h +++ b/client/CPlayerInterface.h @@ -19,30 +19,33 @@ #define sprintf_s snprintf #endif +VCMI_LIB_NAMESPACE_BEGIN + class Artifact; +struct TryMoveHero; +class CGHeroInstance; +class CStack; +class CCreature; +struct CGPath; +class CCreatureSet; +class CGObjectInstance; +struct UpgradeInfo; +template struct CondSh; +struct CPathsInfo; + +VCMI_LIB_NAMESPACE_END + class CButton; class CToggleGroup; -struct TryMoveHero; -class CGHeroInstance; class CAdvMapInt; class CCastleInterface; class CBattleInterface; -class CStack; class CComponent; -class CCreature; -struct SDL_Surface; -struct CGPath; class CCreatureAnimation; class CSelectableComponent; -class CCreatureSet; -class CGObjectInstance; class CSlider; -struct UpgradeInfo; -template struct CondSh; class CInGameConsole; -class CInGameConsole; -union SDL_Event; class CInfoWindow; class IShowActivatable; class ClickableL; @@ -52,7 +55,9 @@ class KeyInterested; class MotionInterested; class TimeInterested; class IShowable; -struct CPathsInfo; + +struct SDL_Surface; +union SDL_Event; namespace boost { diff --git a/client/CServerHandler.h b/client/CServerHandler.h index 03ac005ed..749e46cb7 100644 --- a/client/CServerHandler.h +++ b/client/CServerHandler.h @@ -14,7 +14,8 @@ #include "../lib/StartInfo.h" #include "../lib/CondSh.h" -struct SharedMemory; +VCMI_LIB_NAMESPACE_BEGIN + class CConnection; class PlayerColor; struct StartInfo; @@ -23,9 +24,15 @@ class CMapInfo; struct ClientPlayer; struct CPack; struct CPackForLobby; -class CClient; template class CApplier; + +VCMI_LIB_NAMESPACE_END + +struct SharedMemory; + +class CClient; + class CBaseForLobbyApply; // TODO: Add mutex so we can't set CONNECTION_CANCELLED if client already connected, but thread not setup yet diff --git a/client/Client.h b/client/Client.h index 38a2b4551..569277e93 100644 --- a/client/Client.h +++ b/client/Client.h @@ -19,25 +19,22 @@ #include "../lib/CondSh.h" #include "../lib/CPathfinder.h" +VCMI_LIB_NAMESPACE_BEGIN + struct CPack; struct CPackForServer; class CCampaignState; -class CBattleCallback; class IGameEventsReceiver; class IBattleEventsReceiver; class CBattleGameInterface; class CGameState; class CGameInterface; -class CCallback; class BattleAction; -class CClient; struct CPathsInfo; class BinaryDeserializer; class BinarySerializer; -namespace boost { class thread; } template class CApplier; -class CBaseForCLApply; #if SCRIPTING_ENABLED namespace scripting @@ -51,6 +48,15 @@ namespace events class EventBus; } +VCMI_LIB_NAMESPACE_END + +class CBattleCallback; +class CCallback; +class CClient; +class CBaseForCLApply; + +namespace boost { class thread; } + template class ThreadSafeVector { diff --git a/client/Graphics.h b/client/Graphics.h index c1461b064..faf0aaf95 100644 --- a/client/Graphics.h +++ b/client/Graphics.h @@ -13,18 +13,23 @@ #include "../lib/GameConstants.h" #include "gui/Geometries.h" -struct SDL_Surface; +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class CGTownInstance; class CHeroClass; -struct SDL_Color; struct InfoAboutHero; struct InfoAboutTown; class CGObjectInstance; class ObjectTemplate; -class CAnimation; class EntityService; +VCMI_LIB_NAMESPACE_END + +struct SDL_Surface; +struct SDL_Color; +class CAnimation; + enum EFonts { FONT_BIG, FONT_CALLI, FONT_CREDITS, FONT_HIGH_SCORE, FONT_MEDIUM, FONT_SMALL, FONT_TIMES, FONT_TINY, FONT_VERD diff --git a/client/SDLRWwrapper.h b/client/SDLRWwrapper.h index ab1152a32..ea2f099e9 100644 --- a/client/SDLRWwrapper.h +++ b/client/SDLRWwrapper.h @@ -9,7 +9,12 @@ */ #pragma once -struct SDL_RWops; +VCMI_LIB_NAMESPACE_BEGIN + class CInputStream; +VCMI_LIB_NAMESPACE_END + +struct SDL_RWops; + SDL_RWops* MakeSDLRWops(std::unique_ptr in); diff --git a/client/StdInc.h b/client/StdInc.h index b03f5812c..8e35b9a2d 100644 --- a/client/StdInc.h +++ b/client/StdInc.h @@ -7,3 +7,5 @@ // This header should be treated as a pre compiled header file(PCH) in the compiler building settings. // Here you can add specific libraries and macros which are specific to this project. + +VCMI_LIB_USING_NAMESPACE diff --git a/client/battle/CBattleAnimations.h b/client/battle/CBattleAnimations.h index 93422e6d7..c71d78195 100644 --- a/client/battle/CBattleAnimations.h +++ b/client/battle/CBattleAnimations.h @@ -12,8 +12,13 @@ #include "../../lib/battle/BattleHex.h" #include "../widgets/Images.h" -class CBattleInterface; +VCMI_LIB_NAMESPACE_BEGIN + class CStack; + +VCMI_LIB_NAMESPACE_END + +class CBattleInterface; class CCreatureAnimation; struct CatapultProjectileInfo; struct StackAttackedInfo; diff --git a/client/battle/CBattleInterface.h b/client/battle/CBattleInterface.h index ed5eb1dc7..0fdd232fe 100644 --- a/client/battle/CBattleInterface.h +++ b/client/battle/CBattleInterface.h @@ -19,14 +19,11 @@ #include "../../lib/spells/CSpellHandler.h" //CSpell::TAnimation #include "../../lib/battle/CBattleInfoCallback.h" -class CLabel; +VCMI_LIB_NAMESPACE_BEGIN + class CCreatureSet; class CGHeroInstance; class CStack; -class CCallback; -class CButton; -class CToggleButton; -class CToggleGroup; struct BattleResult; struct BattleSpellCast; struct CObstacleInstance; @@ -35,8 +32,21 @@ struct SetStackEffect; class BattleAction; class CGTownInstance; struct CatapultAttack; -struct CatapultProjectileInfo; struct BattleTriggerEffect; +struct BattleHex; +struct InfoAboutHero; +class CBattleGameInterface; +struct CustomEffectInfo; +class CSpell; + +VCMI_LIB_NAMESPACE_END + +class CLabel; +class CCallback; +class CButton; +class CToggleButton; +class CToggleGroup; +struct CatapultProjectileInfo; class CBattleAnimation; class CBattleHero; class CBattleConsole; @@ -46,13 +56,8 @@ class CPlayerInterface; class CCreatureAnimation; struct ProjectileInfo; class CClickableHex; -struct BattleHex; -struct InfoAboutHero; -class CBattleGameInterface; -struct CustomEffectInfo; class CAnimation; class IImage; -class CSpell; /// Small struct which contains information about the id of the attacked stack, the damage dealt,... struct StackAttackedInfo diff --git a/client/battle/CBattleInterfaceClasses.h b/client/battle/CBattleInterfaceClasses.h index 079014ba7..c0b657d27 100644 --- a/client/battle/CBattleInterfaceClasses.h +++ b/client/battle/CBattleInterfaceClasses.h @@ -13,8 +13,20 @@ #include "../../lib/battle/BattleHex.h" #include "../windows/CWindowObject.h" -struct SDL_Surface; +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; +struct BattleResult; +class CStack; + +namespace battle +{ +class Unit; +} + +VCMI_LIB_NAMESPACE_END + +struct SDL_Surface; class CBattleInterface; class CPicture; class CFilledTexture; @@ -23,12 +35,6 @@ class CToggleButton; class CToggleGroup; class CLabel; class CTextBox; -struct BattleResult; -class CStack; -namespace battle -{ - class Unit; -} class CAnimImage; class CPlayerInterface; diff --git a/client/gui/CAnimation.h b/client/gui/CAnimation.h index 0b1fa9e10..cb885fa36 100644 --- a/client/gui/CAnimation.h +++ b/client/gui/CAnimation.h @@ -21,8 +21,13 @@ #undef OUT #endif -struct SDL_Surface; +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; + +VCMI_LIB_NAMESPACE_END + +struct SDL_Surface; class CDefFile; class ColorShifter; diff --git a/client/gui/CGuiHandler.h b/client/gui/CGuiHandler.h index 18be56380..7f6373dfb 100644 --- a/client/gui/CGuiHandler.h +++ b/client/gui/CGuiHandler.h @@ -13,6 +13,12 @@ #include "Geometries.h" #include "SDL_Extensions.h" +VCMI_LIB_NAMESPACE_BEGIN + +template struct CondSh; + +VCMI_LIB_NAMESPACE_END + class CFramerateManager; class CGStatusBar; class CIntObject; @@ -20,7 +26,6 @@ class IUpdateable; class IShowActivatable; class IShowable; enum class EIntObjMouseBtnType; -template struct CondSh; // TODO: event handling need refactoring enum EUserEvent diff --git a/client/gui/Fonts.h b/client/gui/Fonts.h index f471e8967..a5aad2c46 100644 --- a/client/gui/Fonts.h +++ b/client/gui/Fonts.h @@ -9,8 +9,12 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; +VCMI_LIB_NAMESPACE_END + struct Point; struct SDL_Surface; struct SDL_Color; diff --git a/client/lobby/CBonusSelection.h b/client/lobby/CBonusSelection.h index 9c9c7d178..ecf322758 100644 --- a/client/lobby/CBonusSelection.h +++ b/client/lobby/CBonusSelection.h @@ -10,8 +10,13 @@ #pragma once #include "../windows/CWindowObject.h" -struct SDL_Surface; +VCMI_LIB_NAMESPACE_BEGIN + class CCampaignState; + +VCMI_LIB_NAMESPACE_END + +struct SDL_Surface; class CButton; class CTextBox; class CToggleGroup; @@ -90,4 +95,4 @@ public: std::shared_ptr buttonDifficultyLeft; std::shared_ptr buttonDifficultyRight; std::shared_ptr iconsMapSizes; -}; \ No newline at end of file +}; diff --git a/client/lobby/CSavingScreen.h b/client/lobby/CSavingScreen.h index 20c04141d..ac966a457 100644 --- a/client/lobby/CSavingScreen.h +++ b/client/lobby/CSavingScreen.h @@ -11,10 +11,15 @@ #include "CSelectionBase.h" -class CSelectionBase; +VCMI_LIB_NAMESPACE_BEGIN + struct StartInfo; class CMapInfo; +VCMI_LIB_NAMESPACE_END + +class CSelectionBase; + class CSavingScreen : public CSelectionBase { public: diff --git a/client/lobby/CSelectionBase.h b/client/lobby/CSelectionBase.h index e157607fd..7d2671f6c 100644 --- a/client/lobby/CSelectionBase.h +++ b/client/lobby/CSelectionBase.h @@ -11,6 +11,14 @@ #include "../mainmenu/CMainMenu.h" +VCMI_LIB_NAMESPACE_BEGIN + +class CMapInfo; +struct StartInfo; +struct PlayerInfo; + +VCMI_LIB_NAMESPACE_END + class CButton; class CTextBox; class CTextInput; @@ -21,9 +29,6 @@ class OptionsTab; class SelectionTab; class InfoCard; class CChatBox; -class CMapInfo; -struct StartInfo; -struct PlayerInfo; class CLabel; class CFlagBox; class CLabelGroup; diff --git a/client/lobby/RandomMapTab.h b/client/lobby/RandomMapTab.h index f9e9f42b0..f7e399a17 100644 --- a/client/lobby/RandomMapTab.h +++ b/client/lobby/RandomMapTab.h @@ -14,7 +14,12 @@ #include "../../lib/FunctionList.h" #include "../../lib/GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class CMapGenOptions; + +VCMI_LIB_NAMESPACE_END + class CToggleButton; class CLabel; class CLabelGroup; diff --git a/client/mainmenu/CCampaignScreen.h b/client/mainmenu/CCampaignScreen.h index b0a1acb85..f40f78c8c 100644 --- a/client/mainmenu/CCampaignScreen.h +++ b/client/mainmenu/CCampaignScreen.h @@ -11,11 +11,16 @@ #include "../windows/CWindowObject.h" +VCMI_LIB_NAMESPACE_BEGIN + +class JsonNode; + +VCMI_LIB_NAMESPACE_END + class CLabel; class CPicture; class CButton; struct SDL_Surface; -class JsonNode; class CCampaignScreen : public CWindowObject { diff --git a/client/mainmenu/CMainMenu.h b/client/mainmenu/CMainMenu.h index 6220230b3..4fdebb93d 100644 --- a/client/mainmenu/CMainMenu.h +++ b/client/mainmenu/CMainMenu.h @@ -12,7 +12,12 @@ #include "../windows/CWindowObject.h" #include "../../lib/JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + class CCampaignState; + +VCMI_LIB_NAMESPACE_END + class CTextInput; class CGStatusBar; class CTextBox; diff --git a/client/mapHandler.h b/client/mapHandler.h index 4c440d8ce..6a0e5a7f9 100644 --- a/client/mapHandler.h +++ b/client/mapHandler.h @@ -23,17 +23,22 @@ #undef OUT #endif +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class CGHeroInstance; class CGBoat; class CMap; struct TerrainTile; +class PlayerColor; + +VCMI_LIB_NAMESPACE_END + struct SDL_Surface; struct SDL_Rect; class CAnimation; class IImage; class CFadeAnimation; -class PlayerColor; enum class EWorldViewIcon { diff --git a/client/widgets/AdventureMapClasses.h b/client/widgets/AdventureMapClasses.h index de9b98c8b..639732a9f 100644 --- a/client/widgets/AdventureMapClasses.h +++ b/client/widgets/AdventureMapClasses.h @@ -13,21 +13,26 @@ #include "../../lib/FunctionList.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class CArmedInstance; -class CAnimation; -class CAnimImage; -class CShowableAnim; -class CFilledTexture; class CGGarrison; class CGObjectInstance; class CGHeroInstance; class CGTownInstance; -class CButton; struct Component; -class CComponent; struct InfoAboutArmy; struct InfoAboutHero; struct InfoAboutTown; + +VCMI_LIB_NAMESPACE_END + +class CAnimation; +class CAnimImage; +class CShowableAnim; +class CFilledTexture; +class CButton; +class CComponent; class CHeroTooltip; class CTownTooltip; class CTextBox; diff --git a/client/widgets/Buttons.h b/client/widgets/Buttons.h index 9e8ac298b..d370b515e 100644 --- a/client/widgets/Buttons.h +++ b/client/widgets/Buttons.h @@ -14,17 +14,21 @@ #include "../../lib/FunctionList.h" +VCMI_LIB_NAMESPACE_BEGIN + +namespace config +{ +struct ButtonInfo; +} + +VCMI_LIB_NAMESPACE_END + struct SDL_Surface; struct Rect; class CAnimImage; class CLabel; class CAnimation; -namespace config -{ - struct ButtonInfo; -} - /// Typical Heroes 3 button which can be inactive or active and can /// hold further information if you right-click it class CButton : public CKeyShortcut diff --git a/client/widgets/CArtifactHolder.h b/client/widgets/CArtifactHolder.h index cdf92e69e..eff474737 100644 --- a/client/widgets/CArtifactHolder.h +++ b/client/widgets/CArtifactHolder.h @@ -11,12 +11,16 @@ #include "MiscWidgets.h" +VCMI_LIB_NAMESPACE_BEGIN + +struct ArtifactLocation; + +VCMI_LIB_NAMESPACE_END + class CArtifactsOfHero; class CAnimImage; class CButton; -struct ArtifactLocation; - class CArtifactHolder { public: diff --git a/client/widgets/CComponent.h b/client/widgets/CComponent.h index f46428b25..ba7ad3065 100644 --- a/client/widgets/CComponent.h +++ b/client/widgets/CComponent.h @@ -11,7 +11,12 @@ #include "../gui/CIntObject.h" +VCMI_LIB_NAMESPACE_BEGIN + struct Component; + +VCMI_LIB_NAMESPACE_END + class CAnimImage; class CLabel; diff --git a/client/widgets/CGarrisonInt.h b/client/widgets/CGarrisonInt.h index c14502a97..3c7a7914e 100644 --- a/client/widgets/CGarrisonInt.h +++ b/client/widgets/CGarrisonInt.h @@ -11,13 +11,18 @@ #include "../windows/CWindowObject.h" +VCMI_LIB_NAMESPACE_BEGIN + +class CArmedInstance; +class CCreatureSet; +class CStackInstance; + +VCMI_LIB_NAMESPACE_END + class CGarrisonInt; class CButton; -class CArmedInstance; class CAnimImage; -class CCreatureSet; class CGarrisonSlot; -class CStackInstance; class CLabel; /// A single garrison slot which holds one creature of a specific amount diff --git a/client/widgets/MiscWidgets.h b/client/widgets/MiscWidgets.h index c5f1088d7..f97a41bbf 100644 --- a/client/widgets/MiscWidgets.h +++ b/client/widgets/MiscWidgets.h @@ -11,13 +11,18 @@ #include "../gui/CIntObject.h" -class CLabel; -class CCreatureAnim; -class CComponent; +VCMI_LIB_NAMESPACE_BEGIN + class CGGarrison; struct InfoAboutArmy; class CArmedInstance; class IBonusBearer; + +VCMI_LIB_NAMESPACE_END + +class CLabel; +class CCreatureAnim; +class CComponent; class CAnimImage; /// Shows a text by moving the mouse cursor over the object diff --git a/client/windows/CAdvmapInterface.h b/client/windows/CAdvmapInterface.h index 6c851828d..eb38b3cd6 100644 --- a/client/windows/CAdvmapInterface.h +++ b/client/windows/CAdvmapInterface.h @@ -17,14 +17,19 @@ #include "../../lib/spells/ViewSpellInt.h" -class CCallback; +VCMI_LIB_NAMESPACE_BEGIN + struct CGPath; -class CAdvMapInt; class CGHeroInstance; class CGTownInstance; -class CHeroWindow; class CSpell; class IShipyard; + +VCMI_LIB_NAMESPACE_END + +class CCallback; +class CAdvMapInt; +class CHeroWindow; enum class EMapAnimRedrawStatus; class CFadeAnimation; diff --git a/client/windows/CCastleInterface.h b/client/windows/CCastleInterface.h index 088bb63bf..915e7579d 100644 --- a/client/windows/CCastleInterface.h +++ b/client/windows/CCastleInterface.h @@ -12,23 +12,28 @@ #include "../widgets/CGarrisonInt.h" #include "../widgets/Images.h" -class CButton; +VCMI_LIB_NAMESPACE_BEGIN + class CBuilding; +class CGTownInstance; +class CSpell; +struct CStructure; +class CGHeroInstance; +class CCreature; + +VCMI_LIB_NAMESPACE_END + +class CButton; class CCastleBuildings; class CCreaturePic; class CGStatusBar; -class CGTownInstance; class CLabel; class CMinorResDataBar; class CPicture; class CResDataBar; -class CSpell; class CTextBox; class CTownList; -struct CStructure; -class CGHeroInstance; class CGarrisonInt; -class CCreature; class CComponent; class CComponentBox; diff --git a/client/windows/CCreatureWindow.h b/client/windows/CCreatureWindow.h index f19f32689..ef51b57b8 100644 --- a/client/windows/CCreatureWindow.h +++ b/client/windows/CCreatureWindow.h @@ -13,11 +13,16 @@ #include "../widgets/MiscWidgets.h" #include "CWindowObject.h" -class UnitView; +VCMI_LIB_NAMESPACE_BEGIN + class CCommanderInstance; class CStackInstance; class CStack; struct UpgradeInfo; + +VCMI_LIB_NAMESPACE_END + +class UnitView; class CTabbedInt; class CButton; class CMultiLineLabel; diff --git a/client/windows/CHeroWindow.h b/client/windows/CHeroWindow.h index b973117e8..685741b23 100644 --- a/client/windows/CHeroWindow.h +++ b/client/windows/CHeroWindow.h @@ -13,9 +13,14 @@ #include "../widgets/CArtifactHolder.h" #include "../widgets/CGarrisonInt.h" +VCMI_LIB_NAMESPACE_BEGIN + +class CGHeroInstance; + +VCMI_LIB_NAMESPACE_END + class CButton; struct SDL_Surface; -class CGHeroInstance; class CHeroWindow; class LClickableAreaHero; class LRClickableAreaWText; diff --git a/client/windows/CQuestLog.cpp b/client/windows/CQuestLog.cpp index 85c1a2a5d..fd5763ec0 100644 --- a/client/windows/CQuestLog.cpp +++ b/client/windows/CQuestLog.cpp @@ -29,7 +29,12 @@ #include "../../lib/NetPacksBase.h" #include "../../lib/mapObjects/CQuest.h" +VCMI_LIB_NAMESPACE_BEGIN + struct QuestInfo; + +VCMI_LIB_NAMESPACE_END + class CAdvmapInterface; void CQuestLabel::clickLeft(tribool down, bool previousState) diff --git a/client/windows/CQuestLog.h b/client/windows/CQuestLog.h index 47a2dfa59..228776617 100644 --- a/client/windows/CQuestLog.h +++ b/client/windows/CQuestLog.h @@ -15,11 +15,17 @@ #include "../widgets/Images.h" #include "CWindowObject.h" +VCMI_LIB_NAMESPACE_BEGIN + class CCreature; class CStackInstance; +class CGHeroInstance; +struct QuestInfo; + +VCMI_LIB_NAMESPACE_END + class CButton; class CToggleButton; -class CGHeroInstance; class CComponentBox; class LRClickableAreaWText; class CButton; @@ -28,7 +34,6 @@ class CCreaturePic; class LRClickableAreaWTextComp; class CSlider; class CLabel; -struct QuestInfo; const int QUEST_COUNT = 6; const int DESCRIPTION_HEIGHT_MAX = 355; diff --git a/client/windows/CSpellWindow.h b/client/windows/CSpellWindow.h index e77a60267..b23891da1 100644 --- a/client/windows/CSpellWindow.h +++ b/client/windows/CSpellWindow.h @@ -11,17 +11,22 @@ #include "CWindowObject.h" +VCMI_LIB_NAMESPACE_BEGIN + +class CGHeroInstance; +class CSpell; + +VCMI_LIB_NAMESPACE_END + struct SDL_Surface; struct SDL_Rect; class IImage; class CAnimImage; class CPicture; class CLabel; -class CGHeroInstance; class CGStatusBar; class CPlayerInterface; class CSpellWindow; -class CSpell; /// The spell window class CSpellWindow : public CWindowObject diff --git a/client/windows/CTradeWindow.h b/client/windows/CTradeWindow.h index fd7049d69..a19a56a62 100644 --- a/client/windows/CTradeWindow.h +++ b/client/windows/CTradeWindow.h @@ -13,7 +13,12 @@ #include "CWindowObject.h" #include "../../lib/FunctionList.h" +VCMI_LIB_NAMESPACE_BEGIN + class IMarket; + +VCMI_LIB_NAMESPACE_END + class CSlider; class CTextBox; class CGStatusBar; diff --git a/client/windows/GUIClasses.h b/client/windows/GUIClasses.h index dc6bc9980..98494cfb6 100644 --- a/client/windows/GUIClasses.h +++ b/client/windows/GUIClasses.h @@ -17,9 +17,14 @@ #include "../widgets/CGarrisonInt.h" #include "../widgets/Images.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGDwelling; -class CreatureCostBox; class IMarket; + +VCMI_LIB_NAMESPACE_END + +class CreatureCostBox; class CCreaturePic; class MoraleLuckBox; class CHeroArea; diff --git a/client/windows/InfoWindows.h b/client/windows/InfoWindows.h index 95924308d..c05983bcc 100644 --- a/client/windows/InfoWindows.h +++ b/client/windows/InfoWindows.h @@ -12,6 +12,12 @@ #include "CWindowObject.h" #include "../../lib/FunctionList.h" +VCMI_LIB_NAMESPACE_BEGIN + +class CGGarrison; + +VCMI_LIB_NAMESPACE_END + struct SDL_Surface; struct Rect; class CAnimImage; @@ -19,7 +25,6 @@ class CLabel; class CAnimation; class CComponent; class CSelectableComponent; -class CGGarrison; class CTextBox; class CButton; class CSlider; diff --git a/include/vcmi/Artifact.h b/include/vcmi/Artifact.h index 7ffd8431f..f9f7ad89e 100644 --- a/include/vcmi/Artifact.h +++ b/include/vcmi/Artifact.h @@ -12,6 +12,8 @@ #include "Entity.h" +VCMI_LIB_NAMESPACE_BEGIN + class ArtifactID; class CreatureID; @@ -25,3 +27,5 @@ public: virtual uint32_t getPrice() const = 0; virtual CreatureID getWarMachine() const = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/ArtifactService.h b/include/vcmi/ArtifactService.h index 3dc8588b1..ecd8ebc99 100644 --- a/include/vcmi/ArtifactService.h +++ b/include/vcmi/ArtifactService.h @@ -12,6 +12,8 @@ #include "EntityService.h" +VCMI_LIB_NAMESPACE_BEGIN + class ArtifactID; class Artifact; @@ -19,3 +21,5 @@ class DLL_LINKAGE ArtifactService : public EntityServiceT { public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/Creature.h b/include/vcmi/Creature.h index c3c5ba2a2..1ada50ce2 100644 --- a/include/vcmi/Creature.h +++ b/include/vcmi/Creature.h @@ -12,6 +12,8 @@ #include "Entity.h" +VCMI_LIB_NAMESPACE_BEGIN + class CreatureID; class DLL_LINKAGE Creature : public EntityWithBonuses @@ -43,3 +45,5 @@ public: virtual bool isDoubleWide() const = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/CreatureService.h b/include/vcmi/CreatureService.h index 2e3ad04e0..860a3a575 100644 --- a/include/vcmi/CreatureService.h +++ b/include/vcmi/CreatureService.h @@ -12,6 +12,8 @@ #include "EntityService.h" +VCMI_LIB_NAMESPACE_BEGIN + class CreatureID; class Creature; @@ -19,3 +21,5 @@ class DLL_LINKAGE CreatureService : public EntityServiceT { public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/Entity.h b/include/vcmi/Entity.h index 877cb3372..77a70f5d1 100644 --- a/include/vcmi/Entity.h +++ b/include/vcmi/Entity.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class IBonusBearer; class DLL_LINKAGE Entity @@ -40,3 +42,5 @@ class DLL_LINKAGE EntityWithBonuses : public EntityT public: virtual const IBonusBearer * accessBonuses() const = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/EntityService.h b/include/vcmi/EntityService.h index 1b818131e..96c90ca5d 100644 --- a/include/vcmi/EntityService.h +++ b/include/vcmi/EntityService.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class Entity; class DLL_LINKAGE EntityService @@ -30,3 +32,5 @@ public: virtual void forEach(const std::function & cb) const = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/Environment.h b/include/vcmi/Environment.h index 0fa63aa89..8c456bca2 100644 --- a/include/vcmi/Environment.h +++ b/include/vcmi/Environment.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class Services; class IGameInfoCallback; @@ -23,8 +25,8 @@ namespace events class DLL_LINKAGE Environment { public: - using BattleCb = ::IBattleInfoCallback; - using GameCb = ::IGameInfoCallback; + using BattleCb = IBattleInfoCallback; + using GameCb = IGameInfoCallback; virtual ~Environment() = default; @@ -34,3 +36,5 @@ public: virtual vstd::CLoggerBase * logger() const = 0; virtual events::EventBus * eventBus() const = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/Faction.h b/include/vcmi/Faction.h index 5fc52c2fb..de50f29b9 100644 --- a/include/vcmi/Faction.h +++ b/include/vcmi/Faction.h @@ -12,6 +12,8 @@ #include "Entity.h" +VCMI_LIB_NAMESPACE_BEGIN + class FactionID; class DLL_LINKAGE Faction : public EntityT @@ -19,3 +21,5 @@ class DLL_LINKAGE Faction : public EntityT public: virtual bool hasTown() const = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/FactionService.h b/include/vcmi/FactionService.h index 884d77868..94cf78122 100644 --- a/include/vcmi/FactionService.h +++ b/include/vcmi/FactionService.h @@ -12,6 +12,8 @@ #include "EntityService.h" +VCMI_LIB_NAMESPACE_BEGIN + class FactionID; class Faction; @@ -19,3 +21,5 @@ class DLL_LINKAGE FactionService : public EntityServiceT { public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/HeroClass.h b/include/vcmi/HeroClass.h index 713672003..5440910e0 100644 --- a/include/vcmi/HeroClass.h +++ b/include/vcmi/HeroClass.h @@ -12,6 +12,8 @@ #include "Entity.h" +VCMI_LIB_NAMESPACE_BEGIN + class HeroClassID; class DLL_LINKAGE HeroClass : public EntityT @@ -20,3 +22,5 @@ public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/HeroClassService.h b/include/vcmi/HeroClassService.h index 9fb85c00b..df872c08d 100644 --- a/include/vcmi/HeroClassService.h +++ b/include/vcmi/HeroClassService.h @@ -12,6 +12,8 @@ #include "EntityService.h" +VCMI_LIB_NAMESPACE_BEGIN + class HeroClassID; class HeroClass; @@ -19,3 +21,5 @@ class DLL_LINKAGE HeroClassService : public EntityServiceT @@ -20,3 +22,5 @@ public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/HeroTypeService.h b/include/vcmi/HeroTypeService.h index 81f4305bb..dca8a438f 100644 --- a/include/vcmi/HeroTypeService.h +++ b/include/vcmi/HeroTypeService.h @@ -12,6 +12,8 @@ #include "EntityService.h" +VCMI_LIB_NAMESPACE_BEGIN + class HeroTypeID; class HeroType; @@ -19,3 +21,5 @@ class DLL_LINKAGE HeroTypeService : public EntityServiceT { public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/Metatype.h b/include/vcmi/Metatype.h index e8101f4c8..0ed9b1464 100644 --- a/include/vcmi/Metatype.h +++ b/include/vcmi/Metatype.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + enum class Metatype : uint32_t { UNKNOWN = 0, @@ -28,3 +30,5 @@ enum class Metatype : uint32_t SPELL }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/Player.h b/include/vcmi/Player.h index ac79e94a1..d559d1e7b 100644 --- a/include/vcmi/Player.h +++ b/include/vcmi/Player.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class PlayerColor; class TeamID; class IBonusBearer; @@ -24,7 +26,4 @@ public: virtual int getResourceAmount(int type) const = 0; }; - - - - +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/ServerCallback.h b/include/vcmi/ServerCallback.h index af35b4ea5..d69257009 100644 --- a/include/vcmi/ServerCallback.h +++ b/include/vcmi/ServerCallback.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace vstd { class RNG; @@ -44,3 +46,5 @@ public: virtual void apply(BattleObstaclesChanged * pack) = 0; virtual void apply(CatapultAttack * pack) = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/Services.h b/include/vcmi/Services.h index 1bc33a1dd..33535a1d4 100644 --- a/include/vcmi/Services.h +++ b/include/vcmi/Services.h @@ -12,6 +12,8 @@ #include "Metatype.h" +VCMI_LIB_NAMESPACE_BEGIN + class ArtifactService; class CreatureService; class FactionService; @@ -63,3 +65,5 @@ public: virtual spells::effects::Registry * spellEffects() = 0; //TODO: put map object types registry access here }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/Skill.h b/include/vcmi/Skill.h index 14b308486..363e67869 100644 --- a/include/vcmi/Skill.h +++ b/include/vcmi/Skill.h @@ -12,6 +12,8 @@ #include "Entity.h" +VCMI_LIB_NAMESPACE_BEGIN + class SecondarySkill; class DLL_LINKAGE Skill : public EntityT @@ -20,3 +22,5 @@ public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/SkillService.h b/include/vcmi/SkillService.h index 47a9bbce9..6e8618898 100644 --- a/include/vcmi/SkillService.h +++ b/include/vcmi/SkillService.h @@ -12,6 +12,8 @@ #include "EntityService.h" +VCMI_LIB_NAMESPACE_BEGIN + class SecondarySkill; class Skill; @@ -19,3 +21,5 @@ class DLL_LINKAGE SkillService : public EntityServiceT { public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/ApplyDamage.h b/include/vcmi/events/ApplyDamage.h index c92e80aeb..5ea190e4f 100644 --- a/include/vcmi/events/ApplyDamage.h +++ b/include/vcmi/events/ApplyDamage.h @@ -13,6 +13,8 @@ #include "Event.h" #include "SubscriptionRegistry.h" +VCMI_LIB_NAMESPACE_BEGIN + struct BattleStackAttacked; namespace battle @@ -43,3 +45,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/Event.h b/include/vcmi/events/Event.h index 3f92a30bc..a1b44ccc7 100644 --- a/include/vcmi/events/Event.h +++ b/include/vcmi/events/Event.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -27,3 +29,5 @@ public: } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/EventBus.h b/include/vcmi/events/EventBus.h index e77f53370..4e46be043 100644 --- a/include/vcmi/events/EventBus.h +++ b/include/vcmi/events/EventBus.h @@ -12,6 +12,8 @@ #include "SubscriptionRegistry.h" +VCMI_LIB_NAMESPACE_BEGIN + class Environment; namespace events @@ -42,3 +44,5 @@ public: } }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/GameResumed.h b/include/vcmi/events/GameResumed.h index 33a8436f1..0bc7f99e7 100644 --- a/include/vcmi/events/GameResumed.h +++ b/include/vcmi/events/GameResumed.h @@ -13,6 +13,8 @@ #include "Event.h" #include "SubscriptionRegistry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -33,3 +35,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/ObjectVisitEnded.h b/include/vcmi/events/ObjectVisitEnded.h index b8508e260..7789d5e3a 100644 --- a/include/vcmi/events/ObjectVisitEnded.h +++ b/include/vcmi/events/ObjectVisitEnded.h @@ -13,6 +13,8 @@ #include "Event.h" #include "SubscriptionRegistry.h" +VCMI_LIB_NAMESPACE_BEGIN + class PlayerColor; class ObjectInstanceID; @@ -38,3 +40,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/ObjectVisitStarted.h b/include/vcmi/events/ObjectVisitStarted.h index 8e8577ca0..747aaf02c 100644 --- a/include/vcmi/events/ObjectVisitStarted.h +++ b/include/vcmi/events/ObjectVisitStarted.h @@ -13,6 +13,8 @@ #include "Event.h" #include "SubscriptionRegistry.h" +VCMI_LIB_NAMESPACE_BEGIN + class PlayerColor; class ObjectInstanceID; @@ -41,3 +43,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/PlayerGotTurn.h b/include/vcmi/events/PlayerGotTurn.h index 4b6fa009b..a75380cca 100644 --- a/include/vcmi/events/PlayerGotTurn.h +++ b/include/vcmi/events/PlayerGotTurn.h @@ -13,6 +13,8 @@ #include "Event.h" #include "SubscriptionRegistry.h" +VCMI_LIB_NAMESPACE_BEGIN + class PlayerColor; namespace events @@ -39,3 +41,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/SubscriptionRegistry.h b/include/vcmi/events/SubscriptionRegistry.h index 01af2876f..0e273d79c 100644 --- a/include/vcmi/events/SubscriptionRegistry.h +++ b/include/vcmi/events/SubscriptionRegistry.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class Environment; namespace events @@ -164,3 +166,5 @@ private: } }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/events/TurnStarted.h b/include/vcmi/events/TurnStarted.h index 1caccddf6..a5a600047 100644 --- a/include/vcmi/events/TurnStarted.h +++ b/include/vcmi/events/TurnStarted.h @@ -13,6 +13,8 @@ #include "Event.h" #include "SubscriptionRegistry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -31,3 +33,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/scripting/Service.h b/include/vcmi/scripting/Service.h index e94300598..c000ae052 100644 --- a/include/vcmi/scripting/Service.h +++ b/include/vcmi/scripting/Service.h @@ -13,6 +13,8 @@ #if SCRIPTING_ENABLED #include +VCMI_LIB_NAMESPACE_BEGIN + class Services; class JsonNode; class ServerCallback; @@ -20,8 +22,8 @@ class ServerCallback; namespace scripting { -using BattleCb = ::Environment::BattleCb; -using GameCb = ::Environment::GameCb; +using BattleCb = Environment::BattleCb; +using GameCb = Environment::GameCb; class DLL_LINKAGE Context { @@ -79,4 +81,6 @@ public: } + +VCMI_LIB_NAMESPACE_END #endif diff --git a/include/vcmi/spells/Caster.h b/include/vcmi/spells/Caster.h index 5ed5ca475..123865a97 100644 --- a/include/vcmi/spells/Caster.h +++ b/include/vcmi/spells/Caster.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class PlayerColor; struct MetaString; class ServerCallback; @@ -66,3 +68,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/spells/Magic.h b/include/vcmi/spells/Magic.h index 65d7f5ef2..af69982f2 100644 --- a/include/vcmi/spells/Magic.h +++ b/include/vcmi/spells/Magic.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + struct MetaString; namespace battle @@ -24,7 +26,7 @@ class Caster; class Spell; class Mechanics; class BattleCast; -using Destination = ::battle::Destination; +using Destination = battle::Destination; using Target = std::vector; @@ -67,3 +69,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/spells/Service.h b/include/vcmi/spells/Service.h index badd9487a..98fb863a7 100644 --- a/include/vcmi/spells/Service.h +++ b/include/vcmi/spells/Service.h @@ -12,6 +12,8 @@ #include "../EntityService.h" +VCMI_LIB_NAMESPACE_BEGIN + class SpellID; namespace spells @@ -24,3 +26,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vcmi/spells/Spell.h b/include/vcmi/spells/Spell.h index e64fb11a4..302ae05f6 100644 --- a/include/vcmi/spells/Spell.h +++ b/include/vcmi/spells/Spell.h @@ -12,6 +12,8 @@ #include "../Entity.h" +VCMI_LIB_NAMESPACE_BEGIN + class SpellID; namespace spells @@ -54,3 +56,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vstd/CLoggerBase.h b/include/vstd/CLoggerBase.h index 0c5ad7f10..24df8a0a7 100644 --- a/include/vstd/CLoggerBase.h +++ b/include/vstd/CLoggerBase.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace ELogLevel { enum ELogLevel @@ -191,3 +193,5 @@ extern DLL_LINKAGE vstd::CLoggerBase * logNetwork; extern DLL_LINKAGE vstd::CLoggerBase * logAi; extern DLL_LINKAGE vstd::CLoggerBase * logAnim; extern DLL_LINKAGE vstd::CLoggerBase * logMod; + +VCMI_LIB_NAMESPACE_END diff --git a/include/vstd/ContainerUtils.h b/include/vstd/ContainerUtils.h index cb616a775..0e93a13e5 100644 --- a/include/vstd/ContainerUtils.h +++ b/include/vstd/ContainerUtils.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace vstd { template @@ -24,5 +26,4 @@ namespace vstd } } - - +VCMI_LIB_NAMESPACE_END diff --git a/include/vstd/RNG.h b/include/vstd/RNG.h index 5535b13e9..9a8653141 100644 --- a/include/vstd/RNG.h +++ b/include/vstd/RNG.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace vstd { @@ -56,3 +58,5 @@ namespace RandomGeneratorUtil } } } + +VCMI_LIB_NAMESPACE_END diff --git a/include/vstd/StringUtils.h b/include/vstd/StringUtils.h index 9b90fdbe3..b6d3ac8e4 100644 --- a/include/vstd/StringUtils.h +++ b/include/vstd/StringUtils.h @@ -1,5 +1,7 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace vstd { @@ -7,3 +9,5 @@ namespace vstd DLL_LINKAGE std::pair splitStringToPair(std::string input, char separator); } + +VCMI_LIB_NAMESPACE_END diff --git a/launcher/updatedialog_moc.h b/launcher/updatedialog_moc.h index aab93ff89..93ec1f1ea 100644 --- a/launcher/updatedialog_moc.h +++ b/launcher/updatedialog_moc.h @@ -11,8 +11,12 @@ #include #include +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; +VCMI_LIB_NAMESPACE_END + namespace Ui { class UpdateDialog; } diff --git a/lib/BattleFieldHandler.cpp b/lib/BattleFieldHandler.cpp index 1155e1d3f..18fc7664c 100644 --- a/lib/BattleFieldHandler.cpp +++ b/lib/BattleFieldHandler.cpp @@ -12,6 +12,8 @@ #include #include "BattleFieldHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + BattleFieldInfo * BattleFieldHandler::loadFromJson(const std::string & scope, const JsonNode & json, const std::string & identifier, size_t index) { BattleFieldInfo * info = new BattleFieldInfo(BattleField(index), identifier); @@ -105,4 +107,6 @@ void BattleFieldInfo::registerIcons(const IconRegistar & cb) const BattleField BattleFieldInfo::getId() const { return battlefield; -} \ No newline at end of file +} + +VCMI_LIB_NAMESPACE_END diff --git a/lib/BattleFieldHandler.h b/lib/BattleFieldHandler.h index b9023f3d0..51822e0cc 100644 --- a/lib/BattleFieldHandler.h +++ b/lib/BattleFieldHandler.h @@ -17,6 +17,8 @@ #include "Terrain.h" #include "battle/BattleHex.h" +VCMI_LIB_NAMESPACE_BEGIN + class BattleFieldInfo : public EntityT { public: @@ -84,3 +86,5 @@ public: h & objects; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CArtHandler.cpp b/lib/CArtHandler.cpp index daeaa632c..4cf2d9d69 100644 --- a/lib/CArtHandler.cpp +++ b/lib/CArtHandler.cpp @@ -48,6 +48,8 @@ ART_POS(SHOULDERS) \ ART_POS(HEAD) +VCMI_LIB_NAMESPACE_BEGIN + int32_t CArtifact::getIndex() const { return id.toEnum(); @@ -1434,3 +1436,5 @@ void CArtifactSet::serializeJsonSlot(JsonSerializeFormat & handler, const Artifa } } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CArtHandler.h b/lib/CArtHandler.h index 2bf087101..9a0d55be0 100644 --- a/lib/CArtHandler.h +++ b/lib/CArtHandler.h @@ -16,6 +16,8 @@ #include "GameConstants.h" #include "IHandlerBase.h" +VCMI_LIB_NAMESPACE_BEGIN + class CArtHandler; class CArtifact; class CGHeroInstance; @@ -358,3 +360,5 @@ private: void serializeJsonSlot(JsonSerializeFormat & handler, const ArtifactPosition & slot, CMap * map);//normal slots }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CBonusTypeHandler.cpp b/lib/CBonusTypeHandler.cpp index bb31926e0..00342ec9f 100644 --- a/lib/CBonusTypeHandler.cpp +++ b/lib/CBonusTypeHandler.cpp @@ -20,7 +20,9 @@ #include "CCreatureHandler.h" #include "spells/CSpellHandler.h" -template class std::vector; +template class std::vector; + +VCMI_LIB_NAMESPACE_BEGIN ///MacroString @@ -326,3 +328,5 @@ void CBonusTypeHandler::loadItem(const JsonNode & source, CBonusType & dest) } dest.buildMacros(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CBonusTypeHandler.h b/lib/CBonusTypeHandler.h index 0b64a0434..977efe051 100644 --- a/lib/CBonusTypeHandler.h +++ b/lib/CBonusTypeHandler.h @@ -14,6 +14,8 @@ #include "IHandlerBase.h" #include "HeroBonus.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; @@ -94,6 +96,8 @@ private: std::vector bonusTypes; //index = BonusTypeID }; +VCMI_LIB_NAMESPACE_END + #ifndef INSTANTIATE_CBonusTypeHandler_HERE -extern template class std::vector; +extern template class std::vector; #endif diff --git a/lib/CBuildingHandler.cpp b/lib/CBuildingHandler.cpp index 5543d9805..ee48359da 100644 --- a/lib/CBuildingHandler.cpp +++ b/lib/CBuildingHandler.cpp @@ -10,6 +10,8 @@ #include "StdInc.h" #include "CBuildingHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + BuildingID CBuildingHandler::campToERMU( int camp, int townType, std::set builtBuildings ) { static const std::vector campToERMU = @@ -75,3 +77,5 @@ BuildingID CBuildingHandler::campToERMU( int camp, int townType, std::set builtBuildings); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CConfigHandler.cpp b/lib/CConfigHandler.cpp index cc962b3cd..d2de0e086 100644 --- a/lib/CConfigHandler.cpp +++ b/lib/CConfigHandler.cpp @@ -15,6 +15,8 @@ #include "../lib/GameConstants.h" #include "../lib/VCMIDirs.h" +VCMI_LIB_NAMESPACE_BEGIN + using namespace config; SettingsStorage settings; @@ -302,3 +304,5 @@ void config::CConfigHandler::init() // That way method definitions can sit in the cpp file template struct SettingsStorage::NodeAccessor; template struct SettingsStorage::NodeAccessor; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CConfigHandler.h b/lib/CConfigHandler.h index dad7e66ba..7a579d39a 100644 --- a/lib/CConfigHandler.h +++ b/lib/CConfigHandler.h @@ -11,6 +11,8 @@ #include "../lib/JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + class Settings; class SettingsListener; @@ -188,3 +190,5 @@ namespace config extern DLL_LINKAGE SettingsStorage settings; extern DLL_LINKAGE config::CConfigHandler conf; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CConsoleHandler.cpp b/lib/CConsoleHandler.cpp index b5489b984..52d85bc91 100644 --- a/lib/CConsoleHandler.cpp +++ b/lib/CConsoleHandler.cpp @@ -13,6 +13,8 @@ #include "CThreadHelper.h" +VCMI_LIB_NAMESPACE_BEGIN + boost::mutex CConsoleHandler::smx; DLL_LINKAGE CConsoleHandler * console = nullptr; @@ -285,3 +287,5 @@ void CConsoleHandler::start() { thread = new boost::thread(std::bind(&CConsoleHandler::run,console)); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CConsoleHandler.h b/lib/CConsoleHandler.h index c521acdd5..4ac139260 100644 --- a/lib/CConsoleHandler.h +++ b/lib/CConsoleHandler.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace EConsoleTextColor { /** The color enum is used for colored text console output. */ @@ -92,3 +94,5 @@ private: }; extern DLL_LINKAGE CConsoleHandler * console; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CCreatureHandler.cpp b/lib/CCreatureHandler.cpp index 709b40242..bc27abe42 100644 --- a/lib/CCreatureHandler.cpp +++ b/lib/CCreatureHandler.cpp @@ -22,6 +22,8 @@ #include "serializer/JsonUpdater.h" #include "mapObjects/CObjectClassesHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + int32_t CCreature::getIndex() const { return idNumber.toEnum(); @@ -1360,3 +1362,5 @@ void CCreatureHandler::deserializationFix() { buildBonusTreeForTiers(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CCreatureHandler.h b/lib/CCreatureHandler.h index 66f652a59..4a3bbe6e4 100644 --- a/lib/CCreatureHandler.h +++ b/lib/CCreatureHandler.h @@ -21,6 +21,8 @@ #include "CRandomGenerator.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class CLegacyConfigParser; class CCreatureHandler; class CCreature; @@ -303,3 +305,5 @@ public: BONUS_TREE_DESERIALIZATION_FIX } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CCreatureSet.cpp b/lib/CCreatureSet.cpp index 35e6a4a24..6753c7174 100644 --- a/lib/CCreatureSet.cpp +++ b/lib/CCreatureSet.cpp @@ -23,6 +23,8 @@ #include "serializer/JsonSerializeFormat.h" #include "NetPacksBase.h" +VCMI_LIB_NAMESPACE_BEGIN + bool CreatureSlotComparer::operator()(const TPairCreatureSlot & lhs, const TPairCreatureSlot & rhs) { @@ -1074,3 +1076,5 @@ bool CSimpleArmy::setCreature(SlotID slot, CreatureID cre, TQuantity count) army[slot] = std::make_pair(cre, count); return true; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CCreatureSet.h b/lib/CCreatureSet.h index f073f5671..484133c2b 100644 --- a/lib/CCreatureSet.h +++ b/lib/CCreatureSet.h @@ -13,6 +13,8 @@ #include "GameConstants.h" #include "CArtHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; class CCreature; class CGHeroInstance; @@ -262,3 +264,5 @@ public: } void sweep(); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGameInfoCallback.cpp b/lib/CGameInfoCallback.cpp index 0d0a8d6b0..6ec0febe7 100644 --- a/lib/CGameInfoCallback.cpp +++ b/lib/CGameInfoCallback.cpp @@ -21,6 +21,8 @@ #include "mapping/CMap.h" #include "CPlayerState.h" +VCMI_LIB_NAMESPACE_BEGIN + //TODO make clean #define ERROR_VERBOSE_OR_NOT_RET_VAL_IF(cond, verbose, txt, retVal) do {if(cond){if(verbose)logGlobal->error("%s: %s",BOOST_CURRENT_FUNCTION, txt); return retVal;}} while(0) #define ERROR_RET_IF(cond, txt) do {if(cond){logGlobal->error("%s: %s", BOOST_CURRENT_FUNCTION, txt); return;}} while(0) @@ -999,3 +1001,5 @@ bool CGameInfoCallback::isTeleportEntrancePassable(const CGTeleport * obj, Playe { return obj && obj->isEntrance() && !isTeleportChannelImpassable(obj->channel, player); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGameInfoCallback.h b/lib/CGameInfoCallback.h index 53aa5524f..70d3a45cf 100644 --- a/lib/CGameInfoCallback.h +++ b/lib/CGameInfoCallback.h @@ -12,6 +12,9 @@ #include "int3.h" #include "ResourceSet.h" // for Res::ERes #include "battle/CCallbackBase.h" + +VCMI_LIB_NAMESPACE_BEGIN + class Player; class Team; @@ -239,3 +242,5 @@ public: //virtual const PlayerSettings * getPlayerSettings(PlayerColor color) const; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGameInterface.cpp b/lib/CGameInterface.cpp index 84b9e9745..5abf49072 100644 --- a/lib/CGameInterface.cpp +++ b/lib/CGameInterface.cpp @@ -29,6 +29,8 @@ #endif +VCMI_LIB_NAMESPACE_BEGIN + template std::shared_ptr createAny(const boost::filesystem::path & libpath, const std::string & methodName) { @@ -257,3 +259,5 @@ void CAdventureAI::loadGame(BinaryDeserializer & h, const int version) /*loading battleAI->init(env, cbc); } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGameInterface.h b/lib/CGameInterface.h index c4ab18378..2228a86e3 100644 --- a/lib/CGameInterface.h +++ b/lib/CGameInterface.h @@ -17,12 +17,15 @@ #include "mapObjects/CObjectHandler.h" +class CBattleCallback; +class CCallback; + +VCMI_LIB_NAMESPACE_BEGIN + using boost::logic::tribool; class Environment; -class CCallback; -class CBattleCallback; class ICallback; class CGlobalAI; struct Component; @@ -159,3 +162,5 @@ public: virtual void saveGame(BinarySerializer & h, const int version) override; virtual void loadGame(BinaryDeserializer & h, const int version) override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGameState.cpp b/lib/CGameState.cpp index c81a760c6..e70643c5f 100644 --- a/lib/CGameState.cpp +++ b/lib/CGameState.cpp @@ -37,6 +37,8 @@ #include "serializer/CMemorySerializer.h" #include "VCMIDirs.h" +VCMI_LIB_NAMESPACE_BEGIN + boost::shared_mutex CGameState::mutex; template class CApplyOnGS; @@ -3106,3 +3108,5 @@ CRandomGenerator & CGameState::getRandomGenerator() { return rand; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGameState.h b/lib/CGameState.h index 84e3077b3..862ac4c2c 100644 --- a/lib/CGameState.h +++ b/lib/CGameState.h @@ -22,8 +22,14 @@ #include "CGameStateFwd.h" #include "CPathfinder.h" +namespace boost +{ +class shared_mutex; +} + +VCMI_LIB_NAMESPACE_BEGIN + class CTown; -class CCallback; class IGameCallback; class CCreatureSet; class CQuest; @@ -36,7 +42,6 @@ class CGObjectInstance; class CCreature; class CMap; struct StartInfo; -class CMapHandler; struct SetObjectProperty; struct MetaString; struct CPack; @@ -47,7 +52,6 @@ class CCampaign; class CCampaignState; class IModableArt; class CGGarrison; -class CGameInfo; struct QuestInfo; class CQuest; class CCampaignScenario; @@ -55,12 +59,6 @@ struct EventCondition; class CScenarioTravel; class IMapService; -namespace boost -{ - class shared_mutex; -} - - template class CApplier; class CBaseForGSApply; @@ -305,3 +303,5 @@ private: friend class CMapHandler; friend class CGameHandler; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGameStateFwd.h b/lib/CGameStateFwd.h index 63904fcb1..1f1b5c660 100644 --- a/lib/CGameStateFwd.h +++ b/lib/CGameStateFwd.h @@ -12,6 +12,8 @@ #include "CCreatureSet.h" #include "int3.h" +VCMI_LIB_NAMESPACE_BEGIN + class CQuest; class CGObjectInstance; class CHeroClass; @@ -206,3 +208,5 @@ struct DLL_LINKAGE QuestInfo //universal interface for human and AI h & tile; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGeneralTextHandler.cpp b/lib/CGeneralTextHandler.cpp index aa19fdfb3..b8070c7e6 100644 --- a/lib/CGeneralTextHandler.cpp +++ b/lib/CGeneralTextHandler.cpp @@ -19,6 +19,8 @@ #include "VCMI_Lib.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + size_t Unicode::getCharacterSize(char firstByte) { // length of utf-8 character can be determined from 1st byte by counting number of highest bits set to 1: @@ -519,3 +521,5 @@ int32_t CGeneralTextHandler::pluralText(const int32_t textIndex, const int32_t c else return textIndex + 1; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CGeneralTextHandler.h b/lib/CGeneralTextHandler.h index 58feed9ce..b7bffd1f9 100644 --- a/lib/CGeneralTextHandler.h +++ b/lib/CGeneralTextHandler.h @@ -11,6 +11,8 @@ #include "JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + /// Namespace that provides utilites for unicode support (UTF-8) namespace Unicode { @@ -149,3 +151,5 @@ public: CGeneralTextHandler(const CGeneralTextHandler&) = delete; CGeneralTextHandler operator=(const CGeneralTextHandler&) = delete; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CHeroHandler.cpp b/lib/CHeroHandler.cpp index 890189eeb..6ed393ae5 100644 --- a/lib/CHeroHandler.cpp +++ b/lib/CHeroHandler.cpp @@ -27,6 +27,8 @@ #include "mapObjects/CObjectClassesHandler.h" #include "BattleFieldHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + CHero::CHero() = default; CHero::~CHero() = default; @@ -991,3 +993,5 @@ std::vector CHeroHandler::getDefaultAllowed() const return allowedHeroes; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CHeroHandler.h b/lib/CHeroHandler.h index 87da89149..d24f3de15 100644 --- a/lib/CHeroHandler.h +++ b/lib/CHeroHandler.h @@ -20,8 +20,9 @@ #include "IHandlerBase.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class CHeroClass; -class CGameInfo; class CGHeroInstance; struct BattleHex; class JsonNode; @@ -316,3 +317,5 @@ protected: const std::vector & getTypeNames() const override; CHero * loadFromJson(const std::string & scope, const JsonNode & node, const std::string & identifier, size_t index) override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CModHandler.cpp b/lib/CModHandler.cpp index e8a72cb5b..36a36dadc 100644 --- a/lib/CModHandler.cpp +++ b/lib/CModHandler.cpp @@ -30,6 +30,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + CIdentifierStorage::CIdentifierStorage(): state(LOADING) { @@ -1144,3 +1146,5 @@ std::string CModHandler::makeFullIdentifier(const std::string & scope, const std return actualName == "" ? actualScope+ ":" + type : actualScope + ":" + type + "." + actualName; } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CModHandler.h b/lib/CModHandler.h index 1605f59fd..01f7a092b 100644 --- a/lib/CModHandler.h +++ b/lib/CModHandler.h @@ -14,6 +14,8 @@ #include "VCMI_Lib.h" #include "JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + class CModHandler; class CModIndentifier; class CModInfo; @@ -398,3 +400,5 @@ public: h & identifiers; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CPathfinder.cpp b/lib/CPathfinder.cpp index 6ae919db0..0961ee52a 100644 --- a/lib/CPathfinder.cpp +++ b/lib/CPathfinder.cpp @@ -20,6 +20,8 @@ #include "CPlayerState.h" #include "PathfinderUtil.h" +VCMI_LIB_NAMESPACE_BEGIN + bool canSeeObj(const CGObjectInstance * obj) { /// Pathfinder should ignore placed events @@ -1424,3 +1426,5 @@ bool PathNodeInfo::isNodeObjectVisitable() const return (node->layer == EPathfindingLayer::LAND || node->layer == EPathfindingLayer::SAIL) && (canSeeObj(nodeObject) || canSeeObj(nodeHero)); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CPathfinder.h b/lib/CPathfinder.h index c047701a4..a5ed9e764 100644 --- a/lib/CPathfinder.h +++ b/lib/CPathfinder.h @@ -17,6 +17,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class CGObjectInstance; @@ -610,3 +612,5 @@ public: int movementPointsAfterEmbark(int movement, int basicCost, bool disembark) const; bool passOneTurnLimitCheck(const PathNodeInfo & source) const; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CPlayerState.cpp b/lib/CPlayerState.cpp index 78ee6b68a..edcc8c0db 100644 --- a/lib/CPlayerState.cpp +++ b/lib/CPlayerState.cpp @@ -12,6 +12,8 @@ #include "CPlayerState.h" #include "CGameStateFwd.h" +VCMI_LIB_NAMESPACE_BEGIN + PlayerState::PlayerState() : color(-1), human(false), enteredWinningCheatCode(false), enteredLosingCheatCode(false), status(EPlayerStatus::INGAME) @@ -67,3 +69,5 @@ int PlayerState::getResourceAmount(int type) const { return vstd::atOrDefault(resources, static_cast(type), 0); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CPlayerState.h b/lib/CPlayerState.h index 1caafa314..4d042f434 100644 --- a/lib/CPlayerState.h +++ b/lib/CPlayerState.h @@ -15,6 +15,8 @@ #include "HeroBonus.h" #include "ResourceSet.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class CGTownInstance; class CGDwelling; @@ -95,3 +97,5 @@ public: } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CRandomGenerator.cpp b/lib/CRandomGenerator.cpp index c05b126b3..f55e97030 100644 --- a/lib/CRandomGenerator.cpp +++ b/lib/CRandomGenerator.cpp @@ -11,6 +11,8 @@ #include "StdInc.h" #include "CRandomGenerator.h" +VCMI_LIB_NAMESPACE_BEGIN + boost::thread_specific_ptr CRandomGenerator::defaultRand; CRandomGenerator::CRandomGenerator() @@ -88,3 +90,5 @@ TGenerator & CRandomGenerator::getStdGenerator() { return rand; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CRandomGenerator.h b/lib/CRandomGenerator.h index 0d052b32b..0b14c65ee 100644 --- a/lib/CRandomGenerator.h +++ b/lib/CRandomGenerator.h @@ -12,6 +12,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + typedef std::mt19937 TGenerator; typedef std::uniform_int_distribution TIntDist; typedef std::uniform_int_distribution TInt64Dist; @@ -98,3 +100,5 @@ public: } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CScriptingModule.cpp b/lib/CScriptingModule.cpp index c6da26f01..f54ea063d 100644 --- a/lib/CScriptingModule.cpp +++ b/lib/CScriptingModule.cpp @@ -12,6 +12,8 @@ #include "CScriptingModule.h" #if SCRIPTING_ENABLED +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { @@ -31,4 +33,6 @@ Module::Module() Module::~Module() = default; } + +VCMI_LIB_NAMESPACE_END #endif diff --git a/lib/CScriptingModule.h b/lib/CScriptingModule.h index 77b59249f..9197d4951 100644 --- a/lib/CScriptingModule.h +++ b/lib/CScriptingModule.h @@ -12,6 +12,8 @@ #if SCRIPTING_ENABLED #include +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -46,4 +48,6 @@ public: }; } + +VCMI_LIB_NAMESPACE_END #endif diff --git a/lib/CSkillHandler.cpp b/lib/CSkillHandler.cpp index feea6b009..74da3179c 100644 --- a/lib/CSkillHandler.cpp +++ b/lib/CSkillHandler.cpp @@ -22,6 +22,8 @@ #include "CModHandler.h" #include "StringConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + ///CSkill CSkill::LevelInfo::LevelInfo() { @@ -281,3 +283,5 @@ std::string CSkillHandler::encodeSkillWithType(const si32 index) { return CModHandler::makeFullIdentifier("", "skill", encodeSkill(index)); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CSkillHandler.h b/lib/CSkillHandler.h index 1f93b4678..2d06c3f3c 100644 --- a/lib/CSkillHandler.h +++ b/lib/CSkillHandler.h @@ -16,6 +16,8 @@ #include "GameConstants.h" #include "IHandlerBase.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonSerializeFormat; class DLL_LINKAGE CSkill : public Skill @@ -114,3 +116,5 @@ protected: const std::vector & getTypeNames() const override; CSkill * loadFromJson(const std::string & scope, const JsonNode & json, const std::string & identifier, size_t index) override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CSoundBase.h b/lib/CSoundBase.h index 94ca7349c..d8b421494 100644 --- a/lib/CSoundBase.h +++ b/lib/CSoundBase.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + // Use some magic to keep the list of files and their code name in sync. #define VCMI_SOUND_LIST \ @@ -1060,3 +1062,5 @@ public: #undef VCMI_SOUND_FILE #undef VCMI_SOUND_NAME }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CStack.cpp b/lib/CStack.cpp index 64c5e98f8..df76d3067 100644 --- a/lib/CStack.cpp +++ b/lib/CStack.cpp @@ -19,6 +19,8 @@ #include "spells/CSpellHandler.h" #include "NetPacks.h" +VCMI_LIB_NAMESPACE_BEGIN + ///CStack CStack::CStack(const CStackInstance * Base, PlayerColor O, int I, ui8 Side, SlotID S) @@ -410,3 +412,5 @@ void CStack::spendMana(ServerCallback * server, const int spellCost) const ssp.absolute = false; server->apply(&ssp); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CStack.h b/lib/CStack.h index f969efab3..645e4000e 100644 --- a/lib/CStack.h +++ b/lib/CStack.h @@ -18,6 +18,8 @@ #include "battle/CUnitState.h" +VCMI_LIB_NAMESPACE_BEGIN + struct BattleStackAttacked; class BattleInfo; @@ -139,3 +141,5 @@ public: private: const BattleInfo * battle; //do not serialize }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CStopWatch.h b/lib/CStopWatch.h index b2821130c..46e3cb65c 100644 --- a/lib/CStopWatch.h +++ b/lib/CStopWatch.h @@ -19,6 +19,8 @@ #define TO_MS_DIVISOR (CLOCKS_PER_SEC / 1000) #endif +VCMI_LIB_NAMESPACE_BEGIN + class CStopWatch { si64 start, last, mem; @@ -62,3 +64,5 @@ private: #endif } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CThreadHelper.cpp b/lib/CThreadHelper.cpp index d388807e6..0394d60d5 100644 --- a/lib/CThreadHelper.cpp +++ b/lib/CThreadHelper.cpp @@ -16,6 +16,8 @@ #include #endif +VCMI_LIB_NAMESPACE_BEGIN + CThreadHelper::CThreadHelper(std::vector > *Tasks, int Threads) { currentTask = 0; amount = (int)Tasks->size(); @@ -88,3 +90,5 @@ void setThreadName(const std::string &name) pthread_setname_np(name.c_str()); #endif } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CThreadHelper.h b/lib/CThreadHelper.h index 78205de22..a4eaf8f8b 100644 --- a/lib/CThreadHelper.h +++ b/lib/CThreadHelper.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + ///DEPRECATED /// Can assign CPU work to other threads/cores @@ -81,3 +83,5 @@ private: void DLL_LINKAGE setThreadName(const std::string &name); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CTownHandler.cpp b/lib/CTownHandler.cpp index bb5085f2b..393943d2d 100644 --- a/lib/CTownHandler.cpp +++ b/lib/CTownHandler.cpp @@ -24,6 +24,8 @@ #include "mapObjects/CObjectHandler.h" #include "HeroBonus.h" +VCMI_LIB_NAMESPACE_BEGIN + const int NAMES_PER_TOWN=16; // number of town names per faction in H3 files. Json can define any number const Terrain CTownHandler::defaultGoodTerrain{"grass"}; @@ -1179,3 +1181,5 @@ const std::vector & CTownHandler::getTypeNames() const return typeNames; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CTownHandler.h b/lib/CTownHandler.h index 7728d2992..47727abf0 100644 --- a/lib/CTownHandler.h +++ b/lib/CTownHandler.h @@ -22,6 +22,8 @@ #include "HeroBonus.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class CLegacyConfigParser; class JsonNode; class CTown; @@ -430,3 +432,5 @@ protected: const std::vector & getTypeNames() const override; CFaction * loadFromJson(const std::string & scope, const JsonNode & data, const std::string & identifier, size_t index) override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/CondSh.h b/lib/CondSh.h index 829af99a7..165e2a0c1 100644 --- a/lib/CondSh.h +++ b/lib/CondSh.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + /// Used for multithreading, wraps boost functions template struct CondSh { @@ -63,3 +65,5 @@ template struct CondSh cond.wait(un); } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/ConstTransitivePtr.h b/lib/ConstTransitivePtr.h index 5aaaef5df..3fccbc554 100644 --- a/lib/ConstTransitivePtr.h +++ b/lib/ConstTransitivePtr.h @@ -11,6 +11,8 @@ class CGameHandler; +VCMI_LIB_NAMESPACE_BEGIN + template class ConstTransitivePtr { @@ -75,5 +77,7 @@ public: h & ptr; } - friend class CGameHandler; + friend class ::CGameHandler; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/FunctionList.h b/lib/FunctionList.h index eca94edfc..3c3ef4afe 100644 --- a/lib/FunctionList.h +++ b/lib/FunctionList.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + /// List of functions that share the same signature - can be used to call all of them easily template class CFunctionList @@ -61,3 +63,5 @@ public: } } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/GameConstants.cpp b/lib/GameConstants.cpp index 7f6155316..a8d729d04 100644 --- a/lib/GameConstants.cpp +++ b/lib/GameConstants.cpp @@ -37,6 +37,8 @@ #include "BattleFieldHandler.h" #include "ObstacleHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + const SlotID SlotID::COMMANDER_SLOT_PLACEHOLDER = SlotID(-2); const SlotID SlotID::SUMMONED_SLOT_PLACEHOLDER = SlotID(-3); const SlotID SlotID::WAR_MACHINES_SLOT = SlotID(-4); @@ -322,3 +324,5 @@ Obstacle Obstacle::fromString(std::string identifier) else return Obstacle(-1); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/GameConstants.h b/lib/GameConstants.h index 54d098e12..642089dba 100644 --- a/lib/GameConstants.h +++ b/lib/GameConstants.h @@ -11,6 +11,8 @@ #include "ConstTransitivePtr.h" +VCMI_LIB_NAMESPACE_BEGIN + class Artifact; class ArtifactService; class Creature; @@ -1194,3 +1196,5 @@ typedef int TRmgTemplateZoneId; #undef ID_LIKE_OPERATORS_INTERNAL #undef INSTID_LIKE_CLASS_COMMON #undef OP_DECL_INT + +VCMI_LIB_NAMESPACE_END diff --git a/lib/HeroBonus.cpp b/lib/HeroBonus.cpp index 081d874f7..2fcdabeb7 100644 --- a/lib/HeroBonus.cpp +++ b/lib/HeroBonus.cpp @@ -25,6 +25,8 @@ #include "StringConstants.h" #include "battle/BattleInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + #define FOREACH_PARENT(pname) TNodes lparents; getParents(lparents); for(CBonusSystemNode *pname : lparents) #define FOREACH_RED_CHILD(pname) TNodes lchildren; getRedChildren(lchildren); for(CBonusSystemNode *pname : lchildren) @@ -2559,3 +2561,5 @@ std::shared_ptr OwnerUpdater::createUpdatedBonus(const std::shared_ptrlimiter = std::make_shared(owner); return updated; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/HeroBonus.h b/lib/HeroBonus.h index 61941c27a..5afb1c92f 100644 --- a/lib/HeroBonus.h +++ b/lib/HeroBonus.h @@ -13,6 +13,8 @@ #include "JsonNode.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class CCreature; struct Bonus; class IBonusBearer; @@ -1290,3 +1292,5 @@ public: virtual std::string toString() const override; virtual JsonNode toJsonNode() const override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/IBonusTypeHandler.h b/lib/IBonusTypeHandler.h index 9563f4c87..f7edceb35 100644 --- a/lib/IBonusTypeHandler.h +++ b/lib/IBonusTypeHandler.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class IBonusBearer; struct Bonus; @@ -22,3 +24,5 @@ public: virtual std::string bonusToString(const std::shared_ptr & bonus, const IBonusBearer * bearer, bool description) const = 0; virtual std::string bonusToGraphics(const std::shared_ptr & bonus) const = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/IGameCallback.cpp b/lib/IGameCallback.cpp index cf1d235f3..877eb0465 100644 --- a/lib/IGameCallback.cpp +++ b/lib/IGameCallback.cpp @@ -35,6 +35,8 @@ #include "serializer/Connection.h" +VCMI_LIB_NAMESPACE_BEGIN + void CPrivilegedInfoCallback::getFreeTiles(std::vector & tiles) const { std::vector floors; @@ -248,3 +250,5 @@ bool IGameCallback::isVisitCoveredByAnotherQuery(const CGObjectInstance *obj, co logGlobal->error("isVisitCoveredByAnotherQuery call on client side"); return false; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/IGameCallback.h b/lib/IGameCallback.h index 0f4ad0940..4850fdce1 100644 --- a/lib/IGameCallback.h +++ b/lib/IGameCallback.h @@ -14,6 +14,8 @@ #include "CGameInfoCallback.h" // for CGameInfoCallback #include "CRandomGenerator.h" +VCMI_LIB_NAMESPACE_BEGIN + struct SetMovePoints; struct GiveBonus; struct BlockingDialog; @@ -145,3 +147,5 @@ public: friend struct CPackForServer; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/IGameEventsReceiver.h b/lib/IGameEventsReceiver.h index 53cda9427..632489c76 100644 --- a/lib/IGameEventsReceiver.h +++ b/lib/IGameEventsReceiver.h @@ -14,6 +14,10 @@ #include "GameConstants.h" #include "int3.h" +class CCallback; + +VCMI_LIB_NAMESPACE_BEGIN + class CGTownInstance; class CCreature; class CArmedInstance; @@ -21,7 +25,6 @@ struct StackLocation; struct TryMoveHero; struct ArtifactLocation; class CGHeroInstance; -class CCallback; class IShipyard; class CGDwelling; struct Component; @@ -42,7 +45,6 @@ class CCreatureSet; struct BattleAttack; struct SetStackEffect; struct BattleTriggerEffect; -class CComponent; struct CObstacleInstance; struct CPackForServer; class EVictoryLossCheckResult; @@ -133,3 +135,5 @@ public: //TODO shouldn't be moved down the tree? virtual void heroExchangeStarted(ObjectInstanceID hero1, ObjectInstanceID hero2, QueryID queryID){}; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/IHandlerBase.cpp b/lib/IHandlerBase.cpp index e4bfe44e7..fe35ed850 100644 --- a/lib/IHandlerBase.cpp +++ b/lib/IHandlerBase.cpp @@ -12,6 +12,8 @@ #include "IHandlerBase.h" #include "CModHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + void IHandlerBase::registerObject(std::string scope, std::string type_name, std::string name, si32 index) { @@ -22,3 +24,5 @@ std::string IHandlerBase::normalizeIdentifier(const std::string& scope, const st { return VLC->modh->normalizeIdentifier(scope, remoteScope, identifier); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/IHandlerBase.h b/lib/IHandlerBase.h index 18566f294..04aa4d0e7 100644 --- a/lib/IHandlerBase.h +++ b/lib/IHandlerBase.h @@ -12,6 +12,8 @@ #include "../lib/ConstTransitivePtr.h" #include "VCMI_Lib.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; class Entity; @@ -163,3 +165,5 @@ protected: public: //todo: make private std::vector> objects; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/Interprocess.h b/lib/Interprocess.h index 8137e77b7..cafe9666f 100644 --- a/lib/Interprocess.h +++ b/lib/Interprocess.h @@ -15,6 +15,8 @@ #include #include +VCMI_LIB_NAMESPACE_BEGIN + struct ServerReady { bool ready; @@ -78,3 +80,5 @@ struct SharedMemory boost::interprocess::shared_memory_object::remove(name.c_str()); } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/JsonDetail.cpp b/lib/JsonDetail.cpp index fde2a7523..3d0a6c47e 100644 --- a/lib/JsonDetail.cpp +++ b/lib/JsonDetail.cpp @@ -18,6 +18,8 @@ #include "filesystem/Filesystem.h" #include "ScopeGuard.h" +VCMI_LIB_NAMESPACE_BEGIN + static const JsonNode nullNode; template @@ -1242,3 +1244,5 @@ namespace Validation } } // Validation namespace + +VCMI_LIB_NAMESPACE_END diff --git a/lib/JsonDetail.h b/lib/JsonDetail.h index 89d19d5a6..23d3d8fb2 100644 --- a/lib/JsonDetail.h +++ b/lib/JsonDetail.h @@ -11,6 +11,8 @@ #include "JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonWriter { //prefix for each line (tabulation) @@ -127,3 +129,5 @@ namespace Validation std::string check(std::string schemaName, const JsonNode & data, ValidationData & validator); std::string check(const JsonNode & schema, const JsonNode & data, ValidationData & validator); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/JsonNode.cpp b/lib/JsonNode.cpp index f80e8cfba..0014ae3a5 100644 --- a/lib/JsonNode.cpp +++ b/lib/JsonNode.cpp @@ -21,6 +21,40 @@ #include "JsonDetail.h" #include "StringConstants.h" +namespace +{ +// to avoid duplicating const and non-const code +template +Node & resolvePointer(Node & in, const std::string & pointer) +{ + if (pointer.empty()) + return in; + assert(pointer[0] == '/'); + + size_t splitPos = pointer.find('/', 1); + + std::string entry = pointer.substr(1, splitPos -1); + std::string remainer = splitPos == std::string::npos ? "" : pointer.substr(splitPos); + + if (in.getType() == VCMI_LIB_WRAP_NAMESPACE(JsonNode)::JsonType::DATA_VECTOR) + { + if (entry.find_first_not_of("0123456789") != std::string::npos) // non-numbers in string + throw std::runtime_error("Invalid Json pointer"); + + if (entry.size() > 1 && entry[0] == '0') // leading zeros are not allowed + throw std::runtime_error("Invalid Json pointer"); + + size_t index = boost::lexical_cast(entry); + + if (in.Vector().size() > index) + return in.Vector()[index].resolvePointer(remainer); + } + return in[entry].resolvePointer(remainer); +} +} + +VCMI_LIB_NAMESPACE_BEGIN + using namespace JsonDetail; class LibClasses; @@ -406,35 +440,6 @@ const JsonNode & JsonNode::operator[](std::string child) const return nullNode; } -// to avoid duplicating const and non-const code -template -Node & resolvePointer(Node & in, const std::string & pointer) -{ - if (pointer.empty()) - return in; - assert(pointer[0] == '/'); - - size_t splitPos = pointer.find('/', 1); - - std::string entry = pointer.substr(1, splitPos -1); - std::string remainer = splitPos == std::string::npos ? "" : pointer.substr(splitPos); - - if (in.getType() == JsonNode::JsonType::DATA_VECTOR) - { - if (entry.find_first_not_of("0123456789") != std::string::npos) // non-numbers in string - throw std::runtime_error("Invalid Json pointer"); - - if (entry.size() > 1 && entry[0] == '0') // leading zeros are not allowed - throw std::runtime_error("Invalid Json pointer"); - - size_t index = boost::lexical_cast(entry); - - if (in.Vector().size() > index) - return in.Vector()[index].resolvePointer(remainer); - } - return in[entry].resolvePointer(remainer); -} - const JsonNode & JsonNode::resolvePointer(const std::string &jsonPointer) const { return ::resolvePointer(*this, jsonPointer); @@ -1212,3 +1217,5 @@ DLL_LINKAGE JsonNode JsonUtils::intNode(si64 value) node.Integer() = value; return node; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/JsonNode.h b/lib/JsonNode.h index e29865f49..44a1ebdfc 100644 --- a/lib/JsonNode.h +++ b/lib/JsonNode.h @@ -10,6 +10,8 @@ #pragma once #include "GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; typedef std::map JsonMap; typedef std::vector JsonVector; @@ -360,3 +362,5 @@ Type JsonNode::convertTo() const { return JsonDetail::JsonConverter::convert(*this); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/LogicalExpression.cpp b/lib/LogicalExpression.cpp index 42207afa8..e14891bf2 100644 --- a/lib/LogicalExpression.cpp +++ b/lib/LogicalExpression.cpp @@ -14,8 +14,12 @@ #include "VCMI_Lib.h" #include "CGeneralTextHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + std::string LogicalExpressionDetail::getTextForOperator(std::string operation) { //placed in cpp mostly to avoid unnecessary includes in header return VLC->generaltexth->localizedTexts["logicalExpressions"][operation].String(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/LogicalExpression.h b/lib/LogicalExpression.h index d567eafa5..a1f2fb528 100644 --- a/lib/LogicalExpression.h +++ b/lib/LogicalExpression.h @@ -12,6 +12,8 @@ //FIXME: move some of code into .cpp to avoid this include? #include "JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace LogicalExpressionDetail { /// class that defines required types for logical expressions @@ -625,3 +627,5 @@ public: h & data; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/NetPacks.h b/lib/NetPacks.h index 3016b2d19..e7ec6341f 100644 --- a/lib/NetPacks.h +++ b/lib/NetPacks.h @@ -23,8 +23,11 @@ #include "spells/ViewSpellInt.h" class CClient; -class CGameState; class CGameHandler; + +VCMI_LIB_NAMESPACE_BEGIN + +class CGameState; class CArtifact; class CGObjectInstance; class CArtifactInstance; @@ -2451,3 +2454,5 @@ struct CenterView : public CPackForClient h & focusTime; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/NetPacksBase.h b/lib/NetPacksBase.h index 868e50245..d14cf0eb4 100644 --- a/lib/NetPacksBase.h +++ b/lib/NetPacksBase.h @@ -9,9 +9,18 @@ */ #pragma once +#include + +#include "ConstTransitivePtr.h" +#include "GameConstants.h" +#include "JsonNode.h" + class CClient; -class CGameState; class CGameHandler; + +VCMI_LIB_NAMESPACE_BEGIN + +class CGameState; class CConnection; class CStackBasicDescriptor; class CGHeroInstance; @@ -21,12 +30,6 @@ class CArtifactSet; class CBonusSystemNode; struct ArtSlotInfo; -#include - -#include "ConstTransitivePtr.h" -#include "GameConstants.h" -#include "JsonNode.h" - struct DLL_LINKAGE CPack { std::shared_ptr c; // Pointer to connection that pack received from @@ -368,3 +371,5 @@ public: h & operation; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/NetPacksLib.cpp b/lib/NetPacksLib.cpp index 3fa981434..fe303a849 100644 --- a/lib/NetPacksLib.cpp +++ b/lib/NetPacksLib.cpp @@ -28,6 +28,8 @@ #include "StartInfo.h" #include "CPlayerState.h" +VCMI_LIB_NAMESPACE_BEGIN + DLL_LINKAGE void SetResources::applyGs(CGameState *gs) { @@ -1698,3 +1700,5 @@ DLL_LINKAGE void EntitiesChanged::applyGs(CGameState * gs) for(const auto & change : changes) gs->updateEntity(change.metatype, change.entityIndex, change.data); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/NetPacksLobby.h b/lib/NetPacksLobby.h index f635d3fa0..923cb84b8 100644 --- a/lib/NetPacksLobby.h +++ b/lib/NetPacksLobby.h @@ -13,14 +13,17 @@ #include "StartInfo.h" -class CCampaignState; class CLobbyScreen; class CServerHandler; +class CVCMIServer; + +VCMI_LIB_NAMESPACE_BEGIN + +class CCampaignState; class CMapInfo; struct StartInfo; class CMapGenOptions; struct ClientPlayer; -class CVCMIServer; struct CPackForLobby : public CPack { @@ -309,3 +312,5 @@ struct LobbyForceSetPlayer : public CLobbyPackToServer h & targetPlayerColor; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/ObstacleHandler.cpp b/lib/ObstacleHandler.cpp index a55fe0678..5e37d9a3d 100644 --- a/lib/ObstacleHandler.cpp +++ b/lib/ObstacleHandler.cpp @@ -11,6 +11,8 @@ #include "ObstacleHandler.h" #include "BattleFieldHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + int32_t ObstacleInfo::getIndex() const { return obstacle.getNum(); @@ -110,3 +112,5 @@ const std::vector & ObstacleHandler::getTypeNames() const static const std::vector types = { "obstacle" }; return types; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/ObstacleHandler.h b/lib/ObstacleHandler.h index 7075d140b..aa3e0be9c 100644 --- a/lib/ObstacleHandler.h +++ b/lib/ObstacleHandler.h @@ -16,6 +16,8 @@ #include "Terrain.h" #include "battle/BattleHex.h" +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE ObstacleInfo : public EntityT { public: @@ -92,3 +94,5 @@ public: h & objects; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/PathfinderUtil.h b/lib/PathfinderUtil.h index 0e750e9d4..558ee651d 100644 --- a/lib/PathfinderUtil.h +++ b/lib/PathfinderUtil.h @@ -12,6 +12,8 @@ #include "mapping/CMapDefines.h" #include "CGameState.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace PathfinderUtil { using FoW = std::shared_ptr>; @@ -74,3 +76,5 @@ namespace PathfinderUtil return CGPathNode::ACCESSIBLE; } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/ResourceSet.cpp b/lib/ResourceSet.cpp index 3d922c6f2..0a3470c5a 100644 --- a/lib/ResourceSet.cpp +++ b/lib/ResourceSet.cpp @@ -16,6 +16,8 @@ #include "VCMI_Lib.h" #include "mapObjects/CObjectHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + Res::ResourceSet::ResourceSet() { resize(GameConstants::RESOURCE_QUANTITY, 0); @@ -68,19 +70,19 @@ bool Res::ResourceSet::nonZero() const void Res::ResourceSet::amax(const TResourceCap &val) { for(auto & elem : *this) - ::vstd::amax(elem, val); + vstd::amax(elem, val); } void Res::ResourceSet::amin(const TResourceCap &val) { for(auto & elem : *this) - ::vstd::amin(elem, val); + vstd::amin(elem, val); } void Res::ResourceSet::positive() { for(auto & elem : *this) - ::vstd::amax(elem, 0); + vstd::amax(elem, 0); } bool Res::ResourceSet::canBeAfforded(const ResourceSet &res) const @@ -172,3 +174,5 @@ Res::ResourceSet::nziterator::nziterator(const ResourceSet &RS) if(!valid()) advance(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/ResourceSet.h b/lib/ResourceSet.h index 7a6e58123..1ac047962 100644 --- a/lib/ResourceSet.h +++ b/lib/ResourceSet.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + typedef si32 TResource; typedef si64 TResourceCap; //to avoid overflow when adding integers. Signed values are easier to control. @@ -167,3 +169,5 @@ namespace Res typedef Res::ResourceSet TResources; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/ScopeGuard.h b/lib/ScopeGuard.h index 6c57a0ca0..d72903711 100644 --- a/lib/ScopeGuard.h +++ b/lib/ScopeGuard.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace vstd { @@ -45,3 +47,5 @@ namespace vstd return ScopeGuard(std::forward(exitScope)); } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/ScriptHandler.cpp b/lib/ScriptHandler.cpp index 955ca2852..b64b0de2b 100644 --- a/lib/ScriptHandler.cpp +++ b/lib/ScriptHandler.cpp @@ -23,6 +23,8 @@ #include "serializer/JsonSerializer.h" #include "filesystem/Filesystem.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::vector IMPLEMENTS_MAP = { "ANYTHING", @@ -69,7 +71,7 @@ const std::string & ScriptImpl::getSource() const return sourceText; } -void ScriptImpl::performRegistration(::Services * services) const +void ScriptImpl::performRegistration(Services * services) const { switch(implements) { @@ -312,4 +314,6 @@ void ScriptHandler::saveState(JsonNode & state) } + +VCMI_LIB_NAMESPACE_END #endif diff --git a/lib/ScriptHandler.h b/lib/ScriptHandler.h index 53d91110c..a4eda8ab2 100644 --- a/lib/ScriptHandler.h +++ b/lib/ScriptHandler.h @@ -15,6 +15,8 @@ #include "IHandlerBase.h" #include "JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; class JsonSerializeFormat; class Services; @@ -61,7 +63,7 @@ public: const std::string & getName() const override; const std::string & getSource() const override; - void performRegistration(::Services * services) const; + void performRegistration(Services * services) const; private: const ScriptHandler * owner; @@ -85,7 +87,7 @@ private: ServerCallback * srv; }; -class DLL_LINKAGE ScriptHandler : public ::IHandlerBase, public Service +class DLL_LINKAGE ScriptHandler : public IHandlerBase, public Service { public: ScriptMap objects; @@ -132,4 +134,6 @@ private: }; } + +VCMI_LIB_NAMESPACE_END #endif diff --git a/lib/StartInfo.cpp b/lib/StartInfo.cpp index 97b703616..ba98f09c0 100644 --- a/lib/StartInfo.cpp +++ b/lib/StartInfo.cpp @@ -14,6 +14,8 @@ #include "rmg/CMapGenOptions.h" #include "mapping/CMapInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + PlayerSettings::PlayerSettings() : bonus(RANDOM), castle(NONE), hero(RANDOM), heroPortrait(RANDOM), color(0), handicap(NO_HANDICAP), team(0), compOnly(false) { @@ -193,3 +195,5 @@ TeamID LobbyInfo::getPlayerTeamId(PlayerColor color) else return TeamID::NO_TEAM; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/StartInfo.h b/lib/StartInfo.h index 2f0fb3b71..35db7ca66 100644 --- a/lib/StartInfo.h +++ b/lib/StartInfo.h @@ -11,6 +11,8 @@ #include "GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class CMapGenOptions; class CCampaignState; class CMapInfo; @@ -175,3 +177,8 @@ struct DLL_LINKAGE LobbyInfo : public LobbyState TeamID getPlayerTeamId(PlayerColor color); }; +class ExceptionMapMissing : public std::exception {}; +class ExceptionNoHuman : public std::exception {}; +class ExceptionNoTemplate : public std::exception {}; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/StringConstants.h b/lib/StringConstants.h index 721a070ae..08b0cbd9f 100644 --- a/lib/StringConstants.h +++ b/lib/StringConstants.h @@ -11,6 +11,8 @@ #include "GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + /// /// String ID which are pointless to move to config file - these types are mostly hardcoded /// @@ -114,3 +116,5 @@ namespace NMetaclass "object", "primarySkill", "secondarySkill", "spell", "resource" }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/Terrain.cpp b/lib/Terrain.cpp index 7f89447d2..12f7f72fb 100644 --- a/lib/Terrain.cpp +++ b/lib/Terrain.cpp @@ -13,6 +13,8 @@ #include "VCMI_Lib.h" #include "CModHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + //regular expression to change id for string at config //("allowedTerrain"\s*:\s*\[.*)9(.*\],\n) //\1"rock"\2 @@ -251,3 +253,5 @@ bool Terrain::isTransitionRequired() const { return Terrain::Manager::getInfo(*this).transitionRequired; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/Terrain.h b/lib/Terrain.h index 95fa343b0..b71dc172e 100644 --- a/lib/Terrain.h +++ b/lib/Terrain.h @@ -14,6 +14,7 @@ #include "GameConstants.h" #include "JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN class DLL_LINKAGE Terrain { @@ -103,3 +104,5 @@ protected: }; DLL_LINKAGE std::ostream & operator<<(std::ostream & os, const Terrain terrainType); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/UnlockGuard.h b/lib/UnlockGuard.h index f8a2835d1..51ec8541d 100644 --- a/lib/UnlockGuard.h +++ b/lib/UnlockGuard.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace vstd { namespace detail @@ -114,3 +116,5 @@ namespace vstd typedef unlock_guard > unlock_shared_guard; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index 7037bf72f..87b2abd50 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -11,6 +11,8 @@ #include "StdInc.h" #include "VCMIDirs.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace bfs = boost::filesystem; bfs::path IVCMIDirs::userLogsPath() const { return userCachePath(); } @@ -699,3 +701,5 @@ namespace VCMIDirs } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/VCMIDirs.h b/lib/VCMIDirs.h index deaa263ab..791f07483 100644 --- a/lib/VCMIDirs.h +++ b/lib/VCMIDirs.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE IVCMIDirs { public: @@ -64,3 +66,5 @@ namespace VCMIDirs { extern DLL_LINKAGE const IVCMIDirs & get(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/VCMI_Lib.cpp b/lib/VCMI_Lib.cpp index d79a9003a..f1c862d7c 100644 --- a/lib/VCMI_Lib.cpp +++ b/lib/VCMI_Lib.cpp @@ -35,6 +35,8 @@ #include "BattleFieldHandler.h" #include "ObstacleHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + LibClasses * VLC = nullptr; DLL_LINKAGE void preinitDLL(CConsoleHandler * Console, bool onlyEssential) @@ -316,3 +318,5 @@ void LibClasses::setContent(std::shared_ptr content) { modh->content = content; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/VCMI_Lib.h b/lib/VCMI_Lib.h index 4b822751b..476819e36 100644 --- a/lib/VCMI_Lib.h +++ b/lib/VCMI_Lib.h @@ -11,6 +11,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + class CConsoleHandler; class CArtHandler; class CHeroHandler; @@ -149,3 +151,5 @@ extern DLL_LINKAGE LibClasses * VLC; DLL_LINKAGE void preinitDLL(CConsoleHandler * Console, bool onlyEssential = false); DLL_LINKAGE void loadDLLClasses(bool onlyEssential = false); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/abilities/Ability.h b/lib/abilities/Ability.h index 30f10fb67..14bf3d54e 100644 --- a/lib/abilities/Ability.h +++ b/lib/abilities/Ability.h @@ -7,6 +7,9 @@ * Full text of license available in license.txt file, in main folder * */ + +VCMI_LIB_NAMESPACE_BEGIN + namespace abilities { @@ -16,3 +19,5 @@ class DLL_LINKAGE Ability }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/AccessibilityInfo.cpp b/lib/battle/AccessibilityInfo.cpp index 4ba58a802..2681dfeed 100644 --- a/lib/battle/AccessibilityInfo.cpp +++ b/lib/battle/AccessibilityInfo.cpp @@ -12,6 +12,8 @@ #include "Unit.h" #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + bool AccessibilityInfo::accessible(BattleHex tile, const battle::Unit * stack) const { return accessible(tile, stack->doubleWide(), stack->unitSide()); @@ -37,3 +39,5 @@ bool AccessibilityInfo::accessible(BattleHex tile, bool doubleWide, ui8 side) co return true; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/AccessibilityInfo.h b/lib/battle/AccessibilityInfo.h index 7386b794f..597b1473e 100644 --- a/lib/battle/AccessibilityInfo.h +++ b/lib/battle/AccessibilityInfo.h @@ -11,6 +11,8 @@ #include "BattleHex.h" #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace battle { class Unit; @@ -36,3 +38,5 @@ struct DLL_LINKAGE AccessibilityInfo : TAccessibilityArray bool accessible(BattleHex tile, const battle::Unit * stack) const; //checks for both tiles if stack is double wide bool accessible(BattleHex tile, bool doubleWide, ui8 side) const; //checks for both tiles if stack is double wide }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleAction.cpp b/lib/battle/BattleAction.cpp index 36c53560b..9567ffbb1 100644 --- a/lib/battle/BattleAction.cpp +++ b/lib/battle/BattleAction.cpp @@ -13,6 +13,8 @@ #include "Unit.h" #include "CBattleInfoCallback.h" +VCMI_LIB_NAMESPACE_BEGIN + static const int32_t INVALID_UNIT_ID = -1000; BattleAction::BattleAction(): @@ -181,3 +183,5 @@ std::ostream & operator<<(std::ostream & os, const BattleAction & ba) os << ba.toString(); return os; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleAction.h b/lib/battle/BattleAction.h index 228558ab5..ecce56ccb 100644 --- a/lib/battle/BattleAction.h +++ b/lib/battle/BattleAction.h @@ -11,6 +11,8 @@ #include "Destination.h" #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class CBattleInfoCallback; namespace battle @@ -73,3 +75,5 @@ private: }; DLL_EXPORT std::ostream & operator<<(std::ostream & os, const BattleAction & ba); //todo: remove + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleAttackInfo.cpp b/lib/battle/BattleAttackInfo.cpp index 7b42e23c8..1d38d699b 100644 --- a/lib/battle/BattleAttackInfo.cpp +++ b/lib/battle/BattleAttackInfo.cpp @@ -11,6 +11,8 @@ #include "BattleAttackInfo.h" #include "CUnitState.h" +VCMI_LIB_NAMESPACE_BEGIN + BattleAttackInfo::BattleAttackInfo(const battle::Unit * Attacker, const battle::Unit * Defender, bool Shooting) : attacker(Attacker), defender(Defender) @@ -38,3 +40,5 @@ BattleAttackInfo BattleAttackInfo::reverse() const return ret; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleAttackInfo.h b/lib/battle/BattleAttackInfo.h index c121dc177..b24376a30 100644 --- a/lib/battle/BattleAttackInfo.h +++ b/lib/battle/BattleAttackInfo.h @@ -9,14 +9,16 @@ */ #pragma once +#include "BattleHex.h" + +VCMI_LIB_NAMESPACE_BEGIN + namespace battle { class Unit; class CUnitState; } -#include "BattleHex.h" - struct DLL_LINKAGE BattleAttackInfo { const battle::Unit * attacker; @@ -34,3 +36,5 @@ struct DLL_LINKAGE BattleAttackInfo BattleAttackInfo(const battle::Unit * Attacker, const battle::Unit * Defender, bool Shooting = false); BattleAttackInfo reverse() const; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleHex.cpp b/lib/battle/BattleHex.cpp index db83f9c4f..7763fb335 100644 --- a/lib/battle/BattleHex.cpp +++ b/lib/battle/BattleHex.cpp @@ -10,6 +10,8 @@ #include "StdInc.h" #include "BattleHex.h" +VCMI_LIB_NAMESPACE_BEGIN + BattleHex::BattleHex() : hex(INVALID) {} BattleHex::BattleHex(si16 _hex) : hex(_hex) {} @@ -224,3 +226,5 @@ static BattleHex::NeighbouringTilesCache calculateNeighbouringTiles() } const BattleHex::NeighbouringTilesCache BattleHex::neighbouringTilesCache = calculateNeighbouringTiles(); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleHex.h b/lib/battle/BattleHex.h index 6633da3e6..c79d77a0a 100644 --- a/lib/battle/BattleHex.h +++ b/lib/battle/BattleHex.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + //TODO: change to enum class namespace BattleSide @@ -82,3 +84,5 @@ struct DLL_LINKAGE BattleHex //TODO: decide if this should be changed to class f }; DLL_EXPORT std::ostream & operator<<(std::ostream & os, const BattleHex & hex); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleInfo.cpp b/lib/battle/BattleInfo.cpp index 3ffa5d742..c7a1c533a 100644 --- a/lib/battle/BattleInfo.cpp +++ b/lib/battle/BattleInfo.cpp @@ -22,6 +22,8 @@ //TODO: remove #include "../IGameCallback.h" +VCMI_LIB_NAMESPACE_BEGIN + ///BattleInfo std::pair< std::vector, int > BattleInfo::getPath(BattleHex start, BattleHex dest, const CStack * stack) { @@ -1011,3 +1013,5 @@ CMP_stack::CMP_stack(int Phase, int Turn, uint8_t Side) turn = Turn; side = Side; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleInfo.h b/lib/battle/BattleInfo.h index 73a4ad0cc..bfcb52641 100644 --- a/lib/battle/BattleInfo.h +++ b/lib/battle/BattleInfo.h @@ -15,6 +15,8 @@ #include "SiegeInfo.h" #include "SideInBattle.h" +VCMI_LIB_NAMESPACE_BEGIN + class CStack; class CStackInstance; class CStackBasicDescriptor; @@ -160,3 +162,5 @@ public: bool operator ()(const battle::Unit * a, const battle::Unit * b); CMP_stack(int Phase = 1, int Turn = 0, uint8_t Side = BattleSide::ATTACKER); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleProxy.cpp b/lib/battle/BattleProxy.cpp index 83df1520a..4c10cde52 100644 --- a/lib/battle/BattleProxy.cpp +++ b/lib/battle/BattleProxy.cpp @@ -12,6 +12,8 @@ #include "Unit.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + ///BattleProxy BattleProxy::BattleProxy(Subject subject_) @@ -112,3 +114,5 @@ const IBonusBearer * BattleProxy::asBearer() const return subject->getBattleNode(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/BattleProxy.h b/lib/battle/BattleProxy.h index b756dadea..cd728ef53 100644 --- a/lib/battle/BattleProxy.h +++ b/lib/battle/BattleProxy.h @@ -12,6 +12,8 @@ #include "CBattleInfoCallback.h" #include "IBattleState.h" +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE BattleProxy : public CBattleInfoCallback, public IBattleState { public: @@ -52,3 +54,5 @@ public: protected: Subject subject; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CBattleInfoCallback.cpp b/lib/battle/CBattleInfoCallback.cpp index fbeb7d20a..8d891a8f6 100644 --- a/lib/battle/CBattleInfoCallback.cpp +++ b/lib/battle/CBattleInfoCallback.cpp @@ -19,6 +19,8 @@ #include "../mapObjects/CGTownInstance.h" #include "../BattleFieldHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace SiegeStuffThatShouldBeMovedToHandlers // <=== TODO { /* @@ -1991,3 +1993,5 @@ boost::optional CBattleInfoCallback::battleIsFinished() const else return 1; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CBattleInfoCallback.h b/lib/battle/CBattleInfoCallback.h index b5cd714c3..db88b9f11 100644 --- a/lib/battle/CBattleInfoCallback.h +++ b/lib/battle/CBattleInfoCallback.h @@ -15,6 +15,8 @@ #include "ReachabilityInfo.h" #include "BattleAttackInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class CStack; class ISpellCaster; @@ -151,3 +153,5 @@ protected: bool isInObstacle(BattleHex hex, const std::set & obstacles, const ReachabilityInfo::Parameters & params) const; std::set getStoppers(BattlePerspective::BattlePerspective whichSidePerspective) const; //get hexes with stopping obstacles (quicksands) }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CBattleInfoEssentials.cpp b/lib/battle/CBattleInfoEssentials.cpp index 9d0370a1f..8ed3b44a5 100644 --- a/lib/battle/CBattleInfoEssentials.cpp +++ b/lib/battle/CBattleInfoEssentials.cpp @@ -14,6 +14,8 @@ #include "../NetPacks.h" #include "../mapObjects/CGTownInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + Terrain CBattleInfoEssentials::battleTerrainType() const { RETURN_IF_NOT_BATTLE(Terrain()); @@ -423,3 +425,5 @@ bool CBattleInfoEssentials::battleMatchOwner(const PlayerColor & attacker, const return boost::logic::indeterminate(positivness) || (attacker == initialOwner) == (bool)positivness; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CBattleInfoEssentials.h b/lib/battle/CBattleInfoEssentials.h index bc354ab78..cc3ec0992 100644 --- a/lib/battle/CBattleInfoEssentials.h +++ b/lib/battle/CBattleInfoEssentials.h @@ -11,6 +11,8 @@ #include "CCallbackBase.h" #include "IBattleInfoCallback.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGTownInstance; class CGHeroInstance; class CStack; @@ -113,3 +115,5 @@ public: bool battleMatchOwner(const battle::Unit * attacker, const battle::Unit * defender, const boost::logic::tribool positivness = false) const; bool battleMatchOwner(const PlayerColor & attacker, const battle::Unit * defender, const boost::logic::tribool positivness = false) const; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CCallbackBase.cpp b/lib/battle/CCallbackBase.cpp index 39bdb5087..6bf4f7840 100644 --- a/lib/battle/CCallbackBase.cpp +++ b/lib/battle/CCallbackBase.cpp @@ -11,6 +11,8 @@ #include "CCallbackBase.h" #include "IBattleState.h" +VCMI_LIB_NAMESPACE_BEGIN + bool CCallbackBase::duringBattle() const { return getBattle() != nullptr; @@ -39,3 +41,5 @@ boost::optional CCallbackBase::getPlayerID() const return player; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CCallbackBase.h b/lib/battle/CCallbackBase.h index 43ff7cfc8..b83a8e82e 100644 --- a/lib/battle/CCallbackBase.h +++ b/lib/battle/CCallbackBase.h @@ -13,6 +13,8 @@ #define RETURN_IF_NOT_BATTLE(...) if(!duringBattle()) {logGlobal->error("%s called when no battle!", __FUNCTION__); return __VA_ARGS__; } #define ASSERT_IF_CALLED_WITH_PLAYER if(!player) {logGlobal->error(BOOST_CURRENT_FUNCTION); assert(0);} +VCMI_LIB_NAMESPACE_BEGIN + class IBattleInfo; class BattleInfo; class CBattleInfoEssentials; @@ -40,3 +42,5 @@ public: friend class CBattleInfoEssentials; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CObstacleInstance.cpp b/lib/battle/CObstacleInstance.cpp index 78edff13b..92e07c76c 100644 --- a/lib/battle/CObstacleInstance.cpp +++ b/lib/battle/CObstacleInstance.cpp @@ -18,6 +18,8 @@ #include "../serializer/JsonDeserializer.h" #include "../serializer/JsonSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + CObstacleInstance::CObstacleInstance() { obstacleType = USUAL; @@ -213,3 +215,5 @@ std::vector MoatObstacle::getAffectedTiles() const { return (*VLC->townh)[ID]->town->moatHexes; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CObstacleInstance.h b/lib/battle/CObstacleInstance.h index 041330779..c668b8ba4 100644 --- a/lib/battle/CObstacleInstance.h +++ b/lib/battle/CObstacleInstance.h @@ -10,6 +10,8 @@ #pragma once #include "BattleHex.h" +VCMI_LIB_NAMESPACE_BEGIN + class ObstacleInfo; class ObstacleChanges; class JsonSerializeFormat; @@ -118,3 +120,5 @@ struct DLL_LINKAGE SpellCreatedObstacle : CObstacleInstance h & customSize; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CPlayerBattleCallback.cpp b/lib/battle/CPlayerBattleCallback.cpp index 5dae89f11..abdc631ed 100644 --- a/lib/battle/CPlayerBattleCallback.cpp +++ b/lib/battle/CPlayerBattleCallback.cpp @@ -12,6 +12,8 @@ #include "../CStack.h" #include "../CGameState.h" +VCMI_LIB_NAMESPACE_BEGIN + bool CPlayerBattleCallback::battleCanFlee() const { RETURN_IF_NOT_BATTLE(false); @@ -52,3 +54,5 @@ InfoAboutHero CPlayerBattleCallback::battleGetEnemyHero() const return battleGetHeroInfo(!battleGetMySide()); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CPlayerBattleCallback.h b/lib/battle/CPlayerBattleCallback.h index 38ac80baa..f903a37af 100644 --- a/lib/battle/CPlayerBattleCallback.h +++ b/lib/battle/CPlayerBattleCallback.h @@ -10,6 +10,8 @@ #pragma once #include "CBattleInfoCallback.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class DLL_LINKAGE CPlayerBattleCallback : public CBattleInfoCallback @@ -24,3 +26,5 @@ public: InfoAboutHero battleGetEnemyHero() const; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CUnitState.cpp b/lib/battle/CUnitState.cpp index 248dcfd10..770ce2b9d 100644 --- a/lib/battle/CUnitState.cpp +++ b/lib/battle/CUnitState.cpp @@ -19,6 +19,8 @@ #include "../serializer/JsonDeserializer.h" #include "../serializer/JsonSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace battle { ///CAmmo @@ -952,3 +954,5 @@ void CUnitStateDetached::spendMana(ServerCallback * server, const int spellCost) } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/CUnitState.h b/lib/battle/CUnitState.h index 46fee68b3..5bd3e02e4 100644 --- a/lib/battle/CUnitState.h +++ b/lib/battle/CUnitState.h @@ -12,6 +12,8 @@ #include "Unit.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonSerializeFormat; class UnitChanges; @@ -294,3 +296,5 @@ private: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/Destination.cpp b/lib/battle/Destination.cpp index ba7fea41d..406b51f97 100644 --- a/lib/battle/Destination.cpp +++ b/lib/battle/Destination.cpp @@ -13,6 +13,8 @@ #include "Unit.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace battle { @@ -62,3 +64,5 @@ Destination & Destination::operator=(const Destination & other) } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/Destination.h b/lib/battle/Destination.h index 8d5cb274f..904e8fc8d 100644 --- a/lib/battle/Destination.h +++ b/lib/battle/Destination.h @@ -12,6 +12,8 @@ #include "BattleHex.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace battle { @@ -37,3 +39,5 @@ public: using Target = std::vector; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/IBattleInfoCallback.h b/lib/battle/IBattleInfoCallback.h index fcce0c7f2..d1bb1a3d6 100644 --- a/lib/battle/IBattleInfoCallback.h +++ b/lib/battle/IBattleInfoCallback.h @@ -12,6 +12,8 @@ #include "BattleHex.h" +VCMI_LIB_NAMESPACE_BEGIN + struct CObstacleInstance; class BattleField; class Terrain; @@ -62,3 +64,5 @@ public: }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/IBattleState.h b/lib/battle/IBattleState.h index 02f21d935..6e88b13ac 100644 --- a/lib/battle/IBattleState.h +++ b/lib/battle/IBattleState.h @@ -11,6 +11,8 @@ #pragma once #include "CBattleInfoEssentials.h" +VCMI_LIB_NAMESPACE_BEGIN + class ObstacleChanges; class UnitChanges; struct Bonus; @@ -91,3 +93,5 @@ public: virtual void updateObstacle(const ObstacleChanges & changes) = 0; virtual void removeObstacle(uint32_t id) = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/IUnitInfo.h b/lib/battle/IUnitInfo.h index e8edfe3f0..f91ccce2f 100644 --- a/lib/battle/IUnitInfo.h +++ b/lib/battle/IUnitInfo.h @@ -12,6 +12,8 @@ #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class CCreature; namespace battle @@ -41,3 +43,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/ReachabilityInfo.cpp b/lib/battle/ReachabilityInfo.cpp index 2dc8caa61..0a5452e26 100644 --- a/lib/battle/ReachabilityInfo.cpp +++ b/lib/battle/ReachabilityInfo.cpp @@ -12,6 +12,8 @@ #include "ReachabilityInfo.h" #include "Unit.h" +VCMI_LIB_NAMESPACE_BEGIN + ReachabilityInfo::Parameters::Parameters() { @@ -72,3 +74,5 @@ int ReachabilityInfo::distToNearestNeighbour( return distToNearestNeighbour(attackableHexes, chosenHex); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/ReachabilityInfo.h b/lib/battle/ReachabilityInfo.h index 9078a3b86..502a269ec 100644 --- a/lib/battle/ReachabilityInfo.h +++ b/lib/battle/ReachabilityInfo.h @@ -12,6 +12,8 @@ #include "CBattleInfoEssentials.h" #include "AccessibilityInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + // Reachability info is result of BFS calculation. It's dependent on stack (it's owner, whether it's flying), // startPosition and perpective. struct DLL_LINKAGE ReachabilityInfo @@ -55,3 +57,5 @@ struct DLL_LINKAGE ReachabilityInfo }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/SideInBattle.cpp b/lib/battle/SideInBattle.cpp index 3696f4128..638de4929 100644 --- a/lib/battle/SideInBattle.cpp +++ b/lib/battle/SideInBattle.cpp @@ -11,6 +11,8 @@ #include "SideInBattle.h" #include "../mapObjects/CArmedInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + SideInBattle::SideInBattle() { color = PlayerColor::CANNOT_DETERMINE; @@ -29,3 +31,5 @@ void SideInBattle::init(const CGHeroInstance * Hero, const CArmedInstance * Army if(color == PlayerColor::UNFLAGGABLE) color = PlayerColor::NEUTRAL; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/SideInBattle.h b/lib/battle/SideInBattle.h index 9f571e614..14ff2cc13 100644 --- a/lib/battle/SideInBattle.h +++ b/lib/battle/SideInBattle.h @@ -10,6 +10,8 @@ #pragma once #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class CArmedInstance; @@ -37,3 +39,5 @@ struct DLL_LINKAGE SideInBattle h & enchanterCounter; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/SiegeInfo.cpp b/lib/battle/SiegeInfo.cpp index 42a33e9de..13c2dc468 100644 --- a/lib/battle/SiegeInfo.cpp +++ b/lib/battle/SiegeInfo.cpp @@ -10,6 +10,8 @@ #include "StdInc.h" #include "SiegeInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + SiegeInfo::SiegeInfo() { @@ -37,3 +39,5 @@ EWallState::EWallState SiegeInfo::applyDamage(EWallState::EWallState state, unsi return EWallState::NONE; } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/SiegeInfo.h b/lib/battle/SiegeInfo.h index 7859d2740..f508c1f14 100644 --- a/lib/battle/SiegeInfo.h +++ b/lib/battle/SiegeInfo.h @@ -10,6 +10,8 @@ #pragma once #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + //only for use in BattleInfo struct DLL_LINKAGE SiegeInfo { @@ -27,3 +29,5 @@ struct DLL_LINKAGE SiegeInfo h & gateState; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/Unit.cpp b/lib/battle/Unit.cpp index 663da7d89..d98cfe2e9 100644 --- a/lib/battle/Unit.cpp +++ b/lib/battle/Unit.cpp @@ -18,6 +18,8 @@ #include "../serializer/JsonDeserializer.h" #include "../serializer/JsonSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace battle { @@ -238,3 +240,5 @@ void UnitInfo::load(uint32_t id_, const JsonNode & data) } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/battle/Unit.h b/lib/battle/Unit.h index 26d834d93..656c7bd7a 100644 --- a/lib/battle/Unit.h +++ b/lib/battle/Unit.h @@ -17,6 +17,8 @@ #include "IUnitInfo.h" #include "BattleHex.h" +VCMI_LIB_NAMESPACE_BEGIN + struct MetaString; class JsonNode; class JsonSerializeFormat; @@ -129,3 +131,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/ApplyDamage.cpp b/lib/events/ApplyDamage.cpp index 93b387899..b0466da64 100644 --- a/lib/events/ApplyDamage.cpp +++ b/lib/events/ApplyDamage.cpp @@ -15,6 +15,8 @@ #include "../../lib/NetPacks.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -58,3 +60,5 @@ const battle::Unit * CApplyDamage::getTarget() const }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/ApplyDamage.h b/lib/events/ApplyDamage.h index 178d12224..a7a426c45 100644 --- a/lib/events/ApplyDamage.h +++ b/lib/events/ApplyDamage.h @@ -12,6 +12,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -33,3 +35,5 @@ private: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/GameResumed.cpp b/lib/events/GameResumed.cpp index b7d98bb77..b2e493900 100644 --- a/lib/events/GameResumed.cpp +++ b/lib/events/GameResumed.cpp @@ -13,6 +13,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -37,3 +39,5 @@ bool CGameResumed::isEnabled() const } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/GameResumed.h b/lib/events/GameResumed.h index c0c36e3be..9fc3df73a 100644 --- a/lib/events/GameResumed.h +++ b/lib/events/GameResumed.h @@ -12,6 +12,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -24,3 +26,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/ObjectVisitEnded.cpp b/lib/events/ObjectVisitEnded.cpp index 6c8f2e2af..61d4d801f 100644 --- a/lib/events/ObjectVisitEnded.cpp +++ b/lib/events/ObjectVisitEnded.cpp @@ -13,6 +13,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -53,3 +55,5 @@ ObjectInstanceID CObjectVisitEnded::getHero() const } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/ObjectVisitEnded.h b/lib/events/ObjectVisitEnded.h index a3b8323ab..2cdf22d2e 100644 --- a/lib/events/ObjectVisitEnded.h +++ b/lib/events/ObjectVisitEnded.h @@ -14,6 +14,8 @@ #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -31,3 +33,5 @@ private: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/ObjectVisitStarted.cpp b/lib/events/ObjectVisitStarted.cpp index 863da819d..d535bd263 100644 --- a/lib/events/ObjectVisitStarted.cpp +++ b/lib/events/ObjectVisitStarted.cpp @@ -13,6 +13,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -65,3 +67,5 @@ void CObjectVisitStarted::setEnabled(bool enable) } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/ObjectVisitStarted.h b/lib/events/ObjectVisitStarted.h index d3754bddc..68fca2d8e 100644 --- a/lib/events/ObjectVisitStarted.h +++ b/lib/events/ObjectVisitStarted.h @@ -14,6 +14,8 @@ #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -36,3 +38,5 @@ private: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/PlayerGotTurn.cpp b/lib/events/PlayerGotTurn.cpp index ae5453a7a..cbe7f7c2d 100644 --- a/lib/events/PlayerGotTurn.cpp +++ b/lib/events/PlayerGotTurn.cpp @@ -13,6 +13,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -59,3 +61,5 @@ void CPlayerGotTurn::setPlayerIndex(int32_t value) } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/PlayerGotTurn.h b/lib/events/PlayerGotTurn.h index 8258f25e6..78d61adc5 100644 --- a/lib/events/PlayerGotTurn.h +++ b/lib/events/PlayerGotTurn.h @@ -14,6 +14,8 @@ #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -34,3 +36,5 @@ private: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/TurnStarted.cpp b/lib/events/TurnStarted.cpp index 015ab9ca0..655c32532 100644 --- a/lib/events/TurnStarted.cpp +++ b/lib/events/TurnStarted.cpp @@ -13,6 +13,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -37,3 +39,5 @@ bool CTurnStarted::isEnabled() const } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/events/TurnStarted.h b/lib/events/TurnStarted.h index a7bb3cb98..5a5520a02 100644 --- a/lib/events/TurnStarted.h +++ b/lib/events/TurnStarted.h @@ -12,6 +12,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace events { @@ -24,3 +26,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/AdapterLoaders.cpp b/lib/filesystem/AdapterLoaders.cpp index dd483d2ae..361bcf6c6 100644 --- a/lib/filesystem/AdapterLoaders.cpp +++ b/lib/filesystem/AdapterLoaders.cpp @@ -13,6 +13,8 @@ #include "../JsonNode.h" #include "Filesystem.h" +VCMI_LIB_NAMESPACE_BEGIN + CMappedFileLoader::CMappedFileLoader(const std::string & mountPoint, const JsonNode &config) { for(auto entry : config.Struct()) @@ -181,3 +183,5 @@ bool CFilesystemList::removeLoader(ISimpleResourceLoader * loader) } return false; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/AdapterLoaders.h b/lib/filesystem/AdapterLoaders.h index 460a54d63..7f5620c88 100644 --- a/lib/filesystem/AdapterLoaders.h +++ b/lib/filesystem/AdapterLoaders.h @@ -12,6 +12,8 @@ #include "ISimpleResourceLoader.h" #include "ResourceID.h" +VCMI_LIB_NAMESPACE_BEGIN + class CInputStream; class JsonNode; @@ -95,3 +97,5 @@ public: */ bool removeLoader(ISimpleResourceLoader * loader); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CArchiveLoader.cpp b/lib/filesystem/CArchiveLoader.cpp index 294f4db2d..f53241d46 100644 --- a/lib/filesystem/CArchiveLoader.cpp +++ b/lib/filesystem/CArchiveLoader.cpp @@ -15,6 +15,8 @@ #include "CBinaryReader.h" +VCMI_LIB_NAMESPACE_BEGIN + ArchiveEntry::ArchiveEntry() : offset(0), fullSize(0), compressedSize(0) { @@ -179,3 +181,5 @@ std::unordered_set CArchiveLoader::getFilteredFiles(std::function entries; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CBinaryReader.cpp b/lib/filesystem/CBinaryReader.cpp index 5a4808003..a3c7fc706 100644 --- a/lib/filesystem/CBinaryReader.cpp +++ b/lib/filesystem/CBinaryReader.cpp @@ -15,6 +15,8 @@ #include "CInputStream.h" #include "../CGeneralTextHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + #if SDL_BYTEORDER == SDL_BIG_ENDIAN template CData readLE(CData data) @@ -117,3 +119,5 @@ std::string CBinaryReader::getEndOfStreamExceptionMsg(long bytesToRead) const return ss.str(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CBinaryReader.h b/lib/filesystem/CBinaryReader.h index 166adc0b3..c5a5f2829 100644 --- a/lib/filesystem/CBinaryReader.h +++ b/lib/filesystem/CBinaryReader.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class CInputStream; /** @@ -101,3 +103,5 @@ private: /** The underlying base stream */ CInputStream * stream; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CCompressedStream.cpp b/lib/filesystem/CCompressedStream.cpp index 7fa23529f..520011784 100644 --- a/lib/filesystem/CCompressedStream.cpp +++ b/lib/filesystem/CCompressedStream.cpp @@ -12,6 +12,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + static const int inflateBlockSize = 10000; CBufferedStream::CBufferedStream(): @@ -189,3 +191,5 @@ bool CCompressedStream::getNextBlock() reset(); return true; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CCompressedStream.h b/lib/filesystem/CCompressedStream.h index 8f6191cdb..5c5930e67 100644 --- a/lib/filesystem/CCompressedStream.h +++ b/lib/filesystem/CCompressedStream.h @@ -13,6 +13,8 @@ struct z_stream_s; +VCMI_LIB_NAMESPACE_BEGIN + /// Abstract class that provides buffer for one-directional input streams (e.g. compressed data) /// Used for zip archives support and in .lod deflate compression class CBufferedStream : public CInputStream @@ -135,3 +137,5 @@ private: FINISHED }; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CFileInputStream.cpp b/lib/filesystem/CFileInputStream.cpp index aa54e353c..eb14e3eda 100644 --- a/lib/filesystem/CFileInputStream.cpp +++ b/lib/filesystem/CFileInputStream.cpp @@ -10,6 +10,8 @@ #include "StdInc.h" #include "CFileInputStream.h" +VCMI_LIB_NAMESPACE_BEGIN + CFileInputStream::CFileInputStream(const boost::filesystem::path & file, si64 start, si64 size) : dataStart{start}, dataSize{size}, @@ -61,3 +63,5 @@ si64 CFileInputStream::getSize() { return dataSize; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CFileInputStream.h b/lib/filesystem/CFileInputStream.h index e72755feb..4dd499188 100644 --- a/lib/filesystem/CFileInputStream.h +++ b/lib/filesystem/CFileInputStream.h @@ -12,6 +12,8 @@ #include "CInputStream.h" #include "FileStream.h" +VCMI_LIB_NAMESPACE_BEGIN + /** * A class which provides method definitions for reading a file from the filesystem. */ @@ -75,3 +77,5 @@ private: /** Native c++ input file stream object. */ FileStream fileStream; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CFilesystemLoader.cpp b/lib/filesystem/CFilesystemLoader.cpp index d4c8b7e51..122d22bf8 100644 --- a/lib/filesystem/CFilesystemLoader.cpp +++ b/lib/filesystem/CFilesystemLoader.cpp @@ -13,6 +13,8 @@ #include "CFileInputStream.h" #include "FileStream.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace bfs = boost::filesystem; CFilesystemLoader::CFilesystemLoader(std::string _mountPoint, bfs::path baseDirectory, size_t depth, bool initial): @@ -164,3 +166,5 @@ std::unordered_map CFilesystemLoader::listFiles(const std return fileList; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CFilesystemLoader.h b/lib/filesystem/CFilesystemLoader.h index e8230b91b..847aaa42c 100644 --- a/lib/filesystem/CFilesystemLoader.h +++ b/lib/filesystem/CFilesystemLoader.h @@ -12,6 +12,8 @@ #include "ISimpleResourceLoader.h" #include "ResourceID.h" +VCMI_LIB_NAMESPACE_BEGIN + class CInputStream; /** @@ -65,3 +67,5 @@ private: */ std::unordered_map listFiles(const std::string &mountPoint, size_t depth, bool initial) const; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CInputOutputStream.h b/lib/filesystem/CInputOutputStream.h index 8c80c4bac..86d561997 100644 --- a/lib/filesystem/CInputOutputStream.h +++ b/lib/filesystem/CInputOutputStream.h @@ -12,7 +12,11 @@ #include "CInputStream.h" #include "COutputStream.h" +VCMI_LIB_NAMESPACE_BEGIN + class CInputOutputStream: public CInputStream, public COutputStream { }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CInputStream.h b/lib/filesystem/CInputStream.h index 087534330..e5f2c0839 100644 --- a/lib/filesystem/CInputStream.h +++ b/lib/filesystem/CInputStream.h @@ -11,6 +11,8 @@ #include "CStream.h" +VCMI_LIB_NAMESPACE_BEGIN + /** * Abstract class which provides method definitions for reading from a stream. */ @@ -65,3 +67,5 @@ public: return checksum.checksum(); } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CMemoryBuffer.cpp b/lib/filesystem/CMemoryBuffer.cpp index 849502e7a..a7fcbcc59 100644 --- a/lib/filesystem/CMemoryBuffer.cpp +++ b/lib/filesystem/CMemoryBuffer.cpp @@ -11,6 +11,8 @@ #include "StdInc.h" #include "CMemoryBuffer.h" +VCMI_LIB_NAMESPACE_BEGIN + ///CMemoryBuffer CMemoryBuffer::CMemoryBuffer(): position(0) @@ -71,3 +73,5 @@ si64 CMemoryBuffer::getSize() } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CMemoryBuffer.h b/lib/filesystem/CMemoryBuffer.h index e35a78313..add14cf15 100644 --- a/lib/filesystem/CMemoryBuffer.h +++ b/lib/filesystem/CMemoryBuffer.h @@ -11,6 +11,8 @@ #include "CInputOutputStream.h" +VCMI_LIB_NAMESPACE_BEGIN + /** * A class which provides IO memory buffer. */ @@ -84,3 +86,5 @@ private: si64 position; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CMemoryStream.cpp b/lib/filesystem/CMemoryStream.cpp index 36eaacfaa..3c3ef4ba3 100644 --- a/lib/filesystem/CMemoryStream.cpp +++ b/lib/filesystem/CMemoryStream.cpp @@ -10,6 +10,8 @@ #include "StdInc.h" #include "CMemoryStream.h" +VCMI_LIB_NAMESPACE_BEGIN + CMemoryStream::CMemoryStream(const ui8 * data, si64 size) : data(data), size(size), position(0) { @@ -47,3 +49,5 @@ si64 CMemoryStream::getSize() { return size; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CMemoryStream.h b/lib/filesystem/CMemoryStream.h index 8af312cc3..f21e5ba14 100644 --- a/lib/filesystem/CMemoryStream.h +++ b/lib/filesystem/CMemoryStream.h @@ -11,6 +11,8 @@ #include "CInputStream.h" +VCMI_LIB_NAMESPACE_BEGIN + /** * A class which provides method definitions for reading from memory. * @deprecated use CMemoryBuffer @@ -75,3 +77,5 @@ private: /** Current reading position of the stream. */ si64 position; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/COutputStream.h b/lib/filesystem/COutputStream.h index 819fa8820..a6e3d008a 100644 --- a/lib/filesystem/COutputStream.h +++ b/lib/filesystem/COutputStream.h @@ -11,6 +11,8 @@ #include "CStream.h" +VCMI_LIB_NAMESPACE_BEGIN + /** * Abstract class which provides method definitions for writing into a stream. */ @@ -31,3 +33,5 @@ public: */ virtual si64 write(const ui8 * data, si64 size) = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CStream.h b/lib/filesystem/CStream.h index b8a0ca55f..0a1e6c961 100644 --- a/lib/filesystem/CStream.h +++ b/lib/filesystem/CStream.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE CStream : private boost::noncopyable { public: @@ -47,3 +49,5 @@ public: */ virtual si64 getSize() = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CZipLoader.cpp b/lib/filesystem/CZipLoader.cpp index 35e4cdcd8..30604b952 100644 --- a/lib/filesystem/CZipLoader.cpp +++ b/lib/filesystem/CZipLoader.cpp @@ -13,6 +13,8 @@ #include "../ScopeGuard.h" +VCMI_LIB_NAMESPACE_BEGIN + CZipStream::CZipStream(std::shared_ptr api, const boost::filesystem::path & archive, unz64_file_pos filepos) { zlib_filefunc64_def zlibApi; @@ -216,3 +218,5 @@ bool ZipArchive::extract(boost::filesystem::path from, boost::filesystem::path w } return true; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CZipLoader.h b/lib/filesystem/CZipLoader.h index 0365c67c2..288362da3 100644 --- a/lib/filesystem/CZipLoader.h +++ b/lib/filesystem/CZipLoader.h @@ -16,6 +16,8 @@ #include "MinizipExtensions.h" +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE CZipStream : public CBufferedStream { unzFile file; @@ -70,3 +72,5 @@ namespace ZipArchive ///same as above, but extracts only files mentioned in "what" list bool DLL_LINKAGE extract(boost::filesystem::path from, boost::filesystem::path where, std::vector what); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CZipSaver.cpp b/lib/filesystem/CZipSaver.cpp index 28647cb2b..87c3b848d 100644 --- a/lib/filesystem/CZipSaver.cpp +++ b/lib/filesystem/CZipSaver.cpp @@ -11,6 +11,8 @@ #include "StdInc.h" #include "CZipSaver.h" +VCMI_LIB_NAMESPACE_BEGIN + ///CZipOutputStream CZipOutputStream::CZipOutputStream(CZipSaver * owner_, zipFile archive, const std::string & archiveFilename): handle(archive), @@ -118,3 +120,5 @@ std::unique_ptr CZipSaver::addFile(const std::string & archiveFil return stream; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/CZipSaver.h b/lib/filesystem/CZipSaver.h index 88993f5d4..d9214468d 100644 --- a/lib/filesystem/CZipSaver.h +++ b/lib/filesystem/CZipSaver.h @@ -13,6 +13,8 @@ #include "MinizipExtensions.h" +VCMI_LIB_NAMESPACE_BEGIN + class CZipSaver; class DLL_LINKAGE CZipOutputStream: public COutputStream @@ -54,3 +56,5 @@ private: COutputStream * activeStream; friend class CZipOutputStream; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/FileInfo.cpp b/lib/filesystem/FileInfo.cpp index 89498a3a2..332fb71fa 100644 --- a/lib/filesystem/FileInfo.cpp +++ b/lib/filesystem/FileInfo.cpp @@ -11,6 +11,8 @@ #include "FileInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace FileInfo { @@ -63,3 +65,5 @@ boost::string_ref GetPathStem(boost::string_ref path) } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/FileInfo.h b/lib/filesystem/FileInfo.h index 484f17ecd..a8cd7963c 100644 --- a/lib/filesystem/FileInfo.h +++ b/lib/filesystem/FileInfo.h @@ -11,6 +11,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace FileInfo { @@ -50,3 +52,5 @@ boost::string_ref DLL_LINKAGE GetParentPath(boost::string_ref path); boost::string_ref DLL_LINKAGE GetPathStem(boost::string_ref path); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/FileStream.cpp b/lib/filesystem/FileStream.cpp index d3d4796f8..a85fcc913 100644 --- a/lib/filesystem/FileStream.cpp +++ b/lib/filesystem/FileStream.cpp @@ -218,6 +218,10 @@ void fill_fopen64_filefunc(zlib_filefunc64_def* pzlib_filefunc_def) } +template struct boost::iostreams::stream; + +VCMI_LIB_NAMESPACE_BEGIN + zlib_filefunc64_def* FileStream::GetMinizipFilefunc() { static zlib_filefunc64_def MinizipFilefunc; @@ -231,8 +235,6 @@ zlib_filefunc64_def* FileStream::GetMinizipFilefunc() return &MinizipFilefunc; } -template struct boost::iostreams::stream; - /*static*/ bool FileStream::CreateFile(const boost::filesystem::path& filename) { @@ -322,3 +324,5 @@ std::streamoff FileBuf::seek(std::streamoff off, std::ios_base::seekdir way) return static_cast(std::ftell(GETFILE)); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/FileStream.h b/lib/filesystem/FileStream.h index 57b9b420d..145a2e067 100644 --- a/lib/filesystem/FileStream.h +++ b/lib/filesystem/FileStream.h @@ -12,6 +12,8 @@ #include #include +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE FileBuf { public: @@ -32,13 +34,17 @@ private: void* filePtr; }; +VCMI_LIB_NAMESPACE_END + struct zlib_filefunc64_def_s; typedef zlib_filefunc64_def_s zlib_filefunc64_def; #ifdef VCMI_DLL -extern template struct DLL_LINKAGE boost::iostreams::stream; +extern template struct DLL_LINKAGE boost::iostreams::stream; #endif +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE FileStream : public boost::iostreams::stream { public: @@ -50,3 +56,5 @@ public: static zlib_filefunc64_def* GetMinizipFilefunc(); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/Filesystem.cpp b/lib/filesystem/Filesystem.cpp index 7afe29345..45e423a56 100644 --- a/lib/filesystem/Filesystem.cpp +++ b/lib/filesystem/Filesystem.cpp @@ -21,6 +21,8 @@ #include "../VCMIDirs.h" #include "../CStopWatch.h" +VCMI_LIB_NAMESPACE_BEGIN + std::map CResourceHandler::knownLoaders = std::map(); CResourceHandler CResourceHandler::globalResourceHandler; @@ -247,3 +249,5 @@ ISimpleResourceLoader * CResourceHandler::createFileSystem(const std::string & p generator.loadConfig(fsConfig); return generator.getFilesystem(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/Filesystem.h b/lib/filesystem/Filesystem.h index 8839a0e9c..1ea993b4d 100644 --- a/lib/filesystem/Filesystem.h +++ b/lib/filesystem/Filesystem.h @@ -13,6 +13,8 @@ #include "ISimpleResourceLoader.h" #include "ResourceID.h" +VCMI_LIB_NAMESPACE_BEGIN + class CFilesystemList; class JsonNode; @@ -113,3 +115,5 @@ private: CResourceHandler() {}; std::unique_ptr rootLoader; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/ISimpleResourceLoader.h b/lib/filesystem/ISimpleResourceLoader.h index 05371a22b..833000df1 100644 --- a/lib/filesystem/ISimpleResourceLoader.h +++ b/lib/filesystem/ISimpleResourceLoader.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class CInputStream; class ResourceID; @@ -105,3 +107,5 @@ public: return std::vector(); } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/MinizipExtensions.cpp b/lib/filesystem/MinizipExtensions.cpp index 23edf26d4..3ddf40b09 100644 --- a/lib/filesystem/MinizipExtensions.cpp +++ b/lib/filesystem/MinizipExtensions.cpp @@ -13,6 +13,8 @@ #include "CMemoryBuffer.h" #include "FileStream.h" +VCMI_LIB_NAMESPACE_BEGIN + template inline uLong streamRead(voidpf opaque, voidpf stream, void * buf, uLong size) { assert(opaque != nullptr); @@ -252,3 +254,5 @@ int ZCALLBACK CProxyROIOApi::errorFileProxy(voidpf opaque, voidpf stream) { return 0; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/MinizipExtensions.h b/lib/filesystem/MinizipExtensions.h index 43c739440..d4029ed83 100644 --- a/lib/filesystem/MinizipExtensions.h +++ b/lib/filesystem/MinizipExtensions.h @@ -18,6 +18,9 @@ #include "../minizip/zip.h" #include "../minizip/ioapi.h" #endif + +VCMI_LIB_NAMESPACE_BEGIN + class CInputStream; class CInputOutputStream; class CMemoryBuffer; @@ -85,3 +88,5 @@ private: static int ZCALLBACK errorFileProxy(voidpf opaque, voidpf stream); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/ResourceID.cpp b/lib/filesystem/ResourceID.cpp index 7b70d960c..63f61afca 100644 --- a/lib/filesystem/ResourceID.cpp +++ b/lib/filesystem/ResourceID.cpp @@ -11,6 +11,8 @@ #include "ResourceID.h" #include "FileInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + // trivial to_upper that completely ignores localization and only work with ASCII // Technically not a problem since // 1) Right now VCMI does not supports unicode in filenames on Win @@ -205,3 +207,5 @@ std::string EResTypeHelper::getEResTypeAsString(EResType::Type type) return iter->second; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/filesystem/ResourceID.h b/lib/filesystem/ResourceID.h index 4310b5911..d30fb4288 100644 --- a/lib/filesystem/ResourceID.h +++ b/lib/filesystem/ResourceID.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + /** * Specifies the resource type. @@ -114,19 +116,6 @@ private: std::string name; }; -namespace std -{ - template <> struct hash - { - size_t operator()(const ResourceID & resourceIdent) const - { - std::hash intHasher; - std::hash stringHasher; - return stringHasher(resourceIdent.getName()) ^ intHasher(static_cast(resourceIdent.getType())); - } - }; -} - /** * A helper class which provides a functionality to convert extension strings to EResTypes. */ @@ -149,3 +138,16 @@ public: */ static std::string getEResTypeAsString(EResType::Type type); }; + +VCMI_LIB_NAMESPACE_END + + +template <> struct std::hash +{ + size_t operator()(const VCMI_LIB_WRAP_NAMESPACE(ResourceID) & resourceIdent) const + { + std::hash intHasher; + std::hash stringHasher; + return stringHasher(resourceIdent.getName()) ^ intHasher(static_cast(resourceIdent.getType())); + } +}; diff --git a/lib/int3.h b/lib/int3.h index d8861e314..b77e508b4 100644 --- a/lib/int3.h +++ b/lib/int3.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + /// Class which consists of three integer values. Represents position on adventure map. class int3 { @@ -216,3 +218,5 @@ int3 findClosestTile (Container & container, int3 dest) } return result; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/logging/CBasicLogConfigurator.cpp b/lib/logging/CBasicLogConfigurator.cpp index 94e37b17d..727386bf0 100644 --- a/lib/logging/CBasicLogConfigurator.cpp +++ b/lib/logging/CBasicLogConfigurator.cpp @@ -13,6 +13,8 @@ #include "../CConfigHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + CBasicLogConfigurator::CBasicLogConfigurator(boost::filesystem::path filePath, CConsoleHandler * const console) : filePath(std::move(filePath)), console(console), appendToLogFile(false) {} @@ -147,3 +149,5 @@ void CBasicLogConfigurator::deconfigure() if(l != nullptr) l->clearTargets(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/logging/CBasicLogConfigurator.h b/lib/logging/CBasicLogConfigurator.h index df0bfe587..ba96f3d3f 100644 --- a/lib/logging/CBasicLogConfigurator.h +++ b/lib/logging/CBasicLogConfigurator.h @@ -12,6 +12,8 @@ #include "../CConsoleHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + class CConsoleHandler; class JsonNode; @@ -45,3 +47,5 @@ private: CConsoleHandler * console; bool appendToLogFile; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/logging/CLogger.cpp b/lib/logging/CLogger.cpp index fa30eea09..9799c4bb5 100644 --- a/lib/logging/CLogger.cpp +++ b/lib/logging/CLogger.cpp @@ -37,6 +37,8 @@ extern "C" { } #endif +VCMI_LIB_NAMESPACE_BEGIN + namespace vstd { @@ -447,3 +449,5 @@ CLogFileTarget::~CLogFileTarget() { file.close(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/logging/CLogger.h b/lib/logging/CLogger.h index d2a15fb39..4f5ee2773 100644 --- a/lib/logging/CLogger.h +++ b/lib/logging/CLogger.h @@ -12,6 +12,8 @@ #include "../CConsoleHandler.h" #include "../filesystem/FileStream.h" +VCMI_LIB_NAMESPACE_BEGIN + class CLogger; struct LogRecord; class ILogTarget; @@ -225,3 +227,5 @@ private: CLogFormatter formatter; mutable boost::mutex mx; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CArmedInstance.cpp b/lib/mapObjects/CArmedInstance.cpp index 5d23e8ef4..e98b4b719 100644 --- a/lib/mapObjects/CArmedInstance.cpp +++ b/lib/mapObjects/CArmedInstance.cpp @@ -17,6 +17,8 @@ #include "../CGameState.h" #include "../CPlayerState.h" +VCMI_LIB_NAMESPACE_BEGIN + void CArmedInstance::randomizeArmy(int type) { for (auto & elem : stacks) @@ -152,3 +154,5 @@ CBonusSystemNode * CArmedInstance::whatShouldBeAttached() { return this; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CArmedInstance.h b/lib/mapObjects/CArmedInstance.h index a17a3998e..559e94e51 100644 --- a/lib/mapObjects/CArmedInstance.h +++ b/lib/mapObjects/CArmedInstance.h @@ -1,4 +1,4 @@ -/* +/* * CArmedInstance.h, part of VCMI engine * * Authors: listed in file AUTHORS in main folder @@ -12,6 +12,8 @@ #include "CObjectHandler.h" #include "../CCreatureSet.h" +VCMI_LIB_NAMESPACE_BEGIN + class BattleInfo; class CGameState; @@ -50,3 +52,5 @@ public: h & static_cast(*this); } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CBank.cpp b/lib/mapObjects/CBank.cpp index 69e4d6459..7cbe050b1 100644 --- a/lib/mapObjects/CBank.cpp +++ b/lib/mapObjects/CBank.cpp @@ -1,4 +1,4 @@ -/* +/* * CBank.cpp, part of VCMI engine * * Authors: listed in file AUTHORS in main folder @@ -21,6 +21,8 @@ #include "../IGameCallback.h" #include "../CGameState.h" +VCMI_LIB_NAMESPACE_BEGIN + ///helpers static std::string & visitedTxt(const bool visited) { @@ -351,3 +353,5 @@ void CBank::blockingDialogAnswered(const CGHeroInstance *hero, ui32 answer) cons doVisit(hero); } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CBank.h b/lib/mapObjects/CBank.h index c274fe653..22819005a 100644 --- a/lib/mapObjects/CBank.h +++ b/lib/mapObjects/CBank.h @@ -1,4 +1,4 @@ -/* +/* * CBank.h, part of VCMI engine * * Authors: listed in file AUTHORS in main folder @@ -12,6 +12,8 @@ #include "CObjectHandler.h" #include "CArmedInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + struct BankConfig; class CBankInstanceConstructor; @@ -48,3 +50,5 @@ public: friend class CBankInstanceConstructor; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGHeroInstance.cpp b/lib/mapObjects/CGHeroInstance.cpp index 903de00dd..743af6b32 100644 --- a/lib/mapObjects/CGHeroInstance.cpp +++ b/lib/mapObjects/CGHeroInstance.cpp @@ -32,6 +32,8 @@ #include "../StringConstants.h" #include "../battle/Unit.h" +VCMI_LIB_NAMESPACE_BEGIN + ///helpers static void showInfoDialog(const PlayerColor playerID, const ui32 txtID, const ui16 soundID = 0) @@ -1642,3 +1644,5 @@ bool CGHeroInstance::isMissionCritical() const } return false; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGHeroInstance.h b/lib/mapObjects/CGHeroInstance.h index ea88e41b9..61a50aed0 100644 --- a/lib/mapObjects/CGHeroInstance.h +++ b/lib/mapObjects/CGHeroInstance.h @@ -17,6 +17,8 @@ #include "../CArtHandler.h" // For CArtifactSet #include "../CRandomGenerator.h" +VCMI_LIB_NAMESPACE_BEGIN + class CHero; class CGBoat; class CGTownInstance; @@ -315,3 +317,5 @@ public: BONUS_TREE_DESERIALIZATION_FIX } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGMarket.cpp b/lib/mapObjects/CGMarket.cpp index 81f7150c9..95687a963 100644 --- a/lib/mapObjects/CGMarket.cpp +++ b/lib/mapObjects/CGMarket.cpp @@ -20,6 +20,8 @@ #include "../CModHandler.h" #include "../CSkillHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + ///helpers static void openWindow(const OpenWindow::EWindow type, const int id1, const int id2 = -1) { @@ -339,3 +341,5 @@ void CGUniversity::onHeroVisit(const CGHeroInstance * h) const { openWindow(OpenWindow::UNIVERSITY_WINDOW,id.getNum(),h->id.getNum()); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGMarket.h b/lib/mapObjects/CGMarket.h index bdf7cba71..4697179d8 100644 --- a/lib/mapObjects/CGMarket.h +++ b/lib/mapObjects/CGMarket.h @@ -1,4 +1,4 @@ -/* +/* * CGMarket.h, part of VCMI engine * * Authors: listed in file AUTHORS in main folder @@ -11,6 +11,8 @@ #include "CObjectHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE IMarket { public: @@ -85,3 +87,5 @@ public: h & skills; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGPandoraBox.cpp b/lib/mapObjects/CGPandoraBox.cpp index c07de1358..e04dfa377 100644 --- a/lib/mapObjects/CGPandoraBox.cpp +++ b/lib/mapObjects/CGPandoraBox.cpp @@ -1,4 +1,4 @@ -/* +/* * CGPandoraBox.cpp, part of VCMI engine * * Authors: listed in file AUTHORS in main folder @@ -23,6 +23,8 @@ #include "../StringConstants.h" #include "../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + ///helpers static void showInfoDialog(const PlayerColor playerID, const ui32 txtID, const ui16 soundID) { @@ -530,3 +532,5 @@ void CGEvent::serializeJsonOptions(JsonSerializeFormat & handler) handler.serializeIdArray("availableFor", availableFor, GameConstants::ALL_PLAYERS, decodePlayer, encodePlayer); } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGPandoraBox.h b/lib/mapObjects/CGPandoraBox.h index 3af409e0c..d525bf279 100644 --- a/lib/mapObjects/CGPandoraBox.h +++ b/lib/mapObjects/CGPandoraBox.h @@ -1,4 +1,4 @@ -/* +/* * CGPandoraBox.h, part of VCMI engine * * Authors: listed in file AUTHORS in main folder @@ -13,6 +13,8 @@ #include "CArmedInstance.h" #include "../ResourceSet.h" +VCMI_LIB_NAMESPACE_BEGIN + struct InfoWindow; class DLL_LINKAGE CGPandoraBox : public CArmedInstance @@ -93,3 +95,5 @@ private: void activated(const CGHeroInstance * h) const; void afterSuccessfulVisit() const override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGTownInstance.cpp b/lib/mapObjects/CGTownInstance.cpp index 42cd5c2d2..a9d7dedbb 100644 --- a/lib/mapObjects/CGTownInstance.cpp +++ b/lib/mapObjects/CGTownInstance.cpp @@ -23,6 +23,8 @@ #include "../serializer/JsonSerializeFormat.h" #include "../HeroBonus.h" +VCMI_LIB_NAMESPACE_BEGIN + std::vector CGTownInstance::merchantArtifacts; std::vector CGTownInstance::universitySkills; @@ -1867,3 +1869,5 @@ const std::string CGTownBuilding::getCustomBonusGreeting(const Bonus & bonus) co std::string greeting = fmt.str(); return greeting; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGTownInstance.h b/lib/mapObjects/CGTownInstance.h index fea47b1a4..0d261f2af 100644 --- a/lib/mapObjects/CGTownInstance.h +++ b/lib/mapObjects/CGTownInstance.h @@ -15,6 +15,8 @@ #include "../CTownHandler.h" // For CTown +VCMI_LIB_NAMESPACE_BEGIN + class CCastleEvent; class CGTownInstance; class CGDwelling; @@ -365,3 +367,5 @@ private: void initOverriddenBids(); void addTownBonuses(); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CObjectClassesHandler.cpp b/lib/mapObjects/CObjectClassesHandler.cpp index 4a3e8ad12..03ed19e24 100644 --- a/lib/mapObjects/CObjectClassesHandler.cpp +++ b/lib/mapObjects/CObjectClassesHandler.cpp @@ -24,6 +24,8 @@ #include "CommonConstructors.h" #include "MapObjects.h" +VCMI_LIB_NAMESPACE_BEGIN + // FIXME: move into inheritNode? static void inheritNodeWithMeta(JsonNode & descendant, const JsonNode & base) { @@ -627,3 +629,5 @@ bool AObjectTypeHandler::isStaticObject() void AObjectTypeHandler::afterLoadFinalization() { } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CObjectClassesHandler.h b/lib/mapObjects/CObjectClassesHandler.h index cff16a715..af7099b6a 100644 --- a/lib/mapObjects/CObjectClassesHandler.h +++ b/lib/mapObjects/CObjectClassesHandler.h @@ -17,6 +17,8 @@ #include "../JsonNode.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; class CRandomGenerator; @@ -320,3 +322,5 @@ public: h & objects; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CObjectHandler.cpp b/lib/mapObjects/CObjectHandler.cpp index 35904fb65..0dc476d61 100644 --- a/lib/mapObjects/CObjectHandler.cpp +++ b/lib/mapObjects/CObjectHandler.cpp @@ -26,6 +26,8 @@ #include "../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + IGameCallback * IObjectInterface::cb = nullptr; ///helpers @@ -524,3 +526,5 @@ const IShipyard * IShipyard::castFrom( const CGObjectInstance *obj ) { return castFrom(const_cast(obj)); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CObjectHandler.h b/lib/mapObjects/CObjectHandler.h index 1afa229a6..387020f72 100644 --- a/lib/mapObjects/CObjectHandler.h +++ b/lib/mapObjects/CObjectHandler.h @@ -15,6 +15,8 @@ #include "../int3.h" #include "../HeroBonus.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class IGameCallback; class CGObjectInstance; @@ -255,3 +257,5 @@ public: h & resVals; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CQuest.cpp b/lib/mapObjects/CQuest.cpp index 53e0dd43d..f22327ed7 100644 --- a/lib/mapObjects/CQuest.cpp +++ b/lib/mapObjects/CQuest.cpp @@ -28,6 +28,8 @@ #include "../CSkillHandler.h" #include "../mapping/CMap.h" +VCMI_LIB_NAMESPACE_BEGIN + std::map > CGKeys::playerKeyMap; @@ -1172,3 +1174,5 @@ bool CGBorderGate::passableFor(PlayerColor color) const { return wasMyColorVisited(color); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CQuest.h b/lib/mapObjects/CQuest.h index 3fff59254..a2cb8b75f 100644 --- a/lib/mapObjects/CQuest.h +++ b/lib/mapObjects/CQuest.h @@ -15,6 +15,8 @@ #include "../CCreatureSet.h" #include "../NetPacksBase.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGCreature; class DLL_LINKAGE CQuest @@ -239,3 +241,5 @@ public: h & static_cast(*this); //need to serialize or object will be empty } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CRewardableConstructor.cpp b/lib/mapObjects/CRewardableConstructor.cpp index dbe59e68e..4a6442eb7 100644 --- a/lib/mapObjects/CRewardableConstructor.cpp +++ b/lib/mapObjects/CRewardableConstructor.cpp @@ -16,6 +16,8 @@ #include "JsonRandom.h" #include "../IGameCallback.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace { MetaString loadMessage(const JsonNode & value) { @@ -220,3 +222,5 @@ std::unique_ptr CRewardableConstructor::getObjectInfo(std::shared_p { return std::unique_ptr(new CRandomRewardObjectInfo(objectInfo)); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CRewardableConstructor.h b/lib/mapObjects/CRewardableConstructor.h index 4157ae7cb..7dee06f27 100644 --- a/lib/mapObjects/CRewardableConstructor.h +++ b/lib/mapObjects/CRewardableConstructor.h @@ -14,6 +14,8 @@ #include "../JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE CRandomRewardObjectInfo : public IObjectInfo { JsonNode parameters; @@ -55,3 +57,5 @@ public: std::unique_ptr getObjectInfo(std::shared_ptr tmpl) const override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CRewardableObject.cpp b/lib/mapObjects/CRewardableObject.cpp index 34b57072d..8e78fc8e3 100644 --- a/lib/mapObjects/CRewardableObject.cpp +++ b/lib/mapObjects/CRewardableObject.cpp @@ -20,6 +20,8 @@ #include "CObjectClassesHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + bool CRewardLimiter::heroAllowed(const CGHeroInstance * hero) const { if(dayOfWeek != 0) @@ -1163,3 +1165,5 @@ std::vector CGMagicSpring::getAvailableRewards(const CGHeroInstance * hero // hero is either not on visitable tile (should not happen) or tile is already used return std::vector(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CRewardableObject.h b/lib/mapObjects/CRewardableObject.h index a259153ea..60ab5e386 100644 --- a/lib/mapObjects/CRewardableObject.h +++ b/lib/mapObjects/CRewardableObject.h @@ -15,6 +15,8 @@ #include "../NetPacksBase.h" #include "../ResourceSet.h" +VCMI_LIB_NAMESPACE_BEGIN + class CRandomRewardObjectInfo; /// Limiters of rewards. Rewards will be granted to hero only if he satisfies requirements @@ -403,3 +405,5 @@ public: // class DLL_LINKAGE CGSignBottle : public CGObjectInstance //signs and ocean bottles // class DLL_LINKAGE CGWitchHut : public CPlayersVisited // class DLL_LINKAGE CGScholar : public CGObjectInstance + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CommonConstructors.cpp b/lib/mapObjects/CommonConstructors.cpp index 3b870847a..a7d39bb0d 100644 --- a/lib/mapObjects/CommonConstructors.cpp +++ b/lib/mapObjects/CommonConstructors.cpp @@ -20,6 +20,8 @@ #include "../CModHandler.h" #include "../IGameCallback.h" +VCMI_LIB_NAMESPACE_BEGIN + CObstacleConstructor::CObstacleConstructor() { } @@ -498,3 +500,5 @@ std::unique_ptr CBankInstanceConstructor::getObjectInfo(std::shared { return std::unique_ptr(new CBankInfo(levels)); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CommonConstructors.h b/lib/mapObjects/CommonConstructors.h index 605ad429c..98b3e623b 100644 --- a/lib/mapObjects/CommonConstructors.h +++ b/lib/mapObjects/CommonConstructors.h @@ -13,6 +13,8 @@ #include "../CTownHandler.h" // for building ID-based filters #include "MapObjects.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class CGTownInstance; class CGHeroInstance; @@ -233,3 +235,5 @@ public: h & static_cast&>(*this); } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/JsonRandom.cpp b/lib/mapObjects/JsonRandom.cpp index aecba04a9..b2d10559d 100644 --- a/lib/mapObjects/JsonRandom.cpp +++ b/lib/mapObjects/JsonRandom.cpp @@ -21,6 +21,8 @@ #include "../CCreatureSet.h" #include "../spells/CSpellHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace JsonRandom { si32 loadValue(const JsonNode & value, CRandomGenerator & rng, si32 defaultValue) @@ -225,3 +227,5 @@ namespace JsonRandom } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/JsonRandom.h b/lib/mapObjects/JsonRandom.h index 8eaf085fb..0ed636aae 100644 --- a/lib/mapObjects/JsonRandom.h +++ b/lib/mapObjects/JsonRandom.h @@ -12,6 +12,8 @@ #include "../GameConstants.h" #include "../ResourceSet.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; typedef std::vector JsonVector; class CRandomGenerator; @@ -47,3 +49,5 @@ namespace JsonRandom DLL_LINKAGE std::vector loadBonuses(const JsonNode & value); //DLL_LINKAGE std::vector loadComponents(const JsonNode & value); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/MiscObjects.cpp b/lib/mapObjects/MiscObjects.cpp index 741ad4ba9..cd9b5a620 100644 --- a/lib/mapObjects/MiscObjects.cpp +++ b/lib/mapObjects/MiscObjects.cpp @@ -26,6 +26,8 @@ #include "../CPlayerState.h" #include "../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + std::map > CGMagi::eyelist; ui8 CGObelisk::obeliskCount = 0; //how many obelisks are on map std::map CGObelisk::visited; //map: team_id => how many obelisks has been visited @@ -2207,4 +2209,6 @@ void CGLighthouse::giveBonusTo(PlayerColor player, bool onInit) const void CGLighthouse::serializeJsonOptions(JsonSerializeFormat& handler) { serializeJsonOwner(handler); -} \ No newline at end of file +} + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/MiscObjects.h b/lib/mapObjects/MiscObjects.h index 8949debeb..9eeeee41e 100644 --- a/lib/mapObjects/MiscObjects.h +++ b/lib/mapObjects/MiscObjects.h @@ -13,6 +13,8 @@ #include "CArmedInstance.h" #include "../ResourceSet.h" +VCMI_LIB_NAMESPACE_BEGIN + class CMap; /// Legacy class, use CRewardableObject instead @@ -541,3 +543,5 @@ public: return true; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/ObjectTemplate.cpp b/lib/mapObjects/ObjectTemplate.cpp index 40f9693df..3eb23cd86 100644 --- a/lib/mapObjects/ObjectTemplate.cpp +++ b/lib/mapObjects/ObjectTemplate.cpp @@ -23,6 +23,8 @@ #include "CRewardableConstructor.h" +VCMI_LIB_NAMESPACE_BEGIN + static bool isOnVisitableFromTopList(int identifier, int type) { if(type == 2 || type == 3 || type == 4 || type == 5) //creature, hero, artifact, resource @@ -572,3 +574,4 @@ void ObjectTemplate::recalculate() calculateVisitableOffset(); } +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/ObjectTemplate.h b/lib/mapObjects/ObjectTemplate.h index e10f1efad..24a219ac0 100644 --- a/lib/mapObjects/ObjectTemplate.h +++ b/lib/mapObjects/ObjectTemplate.h @@ -12,6 +12,8 @@ #include "../GameConstants.h" #include "../int3.h" +VCMI_LIB_NAMESPACE_BEGIN + class CBinaryReader; class CLegacyConfigParser; class JsonNode; @@ -153,3 +155,5 @@ public: } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CCampaignHandler.cpp b/lib/mapping/CCampaignHandler.cpp index 71c130383..60918e0b3 100644 --- a/lib/mapping/CCampaignHandler.cpp +++ b/lib/mapping/CCampaignHandler.cpp @@ -30,6 +30,8 @@ #include "serializer/JsonDeserializer.h" #include "serializer/JsonSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + CCampaignHeader::CCampaignHeader() : version(0), mapVersion(0), difficultyChoosenByPlayer(0), music(0), filename(), loadFromLod(0) { @@ -562,3 +564,5 @@ std::string CCampaignHandler::prologVoiceName(ui8 index) + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CCampaignHandler.h b/lib/mapping/CCampaignHandler.h index 1e3e923c1..ebd11d459 100644 --- a/lib/mapping/CCampaignHandler.h +++ b/lib/mapping/CCampaignHandler.h @@ -11,6 +11,8 @@ #include "../../lib/GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + struct StartInfo; class CGHeroInstance; class CBinaryReader; @@ -242,3 +244,5 @@ public: static std::unique_ptr getCampaign(const std::string & name); //name - name of appropriate file }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CDrawRoadsOperation.cpp b/lib/mapping/CDrawRoadsOperation.cpp index d0dd1fff9..c7bd1d6e6 100644 --- a/lib/mapping/CDrawRoadsOperation.cpp +++ b/lib/mapping/CDrawRoadsOperation.cpp @@ -12,6 +12,8 @@ #include "CDrawRoadsOperation.h" #include "CMap.h" +VCMI_LIB_NAMESPACE_BEGIN + const std::vector CDrawLinesOperation::patterns = { //single tile. fall-back pattern @@ -389,3 +391,5 @@ void CDrawRiversOperation::updateTile(TerrainTile & tile, const LinePattern & pa tile.riverDir = gen->nextInt(mapping.first, mapping.second); tile.extTileFlags = (tile.extTileFlags & 0b00111111) | (flip << 2); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CDrawRoadsOperation.h b/lib/mapping/CDrawRoadsOperation.h index b283c5dc8..67c9bb0ff 100644 --- a/lib/mapping/CDrawRoadsOperation.h +++ b/lib/mapping/CDrawRoadsOperation.h @@ -13,6 +13,8 @@ #include "../CRandomGenerator.h" #include "CMapEditManager.h" +VCMI_LIB_NAMESPACE_BEGIN + struct TerrainTile; class CDrawLinesOperation : public CMapOperation @@ -91,3 +93,5 @@ protected: private: std::string riverType; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMap.cpp b/lib/mapping/CMap.cpp index 742e709a8..fa0037f48 100644 --- a/lib/mapping/CMap.cpp +++ b/lib/mapping/CMap.cpp @@ -23,6 +23,8 @@ #include "CMapEditManager.h" #include "../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + SHeroName::SHeroName() : heroId(-1) { @@ -713,3 +715,5 @@ void CMap::resetStaticData() CGObelisk::reset(); CGTownInstance::reset(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMap.h b/lib/mapping/CMap.h index 1c1ae34db..e32d47ab6 100644 --- a/lib/mapping/CMap.h +++ b/lib/mapping/CMap.h @@ -20,6 +20,8 @@ #include "../LogicalExpression.h" #include "CMapDefines.h" +VCMI_LIB_NAMESPACE_BEGIN + class CArtifactInstance; class CGObjectInstance; class CGHeroInstance; @@ -496,3 +498,5 @@ public: h & instanceNames; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapDefines.h b/lib/mapping/CMapDefines.h index dbaf97f30..9e55436a1 100644 --- a/lib/mapping/CMapDefines.h +++ b/lib/mapping/CMapDefines.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + /// The map event is an event which e.g. gives or takes resources of a specific /// amount to/from players and can appear regularly or once a time. class DLL_LINKAGE CMapEvent @@ -111,3 +113,5 @@ struct DLL_LINKAGE TerrainTile h & blockingObjects; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapEditManager.cpp b/lib/mapping/CMapEditManager.cpp index 2f8d44af9..ba8ab5d59 100644 --- a/lib/mapping/CMapEditManager.cpp +++ b/lib/mapping/CMapEditManager.cpp @@ -18,6 +18,8 @@ #include "../mapping/CMap.h" #include "CMapOperation.h" +VCMI_LIB_NAMESPACE_BEGIN + CMapUndoManager::CMapUndoManager() : undoRedoLimit(100000), //not sure if we ever need to bother about undo limit undoCallback([](bool, bool) {}) @@ -199,3 +201,5 @@ CMapUndoManager & CMapEditManager::getUndoManager() { return undoManager; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapEditManager.h b/lib/mapping/CMapEditManager.h index 7fe216d16..7ce123e8a 100644 --- a/lib/mapping/CMapEditManager.h +++ b/lib/mapping/CMapEditManager.h @@ -14,6 +14,8 @@ #include "CMapOperation.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class CTerrainViewPatternConfig; struct TerrainViewPattern; @@ -98,3 +100,5 @@ private: CTerrainSelection terrainSel; CObjectSelection objectSel; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapInfo.cpp b/lib/mapping/CMapInfo.cpp index 25b6a78b8..3756ae580 100644 --- a/lib/mapping/CMapInfo.cpp +++ b/lib/mapping/CMapInfo.cpp @@ -23,6 +23,8 @@ #include "../CHeroHandler.h" #include "../CModHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + CMapInfo::CMapInfo() : scenarioOptionsOfSave(nullptr), amountOfPlayersOnMap(0), amountOfHumanControllablePlayers(0), amountOfHumanPlayersInSave(0), isRandomMap(false) { @@ -182,3 +184,5 @@ std::string CMapInfo::getMapSizeName() const return "C"; } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapInfo.h b/lib/mapping/CMapInfo.h index c04058bd9..69c4e96de 100644 --- a/lib/mapping/CMapInfo.h +++ b/lib/mapping/CMapInfo.h @@ -20,6 +20,8 @@ #include "CMap.h" #include "CCampaignHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + struct StartInfo; /** @@ -69,3 +71,5 @@ public: h & isRandomMap; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapOperation.cpp b/lib/mapping/CMapOperation.cpp index 4e00496c1..c89a5518d 100644 --- a/lib/mapping/CMapOperation.cpp +++ b/lib/mapping/CMapOperation.cpp @@ -13,7 +13,9 @@ #include "../VCMI_Lib.h" #include "CMap.h" -#include "MapEditUtils.h" +#include "MapEditUtils.h" + +VCMI_LIB_NAMESPACE_BEGIN CMapOperation::CMapOperation(CMap* map) : map(map) { @@ -672,3 +674,5 @@ std::string CRemoveObjectOperation::getLabel() const { return "Remove Object"; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapOperation.h b/lib/mapping/CMapOperation.h index 921832470..2121e9fad 100644 --- a/lib/mapping/CMapOperation.h +++ b/lib/mapping/CMapOperation.h @@ -13,6 +13,8 @@ #include "../int3.h" #include "MapEditUtils.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class CMap; class CRandomGenerator; @@ -158,4 +160,6 @@ public: private: CGObjectInstance* obj; -}; \ No newline at end of file +}; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapService.cpp b/lib/mapping/CMapService.cpp index 4c27ed957..2ad1c8430 100644 --- a/lib/mapping/CMapService.cpp +++ b/lib/mapping/CMapService.cpp @@ -21,6 +21,8 @@ #include "MapFormatH3M.h" #include "MapFormatJson.h" +VCMI_LIB_NAMESPACE_BEGIN + std::unique_ptr CMapService::loadMap(const ResourceID & name) const { @@ -138,3 +140,5 @@ std::unique_ptr CMapService::getMapPatcher(std::string scenarioName logGlobal->debug("Request to patch map %s", scenarioName); return std::unique_ptr(new CMapPatcher(node[scenarioName])); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/CMapService.h b/lib/mapping/CMapService.h index f0882640f..98aac2a4c 100644 --- a/lib/mapping/CMapService.h +++ b/lib/mapping/CMapService.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + class ResourceID; class CMap; @@ -171,3 +173,5 @@ public: virtual ~IMapSaver(){} }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/MapEditUtils.cpp b/lib/mapping/MapEditUtils.cpp index 489954356..2d1b491f6 100644 --- a/lib/mapping/MapEditUtils.cpp +++ b/lib/mapping/MapEditUtils.cpp @@ -16,6 +16,8 @@ #include "CMap.h" #include "CMapOperation.h" +VCMI_LIB_NAMESPACE_BEGIN + MapRect::MapRect() : x(0), y(0), z(0), width(0), height(0) { @@ -369,3 +371,5 @@ void CTerrainViewPatternUtils::printDebuggingInfoAboutTile(const CMap * map, int logGlobal->debug(line); } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/MapEditUtils.h b/lib/mapping/MapEditUtils.h index 6df777a3d..d2f35781a 100644 --- a/lib/mapping/MapEditUtils.h +++ b/lib/mapping/MapEditUtils.h @@ -14,6 +14,8 @@ #include "../CRandomGenerator.h" #include "Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class CMap; @@ -231,3 +233,5 @@ class DLL_LINKAGE CTerrainViewPatternUtils public: static void printDebuggingInfoAboutTile(const CMap * map, int3 pos); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/MapFormatH3M.cpp b/lib/mapping/MapFormatH3M.cpp index 26faf348b..fdd35b68a 100644 --- a/lib/mapping/MapFormatH3M.cpp +++ b/lib/mapping/MapFormatH3M.cpp @@ -26,6 +26,8 @@ #include "../VCMI_Lib.h" #include "../NetPacksBase.h" +VCMI_LIB_NAMESPACE_BEGIN + const bool CMapLoaderH3M::IS_PROFILING_ENABLED = false; @@ -2266,3 +2268,5 @@ void CMapLoaderH3M::afterRead() } } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/MapFormatH3M.h b/lib/mapping/MapFormatH3M.h index 1a71f2d1d..908cef1a7 100644 --- a/lib/mapping/MapFormatH3M.h +++ b/lib/mapping/MapFormatH3M.h @@ -19,6 +19,8 @@ #include "../filesystem/CBinaryReader.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGHeroInstance; class CArtifactInstance; class CGObjectInstance; @@ -260,3 +262,5 @@ private: CInputStream * inputStream; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/MapFormatJson.cpp b/lib/mapping/MapFormatJson.cpp index e14de101b..f06a84ce3 100644 --- a/lib/mapping/MapFormatJson.cpp +++ b/lib/mapping/MapFormatJson.cpp @@ -30,6 +30,8 @@ #include "../serializer/JsonDeserializer.h" #include "../serializer/JsonSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + class MapObjectResolver: public IInstanceResolver { public: @@ -1364,3 +1366,5 @@ void CMapSaverJson::writeObjects() addToArchive(data, OBJECTS_FILE_NAME); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/mapping/MapFormatJson.h b/lib/mapping/MapFormatJson.h index 4dc36df5a..149984e63 100644 --- a/lib/mapping/MapFormatJson.h +++ b/lib/mapping/MapFormatJson.h @@ -19,6 +19,8 @@ #include "../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + struct TriggeredEvent; struct TerrainTile; struct PlayerInfo; @@ -265,3 +267,5 @@ private: std::shared_ptr ioApi; CZipSaver saver;///< object to handle zip archive operations }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/RegisterTypes.cpp b/lib/registerTypes/RegisterTypes.cpp index a3db27100..94b8436e5 100644 --- a/lib/registerTypes/RegisterTypes.cpp +++ b/lib/registerTypes/RegisterTypes.cpp @@ -24,6 +24,8 @@ #include "../serializer/BinarySerializer.h" #include "../serializer/CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + // For reference: peak memory usage by gcc during compilation of register type templates // registerTypesMapObjects: 1.9 Gb // registerTypes2: 2.2 Gb @@ -49,3 +51,5 @@ DEFINE_EXTERNAL_METHOD(registerTypesLobbyPacks) template void registerTypes(BinaryDeserializer & s); template void registerTypes(BinarySerializer & s); template void registerTypes(CTypeList & s); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/RegisterTypes.h b/lib/registerTypes/RegisterTypes.h index 17e46c54c..f50fac623 100644 --- a/lib/registerTypes/RegisterTypes.h +++ b/lib/registerTypes/RegisterTypes.h @@ -24,6 +24,8 @@ #include "../battle/CObstacleInstance.h" #include "../CStack.h" +VCMI_LIB_NAMESPACE_BEGIN + class BinarySerializer; class BinaryDeserializer; class CTypeList; @@ -408,3 +410,5 @@ extern template DLL_LINKAGE void registerTypes(CTypeList & s); #endif + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/TypesClientPacks1.cpp b/lib/registerTypes/TypesClientPacks1.cpp index 3044df426..305f53e56 100644 --- a/lib/registerTypes/TypesClientPacks1.cpp +++ b/lib/registerTypes/TypesClientPacks1.cpp @@ -29,7 +29,11 @@ #include "../serializer/BinarySerializer.h" #include "../serializer/CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + template void registerTypesClientPacks1(BinaryDeserializer & s); template void registerTypesClientPacks1(BinarySerializer & s); template void registerTypesClientPacks1(CTypeList & s); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/TypesClientPacks2.cpp b/lib/registerTypes/TypesClientPacks2.cpp index 4a6dd9b30..5d8400b80 100644 --- a/lib/registerTypes/TypesClientPacks2.cpp +++ b/lib/registerTypes/TypesClientPacks2.cpp @@ -31,9 +31,13 @@ #include "../serializer/BinarySerializer.h" #include "../serializer/CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + template void registerTypesClientPacks2(BinaryDeserializer & s); template void registerTypesClientPacks2(BinarySerializer & s); template void registerTypesClientPacks2(CTypeList & s); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/TypesLobbyPacks.cpp b/lib/registerTypes/TypesLobbyPacks.cpp index e7360a6e3..3a65eb231 100644 --- a/lib/registerTypes/TypesLobbyPacks.cpp +++ b/lib/registerTypes/TypesLobbyPacks.cpp @@ -31,7 +31,11 @@ #include "../serializer/BinarySerializer.h" #include "../serializer/CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + template void registerTypesLobbyPacks(BinaryDeserializer & s); template void registerTypesLobbyPacks(BinarySerializer & s); template void registerTypesLobbyPacks(CTypeList & s); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/TypesMapObjects1.cpp b/lib/registerTypes/TypesMapObjects1.cpp index 7fc2e66b6..690248cd5 100644 --- a/lib/registerTypes/TypesMapObjects1.cpp +++ b/lib/registerTypes/TypesMapObjects1.cpp @@ -29,8 +29,12 @@ #include "../serializer/BinarySerializer.h" #include "../serializer/CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + template void registerTypesMapObjects1(BinaryDeserializer & s); template void registerTypesMapObjects1(BinarySerializer & s); template void registerTypesMapObjects1(CTypeList & s); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/TypesMapObjects2.cpp b/lib/registerTypes/TypesMapObjects2.cpp index 7a52f3764..cc3a05e47 100644 --- a/lib/registerTypes/TypesMapObjects2.cpp +++ b/lib/registerTypes/TypesMapObjects2.cpp @@ -31,8 +31,12 @@ #include "../serializer/BinarySerializer.h" #include "../serializer/CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + template void registerTypesMapObjects2(BinaryDeserializer & s); template void registerTypesMapObjects2(BinarySerializer & s); template void registerTypesMapObjects2(CTypeList & s); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/TypesMapObjects3.cpp b/lib/registerTypes/TypesMapObjects3.cpp index 03022ffb7..fbac38dc0 100644 --- a/lib/registerTypes/TypesMapObjects3.cpp +++ b/lib/registerTypes/TypesMapObjects3.cpp @@ -29,6 +29,10 @@ #include "../serializer/BinarySerializer.h" #include "../serializer/CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + template void registerTypesMapObjectTypes(BinaryDeserializer & s); template void registerTypesMapObjectTypes(BinarySerializer & s); template void registerTypesMapObjectTypes(CTypeList & s); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/registerTypes/TypesServerPacks.cpp b/lib/registerTypes/TypesServerPacks.cpp index 18f9e53e3..82d00d4f0 100644 --- a/lib/registerTypes/TypesServerPacks.cpp +++ b/lib/registerTypes/TypesServerPacks.cpp @@ -29,6 +29,10 @@ #include "../serializer/BinarySerializer.h" #include "../serializer/CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + template void registerTypesServerPacks(BinaryDeserializer & s); template void registerTypesServerPacks(BinarySerializer & s); template void registerTypesServerPacks(CTypeList & s); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CMapGenOptions.cpp b/lib/rmg/CMapGenOptions.cpp index dfd8f4ec8..774f374d5 100644 --- a/lib/rmg/CMapGenOptions.cpp +++ b/lib/rmg/CMapGenOptions.cpp @@ -18,6 +18,8 @@ #include "../VCMI_Lib.h" #include "../CTownHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + CMapGenOptions::CMapGenOptions() : width(CMapHeader::MAP_SIZE_MIDDLE), height(CMapHeader::MAP_SIZE_MIDDLE), hasTwoLevels(true), playerCount(RANDOM_SIZE), teamCount(RANDOM_SIZE), compOnlyPlayerCount(RANDOM_SIZE), compOnlyTeamCount(RANDOM_SIZE), @@ -491,3 +493,5 @@ void CMapGenOptions::CPlayerSettings::setPlayerType(EPlayerType::EPlayerType val { playerType = value; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CMapGenOptions.h b/lib/rmg/CMapGenOptions.h index 01c2f815f..9017576b1 100644 --- a/lib/rmg/CMapGenOptions.h +++ b/lib/rmg/CMapGenOptions.h @@ -12,6 +12,8 @@ #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class CRmgTemplate; class CRandomGenerator; @@ -188,3 +190,5 @@ public: //TODO add name of template to class, enables selection of a template by a user } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CMapGenerator.cpp b/lib/rmg/CMapGenerator.cpp index 60f54eee1..7796e5f49 100644 --- a/lib/rmg/CMapGenerator.cpp +++ b/lib/rmg/CMapGenerator.cpp @@ -27,6 +27,8 @@ #include "TreasurePlacer.h" #include "RoadPlacer.h" +VCMI_LIB_NAMESPACE_BEGIN + CMapGenerator::CMapGenerator(CMapGenOptions& mapGenOptions, int RandomSeed) : mapGenOptions(mapGenOptions), randomSeed(RandomSeed), prisonsRemaining(0), monolithIndex(0) @@ -396,3 +398,5 @@ Zone * CMapGenerator::getZoneWater() const return z.second.get(); return nullptr; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CMapGenerator.h b/lib/rmg/CMapGenerator.h index 96c52ce98..5bbc575ae 100644 --- a/lib/rmg/CMapGenerator.h +++ b/lib/rmg/CMapGenerator.h @@ -17,6 +17,8 @@ #include "CRmgTemplate.h" #include "../LoadProgress.h" +VCMI_LIB_NAMESPACE_BEGIN + class CRmgTemplate; class CMapGenOptions; class JsonNode; @@ -100,3 +102,5 @@ private: void fillZones(); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CRmgTemplate.cpp b/lib/rmg/CRmgTemplate.cpp index 1025ff874..f1d8e8bec 100644 --- a/lib/rmg/CRmgTemplate.cpp +++ b/lib/rmg/CRmgTemplate.cpp @@ -20,6 +20,8 @@ #include "../serializer/JsonSerializeFormat.h" #include "../StringConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace { si32 decodeZoneId(const std::string & json) @@ -799,3 +801,5 @@ void CRmgTemplate::serializePlayers(JsonSerializeFormat & handler, CPlayerCountR value.fromString(encodedValue); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CRmgTemplate.h b/lib/rmg/CRmgTemplate.h index 2637d8c5a..31cc4bca7 100644 --- a/lib/rmg/CRmgTemplate.h +++ b/lib/rmg/CRmgTemplate.h @@ -16,6 +16,8 @@ #include "../Terrain.h" #include "CMapGenOptions.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonSerializeFormat; namespace ETemplateZoneType @@ -216,3 +218,5 @@ private: void serializeSize(JsonSerializeFormat & handler, int3 & value, const std::string & fieldName); void serializePlayers(JsonSerializeFormat & handler, CPlayerCountRange & value, const std::string & fieldName); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CRmgTemplateStorage.cpp b/lib/rmg/CRmgTemplateStorage.cpp index ec3f7e890..15648a224 100644 --- a/lib/rmg/CRmgTemplateStorage.cpp +++ b/lib/rmg/CRmgTemplateStorage.cpp @@ -15,6 +15,8 @@ #include "../serializer/JsonDeserializer.h" +VCMI_LIB_NAMESPACE_BEGIN + using namespace rmg; void CRmgTemplateStorage::loadObject(std::string scope, std::string name, const JsonNode & data, size_t index) @@ -78,3 +80,5 @@ std::vector CRmgTemplateStorage::getTemplates() const } return result; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CRmgTemplateStorage.h b/lib/rmg/CRmgTemplateStorage.h index b59631802..0e6f66288 100644 --- a/lib/rmg/CRmgTemplateStorage.h +++ b/lib/rmg/CRmgTemplateStorage.h @@ -14,6 +14,8 @@ #include "../int3.h" #include "CRmgTemplate.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; /// The CJsonRmgTemplateLoader loads templates from a JSON file. @@ -38,3 +40,5 @@ private: std::map templatesByName; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CZonePlacer.cpp b/lib/rmg/CZonePlacer.cpp index 8200895a7..4c37f3458 100644 --- a/lib/rmg/CZonePlacer.cpp +++ b/lib/rmg/CZonePlacer.cpp @@ -17,6 +17,8 @@ #include "Zone.h" #include "Functions.h" +VCMI_LIB_NAMESPACE_BEGIN + class CRandomGenerator; CZonePlacer::CZonePlacer(RmgMap & map) @@ -576,3 +578,5 @@ void CZonePlacer::assignZones(CRandomGenerator * rand) } logGlobal->info("Finished zone colouring"); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/CZonePlacer.h b/lib/rmg/CZonePlacer.h index 6558435bb..8e26a7e7e 100644 --- a/lib/rmg/CZonePlacer.h +++ b/lib/rmg/CZonePlacer.h @@ -14,6 +14,8 @@ #include "../int3.h" #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class CZoneGraph; class CMap; class CRandomGenerator; @@ -58,3 +60,5 @@ private: //std::unique_ptr graph; RmgMap & map; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/ConnectionsPlacer.cpp b/lib/rmg/ConnectionsPlacer.cpp index bd4633398..dcdb2b28d 100644 --- a/lib/rmg/ConnectionsPlacer.cpp +++ b/lib/rmg/ConnectionsPlacer.cpp @@ -25,6 +25,8 @@ #include "WaterProxy.h" #include "TownPlacer.h" +VCMI_LIB_NAMESPACE_BEGIN + void ConnectionsPlacer::process() { collectNeighbourZones(); @@ -278,3 +280,5 @@ void ConnectionsPlacer::collectNeighbourZones() dNeighbourZones[zid].insert(i); } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/ConnectionsPlacer.h b/lib/rmg/ConnectionsPlacer.h index bdbd86740..ac577b687 100644 --- a/lib/rmg/ConnectionsPlacer.h +++ b/lib/rmg/ConnectionsPlacer.h @@ -12,6 +12,8 @@ #include "Zone.h" #include "RmgArea.h" +VCMI_LIB_NAMESPACE_BEGIN + class ConnectionsPlacer: public Modificator { public: @@ -33,3 +35,5 @@ protected: std::vector dConnections, dCompleted; std::map dNeighbourZones; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/Functions.cpp b/lib/rmg/Functions.cpp index 210bf9fe2..9795cc621 100644 --- a/lib/rmg/Functions.cpp +++ b/lib/rmg/Functions.cpp @@ -28,6 +28,8 @@ #include "../mapObjects/MapObjects.h" //needed to resolve templates for CommonConstructors.h #include "../VCMI_Lib.h" +VCMI_LIB_NAMESPACE_BEGIN + void createModificators(RmgMap & map) { for(auto & z : map.getZones()) @@ -176,3 +178,5 @@ void createObstaclesCommon2(RmgMap & map, CRandomGenerator & generator) } } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/Functions.h b/lib/rmg/Functions.h index 0be072e84..5696126da 100644 --- a/lib/rmg/Functions.h +++ b/lib/rmg/Functions.h @@ -13,6 +13,8 @@ #include "Zone.h" #include //A* +VCMI_LIB_NAMESPACE_BEGIN + class RmgMap; class ObjectManager; class ObjectTemplate; @@ -46,3 +48,5 @@ void initTerrainType(Zone & zone, CMapGenerator & gen); int chooseRandomAppearance(CRandomGenerator & generator, si32 ObjID, const Terrain & terrain); + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/ObjectManager.cpp b/lib/rmg/ObjectManager.cpp index 875b9974a..217c03017 100644 --- a/lib/rmg/ObjectManager.cpp +++ b/lib/rmg/ObjectManager.cpp @@ -24,6 +24,8 @@ #include "Functions.h" #include "RmgObject.h" +VCMI_LIB_NAMESPACE_BEGIN + void ObjectManager::process() { zone.fractalize(); @@ -491,3 +493,5 @@ bool ObjectManager::addGuard(rmg::Object & object, si32 strength, bool zoneGuard return true; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/ObjectManager.h b/lib/rmg/ObjectManager.h index 071b3ab8a..37ad5b1f0 100644 --- a/lib/rmg/ObjectManager.h +++ b/lib/rmg/ObjectManager.h @@ -14,6 +14,8 @@ #include "RmgObject.h" #include //A* +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class ObjectTemplate; class CGCreature; @@ -79,3 +81,5 @@ protected: boost::heap::priority_queue> tilesByDistance; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/ObstaclePlacer.cpp b/lib/rmg/ObstaclePlacer.cpp index 29fba34ab..519cacf00 100644 --- a/lib/rmg/ObstaclePlacer.cpp +++ b/lib/rmg/ObstaclePlacer.cpp @@ -24,6 +24,8 @@ #include "Functions.h" #include "../mapping/CMapEditManager.h" +VCMI_LIB_NAMESPACE_BEGIN + void ObstacleProxy::collectPossibleObstacles(const Terrain & terrain) { //get all possible obstacles for this terrain @@ -262,3 +264,5 @@ bool ObstaclePlacer::isProhibited(const rmg::Area & objArea) const void ObstaclePlacer::finalInsertion(CMapEditManager *, std::set &) { } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/ObstaclePlacer.h b/lib/rmg/ObstaclePlacer.h index b98d042aa..8f2fedbbe 100644 --- a/lib/rmg/ObstaclePlacer.h +++ b/lib/rmg/ObstaclePlacer.h @@ -11,10 +11,13 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + class CMap; class CMapEditManager; class RiverPlacer; class ObjectManager; + class DLL_LINKAGE ObstacleProxy { public: @@ -69,3 +72,5 @@ private: RiverPlacer * riverManager; ObjectManager * manager; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RiverPlacer.cpp b/lib/rmg/RiverPlacer.cpp index 599c1cded..b1d6229db 100644 --- a/lib/rmg/RiverPlacer.cpp +++ b/lib/rmg/RiverPlacer.cpp @@ -22,6 +22,8 @@ #include "WaterProxy.h" #include "RoadPlacer.h" +VCMI_LIB_NAMESPACE_BEGIN + const int RIVER_DELTA_ID = 143; const int RIVER_DELTA_SUBTYPE = 0; const std::map RIVER_DELTA_TEMPLATE_NAME @@ -402,3 +404,5 @@ void RiverPlacer::connectRiver(const int3 & tile) rivers.unite(pathToSource.getPathArea()); rivers.unite(pathToSink.getPathArea()); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RiverPlacer.h b/lib/rmg/RiverPlacer.h index 46c6e1e23..f20233af7 100644 --- a/lib/rmg/RiverPlacer.h +++ b/lib/rmg/RiverPlacer.h @@ -11,6 +11,8 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + class RiverPlacer: public Modificator { public: @@ -46,3 +48,5 @@ private: std::map heightMap; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RmgArea.cpp b/lib/rmg/RmgArea.cpp index a2fb40045..f733a4d01 100644 --- a/lib/rmg/RmgArea.cpp +++ b/lib/rmg/RmgArea.cpp @@ -12,6 +12,8 @@ #include "RmgArea.h" #include "CMapGenerator.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace rmg { @@ -402,3 +404,5 @@ bool operator== (const Area & l, const Area & r) } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RmgArea.h b/lib/rmg/RmgArea.h index cc995f6b0..a9b0f4d0b 100644 --- a/lib/rmg/RmgArea.h +++ b/lib/rmg/RmgArea.h @@ -13,6 +13,8 @@ #include "../GameConstants.h" #include "../int3.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace rmg { static const std::array dirs4 = { int3(0,1,0),int3(0,-1,0),int3(-1,0,0),int3(+1,0,0) }; @@ -84,3 +86,5 @@ namespace rmg mutable int3 dTotalShiftCache; }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RmgMap.cpp b/lib/rmg/RmgMap.cpp index 95c40acbb..ee8d35767 100644 --- a/lib/rmg/RmgMap.cpp +++ b/lib/rmg/RmgMap.cpp @@ -30,6 +30,8 @@ #include "Functions.h" #include "CMapGenerator.h" +VCMI_LIB_NAMESPACE_BEGIN + RmgMap::RmgMap(const CMapGenOptions& mapGenOptions) : mapGenOptions(mapGenOptions), zonesTotal(0) { @@ -338,3 +340,5 @@ void RmgMap::dump(bool zoneId) const } out << std::endl; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RmgMap.h b/lib/rmg/RmgMap.h index ab5be9b78..a4702c362 100644 --- a/lib/rmg/RmgMap.h +++ b/lib/rmg/RmgMap.h @@ -13,6 +13,8 @@ #include "../GameConstants.h" #include "../mapping/CMap.h" +VCMI_LIB_NAMESPACE_BEGIN + class CMapEditManager; class TileInfo; class CMapGenOptions; @@ -79,3 +81,5 @@ private: boost::multi_array tiles; //[x][y][z] boost::multi_array zoneColouring; //[x][y][z] }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RmgObject.cpp b/lib/rmg/RmgObject.cpp index 9635daf53..f7898f143 100644 --- a/lib/rmg/RmgObject.cpp +++ b/lib/rmg/RmgObject.cpp @@ -19,6 +19,8 @@ #include "../mapObjects/MapObjects.h" //needed to resolve templates for CommonConstructors.h #include "Functions.h" +VCMI_LIB_NAMESPACE_BEGIN + using namespace rmg; Object::Instance::Instance(const Object& parent, CGObjectInstance & object): dParent(parent), dObject(object) @@ -325,3 +327,5 @@ void Object::clear() dAccessibleAreaFullCache.clear(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RmgObject.h b/lib/rmg/RmgObject.h index e418631c3..9a4737c70 100644 --- a/lib/rmg/RmgObject.h +++ b/lib/rmg/RmgObject.h @@ -14,6 +14,8 @@ #include "../int3.h" #include "RmgArea.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class RmgMap; class Terrain; @@ -85,3 +87,5 @@ private: ui32 dStrenght; }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RmgPath.cpp b/lib/rmg/RmgPath.cpp index 7e38ae04c..fe7319736 100644 --- a/lib/rmg/RmgPath.cpp +++ b/lib/rmg/RmgPath.cpp @@ -12,6 +12,8 @@ #include "RmgPath.h" #include //A* +VCMI_LIB_NAMESPACE_BEGIN + using namespace rmg; const std::function Path::DEFAULT_MOVEMENT_FUNCTION = @@ -191,3 +193,5 @@ const Area & Path::getPathArea() const { return dPath; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RmgPath.h b/lib/rmg/RmgPath.h index 0866f856c..6f65c1454 100644 --- a/lib/rmg/RmgPath.h +++ b/lib/rmg/RmgPath.h @@ -14,6 +14,8 @@ #include "../int3.h" #include "RmgArea.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace rmg { class Path @@ -47,3 +49,5 @@ private: Area dPath; }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RoadPlacer.cpp b/lib/rmg/RoadPlacer.cpp index 8f605a0d6..8dde55600 100644 --- a/lib/rmg/RoadPlacer.cpp +++ b/lib/rmg/RoadPlacer.cpp @@ -18,6 +18,8 @@ #include "../mapping/CMapEditManager.h" #include "RmgPath.h" +VCMI_LIB_NAMESPACE_BEGIN + void RoadPlacer::process() { connectRoads(); @@ -121,3 +123,5 @@ char RoadPlacer::dump(const int3 & t) return 'i'; return Modificator::dump(t); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RoadPlacer.h b/lib/rmg/RoadPlacer.h index 585679ee6..092f3499f 100644 --- a/lib/rmg/RoadPlacer.h +++ b/lib/rmg/RoadPlacer.h @@ -11,6 +11,8 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + class RoadPlacer: public Modificator { public: @@ -35,3 +37,5 @@ protected: rmg::Area roads; //all tiles with roads rmg::Area areaRoads, isolated; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RockPlacer.cpp b/lib/rmg/RockPlacer.cpp index 7688c690c..c07251a04 100644 --- a/lib/rmg/RockPlacer.cpp +++ b/lib/rmg/RockPlacer.cpp @@ -20,6 +20,8 @@ #include "../CRandomGenerator.h" #include "../mapping/CMapEditManager.h" +VCMI_LIB_NAMESPACE_BEGIN + void RockPlacer::process() { rockTerrain = Terrain::Manager::getInfo(zone.getTerrainType()).rockTerrain; @@ -101,3 +103,5 @@ char RockPlacer::dump(const int3 & t) } return Modificator::dump(t); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/RockPlacer.h b/lib/rmg/RockPlacer.h index c7217674f..76bd77a14 100644 --- a/lib/rmg/RockPlacer.h +++ b/lib/rmg/RockPlacer.h @@ -11,6 +11,8 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + class RockPlacer: public Modificator { public: @@ -28,3 +30,5 @@ protected: rmg::Area rockArea, accessibleArea; Terrain rockTerrain; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/TerrainPainter.cpp b/lib/rmg/TerrainPainter.cpp index fba82c55c..bec92812b 100644 --- a/lib/rmg/TerrainPainter.cpp +++ b/lib/rmg/TerrainPainter.cpp @@ -19,6 +19,8 @@ #include "CMapGenerator.h" #include "RmgMap.h" +VCMI_LIB_NAMESPACE_BEGIN + void TerrainPainter::process() { initTerrainType(zone, generator); @@ -33,3 +35,5 @@ void TerrainPainter::init() POSTFUNCTION_ALL(ConnectionsPlacer); POSTFUNCTION(ObjectManager); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/TerrainPainter.h b/lib/rmg/TerrainPainter.h index 7052d883f..59024c9e1 100644 --- a/lib/rmg/TerrainPainter.h +++ b/lib/rmg/TerrainPainter.h @@ -11,6 +11,8 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + class TerrainPainter: public Modificator { public: @@ -19,3 +21,5 @@ public: void process() override; void init() override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/TileInfo.cpp b/lib/rmg/TileInfo.cpp index 9070333d3..a4475f0cf 100644 --- a/lib/rmg/TileInfo.cpp +++ b/lib/rmg/TileInfo.cpp @@ -11,6 +11,8 @@ #include "StdInc.h" #include "TileInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + TileInfo::TileInfo():nearestObjectDistance(float(INT_MAX)), terrain() { occupied = ETileType::POSSIBLE; //all tiles are initially possible to place objects or passages @@ -76,3 +78,5 @@ void TileInfo::setRoadType(const std::string & value) roadType = value; // setOccupied(ETileType::FREE); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/TileInfo.h b/lib/rmg/TileInfo.h index 30ed5d90f..02b4887c0 100644 --- a/lib/rmg/TileInfo.h +++ b/lib/rmg/TileInfo.h @@ -13,6 +13,8 @@ #include "../GameConstants.h" #include "../Terrain.h" +VCMI_LIB_NAMESPACE_BEGIN + class TileInfo { public: @@ -39,3 +41,5 @@ private: Terrain terrain; std::string roadType; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/TownPlacer.cpp b/lib/rmg/TownPlacer.cpp index d33ae032b..d6971adfd 100644 --- a/lib/rmg/TownPlacer.cpp +++ b/lib/rmg/TownPlacer.cpp @@ -24,6 +24,8 @@ #include "WaterAdopter.h" #include "TileInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + void TownPlacer::process() { auto * manager = zone.getModificator(); @@ -278,3 +280,5 @@ int TownPlacer::getTotalTowns() const { return totalTowns; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/TownPlacer.h b/lib/rmg/TownPlacer.h index 3c7fcadbe..d667852db 100644 --- a/lib/rmg/TownPlacer.h +++ b/lib/rmg/TownPlacer.h @@ -10,6 +10,8 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + class ObjectManager; class CGTownInstance; @@ -35,3 +37,5 @@ protected: int totalTowns = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/TreasurePlacer.cpp b/lib/rmg/TreasurePlacer.cpp index cf1d58abb..7ae6a37d7 100644 --- a/lib/rmg/TreasurePlacer.cpp +++ b/lib/rmg/TreasurePlacer.cpp @@ -24,6 +24,8 @@ #include "../mapping/CMap.h" #include "../mapping/CMapEditManager.h" +VCMI_LIB_NAMESPACE_BEGIN + void TreasurePlacer::process() { addAllPossibleObjects(); @@ -823,3 +825,5 @@ void ObjectInfo::setTemplate(si32 type, si32 subtype, Terrain terrainType) templ = templates.front(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/TreasurePlacer.h b/lib/rmg/TreasurePlacer.h index 457ef35a8..baba38047 100644 --- a/lib/rmg/TreasurePlacer.h +++ b/lib/rmg/TreasurePlacer.h @@ -12,6 +12,8 @@ #include "Zone.h" #include "../mapObjects/ObjectTemplate.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class ObjectManager; class RmgMap; @@ -65,3 +67,5 @@ protected: Zone * questArtZone = nullptr; //artifacts required for Seer Huts will be placed here - or not if null }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/WaterAdopter.cpp b/lib/rmg/WaterAdopter.cpp index df06e682d..2dd540995 100644 --- a/lib/rmg/WaterAdopter.cpp +++ b/lib/rmg/WaterAdopter.cpp @@ -25,6 +25,8 @@ #include "ConnectionsPlacer.h" #include "TileInfo.h" +VCMI_LIB_NAMESPACE_BEGIN + void WaterAdopter::process() { createWater(map.getMapGenOptions().getWaterContent()); @@ -259,3 +261,5 @@ char WaterAdopter::dump(const int3 & t) return Modificator::dump(t); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/WaterAdopter.h b/lib/rmg/WaterAdopter.h index 8b97b8d74..ef47d3fa8 100644 --- a/lib/rmg/WaterAdopter.h +++ b/lib/rmg/WaterAdopter.h @@ -11,6 +11,8 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + class WaterAdopter: public Modificator { public: @@ -34,3 +36,5 @@ protected: std::map distanceMap; std::map reverseDistanceMap; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/WaterProxy.cpp b/lib/rmg/WaterProxy.cpp index 777cf8c11..a2a8c9f93 100644 --- a/lib/rmg/WaterProxy.cpp +++ b/lib/rmg/WaterProxy.cpp @@ -27,6 +27,8 @@ #include "WaterAdopter.h" #include "RmgArea.h" +VCMI_LIB_NAMESPACE_BEGIN + void WaterProxy::process() { for(auto & t : zone.area().getTilesVector()) @@ -358,3 +360,5 @@ char WaterProxy::dump(const int3 & t) return '~'; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/WaterProxy.h b/lib/rmg/WaterProxy.h index 769d70208..de50f7354 100644 --- a/lib/rmg/WaterProxy.h +++ b/lib/rmg/WaterProxy.h @@ -11,6 +11,8 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + struct RouteInfo { rmg::Area blocked; @@ -53,3 +55,5 @@ protected: std::map lakeMap; //map tile on lakeId which is position of lake in lakes array +1 }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/WaterRoutes.cpp b/lib/rmg/WaterRoutes.cpp index 40569d4a2..8cca1e426 100644 --- a/lib/rmg/WaterRoutes.cpp +++ b/lib/rmg/WaterRoutes.cpp @@ -28,6 +28,8 @@ #include "WaterAdopter.h" #include "RmgArea.h" +VCMI_LIB_NAMESPACE_BEGIN + void WaterRoutes::process() { auto * wproxy = zone.getModificator(); @@ -117,3 +119,5 @@ char WaterRoutes::dump(const int3 & t) return ' '; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/WaterRoutes.h b/lib/rmg/WaterRoutes.h index 996318362..b693f3d2b 100644 --- a/lib/rmg/WaterRoutes.h +++ b/lib/rmg/WaterRoutes.h @@ -11,6 +11,8 @@ #pragma once #include "Zone.h" +VCMI_LIB_NAMESPACE_BEGIN + struct RouteInfo; class WaterRoutes: public Modificator @@ -25,3 +27,5 @@ public: private: std::vector result; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/Zone.cpp b/lib/rmg/Zone.cpp index 6b2f977f2..b66cf44c8 100644 --- a/lib/rmg/Zone.cpp +++ b/lib/rmg/Zone.cpp @@ -18,6 +18,8 @@ #include "CMapGenerator.h" #include "RmgPath.h" +VCMI_LIB_NAMESPACE_BEGIN + std::function AREA_NO_FILTER = [](const int3 & t) { return true; @@ -405,3 +407,5 @@ Modificator::~Modificator() { } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/Zone.h b/lib/rmg/Zone.h index 3679506c5..37cf07e22 100644 --- a/lib/rmg/Zone.h +++ b/lib/rmg/Zone.h @@ -33,6 +33,8 @@ postfunction(z.second->getModificator()); \ } +VCMI_LIB_NAMESPACE_BEGIN + class RmgMap; class CMapGenerator; class Zone; @@ -141,3 +143,5 @@ protected: Terrain terrainType; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/rmg/float3.h b/lib/rmg/float3.h index 13942d6fb..3398f2877 100644 --- a/lib/rmg/float3.h +++ b/lib/rmg/float3.h @@ -9,6 +9,8 @@ */ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + // FIXME: Class doesn't contain three float values. Update name and description. /// Class which consists of three float values. Represents position virtual RMG (0;1) area. class float3 @@ -161,3 +163,5 @@ struct Shashfloat3 return ret; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/BinaryDeserializer.cpp b/lib/serializer/BinaryDeserializer.cpp index d48587c42..d1773b434 100644 --- a/lib/serializer/BinaryDeserializer.cpp +++ b/lib/serializer/BinaryDeserializer.cpp @@ -13,6 +13,8 @@ #include "../registerTypes/RegisterTypes.h" +VCMI_LIB_NAMESPACE_BEGIN + extern template void registerTypes(BinaryDeserializer & s); CLoadFile::CLoadFile(const boost::filesystem::path & fname, int minimalVersion) @@ -101,3 +103,5 @@ void CLoadFile::checkMagicBytes(const std::string &text) if(loaded != text) throw std::runtime_error("Magic bytes doesn't match!"); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/BinaryDeserializer.h b/lib/serializer/BinaryDeserializer.h index 16b7f22ce..bbb2b0774 100644 --- a/lib/serializer/BinaryDeserializer.h +++ b/lib/serializer/BinaryDeserializer.h @@ -15,6 +15,8 @@ #include "../mapObjects/CGHeroInstance.h" #include "../../Global.h" +VCMI_LIB_NAMESPACE_BEGIN + class CStackInstance; class FileStream; @@ -601,3 +603,5 @@ public: return * this; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/BinarySerializer.cpp b/lib/serializer/BinarySerializer.cpp index 229860012..0e3870920 100644 --- a/lib/serializer/BinarySerializer.cpp +++ b/lib/serializer/BinarySerializer.cpp @@ -13,6 +13,8 @@ #include "../registerTypes/RegisterTypes.h" +VCMI_LIB_NAMESPACE_BEGIN + extern template void registerTypes(BinarySerializer & s); CSaveFile::CSaveFile(const boost::filesystem::path &fname) @@ -73,3 +75,5 @@ void CSaveFile::putMagicBytes(const std::string &text) { write(text.c_str(), (unsigned int)text.length()); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/BinarySerializer.h b/lib/serializer/BinarySerializer.h index 4b6df7d8d..be1cb377c 100644 --- a/lib/serializer/BinarySerializer.h +++ b/lib/serializer/BinarySerializer.h @@ -12,6 +12,8 @@ #include "CTypeList.h" #include "../mapObjects/CArmedInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + class FileStream; class DLL_LINKAGE CSaverBase @@ -389,3 +391,5 @@ public: return * this; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/CLoadIntegrityValidator.cpp b/lib/serializer/CLoadIntegrityValidator.cpp index 7b4637921..e04e4fbff 100644 --- a/lib/serializer/CLoadIntegrityValidator.cpp +++ b/lib/serializer/CLoadIntegrityValidator.cpp @@ -13,6 +13,8 @@ #include "../registerTypes/RegisterTypes.h" +VCMI_LIB_NAMESPACE_BEGIN + CLoadIntegrityValidator::CLoadIntegrityValidator(const boost::filesystem::path &primaryFileName, const boost::filesystem::path &controlFileName, int minimalVersion) : serializer(this), foundDesync(false) { @@ -63,3 +65,5 @@ void CLoadIntegrityValidator::checkMagicBytes( const std::string &text ) primaryFile->checkMagicBytes(text); controlFile->checkMagicBytes(text); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/CLoadIntegrityValidator.h b/lib/serializer/CLoadIntegrityValidator.h index 7ab627914..139e73db1 100644 --- a/lib/serializer/CLoadIntegrityValidator.h +++ b/lib/serializer/CLoadIntegrityValidator.h @@ -11,6 +11,8 @@ #include "BinaryDeserializer.h" +VCMI_LIB_NAMESPACE_BEGIN + /// Simple byte-to-byte saves comparator class DLL_LINKAGE CLoadIntegrityValidator : public IBinaryReader @@ -27,3 +29,5 @@ public: std::unique_ptr decay(); //returns primary file. CLoadIntegrityValidator stops being usable anymore }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/CMemorySerializer.cpp b/lib/serializer/CMemorySerializer.cpp index e63fa67b5..341ab925f 100644 --- a/lib/serializer/CMemorySerializer.cpp +++ b/lib/serializer/CMemorySerializer.cpp @@ -12,6 +12,8 @@ #include "../registerTypes/RegisterTypes.h" +VCMI_LIB_NAMESPACE_BEGIN + int CMemorySerializer::read(void * data, unsigned size) { if(buffer.size() < readPos + size) @@ -38,3 +40,5 @@ CMemorySerializer::CMemorySerializer(): iser(this), oser(this) iser.fileVersion = SERIALIZATION_VERSION; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/CMemorySerializer.h b/lib/serializer/CMemorySerializer.h index 799faa424..586220724 100644 --- a/lib/serializer/CMemorySerializer.h +++ b/lib/serializer/CMemorySerializer.h @@ -12,6 +12,8 @@ #include "BinarySerializer.h" #include "BinaryDeserializer.h" +VCMI_LIB_NAMESPACE_BEGIN + /// Serializer that stores objects in the dynamic buffer. Allows performing deep object copies. class DLL_LINKAGE CMemorySerializer : public IBinaryReader, public IBinaryWriter @@ -39,3 +41,5 @@ public: return ret; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/CSerializer.cpp b/lib/serializer/CSerializer.cpp index ee9977f75..fe53ad072 100644 --- a/lib/serializer/CSerializer.cpp +++ b/lib/serializer/CSerializer.cpp @@ -15,6 +15,8 @@ #include "../CHeroHandler.h" #include "../mapObjects/CGHeroInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + CSerializer::~CSerializer() { @@ -46,3 +48,5 @@ void CSerializer::addStdVecItems(CGameState *gs, LibClasses *lib) smartVectorMembersSerialization = true; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/CSerializer.h b/lib/serializer/CSerializer.h index 00891b786..9b0d14e47 100644 --- a/lib/serializer/CSerializer.h +++ b/lib/serializer/CSerializer.h @@ -12,6 +12,8 @@ #include "../ConstTransitivePtr.h" #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + const ui32 SERIALIZATION_VERSION = 805; const ui32 MINIMAL_SERIALIZATION_VERSION = 805; const std::string SAVEGAME_MAGIC = "VCMISVG"; @@ -199,3 +201,5 @@ class DLL_LINKAGE IBinaryWriter : public virtual CSerializer public: virtual int write(const void * data, unsigned size) = 0; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/CTypeList.cpp b/lib/serializer/CTypeList.cpp index 8ff73749d..64ae07050 100644 --- a/lib/serializer/CTypeList.cpp +++ b/lib/serializer/CTypeList.cpp @@ -12,6 +12,8 @@ #include "../registerTypes/RegisterTypes.h" +VCMI_LIB_NAMESPACE_BEGIN + extern template void registerTypes(CTypeList & s); CTypeList typeList; @@ -135,3 +137,5 @@ CTypeList::TypeInfoPtr CTypeList::getTypeDescriptor(const std::type_info *type, THROW_FORMAT("Cannot find type descriptor for type %s. Was it registered?", type->name()); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/CTypeList.h b/lib/serializer/CTypeList.h index 951df3ec0..38ba68975 100644 --- a/lib/serializer/CTypeList.h +++ b/lib/serializer/CTypeList.h @@ -11,6 +11,8 @@ #include "CSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + struct IPointerCaster { virtual boost::any castRawPtr(const boost::any &ptr) const = 0; // takes From*, returns To* @@ -231,3 +233,5 @@ public: addApplier(typeList.getTypeID(d)); } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/Cast.h b/lib/serializer/Cast.h index 4bef39ce6..ebc7957af 100644 --- a/lib/serializer/Cast.h +++ b/lib/serializer/Cast.h @@ -13,6 +13,8 @@ #include #include "CTypeList.h" +VCMI_LIB_NAMESPACE_BEGIN + template inline const T * dynamic_ptr_cast(const F * ptr) { @@ -60,3 +62,5 @@ inline T * dynamic_ptr_cast(F * ptr) return static_cast(ptr); #endif } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/Connection.cpp b/lib/serializer/Connection.cpp index cd98406b4..bce54123f 100644 --- a/lib/serializer/Connection.cpp +++ b/lib/serializer/Connection.cpp @@ -16,6 +16,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + using namespace boost; using namespace boost::asio::ip; @@ -282,3 +284,5 @@ std::string CConnection::toString() const fmt % name % connectionID % uuid; return fmt.str(); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/Connection.h b/lib/serializer/Connection.h index 6ba68d269..63a161b56 100644 --- a/lib/serializer/Connection.h +++ b/lib/serializer/Connection.h @@ -12,8 +12,6 @@ #include "BinaryDeserializer.h" #include "BinarySerializer.h" -struct CPack; - #if BOOST_VERSION >= 107000 // Boost version >= 1.70 #include typedef boost::asio::basic_stream_socket < boost::asio::ip::tcp > TSocket; @@ -51,6 +49,10 @@ typedef boost::asio::basic_socket_acceptor +VCMI_LIB_NAMESPACE_BEGIN + JsonDeserializer::JsonDeserializer(const IInstanceResolver * instanceResolver_, const JsonNode & root_): JsonTreeSerializer(instanceResolver_, &root_, false, false) { @@ -281,3 +283,5 @@ void JsonDeserializer::readLICPart(const JsonNode & part, const TDecoder & decod } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/JsonDeserializer.h b/lib/serializer/JsonDeserializer.h index bace8e371..8c19c15a2 100644 --- a/lib/serializer/JsonDeserializer.h +++ b/lib/serializer/JsonDeserializer.h @@ -11,6 +11,8 @@ #include "JsonTreeSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE JsonDeserializer: public JsonTreeSerializer { public: @@ -38,3 +40,5 @@ private: void readLICPart(const JsonNode & part, const TDecoder & decoder, const bool val, std::vector & value); void readLICPart(const JsonNode & part, const TDecoder & decoder, std::set & value); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/JsonSerializeFormat.cpp b/lib/serializer/JsonSerializeFormat.cpp index 8e7143629..7525685f3 100644 --- a/lib/serializer/JsonSerializeFormat.cpp +++ b/lib/serializer/JsonSerializeFormat.cpp @@ -12,6 +12,8 @@ #include "../JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + //JsonSerializeHelper JsonSerializeHelper::JsonSerializeHelper(JsonSerializeHelper && other): owner(other.owner), @@ -151,3 +153,5 @@ void JsonSerializeFormat::serializeBool(const std::string & fieldName, bool & va { serializeBool(fieldName, value, true, false, defaultValue); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/JsonSerializeFormat.h b/lib/serializer/JsonSerializeFormat.h index 27070923a..83d171c90 100644 --- a/lib/serializer/JsonSerializeFormat.h +++ b/lib/serializer/JsonSerializeFormat.h @@ -11,6 +11,8 @@ #include "../JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonSerializeFormat; class JsonStructSerializer; class JsonArraySerializer; @@ -523,3 +525,5 @@ void JsonArraySerializer::serializeInt(const size_t index, T & value) if (!owner->saving) value = static_cast(temp); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/JsonSerializer.cpp b/lib/serializer/JsonSerializer.cpp index 7285d7e9e..d01ca0e4c 100644 --- a/lib/serializer/JsonSerializer.cpp +++ b/lib/serializer/JsonSerializer.cpp @@ -12,6 +12,8 @@ #include "../JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + JsonSerializer::JsonSerializer(const IInstanceResolver * instanceResolver_, JsonNode & root_): JsonTreeSerializer(instanceResolver_, &root_, true, false) { @@ -185,3 +187,5 @@ void JsonSerializer::writeLICPartBuffer(const std::string & fieldName, const std } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/JsonSerializer.h b/lib/serializer/JsonSerializer.h index 8621750c9..c75bf1ac6 100644 --- a/lib/serializer/JsonSerializer.h +++ b/lib/serializer/JsonSerializer.h @@ -11,6 +11,8 @@ #include "JsonTreeSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + class DLL_LINKAGE JsonSerializer : public JsonTreeSerializer { public: @@ -44,3 +46,5 @@ private: void writeLICPartBuffer(const std::string & fieldName, const std::string & partName, std::vector & buffer); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/JsonTreeSerializer.h b/lib/serializer/JsonTreeSerializer.h index c5d2becac..c1cb36e61 100644 --- a/lib/serializer/JsonTreeSerializer.h +++ b/lib/serializer/JsonTreeSerializer.h @@ -12,6 +12,8 @@ #include "JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + template class JsonTreeSerializer : public JsonSerializeFormat { @@ -71,3 +73,5 @@ private: currentObject = newCurrentObject; } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/JsonUpdater.cpp b/lib/serializer/JsonUpdater.cpp index dc69e991b..b5702236b 100644 --- a/lib/serializer/JsonUpdater.cpp +++ b/lib/serializer/JsonUpdater.cpp @@ -13,6 +13,8 @@ #include "../JsonNode.h" #include "../HeroBonus.h" +VCMI_LIB_NAMESPACE_BEGIN + JsonUpdater::JsonUpdater(const IInstanceResolver * instanceResolver_, const JsonNode & root_) : JsonTreeSerializer(instanceResolver_, &root_, false, true) { @@ -307,3 +309,5 @@ void JsonUpdater::readLICPart(const JsonNode & part, const TDecoder & decoder, s } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/serializer/JsonUpdater.h b/lib/serializer/JsonUpdater.h index d1caa7ec7..238058692 100644 --- a/lib/serializer/JsonUpdater.h +++ b/lib/serializer/JsonUpdater.h @@ -11,6 +11,8 @@ #include "JsonTreeSerializer.h" +VCMI_LIB_NAMESPACE_BEGIN + class CBonusSystemNode; class DLL_LINKAGE JsonUpdater: public JsonTreeSerializer @@ -42,3 +44,5 @@ private: void readLICPart(const JsonNode & part, const TDecoder & decoder, const bool val, std::vector & value); void readLICPart(const JsonNode & part, const TDecoder & decoder, std::set & value); }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/AbilityCaster.cpp b/lib/spells/AbilityCaster.cpp index 0a9192d89..1e9d23c3c 100644 --- a/lib/spells/AbilityCaster.cpp +++ b/lib/spells/AbilityCaster.cpp @@ -15,6 +15,8 @@ #include "../battle/Unit.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -58,3 +60,5 @@ void AbilityCaster::spendMana(ServerCallback * server, const int32_t spellCost) } } // namespace spells + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/AbilityCaster.h b/lib/spells/AbilityCaster.h index 86585ffdc..2b9c7c2ff 100644 --- a/lib/spells/AbilityCaster.h +++ b/lib/spells/AbilityCaster.h @@ -12,6 +12,8 @@ #include "ProxyCaster.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -32,3 +34,5 @@ private: }; } // namespace spells + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/AdventureSpellMechanics.cpp b/lib/spells/AdventureSpellMechanics.cpp index b428db9e3..2d00da72b 100644 --- a/lib/spells/AdventureSpellMechanics.cpp +++ b/lib/spells/AdventureSpellMechanics.cpp @@ -21,6 +21,8 @@ #include "../mapping/CMap.h" #include "../CPlayerState.h" +VCMI_LIB_NAMESPACE_BEGIN + ///AdventureSpellMechanics AdventureSpellMechanics::AdventureSpellMechanics(const CSpell * s): IAdventureSpellMechanics(s) @@ -612,3 +614,5 @@ bool ViewEarthMechanics::filterObject(const CGObjectInstance * obj, const int32_ return (obj->ID == Obj::RESOURCE) || (spellLevel > 1 && obj->ID == Obj::MINE); } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/AdventureSpellMechanics.h b/lib/spells/AdventureSpellMechanics.h index f8860f8b6..9b6a5cf63 100644 --- a/lib/spells/AdventureSpellMechanics.h +++ b/lib/spells/AdventureSpellMechanics.h @@ -12,6 +12,8 @@ #include "ISpellMechanics.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGTownInstance; enum class ESpellCastResult @@ -99,3 +101,5 @@ protected: }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/BattleSpellMechanics.cpp b/lib/spells/BattleSpellMechanics.cpp index 3ab3fd991..135c9eee2 100644 --- a/lib/spells/BattleSpellMechanics.cpp +++ b/lib/spells/BattleSpellMechanics.cpp @@ -20,6 +20,8 @@ #include "../CStack.h" #include "../NetPacks.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -674,3 +676,5 @@ const Spell * BattleSpellMechanics::getSpell() const } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/BattleSpellMechanics.h b/lib/spells/BattleSpellMechanics.h index d4a792412..3742f1b23 100644 --- a/lib/spells/BattleSpellMechanics.h +++ b/lib/spells/BattleSpellMechanics.h @@ -14,6 +14,8 @@ #include "effects/Effects.h" +VCMI_LIB_NAMESPACE_BEGIN + struct BattleSpellCast; namespace spells @@ -69,3 +71,5 @@ private: } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/BonusCaster.cpp b/lib/spells/BonusCaster.cpp index e6f2a8959..09cafa4bd 100644 --- a/lib/spells/BonusCaster.cpp +++ b/lib/spells/BonusCaster.cpp @@ -17,6 +17,8 @@ #include "../HeroBonus.h" #include "../battle/Unit.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -57,3 +59,5 @@ void BonusCaster::spendMana(ServerCallback * server, const int spellCost) const } // namespace spells + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/BonusCaster.h b/lib/spells/BonusCaster.h index c102c662b..12f888b77 100644 --- a/lib/spells/BonusCaster.h +++ b/lib/spells/BonusCaster.h @@ -12,6 +12,8 @@ #include "ProxyCaster.h" +VCMI_LIB_NAMESPACE_BEGIN + struct Bonus; namespace spells @@ -34,3 +36,5 @@ private: } // namespace spells + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/CSpellHandler.cpp b/lib/spells/CSpellHandler.cpp index aca31549c..6595ab950 100644 --- a/lib/spells/CSpellHandler.cpp +++ b/lib/spells/CSpellHandler.cpp @@ -32,6 +32,8 @@ #include "ISpellMechanics.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace SpellConfig { static const std::string LEVEL_NAMES[] = {"none", "basic", "advanced", "expert"}; @@ -1017,4 +1019,6 @@ std::vector CSpellHandler::getDefaultAllowed() const } return allowedSpells; -} \ No newline at end of file +} + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/CSpellHandler.h b/lib/spells/CSpellHandler.h index f821abc46..53345fcfe 100644 --- a/lib/spells/CSpellHandler.h +++ b/lib/spells/CSpellHandler.h @@ -21,6 +21,8 @@ #include "../battle/BattleHex.h" #include "../HeroBonus.h" +VCMI_LIB_NAMESPACE_BEGIN + class CSpell; class IAdventureSpellMechanics; class CBattleInfoCallback; @@ -391,3 +393,5 @@ protected: const std::vector & getTypeNames() const override; CSpell * loadFromJson(const std::string & scope, const JsonNode & json, const std::string & identifier, size_t index) override; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/ISpellMechanics.cpp b/lib/spells/ISpellMechanics.cpp index 29578ff56..1a14e0d53 100644 --- a/lib/spells/ISpellMechanics.cpp +++ b/lib/spells/ISpellMechanics.cpp @@ -42,6 +42,8 @@ #include "../IGameCallback.h"//todo: remove #include "../BattleFieldHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -776,3 +778,5 @@ std::unique_ptr IAdventureSpellMechanics::createMechan return std::unique_ptr(); } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/ISpellMechanics.h b/lib/spells/ISpellMechanics.h index 927a5a308..6206da9ba 100644 --- a/lib/spells/ISpellMechanics.h +++ b/lib/spells/ISpellMechanics.h @@ -18,6 +18,8 @@ #include "../GameConstants.h" #include "../HeroBonus.h" +VCMI_LIB_NAMESPACE_BEGIN + struct Query; class IBattleState; class CRandomGenerator; @@ -362,3 +364,5 @@ public: protected: const CSpell * owner; }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/Problem.cpp b/lib/spells/Problem.cpp index 6e8c76766..7d17d0bbc 100644 --- a/lib/spells/Problem.cpp +++ b/lib/spells/Problem.cpp @@ -11,6 +11,8 @@ #include "Problem.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace detail @@ -52,3 +54,5 @@ void ProblemImpl::getAll(std::vector & target) const } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/Problem.h b/lib/spells/Problem.h index b5432d98f..c3d5e247d 100644 --- a/lib/spells/Problem.h +++ b/lib/spells/Problem.h @@ -14,6 +14,8 @@ #include "../NetPacksBase.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace detail @@ -36,3 +38,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/ProxyCaster.cpp b/lib/spells/ProxyCaster.cpp index 1ae601b62..e93afe58c 100644 --- a/lib/spells/ProxyCaster.cpp +++ b/lib/spells/ProxyCaster.cpp @@ -13,6 +13,8 @@ #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -85,3 +87,5 @@ void ProxyCaster::spendMana(ServerCallback * server, const int32_t spellCost) co } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/ProxyCaster.h b/lib/spells/ProxyCaster.h index f3656e880..b3829da7f 100644 --- a/lib/spells/ProxyCaster.h +++ b/lib/spells/ProxyCaster.h @@ -12,6 +12,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -39,3 +41,5 @@ private: }; } // namespace spells + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/TargetCondition.cpp b/lib/spells/TargetCondition.cpp index cb4ddc976..cdcc2086e 100644 --- a/lib/spells/TargetCondition.cpp +++ b/lib/spells/TargetCondition.cpp @@ -20,6 +20,8 @@ #include "../VCMI_Lib.h" #include "../CModHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -512,3 +514,5 @@ void TargetCondition::loadConditions(const JsonNode & source, bool exclusive, bo } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/TargetCondition.h b/lib/spells/TargetCondition.h index c5ab39b9e..36dd413ae 100644 --- a/lib/spells/TargetCondition.h +++ b/lib/spells/TargetCondition.h @@ -12,6 +12,8 @@ #include "ISpellMechanics.h" +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; class JsonSerializeFormat; @@ -83,3 +85,5 @@ private: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/ViewSpellInt.cpp b/lib/spells/ViewSpellInt.cpp index 950da1447..7d436f284 100644 --- a/lib/spells/ViewSpellInt.cpp +++ b/lib/spells/ViewSpellInt.cpp @@ -14,6 +14,8 @@ #include "../mapObjects/CObjectHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + ObjectPosInfo::ObjectPosInfo(): pos(), id(Obj::NO_OBJ), subId(-1), owner(PlayerColor::CANNOT_DETERMINE) { @@ -25,3 +27,5 @@ ObjectPosInfo::ObjectPosInfo(const CGObjectInstance * obj): { } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/ViewSpellInt.h b/lib/spells/ViewSpellInt.h index 67efe94c6..d570967bf 100644 --- a/lib/spells/ViewSpellInt.h +++ b/lib/spells/ViewSpellInt.h @@ -13,6 +13,8 @@ #include "../int3.h" #include "../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; struct DLL_LINKAGE ObjectPosInfo @@ -33,3 +35,5 @@ } }; + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Catapult.cpp b/lib/spells/effects/Catapult.cpp index f1ed4051f..660be493e 100644 --- a/lib/spells/effects/Catapult.cpp +++ b/lib/spells/effects/Catapult.cpp @@ -21,6 +21,8 @@ #include "../../mapObjects/CGTownInstance.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:catapult"; namespace spells @@ -152,3 +154,5 @@ void Catapult::serializeJsonEffect(JsonSerializeFormat & handler) } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Catapult.h b/lib/spells/effects/Catapult.h index 762cd49d6..d03ef8e35 100644 --- a/lib/spells/effects/Catapult.h +++ b/lib/spells/effects/Catapult.h @@ -12,6 +12,8 @@ #include "LocationEffect.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -34,3 +36,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Clone.cpp b/lib/spells/effects/Clone.cpp index 97e9e7ebd..58c7e2b11 100644 --- a/lib/spells/effects/Clone.cpp +++ b/lib/spells/effects/Clone.cpp @@ -17,6 +17,8 @@ #include "../../battle/CUnitState.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:clone"; namespace spells @@ -137,3 +139,5 @@ void Clone::serializeJsonUnitEffect(JsonSerializeFormat & handler) } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Clone.h b/lib/spells/effects/Clone.h index 8047a0e51..824551f6e 100644 --- a/lib/spells/effects/Clone.h +++ b/lib/spells/effects/Clone.h @@ -12,6 +12,8 @@ #include "UnitEffect.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -35,3 +37,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Damage.cpp b/lib/spells/effects/Damage.cpp index 2db14bf46..88b0d1848 100644 --- a/lib/spells/effects/Damage.cpp +++ b/lib/spells/effects/Damage.cpp @@ -20,6 +20,8 @@ #include "../../CGeneralTextHandler.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:damage"; namespace spells @@ -225,3 +227,5 @@ void Damage::describeEffect(std::vector & log, const Mechanics * m, } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Damage.h b/lib/spells/effects/Damage.h index 27e6bb5af..699d5005d 100644 --- a/lib/spells/effects/Damage.h +++ b/lib/spells/effects/Damage.h @@ -12,6 +12,8 @@ #include "UnitEffect.h" +VCMI_LIB_NAMESPACE_BEGIN + struct StacksInjured; namespace spells @@ -44,3 +46,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Dispel.cpp b/lib/spells/effects/Dispel.cpp index 06d41dfba..ffe6bb454 100644 --- a/lib/spells/effects/Dispel.cpp +++ b/lib/spells/effects/Dispel.cpp @@ -21,6 +21,8 @@ #include "../../battle/Unit.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:dispel"; namespace spells @@ -142,3 +144,5 @@ std::shared_ptr Dispel::getBonuses(const Mechanics * m, const b } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Dispel.h b/lib/spells/effects/Dispel.h index bebb1200a..54667f25f 100644 --- a/lib/spells/effects/Dispel.h +++ b/lib/spells/effects/Dispel.h @@ -12,6 +12,8 @@ #include "UnitEffect.h" +VCMI_LIB_NAMESPACE_BEGIN + struct Bonus; class CSelector; class BonusList; @@ -44,3 +46,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Effect.cpp b/lib/spells/effects/Effect.cpp index 77f240f51..cb0462f6a 100644 --- a/lib/spells/effects/Effect.cpp +++ b/lib/spells/effects/Effect.cpp @@ -14,6 +14,8 @@ #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -64,3 +66,5 @@ std::shared_ptr Effect::create(const Registry * registry, const std::str } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Effect.h b/lib/spells/effects/Effect.h index 8ebf0f332..a8f6ec387 100644 --- a/lib/spells/effects/Effect.h +++ b/lib/spells/effects/Effect.h @@ -12,6 +12,8 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + struct BattleHex; class CBattleInfoCallback; class JsonSerializeFormat; @@ -28,7 +30,7 @@ using EffectTarget = Target; namespace effects { -using RNG = ::vstd::RNG; +using RNG = vstd::RNG; class Effects; class Effect; class Registry; @@ -36,7 +38,7 @@ class Registry; template class RegisterEffect; -using TargetType = ::spells::AimType; +using TargetType = spells::AimType; class DLL_LINKAGE Effect { @@ -72,3 +74,5 @@ protected: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Effects.cpp b/lib/spells/effects/Effects.cpp index 4a300d49b..f953ab0a7 100644 --- a/lib/spells/effects/Effects.cpp +++ b/lib/spells/effects/Effects.cpp @@ -17,6 +17,8 @@ #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -156,3 +158,5 @@ void Effects::serializeJson(const Registry * registry, JsonSerializeFormat & han } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Effects.h b/lib/spells/effects/Effects.h index f9bc264df..7dc7f4e21 100644 --- a/lib/spells/effects/Effects.h +++ b/lib/spells/effects/Effects.h @@ -13,6 +13,8 @@ #include "Effect.h" #include "../../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -46,3 +48,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/EffectsFwd.h b/lib/spells/effects/EffectsFwd.h index d9db3e64f..b7c2bf9e9 100644 --- a/lib/spells/effects/EffectsFwd.h +++ b/lib/spells/effects/EffectsFwd.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -21,3 +23,5 @@ class Effects; } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Heal.cpp b/lib/spells/effects/Heal.cpp index 4d07e15dd..b192315b8 100644 --- a/lib/spells/effects/Heal.cpp +++ b/lib/spells/effects/Heal.cpp @@ -19,6 +19,8 @@ #include "../../battle/Unit.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:heal"; @@ -137,3 +139,5 @@ void Heal::prepareHealEffect(int64_t value, BattleUnitsChanged & pack, RNG & rng } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Heal.h b/lib/spells/effects/Heal.h index 0160be35f..138935626 100644 --- a/lib/spells/effects/Heal.h +++ b/lib/spells/effects/Heal.h @@ -13,6 +13,8 @@ #include "UnitEffect.h" #include "../../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + struct BattleUnitsChanged; namespace spells @@ -45,3 +47,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/LocationEffect.cpp b/lib/spells/effects/LocationEffect.cpp index e66d80e63..5bd88dd74 100644 --- a/lib/spells/effects/LocationEffect.cpp +++ b/lib/spells/effects/LocationEffect.cpp @@ -12,6 +12,8 @@ #include "LocationEffect.h" #include "../ISpellMechanics.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -53,3 +55,5 @@ EffectTarget LocationEffect::transformTarget(const Mechanics * m, const Target & } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/LocationEffect.h b/lib/spells/effects/LocationEffect.h index d51c9568d..b13a375c7 100644 --- a/lib/spells/effects/LocationEffect.h +++ b/lib/spells/effects/LocationEffect.h @@ -12,6 +12,8 @@ #include "Effect.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { @@ -38,3 +40,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Obstacle.cpp b/lib/spells/effects/Obstacle.cpp index 99b4a7f5b..5f8cbcc3e 100644 --- a/lib/spells/effects/Obstacle.cpp +++ b/lib/spells/effects/Obstacle.cpp @@ -19,6 +19,8 @@ #include "../../battle/CBattleInfoCallback.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:obstacle"; namespace spells @@ -340,3 +342,5 @@ void Obstacle::placeObstacles(ServerCallback * server, const Mechanics * m, cons } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Obstacle.h b/lib/spells/effects/Obstacle.h index bea14ee1c..5cc1fd215 100644 --- a/lib/spells/effects/Obstacle.h +++ b/lib/spells/effects/Obstacle.h @@ -14,6 +14,8 @@ #include "../../battle/BattleHex.h" #include "../../battle/CObstacleInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -77,3 +79,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Registry.cpp b/lib/spells/effects/Registry.cpp index 5d12c2283..09cecd826 100644 --- a/lib/spells/effects/Registry.cpp +++ b/lib/spells/effects/Registry.cpp @@ -11,6 +11,8 @@ #include "Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -56,3 +58,5 @@ Registry * GlobalRegistry::get() } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Registry.h b/lib/spells/effects/Registry.h index 8e0eeac17..2f4ae202b 100644 --- a/lib/spells/effects/Registry.h +++ b/lib/spells/effects/Registry.h @@ -19,6 +19,8 @@ RegisterEffect register ## Type(Name);\ }\ \ +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -78,3 +80,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/RemoveObstacle.cpp b/lib/spells/effects/RemoveObstacle.cpp index 7e12568ba..1953668d3 100644 --- a/lib/spells/effects/RemoveObstacle.cpp +++ b/lib/spells/effects/RemoveObstacle.cpp @@ -20,6 +20,8 @@ #include "../../battle/CObstacleInstance.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:removeObstacle"; namespace spells @@ -112,3 +114,5 @@ std::set RemoveObstacle::getTargets(const Mechanics * } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/RemoveObstacle.h b/lib/spells/effects/RemoveObstacle.h index bdbc2dd31..3e159c6b3 100644 --- a/lib/spells/effects/RemoveObstacle.h +++ b/lib/spells/effects/RemoveObstacle.h @@ -14,6 +14,8 @@ #include "../../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + struct CObstacleInstance; struct BattleObstaclesChanged; @@ -50,3 +52,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Sacrifice.cpp b/lib/spells/effects/Sacrifice.cpp index 52e60920d..5ec826006 100644 --- a/lib/spells/effects/Sacrifice.cpp +++ b/lib/spells/effects/Sacrifice.cpp @@ -19,6 +19,8 @@ #include "../../battle/Unit.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:sacrifice"; @@ -174,3 +176,5 @@ int64_t Sacrifice::calculateHealEffectValue(const Mechanics * m, const battle::U } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Sacrifice.h b/lib/spells/effects/Sacrifice.h index e89ef0c48..b449bbc7d 100644 --- a/lib/spells/effects/Sacrifice.h +++ b/lib/spells/effects/Sacrifice.h @@ -12,6 +12,8 @@ #include "Heal.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -41,3 +43,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Summon.cpp b/lib/spells/effects/Summon.cpp index 2601f7d52..83082b012 100644 --- a/lib/spells/effects/Summon.cpp +++ b/lib/spells/effects/Summon.cpp @@ -22,6 +22,8 @@ #include "../../CHeroHandler.h" #include "../../mapObjects/CGHeroInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:summon"; @@ -197,3 +199,5 @@ EffectTarget Summon::transformTarget(const Mechanics * m, const Target & aimPoin } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Summon.h b/lib/spells/effects/Summon.h index d12d5373b..97991c612 100644 --- a/lib/spells/effects/Summon.h +++ b/lib/spells/effects/Summon.h @@ -13,6 +13,8 @@ #include "Effect.h" #include "../../GameConstants.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -49,3 +51,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Teleport.cpp b/lib/spells/effects/Teleport.cpp index 5501a189e..6df50f0aa 100644 --- a/lib/spells/effects/Teleport.cpp +++ b/lib/spells/effects/Teleport.cpp @@ -17,6 +17,8 @@ #include "../../battle/CBattleInfoCallback.h" #include "../../battle/Unit.h" +VCMI_LIB_NAMESPACE_BEGIN + //TODO: Teleport effect static const std::string EFFECT_NAME = "core:teleport"; @@ -122,3 +124,5 @@ EffectTarget Teleport::transformTarget(const Mechanics * m, const Target & aimPo } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Teleport.h b/lib/spells/effects/Teleport.h index b547bf7f6..04707400e 100644 --- a/lib/spells/effects/Teleport.h +++ b/lib/spells/effects/Teleport.h @@ -12,6 +12,8 @@ #include "UnitEffect.h" +VCMI_LIB_NAMESPACE_BEGIN + struct BattleStackMoved; namespace spells @@ -39,3 +41,5 @@ protected: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Timed.cpp b/lib/spells/effects/Timed.cpp index 300fbedce..c9d6322f3 100644 --- a/lib/spells/effects/Timed.cpp +++ b/lib/spells/effects/Timed.cpp @@ -18,6 +18,8 @@ #include "../../battle/Unit.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + static const std::string EFFECT_NAME = "core:timed"; namespace spells @@ -276,3 +278,5 @@ void Timed::serializeJsonUnitEffect(JsonSerializeFormat & handler) } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/Timed.h b/lib/spells/effects/Timed.h index 34bbde91c..3867692f6 100644 --- a/lib/spells/effects/Timed.h +++ b/lib/spells/effects/Timed.h @@ -12,6 +12,8 @@ #include "UnitEffect.h" +VCMI_LIB_NAMESPACE_BEGIN + struct Bonus; struct SetStackEffect; struct MetaString; @@ -43,3 +45,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/UnitEffect.cpp b/lib/spells/effects/UnitEffect.cpp index 583d86b24..665842750 100644 --- a/lib/spells/effects/UnitEffect.cpp +++ b/lib/spells/effects/UnitEffect.cpp @@ -18,6 +18,8 @@ #include "../../battle/Unit.h" #include "../../serializer/JsonSerializeFormat.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -291,3 +293,5 @@ void UnitEffect::serializeJsonEffect(JsonSerializeFormat & handler) } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/spells/effects/UnitEffect.h b/lib/spells/effects/UnitEffect.h index 1b076c660..81456e2e6 100644 --- a/lib/spells/effects/UnitEffect.h +++ b/lib/spells/effects/UnitEffect.h @@ -12,6 +12,8 @@ #include "Effect.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -58,3 +60,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/vcmi_endian.h b/lib/vcmi_endian.h index 865be44be..45db01bfb 100644 --- a/lib/vcmi_endian.h +++ b/lib/vcmi_endian.h @@ -12,6 +12,8 @@ //FIXME:library file depends on SDL - make cause troubles #include +VCMI_LIB_NAMESPACE_BEGIN + /* Reading values from memory. * * read_le_u16, read_le_u32 : read a little endian value from @@ -68,3 +70,5 @@ static inline std::string readString(const ui8 * buffer, int & i) } return ret; } + +VCMI_LIB_NAMESPACE_END diff --git a/lib/vstd/StringUtils.cpp b/lib/vstd/StringUtils.cpp index e46779026..51499078c 100644 --- a/lib/vstd/StringUtils.cpp +++ b/lib/vstd/StringUtils.cpp @@ -1,6 +1,8 @@ #include "StdInc.h" #include +VCMI_LIB_NAMESPACE_BEGIN + namespace vstd { @@ -30,3 +32,5 @@ namespace vstd } } + +VCMI_LIB_NAMESPACE_END diff --git a/server/CGameHandler.cpp b/server/CGameHandler.cpp index 0604c48e8..9174f80a7 100644 --- a/server/CGameHandler.cpp +++ b/server/CGameHandler.cpp @@ -91,6 +91,7 @@ private: CGameHandler * gh; }; +VCMI_LIB_NAMESPACE_BEGIN namespace spells { @@ -185,6 +186,7 @@ private: }; }// +VCMI_LIB_NAMESPACE_END CondSh battleMadeAction(false); CondSh battleResult(nullptr); diff --git a/server/CGameHandler.h b/server/CGameHandler.h index 279fca93e..bcb69f2e8 100644 --- a/server/CGameHandler.h +++ b/server/CGameHandler.h @@ -18,8 +18,8 @@ #include "../lib/ScriptHandler.h" #include "CQuery.h" -class CGameHandler; -class CVCMIServer; +VCMI_LIB_NAMESPACE_BEGIN + class CGameState; struct StartInfo; struct BattleResult; @@ -43,6 +43,11 @@ namespace scripting template class CApplier; + +VCMI_LIB_NAMESPACE_END + +class CGameHandler; +class CVCMIServer; class CBaseForGHApply; struct PlayerStatus diff --git a/server/CQuery.h b/server/CQuery.h index 45f6c11f3..aa5446f3c 100644 --- a/server/CQuery.h +++ b/server/CQuery.h @@ -12,9 +12,14 @@ #include "../lib/int3.h" #include "../lib/NetPacks.h" +VCMI_LIB_NAMESPACE_BEGIN + class CGObjectInstance; class CGHeroInstance; class CArmedInstance; + +VCMI_LIB_NAMESPACE_END + class CGameHandler; class CObjectVisitQuery; class CQuery; diff --git a/server/CVCMIServer.h b/server/CVCMIServer.h index 7cd84eb46..1ec212581 100644 --- a/server/CVCMIServer.h +++ b/server/CVCMIServer.h @@ -14,10 +14,11 @@ #include +VCMI_LIB_NAMESPACE_BEGIN + class CMapInfo; struct CPackForLobby; -class CGameHandler; struct SharedMemory; struct StartInfo; @@ -26,6 +27,10 @@ struct PlayerSettings; class PlayerColor; template class CApplier; + +VCMI_LIB_NAMESPACE_END + +class CGameHandler; class CBaseForServerApply; class CBaseForGHApply; diff --git a/server/StdInc.h b/server/StdInc.h index 9cc0f48e0..fbf8bbce5 100644 --- a/server/StdInc.h +++ b/server/StdInc.h @@ -18,3 +18,4 @@ #include #include +VCMI_LIB_USING_NAMESPACE From 267e8df7db3131c0ae27d1894b36c1c383a6425e Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 27 Jul 2022 11:53:53 +0300 Subject: [PATCH 068/131] move lib/CMakeLists.txt to cmake_modules/VCMI_lib.cmake preparation to be able to duplicate the lib target --- lib/CMakeLists.txt => cmake_modules/VCMI_lib.cmake | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename lib/CMakeLists.txt => cmake_modules/VCMI_lib.cmake (100%) diff --git a/lib/CMakeLists.txt b/cmake_modules/VCMI_lib.cmake similarity index 100% rename from lib/CMakeLists.txt rename to cmake_modules/VCMI_lib.cmake From 2d3002bc1dda224058170bf22835bbeee81103af Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 27 Jul 2022 12:12:57 +0300 Subject: [PATCH 069/131] add standard lib target back - the moved CMakeLists.txt is turned into a macro (adds whitespace difference) - now uses absolute paths to the lib and include dirs - refactors iOS install section to use "early continue" in the foreach loop --- cmake_modules/VCMI_lib.cmake | 941 ++++++++++++++++++----------------- lib/CMakeLists.txt | 1 + 2 files changed, 475 insertions(+), 467 deletions(-) create mode 100644 lib/CMakeLists.txt diff --git a/cmake_modules/VCMI_lib.cmake b/cmake_modules/VCMI_lib.cmake index 62da10ae9..09a28fbbd 100644 --- a/cmake_modules/VCMI_lib.cmake +++ b/cmake_modules/VCMI_lib.cmake @@ -1,515 +1,522 @@ -set(lib_SRCS - StdInc.cpp +macro(add_main_lib TARGET_NAME LIBRARY_TYPE) + set(MAIN_LIB_DIR "${CMAKE_SOURCE_DIR}/lib") + set(lib_SRCS + ${MAIN_LIB_DIR}/StdInc.cpp ${CMAKE_BINARY_DIR}/Version.cpp - battle/AccessibilityInfo.cpp - battle/BattleAction.cpp - battle/BattleAttackInfo.cpp - battle/BattleHex.cpp - battle/BattleInfo.cpp - battle/BattleProxy.cpp - battle/CBattleInfoCallback.cpp - battle/CBattleInfoEssentials.cpp - battle/CCallbackBase.cpp - battle/CObstacleInstance.cpp - battle/CPlayerBattleCallback.cpp - battle/CUnitState.cpp - battle/Destination.cpp - battle/IBattleState.cpp - battle/ReachabilityInfo.cpp - battle/SideInBattle.cpp - battle/SiegeInfo.cpp - battle/Unit.cpp + ${MAIN_LIB_DIR}/battle/AccessibilityInfo.cpp + ${MAIN_LIB_DIR}/battle/BattleAction.cpp + ${MAIN_LIB_DIR}/battle/BattleAttackInfo.cpp + ${MAIN_LIB_DIR}/battle/BattleHex.cpp + ${MAIN_LIB_DIR}/battle/BattleInfo.cpp + ${MAIN_LIB_DIR}/battle/BattleProxy.cpp + ${MAIN_LIB_DIR}/battle/CBattleInfoCallback.cpp + ${MAIN_LIB_DIR}/battle/CBattleInfoEssentials.cpp + ${MAIN_LIB_DIR}/battle/CCallbackBase.cpp + ${MAIN_LIB_DIR}/battle/CObstacleInstance.cpp + ${MAIN_LIB_DIR}/battle/CPlayerBattleCallback.cpp + ${MAIN_LIB_DIR}/battle/CUnitState.cpp + ${MAIN_LIB_DIR}/battle/Destination.cpp + ${MAIN_LIB_DIR}/battle/IBattleState.cpp + ${MAIN_LIB_DIR}/battle/ReachabilityInfo.cpp + ${MAIN_LIB_DIR}/battle/SideInBattle.cpp + ${MAIN_LIB_DIR}/battle/SiegeInfo.cpp + ${MAIN_LIB_DIR}/battle/Unit.cpp - events/ApplyDamage.cpp - events/GameResumed.cpp - events/ObjectVisitEnded.cpp - events/ObjectVisitStarted.cpp - events/PlayerGotTurn.cpp - events/TurnStarted.cpp + ${MAIN_LIB_DIR}/events/ApplyDamage.cpp + ${MAIN_LIB_DIR}/events/GameResumed.cpp + ${MAIN_LIB_DIR}/events/ObjectVisitEnded.cpp + ${MAIN_LIB_DIR}/events/ObjectVisitStarted.cpp + ${MAIN_LIB_DIR}/events/PlayerGotTurn.cpp + ${MAIN_LIB_DIR}/events/TurnStarted.cpp - filesystem/AdapterLoaders.cpp - filesystem/CArchiveLoader.cpp - filesystem/CBinaryReader.cpp - filesystem/CCompressedStream.cpp - filesystem/CFileInputStream.cpp - filesystem/CFilesystemLoader.cpp - filesystem/CMemoryBuffer.cpp - filesystem/CMemoryStream.cpp - filesystem/CZipLoader.cpp - filesystem/CZipSaver.cpp - filesystem/FileInfo.cpp - filesystem/FileStream.cpp - filesystem/Filesystem.cpp - filesystem/MinizipExtensions.cpp - filesystem/ResourceID.cpp + ${MAIN_LIB_DIR}/filesystem/AdapterLoaders.cpp + ${MAIN_LIB_DIR}/filesystem/CArchiveLoader.cpp + ${MAIN_LIB_DIR}/filesystem/CBinaryReader.cpp + ${MAIN_LIB_DIR}/filesystem/CCompressedStream.cpp + ${MAIN_LIB_DIR}/filesystem/CFileInputStream.cpp + ${MAIN_LIB_DIR}/filesystem/CFilesystemLoader.cpp + ${MAIN_LIB_DIR}/filesystem/CMemoryBuffer.cpp + ${MAIN_LIB_DIR}/filesystem/CMemoryStream.cpp + ${MAIN_LIB_DIR}/filesystem/CZipLoader.cpp + ${MAIN_LIB_DIR}/filesystem/CZipSaver.cpp + ${MAIN_LIB_DIR}/filesystem/FileInfo.cpp + ${MAIN_LIB_DIR}/filesystem/FileStream.cpp + ${MAIN_LIB_DIR}/filesystem/Filesystem.cpp + ${MAIN_LIB_DIR}/filesystem/MinizipExtensions.cpp + ${MAIN_LIB_DIR}/filesystem/ResourceID.cpp - logging/CBasicLogConfigurator.cpp - logging/CLogger.cpp + ${MAIN_LIB_DIR}/logging/CBasicLogConfigurator.cpp + ${MAIN_LIB_DIR}/logging/CLogger.cpp - mapObjects/CArmedInstance.cpp - mapObjects/CBank.cpp - mapObjects/CGHeroInstance.cpp - mapObjects/CGMarket.cpp - mapObjects/CGPandoraBox.cpp - mapObjects/CGTownInstance.cpp - mapObjects/CObjectClassesHandler.cpp - mapObjects/CObjectHandler.cpp - mapObjects/CommonConstructors.cpp - mapObjects/CQuest.cpp - mapObjects/CRewardableConstructor.cpp - mapObjects/CRewardableObject.cpp - mapObjects/JsonRandom.cpp - mapObjects/MiscObjects.cpp - mapObjects/ObjectTemplate.cpp + ${MAIN_LIB_DIR}/mapObjects/CArmedInstance.cpp + ${MAIN_LIB_DIR}/mapObjects/CBank.cpp + ${MAIN_LIB_DIR}/mapObjects/CGHeroInstance.cpp + ${MAIN_LIB_DIR}/mapObjects/CGMarket.cpp + ${MAIN_LIB_DIR}/mapObjects/CGPandoraBox.cpp + ${MAIN_LIB_DIR}/mapObjects/CGTownInstance.cpp + ${MAIN_LIB_DIR}/mapObjects/CObjectClassesHandler.cpp + ${MAIN_LIB_DIR}/mapObjects/CObjectHandler.cpp + ${MAIN_LIB_DIR}/mapObjects/CommonConstructors.cpp + ${MAIN_LIB_DIR}/mapObjects/CQuest.cpp + ${MAIN_LIB_DIR}/mapObjects/CRewardableConstructor.cpp + ${MAIN_LIB_DIR}/mapObjects/CRewardableObject.cpp + ${MAIN_LIB_DIR}/mapObjects/JsonRandom.cpp + ${MAIN_LIB_DIR}/mapObjects/MiscObjects.cpp + ${MAIN_LIB_DIR}/mapObjects/ObjectTemplate.cpp - mapping/CCampaignHandler.cpp - mapping/CDrawRoadsOperation.cpp - mapping/CMap.cpp - mapping/CMapEditManager.cpp - mapping/CMapInfo.cpp - mapping/CMapOperation.cpp - mapping/CMapService.cpp - mapping/MapEditUtils.cpp - mapping/MapFormatH3M.cpp - mapping/MapFormatJson.cpp + ${MAIN_LIB_DIR}/mapping/CCampaignHandler.cpp + ${MAIN_LIB_DIR}/mapping/CDrawRoadsOperation.cpp + ${MAIN_LIB_DIR}/mapping/CMap.cpp + ${MAIN_LIB_DIR}/mapping/CMapEditManager.cpp + ${MAIN_LIB_DIR}/mapping/CMapInfo.cpp + ${MAIN_LIB_DIR}/mapping/CMapOperation.cpp + ${MAIN_LIB_DIR}/mapping/CMapService.cpp + ${MAIN_LIB_DIR}/mapping/MapEditUtils.cpp + ${MAIN_LIB_DIR}/mapping/MapFormatH3M.cpp + ${MAIN_LIB_DIR}/mapping/MapFormatJson.cpp - registerTypes/RegisterTypes.cpp - registerTypes/TypesClientPacks1.cpp - registerTypes/TypesClientPacks2.cpp - registerTypes/TypesMapObjects1.cpp - registerTypes/TypesMapObjects2.cpp - registerTypes/TypesMapObjects3.cpp - registerTypes/TypesLobbyPacks.cpp - registerTypes/TypesServerPacks.cpp + ${MAIN_LIB_DIR}/registerTypes/RegisterTypes.cpp + ${MAIN_LIB_DIR}/registerTypes/TypesClientPacks1.cpp + ${MAIN_LIB_DIR}/registerTypes/TypesClientPacks2.cpp + ${MAIN_LIB_DIR}/registerTypes/TypesMapObjects1.cpp + ${MAIN_LIB_DIR}/registerTypes/TypesMapObjects2.cpp + ${MAIN_LIB_DIR}/registerTypes/TypesMapObjects3.cpp + ${MAIN_LIB_DIR}/registerTypes/TypesLobbyPacks.cpp + ${MAIN_LIB_DIR}/registerTypes/TypesServerPacks.cpp - rmg/RmgArea.cpp - rmg/RmgObject.cpp - rmg/RmgPath.cpp - rmg/CMapGenerator.cpp - rmg/CMapGenOptions.cpp - rmg/CRmgTemplate.cpp - rmg/CRmgTemplateStorage.cpp - rmg/CZonePlacer.cpp - rmg/TileInfo.cpp - rmg/Zone.cpp - rmg/Functions.cpp - rmg/ObjectManager.cpp - rmg/RoadPlacer.cpp - rmg/TreasurePlacer.cpp - rmg/RmgMap.cpp - rmg/ConnectionsPlacer.cpp - rmg/WaterAdopter.cpp - rmg/TownPlacer.cpp - rmg/WaterProxy.cpp - rmg/WaterRoutes.cpp - rmg/RockPlacer.cpp - rmg/ObstaclePlacer.cpp - rmg/RiverPlacer.cpp - rmg/TerrainPainter.cpp + ${MAIN_LIB_DIR}/rmg/RmgArea.cpp + ${MAIN_LIB_DIR}/rmg/RmgObject.cpp + ${MAIN_LIB_DIR}/rmg/RmgPath.cpp + ${MAIN_LIB_DIR}/rmg/CMapGenerator.cpp + ${MAIN_LIB_DIR}/rmg/CMapGenOptions.cpp + ${MAIN_LIB_DIR}/rmg/CRmgTemplate.cpp + ${MAIN_LIB_DIR}/rmg/CRmgTemplateStorage.cpp + ${MAIN_LIB_DIR}/rmg/CZonePlacer.cpp + ${MAIN_LIB_DIR}/rmg/TileInfo.cpp + ${MAIN_LIB_DIR}/rmg/Zone.cpp + ${MAIN_LIB_DIR}/rmg/Functions.cpp + ${MAIN_LIB_DIR}/rmg/ObjectManager.cpp + ${MAIN_LIB_DIR}/rmg/RoadPlacer.cpp + ${MAIN_LIB_DIR}/rmg/TreasurePlacer.cpp + ${MAIN_LIB_DIR}/rmg/RmgMap.cpp + ${MAIN_LIB_DIR}/rmg/ConnectionsPlacer.cpp + ${MAIN_LIB_DIR}/rmg/WaterAdopter.cpp + ${MAIN_LIB_DIR}/rmg/TownPlacer.cpp + ${MAIN_LIB_DIR}/rmg/WaterProxy.cpp + ${MAIN_LIB_DIR}/rmg/WaterRoutes.cpp + ${MAIN_LIB_DIR}/rmg/RockPlacer.cpp + ${MAIN_LIB_DIR}/rmg/ObstaclePlacer.cpp + ${MAIN_LIB_DIR}/rmg/RiverPlacer.cpp + ${MAIN_LIB_DIR}/rmg/TerrainPainter.cpp - serializer/BinaryDeserializer.cpp - serializer/BinarySerializer.cpp - serializer/CLoadIntegrityValidator.cpp - serializer/CMemorySerializer.cpp - serializer/Connection.cpp - serializer/CSerializer.cpp - serializer/CTypeList.cpp - serializer/JsonDeserializer.cpp - serializer/JsonSerializeFormat.cpp - serializer/JsonSerializer.cpp - serializer/JsonUpdater.cpp + ${MAIN_LIB_DIR}/serializer/BinaryDeserializer.cpp + ${MAIN_LIB_DIR}/serializer/BinarySerializer.cpp + ${MAIN_LIB_DIR}/serializer/CLoadIntegrityValidator.cpp + ${MAIN_LIB_DIR}/serializer/CMemorySerializer.cpp + ${MAIN_LIB_DIR}/serializer/Connection.cpp + ${MAIN_LIB_DIR}/serializer/CSerializer.cpp + ${MAIN_LIB_DIR}/serializer/CTypeList.cpp + ${MAIN_LIB_DIR}/serializer/JsonDeserializer.cpp + ${MAIN_LIB_DIR}/serializer/JsonSerializeFormat.cpp + ${MAIN_LIB_DIR}/serializer/JsonSerializer.cpp + ${MAIN_LIB_DIR}/serializer/JsonUpdater.cpp - spells/AbilityCaster.cpp - spells/AdventureSpellMechanics.cpp - spells/BattleSpellMechanics.cpp - spells/BonusCaster.cpp - spells/CSpellHandler.cpp - spells/ISpellMechanics.cpp - spells/Problem.cpp - spells/ProxyCaster.cpp - spells/TargetCondition.cpp - spells/ViewSpellInt.cpp + ${MAIN_LIB_DIR}/spells/AbilityCaster.cpp + ${MAIN_LIB_DIR}/spells/AdventureSpellMechanics.cpp + ${MAIN_LIB_DIR}/spells/BattleSpellMechanics.cpp + ${MAIN_LIB_DIR}/spells/BonusCaster.cpp + ${MAIN_LIB_DIR}/spells/CSpellHandler.cpp + ${MAIN_LIB_DIR}/spells/ISpellMechanics.cpp + ${MAIN_LIB_DIR}/spells/Problem.cpp + ${MAIN_LIB_DIR}/spells/ProxyCaster.cpp + ${MAIN_LIB_DIR}/spells/TargetCondition.cpp + ${MAIN_LIB_DIR}/spells/ViewSpellInt.cpp - spells/effects/Catapult.cpp - spells/effects/Clone.cpp - spells/effects/Damage.cpp - spells/effects/Dispel.cpp - spells/effects/Effect.cpp - spells/effects/Effects.cpp - spells/effects/Heal.cpp - spells/effects/LocationEffect.cpp - spells/effects/Obstacle.cpp - spells/effects/Registry.cpp - spells/effects/UnitEffect.cpp - spells/effects/Summon.cpp - spells/effects/Teleport.cpp - spells/effects/Timed.cpp - spells/effects/RemoveObstacle.cpp - spells/effects/Sacrifice.cpp + ${MAIN_LIB_DIR}/spells/effects/Catapult.cpp + ${MAIN_LIB_DIR}/spells/effects/Clone.cpp + ${MAIN_LIB_DIR}/spells/effects/Damage.cpp + ${MAIN_LIB_DIR}/spells/effects/Dispel.cpp + ${MAIN_LIB_DIR}/spells/effects/Effect.cpp + ${MAIN_LIB_DIR}/spells/effects/Effects.cpp + ${MAIN_LIB_DIR}/spells/effects/Heal.cpp + ${MAIN_LIB_DIR}/spells/effects/LocationEffect.cpp + ${MAIN_LIB_DIR}/spells/effects/Obstacle.cpp + ${MAIN_LIB_DIR}/spells/effects/Registry.cpp + ${MAIN_LIB_DIR}/spells/effects/UnitEffect.cpp + ${MAIN_LIB_DIR}/spells/effects/Summon.cpp + ${MAIN_LIB_DIR}/spells/effects/Teleport.cpp + ${MAIN_LIB_DIR}/spells/effects/Timed.cpp + ${MAIN_LIB_DIR}/spells/effects/RemoveObstacle.cpp + ${MAIN_LIB_DIR}/spells/effects/Sacrifice.cpp - vstd/StringUtils.cpp - - BattleFieldHandler.cpp - CAndroidVMHelper.cpp - CArtHandler.cpp - CBonusTypeHandler.cpp - CBuildingHandler.cpp - CConfigHandler.cpp - CConsoleHandler.cpp - CCreatureHandler.cpp - CCreatureSet.cpp - CGameInfoCallback.cpp - CGameInterface.cpp - CGameState.cpp - CGeneralTextHandler.cpp - CHeroHandler.cpp - CModHandler.cpp - CPathfinder.cpp - CPlayerState.cpp - CRandomGenerator.cpp - CScriptingModule.cpp - CSkillHandler.cpp - CStack.cpp - CThreadHelper.cpp - CTownHandler.cpp - GameConstants.cpp - HeroBonus.cpp - IGameCallback.cpp - IHandlerBase.cpp - JsonDetail.cpp - JsonNode.cpp - LoadProgress.cpp - LogicalExpression.cpp - NetPacksLib.cpp - ObstacleHandler.cpp - StartInfo.cpp - ResourceSet.cpp - ScriptHandler.cpp - Terrain.cpp - VCMIDirs.cpp - VCMI_Lib.cpp + ${MAIN_LIB_DIR}/vstd/StringUtils.cpp + + ${MAIN_LIB_DIR}/BattleFieldHandler.cpp + ${MAIN_LIB_DIR}/CAndroidVMHelper.cpp + ${MAIN_LIB_DIR}/CArtHandler.cpp + ${MAIN_LIB_DIR}/CBonusTypeHandler.cpp + ${MAIN_LIB_DIR}/CBuildingHandler.cpp + ${MAIN_LIB_DIR}/CConfigHandler.cpp + ${MAIN_LIB_DIR}/CConsoleHandler.cpp + ${MAIN_LIB_DIR}/CCreatureHandler.cpp + ${MAIN_LIB_DIR}/CCreatureSet.cpp + ${MAIN_LIB_DIR}/CGameInfoCallback.cpp + ${MAIN_LIB_DIR}/CGameInterface.cpp + ${MAIN_LIB_DIR}/CGameState.cpp + ${MAIN_LIB_DIR}/CGeneralTextHandler.cpp + ${MAIN_LIB_DIR}/CHeroHandler.cpp + ${MAIN_LIB_DIR}/CModHandler.cpp + ${MAIN_LIB_DIR}/CPathfinder.cpp + ${MAIN_LIB_DIR}/CPlayerState.cpp + ${MAIN_LIB_DIR}/CRandomGenerator.cpp + ${MAIN_LIB_DIR}/CScriptingModule.cpp + ${MAIN_LIB_DIR}/CSkillHandler.cpp + ${MAIN_LIB_DIR}/CStack.cpp + ${MAIN_LIB_DIR}/CThreadHelper.cpp + ${MAIN_LIB_DIR}/CTownHandler.cpp + ${MAIN_LIB_DIR}/GameConstants.cpp + ${MAIN_LIB_DIR}/HeroBonus.cpp + ${MAIN_LIB_DIR}/IGameCallback.cpp + ${MAIN_LIB_DIR}/IHandlerBase.cpp + ${MAIN_LIB_DIR}/JsonDetail.cpp + ${MAIN_LIB_DIR}/JsonNode.cpp + ${MAIN_LIB_DIR}/LoadProgress.cpp + ${MAIN_LIB_DIR}/LogicalExpression.cpp + ${MAIN_LIB_DIR}/NetPacksLib.cpp + ${MAIN_LIB_DIR}/ObstacleHandler.cpp + ${MAIN_LIB_DIR}/StartInfo.cpp + ${MAIN_LIB_DIR}/ResourceSet.cpp + ${MAIN_LIB_DIR}/ScriptHandler.cpp + ${MAIN_LIB_DIR}/Terrain.cpp + ${MAIN_LIB_DIR}/VCMIDirs.cpp + ${MAIN_LIB_DIR}/VCMI_Lib.cpp ${VCMILIB_ADDITIONAL_SOURCES} -) + ) -# Version.cpp is a generated file -set_source_files_properties(${CMAKE_BINARY_DIR}/Version.cpp - PROPERTIES GENERATED TRUE -) + # Version.cpp is a generated file + set_source_files_properties(${CMAKE_BINARY_DIR}/Version.cpp + PROPERTIES GENERATED TRUE + ) -set(lib_HEADERS - ../include/vstd/CLoggerBase.h - ../Global.h - StdInc.h + set(lib_HEADERS + ${CMAKE_SOURCE_DIR}/include/vstd/CLoggerBase.h + ${CMAKE_SOURCE_DIR}/Global.h + ${MAIN_LIB_DIR}/StdInc.h - ../include/vstd/ContainerUtils.h - ../include/vstd/RNG.h - ../include/vstd/StringUtils.h + ${CMAKE_SOURCE_DIR}/include/vstd/ContainerUtils.h + ${CMAKE_SOURCE_DIR}/include/vstd/RNG.h + ${CMAKE_SOURCE_DIR}/include/vstd/StringUtils.h - ../include/vcmi/events/ApplyDamage.h - ../include/vcmi/events/Event.h - ../include/vcmi/events/EventBus.h - ../include/vcmi/events/SubscriptionRegistry.h + ${CMAKE_SOURCE_DIR}/include/vcmi/events/ApplyDamage.h + ${CMAKE_SOURCE_DIR}/include/vcmi/events/Event.h + ${CMAKE_SOURCE_DIR}/include/vcmi/events/EventBus.h + ${CMAKE_SOURCE_DIR}/include/vcmi/events/SubscriptionRegistry.h - ../include/vcmi/scripting/Service.h + ${CMAKE_SOURCE_DIR}/include/vcmi/scripting/Service.h - ../include/vcmi/spells/Caster.h - ../include/vcmi/spells/Magic.h - ../include/vcmi/spells/Service.h - ../include/vcmi/spells/Spell.h + ${CMAKE_SOURCE_DIR}/include/vcmi/spells/Caster.h + ${CMAKE_SOURCE_DIR}/include/vcmi/spells/Magic.h + ${CMAKE_SOURCE_DIR}/include/vcmi/spells/Service.h + ${CMAKE_SOURCE_DIR}/include/vcmi/spells/Spell.h - ../include/vcmi/Artifact.h - ../include/vcmi/ArtifactService.h - ../include/vcmi/Creature.h - ../include/vcmi/CreatureService.h - ../include/vcmi/Entity.h - ../include/vcmi/Environment.h - ../include/vcmi/Services.h + ${CMAKE_SOURCE_DIR}/include/vcmi/Artifact.h + ${CMAKE_SOURCE_DIR}/include/vcmi/ArtifactService.h + ${CMAKE_SOURCE_DIR}/include/vcmi/Creature.h + ${CMAKE_SOURCE_DIR}/include/vcmi/CreatureService.h + ${CMAKE_SOURCE_DIR}/include/vcmi/Entity.h + ${CMAKE_SOURCE_DIR}/include/vcmi/Environment.h + ${CMAKE_SOURCE_DIR}/include/vcmi/Services.h - abilities/Ability.h + ${MAIN_LIB_DIR}/abilities/Ability.h - battle/AccessibilityInfo.h - battle/BattleAction.h - battle/BattleAttackInfo.h - battle/BattleHex.h - battle/BattleInfo.h - battle/BattleProxy.h - battle/CBattleInfoCallback.h - battle/CBattleInfoEssentials.h - battle/CCallbackBase.h - battle/CObstacleInstance.h - battle/CPlayerBattleCallback.h - battle/CUnitState.h - battle/Destination.h - battle/IBattleInfoCallback.h - battle/IBattleState.h - battle/IUnitInfo.h - battle/ReachabilityInfo.h - battle/SideInBattle.h - battle/SiegeInfo.h - battle/Unit.h + ${MAIN_LIB_DIR}/battle/AccessibilityInfo.h + ${MAIN_LIB_DIR}/battle/BattleAction.h + ${MAIN_LIB_DIR}/battle/BattleAttackInfo.h + ${MAIN_LIB_DIR}/battle/BattleHex.h + ${MAIN_LIB_DIR}/battle/BattleInfo.h + ${MAIN_LIB_DIR}/battle/BattleProxy.h + ${MAIN_LIB_DIR}/battle/CBattleInfoCallback.h + ${MAIN_LIB_DIR}/battle/CBattleInfoEssentials.h + ${MAIN_LIB_DIR}/battle/CCallbackBase.h + ${MAIN_LIB_DIR}/battle/CObstacleInstance.h + ${MAIN_LIB_DIR}/battle/CPlayerBattleCallback.h + ${MAIN_LIB_DIR}/battle/CUnitState.h + ${MAIN_LIB_DIR}/battle/Destination.h + ${MAIN_LIB_DIR}/battle/IBattleInfoCallback.h + ${MAIN_LIB_DIR}/battle/IBattleState.h + ${MAIN_LIB_DIR}/battle/IUnitInfo.h + ${MAIN_LIB_DIR}/battle/ReachabilityInfo.h + ${MAIN_LIB_DIR}/battle/SideInBattle.h + ${MAIN_LIB_DIR}/battle/SiegeInfo.h + ${MAIN_LIB_DIR}/battle/Unit.h - events/ApplyDamage.h - events/GameResumed.h - events/ObjectVisitEnded.h - events/ObjectVisitStarted.h - events/PlayerGotTurn.h - events/TurnStarted.h + ${MAIN_LIB_DIR}/events/ApplyDamage.h + ${MAIN_LIB_DIR}/events/GameResumed.h + ${MAIN_LIB_DIR}/events/ObjectVisitEnded.h + ${MAIN_LIB_DIR}/events/ObjectVisitStarted.h + ${MAIN_LIB_DIR}/events/PlayerGotTurn.h + ${MAIN_LIB_DIR}/events/TurnStarted.h - filesystem/AdapterLoaders.h - filesystem/CArchiveLoader.h - filesystem/CBinaryReader.h - filesystem/CCompressedStream.h - filesystem/CFileInputStream.h - filesystem/CFilesystemLoader.h - filesystem/CInputOutputStream.h - filesystem/CInputStream.h - filesystem/CMemoryBuffer.h - filesystem/CMemoryStream.h - filesystem/COutputStream.h - filesystem/CStream.h - filesystem/CZipLoader.h - filesystem/CZipSaver.h - filesystem/FileInfo.h - filesystem/FileStream.h - filesystem/Filesystem.h - filesystem/ISimpleResourceLoader.h - filesystem/MinizipExtensions.h - filesystem/ResourceID.h + ${MAIN_LIB_DIR}/filesystem/AdapterLoaders.h + ${MAIN_LIB_DIR}/filesystem/CArchiveLoader.h + ${MAIN_LIB_DIR}/filesystem/CBinaryReader.h + ${MAIN_LIB_DIR}/filesystem/CCompressedStream.h + ${MAIN_LIB_DIR}/filesystem/CFileInputStream.h + ${MAIN_LIB_DIR}/filesystem/CFilesystemLoader.h + ${MAIN_LIB_DIR}/filesystem/CInputOutputStream.h + ${MAIN_LIB_DIR}/filesystem/CInputStream.h + ${MAIN_LIB_DIR}/filesystem/CMemoryBuffer.h + ${MAIN_LIB_DIR}/filesystem/CMemoryStream.h + ${MAIN_LIB_DIR}/filesystem/COutputStream.h + ${MAIN_LIB_DIR}/filesystem/CStream.h + ${MAIN_LIB_DIR}/filesystem/CZipLoader.h + ${MAIN_LIB_DIR}/filesystem/CZipSaver.h + ${MAIN_LIB_DIR}/filesystem/FileInfo.h + ${MAIN_LIB_DIR}/filesystem/FileStream.h + ${MAIN_LIB_DIR}/filesystem/Filesystem.h + ${MAIN_LIB_DIR}/filesystem/ISimpleResourceLoader.h + ${MAIN_LIB_DIR}/filesystem/MinizipExtensions.h + ${MAIN_LIB_DIR}/filesystem/ResourceID.h - logging/CBasicLogConfigurator.h - logging/CLogger.h + ${MAIN_LIB_DIR}/logging/CBasicLogConfigurator.h + ${MAIN_LIB_DIR}/logging/CLogger.h - mapObjects/CArmedInstance.h - mapObjects/CBank.h - mapObjects/CGHeroInstance.h - mapObjects/CGMarket.h - mapObjects/CGPandoraBox.h - mapObjects/CGTownInstance.h - mapObjects/CObjectClassesHandler.h - mapObjects/CObjectHandler.h - mapObjects/CommonConstructors.h - mapObjects/CQuest.h - mapObjects/CRewardableConstructor.h - mapObjects/CRewardableObject.h - mapObjects/JsonRandom.h - mapObjects/MapObjects.h - mapObjects/MiscObjects.h - mapObjects/ObjectTemplate.h + ${MAIN_LIB_DIR}/mapObjects/CArmedInstance.h + ${MAIN_LIB_DIR}/mapObjects/CBank.h + ${MAIN_LIB_DIR}/mapObjects/CGHeroInstance.h + ${MAIN_LIB_DIR}/mapObjects/CGMarket.h + ${MAIN_LIB_DIR}/mapObjects/CGPandoraBox.h + ${MAIN_LIB_DIR}/mapObjects/CGTownInstance.h + ${MAIN_LIB_DIR}/mapObjects/CObjectClassesHandler.h + ${MAIN_LIB_DIR}/mapObjects/CObjectHandler.h + ${MAIN_LIB_DIR}/mapObjects/CommonConstructors.h + ${MAIN_LIB_DIR}/mapObjects/CQuest.h + ${MAIN_LIB_DIR}/mapObjects/CRewardableConstructor.h + ${MAIN_LIB_DIR}/mapObjects/CRewardableObject.h + ${MAIN_LIB_DIR}/mapObjects/JsonRandom.h + ${MAIN_LIB_DIR}/mapObjects/MapObjects.h + ${MAIN_LIB_DIR}/mapObjects/MiscObjects.h + ${MAIN_LIB_DIR}/mapObjects/ObjectTemplate.h - mapping/CCampaignHandler.h - mapping/CDrawRoadsOperation.h - mapping/CMapDefines.h - mapping/CMapEditManager.h - mapping/CMap.h - mapping/CMapInfo.h - mapping/CMapOperation.h - mapping/CMapService.h - mapping/MapEditUtils.h - mapping/MapFormatH3M.h - mapping/MapFormatJson.h + ${MAIN_LIB_DIR}/mapping/CCampaignHandler.h + ${MAIN_LIB_DIR}/mapping/CDrawRoadsOperation.h + ${MAIN_LIB_DIR}/mapping/CMapDefines.h + ${MAIN_LIB_DIR}/mapping/CMapEditManager.h + ${MAIN_LIB_DIR}/mapping/CMap.h + ${MAIN_LIB_DIR}/mapping/CMapInfo.h + ${MAIN_LIB_DIR}/mapping/CMapOperation.h + ${MAIN_LIB_DIR}/mapping/CMapService.h + ${MAIN_LIB_DIR}/mapping/MapEditUtils.h + ${MAIN_LIB_DIR}/mapping/MapFormatH3M.h + ${MAIN_LIB_DIR}/mapping/MapFormatJson.h - registerTypes/RegisterTypes.h + ${MAIN_LIB_DIR}/registerTypes/RegisterTypes.h - rmg/RmgArea.h - rmg/RmgObject.h - rmg/RmgPath.h - rmg/CMapGenerator.h - rmg/CMapGenOptions.h - rmg/CRmgTemplate.h - rmg/CRmgTemplateStorage.h - rmg/CZonePlacer.h - rmg/TileInfo.h - rmg/Zone.h - rmg/Functions.h - rmg/ObjectManager.h - rmg/RoadPlacer.h - rmg/TreasurePlacer.h - rmg/RmgMap.h - rmg/ConnectionsPlacer.h - rmg/WaterAdopter.h - rmg/TownPlacer.h - rmg/WaterProxy.h - rmg/WaterRoutes.h - rmg/RockPlacer.h - rmg/ObstaclePlacer.h - rmg/RiverPlacer.h - rmg/TerrainPainter.h - rmg/float3.h + ${MAIN_LIB_DIR}/rmg/RmgArea.h + ${MAIN_LIB_DIR}/rmg/RmgObject.h + ${MAIN_LIB_DIR}/rmg/RmgPath.h + ${MAIN_LIB_DIR}/rmg/CMapGenerator.h + ${MAIN_LIB_DIR}/rmg/CMapGenOptions.h + ${MAIN_LIB_DIR}/rmg/CRmgTemplate.h + ${MAIN_LIB_DIR}/rmg/CRmgTemplateStorage.h + ${MAIN_LIB_DIR}/rmg/CZonePlacer.h + ${MAIN_LIB_DIR}/rmg/TileInfo.h + ${MAIN_LIB_DIR}/rmg/Zone.h + ${MAIN_LIB_DIR}/rmg/Functions.h + ${MAIN_LIB_DIR}/rmg/ObjectManager.h + ${MAIN_LIB_DIR}/rmg/RoadPlacer.h + ${MAIN_LIB_DIR}/rmg/TreasurePlacer.h + ${MAIN_LIB_DIR}/rmg/RmgMap.h + ${MAIN_LIB_DIR}/rmg/ConnectionsPlacer.h + ${MAIN_LIB_DIR}/rmg/WaterAdopter.h + ${MAIN_LIB_DIR}/rmg/TownPlacer.h + ${MAIN_LIB_DIR}/rmg/WaterProxy.h + ${MAIN_LIB_DIR}/rmg/WaterRoutes.h + ${MAIN_LIB_DIR}/rmg/RockPlacer.h + ${MAIN_LIB_DIR}/rmg/ObstaclePlacer.h + ${MAIN_LIB_DIR}/rmg/RiverPlacer.h + ${MAIN_LIB_DIR}/rmg/TerrainPainter.h + ${MAIN_LIB_DIR}/rmg/float3.h - serializer/BinaryDeserializer.h - serializer/BinarySerializer.h - serializer/CLoadIntegrityValidator.h - serializer/CMemorySerializer.h - serializer/Connection.h - serializer/CSerializer.h - serializer/CTypeList.h - serializer/JsonDeserializer.h - serializer/JsonSerializeFormat.h - serializer/JsonSerializer.h - serializer/JsonUpdater.h - serializer/Cast.h + ${MAIN_LIB_DIR}/serializer/BinaryDeserializer.h + ${MAIN_LIB_DIR}/serializer/BinarySerializer.h + ${MAIN_LIB_DIR}/serializer/CLoadIntegrityValidator.h + ${MAIN_LIB_DIR}/serializer/CMemorySerializer.h + ${MAIN_LIB_DIR}/serializer/Connection.h + ${MAIN_LIB_DIR}/serializer/CSerializer.h + ${MAIN_LIB_DIR}/serializer/CTypeList.h + ${MAIN_LIB_DIR}/serializer/JsonDeserializer.h + ${MAIN_LIB_DIR}/serializer/JsonSerializeFormat.h + ${MAIN_LIB_DIR}/serializer/JsonSerializer.h + ${MAIN_LIB_DIR}/serializer/JsonUpdater.h + ${MAIN_LIB_DIR}/serializer/Cast.h - spells/AbilityCaster.h - spells/AdventureSpellMechanics.h - spells/BattleSpellMechanics.h - spells/BonusCaster.h - spells/CSpellHandler.h - spells/ISpellMechanics.h - spells/Problem.h - spells/ProxyCaster.h - spells/TargetCondition.h - spells/ViewSpellInt.h + ${MAIN_LIB_DIR}/spells/AbilityCaster.h + ${MAIN_LIB_DIR}/spells/AdventureSpellMechanics.h + ${MAIN_LIB_DIR}/spells/BattleSpellMechanics.h + ${MAIN_LIB_DIR}/spells/BonusCaster.h + ${MAIN_LIB_DIR}/spells/CSpellHandler.h + ${MAIN_LIB_DIR}/spells/ISpellMechanics.h + ${MAIN_LIB_DIR}/spells/Problem.h + ${MAIN_LIB_DIR}/spells/ProxyCaster.h + ${MAIN_LIB_DIR}/spells/TargetCondition.h + ${MAIN_LIB_DIR}/spells/ViewSpellInt.h - spells/effects/Catapult.h - spells/effects/Clone.h - spells/effects/Damage.h - spells/effects/Dispel.h - spells/effects/Effect.h - spells/effects/Effects.h - spells/effects/EffectsFwd.h - spells/effects/Heal.h - spells/effects/LocationEffect.h - spells/effects/Obstacle.h - spells/effects/Registry.h - spells/effects/UnitEffect.h - spells/effects/Summon.h - spells/effects/Teleport.h - spells/effects/Timed.h - spells/effects/RemoveObstacle.h - spells/effects/Sacrifice.h + ${MAIN_LIB_DIR}/spells/effects/Catapult.h + ${MAIN_LIB_DIR}/spells/effects/Clone.h + ${MAIN_LIB_DIR}/spells/effects/Damage.h + ${MAIN_LIB_DIR}/spells/effects/Dispel.h + ${MAIN_LIB_DIR}/spells/effects/Effect.h + ${MAIN_LIB_DIR}/spells/effects/Effects.h + ${MAIN_LIB_DIR}/spells/effects/EffectsFwd.h + ${MAIN_LIB_DIR}/spells/effects/Heal.h + ${MAIN_LIB_DIR}/spells/effects/LocationEffect.h + ${MAIN_LIB_DIR}/spells/effects/Obstacle.h + ${MAIN_LIB_DIR}/spells/effects/Registry.h + ${MAIN_LIB_DIR}/spells/effects/UnitEffect.h + ${MAIN_LIB_DIR}/spells/effects/Summon.h + ${MAIN_LIB_DIR}/spells/effects/Teleport.h + ${MAIN_LIB_DIR}/spells/effects/Timed.h + ${MAIN_LIB_DIR}/spells/effects/RemoveObstacle.h + ${MAIN_LIB_DIR}/spells/effects/Sacrifice.h - AI_Base.h - BattleFieldHandler.h - CAndroidVMHelper.h - CArtHandler.h - CBonusTypeHandler.h - CBuildingHandler.h - CConfigHandler.h - CConsoleHandler.h - CCreatureHandler.h - CCreatureSet.h - CGameInfoCallback.h - CGameInterface.h - CGameStateFwd.h - CGameState.h - CGeneralTextHandler.h - CHeroHandler.h - CModHandler.h - CondSh.h - ConstTransitivePtr.h - CPathfinder.h - CPlayerState.h - CRandomGenerator.h - CScriptingModule.h - CSkillHandler.h - CSoundBase.h - CStack.h - CStopWatch.h - CThreadHelper.h - CTownHandler.h - FunctionList.h - GameConstants.h - HeroBonus.h - IBonusTypeHandler.h - IGameCallback.h - IGameEventsReceiver.h - IHandlerBase.h - int3.h - Interprocess.h - JsonDetail.h - JsonNode.h - LoadProgress.h - LogicalExpression.h - NetPacksBase.h - NetPacks.h - NetPacksLobby.h - ObstacleHandler.h - PathfinderUtil.h - ResourceSet.h - ScriptHandler.h - ScopeGuard.h - StartInfo.h - StringConstants.h - Terrain.h - UnlockGuard.h - VCMIDirs.h - vcmi_endian.h - VCMI_Lib.h -) + ${MAIN_LIB_DIR}/AI_Base.h + ${MAIN_LIB_DIR}/BattleFieldHandler.h + ${MAIN_LIB_DIR}/CAndroidVMHelper.h + ${MAIN_LIB_DIR}/CArtHandler.h + ${MAIN_LIB_DIR}/CBonusTypeHandler.h + ${MAIN_LIB_DIR}/CBuildingHandler.h + ${MAIN_LIB_DIR}/CConfigHandler.h + ${MAIN_LIB_DIR}/CConsoleHandler.h + ${MAIN_LIB_DIR}/CCreatureHandler.h + ${MAIN_LIB_DIR}/CCreatureSet.h + ${MAIN_LIB_DIR}/CGameInfoCallback.h + ${MAIN_LIB_DIR}/CGameInterface.h + ${MAIN_LIB_DIR}/CGameStateFwd.h + ${MAIN_LIB_DIR}/CGameState.h + ${MAIN_LIB_DIR}/CGeneralTextHandler.h + ${MAIN_LIB_DIR}/CHeroHandler.h + ${MAIN_LIB_DIR}/CModHandler.h + ${MAIN_LIB_DIR}/CondSh.h + ${MAIN_LIB_DIR}/ConstTransitivePtr.h + ${MAIN_LIB_DIR}/CPathfinder.h + ${MAIN_LIB_DIR}/CPlayerState.h + ${MAIN_LIB_DIR}/CRandomGenerator.h + ${MAIN_LIB_DIR}/CScriptingModule.h + ${MAIN_LIB_DIR}/CSkillHandler.h + ${MAIN_LIB_DIR}/CSoundBase.h + ${MAIN_LIB_DIR}/CStack.h + ${MAIN_LIB_DIR}/CStopWatch.h + ${MAIN_LIB_DIR}/CThreadHelper.h + ${MAIN_LIB_DIR}/CTownHandler.h + ${MAIN_LIB_DIR}/FunctionList.h + ${MAIN_LIB_DIR}/GameConstants.h + ${MAIN_LIB_DIR}/HeroBonus.h + ${MAIN_LIB_DIR}/IBonusTypeHandler.h + ${MAIN_LIB_DIR}/IGameCallback.h + ${MAIN_LIB_DIR}/IGameEventsReceiver.h + ${MAIN_LIB_DIR}/IHandlerBase.h + ${MAIN_LIB_DIR}/int3.h + ${MAIN_LIB_DIR}/Interprocess.h + ${MAIN_LIB_DIR}/JsonDetail.h + ${MAIN_LIB_DIR}/JsonNode.h + ${MAIN_LIB_DIR}/LoadProgress.h + ${MAIN_LIB_DIR}/LogicalExpression.h + ${MAIN_LIB_DIR}/NetPacksBase.h + ${MAIN_LIB_DIR}/NetPacks.h + ${MAIN_LIB_DIR}/NetPacksLobby.h + ${MAIN_LIB_DIR}/ObstacleHandler.h + ${MAIN_LIB_DIR}/PathfinderUtil.h + ${MAIN_LIB_DIR}/ResourceSet.h + ${MAIN_LIB_DIR}/ScriptHandler.h + ${MAIN_LIB_DIR}/ScopeGuard.h + ${MAIN_LIB_DIR}/StartInfo.h + ${MAIN_LIB_DIR}/StringConstants.h + ${MAIN_LIB_DIR}/Terrain.h + ${MAIN_LIB_DIR}/UnlockGuard.h + ${MAIN_LIB_DIR}/VCMIDirs.h + ${MAIN_LIB_DIR}/vcmi_endian.h + ${MAIN_LIB_DIR}/VCMI_Lib.h + ) -if(APPLE_IOS) - set(lib_SRCS ${lib_SRCS} CIOSUtils.m) - set(lib_HEADERS ${lib_HEADERS} CIOSUtils.h) -endif(APPLE_IOS) + if(APPLE_IOS) + set(lib_SRCS ${lib_SRCS} ${MAIN_LIB_DIR}/CIOSUtils.m) + set(lib_HEADERS ${lib_HEADERS} ${MAIN_LIB_DIR}/CIOSUtils.h) + endif(APPLE_IOS) -assign_source_group(${lib_SRCS} ${lib_HEADERS}) + assign_source_group(${lib_SRCS} ${lib_HEADERS}) -add_library(vcmi SHARED ${lib_SRCS} ${lib_HEADERS}) -set_target_properties(vcmi PROPERTIES COMPILE_DEFINITIONS "VCMI_DLL=1") -target_link_libraries(vcmi PUBLIC + add_library(${TARGET_NAME} ${LIBRARY_TYPE} ${lib_SRCS} ${lib_HEADERS}) + set_target_properties(${TARGET_NAME} PROPERTIES COMPILE_DEFINITIONS "VCMI_DLL=1") + target_link_libraries(${TARGET_NAME} PUBLIC minizip::minizip ZLIB::ZLIB ${SYSTEM_LIBS} Boost::boost Boost::thread Boost::filesystem Boost::program_options Boost::locale Boost::date_time -) - -target_include_directories(vcmi - PUBLIC ${CMAKE_CURRENT_SOURCE_DIR} - PUBLIC ${CMAKE_HOME_DIRECTORY} - PUBLIC ${CMAKE_HOME_DIRECTORY}/include - PRIVATE ${SDL2_INCLUDE_DIR} -) - -if(WIN32) - set_target_properties(vcmi - PROPERTIES - OUTPUT_NAME "VCMI_lib" - PROJECT_LABEL "VCMI_lib" ) -endif() -if(ANDROID) - return() -endif() - -vcmi_set_output_dir(vcmi "") - -enable_pch(vcmi) - -# We want to deploy assets into build directory for easier debugging without install -if(NOT APPLE_IOS) - add_custom_command(TARGET vcmi POST_BUILD - COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config - COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/config ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config - COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/Mods ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods + target_include_directories(${TARGET_NAME} + PUBLIC ${CMAKE_CURRENT_SOURCE_DIR} + PUBLIC ${CMAKE_SOURCE_DIR} + PUBLIC ${CMAKE_SOURCE_DIR}/include + PUBLIC ${MAIN_LIB_DIR} + PRIVATE ${SDL2_INCLUDE_DIR} ) -endif() -# Update version before vcmi compiling -if(TARGET update_version) - add_dependencies(vcmi update_version) -endif() + if(WIN32) + set_target_properties(${TARGET_NAME} + PROPERTIES + OUTPUT_NAME "VCMI_lib" + PROJECT_LABEL "VCMI_lib" + ) + endif() -install(TARGETS vcmi RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) -if(APPLE_IOS) - get_target_property(LINKED_LIBS vcmi LINK_LIBRARIES) - foreach(LINKED_LIB IN LISTS LINKED_LIBS) - if(TARGET ${LINKED_LIB}) - get_target_property(LIB_TYPE ${LINKED_LIB} TYPE) - if(LIB_TYPE STREQUAL "SHARED_LIBRARY") - get_target_property(_aliased ${LINKED_LIB} ALIASED_TARGET) - if(_aliased) - set(LINKED_LIB_REAL ${_aliased}) - else() - set(LINKED_LIB_REAL ${LINKED_LIB}) + if(ANDROID) + return() + endif() + + vcmi_set_output_dir(${TARGET_NAME} "") + + enable_pch(${TARGET_NAME}) + + # We want to deploy assets into build directory for easier debugging without install + if(NOT APPLE_IOS) + add_custom_command(TARGET ${TARGET_NAME} POST_BUILD + COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config + COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods + COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/config ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/config + COMMAND ${CMAKE_COMMAND} -E copy_directory ${CMAKE_SOURCE_DIR}/Mods ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/Mods + ) + endif() + + # Update version before vcmi compiling + if(TARGET update_version) + add_dependencies(${TARGET_NAME} update_version) + endif() + + install(TARGETS ${TARGET_NAME} RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + if(APPLE_IOS) + get_target_property(LINKED_LIBS ${TARGET_NAME} LINK_LIBRARIES) + foreach(LINKED_LIB IN LISTS LINKED_LIBS) + if(NOT TARGET ${LINKED_LIB}) + if(LINKED_LIB MATCHES "\\${CMAKE_SHARED_LIBRARY_SUFFIX}$") + install(FILES ${LINKED_LIB} DESTINATION ${LIB_DIR} COMPONENT core) endif() - install(TARGETS ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + continue() endif() - else() - if(LINKED_LIB MATCHES "\\${CMAKE_SHARED_LIBRARY_SUFFIX}$") - install(FILES ${LINKED_LIB} DESTINATION ${LIB_DIR} COMPONENT core) + + get_target_property(LIB_TYPE ${LINKED_LIB} TYPE) + if(NOT LIB_TYPE STREQUAL "SHARED_LIBRARY") + continue() endif() - endif() - endforeach() -endif() + + get_target_property(_aliased ${LINKED_LIB} ALIASED_TARGET) + if(_aliased) + set(LINKED_LIB_REAL ${_aliased}) + else() + set(LINKED_LIB_REAL ${LINKED_LIB}) + endif() + install(TARGETS ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + endforeach() + endif() +endmacro() diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt new file mode 100644 index 000000000..d0536b245 --- /dev/null +++ b/lib/CMakeLists.txt @@ -0,0 +1 @@ +add_main_lib(vcmi SHARED) From 0a1f824adde6688f2c44bd8a750418606b280f14 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 27 Jul 2022 12:18:43 +0300 Subject: [PATCH 070/131] fix installing shared Boost libraries --- cmake_modules/VCMI_lib.cmake | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/cmake_modules/VCMI_lib.cmake b/cmake_modules/VCMI_lib.cmake index 09a28fbbd..f83249f13 100644 --- a/cmake_modules/VCMI_lib.cmake +++ b/cmake_modules/VCMI_lib.cmake @@ -516,7 +516,21 @@ macro(add_main_lib TARGET_NAME LIBRARY_TYPE) else() set(LINKED_LIB_REAL ${LINKED_LIB}) endif() - install(TARGETS ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + + get_target_property(_imported ${LINKED_LIB_REAL} IMPORTED) + if(_imported) + set(INSTALL_TYPE IMPORTED_RUNTIME_ARTIFACTS) + get_target_property(BOOST_DEPENDENCIES ${LINKED_LIB_REAL} INTERFACE_LINK_LIBRARIES) + foreach(BOOST_DEPENDENCY IN LISTS BOOST_DEPENDENCIES) + get_target_property(BOOST_DEPENDENCY_TYPE ${BOOST_DEPENDENCY} TYPE) + if(BOOST_DEPENDENCY_TYPE STREQUAL "SHARED_LIBRARY") + install(IMPORTED_RUNTIME_ARTIFACTS ${BOOST_DEPENDENCY} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + endif() + endforeach() + else() + set(INSTALL_TYPE TARGETS) + endif() + install(${INSTALL_TYPE} ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) endforeach() endif() endmacro() From c6e51852d02797253743632ac88785ef5db42de1 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 27 Jul 2022 12:23:37 +0300 Subject: [PATCH 071/131] add ability to build VCMI as single process "Client process -> shared VCMI lib <- Server process" is turned into "shared Client-VCMI lib -> process <- static Server-VCMI lib" - adds lib_client and lib_server targets that define distinct namespaces - lib_client is a dynamic library which is shared with AI libs, lib_server is static --- AI/BattleAI/CMakeLists.txt | 2 +- AI/EmptyAI/CMakeLists.txt | 2 +- AI/Nullkiller/CMakeLists.txt | 2 +- AI/StupidAI/CMakeLists.txt | 2 +- AI/VCAI/CMakeLists.txt | 2 +- CMakeLists.txt | 14 +++++++++++++- client/CMakeLists.txt | 8 +++++++- lib_client/CMakeLists.txt | 2 ++ lib_server/CMakeLists.txt | 2 ++ server/CMakeLists.txt | 9 +++++++-- 10 files changed, 36 insertions(+), 9 deletions(-) create mode 100644 lib_client/CMakeLists.txt create mode 100644 lib_server/CMakeLists.txt diff --git a/AI/BattleAI/CMakeLists.txt b/AI/BattleAI/CMakeLists.txt index 1c0754b4c..2e0c13f40 100644 --- a/AI/BattleAI/CMakeLists.txt +++ b/AI/BattleAI/CMakeLists.txt @@ -33,7 +33,7 @@ endif() add_library(BattleAI SHARED ${battleAI_SRCS} ${battleAI_HEADERS}) target_include_directories(BattleAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) -target_link_libraries(BattleAI PRIVATE vcmi) +target_link_libraries(BattleAI PRIVATE ${VCMI_LIB_TARGET}) vcmi_set_output_dir(BattleAI "AI") enable_pch(BattleAI) diff --git a/AI/EmptyAI/CMakeLists.txt b/AI/EmptyAI/CMakeLists.txt index e6b962fb5..b8656cc93 100644 --- a/AI/EmptyAI/CMakeLists.txt +++ b/AI/EmptyAI/CMakeLists.txt @@ -15,7 +15,7 @@ assign_source_group(${emptyAI_SRCS} ${emptyAI_HEADERS}) add_library(EmptyAI SHARED ${emptyAI_SRCS} ${emptyAI_HEADERS}) target_include_directories(EmptyAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) -target_link_libraries(EmptyAI PRIVATE vcmi) +target_link_libraries(EmptyAI PRIVATE ${VCMI_LIB_TARGET}) vcmi_set_output_dir(EmptyAI "AI") enable_pch(EmptyAI) diff --git a/AI/Nullkiller/CMakeLists.txt b/AI/Nullkiller/CMakeLists.txt index beb4ccd0b..bbe7a2126 100644 --- a/AI/Nullkiller/CMakeLists.txt +++ b/AI/Nullkiller/CMakeLists.txt @@ -130,7 +130,7 @@ add_library(Nullkiller SHARED ${Nullkiller_SRCS} ${Nullkiller_HEADERS}) target_include_directories(Nullkiller PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) -target_link_libraries(Nullkiller PRIVATE vcmi fuzzylite::fuzzylite) +target_link_libraries(Nullkiller PRIVATE ${VCMI_LIB_TARGET} fuzzylite::fuzzylite) target_link_libraries(Nullkiller PRIVATE TBB::tbb) diff --git a/AI/StupidAI/CMakeLists.txt b/AI/StupidAI/CMakeLists.txt index f99948995..efa37ba5d 100644 --- a/AI/StupidAI/CMakeLists.txt +++ b/AI/StupidAI/CMakeLists.txt @@ -14,7 +14,7 @@ set(stupidAI_HEADERS assign_source_group(${stupidAI_SRCS} ${stupidAI_HEADERS}) add_library(StupidAI SHARED ${stupidAI_SRCS} ${stupidAI_HEADERS}) -target_link_libraries(StupidAI PRIVATE vcmi) +target_link_libraries(StupidAI PRIVATE ${VCMI_LIB_TARGET}) target_include_directories(StupidAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) vcmi_set_output_dir(StupidAI "AI") diff --git a/AI/VCAI/CMakeLists.txt b/AI/VCAI/CMakeLists.txt index 7f16361ba..5735eecab 100644 --- a/AI/VCAI/CMakeLists.txt +++ b/AI/VCAI/CMakeLists.txt @@ -107,7 +107,7 @@ add_library(VCAI SHARED ${VCAI_SRCS} ${VCAI_HEADERS}) target_include_directories(VCAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) -target_link_libraries(VCAI PRIVATE vcmi fuzzylite::fuzzylite) +target_link_libraries(VCAI PRIVATE ${VCMI_LIB_TARGET} fuzzylite::fuzzylite) vcmi_set_output_dir(VCAI "AI") enable_pch(VCAI) diff --git a/CMakeLists.txt b/CMakeLists.txt index 885cabff9..32196fd76 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -34,6 +34,10 @@ if(APPLE) endif() endif(APPLE) +if(APPLE_IOS) + set(BUILD_SINGLE_APP 1) +endif() + ############################################ # User-provided options # ############################################ @@ -412,7 +416,15 @@ if(NOT TARGET minizip::minizip) add_subdirectory_with_folder("3rdparty" lib/minizip) add_library(minizip::minizip ALIAS minizip) endif() -add_subdirectory(lib) + +include(VCMI_lib) +if(BUILD_SINGLE_APP) + add_subdirectory(lib_client) + add_subdirectory(lib_server) +else() + add_subdirectory(lib) +endif() + add_subdirectory(client) add_subdirectory(server) add_subdirectory_with_folder("AI" AI) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 95f05c45d..b56e75a16 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -224,8 +224,14 @@ elseif(APPLE_IOS) set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") endif() +if(BUILD_SINGLE_APP) + target_link_libraries(vcmiclient PRIVATE vcmiserver) + set(VCMI_LIB_TARGET vcmi_lib_client) +else() + set(VCMI_LIB_TARGET vcmi) +endif() target_link_libraries(vcmiclient PRIVATE - vcmi SDL2::SDL2 SDL2::Image SDL2::Mixer SDL2::TTF + ${VCMI_LIB_TARGET} SDL2::SDL2 SDL2::Image SDL2::Mixer SDL2::TTF ) if(ffmpeg_LIBRARIES) diff --git a/lib_client/CMakeLists.txt b/lib_client/CMakeLists.txt new file mode 100644 index 000000000..f51966e22 --- /dev/null +++ b/lib_client/CMakeLists.txt @@ -0,0 +1,2 @@ +add_main_lib(vcmi_lib_client SHARED) +target_compile_definitions(vcmi_lib_client PUBLIC VCMI_LIB_NAMESPACE=LIB_CLIENT) diff --git a/lib_server/CMakeLists.txt b/lib_server/CMakeLists.txt new file mode 100644 index 000000000..e9d097e05 --- /dev/null +++ b/lib_server/CMakeLists.txt @@ -0,0 +1,2 @@ +add_main_lib(vcmi_lib_server STATIC) +target_compile_definitions(vcmi_lib_server PUBLIC VCMI_LIB_NAMESPACE=LIB_SERVER) diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 95cd7f135..3df83201e 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -26,9 +26,14 @@ if(ANDROID) # android needs client/server to be libraries, not executables, so w return() endif() -add_executable(vcmiserver ${server_SRCS} ${server_HEADERS}) +if(BUILD_SINGLE_APP) + add_library(vcmiserver STATIC ${server_SRCS} ${server_HEADERS}) + set(server_LIBS vcmi_lib_server) +else() + add_executable(vcmiserver ${server_SRCS} ${server_HEADERS}) + set(server_LIBS vcmi) +endif() -set(server_LIBS vcmi) if(CMAKE_SYSTEM_NAME MATCHES FreeBSD) set(server_LIBS execinfo ${server_LIBS}) elseif(APPLE_IOS) From e61e283b751268d7cdfd269a0d5b6a60bf6bc059 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 26 Jul 2022 16:09:30 +0300 Subject: [PATCH 072/131] [iOS] remove everything related to server app --- server/CMakeLists.txt | 31 +---- server/ios/Entitlements.in | 10 -- .../AppIcon.appiconset/Contents.json | 121 ------------------ .../AppIcon.appiconset/Icon-App-20x20@1x.png | Bin 513 -> 0 bytes .../AppIcon.appiconset/Icon-App-20x20@2x.png | Bin 798 -> 0 bytes .../AppIcon.appiconset/Icon-App-20x20@3x.png | Bin 1128 -> 0 bytes .../AppIcon.appiconset/Icon-App-29x29@1x.png | Bin 634 -> 0 bytes .../AppIcon.appiconset/Icon-App-29x29@2x.png | Bin 1088 -> 0 bytes .../AppIcon.appiconset/Icon-App-29x29@3x.png | Bin 1589 -> 0 bytes .../AppIcon.appiconset/Icon-App-40x40@1x.png | Bin 798 -> 0 bytes .../AppIcon.appiconset/Icon-App-40x40@2x.png | Bin 1434 -> 0 bytes .../AppIcon.appiconset/Icon-App-40x40@3x.png | Bin 2235 -> 0 bytes .../AppIcon.appiconset/Icon-App-60x60@2x.png | Bin 2235 -> 0 bytes .../AppIcon.appiconset/Icon-App-60x60@3x.png | Bin 3758 -> 0 bytes .../AppIcon.appiconset/Icon-App-76x76@1x.png | Bin 1393 -> 0 bytes .../AppIcon.appiconset/Icon-App-76x76@2x.png | Bin 3053 -> 0 bytes .../Icon-App-83.5x83.5@2x.png | Bin 3401 -> 0 bytes server/ios/Images.xcassets/Contents.json | 6 - server/ios/Info.plist | 52 -------- server/ios/main.mm | 119 ----------------- 20 files changed, 1 insertion(+), 338 deletions(-) delete mode 100644 server/ios/Entitlements.in delete mode 100755 server/ios/Images.xcassets/AppIcon.appiconset/Contents.json delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png delete mode 100644 server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png delete mode 100644 server/ios/Images.xcassets/Contents.json delete mode 100644 server/ios/Info.plist delete mode 100644 server/ios/main.mm diff --git a/server/CMakeLists.txt b/server/CMakeLists.txt index 3df83201e..0f0313114 100644 --- a/server/CMakeLists.txt +++ b/server/CMakeLists.txt @@ -16,10 +16,6 @@ set(server_HEADERS CVCMIServer.h ) -if(APPLE_IOS) - set(server_SRCS ${server_SRCS} ios/main.mm) -endif(APPLE_IOS) - assign_source_group(${server_SRCS} ${server_HEADERS}) if(ANDROID) # android needs client/server to be libraries, not executables, so we can't reuse the build part of this script @@ -36,8 +32,6 @@ endif() if(CMAKE_SYSTEM_NAME MATCHES FreeBSD) set(server_LIBS execinfo ${server_LIBS}) -elseif(APPLE_IOS) - set(server_LIBS ${server_LIBS} "-framework UIKit") endif() target_link_libraries(vcmiserver PRIVATE ${server_LIBS} minizip::minizip) @@ -51,34 +45,11 @@ if(WIN32) OUTPUT_NAME "VCMI_server" PROJECT_LABEL "VCMI_server" ) -elseif(APPLE_IOS) - set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) - configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) - - set_target_properties(vcmiserver PROPERTIES - MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" - XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" - XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED "$(CODE_SIGNING_ALLOWED_FOR_APPS)" - XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon - XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} - ) - # TODO: move to a common dir / add macro? - target_sources(vcmiserver PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) - set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") - - target_sources(vcmiserver PRIVATE ios/Images.xcassets) - set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") endif() vcmi_set_output_dir(vcmiserver "") enable_pch(vcmiserver) -if(APPLE_IOS) - # TODO: move to a common dir / add macro? - add_custom_command(TARGET vcmiserver POST_BUILD - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component core --prefix "$" - COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh - ) -else() +if(NOT BUILD_SINGLE_APP) install(TARGETS vcmiserver DESTINATION ${BIN_DIR}) endif() diff --git a/server/ios/Entitlements.in b/server/ios/Entitlements.in deleted file mode 100644 index 73367ec6b..000000000 --- a/server/ios/Entitlements.in +++ /dev/null @@ -1,10 +0,0 @@ - - - - - com.apple.security.application-groups - - group.@BUNDLE_IDENTIFIER_PREFIX@.vcmi - - - diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Contents.json b/server/ios/Images.xcassets/AppIcon.appiconset/Contents.json deleted file mode 100755 index 8122b0a0c..000000000 --- a/server/ios/Images.xcassets/AppIcon.appiconset/Contents.json +++ /dev/null @@ -1,121 +0,0 @@ -{ - "images" : [ - { - "filename" : "Icon-App-20x20@2x.png", - "idiom" : "iphone", - "scale" : "2x", - "size" : "20x20" - }, - { - "filename" : "Icon-App-20x20@3x.png", - "idiom" : "iphone", - "scale" : "3x", - "size" : "20x20" - }, - { - "filename" : "Icon-App-29x29@1x.png", - "idiom" : "iphone", - "scale" : "1x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-29x29@2x.png", - "idiom" : "iphone", - "scale" : "2x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-29x29@3x.png", - "idiom" : "iphone", - "scale" : "3x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-40x40@2x.png", - "idiom" : "iphone", - "scale" : "2x", - "size" : "40x40" - }, - { - "filename" : "Icon-App-40x40@3x.png", - "idiom" : "iphone", - "scale" : "3x", - "size" : "40x40" - }, - { - "filename" : "Icon-App-60x60@2x.png", - "idiom" : "iphone", - "scale" : "2x", - "size" : "60x60" - }, - { - "filename" : "Icon-App-60x60@3x.png", - "idiom" : "iphone", - "scale" : "3x", - "size" : "60x60" - }, - { - "filename" : "Icon-App-20x20@1x.png", - "idiom" : "ipad", - "scale" : "1x", - "size" : "20x20" - }, - { - "filename" : "Icon-App-20x20@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "20x20" - }, - { - "filename" : "Icon-App-29x29@1x.png", - "idiom" : "ipad", - "scale" : "1x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-29x29@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-40x40@1x.png", - "idiom" : "ipad", - "scale" : "1x", - "size" : "40x40" - }, - { - "filename" : "Icon-App-40x40@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "40x40" - }, - { - "filename" : "Icon-App-76x76@1x.png", - "idiom" : "ipad", - "scale" : "1x", - "size" : "76x76" - }, - { - "filename" : "Icon-App-76x76@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "76x76" - }, - { - "filename" : "Icon-App-83.5x83.5@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "83.5x83.5" - }, - { - "idiom" : "ios-marketing", - "scale" : "1x", - "size" : "1024x1024" - } - ], - "info" : { - "author" : "xcode", - "version" : 1 - } -} diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png deleted file mode 100644 index 3eba4d478f83f8480b0ed275579d4d4966a2a60a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 513 zcmV+c0{;DpP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0P0CZK~#90ZICfbLU9zu&%J*`tf)v39&SP=34MWhW3;%sx;VA^#?N3hGTo_L00000NkvXXu0mjf Duk0002eX+uL$Nkc;* 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 Ub21BU#sB~S07*qoM6N<$g27o4I{*Lx diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png deleted file mode 100644 index e38db8555716e5656df227e61a0e75b80391d3ac..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1088 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 JPDHLkV1iX@HF*F4 diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png deleted file mode 100644 index 1c2b0039bed8277d6225ce1792f66b6462b22cab..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2235 zcmV;s2t@aZP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$2c$_vK~#90?U{RU)YTQozvu2FFOtBJNQeP~nTCgrDOjqK0ePs%J0%7*gboOH zN}0}d`uM|XYe$^vbZYHT#*ShuI+aHQreHE+kx;9`D6aEcT-UHy_Mu-ESv0`N;}Xuy{MNT(wS z2%gb%;oPOPoRMk31Ao>Cqh zIQqwPbohrXdxQcCKC7 zT7TUkfsFk7=D8S!W`wjH`lTDd{C!QKfolg>0#jdVJhD`3Fisk?QU!1n;m*nhD@H~;%LZXk2xxfa7HLG%EB0jJv7d7}A)*KmRqF0Yf#?7^$ue`wA5*&MTdeVKiW<1{yPjrnd`6gBA1V13NvA zu0T;chCV?NAn@W&wRDa#N{J|CuyWdYK!lFG32fTL?(nOxm@)*)r34UhH~_cwj;3B< zp)4GP+7Ck^NNIR~b`BLN@4hPcJj1R9$|Qd`$p=7m_IDET&gWu63Q*CqA`!u06Nto! z;aFe@?tcvJTl`(N+tFMGfZ~7SIw$5!c)oDTy_Z2iI%iD4sVyP(l%@@jJ=75kbu+L@ zC{4hw!$JTQZ^c97As`NaDl&;ZQjugXPlEsw$bJggdN#OIqU!83NyY*gf@$AG(^d!o z;*;7%ZX*zU(8vMzMWh?`^-z*A#bf2zHUxL-dGo=^-Z+w43@`^h38}6Z0}8j?H4_4g zJ^^H=N6zf>zs{ixX*OL_27v57{IpYB0)v=6nswC>P|oZu$)o`AH36xKQCkeJC>@uaBN{b82j`Vs0^5c~uBhwU-7D=KBIjO^WTHBBP(6e{-vl*!$74^tkTYSaT>P znR0L!jB49jR1nNDG=L`hxXaX{A+ondjOg`QCGp*NvB1K@$LZbbQ`mcKaVV3x1_7S- zzO-=MEP6M1l^lI4wyd?x_g0S|;T#uy`xBWp{C8<75XLqITV95J&s^Dq#=FHl>_l&V~3&P>0y(u8AIJ(zZ^ix ziMD|8UiwoKkn`6@U$2_0uezGjG4Gyr?CB~LoP7Je&)NbRS)G}4i}Q?#-gxxb7Z^Bx z_>#ed{C4m%BT`p+=8zW3{ke0#w()rFWd)sm?}U=*D)R;f{ehIRQIjd~)LppJnUS48 z5JmyK(wXRl>A+wo01YL8x5bet0K9>;#49?{0YH0QgQA_if1O0P1sHGG^d&a{$J8AP zk8mf`rKZP%?zD0Xd#76`cV2&NgKe-4w!t>o2HW5}80@_Hl-NQr{JPwVSSnCyz@lU^_Bw^tZm$wPTV@WC@5lbS3!mlg2U;XuK< zx|a6FJ@fFb1J?3&{~eOjSn}i*g%mgKe-4w!t>o2H#2G{{rnj^c4K(LYe>o002ov JPDHLkV1iX@HF*F4 diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png deleted file mode 100644 index 5d35d682f25d53c9224e2323ba235d69c6068388..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 3758 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 MYWk|B%C@2Z1^c91`Tzg` diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png deleted file mode 100644 index 902615d4d43322a4b38b6b8e253be0598c9fd099..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1393 zcmV-%1&;cOP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$1X@W%K~#90?U!3@RYeqr|24apgOnoWmltMZ5X6ZR+&-#5hy=+R` zU4@W7od4xavS+^eXJ*Zsb%eNaGB=PFhs9xW*f519^t6-!#B?`}0HBJYia@B{9|3?0 z81amVNd`+n+Q&C#aA&=+?~jd;=(vReN@VZ3r0C<52?>?`p^4+42!2<3{BTrf=EP`3 zT?G>EnRei`15BJVvUd)4Nl&c>9{wdl(mj%k51Z9;>!gxzem=CRIO|DXEKkSu4pox0 zT#2M@4V|^?fVamjvC26^86>0e{-XTf0%$Z4YCFD!GB(2ttHMyj+IXJqJ z+7FCT-H)j)R4PMxzu5>Y@EEOYZIq`TxuW*9S!QljNm{PSa~_PU)yCkMdiB71x7fi$ zxhMBSq1c;o7ZM_GVFl?JlfWs(Au$~#c|ZOj7Ak)qctv3ZB3*~xtzMXD(o$@;hK664 z!pfoQ;0%%2AuS3L(e#zvKm*Fh_s?Lz@oBux!iiOf#l_K<1vIGE+k=SBD=A5Yxl%N) zyjon-x^IQse`t6^PRA~`pFrgE`6Cpl$C#v^BL^Uzfu-S%fRv5DyUiB{V9}^uwa$g= z=O92h#)!=W0ESD_zBuWG%Uy|B znPREg)?E242p~t!{HZYuJt4j<@M*)27Y0D}ff?q_u6@o4o3bRV*r}S)T9~jYO)4M_yYH;>s z``D}us0p>Fy8i@60)%v42qdE|G3|o61y|hk#NKThG&#nuQ`e8bu7MHWkxGaNx+ATp zk7uZ-`=HMLtA_7W7l*}RHv^X7--Rlmx#|)QApg7RS4Vl|>x^Q{PDC?{!sj38TdrLr zzweaB{ExDx*E~A!DEt!)2bC%dr$$ItC2ycRcwhEkfOw5H>@H61w9$F1JA8flhepVh zUk*TY;b?!D?=su(#oQyL+j7=#k>1L&e_2+fAoY!Uf6@?OR90mJlRpT1U)%o+qsz`|yZ$&E@olT)(#0K` z<)1hFmU$ip=SbF$F0|Hf&wNr4<@AfABH0;@`*Pn;^>yZ(&qB?aXAYlF&CVV|VjDu? z5=&#e5t)_{<<)<9ugBTYHGH4CI4lmk8L)o=yO?E30+r(~00000NkvXXu0mjf0QH*t diff --git a/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png b/server/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png deleted file mode 100644 index fc3411d970bc49b2034bd5758177b4571493d0a5..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 3053 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 I+(JhD3oO3#|DyhDfLX*%iN7)R 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 ON7C0ee)L)s8uLG(nwgOR diff --git a/server/ios/Images.xcassets/Contents.json b/server/ios/Images.xcassets/Contents.json deleted file mode 100644 index 73c00596a..000000000 --- a/server/ios/Images.xcassets/Contents.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "info" : { - "author" : "xcode", - "version" : 1 - } -} diff --git a/server/ios/Info.plist b/server/ios/Info.plist deleted file mode 100644 index 9b31b63a2..000000000 --- a/server/ios/Info.plist +++ /dev/null @@ -1,52 +0,0 @@ - - - - - CFBundleDevelopmentRegion - en - CFBundleExecutable - $(PRODUCT_NAME) - CFBundleIdentifier - $(PRODUCT_BUNDLE_IDENTIFIER) - CFBundleInfoDictionaryVersion - 6.0 - CFBundleName - VCMI server - CFBundlePackageType - APPL - CFBundleShortVersionString - $(MARKETING_VERSION) - CFBundleSignature - ???? - CFBundleVersion - 1 - LSRequiresIPhoneOS - - NSAppTransportSecurity - - NSAllowsArbitraryLoads - - - UIFileSharingEnabled - - UILaunchStoryboardName - LaunchScreen - UIRequiredDeviceCapabilities - - armv7 - - UISupportedInterfaceOrientations - - UIInterfaceOrientationLandscapeLeft - UIInterfaceOrientationLandscapeRight - UIInterfaceOrientationPortrait - - UISupportedInterfaceOrientations~ipad - - UIInterfaceOrientationLandscapeLeft - UIInterfaceOrientationLandscapeRight - UIInterfaceOrientationPortrait - UIInterfaceOrientationPortraitUpsideDown - - - diff --git a/server/ios/main.mm b/server/ios/main.mm deleted file mode 100644 index 7b457a8d6..000000000 --- a/server/ios/main.mm +++ /dev/null @@ -1,119 +0,0 @@ -/* - * main_ios.mm, part of VCMI engine - * - * Authors: listed in file AUTHORS in main folder - * - * License: GNU General Public License v2.0 or later - * Full text of license available in license.txt file, in main folder - * - */ -#import - -#include "../Global.h" -#include "CVCMIServer.h" -#import "../lib/CIOSUtils.h" - -@interface ViewController : UIViewController -@property (nonatomic, copy) NSArray *dataDirsInDocuments; -@end - -@implementation ViewController - -- (void)viewDidLoad -{ - [super viewDidLoad]; - - auto startServerButton = [UIButton buttonWithType:UIButtonTypeSystem]; - [startServerButton setTitle:@"Start Server" forState:UIControlStateNormal]; - [startServerButton addTarget:self action:@selector(startServer:) forControlEvents:UIControlEventTouchUpInside]; - [self.view addSubview:startServerButton]; - startServerButton.translatesAutoresizingMaskIntoConstraints = NO; - [NSLayoutConstraint activateConstraints:@[ - [startServerButton.centerXAnchor constraintEqualToAnchor:self.view.centerXAnchor], - [startServerButton.centerYAnchor constraintEqualToAnchor:self.view.centerYAnchor], - ]]; - - auto fm = NSFileManager.defaultManager; - auto sharedGameDataUrl = sharedGameDataURL(); - if (!sharedGameDataUrl || [fm fileExistsAtPath:sharedGameDataUrl.path]) - return; - - auto documentsURL = [fm URLForDirectory:NSDocumentDirectory inDomain:NSUserDomainMask appropriateForURL:nil create:YES error:nullptr]; - auto dirEnumerator = [fm enumeratorAtURL:documentsURL includingPropertiesForKeys:@[NSURLNameKey] options:NSDirectoryEnumerationSkipsSubdirectoryDescendants errorHandler:nil]; - auto dataDirs = [NSMutableArray arrayWithCapacity:3]; - for (NSURL *fileURL in dirEnumerator) - { - NSString *filename; - if (![fileURL getResourceValue:&filename forKey:NSURLNameKey error:nullptr]) - continue; - if ([filename caseInsensitiveCompare:@"data"] == NSOrderedSame || [filename caseInsensitiveCompare:@"maps"] == NSOrderedSame || [filename caseInsensitiveCompare:@"mp3"] == NSOrderedSame) - [dataDirs addObject:fileURL]; - } - if (dataDirs.count < 3) - return; - self.dataDirsInDocuments = dataDirs; - - auto moveDataButton = [UIButton buttonWithType:UIButtonTypeSystem]; - [moveDataButton setTitle:@"Move data to shared dir" forState:UIControlStateNormal]; - [moveDataButton addTarget:self action:@selector(moveDataToSharedDir:) forControlEvents:UIControlEventTouchUpInside]; - [self.view addSubview:moveDataButton]; - - moveDataButton.translatesAutoresizingMaskIntoConstraints = NO; - [NSLayoutConstraint activateConstraints:@[ - [moveDataButton.centerXAnchor constraintEqualToAnchor:self.view.centerXAnchor], - [moveDataButton.topAnchor constraintEqualToAnchor:startServerButton.bottomAnchor constant:10], - ]]; -} - -- (void)startServer:(UIButton *)button -{ - button.enabled = NO; - [NSThread detachNewThreadWithBlock:^{ - NSThread.currentThread.name = @"CVCMIServer"; - CVCMIServer::create(); - dispatch_sync(dispatch_get_main_queue(), ^{ - button.enabled = YES; - }); - }]; -} - -- (void)moveDataToSharedDir:(UIButton *)button -{ - [button removeFromSuperview]; - dispatch_async(dispatch_get_global_queue(QOS_CLASS_USER_INITIATED, 0), ^{ - auto fm = NSFileManager.defaultManager; - auto destinationURL = sharedGameDataURL(); - [fm createDirectoryAtURL:destinationURL withIntermediateDirectories:YES attributes:nil error:nullptr]; - for (NSURL *dirURL in self.dataDirsInDocuments) - [fm moveItemAtURL:dirURL toURL:[destinationURL URLByAppendingPathComponent:dirURL.lastPathComponent] error:nullptr]; - }); -} - -@end - - -@interface AppDelegate : UIResponder -@property (nonatomic, strong) UIWindow *window; -@end - -@implementation AppDelegate - -- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions -{ - self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds]; - self.window.rootViewController = [ViewController new]; - [self.window makeKeyAndVisible]; - - return YES; -} - -@end - - -int main(int argc, char * argv[]) -{ - @autoreleasepool - { - return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class])); - } -} From de054795324b0b8aa000d7afaa8c305c6e48c1ff Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 26 Jul 2022 16:16:37 +0300 Subject: [PATCH 073/131] Revert "attempt to run server in a separate app" This reverts commit 99fe55b295ad95033626c15011cfe49779269156. --- client/CServerHandler.cpp | 25 +++++++++++++++++++++++-- server/CVCMIServer.cpp | 25 +++++++++++++++++++------ server/CVCMIServer.h | 4 +++- 3 files changed, 45 insertions(+), 9 deletions(-) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index f4904c26c..39024dc1b 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -23,7 +23,10 @@ #ifdef VCMI_ANDROID #include "../lib/CAndroidVMHelper.h" -#elif !defined(VCMI_IOS) +#elif defined(VCMI_IOS) +#include "../server/CVCMIServer.h" +// todo ios +#else #include "../lib/Interprocess.h" #endif #include "../lib/CConfigHandler.h" @@ -182,7 +185,18 @@ void CServerHandler::startLocalServerAndConnect() envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true); } #elif defined(VCMI_IOS) - // todo ios + // todo ios: hide keyboard + logNetwork->info("[ios] create server thread"); + boost::condition_variable cond; + threadRunLocalServer = std::make_shared([&cond, this] { + setThreadName("CVCMIServer"); + CVCMIServer::create(&cond); + // todo ios copypaste + threadRunLocalServer.reset(); + CSH->campaignServerRestartLock.setn(false); + }); +// threadRunLocalServer->detach(); + logNetwork->info("[ios] detach server thread"); #else threadRunLocalServer = std::make_shared(&CServerHandler::threadRunServer, this); //runs server executable; #endif @@ -201,6 +215,13 @@ void CServerHandler::startLocalServerAndConnect() androidTestServerReadyFlag = false; #elif defined(VCMI_IOS) // todo ios + { + boost::mutex m; + boost::unique_lock lock{m}; + logNetwork->info("[ios] wait for server"); + cond.wait(lock); + logNetwork->info("[ios] server ready"); + } #else if(shm) shm->sr->waitTillReady(); diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index 142bac68c..c646d8afa 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -112,8 +112,8 @@ public: } }; -std::string NAME_AFFIX = "server"; -std::string NAME = GameConstants::VCMI_VERSION + std::string(" (") + NAME_AFFIX + ')'; +std::string SERVER_NAME_AFFIX = "server"; +std::string SERVER_NAME = GameConstants::VCMI_VERSION + std::string(" (") + SERVER_NAME_AFFIX + ')'; CVCMIServer::CVCMIServer(boost::program_options::variables_map & opts) : port(3030), io(std::make_shared()), state(EServerState::LOBBY), cmdLineOptions(opts), currentClientId(1), currentPlayerId(1), restartGameplay(false) @@ -291,7 +291,7 @@ void CVCMIServer::connectionAccepted(const boost::system::error_code & ec) try { logNetwork->info("We got a new connection! :)"); - auto c = std::make_shared(upcomingConnection, NAME, uuid); + auto c = std::make_shared(upcomingConnection, SERVER_NAME, uuid); upcomingConnection.reset(); connections.insert(c); c->handler = std::make_shared(&CVCMIServer::threadHandleClient, this, c); @@ -918,9 +918,14 @@ int main(int argc, char * argv[]) console = new CConsoleHandler(); CBasicLogConfigurator logConfig(VCMIDirs::get().userLogsPath() / "VCMI_Server_log.txt", console); logConfig.configureDefault(); - logGlobal->info(NAME); + logGlobal->info(SERVER_NAME); - boost::program_options::variables_map opts; + boost::program_options::variables_map opts; +#ifdef VCMI_IOS + argc = 1; + boost::condition_variable * cond = reinterpret_cast(argv[1]); + cond->notify_one(); +#else handleCommandOptions(argc, argv, opts); preinitDLL(console); settings.init(); @@ -928,6 +933,7 @@ int main(int argc, char * argv[]) loadDLLClasses(); srand((ui32)time(nullptr)); +#endif try { boost::asio::io_service io_service; @@ -967,10 +973,17 @@ int main(int argc, char * argv[]) return 0; } -#if defined(VCMI_ANDROID) || defined(VCMI_IOS) +#ifdef VCMI_ANDROID void CVCMIServer::create() { const char * foo[1] = {"android-server"}; main(1, const_cast(foo)); } +#elif defined(VCMI_IOS) +void CVCMIServer::create(boost::condition_variable * cond) +{ + const auto executablePath = VCMIDirs::get().serverPath(); + void *argv[] = {const_cast(executablePath.c_str()), cond}; + main(2, reinterpret_cast(argv)); +} #endif diff --git a/server/CVCMIServer.h b/server/CVCMIServer.h index 1ec212581..80c5b9f39 100644 --- a/server/CVCMIServer.h +++ b/server/CVCMIServer.h @@ -106,7 +106,9 @@ public: ui8 getIdOfFirstUnallocatedPlayer() const; -#if defined(VCMI_ANDROID) || defined(VCMI_IOS) +#ifdef VCMI_ANDROID static void create(); +#elif defined(VCMI_IOS) + static void create(boost::condition_variable * cond); #endif }; From 24a5dd797c6181adc4dcb4830575a9f95e4df984 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 26 Jul 2022 17:39:07 +0300 Subject: [PATCH 074/131] fix starting local server --- client/CServerHandler.cpp | 2 +- server/CVCMIServer.cpp | 13 ++++++++----- 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index 39024dc1b..cc9c8c477 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -195,7 +195,7 @@ void CServerHandler::startLocalServerAndConnect() threadRunLocalServer.reset(); CSH->campaignServerRestartLock.setn(false); }); -// threadRunLocalServer->detach(); + threadRunLocalServer->detach(); logNetwork->info("[ios] detach server thread"); #else threadRunLocalServer = std::make_shared(&CServerHandler::threadRunServer, this); //runs server executable; diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index c646d8afa..cfc2e1da2 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -855,6 +855,7 @@ void handleLinuxSignal(int sig) static void handleCommandOptions(int argc, char * argv[], boost::program_options::variables_map & options) { +#ifndef VCMI_IOS namespace po = boost::program_options; po::options_description opts("Allowed options"); opts.add_options() @@ -897,6 +898,7 @@ static void handleCommandOptions(int argc, char * argv[], boost::program_options std::cout << VCMIDirs::get().genHelpString(); exit(0); } +#endif } #ifdef VCMI_IOS @@ -921,11 +923,6 @@ int main(int argc, char * argv[]) logGlobal->info(SERVER_NAME); boost::program_options::variables_map opts; -#ifdef VCMI_IOS - argc = 1; - boost::condition_variable * cond = reinterpret_cast(argv[1]); - cond->notify_one(); -#else handleCommandOptions(argc, argv, opts); preinitDLL(console); settings.init(); @@ -933,7 +930,13 @@ int main(int argc, char * argv[]) loadDLLClasses(); srand((ui32)time(nullptr)); + +#ifdef VCMI_IOS + argc = 1; + boost::condition_variable * cond = reinterpret_cast(argv[1]); + cond->notify_one(); #endif + try { boost::asio::io_service io_service; From 7f3baf6831609bc06b7da05c9fcde6026ca0e636 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 27 Jul 2022 13:30:14 +0300 Subject: [PATCH 075/131] require fullscreen and only landscape on iPad --- client/ios/Info.plist | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/client/ios/Info.plist b/client/ios/Info.plist index c81867289..0fa924919 100644 --- a/client/ios/Info.plist +++ b/client/ios/Info.plist @@ -45,18 +45,15 @@ armv7 opengles-2 + UIRequiresFullScreen + + UIStatusBarHidden + UISupportedInterfaceOrientations UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight - UISupportedInterfaceOrientations~ipad - - UIInterfaceOrientationLandscapeLeft - UIInterfaceOrientationLandscapeRight - UIInterfaceOrientationPortrait - UIInterfaceOrientationPortraitUpsideDown - UIUserInterfaceStyle Light From 342a859a3fc3e71a34c3402e8e67b778377b3034 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 28 Jul 2022 12:29:39 +0300 Subject: [PATCH 076/131] fix typo --- client/CServerHandler.cpp | 2 +- server/CVCMIServer.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index cc9c8c477..e408a37be 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -79,7 +79,7 @@ public: bool applyOnLobbyHandler(CServerHandler * handler, void * pack) const override { T * ptr = static_cast(pack); - logNetwork->trace("\tImmidiately apply on lobby: %s", typeList.getTypeInfo(ptr)->name()); + logNetwork->trace("\tImmediately apply on lobby: %s", typeList.getTypeInfo(ptr)->name()); return ptr->applyOnLobbyHandler(handler); } diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index cfc2e1da2..2bccd81df 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -370,7 +370,7 @@ void CVCMIServer::announcePack(std::unique_ptr pack) { for(auto c : connections) { - // FIXME: we need to avoid senting something to client that not yet get answer for LobbyClientConnected + // FIXME: we need to avoid sending something to client that not yet get answer for LobbyClientConnected // Until UUID set we only pass LobbyClientConnected to this client if(c->uuid == uuid && !dynamic_cast(pack.get())) continue; From b7bc8495d8dd86d8b25f5f2b643d6a471ce9516e Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 28 Jul 2022 12:31:26 +0300 Subject: [PATCH 077/131] remove copy-paste --- client/CServerHandler.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index e408a37be..e3f1127c3 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -231,10 +231,11 @@ void CServerHandler::startLocalServerAndConnect() th->update(); //put breakpoint here to attach to server before it does something stupid #if !defined(VCMI_ANDROID) && !defined(VCMI_IOS) - justConnectToServer(settings["server"]["server"].String(), shm ? shm->sr->port : 0); + const ui16 port = shm ? shm->sr->port : 0; #else - justConnectToServer(settings["server"]["server"].String()); + const ui16 port = 0; #endif + justConnectToServer(settings["server"]["server"].String(), port); logNetwork->trace("\tConnecting to the server: %d ms", th->getDiff()); } From cd4b68c034f1ef53cd27c2e81d14b886fa06406c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 28 Jul 2022 12:40:06 +0300 Subject: [PATCH 078/131] fix repeated launches of single player now server actually terminates --- client/CServerHandler.cpp | 2 +- server/CVCMIServer.cpp | 22 ++++++++++++++-------- server/CVCMIServer.h | 2 +- 3 files changed, 16 insertions(+), 10 deletions(-) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index e3f1127c3..d2bc4218a 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -190,7 +190,7 @@ void CServerHandler::startLocalServerAndConnect() boost::condition_variable cond; threadRunLocalServer = std::make_shared([&cond, this] { setThreadName("CVCMIServer"); - CVCMIServer::create(&cond); + CVCMIServer::create(&cond, uuid); // todo ios copypaste threadRunLocalServer.reset(); CSH->campaignServerRestartLock.setn(false); diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index 2bccd81df..1598c78f1 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -855,8 +855,11 @@ void handleLinuxSignal(int sig) static void handleCommandOptions(int argc, char * argv[], boost::program_options::variables_map & options) { -#ifndef VCMI_IOS namespace po = boost::program_options; +#ifdef VCMI_IOS + options.emplace("run-by-client", po::variable_value{true, true}); + options.emplace("uuid", po::variable_value{std::string{argv[1]}, true}); +#else po::options_description opts("Allowed options"); opts.add_options() ("help,h", "display help and exit") @@ -878,8 +881,11 @@ static void handleCommandOptions(int argc, char * argv[], boost::program_options std::cerr << "Failure during parsing command-line options:\n" << e.what() << std::endl; } } +#endif po::notify(options); + +#ifndef VCMI_IOS if(options.count("help")) { auto time = std::time(0); @@ -916,7 +922,6 @@ int main(int argc, char * argv[]) signal(SIGSEGV, handleLinuxSignal); #endif - // todo ios: double console log in single-process mode. Why removing the lines below breaks connecting to local server?! console = new CConsoleHandler(); CBasicLogConfigurator logConfig(VCMIDirs::get().userLogsPath() / "VCMI_Server_log.txt", console); logConfig.configureDefault(); @@ -932,8 +937,7 @@ int main(int argc, char * argv[]) srand((ui32)time(nullptr)); #ifdef VCMI_IOS - argc = 1; - boost::condition_variable * cond = reinterpret_cast(argv[1]); + boost::condition_variable * cond = reinterpret_cast(argv[0]); cond->notify_one(); #endif @@ -983,10 +987,12 @@ void CVCMIServer::create() main(1, const_cast(foo)); } #elif defined(VCMI_IOS) -void CVCMIServer::create(boost::condition_variable * cond) +void CVCMIServer::create(boost::condition_variable * cond, const std::string & uuid) { - const auto executablePath = VCMIDirs::get().serverPath(); - void *argv[] = {const_cast(executablePath.c_str()), cond}; - main(2, reinterpret_cast(argv)); + const std::initializer_list argv = { + cond, + uuid.c_str(), + }; + main(argv.size(), reinterpret_cast(const_cast(argv.begin()))); } #endif diff --git a/server/CVCMIServer.h b/server/CVCMIServer.h index 80c5b9f39..55ad15542 100644 --- a/server/CVCMIServer.h +++ b/server/CVCMIServer.h @@ -109,6 +109,6 @@ public: #ifdef VCMI_ANDROID static void create(); #elif defined(VCMI_IOS) - static void create(boost::condition_variable * cond); + static void create(boost::condition_variable * cond, const std::string & uuid); #endif }; From ad256cd11f3b2a92ae7fdd3365e8a40abc6cc85b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 29 Jul 2022 09:52:39 +0300 Subject: [PATCH 079/131] fix building launcher --- configure_ios.sh | 4 ++-- launcher/CMakeLists.txt | 7 ++++++- launcher/StdInc.h | 2 ++ launcher/jsonutils.cpp | 4 ++++ launcher/jsonutils.h | 4 ++++ launcher/modManager/cmodlist.h | 4 ++++ 6 files changed, 22 insertions(+), 3 deletions(-) diff --git a/configure_ios.sh b/configure_ios.sh index c57500617..ea469a570 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -2,7 +2,7 @@ platform=OS64 globalPrefix=~/dev/vcmi/vcmi-ios-depends/build/iphoneos -qtDir=~/dev/Qt-libs/5.15.2/ios +qtDir=~/dev/Qt-libs/5.15.5/ios10-widgets if [[ "$1" ]]; then platform=SIMULATOR64 globalPrefix=~/dev/vcmi/vcmi-ios-depends/build/iphonesimulator @@ -24,7 +24,7 @@ cmake "$srcDir" -G Xcode \ -DBUNDLE_IDENTIFIER_PREFIX=com.kambala \ -Wno-dev \ -DCMAKE_CXX_COMPILER_LAUNCHER=ccache \ - -DCMAKE_TOOLCHAIN_FILE="$srcDir/ios.toolchain.cmake" \ + --toolchain "$srcDir/ios.toolchain.cmake" \ -DPLATFORM=$platform \ -DDEPLOYMENT_TARGET=12.0 \ -DENABLE_BITCODE=OFF \ diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index 0d3bcebbb..2d2880511 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -123,7 +123,12 @@ if(APPLE_IOS) set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") endif() -target_link_libraries(vcmilauncher vcmi Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network) +if(BUILD_SINGLE_APP) + set(VCMI_LIB_TARGET vcmi_lib_client) +else() + set(VCMI_LIB_TARGET vcmi) +endif() +target_link_libraries(vcmilauncher ${VCMI_LIB_TARGET} Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network) target_include_directories(vcmilauncher PUBLIC ${CMAKE_CURRENT_SOURCE_DIR} ) diff --git a/launcher/StdInc.h b/launcher/StdInc.h index dcaee354c..e97483820 100644 --- a/launcher/StdInc.h +++ b/launcher/StdInc.h @@ -10,6 +10,8 @@ #include #include +VCMI_LIB_USING_NAMESPACE + inline QString pathToQString(const boost::filesystem::path & path) { #ifdef VCMI_WINDOWS diff --git a/launcher/jsonutils.cpp b/launcher/jsonutils.cpp index fb2c66834..ccf7bd629 100644 --- a/launcher/jsonutils.cpp +++ b/launcher/jsonutils.cpp @@ -51,6 +51,8 @@ static JsonMap VariantToMap(QVariantMap variant) return map; } +VCMI_LIB_NAMESPACE_BEGIN + namespace JsonUtils { @@ -123,3 +125,5 @@ void JsonToFile(QString filename, QVariant object) } } + +VCMI_LIB_NAMESPACE_END diff --git a/launcher/jsonutils.h b/launcher/jsonutils.h index 09425b48f..6dd7e7bbf 100644 --- a/launcher/jsonutils.h +++ b/launcher/jsonutils.h @@ -12,6 +12,8 @@ #include #include "../lib/JsonNode.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace JsonUtils { QVariant toVariant(const JsonNode & node); @@ -20,3 +22,5 @@ QVariant JsonFromFile(QString filename); JsonNode toJson(QVariant object); void JsonToFile(QString filename, QVariant object); } + +VCMI_LIB_NAMESPACE_END diff --git a/launcher/modManager/cmodlist.h b/launcher/modManager/cmodlist.h index 2bce79c6d..88e9043bb 100644 --- a/launcher/modManager/cmodlist.h +++ b/launcher/modManager/cmodlist.h @@ -13,8 +13,12 @@ #include #include +VCMI_LIB_NAMESPACE_BEGIN + class JsonNode; +VCMI_LIB_NAMESPACE_END + namespace ModStatus { enum EModStatus From 66425925675472d88bfc3802f7fcdf59ed3b2141 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 3 Aug 2022 10:46:51 +0300 Subject: [PATCH 080/131] install main lib only if it's shared --- cmake_modules/VCMI_lib.cmake | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/cmake_modules/VCMI_lib.cmake b/cmake_modules/VCMI_lib.cmake index f83249f13..9873d3cbf 100644 --- a/cmake_modules/VCMI_lib.cmake +++ b/cmake_modules/VCMI_lib.cmake @@ -494,7 +494,9 @@ macro(add_main_lib TARGET_NAME LIBRARY_TYPE) add_dependencies(${TARGET_NAME} update_version) endif() - install(TARGETS ${TARGET_NAME} RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + if("${LIBRARY_TYPE}" STREQUAL SHARED) + install(TARGETS ${TARGET_NAME} RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + endif() if(APPLE_IOS) get_target_property(LINKED_LIBS ${TARGET_NAME} LINK_LIBRARIES) foreach(LINKED_LIB IN LISTS LINKED_LIBS) From 5e838008df7aae3a2d9587038e58884321b1eddb Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 3 Aug 2022 10:49:04 +0300 Subject: [PATCH 081/131] merge launcher and client launcher is a static lib now --- AI/BattleAI/CMakeLists.txt | 2 +- AI/Nullkiller/CMakeLists.txt | 4 ++-- AI/StupidAI/CMakeLists.txt | 2 +- AI/VCAI/CMakeLists.txt | 2 +- CMakeLists.txt | 6 +++--- client/CMakeLists.txt | 6 ++++-- cmake_modules/VCMI_lib.cmake | 8 ++++---- launcher/CMakeLists.txt | 39 +++++++++--------------------------- 8 files changed, 26 insertions(+), 43 deletions(-) diff --git a/AI/BattleAI/CMakeLists.txt b/AI/BattleAI/CMakeLists.txt index 2e0c13f40..415ec9e79 100644 --- a/AI/BattleAI/CMakeLists.txt +++ b/AI/BattleAI/CMakeLists.txt @@ -38,4 +38,4 @@ target_link_libraries(BattleAI PRIVATE ${VCMI_LIB_TARGET}) vcmi_set_output_dir(BattleAI "AI") enable_pch(BattleAI) -install(TARGETS BattleAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} COMPONENT AI) +install(TARGETS BattleAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) diff --git a/AI/Nullkiller/CMakeLists.txt b/AI/Nullkiller/CMakeLists.txt index bbe7a2126..0ccf0a281 100644 --- a/AI/Nullkiller/CMakeLists.txt +++ b/AI/Nullkiller/CMakeLists.txt @@ -137,7 +137,7 @@ target_link_libraries(Nullkiller PRIVATE TBB::tbb) vcmi_set_output_dir(Nullkiller "AI") enable_pch(Nullkiller) -install(TARGETS Nullkiller RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} COMPONENT AI OPTIONAL) +install(TARGETS Nullkiller RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) if(APPLE_IOS) - install(IMPORTED_RUNTIME_ARTIFACTS TBB::tbb LIBRARY DESTINATION ${LIB_DIR} COMPONENT AI OPTIONAL) # CMake 3.21+ + install(IMPORTED_RUNTIME_ARTIFACTS TBB::tbb LIBRARY DESTINATION ${LIB_DIR}) # CMake 3.21+ endif() diff --git a/AI/StupidAI/CMakeLists.txt b/AI/StupidAI/CMakeLists.txt index efa37ba5d..9230b57c3 100644 --- a/AI/StupidAI/CMakeLists.txt +++ b/AI/StupidAI/CMakeLists.txt @@ -20,4 +20,4 @@ target_include_directories(StupidAI PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) vcmi_set_output_dir(StupidAI "AI") enable_pch(StupidAI) -install(TARGETS StupidAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} COMPONENT AI) +install(TARGETS StupidAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) diff --git a/AI/VCAI/CMakeLists.txt b/AI/VCAI/CMakeLists.txt index 5735eecab..259129afe 100644 --- a/AI/VCAI/CMakeLists.txt +++ b/AI/VCAI/CMakeLists.txt @@ -112,4 +112,4 @@ target_link_libraries(VCAI PRIVATE ${VCMI_LIB_TARGET} fuzzylite::fuzzylite) vcmi_set_output_dir(VCAI "AI") enable_pch(VCAI) -install(TARGETS VCAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR} COMPONENT AI) +install(TARGETS VCAI RUNTIME DESTINATION ${AI_LIB_DIR} LIBRARY DESTINATION ${AI_LIB_DIR}) diff --git a/CMakeLists.txt b/CMakeLists.txt index 32196fd76..1feb37be6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -425,12 +425,12 @@ else() add_subdirectory(lib) endif() -add_subdirectory(client) -add_subdirectory(server) -add_subdirectory_with_folder("AI" AI) if(ENABLE_LAUNCHER) add_subdirectory(launcher) endif() +add_subdirectory(client) +add_subdirectory(server) +add_subdirectory_with_folder("AI" AI) if(ENABLE_TEST) enable_testing() add_subdirectory(test) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index b56e75a16..6a32dba15 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -226,6 +226,9 @@ endif() if(BUILD_SINGLE_APP) target_link_libraries(vcmiclient PRIVATE vcmiserver) + if(ENABLE_LAUNCHER) + target_link_libraries(vcmiclient PRIVATE vcmilauncher) + endif() set(VCMI_LIB_TARGET vcmi_lib_client) else() set(VCMI_LIB_TARGET vcmi) @@ -250,8 +253,7 @@ enable_pch(vcmiclient) if(APPLE_IOS) add_custom_command(TARGET vcmiclient POST_BUILD - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component core --prefix "$" - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component AI --prefix "$" + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh ) else() diff --git a/cmake_modules/VCMI_lib.cmake b/cmake_modules/VCMI_lib.cmake index 9873d3cbf..ec688e307 100644 --- a/cmake_modules/VCMI_lib.cmake +++ b/cmake_modules/VCMI_lib.cmake @@ -495,14 +495,14 @@ macro(add_main_lib TARGET_NAME LIBRARY_TYPE) endif() if("${LIBRARY_TYPE}" STREQUAL SHARED) - install(TARGETS ${TARGET_NAME} RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + install(TARGETS ${TARGET_NAME} RUNTIME DESTINATION ${LIB_DIR} LIBRARY DESTINATION ${LIB_DIR}) endif() if(APPLE_IOS) get_target_property(LINKED_LIBS ${TARGET_NAME} LINK_LIBRARIES) foreach(LINKED_LIB IN LISTS LINKED_LIBS) if(NOT TARGET ${LINKED_LIB}) if(LINKED_LIB MATCHES "\\${CMAKE_SHARED_LIBRARY_SUFFIX}$") - install(FILES ${LINKED_LIB} DESTINATION ${LIB_DIR} COMPONENT core) + install(FILES ${LINKED_LIB} DESTINATION ${LIB_DIR}) endif() continue() endif() @@ -526,13 +526,13 @@ macro(add_main_lib TARGET_NAME LIBRARY_TYPE) foreach(BOOST_DEPENDENCY IN LISTS BOOST_DEPENDENCIES) get_target_property(BOOST_DEPENDENCY_TYPE ${BOOST_DEPENDENCY} TYPE) if(BOOST_DEPENDENCY_TYPE STREQUAL "SHARED_LIBRARY") - install(IMPORTED_RUNTIME_ARTIFACTS ${BOOST_DEPENDENCY} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + install(IMPORTED_RUNTIME_ARTIFACTS ${BOOST_DEPENDENCY} LIBRARY DESTINATION ${LIB_DIR}) endif() endforeach() else() set(INSTALL_TYPE TARGETS) endif() - install(${INSTALL_TYPE} ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR} COMPONENT core) + install(${INSTALL_TYPE} ${LINKED_LIB_REAL} LIBRARY DESTINATION ${LIB_DIR}) endforeach() endif() endmacro() diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index 2d2880511..e1cebc975 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -80,7 +80,11 @@ if(WIN32) set(launcher_ICON VCMI_launcher.rc) endif() -add_executable(vcmilauncher WIN32 ${launcher_SRCS} ${launcher_HEADERS} ${launcher_UI_HEADERS} ${launcher_ICON}) +if(BUILD_SINGLE_APP) + add_library(vcmilauncher STATIC ${launcher_SRCS} ${launcher_HEADERS} ${launcher_UI_HEADERS}) +else() + add_executable(vcmilauncher WIN32 ${launcher_SRCS} ${launcher_HEADERS} ${launcher_UI_HEADERS} ${launcher_ICON}) +endif() if(WIN32) set_target_properties(vcmilauncher @@ -102,26 +106,6 @@ if(APPLE) # This makes Xcode project prettier by moving vcmilauncher_autogen directory into vcmiclient subfolder set_property(GLOBAL PROPERTY AUTOGEN_TARGETS_FOLDER vcmilauncher) endif() -if(APPLE_IOS) - set(CMAKE_EXE_LINKER_FLAGS ${CMAKE_EXE_LINKER_FLAGS} "-Wl,-e,_qt_main_wrapper") - - set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) - configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) - - set_target_properties(vcmilauncher PROPERTIES - MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" - XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" - XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED "$(CODE_SIGNING_ALLOWED_FOR_APPS)" - XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon - XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} - ) - - target_sources(vcmilauncher PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) - set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") - - target_sources(vcmilauncher PRIVATE ios/Images.xcassets) - set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") -endif() if(BUILD_SINGLE_APP) set(VCMI_LIB_TARGET vcmi_lib_client) @@ -136,13 +120,10 @@ vcmi_set_output_dir(vcmilauncher "") enable_pch(vcmilauncher) if(APPLE_IOS) - install(DIRECTORY icons DESTINATION ${DATA_DIR} COMPONENT launcher) - add_custom_command(TARGET vcmilauncher POST_BUILD - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component core --prefix "$" - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --component launcher --prefix "$" - COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh - ) + set(ICONS_DESTINATION ${DATA_DIR}) else() + set(ICONS_DESTINATION ${DATA_DIR}/launcher) + # Copy to build directory for easier debugging add_custom_command(TARGET vcmilauncher POST_BUILD COMMAND ${CMAKE_COMMAND} -E remove_directory ${CMAKE_BINARY_DIR}/bin/${CMAKE_CFG_INTDIR}/launcher/icons @@ -150,11 +131,11 @@ else() ) install(TARGETS vcmilauncher DESTINATION ${BIN_DIR}) - # copy whole directory - install(DIRECTORY icons DESTINATION ${DATA_DIR}/launcher) + # Install icons and desktop file on Linux if(NOT WIN32 AND NOT APPLE) install(FILES "vcmilauncher.desktop" DESTINATION share/applications) install(FILES "eu.vcmi.VCMI.metainfo.xml" DESTINATION share/metainfo) endif() endif() +install(DIRECTORY icons DESTINATION ${ICONS_DESTINATION}) From 10a14bd6fdeae8ea7809fb855e33d741f0634ab3 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 3 Aug 2022 10:49:42 +0300 Subject: [PATCH 082/131] remove no longer used iOS launcher files --- launcher/ios/Entitlements.in | 10 -- .../AppIcon.appiconset/Contents.json | 121 ------------------ .../AppIcon.appiconset/Icon-App-20x20@1x.png | Bin 507 -> 0 bytes .../AppIcon.appiconset/Icon-App-20x20@2x.png | Bin 783 -> 0 bytes .../AppIcon.appiconset/Icon-App-20x20@3x.png | Bin 1063 -> 0 bytes .../AppIcon.appiconset/Icon-App-29x29@1x.png | Bin 620 -> 0 bytes .../AppIcon.appiconset/Icon-App-29x29@2x.png | Bin 1047 -> 0 bytes .../AppIcon.appiconset/Icon-App-29x29@3x.png | Bin 1462 -> 0 bytes .../AppIcon.appiconset/Icon-App-40x40@1x.png | Bin 783 -> 0 bytes .../AppIcon.appiconset/Icon-App-40x40@2x.png | Bin 1349 -> 0 bytes .../AppIcon.appiconset/Icon-App-40x40@3x.png | Bin 2058 -> 0 bytes .../AppIcon.appiconset/Icon-App-60x60@2x.png | Bin 2058 -> 0 bytes .../AppIcon.appiconset/Icon-App-60x60@3x.png | Bin 3243 -> 0 bytes .../AppIcon.appiconset/Icon-App-76x76@1x.png | Bin 1283 -> 0 bytes .../AppIcon.appiconset/Icon-App-76x76@2x.png | Bin 2788 -> 0 bytes .../Icon-App-83.5x83.5@2x.png | Bin 3159 -> 0 bytes launcher/ios/Images.xcassets/Contents.json | 6 - launcher/ios/Info.plist | 55 -------- 18 files changed, 192 deletions(-) delete mode 100644 launcher/ios/Entitlements.in delete mode 100755 launcher/ios/Images.xcassets/AppIcon.appiconset/Contents.json delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png delete mode 100644 launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png delete mode 100644 launcher/ios/Images.xcassets/Contents.json delete mode 100644 launcher/ios/Info.plist diff --git a/launcher/ios/Entitlements.in b/launcher/ios/Entitlements.in deleted file mode 100644 index 73367ec6b..000000000 --- a/launcher/ios/Entitlements.in +++ /dev/null @@ -1,10 +0,0 @@ - - - - - com.apple.security.application-groups - - group.@BUNDLE_IDENTIFIER_PREFIX@.vcmi - - - diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Contents.json b/launcher/ios/Images.xcassets/AppIcon.appiconset/Contents.json deleted file mode 100755 index 8122b0a0c..000000000 --- a/launcher/ios/Images.xcassets/AppIcon.appiconset/Contents.json +++ /dev/null @@ -1,121 +0,0 @@ -{ - "images" : [ - { - "filename" : "Icon-App-20x20@2x.png", - "idiom" : "iphone", - "scale" : "2x", - "size" : "20x20" - }, - { - "filename" : "Icon-App-20x20@3x.png", - "idiom" : "iphone", - "scale" : "3x", - "size" : "20x20" - }, - { - "filename" : "Icon-App-29x29@1x.png", - "idiom" : "iphone", - "scale" : "1x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-29x29@2x.png", - "idiom" : "iphone", - "scale" : "2x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-29x29@3x.png", - "idiom" : "iphone", - "scale" : "3x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-40x40@2x.png", - "idiom" : "iphone", - "scale" : "2x", - "size" : "40x40" - }, - { - "filename" : "Icon-App-40x40@3x.png", - "idiom" : "iphone", - "scale" : "3x", - "size" : "40x40" - }, - { - "filename" : "Icon-App-60x60@2x.png", - "idiom" : "iphone", - "scale" : "2x", - "size" : "60x60" - }, - { - "filename" : "Icon-App-60x60@3x.png", - "idiom" : "iphone", - "scale" : "3x", - "size" : "60x60" - }, - { - "filename" : "Icon-App-20x20@1x.png", - "idiom" : "ipad", - "scale" : "1x", - "size" : "20x20" - }, - { - "filename" : "Icon-App-20x20@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "20x20" - }, - { - "filename" : "Icon-App-29x29@1x.png", - "idiom" : "ipad", - "scale" : "1x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-29x29@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "29x29" - }, - { - "filename" : "Icon-App-40x40@1x.png", - "idiom" : "ipad", - "scale" : "1x", - "size" : "40x40" - }, - { - "filename" : "Icon-App-40x40@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "40x40" - }, - { - "filename" : "Icon-App-76x76@1x.png", - "idiom" : "ipad", - "scale" : "1x", - "size" : "76x76" - }, - { - "filename" : "Icon-App-76x76@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "76x76" - }, - { - "filename" : "Icon-App-83.5x83.5@2x.png", - "idiom" : "ipad", - "scale" : "2x", - "size" : "83.5x83.5" - }, - { - "idiom" : "ios-marketing", - "scale" : "1x", - "size" : "1024x1024" - } - ], - "info" : { - "author" : "xcode", - "version" : 1 - } -} diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png deleted file mode 100644 index 488b4844e8063214c8a44f86bac66cb922272761..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 507 zcmV4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0OUzTK~#90ZIHb#L{Sulzq9WMgCI!!m3|}Q1%yt#fLf#SKso4vF0?X%X|LHsW((J;Ufj^xO3AP7)^Ea`TDire+o!TD0% zJ8JATPj)W$EtqMs_BnQcxv@HZn%>@wJ}1KPq0PgUmvLt1c8~hkvJt>AwjYPL9_|{o z^{>I!d((5Hb~U^{EqAi1v_8?APrBl-@1O7@$dQmM<}AYbH=W}%ydaA2#8nWXuWFI3 x^oEagU~(aUHyXXQeYQu0vLnZJLCjQ2{s7MATpsM_v@-wz002ovPDHLkV1hb|<%IwM diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png deleted file mode 100644 index fd9e120456cba1cca6e5c222e1a1aea99208e2cb..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 783 zcmV+q1MvKbP)uk0002eX+uL$Nkc;* zP;zf(X>4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0r*KoK~#90)sjzW6HyR{fAe-XDNU4Wu_diiFenu*+7hW=nuCbwp%M@TFCqv% z_0Xf>&3mC2Q3TPGV6Q^KfX8Z}Q9+GDn>7B35Gqz8((PvV{X8tnCcBlOAUcPIw|sBj z%r_%MXQ4Xe{tM6q0BDK=wf_NxH2mL+6hD`=>e0a$D1n0zfW7GSACY=tU`(w(Rl9q3 zJu@Z%p!g~C@%{F(Zi-){w!WPH44t@Xt9w@m4_Bw+tJ%kFvOb0 z;4B`Xc2t&AT9gvCu|IcB7P3kpkf0vVymV{uKny!8s;Ou|HD*SNjp2rXU{JWhsnXmj zjf;i4C92%q=JlPKJOML~xYZQ|MfaXeCAFTol3RF{Ut#gNb9p$kzEZNwm6972PSnhP zh*nPuJ4QyoE$ZXR_1@)|U71>?XFNgq^<-M&CrH0NO^AY~0SYy?ob}f67Z#VU7YTM; zquG{E-pnT_(=96-`LyWte0j(XbD4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$0}x3>K~#90?N(c8R96&Td*69<@-o7V$ZU=geRvJ{0jpdzIrHKmF{^g~S}D3L&Qnu;}=U}kh;lJTCs`jMH5lDSEv z?T4Dhg>&vbcinZ)+Up#y5YG>N0q!XIH6e#GEdfCKI|2YCL@3$Y{&xh#Qx7D6JPiuK zdH+tiOJaTLGT=#~xVtE7iogDjzFU-vb%i4__Diw1I}&;{h7U_(8B+h6$(A)$E1F35 z9GbB!W!hT1rk+rDJW=T!&A01z9df8Cy}pFQW)Lu98*lBDAmETqx#`m8RpvGgmF zsk--!-(zaRjE=uUZjh{~WDXfJeJ&q!*Uaa>19TnbH8kHR>+ac4)%cb^9k@&ZOyeG&N$Gka&G)2 z!^!A7Du8l&8LVL2&7Z~ONKN6O!eq%}-sbo(f|E<3k8h7Hf&dT_np!krj|;WM7bFIi zN(VYMNC1=&pjcD-&7;*%qveZNIt(@zMvwL_WZjl zGni`w@GRM~7SN!i3TRLPAuv)@%%GZ|JVLyr2jELe4h0R+0O&|U^4};^;w@ocD<=*a z(4aM2$^C_Og@waNGe3;!$l8Fh90J{DkHGw)g#*bV9M0@lE@2svwD5?PNl}_nf9*t2 z3WMDarxOxZJ=0KbL8b@A6Y=^t&VLqjiPHzw1q$S!66JnJu}cwJI63&Q=Kt7L0JC2m hqL`!S_9%H+`~!Pd#=_5Hdc^<$002ovPDHLkV1i*6^;!S` diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png deleted file mode 100644 index b51dd2368c497cdba356989701c5bd00e83885bd..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 620 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 Q-T(jq07*qoM6N<$g6$Nh<^TWy diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png deleted file mode 100644 index fd9e120456cba1cca6e5c222e1a1aea99208e2cb..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 783 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 diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png deleted file mode 100644 index 5496a82ea6de2b33990f93bd46ed463629fe3dff..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2058 zcmV+l2=(`gP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$2J=ZoK~#90?U`$A6xS8U|L4v=yz3VR+Zc?M4VV^CWEvVl;#!4LAi|^$4-+0v zl|s@qZNF5JDphJDNLr~?qDt+DHmD6v)e_9h36Da;qbQ+iL|tKw+8|=tI4LsNV1w7bNXQ)-W~6f-8Gflbk3L6+_`gqbIv{Y%>Ujc!Q_~lB(4p%!8X_i+h7}PgKe-4 z{w#wXmg|_>rGy5G>mWh|0t6K8K6X3tp)u`j?E%V6S93H(EHtrTS->Nq90))mDhxLS zf;kX1s^tP<9|x~@-7F~gO#yBU%##5#hafIz;-C^@U{ud@_alb{WComtR+ke(E!5K3 zX*fh^*0P3h!#`iU#>yz&_EjOU!sR1x`itE(l(&5KoL_i%m?th=9d-p5|HvzGlR@Wy zI!avWtDSx9Qs=M(dTHgtHEyw>CBg2r>~sOBYwn3O3|@E+SbF-7h_Lkkc$W8xeJvli zz5i;BZ)yJX!nfL9R6zcp#fS~TtUm|f(dO=e*?Z+>H&FV=Yj;>I25W=70H=B*?)pl} z{0R8^vU1)13Cg&(H_3iTl~06RpJ25r6~NmEoGo1|Y1aFc*tC zK7}n{a^Q1ofm8ijq^nZLXKoTjAmf#j>Zw|Wrj*h&mTxV;4v-=>dkMPta%}lg$G)W% z&|FFZq%;k15sh0-;|qvTeKA_jMV25_*Qv+Kp&)epRhqM1q6<>7_nSFE05HqH?x7%A~mj&@X!hjAJC)g?8NOY5D1OFJ|fj~#|i<-vIlwr0Q#!M(z!o! zN2q7ds_Nlns80j4yWWGd7fAq!3hsaSAt4A_|3<1ti$xTQN}etN0Mg6ql{9@Ec3E)j zU(b5jI%*nVkSt$}?gJnIg7X)ia54cn+l_+x36)QKpdjp|v35RvcsSy)|MyF3g5#$& zEpSo2hT|Q?5W@cHwNMacwnL^BCiaZxpI*LEWbaMIfY6zXPdoIizyQ{K9#@WmAk_JG zeF+nQU=NU&Yk9@k&qg1$9t9wz@1DPA{1+iTuoBrexG~rbEsp0Odl?_Dymk_T5x z;9!98!R0NEa3Z@30sk;k49bgYCD1scaOv$Q%gp3`(f~son{w&hX5z;CR)pgwULSDV zpK26wY|W#yet^xblImD&l`PtskJoo8#mvl1TI(-2`h-M6 zL#7CT)r%O*YoGwp8D>ZTh!_SCzMmeLu%K3)j~8;BlzQsL+=1`!xS^C%N{t@bQMXJ$ ziu(GA6i8-lro09h1B!-1YIKMcK*aq@`AJLWTXHkyjCW3l#7QM)W6u|Wc|UyXT=S{j zTUWm$rbw{&U;$pfF~VX>XGM*lSh2)IkEbDG&sVk`pISY&K>0do?G1`!AlQ*RQ93B|okTtT~cd#8J6|9|^q8*GDZ zuno4sHrNJFKG=F*{prTBL+S~=^rUI73_TY5q;WXt6d2?x-&~aL)-Z`>=&{gX`>mbl z0nZPNv${9XC?tA|IWtn5M5CY`D(ObYPBPE(djJ3c diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png deleted file mode 100644 index 5d009effd356290dfa8b89196fa77b50a741f317..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 3243 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 diff --git a/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png b/launcher/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@2x.png deleted file mode 100644 index 2e61bb999de08fe13d95c304f70ad4646bb4e378..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2788 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 diff --git a/launcher/ios/Images.xcassets/Contents.json b/launcher/ios/Images.xcassets/Contents.json deleted file mode 100644 index 73c00596a..000000000 --- a/launcher/ios/Images.xcassets/Contents.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "info" : { - "author" : "xcode", - "version" : 1 - } -} diff --git a/launcher/ios/Info.plist b/launcher/ios/Info.plist deleted file mode 100644 index 01c769d73..000000000 --- a/launcher/ios/Info.plist +++ /dev/null @@ -1,55 +0,0 @@ - - - - - CFBundleDevelopmentRegion - en - CFBundleExecutable - $(PRODUCT_NAME) - CFBundleIdentifier - $(PRODUCT_BUNDLE_IDENTIFIER) - CFBundleInfoDictionaryVersion - 6.0 - CFBundleName - VCMI laucher - CFBundlePackageType - APPL - CFBundleShortVersionString - $(MARKETING_VERSION) - CFBundleSignature - ???? - CFBundleVersion - 1 - LSApplicationQueriesSchemes - - vcmi - - LSRequiresIPhoneOS - - NSAppTransportSecurity - - NSAllowsArbitraryLoads - - - UIFileSharingEnabled - - UILaunchStoryboardName - LaunchScreen - UIRequiredDeviceCapabilities - - armv7 - - UISupportedInterfaceOrientations - - UIInterfaceOrientationLandscapeLeft - UIInterfaceOrientationLandscapeRight - - UISupportedInterfaceOrientations~ipad - - UIInterfaceOrientationLandscapeLeft - UIInterfaceOrientationLandscapeRight - UIInterfaceOrientationPortrait - UIInterfaceOrientationPortraitUpsideDown - - - From bb00ec8ce2a14b5a35230140b558e65477ead8f6 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 3 Aug 2022 10:57:27 +0300 Subject: [PATCH 083/131] remove entitlements and shared container usage they're no longer required since we have a single app now --- client/CMakeLists.txt | 4 ---- client/ios/Entitlements.in | 10 ---------- lib/CIOSUtils.h | 6 ------ lib/CIOSUtils.m | 15 --------------- lib/VCMIDirs.cpp | 2 +- 5 files changed, 1 insertion(+), 36 deletions(-) delete mode 100644 client/ios/Entitlements.in diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 6a32dba15..f5d3a90d1 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -206,15 +206,11 @@ elseif(APPLE_IOS) "-weak_framework CoreHaptics" ) - set(ENTITLEMENTS_OUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/VCMI.entitlements) - configure_file(ios/Entitlements.in ${ENTITLEMENTS_OUT_PATH} @ONLY) - set_target_properties(vcmiclient PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_CURRENT_LIST_DIR}/ios/Info.plist" XCODE_ATTRIBUTE_LD_RUNPATH_SEARCH_PATHS "@executable_path/Frameworks" XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED "$(CODE_SIGNING_ALLOWED_FOR_APPS)" XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon - XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS ${ENTITLEMENTS_OUT_PATH} ) target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) diff --git a/client/ios/Entitlements.in b/client/ios/Entitlements.in deleted file mode 100644 index 73367ec6b..000000000 --- a/client/ios/Entitlements.in +++ /dev/null @@ -1,10 +0,0 @@ - - - - - com.apple.security.application-groups - - group.@BUNDLE_IDENTIFIER_PREFIX@.vcmi - - - diff --git a/lib/CIOSUtils.h b/lib/CIOSUtils.h index 3b5bd3e80..1eb34cab6 100644 --- a/lib/CIOSUtils.h +++ b/lib/CIOSUtils.h @@ -22,12 +22,6 @@ extern "C" { extern const char *ios_documentsPath(); extern const char *ios_cachesPath(); -#ifdef __OBJC__ -NSURL *sharedContainerURL(); -NSURL *sharedGameDataURL(); -#endif -extern const char *ios_sharedDataPath(); - #if TARGET_OS_SIMULATOR extern const char *ios_hostApplicationSupportPath(); #endif diff --git a/lib/CIOSUtils.m b/lib/CIOSUtils.m index 27e291642..905e5d62c 100644 --- a/lib/CIOSUtils.m +++ b/lib/CIOSUtils.m @@ -21,21 +21,6 @@ static const char *standardPath(NSSearchPathDirectory directory) { return standa const char *ios_documentsPath() { return standardPath(NSDocumentDirectory); } const char *ios_cachesPath() { return standardPath(NSCachesDirectory); } -NSURL *sharedContainerURL() -{ - static NSURL *sharedPathURL; - static dispatch_once_t onceToken; - dispatch_once(&onceToken, ^{ - __auto_type bundleID = NSBundle.mainBundle.bundleIdentifier; - __auto_type lastDotPos = [bundleID rangeOfString:@"." options:NSBackwardsSearch].location; - __auto_type groupID = [NSString stringWithFormat:@"group.%@.vcmi", [bundleID substringToIndex:lastDotPos]]; - sharedPathURL = [NSFileManager.defaultManager containerURLForSecurityApplicationGroupIdentifier:groupID]; - }); - return sharedPathURL; -} -NSURL *sharedGameDataURL() { return [sharedContainerURL() URLByAppendingPathComponent:@"GameData"]; } -const char *ios_sharedDataPath() { return sharedGameDataURL().fileSystemRepresentation; } - #if TARGET_OS_SIMULATOR const char *ios_hostApplicationSupportPath() { diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index 87b2abd50..1086a6955 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -392,7 +392,7 @@ class VCMIDirsIOS final : public VCMIDirsApple bfs::path binaryPath() const override; }; -bfs::path VCMIDirsIOS::userDataPath() const { return {ios_sharedDataPath() ?: ios_documentsPath()}; } +bfs::path VCMIDirsIOS::userDataPath() const { return {ios_documentsPath()}; } bfs::path VCMIDirsIOS::userCachePath() const { return {ios_cachesPath()}; } bfs::path VCMIDirsIOS::userLogsPath() const { return {ios_documentsPath()}; } From f43d33372135a3e2378defcee59514f08c226cf7 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 3 Aug 2022 15:37:10 +0300 Subject: [PATCH 084/131] add UIApplicationSupportsIndirectInputEvents to Info.plist --- client/ios/Info.plist | 2 ++ 1 file changed, 2 insertions(+) diff --git a/client/ios/Info.plist b/client/ios/Info.plist index 0fa924919..7088cc78a 100644 --- a/client/ios/Info.plist +++ b/client/ios/Info.plist @@ -36,6 +36,8 @@ NSAllowsArbitraryLoads + UIApplicationSupportsIndirectInputEvents + UIFileSharingEnabled UILaunchStoryboardName From 352358b493e120c942d097630e918dc570fda17c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 4 Aug 2022 13:31:46 +0300 Subject: [PATCH 085/131] move launch storyboard to iOS subdirectory --- client/CMakeLists.txt | 4 ++-- client/{ => ios}/LaunchScreen.storyboard | 0 2 files changed, 2 insertions(+), 2 deletions(-) rename client/{ => ios}/LaunchScreen.storyboard (100%) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index f5d3a90d1..414778732 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -213,8 +213,8 @@ elseif(APPLE_IOS) XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon ) - target_sources(vcmiclient PRIVATE ${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard) - set_source_files_properties(${CMAKE_SOURCE_DIR}/client/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") + target_sources(vcmiclient PRIVATE ios/LaunchScreen.storyboard) + set_source_files_properties(ios/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") target_sources(vcmiclient PRIVATE ios/Images.xcassets) set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") diff --git a/client/LaunchScreen.storyboard b/client/ios/LaunchScreen.storyboard similarity index 100% rename from client/LaunchScreen.storyboard rename to client/ios/LaunchScreen.storyboard From 86e4edf71f4eb7ae6f2c1f886e5e0ec6da0b46fe Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 4 Aug 2022 13:31:53 +0300 Subject: [PATCH 086/131] remove no longer used script --- package_ios.sh | 34 ---------------------------------- 1 file changed, 34 deletions(-) delete mode 100755 package_ios.sh diff --git a/package_ios.sh b/package_ios.sh deleted file mode 100755 index ec3dadf1b..000000000 --- a/package_ios.sh +++ /dev/null @@ -1,34 +0,0 @@ -#!/usr/bin/env bash - -pushd bin/Debug -mkdir -p vcmiclient.app/Frameworks - -productsDir=$(pwd) -sdl2Path=~/dev/ios/vcmi-ios-deps/SDL2-lib/lib -for app in vcmiclient vcmiserver; do - install_name_tool -rpath "$sdl2Path" '@executable_path/Frameworks' "$productsDir/$app.app/$app" -done - -cp *.dylib AI/*.dylib "$sdl2Path/libSDL2.dylib" vcmiclient.app -cd vcmiclient.app - -for b in vcmiclient *.dylib; do - for l in minizip vcmi; do - libName="lib${l}.dylib" - install_name_tool -change "$productsDir/$libName" "@rpath/$libName" "$b" - done - if [ "$b" != vcmiclient ]; then - install_name_tool -id "@rpath/$b" "$b" - fi -done - -mv -f *.dylib Frameworks -popd - -cp -R bin/Debug-iphoneos/* "$productsDir/vcmiclient.app" -cp -fR "$productsDir/vcmiclient.app/Frameworks" "$productsDir/vcmiserver.app" - -for l in minizip vcmi; do - libName="lib${l}.dylib" - install_name_tool -change "$productsDir/$libName" "@rpath/$libName" "$productsDir/vcmiserver.app/vcmiserver" -done From ba9ace46ad8d541e2cae3af2c062b12fd5fd3ab9 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 4 Aug 2022 15:55:01 +0300 Subject: [PATCH 087/131] fix compiling storyboard without the need to edit generated xcodeproj manually --- client/CMakeLists.txt | 4 ++++ configure_ios.sh | 6 ------ 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 414778732..8553bf8f3 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -215,6 +215,10 @@ elseif(APPLE_IOS) target_sources(vcmiclient PRIVATE ios/LaunchScreen.storyboard) set_source_files_properties(ios/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") + # workaround to prevent CMAKE_SKIP_PRECOMPILE_HEADERS being added as compile flag + if(CMAKE_VERSION VERSION_GREATER_EQUAL "3.22.0") + set_source_files_properties(ios/LaunchScreen.storyboard PROPERTIES LANGUAGE CXX) + endif() target_sources(vcmiclient PRIVATE ios/Images.xcassets) set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") diff --git a/configure_ios.sh b/configure_ios.sh index ea469a570..c57632bd6 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -33,9 +33,3 @@ cmake "$srcDir" -G Xcode \ -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY='Apple Development' \ -DCMAKE_XCODE_ATTRIBUTE_DEVELOPMENT_TEAM='4XHN44TEVG' # -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED=NO - -# workaround strange cmake bug that adds compile flag to resources -sed -i '' \ - -e 's|\.storyboard \*/; settings = {COMPILER_FLAGS = "-DCMAKE_SKIP_PRECOMPILE_HEADERS "; };|.storyboard */;|g' \ - -e 's|\.xcassets \*/; settings = {COMPILER_FLAGS = "-DCMAKE_SKIP_PRECOMPILE_HEADERS "; };|.xcassets */;|g' \ - VCMI.xcodeproj/project.pbxproj From 1e01780d170efdb6fdadf56fda2ac00eb6617c47 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 5 Aug 2022 14:32:29 +0300 Subject: [PATCH 088/131] start app with launcher, start SDL from launcher kambala-decapitator/vcmi#33 --- client/CMT.cpp | 10 +++- client/CMakeLists.txt | 6 ++- client/ios/AppDelegate.h | 18 +++++++ client/ios/AppDelegate.mm | 49 ++++++++++++++++++ client/ios/main.m | 17 +++++++ client/ios/startSDL.h | 12 +++++ client/ios/{SDL_uikit_main.mm => startSDL.mm} | 50 +++++++++++-------- launcher/CMakeLists.txt | 5 +- launcher/ios/mainwindow_moc.mm | 29 ++++++++--- launcher/main.cpp | 4 ++ launcher/main.h | 19 +++++++ 11 files changed, 186 insertions(+), 33 deletions(-) create mode 100644 client/ios/AppDelegate.h create mode 100644 client/ios/AppDelegate.mm create mode 100644 client/ios/main.m create mode 100644 client/ios/startSDL.h rename client/ios/{SDL_uikit_main.mm => startSDL.mm} (76%) create mode 100644 launcher/main.h diff --git a/client/CMT.cpp b/client/CMT.cpp index 0e792dc62..dca3bbff9 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -159,7 +159,7 @@ static void SDLLogCallback(void* userdata, #if defined(VCMI_WINDOWS) && !defined(__GNUC__) && defined(VCMI_WITH_DEBUG_CONSOLE) int wmain(int argc, wchar_t* argv[]) -#elif defined(VCMI_ANDROID) +#elif defined(VCMI_IOS) || defined(VCMI_ANDROID) int SDL_main(int argc, char *argv[]) #else int main(int argc, char * argv[]) @@ -217,12 +217,20 @@ int main(int argc, char * argv[]) if(vm.count("help")) { prog_help(opts); +#ifdef VCMI_IOS + exit(0); +#else return 0; +#endif } if(vm.count("version")) { prog_version(); +#ifdef VCMI_IOS + exit(0); +#else return 0; +#endif } // Init old logging system and new (temporary) logging system diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 8553bf8f3..7fdbc6a35 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -148,12 +148,16 @@ set(client_HEADERS if(APPLE_IOS) set(client_SRCS ${client_SRCS} CFocusableHelper.cpp + ios/AppDelegate.mm ios/GameChatKeyboardHanlder.m - ios/SDL_uikit_main.mm + ios/main.m + ios/startSDL.mm ) set(client_HEADERS ${client_HEADERS} CFocusableHelper.h + ios/AppDelegate.h ios/GameChatKeyboardHanlder.h + ios/startSDL.h ) endif() diff --git a/client/ios/AppDelegate.h b/client/ios/AppDelegate.h new file mode 100644 index 000000000..022afccd1 --- /dev/null +++ b/client/ios/AppDelegate.h @@ -0,0 +1,18 @@ +/* + * AppDelegate.h, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#import + +NS_ASSUME_NONNULL_BEGIN + +@interface AppDelegate : UIResponder +@property (nonatomic, strong) UIWindow *window; +@end + +NS_ASSUME_NONNULL_END diff --git a/client/ios/AppDelegate.mm b/client/ios/AppDelegate.mm new file mode 100644 index 000000000..01a9169ee --- /dev/null +++ b/client/ios/AppDelegate.mm @@ -0,0 +1,49 @@ +/* + * AppDelegate.mm, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#import "AppDelegate.h" + +#include "startSDL.h" +#include "../launcher/main.h" + +#include + +@implementation AppDelegate + +- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { + self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds]; + self.window.rootViewController = [UIViewController new]; + [self.window makeKeyAndVisible]; + + [NSNotificationCenter.defaultCenter addObserverForName:@"StartGame" object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + [self startMainFunc:startSDL]; + }]; + return YES; +} + +- (void)applicationDidBecomeActive:(UIApplication *)application { + static dispatch_once_t onceToken; + dispatch_once(&onceToken, ^{ + [self startMainFunc:qt_main]; + }); +} + +#pragma mark - Private + +- (void)startMainFunc:(int(*)(int argc, char * argv[]))mainPtr { + auto args = NSProcessInfo.processInfo.arguments; + std::vector argv; + argv.reserve(args.count); + for (NSString *arg in args) + argv.push_back(const_cast(arg.UTF8String)); + + mainPtr(argv.size(), argv.data()); +} + +@end diff --git a/client/ios/main.m b/client/ios/main.m new file mode 100644 index 000000000..3843d8532 --- /dev/null +++ b/client/ios/main.m @@ -0,0 +1,17 @@ +/* + * main.m, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#import "AppDelegate.h" + +int main(int argc, char * argv[]) +{ + @autoreleasepool { + return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class])); + } +} diff --git a/client/ios/startSDL.h b/client/ios/startSDL.h new file mode 100644 index 000000000..9d6212d18 --- /dev/null +++ b/client/ios/startSDL.h @@ -0,0 +1,12 @@ +/* + * startSDL.h, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#pragma once + +int startSDL(int argc, char * argv[]); diff --git a/client/ios/SDL_uikit_main.mm b/client/ios/startSDL.mm similarity index 76% rename from client/ios/SDL_uikit_main.mm rename to client/ios/startSDL.mm index b1faee21b..48999a337 100644 --- a/client/ios/SDL_uikit_main.mm +++ b/client/ios/startSDL.mm @@ -1,12 +1,17 @@ /* - SDL_uikit_main.c, placed in the public domain by Sam Lantinga 3/18/2019 -*/ - -/* Include the SDL main definition header */ + * startSDL.mm, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ #include #include #include +#include #include "../Global.h" #include "CMT.h" @@ -17,8 +22,8 @@ #import -double ios_screenScale() { return UIScreen.mainScreen.nativeScale; } +double ios_screenScale() { return UIScreen.mainScreen.nativeScale; } @interface SDLViewObserver : NSObject @property (nonatomic, strong) GameChatKeyboardHanlder * gameChatHandler; @@ -117,23 +122,24 @@ double ios_screenScale() { return UIScreen.mainScreen.nativeScale; } @end -#ifdef main -#undef main -#endif - -int -main(int argc, char *argv[]) +int startSDL(int argc, char * argv[]) { - @autoreleasepool - { - auto observer = [SDLViewObserver new]; + @autoreleasepool { + auto observer = [SDLViewObserver new]; observer.gameChatHandler = [GameChatKeyboardHanlder new]; - [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { - [UIApplication.sharedApplication.keyWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; - }]; - [NSNotificationCenter.defaultCenter addObserverForName:UITextFieldTextDidEndEditingNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { - removeFocusFromActiveInput(); - }]; - return SDL_UIKitRunApp(argc, argv, SDL_main); - } + [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + [UIApplication.sharedApplication.keyWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; + }]; + [NSNotificationCenter.defaultCenter addObserverForName:UITextFieldTextDidEndEditingNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + removeFocusFromActiveInput(); + }]; + + // copied from -[SDLUIKitDelegate postFinishLaunch] + SDL_SetMainReady(); + SDL_iOSSetEventPump(SDL_TRUE); + auto result = SDL_main(argc, argv); + SDL_iOSSetEventPump(SDL_FALSE); + + return result; + } } diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index e1cebc975..d43209e5a 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -43,6 +43,7 @@ set(launcher_HEADERS launcherdirs.h jsonutils.h updatedialog_moc.h + main.h ) set(launcher_FORMS @@ -54,7 +55,9 @@ set(launcher_FORMS ) if(APPLE_IOS) - set(launcher_SRCS ${launcher_SRCS} ios/mainwindow_moc.mm) + list(APPEND launcher_SRCS + ios/mainwindow_moc.mm + ) endif() assign_source_group(${launcher_SRCS} ${launcher_HEADERS} VCMI_launcher.rc) diff --git a/launcher/ios/mainwindow_moc.mm b/launcher/ios/mainwindow_moc.mm index 7dd80c9fb..b99b9d707 100644 --- a/launcher/ios/mainwindow_moc.mm +++ b/launcher/ios/mainwindow_moc.mm @@ -10,16 +10,29 @@ #include "../mainwindow_moc.h" +#include +#include + #import void MainWindow::startExecutable(QString /*name*/) { - NSString * vcmiScheme = NSBundle.mainBundle.infoDictionary[@"LSApplicationQueriesSchemes"][0]; - [UIApplication.sharedApplication openURL:[NSURL URLWithString:[vcmiScheme stringByAppendingString:@":"]] options:@{} completionHandler:^(BOOL success) { - if (success) - return; - auto alert = [UIAlertController alertControllerWithTitle:@"Can't open VCMI client" message:nil preferredStyle:UIAlertControllerStyleAlert]; - [alert addAction:[UIAlertAction actionWithTitle:@"OK" style:UIAlertActionStyleDefault handler:nil]]; - [UIApplication.sharedApplication.keyWindow.rootViewController presentViewController:alert animated:YES completion:nil]; - }]; + qApp->quit(); + [NSNotificationCenter.defaultCenter postNotificationName:@"StartGame" object:nil]; +} + +void showQtWindow() +{ + auto app = UIApplication.sharedApplication; + auto qtNativeWindowIndex = [app.windows indexOfObjectPassingTest:^BOOL(__kindof UIWindow * _Nonnull window, NSUInteger idx, BOOL * _Nonnull stop) { + return [NSStringFromClass([window class]) isEqualToString:@"QUIWindow"]; + }]; + Q_ASSERT(qtNativeWindowIndex != NSNotFound); + + auto qtWindow = qApp->topLevelWindows()[0]; + auto qtWindowNativeView = (__bridge UIView*)reinterpret_cast(qtWindow->winId()); + + auto qtNativeWindow = app.windows[qtNativeWindowIndex]; + [qtNativeWindow.rootViewController.view addSubview:qtWindowNativeView]; + [qtNativeWindow makeKeyAndVisible]; } diff --git a/launcher/main.cpp b/launcher/main.cpp index 5bfa2467b..41ebabe7d 100644 --- a/launcher/main.cpp +++ b/launcher/main.cpp @@ -10,11 +10,15 @@ #include #include "StdInc.h" #include "mainwindow_moc.h" +#include "main.h" int main(int argc, char * argv[]) { QApplication vcmilauncher(argc, argv); MainWindow mainWindow; mainWindow.show(); +#ifdef Q_OS_IOS + showQtWindow(); +#endif return vcmilauncher.exec(); } diff --git a/launcher/main.h b/launcher/main.h new file mode 100644 index 000000000..43754309c --- /dev/null +++ b/launcher/main.h @@ -0,0 +1,19 @@ +/* + * main.h, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#pragma once + +#include + +#ifdef Q_OS_IOS +void showQtWindow(); + +#define main qt_main +#endif +int main(int argc, char * argv[]); From 74ba228961b2fd0ca6ae33bbdc0d71940ffe4fc4 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 6 Aug 2022 15:28:23 +0300 Subject: [PATCH 089/131] ignore window events: no need to refresh screen --- client/CMT.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/client/CMT.cpp b/client/CMT.cpp index dca3bbff9..d211d6d89 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -1411,7 +1411,9 @@ static void handleEvent(SDL_Event & ev) { switch (ev.window.event) { case SDL_WINDOWEVENT_RESTORED: +#ifndef VCMI_IOS fullScreenChanged(); +#endif break; } return; From d1131556340fa7b7feeace0040ed14d73292bd8f Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 6 Aug 2022 16:19:46 +0300 Subject: [PATCH 090/131] use best scale quality --- client/CMT.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/client/CMT.cpp b/client/CMT.cpp index d211d6d89..eac7bad39 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -1108,6 +1108,7 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn #ifdef VCMI_IOS SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); SDL_SetHint(SDL_HINT_RETURN_KEY_HIDES_IME, "1"); + SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "best"); Uint32 windowFlags = SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI; if(!createWindow(windowFlags | SDL_WINDOW_METAL)) From 1c17ad25850dd032f7a8b8345148e70d55dfe126 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 6 Aug 2022 16:21:49 +0300 Subject: [PATCH 091/131] remove locking light mode --- client/ios/Info.plist | 2 -- 1 file changed, 2 deletions(-) diff --git a/client/ios/Info.plist b/client/ios/Info.plist index 7088cc78a..153c44960 100644 --- a/client/ios/Info.plist +++ b/client/ios/Info.plist @@ -56,7 +56,5 @@ UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight - UIUserInterfaceStyle - Light From 89f14ea58674771e6906764134e5ee5075120adb Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sat, 6 Aug 2022 17:51:48 +0300 Subject: [PATCH 092/131] improve setting window resolution fix kambala-decapitator/vcmi#3 --- client/CMT.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/client/CMT.cpp b/client/CMT.cpp index eac7bad39..da184f672 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -1036,7 +1036,9 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn if (displayIndex < 0) displayIndex = 0; } -#ifndef VCMI_IOS +#ifdef VCMI_IOS + SDL_GetWindowSize(mainWindow, &w, &h); +#else if(!checkVideoMode(displayIndex, w, h)) { logGlobal->error("Error: SDL says that %dx%d resolution is not available!", w, h); From fab3216df0839594984941b503a048b8de71813b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 7 Aug 2022 08:58:04 +0300 Subject: [PATCH 093/131] add setting to control app launch type: launcher or game - removes custom AppDelegate - now starting launcher using qt_main_wrapper - when starting SDL from launcher, SDLUIKitDelegate is created and assigned as app delegate fix kambala-decapitator/vcmi#33 --- client/CMakeLists.txt | 22 +++++---- client/ios/AppDelegate.h | 18 ------- client/ios/AppDelegate.mm | 49 ------------------- client/ios/Settings.bundle/Root.plist | 31 ++++++++++++ .../ios/Settings.bundle/en.lproj/Root.strings | 3 ++ .../ios/Settings.bundle/ru.lproj/Root.strings | 3 ++ client/ios/main.m | 39 +++++++++++++-- client/ios/startSDL.h | 9 +++- client/ios/startSDL.mm | 17 ++++--- launcher/CMakeLists.txt | 2 +- launcher/ios/main.m | 28 +++++++++++ launcher/ios/mainwindow_moc.mm | 38 -------------- launcher/main.cpp | 19 ++++--- launcher/main.h | 9 +--- launcher/mainwindow_moc.cpp | 4 ++ launcher/mainwindow_moc.h | 2 + 16 files changed, 153 insertions(+), 140 deletions(-) delete mode 100644 client/ios/AppDelegate.h delete mode 100644 client/ios/AppDelegate.mm create mode 100644 client/ios/Settings.bundle/Root.plist create mode 100644 client/ios/Settings.bundle/en.lproj/Root.strings create mode 100644 client/ios/Settings.bundle/ru.lproj/Root.strings create mode 100644 launcher/ios/main.m delete mode 100644 launcher/ios/mainwindow_moc.mm diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 7fdbc6a35..012b6d8cf 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -148,14 +148,12 @@ set(client_HEADERS if(APPLE_IOS) set(client_SRCS ${client_SRCS} CFocusableHelper.cpp - ios/AppDelegate.mm ios/GameChatKeyboardHanlder.m ios/main.m ios/startSDL.mm ) set(client_HEADERS ${client_HEADERS} CFocusableHelper.h - ios/AppDelegate.h ios/GameChatKeyboardHanlder.h ios/startSDL.h ) @@ -217,15 +215,19 @@ elseif(APPLE_IOS) XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon ) - target_sources(vcmiclient PRIVATE ios/LaunchScreen.storyboard) - set_source_files_properties(ios/LaunchScreen.storyboard PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") - # workaround to prevent CMAKE_SKIP_PRECOMPILE_HEADERS being added as compile flag - if(CMAKE_VERSION VERSION_GREATER_EQUAL "3.22.0") - set_source_files_properties(ios/LaunchScreen.storyboard PROPERTIES LANGUAGE CXX) - endif() + foreach(XCODE_RESOURCE LaunchScreen.storyboard Images.xcassets Settings.bundle) + set(XCODE_RESOURCE_PATH ios/${XCODE_RESOURCE}) + target_sources(vcmiclient PRIVATE ${XCODE_RESOURCE_PATH}) + set_source_files_properties(${XCODE_RESOURCE_PATH} PROPERTIES MACOSX_PACKAGE_LOCATION Resources) - target_sources(vcmiclient PRIVATE ios/Images.xcassets) - set_source_files_properties(ios/Images.xcassets PROPERTIES MACOSX_PACKAGE_LOCATION "Resources") + # workaround to prevent CMAKE_SKIP_PRECOMPILE_HEADERS being added as compile flag + # add max version condition when https://gitlab.kitware.com/cmake/cmake/-/issues/23821 is fixed + if(CMAKE_VERSION VERSION_GREATER_EQUAL "3.22.0") + set_source_files_properties(${XCODE_RESOURCE_PATH} PROPERTIES LANGUAGE CXX) + endif() + endforeach() + + set(CMAKE_EXE_LINKER_FLAGS "-Wl,-e,_client_main") endif() if(BUILD_SINGLE_APP) diff --git a/client/ios/AppDelegate.h b/client/ios/AppDelegate.h deleted file mode 100644 index 022afccd1..000000000 --- a/client/ios/AppDelegate.h +++ /dev/null @@ -1,18 +0,0 @@ -/* - * AppDelegate.h, part of VCMI engine - * - * Authors: listed in file AUTHORS in main folder - * - * License: GNU General Public License v2.0 or later - * Full text of license available in license.txt file, in main folder - * - */ -#import - -NS_ASSUME_NONNULL_BEGIN - -@interface AppDelegate : UIResponder -@property (nonatomic, strong) UIWindow *window; -@end - -NS_ASSUME_NONNULL_END diff --git a/client/ios/AppDelegate.mm b/client/ios/AppDelegate.mm deleted file mode 100644 index 01a9169ee..000000000 --- a/client/ios/AppDelegate.mm +++ /dev/null @@ -1,49 +0,0 @@ -/* - * AppDelegate.mm, part of VCMI engine - * - * Authors: listed in file AUTHORS in main folder - * - * License: GNU General Public License v2.0 or later - * Full text of license available in license.txt file, in main folder - * - */ -#import "AppDelegate.h" - -#include "startSDL.h" -#include "../launcher/main.h" - -#include - -@implementation AppDelegate - -- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { - self.window = [[UIWindow alloc] initWithFrame:UIScreen.mainScreen.bounds]; - self.window.rootViewController = [UIViewController new]; - [self.window makeKeyAndVisible]; - - [NSNotificationCenter.defaultCenter addObserverForName:@"StartGame" object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { - [self startMainFunc:startSDL]; - }]; - return YES; -} - -- (void)applicationDidBecomeActive:(UIApplication *)application { - static dispatch_once_t onceToken; - dispatch_once(&onceToken, ^{ - [self startMainFunc:qt_main]; - }); -} - -#pragma mark - Private - -- (void)startMainFunc:(int(*)(int argc, char * argv[]))mainPtr { - auto args = NSProcessInfo.processInfo.arguments; - std::vector argv; - argv.reserve(args.count); - for (NSString *arg in args) - argv.push_back(const_cast(arg.UTF8String)); - - mainPtr(argv.size(), argv.data()); -} - -@end diff --git a/client/ios/Settings.bundle/Root.plist b/client/ios/Settings.bundle/Root.plist new file mode 100644 index 000000000..747935f4d --- /dev/null +++ b/client/ios/Settings.bundle/Root.plist @@ -0,0 +1,31 @@ + + + + + StringsTable + Root + PreferenceSpecifiers + + + Type + PSRadioGroupSpecifier + Title + LaunchType + Key + LaunchType + DefaultValue + 0 + Values + + 0 + 1 + + Titles + + Launcher + Game + + + + + diff --git a/client/ios/Settings.bundle/en.lproj/Root.strings b/client/ios/Settings.bundle/en.lproj/Root.strings new file mode 100644 index 000000000..4348ab181 --- /dev/null +++ b/client/ios/Settings.bundle/en.lproj/Root.strings @@ -0,0 +1,3 @@ +"LaunchType" = "App start type"; +"Launcher" = "Launcher"; +"Game" = "Game"; diff --git a/client/ios/Settings.bundle/ru.lproj/Root.strings b/client/ios/Settings.bundle/ru.lproj/Root.strings new file mode 100644 index 000000000..8661a436c --- /dev/null +++ b/client/ios/Settings.bundle/ru.lproj/Root.strings @@ -0,0 +1,3 @@ +"LaunchType" = "Тип запуска приложения"; +"Launcher" = "Конфигурация (лаунчер)"; +"Game" = "Игра"; diff --git a/client/ios/main.m b/client/ios/main.m index 3843d8532..018725e3d 100644 --- a/client/ios/main.m +++ b/client/ios/main.m @@ -7,11 +7,44 @@ * Full text of license available in license.txt file, in main folder * */ -#import "AppDelegate.h" +#import "startSDL.h" -int main(int argc, char * argv[]) +#import + +#import + +static void startSDLManually(int argc, char * argv[]) { + id appDelegate; @autoreleasepool { - return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class])); + __auto_type sdlAppDelegateClass = NSClassFromString(@"SDLUIKitDelegate"); + NSCAssert(sdlAppDelegateClass != nil, @"SDL AppDelegate class doesn't exist"); + NSCAssert(class_conformsToProtocol(sdlAppDelegateClass, @protocol(UIApplicationDelegate)), @"SDL AppDelegate doesn't conform to UIApplicationDelegate"); + appDelegate = [sdlAppDelegateClass new]; + } + UIApplication.sharedApplication.delegate = appDelegate; + + int result = startSDL(argc, argv, YES); + exit(result); +} + +int qt_main_wrapper(int argc, char * argv[]); + +int client_main(int argc, char * argv[]) +{ + NSInteger launchType; + @autoreleasepool { + launchType = [NSUserDefaults.standardUserDefaults integerForKey:@"LaunchType"]; + } + if (launchType == 1) + return startSDL(argc, argv, NO); + + @autoreleasepool { + id __block startGameObserver = [NSNotificationCenter.defaultCenter addObserverForName:@"StartGame" object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + [NSNotificationCenter.defaultCenter removeObserver:startGameObserver]; + startGameObserver = nil; + startSDLManually(argc, argv); + }]; + return qt_main_wrapper(argc, argv); } } diff --git a/client/ios/startSDL.h b/client/ios/startSDL.h index 9d6212d18..abd7419b5 100644 --- a/client/ios/startSDL.h +++ b/client/ios/startSDL.h @@ -9,4 +9,11 @@ */ #pragma once -int startSDL(int argc, char * argv[]); +#ifdef __OBJC__ +#include +#endif + +#ifdef __cplusplus +extern "C" +#endif +int startSDL(int argc, char * argv[], BOOL startManually); diff --git a/client/ios/startSDL.mm b/client/ios/startSDL.mm index 48999a337..ba0f0fd96 100644 --- a/client/ios/startSDL.mm +++ b/client/ios/startSDL.mm @@ -7,18 +7,18 @@ * Full text of license available in license.txt file, in main folder * */ -#include - -#include -#include -#include +#import "startSDL.h" +#import "GameChatKeyboardHanlder.h" #include "../Global.h" #include "CMT.h" #include "CServerHandler.h" #include "CFocusableHelper.h" -#import "GameChatKeyboardHanlder.h" +#include +#include +#include +#include #import @@ -122,7 +122,7 @@ double ios_screenScale() { return UIScreen.mainScreen.nativeScale; } @end -int startSDL(int argc, char * argv[]) +int startSDL(int argc, char * argv[], BOOL startManually) { @autoreleasepool { auto observer = [SDLViewObserver new]; @@ -134,6 +134,9 @@ int startSDL(int argc, char * argv[]) removeFocusFromActiveInput(); }]; + if (!startManually) + return SDL_UIKitRunApp(argc, argv, SDL_main); + // copied from -[SDLUIKitDelegate postFinishLaunch] SDL_SetMainReady(); SDL_iOSSetEventPump(SDL_TRUE); diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index d43209e5a..7042f0fec 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -56,7 +56,7 @@ set(launcher_FORMS if(APPLE_IOS) list(APPEND launcher_SRCS - ios/mainwindow_moc.mm + ios/main.m ) endif() diff --git a/launcher/ios/main.m b/launcher/ios/main.m new file mode 100644 index 000000000..3db701feb --- /dev/null +++ b/launcher/ios/main.m @@ -0,0 +1,28 @@ +/* + * main.m, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#import + +void launchGame(int argc, char * argv[]) { + @autoreleasepool { + __auto_type app = UIApplication.sharedApplication; + __auto_type qtNativeWindowIndex = [app.windows indexOfObjectPassingTest:^BOOL(__kindof UIWindow * _Nonnull window, NSUInteger idx, BOOL * _Nonnull stop) { + return [NSStringFromClass([window class]) isEqualToString:@"QUIWindow"]; + }]; + NSCAssert(qtNativeWindowIndex != NSNotFound, @"Qt native window doesn't exist"); + + __auto_type qtNativeWindow = app.windows[qtNativeWindowIndex]; + qtNativeWindow.hidden = YES; + [qtNativeWindow.rootViewController.view removeFromSuperview]; + qtNativeWindow.rootViewController = nil; + if (@available(iOS 13.0, *)) + qtNativeWindow.windowScene = nil; + } + [NSNotificationCenter.defaultCenter postNotificationName:@"StartGame" object:nil]; +} diff --git a/launcher/ios/mainwindow_moc.mm b/launcher/ios/mainwindow_moc.mm deleted file mode 100644 index b99b9d707..000000000 --- a/launcher/ios/mainwindow_moc.mm +++ /dev/null @@ -1,38 +0,0 @@ -/* - * mainwindow_moc.mm, part of VCMI engine - * - * Authors: listed in file AUTHORS in main folder - * - * License: GNU General Public License v2.0 or later - * Full text of license available in license.txt file, in main folder - * - */ - -#include "../mainwindow_moc.h" - -#include -#include - -#import - -void MainWindow::startExecutable(QString /*name*/) -{ - qApp->quit(); - [NSNotificationCenter.defaultCenter postNotificationName:@"StartGame" object:nil]; -} - -void showQtWindow() -{ - auto app = UIApplication.sharedApplication; - auto qtNativeWindowIndex = [app.windows indexOfObjectPassingTest:^BOOL(__kindof UIWindow * _Nonnull window, NSUInteger idx, BOOL * _Nonnull stop) { - return [NSStringFromClass([window class]) isEqualToString:@"QUIWindow"]; - }]; - Q_ASSERT(qtNativeWindowIndex != NSNotFound); - - auto qtWindow = qApp->topLevelWindows()[0]; - auto qtWindowNativeView = (__bridge UIView*)reinterpret_cast(qtWindow->winId()); - - auto qtNativeWindow = app.windows[qtNativeWindowIndex]; - [qtNativeWindow.rootViewController.view addSubview:qtWindowNativeView]; - [qtNativeWindow makeKeyAndVisible]; -} diff --git a/launcher/main.cpp b/launcher/main.cpp index 41ebabe7d..343bc85a5 100644 --- a/launcher/main.cpp +++ b/launcher/main.cpp @@ -7,18 +7,25 @@ * Full text of license available in license.txt file, in main folder * */ -#include -#include "StdInc.h" -#include "mainwindow_moc.h" #include "main.h" +#include "mainwindow_moc.h" + +#include int main(int argc, char * argv[]) { + int result; +#ifdef VCMI_IOS + { +#endif QApplication vcmilauncher(argc, argv); MainWindow mainWindow; mainWindow.show(); -#ifdef Q_OS_IOS - showQtWindow(); + result = vcmilauncher.exec(); +#ifdef VCMI_IOS + } + if (result == 0) + launchGame(argc, argv); #endif - return vcmilauncher.exec(); + return result; } diff --git a/launcher/main.h b/launcher/main.h index 43754309c..8c77747d2 100644 --- a/launcher/main.h +++ b/launcher/main.h @@ -9,11 +9,6 @@ */ #pragma once -#include - -#ifdef Q_OS_IOS -void showQtWindow(); - -#define main qt_main +#ifdef VCMI_IOS +extern "C" void launchGame(int argc, char * argv[]); #endif -int main(int argc, char * argv[]); diff --git a/launcher/mainwindow_moc.cpp b/launcher/mainwindow_moc.cpp index 84edd9c52..82769300f 100644 --- a/launcher/mainwindow_moc.cpp +++ b/launcher/mainwindow_moc.cpp @@ -103,7 +103,11 @@ MainWindow::~MainWindow() void MainWindow::on_startGameButton_clicked() { +#ifdef Q_OS_IOS + qApp->quit(); +#else startExecutable(pathToQString(VCMIDirs::get().clientPath())); +#endif } #ifndef Q_OS_IOS diff --git a/launcher/mainwindow_moc.h b/launcher/mainwindow_moc.h index ce7c9d625..3ca4d9327 100644 --- a/launcher/mainwindow_moc.h +++ b/launcher/mainwindow_moc.h @@ -27,7 +27,9 @@ class MainWindow : public QMainWindow private: Ui::MainWindow * ui; void load(); +#ifndef Q_OS_IOS void startExecutable(QString name); +#endif public: explicit MainWindow(QWidget * parent = 0); From 5f24307ac8b4ab90c2da2ab2a9e67ba6c0c170be Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 7 Aug 2022 09:31:56 +0300 Subject: [PATCH 094/131] fix observing SDL window's view creation on iOS 15 also improves observers handling fix kambala-decapitator/vcmi#38 --- client/ios/startSDL.mm | 33 ++++++++++++++++++++++----------- 1 file changed, 22 insertions(+), 11 deletions(-) diff --git a/client/ios/startSDL.mm b/client/ios/startSDL.mm index ba0f0fd96..f6969c384 100644 --- a/client/ios/startSDL.mm +++ b/client/ios/startSDL.mm @@ -32,6 +32,8 @@ double ios_screenScale() { return UIScreen.mainScreen.nativeScale; } @implementation SDLViewObserver - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context { + [object removeObserver:self forKeyPath:keyPath]; + UIView * view = [object valueForKeyPath:keyPath]; UITextField * textField; @@ -127,22 +129,31 @@ int startSDL(int argc, char * argv[], BOOL startManually) @autoreleasepool { auto observer = [SDLViewObserver new]; observer.gameChatHandler = [GameChatKeyboardHanlder new]; - [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { - [UIApplication.sharedApplication.keyWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; + + id __block sdlWindowCreationObserver = [NSNotificationCenter.defaultCenter addObserverForName:UIWindowDidBecomeKeyNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + [NSNotificationCenter.defaultCenter removeObserver:sdlWindowCreationObserver]; + sdlWindowCreationObserver = nil; + + UIWindow * sdlWindow = note.object; + [sdlWindow.rootViewController addObserver:observer forKeyPath:NSStringFromSelector(@selector(view)) options:NSKeyValueObservingOptionNew context:NULL]; }]; - [NSNotificationCenter.defaultCenter addObserverForName:UITextFieldTextDidEndEditingNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { + id textFieldObserver = [NSNotificationCenter.defaultCenter addObserverForName:UITextFieldTextDidEndEditingNotification object:nil queue:nil usingBlock:^(NSNotification * _Nonnull note) { removeFocusFromActiveInput(); }]; - if (!startManually) - return SDL_UIKitRunApp(argc, argv, SDL_main); - - // copied from -[SDLUIKitDelegate postFinishLaunch] - SDL_SetMainReady(); - SDL_iOSSetEventPump(SDL_TRUE); - auto result = SDL_main(argc, argv); - SDL_iOSSetEventPump(SDL_FALSE); + int result; + if (startManually) + { + // copied from -[SDLUIKitDelegate postFinishLaunch] + SDL_SetMainReady(); + SDL_iOSSetEventPump(SDL_TRUE); + result = SDL_main(argc, argv); + SDL_iOSSetEventPump(SDL_FALSE); + } + else + result = SDL_UIKitRunApp(argc, argv, SDL_main); + [NSNotificationCenter.defaultCenter removeObserver:textFieldObserver]; return result; } } From 7d8f09c6d40c3c7a369761b89bbfffcc9a12e3bf Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 7 Aug 2022 09:48:10 +0300 Subject: [PATCH 095/131] add overriding launch type via environment variable VCMI_LAUNCH_TYPE --- client/ios/main.m | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/client/ios/main.m b/client/ios/main.m index 018725e3d..dbba2cef3 100644 --- a/client/ios/main.m +++ b/client/ios/main.m @@ -13,6 +13,8 @@ #import +#include + static void startSDLManually(int argc, char * argv[]) { id appDelegate; @@ -33,8 +35,13 @@ int qt_main_wrapper(int argc, char * argv[]); int client_main(int argc, char * argv[]) { NSInteger launchType; - @autoreleasepool { - launchType = [NSUserDefaults.standardUserDefaults integerForKey:@"LaunchType"]; + __auto_type envVar = getenv("VCMI_LAUNCH_TYPE"); + if (envVar) + launchType = envVar[0] == '0' ? 0 : 1; + else { + @autoreleasepool { + launchType = [NSUserDefaults.standardUserDefaults integerForKey:@"LaunchType"]; + } } if (launchType == 1) return startSDL(argc, argv, NO); From 2a958a346e2b3a8dbd2b85c9c05b34237c4a9dc7 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 8 Aug 2022 17:37:16 +0300 Subject: [PATCH 096/131] don't build Nullkiller for 32-bit --- AI/Nullkiller/CMakeLists.txt | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/AI/Nullkiller/CMakeLists.txt b/AI/Nullkiller/CMakeLists.txt index 0ccf0a281..39d4adee0 100644 --- a/AI/Nullkiller/CMakeLists.txt +++ b/AI/Nullkiller/CMakeLists.txt @@ -127,6 +127,12 @@ if(ANDROID) # android compiles ai libs into main lib directly, so we skip this l endif() add_library(Nullkiller SHARED ${Nullkiller_SRCS} ${Nullkiller_HEADERS}) +if(APPLE_IOS) + # Nullkiller dependencies - TBB and LuaJIT - can only be built for 64-bit + set_target_properties(Nullkiller PROPERTIES + XCODE_ATTRIBUTE_EXCLUDED_ARCHS "$(ARCHS_STANDARD_32_BIT)" + ) +endif() target_include_directories(Nullkiller PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) From 1bb6a20b769ceca2c57f63ee1e8e680f2bab1d82 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 8 Aug 2022 17:38:57 +0300 Subject: [PATCH 097/131] get rid of the custom toolchain --- CMakeLists.txt | 30 +- client/CMakeLists.txt | 5 + configure_ios.sh | 26 +- ios.toolchain.cmake | 1014 ----------------------------------------- 4 files changed, 24 insertions(+), 1051 deletions(-) delete mode 100644 ios.toolchain.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 1feb37be6..7d5789772 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -157,19 +157,27 @@ set(CMAKE_MAP_IMPORTED_CONFIG_MINSIZEREL MinSizeRel Release RelWithDebInfo "") # Release falls back to RelWithDebInfo, then MinSizeRel set(CMAKE_MAP_IMPORTED_CONFIG_RELEASE Release RelWithDebInfo MinSizeRel "") +set(CMAKE_XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC YES) +set(CMAKE_XCODE_ATTRIBUTE_DEBUG_INFORMATION_FORMAT[variant=Debug] dwarf) +set(CMAKE_XCODE_ATTRIBUTE_ENABLE_BITCODE NO) +set(CMAKE_XCODE_ATTRIBUTE_MARKETING_VERSION ${APP_SHORT_VERSION}) +set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH NO) +set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH[variant=Debug] YES) + if(APPLE_IOS) set(CMAKE_MACOSX_RPATH 1) + set(CMAKE_OSX_DEPLOYMENT_TARGET 10.0) + + list(APPEND CMAKE_FIND_ROOT_PATH "${CMAKE_PREFIX_PATH}") # required for Boost + set(CMAKE_FIND_USE_CMAKE_ENVIRONMENT_PATH FALSE) + set(CMAKE_FIND_USE_SYSTEM_ENVIRONMENT_PATH FALSE) + set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED NO) set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED_FOR_APPS YES) - set(CMAKE_XCODE_ATTRIBUTE_MARKETING_VERSION ${APP_SHORT_VERSION}) set(CMAKE_XCODE_ATTRIBUTE_PRODUCT_BUNDLE_IDENTIFIER "${BUNDLE_IDENTIFIER_PREFIX}.$(PRODUCT_NAME)") - set(SYSTEM_LIBS ${SYSTEM_LIBS} iconv) # boost.locale + set(CMAKE_XCODE_ATTRIBUTE_TARGETED_DEVICE_FAMILY "1,2") endif(APPLE_IOS) -if(CMAKE_GENERATOR STREQUAL Xcode) - set(CMAKE_XCODE_ATTRIBUTE_DEBUG_INFORMATION_FORMAT[variant=Debug] dwarf) -endif() - if(MINGW OR MSVC) # Windows Vista or newer for FuzzyLite 6 to compile add_definitions(-D_WIN32_WINNT=0x0600) @@ -245,11 +253,6 @@ if(CMAKE_COMPILER_IS_GNUCXX OR NOT WIN32) #so far all *nix compilers support suc endif() endif() -if(APPLE_IOS) - set(CMAKE_XCODE_ATTRIBUTE_TARGETED_DEVICE_FAMILY "1,2") # iPhone + iPad - set(CMAKE_XCODE_ATTRIBUTE_GCC_WARN_64_TO_32_BIT_CONVERSION "NO") -endif(APPLE_IOS) - # Check if some platform-specific libraries are needed for linking if(NOT WIN32 AND NOT APPLE_IOS) include(CheckLibraryExists) @@ -278,11 +281,6 @@ if(TARGET zlib::zlib) add_library(ZLIB::ZLIB ALIAS zlib::zlib) endif() -# TODO: needed only for device+simulator -# if(APPLE_IOS) -# set(ZLIB_LIBRARIES "-lz") -# endif() - set(FFMPEG_COMPONENTS avutil swscale avformat avcodec) if(APPLE_IOS) list(APPEND FFMPEG_COMPONENTS swresample) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 012b6d8cf..90f279776 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -247,6 +247,11 @@ if(ffmpeg_LIBRARIES) target_link_libraries(vcmiclient PRIVATE ${ffmpeg_LIBRARIES} ) + if(APPLE_IOS) + target_link_libraries(vcmiclient PRIVATE + iconv + ) + endif() else() target_compile_definitions(vcmiclient PRIVATE DISABLE_VIDEO) endif() diff --git a/configure_ios.sh b/configure_ios.sh index c57632bd6..a27ef6c33 100755 --- a/configure_ios.sh +++ b/configure_ios.sh @@ -1,34 +1,18 @@ #!/usr/bin/env bash -platform=OS64 -globalPrefix=~/dev/vcmi/vcmi-ios-depends/build/iphoneos -qtDir=~/dev/Qt-libs/5.15.5/ios10-widgets +prefixPath=~/dev/vcmi/vcmi-ios-depends/build/iphoneos if [[ "$1" ]]; then - platform=SIMULATOR64 - globalPrefix=~/dev/vcmi/vcmi-ios-depends/build/iphonesimulator + prefixPath=~/dev/vcmi/vcmi-ios-depends/build/iphonesimulator fi -prefixPath="$globalPrefix;$qtDir" -# prefixPath="$boostPrefix;$sdlLibsDir" -# xcodeMajorVersion=$(xcodebuild -version | fgrep Xcode | cut -d ' ' -f 2 | cut -d . -f 1) -# if [[ $xcodeMajorVersion -ge 12 ]]; then -# extraVars=-DCMAKE_FRAMEWORK_PATH=~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-gpl-4.4-xc12-frameworks -# else -# prefixPath+=;~/dev/ios/vcmi-ios-deps/mobile-ffmpeg-min-universal -# fi +# -DCMAKE_OSX_SYSROOT=iphonesimulator -srcDir="../vcmi" -# cmake "$srcDir" -G Xcode -T buildsystem=1 \ -cmake "$srcDir" -G Xcode \ +cmake ../vcmi -G Xcode \ + -DCMAKE_SYSTEM_NAME=iOS \ -DFORCE_BUNDLED_MINIZIP=ON \ -DBUNDLE_IDENTIFIER_PREFIX=com.kambala \ -Wno-dev \ -DCMAKE_CXX_COMPILER_LAUNCHER=ccache \ - --toolchain "$srcDir/ios.toolchain.cmake" \ - -DPLATFORM=$platform \ - -DDEPLOYMENT_TARGET=12.0 \ - -DENABLE_BITCODE=OFF \ - -DCMAKE_BINARY_DIR=$(pwd) \ -DCMAKE_PREFIX_PATH="$prefixPath" \ -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY='Apple Development' \ -DCMAKE_XCODE_ATTRIBUTE_DEVELOPMENT_TEAM='4XHN44TEVG' diff --git a/ios.toolchain.cmake b/ios.toolchain.cmake deleted file mode 100644 index 5b6ee87a6..000000000 --- a/ios.toolchain.cmake +++ /dev/null @@ -1,1014 +0,0 @@ -# This file is part of the ios-cmake project. It was retrieved from -# https://github.com/leetal/ios-cmake.git, which is a fork of -# https://github.com/gerstrong/ios-cmake.git, which is a fork of -# https://github.com/cristeab/ios-cmake.git, which is a fork of -# https://code.google.com/p/ios-cmake/. Which in turn is based off of -# the Platform/Darwin.cmake and Platform/UnixPaths.cmake files which -# are included with CMake 2.8.4 -# -# The ios-cmake project is licensed under the new BSD license. -# -# Copyright (c) 2014, Bogdan Cristea and LTE Engineering Software, -# Kitware, Inc., Insight Software Consortium. All rights reserved. -# Redistribution and use in source and binary forms, with or without -# modification, are permitted provided that the following conditions -# are met: -# 1. Redistributions of source code must retain the above copyright -# notice, this list of conditions and the following disclaimer. -# -# 2. Redistributions in binary form must reproduce the above copyright -# notice, this list of conditions and the following disclaimer in the -# documentation and/or other materials provided with the distribution. -# -# 3. Neither the name of the copyright holder nor the names of its -# contributors may be used to endorse or promote products derived from -# this software without specific prior written permission. -# -# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS -# FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE -# COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, -# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, -# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; -# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER -# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN -# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE -# POSSIBILITY OF SUCH DAMAGE. -# -# This file is based off of the Platform/Darwin.cmake and -# Platform/UnixPaths.cmake files which are included with CMake 2.8.4 -# It has been altered for iOS development. -# -# Updated by Alex Stewart (alexs.mac@gmail.com) -# -# ***************************************************************************** -# Now maintained by Alexander Widerberg (widerbergaren [at] gmail.com) -# under the BSD-3-Clause license -# https://github.com/leetal/ios-cmake -# ***************************************************************************** -# -# INFORMATION / HELP -# -############################################################################### -# OPTIONS # -############################################################################### -# -# PLATFORM: (default "OS64") -# OS = Build for iPhoneOS. -# OS64 = Build for arm64 iphoneOS. -# OS64COMBINED = Build for arm64 x86_64 iphoneOS. Combined into FAT STATIC lib (supported on 3.14+ of CMakewith "-G Xcode" argument ONLY) -# SIMULATOR = Build for x86 i386 iphoneOS Simulator. -# SIMULATOR64 = Build for x86_64 iphoneOS Simulator. -# SIMULATORARM64 = Build for arm64 iphoneOS Simulator. -# TVOS = Build for arm64 tvOS. -# TVOSCOMBINED = Build for arm64 x86_64 tvOS. Combined into FAT STATIC lib (supported on 3.14+ of CMake with "-G Xcode" argument ONLY) -# SIMULATOR_TVOS = Build for x86_64 tvOS Simulator. -# WATCHOS = Build for armv7k arm64_32 for watchOS. -# WATCHOSCOMBINED = Build for armv7k arm64_32 x86_64 watchOS. Combined into FAT STATIC lib (supported on 3.14+ of CMake with "-G Xcode" argument ONLY) -# SIMULATOR_WATCHOS = Build for x86_64 for watchOS Simulator. -# MAC = Build for x86_64 macOS. -# MAC_ARM64 = Build for Apple Silicon macOS. -# MAC_CATALYST = Build for x86_64 macOS with Catalyst support (iOS toolchain on macOS). -# Note: The build argument "MACOSX_DEPLOYMENT_TARGET" can be used to control min-version of macOS -# MAC_CATALYST_ARM64 = Build for Apple Silicon macOS with Catalyst support (iOS toolchain on macOS). -# Note: The build argument "MACOSX_DEPLOYMENT_TARGET" can be used to control min-version of macOS -# -# CMAKE_OSX_SYSROOT: Path to the SDK to use. By default this is -# automatically determined from PLATFORM and xcodebuild, but -# can also be manually specified (although this should not be required). -# -# CMAKE_DEVELOPER_ROOT: Path to the Developer directory for the platform -# being compiled for. By default this is automatically determined from -# CMAKE_OSX_SYSROOT, but can also be manually specified (although this should -# not be required). -# -# DEPLOYMENT_TARGET: Minimum SDK version to target. Default 2.0 on watchOS and 9.0 on tvOS+iOS -# -# NAMED_LANGUAGE_SUPPORT: -# ON (default) = Will require "enable_language(OBJC) and/or enable_language(OBJCXX)" for full OBJC|OBJCXX support -# OFF = Will embed the OBJC and OBJCXX flags into the CMAKE_C_FLAGS and CMAKE_CXX_FLAGS (legacy behaviour, CMake version < 3.16) -# -# ENABLE_BITCODE: (ON|OFF) Enables or disables bitcode support. Default ON -# -# ENABLE_ARC: (ON|OFF) Enables or disables ARC support. Default ON (ARC enabled by default) -# -# ENABLE_VISIBILITY: (ON|OFF) Enables or disables symbol visibility support. Default OFF (visibility hidden by default) -# -# ENABLE_STRICT_TRY_COMPILE: (ON|OFF) Enables or disables strict try_compile() on all Check* directives (will run linker -# to actually check if linking is possible). Default OFF (will set CMAKE_TRY_COMPILE_TARGET_TYPE to STATIC_LIBRARY) -# -# ARCHS: (armv7 armv7s armv7k arm64 arm64_32 i386 x86_64) If specified, will override the default architectures for the given PLATFORM -# OS = armv7 armv7s arm64 (if applicable) -# OS64 = arm64 (if applicable) -# SIMULATOR = i386 -# SIMULATOR64 = x86_64 -# SIMULATORARM64 = arm64 -# TVOS = arm64 -# SIMULATOR_TVOS = x86_64 (i386 has since long been deprecated) -# WATCHOS = armv7k arm64_32 (if applicable) -# SIMULATOR_WATCHOS = x86_64 (i386 has since long been deprecated) -# MAC = x86_64 -# MAC_ARM64 = arm64 -# MAC_CATALYST = x86_64 -# MAC_CATALYST_ARM64 = arm64 -# -# NOTE: When manually specifying ARCHS, put a semi-colon between the entries. E.g., -DARCHS="armv7;arm64" -# -############################################################################### -# END OPTIONS # -############################################################################### -# -# This toolchain defines the following properties (available via get_property()) for use externally: -# -# PLATFORM: The currently targeted platform. -# XCODE_VERSION: Version number (not including Build version) of Xcode detected. -# SDK_VERSION: Version of SDK being used. -# OSX_ARCHITECTURES: Architectures being compiled for (generated from PLATFORM). -# APPLE_TARGET_TRIPLE: Used by autoconf build systems. NOTE: If "ARCHS" are overridden, this will *NOT* be set! -# -# This toolchain defines the following macros for use externally: -# -# set_xcode_property (TARGET XCODE_PROPERTY XCODE_VALUE XCODE_VARIANT) -# A convenience macro for setting xcode specific properties on targets. -# Available variants are: All, Release, RelWithDebInfo, Debug, MinSizeRel -# example: set_xcode_property (myioslib IPHONEOS_DEPLOYMENT_TARGET "3.1" "all"). -# -# find_host_package (PROGRAM ARGS) -# A macro used to find executable programs on the host system, not within the -# environment. Thanks to the android-cmake project for providing the -# command. -# - -cmake_minimum_required(VERSION 3.8.0) - -# CMake invokes the toolchain file twice during the first build, but only once during subsequent rebuilds. -if(DEFINED ENV{_IOS_TOOLCHAIN_HAS_RUN}) - return() -endif() -set(ENV{_IOS_TOOLCHAIN_HAS_RUN} true) - -# List of supported platform values -list(APPEND _supported_platforms - "OS" "OS64" "OS64COMBINED" "SIMULATOR" "SIMULATOR64" "SIMULATORARM64" - "TVOS" "TVOSCOMBINED" "SIMULATOR_TVOS" - "WATCHOS" "WATCHOSCOMBINED" "SIMULATOR_WATCHOS" - "MAC" "MAC_ARM64" - "MAC_CATALYST" "MAC_CATALYST_ARM64") - -# Cache what generator is used -set(USED_CMAKE_GENERATOR "${CMAKE_GENERATOR}") - -# Check if using a CMake version capable of building combined FAT builds (simulator and target slices combined in one static lib) -if(${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.14") - set(MODERN_CMAKE YES) -endif() - -# Get the Xcode version being used. -# Problem: CMake runs toolchain files multiple times, but can't read cache variables on some runs. -# Workaround: On first run (in which cache variables are always accessible), set an intermediary environment variable. -# -# NOTE: This pattern is used i many places in this toolchain to speed up checks of all sorts -if(DEFINED XCODE_VERSION_INT) - # Environment variables are always preserved. - set(ENV{_XCODE_VERSION_INT} "${XCODE_VERSION_INT}") -elseif(DEFINED ENV{_XCODE_VERSION_INT}) - set(XCODE_VERSION_INT "$ENV{_XCODE_VERSION_INT}") -elseif(NOT DEFINED XCODE_VERSION_INT) - find_program(XCODEBUILD_EXECUTABLE xcodebuild) - if(NOT XCODEBUILD_EXECUTABLE) - message(FATAL_ERROR "xcodebuild not found. Please install either the standalone commandline tools or Xcode.") - endif() - execute_process(COMMAND ${XCODEBUILD_EXECUTABLE} -version - OUTPUT_VARIABLE XCODE_VERSION_INT - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) - string(REGEX MATCH "Xcode [0-9\\.]+" XCODE_VERSION_INT "${XCODE_VERSION_INT}") - string(REGEX REPLACE "Xcode ([0-9\\.]+)" "\\1" XCODE_VERSION_INT "${XCODE_VERSION_INT}") - set(XCODE_VERSION_INT "${XCODE_VERSION_INT}" CACHE INTERNAL "") -endif() - -# Assuming that xcode 12.0 is installed you most probably have ios sdk 14.0 or later installed (tested on Big Sur) -# if you don't set a deployment target it will be set the way you only get 64-bit builds -if(NOT DEFINED DEPLOYMENT_TARGET AND XCODE_VERSION_INT VERSION_GREATER 12.0) - # Temporarily fix the arm64 issues in CMake install-combined by excluding arm64 for simulator builds (needed for Apple Silicon...) - set(CMAKE_XCODE_ATTRIBUTE_EXCLUDED_ARCHS[sdk=iphonesimulator*] "arm64") -endif() - -# Check if the platform variable is set -if(DEFINED PLATFORM) - # Environment variables are always preserved. - set(ENV{_PLATFORM} "${PLATFORM}") -elseif(DEFINED ENV{_PLATFORM}) - set(PLATFORM "$ENV{_PLATFORM}") -elseif(NOT DEFINED PLATFORM) - message(FATAL_ERROR "PLATFORM argument not set. Bailing configure since I don't know what target you want to build for!") -endif () - -if(PLATFORM MATCHES ".*COMBINED" AND NOT CMAKE_GENERATOR MATCHES "Xcode") - message(FATAL_ERROR "The combined builds support requires Xcode to be used as generator via '-G Xcode' command-line argument in CMake") -endif() - -# Safeguard that the platform value is set and is one of the supported values -list(FIND _supported_platforms ${PLATFORM} contains_PLATFORM) -if("${contains_PLATFORM}" EQUAL "-1") - string(REPLACE ";" "\n * " _supported_platforms_formatted "${_supported_platforms}") - message(FATAL_ERROR " Invalid PLATFORM specified! Current value: ${PLATFORM}.\n" - " Supported PLATFORM values: \n * ${_supported_platforms_formatted}") -endif() - -# Check if Apple Silicon is supported -if(PLATFORM MATCHES "^(MAC_ARM64)$|^(MAC_CATALYST_ARM64)$" AND ${CMAKE_VERSION} VERSION_LESS "3.19.5") - message(FATAL_ERROR "Apple Silicon builds requires a minimum of CMake 3.19.5") -endif() - -# Touch toolchain variable to suppress "unused variable" warning. -# This happens if CMake is invoked with the same command line the second time. -if(CMAKE_TOOLCHAIN_FILE) -endif() - -# Fix for PThread library not in path -set(CMAKE_THREAD_LIBS_INIT "-lpthread") -set(CMAKE_HAVE_THREADS_LIBRARY 1) -set(CMAKE_USE_WIN32_THREADS_INIT 0) -set(CMAKE_USE_PTHREADS_INIT 1) - -# Specify named language support defaults. -if(NOT DEFINED NAMED_LANGUAGE_SUPPORT AND ${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.16") - set(NAMED_LANGUAGE_SUPPORT ON) - message(STATUS "[DEFAULTS] Using explicit named language support! E.g., enable_language(CXX) is needed in the project files.") -elseif(NOT DEFINED NAMED_LANGUAGE_SUPPORT AND ${CMAKE_VERSION} VERSION_LESS "3.16") - set(NAMED_LANGUAGE_SUPPORT OFF) - message(STATUS "[DEFAULTS] Disabling explicit named language support. Falling back to legacy behaviour.") -elseif(DEFINED NAMED_LANGUAGE_SUPPORT AND ${CMAKE_VERSION} VERSION_LESS "3.16") - message(FATAL_ERROR "CMake named language support for OBJC and OBJCXX was added in CMake 3.16.") -endif() -set(NAMED_LANGUAGE_SUPPORT_INT ${NAMED_LANGUAGE_SUPPORT} CACHE BOOL - "Whether or not to enable explicit named language support" FORCE) - -# Specify minimum version of deployment target. -if(NOT DEFINED DEPLOYMENT_TARGET) - if (PLATFORM MATCHES "WATCHOS") - # Unless specified, SDK version 4.0 is used by default as minimum target version (watchOS). - set(DEPLOYMENT_TARGET "4.0") - elseif(PLATFORM STREQUAL "MAC") - # Unless specified, SDK version 10.13 (High sierra) is used by default as minimum target version (macos). - set(DEPLOYMENT_TARGET "10.13") - elseif(PLATFORM STREQUAL "MAC_ARM64") - # Unless specified, SDK version 11.0 (Big Sur) is used by default as minimum target version (macos on arm). - set(DEPLOYMENT_TARGET "11.0") - elseif(PLATFORM STREQUAL "MAC_CATALYST" OR PLATFORM STREQUAL "MAC_CATALYST_ARM64") - # Unless specified, SDK version 13.0 is used by default as minimum target version (mac catalyst minimum requirement). - set(DEPLOYMENT_TARGET "13.1") - else() - # Unless specified, SDK version 11.0 is used by default as minimum target version (iOS, tvOS). - set(DEPLOYMENT_TARGET "11.0") - endif() - message(STATUS "[DEFAULTS] Using the default min-version since DEPLOYMENT_TARGET not provided!") -elseif(DEFINED DEPLOYMENT_TARGET AND PLATFORM MATCHES "^MAC_CATALYST" AND ${DEPLOYMENT_TARGET} VERSION_LESS "13.1") - message(FATAL_ERROR "Mac Catalyst builds requires a minimum deployment target of 13.1!") -endif() - -# Store the DEPLOYMENT_TARGET in the cache -set(DEPLOYMENT_TARGET "${DEPLOYMENT_TARGET}" CACHE INTERNAL "") - -# Handle the case where we are targeting iOS and a version above 10.3.4 (32-bit support dropped officially) -if(PLATFORM STREQUAL "OS" AND DEPLOYMENT_TARGET VERSION_GREATER_EQUAL 10.3.4) - set(PLATFORM "OS64") - message(STATUS "Targeting minimum SDK version ${DEPLOYMENT_TARGET}. Dropping 32-bit support.") -elseif(PLATFORM STREQUAL "SIMULATOR" AND DEPLOYMENT_TARGET VERSION_GREATER_EQUAL 10.3.4) - set(PLATFORM "SIMULATOR64") - message(STATUS "Targeting minimum SDK version ${DEPLOYMENT_TARGET}. Dropping 32-bit support.") -endif() - -set(PLATFORM_INT "${PLATFORM}") - -if(DEFINED ARCHS) - string(REPLACE ";" "-" ARCHS_SPLIT "${ARCHS}") -endif() - -# Determine the platform name and architectures for use in xcodebuild commands -# from the specified PLATFORM_INT name. -if(PLATFORM_INT STREQUAL "OS") - set(SDK_NAME iphoneos) - if(NOT ARCHS) - set(ARCHS armv7 armv7s arm64) - set(APPLE_TARGET_TRIPLE_INT arm-apple-ios${DEPLOYMENT_TARGET}) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}) - endif() -elseif(PLATFORM_INT STREQUAL "OS64") - set(SDK_NAME iphoneos) - if(NOT ARCHS) - if (XCODE_VERSION_INT VERSION_GREATER 10.0) - set(ARCHS arm64) # FIXME: Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example - else() - set(ARCHS arm64) - endif() - set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios${DEPLOYMENT_TARGET}) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}) - endif() -elseif(PLATFORM_INT STREQUAL "OS64COMBINED") - set(SDK_NAME iphoneos) - if(MODERN_CMAKE) - if(NOT ARCHS) - if (XCODE_VERSION_INT VERSION_GREATER 10.0) - set(ARCHS arm64 x86_64) # FIXME: Add arm64e when Apple have fixed the integration issues with it, libarclite_iphoneos.a is currently missung bitcode markers for example - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphoneos*] "arm64") - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphonesimulator*] "x86_64") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphoneos*] "arm64") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphonesimulator*] "x86_64") - else() - set(ARCHS arm64 x86_64) - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphoneos*] "arm64") - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=iphonesimulator*] "x86_64") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphoneos*] "arm64") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=iphonesimulator*] "x86_64") - endif() - set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-ios${DEPLOYMENT_TARGET}) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}) - endif() - else() - message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the OS64COMBINED setting work") - endif() -elseif(PLATFORM_INT STREQUAL "SIMULATOR") - set(SDK_NAME iphonesimulator) - if(NOT ARCHS) - set(ARCHS i386) - set(APPLE_TARGET_TRIPLE_INT i386-apple-ios${DEPLOYMENT_TARGET}-simulator) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-simulator) - endif() - message(DEPRECATION "SIMULATOR IS DEPRECATED. Consider using SIMULATOR64 instead.") -elseif(PLATFORM_INT STREQUAL "SIMULATOR64") - set(SDK_NAME iphonesimulator) - if(NOT ARCHS) - set(ARCHS x86_64) - set(APPLE_TARGET_TRIPLE_INT x86_64-apple-ios${DEPLOYMENT_TARGET}-simulator) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-simulator) - endif() -elseif(PLATFORM_INT STREQUAL "SIMULATORARM64") - set(SDK_NAME iphonesimulator) - if(NOT ARCHS) - set(ARCHS arm64) - set(APPLE_TARGET_TRIPLE_INT aarch64-apple-ios${DEPLOYMENT_TARGET}-simulator) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-simulator) - endif() -elseif(PLATFORM_INT STREQUAL "TVOS") - set(SDK_NAME appletvos) - if(NOT ARCHS) - set(ARCHS arm64) - set(APPLE_TARGET_TRIPLE_INT aarch64-apple-tvos${DEPLOYMENT_TARGET}) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos${DEPLOYMENT_TARGET}) - endif() -elseif (PLATFORM_INT STREQUAL "TVOSCOMBINED") - set(SDK_NAME appletvos) - if(MODERN_CMAKE) - if(NOT ARCHS) - set(ARCHS arm64 x86_64) - set(APPLE_TARGET_TRIPLE_INT aarch64-x86_64-apple-tvos${DEPLOYMENT_TARGET}) - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=appletvos*] "arm64") - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=appletvsimulator*] "x86_64") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=appletvos*] "arm64") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=appletvsimulator*] "x86_64") - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos${DEPLOYMENT_TARGET}) - endif() - else() - message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the TVOSCOMBINED setting work") - endif() -elseif(PLATFORM_INT STREQUAL "SIMULATOR_TVOS") - set(SDK_NAME appletvsimulator) - if(NOT ARCHS) - set(ARCHS x86_64) - set(APPLE_TARGET_TRIPLE_INT x86_64-apple-tvos${DEPLOYMENT_TARGET}-simulator) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-tvos${DEPLOYMENT_TARGET}-simulator) - endif() -elseif(PLATFORM_INT STREQUAL "WATCHOS") - set(SDK_NAME watchos) - if(NOT ARCHS) - if (XCODE_VERSION_INT VERSION_GREATER 10.0) - set(ARCHS armv7k arm64_32) - set(APPLE_TARGET_TRIPLE_INT aarch64_32-apple-watchos${DEPLOYMENT_TARGET}) - else() - set(ARCHS armv7k) - set(APPLE_TARGET_TRIPLE_INT arm-apple-watchos${DEPLOYMENT_TARGET}) - endif() - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos${DEPLOYMENT_TARGET}) - endif() -elseif(PLATFORM_INT STREQUAL "WATCHOSCOMBINED") - set(SDK_NAME watchos) - if(MODERN_CMAKE) - if(NOT ARCHS) - if (XCODE_VERSION_INT VERSION_GREATER 10.0) - set(ARCHS armv7k arm64_32 i386) - set(APPLE_TARGET_TRIPLE_INT aarch64_32-i386-apple-watchos${DEPLOYMENT_TARGET}) - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchos*] "armv7k arm64_32") - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchsimulator*] "i386") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchos*] "armv7k arm64_32") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchsimulator*] "i386") - else() - set(ARCHS armv7k i386) - set(APPLE_TARGET_TRIPLE_INT arm-i386-apple-watchos${DEPLOYMENT_TARGET}) - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchos*] "armv7k") - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=watchsimulator*] "i386") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchos*] "armv7k") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=watchsimulator*] "i386") - endif() - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos${DEPLOYMENT_TARGET}) - endif() - else() - message(FATAL_ERROR "Please make sure that you are running CMake 3.14+ to make the WATCHOSCOMBINED setting work") - endif() -elseif(PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") - set(SDK_NAME watchsimulator) - if(NOT ARCHS) - set(ARCHS i386) - set(APPLE_TARGET_TRIPLE_INT i386-apple-watchos${DEPLOYMENT_TARGET}-simulator) - else() - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-watchos${DEPLOYMENT_TARGET}-simulator) - endif() -elseif(PLATFORM_INT STREQUAL "MAC" OR PLATFORM_INT STREQUAL "MAC_CATALYST") - set(SDK_NAME macosx) - if(NOT ARCHS) - set(ARCHS x86_64) - endif() - string(REPLACE ";" "-" ARCHS_SPLIT "${ARCHS}") - if(PLATFORM_INT STREQUAL "MAC") - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-macosx${DEPLOYMENT_TARGET}) - elseif(PLATFORM_INT STREQUAL "MAC_CATALYST") - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-macabi) - endif() -elseif(PLATFORM_INT MATCHES "^(MAC_ARM64)$|^(MAC_CATALYST_ARM64)$") - set(SDK_NAME macosx) - if(NOT ARCHS) - set(ARCHS arm64) - endif() - string(REPLACE ";" "-" ARCHS_SPLIT "${ARCHS}") - if(PLATFORM_INT STREQUAL "MAC_ARM64") - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-macosx${DEPLOYMENT_TARGET}) - elseif(PLATFORM_INT STREQUAL "MAC_CATALYST_ARM64") - set(APPLE_TARGET_TRIPLE_INT ${ARCHS_SPLIT}-apple-ios${DEPLOYMENT_TARGET}-macabi) - endif() -else() - message(FATAL_ERROR "Invalid PLATFORM: ${PLATFORM_INT}") -endif() - -string(REPLACE ";" " " ARCHS_SPACED "${ARCHS}") - -if(MODERN_CMAKE AND PLATFORM_INT MATCHES ".*COMBINED" AND NOT CMAKE_GENERATOR MATCHES "Xcode") - message(FATAL_ERROR "The COMBINED options only work with Xcode generator, -G Xcode") -endif() - -if(CMAKE_GENERATOR MATCHES "Xcode" AND PLATFORM_INT MATCHES "^MAC_CATALYST") - set(CMAKE_XCODE_ATTRIBUTE_CLANG_CXX_LIBRARY "libc++") - set(CMAKE_XCODE_ATTRIBUTE_SUPPORTED_PLATFORMS "macosx") - set(CMAKE_XCODE_EFFECTIVE_PLATFORMS "-maccatalyst") - if(NOT DEFINED MACOSX_DEPLOYMENT_TARGET) - set(CMAKE_XCODE_ATTRIBUTE_MACOSX_DEPLOYMENT_TARGET "10.15") - else() - set(CMAKE_XCODE_ATTRIBUTE_MACOSX_DEPLOYMENT_TARGET "${MACOSX_DEPLOYMENT_TARGET}") - endif() -elseif(CMAKE_GENERATOR MATCHES "Xcode") - set(CMAKE_XCODE_ATTRIBUTE_CLANG_CXX_LIBRARY "libc++") - set(CMAKE_XCODE_ATTRIBUTE_IPHONEOS_DEPLOYMENT_TARGET "${DEPLOYMENT_TARGET}") - if(NOT PLATFORM_INT MATCHES ".*COMBINED") - set(CMAKE_XCODE_ATTRIBUTE_ARCHS[sdk=${SDK_NAME}*] "${ARCHS_SPACED}") - set(CMAKE_XCODE_ATTRIBUTE_VALID_ARCHS[sdk=${SDK_NAME}*] "${ARCHS_SPACED}") - endif() -endif() - -# If user did not specify the SDK root to use, then query xcodebuild for it. -if(DEFINED CMAKE_OSX_SYSROOT_INT) - # Environment variables are always preserved. - set(ENV{_CMAKE_OSX_SYSROOT_INT} "${CMAKE_OSX_SYSROOT_INT}") -elseif(DEFINED ENV{_CMAKE_OSX_SYSROOT_INT}) - set(CMAKE_OSX_SYSROOT_INT "$ENV{_CMAKE_OSX_SYSROOT_INT}") -elseif(NOT DEFINED CMAKE_OSX_SYSROOT_INT) - execute_process(COMMAND ${XCODEBUILD_EXECUTABLE} -version -sdk ${SDK_NAME} Path - OUTPUT_VARIABLE CMAKE_OSX_SYSROOT_INT - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) -endif() - -if (NOT DEFINED CMAKE_OSX_SYSROOT_INT AND NOT DEFINED CMAKE_OSX_SYSROOT) - message(SEND_ERROR "Please make sure that Xcode is installed and that the toolchain" - "is pointing to the correct path. Please run:" - "sudo xcode-select -s /Applications/Xcode.app/Contents/Developer" - "and see if that fixes the problem for you.") - message(FATAL_ERROR "Invalid CMAKE_OSX_SYSROOT: ${CMAKE_OSX_SYSROOT} " - "does not exist.") -elseif(DEFINED CMAKE_OSX_SYSROOT_INT) - set(CMAKE_OSX_SYSROOT_INT "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") - # Specify the location or name of the platform SDK to be used in CMAKE_OSX_SYSROOT. - set(CMAKE_OSX_SYSROOT "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") -endif() - -# Use bitcode or not -if(NOT DEFINED ENABLE_BITCODE AND NOT ARCHS MATCHES "((^|;|, )(i386|x86_64))+") - # Unless specified, enable bitcode support by default - message(STATUS "[DEFAULTS] Enabling bitcode support by default. ENABLE_BITCODE not provided!") - set(ENABLE_BITCODE ON) -elseif(NOT DEFINED ENABLE_BITCODE) - message(STATUS "[DEFAULTS] Disabling bitcode support by default on simulators. ENABLE_BITCODE not provided for override!") - set(ENABLE_BITCODE OFF) -endif() -set(ENABLE_BITCODE_INT ${ENABLE_BITCODE} CACHE BOOL - "Whether or not to enable bitcode" FORCE) -# Use ARC or not -if(NOT DEFINED ENABLE_ARC) - # Unless specified, enable ARC support by default - set(ENABLE_ARC ON) - message(STATUS "[DEFAULTS] Enabling ARC support by default. ENABLE_ARC not provided!") -endif() -set(ENABLE_ARC_INT ${ENABLE_ARC} CACHE BOOL "Whether or not to enable ARC" FORCE) -# Use hidden visibility or not -if(NOT DEFINED ENABLE_VISIBILITY) - # Unless specified, disable symbols visibility by default - set(ENABLE_VISIBILITY OFF) - message(STATUS "[DEFAULTS] Hiding symbols visibility by default. ENABLE_VISIBILITY not provided!") -endif() -set(ENABLE_VISIBILITY_INT ${ENABLE_VISIBILITY} CACHE BOOL "Whether or not to hide symbols from the dynamic linker (-fvisibility=hidden)" FORCE) -# Set strict compiler checks or not -if(NOT DEFINED ENABLE_STRICT_TRY_COMPILE) - # Unless specified, disable strict try_compile() - set(ENABLE_STRICT_TRY_COMPILE OFF) - message(STATUS "[DEFAULTS] Using NON-strict compiler checks by default. ENABLE_STRICT_TRY_COMPILE not provided!") -endif() -set(ENABLE_STRICT_TRY_COMPILE_INT ${ENABLE_STRICT_TRY_COMPILE} CACHE BOOL - "Whether or not to use strict compiler checks" FORCE) - -# Get the SDK version information. -if(DEFINED SDK_VERSION) - # Environment variables are always preserved. - set(ENV{_SDK_VERSION} "${SDK_VERSION}") -elseif(DEFINED ENV{_SDK_VERSION}) - set(SDK_VERSION "$ENV{_SDK_VERSION}") -elseif(NOT DEFINED SDK_VERSION) - execute_process(COMMAND ${XCODEBUILD_EXECUTABLE} -sdk ${CMAKE_OSX_SYSROOT_INT} -version SDKVersion - OUTPUT_VARIABLE SDK_VERSION - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) -endif() - -# Find the Developer root for the specific iOS platform being compiled for -# from CMAKE_OSX_SYSROOT. Should be ../../ from SDK specified in -# CMAKE_OSX_SYSROOT. There does not appear to be a direct way to obtain -# this information from xcrun or xcodebuild. -if (NOT DEFINED CMAKE_DEVELOPER_ROOT AND NOT CMAKE_GENERATOR MATCHES "Xcode") - get_filename_component(PLATFORM_SDK_DIR ${CMAKE_OSX_SYSROOT_INT} PATH) - get_filename_component(CMAKE_DEVELOPER_ROOT ${PLATFORM_SDK_DIR} PATH) - if (NOT EXISTS "${CMAKE_DEVELOPER_ROOT}") - message(FATAL_ERROR "Invalid CMAKE_DEVELOPER_ROOT: ${CMAKE_DEVELOPER_ROOT} does not exist.") - endif() -endif() - -# Find the C & C++ compilers for the specified SDK. -if(DEFINED CMAKE_C_COMPILER) - # Environment variables are always preserved. - set(ENV{_CMAKE_C_COMPILER} "${CMAKE_C_COMPILER}") -elseif(DEFINED ENV{_CMAKE_C_COMPILER}) - set(CMAKE_C_COMPILER "$ENV{_CMAKE_C_COMPILER}") - set(CMAKE_ASM_COMPILER ${CMAKE_C_COMPILER}) -elseif(NOT DEFINED CMAKE_C_COMPILER) - execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find clang - OUTPUT_VARIABLE CMAKE_C_COMPILER - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) - set(CMAKE_ASM_COMPILER ${CMAKE_C_COMPILER}) -endif() -if(DEFINED CMAKE_CXX_COMPILER) - # Environment variables are always preserved. - set(ENV{_CMAKE_CXX_COMPILER} "${CMAKE_CXX_COMPILER}") -elseif(DEFINED ENV{_CMAKE_CXX_COMPILER}) - set(CMAKE_CXX_COMPILER "$ENV{_CMAKE_CXX_COMPILER}") -elseif(NOT DEFINED CMAKE_CXX_COMPILER) - execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find clang++ - OUTPUT_VARIABLE CMAKE_CXX_COMPILER - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) -endif() -# Find (Apple's) libtool. -if(DEFINED BUILD_LIBTOOL) - # Environment variables are always preserved. - set(ENV{_BUILD_LIBTOOL} "${BUILD_LIBTOOL}") -elseif(DEFINED ENV{_BUILD_LIBTOOL}) - set(BUILD_LIBTOOL "$ENV{_BUILD_LIBTOOL}") -elseif(NOT DEFINED BUILD_LIBTOOL) - execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find libtool - OUTPUT_VARIABLE BUILD_LIBTOOL - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) -endif() -# Find the toolchain's provided install_name_tool if none is found on the host -if(DEFINED CMAKE_INSTALL_NAME_TOOL) - # Environment variables are always preserved. - set(ENV{_CMAKE_INSTALL_NAME_TOOL} "${CMAKE_INSTALL_NAME_TOOL}") -elseif(DEFINED ENV{_CMAKE_INSTALL_NAME_TOOL}) - set(CMAKE_INSTALL_NAME_TOOL "$ENV{_CMAKE_INSTALL_NAME_TOOL}") -elseif(NOT DEFINED CMAKE_INSTALL_NAME_TOOL) - execute_process(COMMAND xcrun -sdk ${CMAKE_OSX_SYSROOT_INT} -find install_name_tool - OUTPUT_VARIABLE CMAKE_INSTALL_NAME_TOOL_INT - ERROR_QUIET - OUTPUT_STRIP_TRAILING_WHITESPACE) - set(CMAKE_INSTALL_NAME_TOOL ${CMAKE_INSTALL_NAME_TOOL_INT} CACHE INTERNAL "") -endif() - -# Configure libtool to be used instead of ar + ranlib to build static libraries. -# This is required on Xcode 7+, but should also work on previous versions of -# Xcode. -get_property(languages GLOBAL PROPERTY ENABLED_LANGUAGES) -foreach(lang ${languages}) - set(CMAKE_${lang}_CREATE_STATIC_LIBRARY "${BUILD_LIBTOOL} -static -o " CACHE INTERNAL "") -endforeach() - -# CMake 3.14+ support building for iOS, watchOS and tvOS out of the box. -if(MODERN_CMAKE) - if(SDK_NAME MATCHES "iphone") - set(CMAKE_SYSTEM_NAME iOS) - elseif(SDK_NAME MATCHES "macosx") - set(CMAKE_SYSTEM_NAME Darwin) - elseif(SDK_NAME MATCHES "appletv") - set(CMAKE_SYSTEM_NAME tvOS) - elseif(SDK_NAME MATCHES "watch") - set(CMAKE_SYSTEM_NAME watchOS) - endif() - # Provide flags for a combined FAT library build on newer CMake versions - if(PLATFORM_INT MATCHES ".*COMBINED") - set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH "NO") - set(CMAKE_IOS_INSTALL_COMBINED YES) - endif() -elseif(NOT DEFINED CMAKE_SYSTEM_NAME AND ${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.10") - # Legacy code path prior to CMake 3.14 or fallback if no CMAKE_SYSTEM_NAME specified - set(CMAKE_SYSTEM_NAME iOS) -elseif(NOT DEFINED CMAKE_SYSTEM_NAME) - # Legacy code path prior to CMake 3.14 or fallback if no CMAKE_SYSTEM_NAME specified - set(CMAKE_SYSTEM_NAME Darwin) -endif() -# Standard settings. -set(CMAKE_SYSTEM_VERSION ${SDK_VERSION} CACHE INTERNAL "") -set(UNIX ON CACHE BOOL "") -set(APPLE ON CACHE BOOL "") -if(PLATFORM STREQUAL "MAC" OR PLATFORM STREQUAL "MAC_ARM64") - set(IOS OFF CACHE BOOL "") - set(MACOS ON CACHE BOOL "") -elseif(PLATFORM STREQUAL "MAC_CATALYST" OR PLATFORM STREQUAL "MAC_CATALYST_ARM64") - set(IOS ON CACHE BOOL "") - set(MACOS ON CACHE BOOL "") -else() - set(IOS ON CACHE BOOL "") -endif() -set(CMAKE_AR ar CACHE FILEPATH "" FORCE) -set(CMAKE_RANLIB ranlib CACHE FILEPATH "" FORCE) -set(CMAKE_STRIP strip CACHE FILEPATH "" FORCE) -# Set the architectures for which to build. -set(CMAKE_OSX_ARCHITECTURES ${ARCHS} CACHE INTERNAL "") -# Change the type of target generated for try_compile() so it'll work when cross-compiling, weak compiler checks -if(NOT ENABLE_STRICT_TRY_COMPILE_INT) - set(CMAKE_TRY_COMPILE_TARGET_TYPE STATIC_LIBRARY) -endif() -# All iOS/Darwin specific settings - some may be redundant. -set(CMAKE_MACOSX_BUNDLE YES) -set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_REQUIRED "NO") -set(CMAKE_SHARED_LIBRARY_PREFIX "lib") -set(CMAKE_SHARED_LIBRARY_SUFFIX ".dylib") -set(CMAKE_SHARED_MODULE_PREFIX "lib") -set(CMAKE_SHARED_MODULE_SUFFIX ".so") -set(CMAKE_C_COMPILER_ABI ELF) -set(CMAKE_CXX_COMPILER_ABI ELF) -set(CMAKE_C_HAS_ISYSROOT 1) -set(CMAKE_CXX_HAS_ISYSROOT 1) -set(CMAKE_MODULE_EXISTS 1) -set(CMAKE_DL_LIBS "") -set(CMAKE_C_OSX_COMPATIBILITY_VERSION_FLAG "-compatibility_version ") -set(CMAKE_C_OSX_CURRENT_VERSION_FLAG "-current_version ") -set(CMAKE_CXX_OSX_COMPATIBILITY_VERSION_FLAG "${CMAKE_C_OSX_COMPATIBILITY_VERSION_FLAG}") -set(CMAKE_CXX_OSX_CURRENT_VERSION_FLAG "${CMAKE_C_OSX_CURRENT_VERSION_FLAG}") - -if(ARCHS MATCHES "((^|;|, )(arm64|arm64e|x86_64))+") - set(CMAKE_C_SIZEOF_DATA_PTR 8) - set(CMAKE_CXX_SIZEOF_DATA_PTR 8) - if(ARCHS MATCHES "((^|;|, )(arm64|arm64e))+") - set(CMAKE_SYSTEM_PROCESSOR "aarch64") - else() - set(CMAKE_SYSTEM_PROCESSOR "x86_64") - endif() -else() - set(CMAKE_C_SIZEOF_DATA_PTR 4) - set(CMAKE_CXX_SIZEOF_DATA_PTR 4) - set(CMAKE_SYSTEM_PROCESSOR "arm") -endif() - -# Note that only Xcode 7+ supports the newer more specific: -# -m${SDK_NAME}-version-min flags, older versions of Xcode use: -# -m(ios/ios-simulator)-version-min instead. -if(${CMAKE_VERSION} VERSION_LESS "3.11") - if(PLATFORM_INT STREQUAL "OS" OR PLATFORM_INT STREQUAL "OS64") - if(XCODE_VERSION_INT VERSION_LESS 7.0) - set(SDK_NAME_VERSION_FLAGS - "-mios-version-min=${DEPLOYMENT_TARGET}") - else() - # Xcode 7.0+ uses flags we can build directly from SDK_NAME. - set(SDK_NAME_VERSION_FLAGS - "-m${SDK_NAME}-version-min=${DEPLOYMENT_TARGET}") - endif() - elseif(PLATFORM_INT STREQUAL "TVOS") - set(SDK_NAME_VERSION_FLAGS - "-mtvos-version-min=${DEPLOYMENT_TARGET}") - elseif(PLATFORM_INT STREQUAL "SIMULATOR_TVOS") - set(SDK_NAME_VERSION_FLAGS - "-mtvos-simulator-version-min=${DEPLOYMENT_TARGET}") - elseif(PLATFORM_INT STREQUAL "WATCHOS") - set(SDK_NAME_VERSION_FLAGS - "-mwatchos-version-min=${DEPLOYMENT_TARGET}") - elseif(PLATFORM_INT STREQUAL "SIMULATOR_WATCHOS") - set(SDK_NAME_VERSION_FLAGS - "-mwatchos-simulator-version-min=${DEPLOYMENT_TARGET}") - elseif(PLATFORM_INT STREQUAL "MAC") - set(SDK_NAME_VERSION_FLAGS - "-mmacosx-version-min=${DEPLOYMENT_TARGET}") - else() - # SIMULATOR or SIMULATOR64 both use -mios-simulator-version-min. - set(SDK_NAME_VERSION_FLAGS - "-mios-simulator-version-min=${DEPLOYMENT_TARGET}") - endif() -elseif(NOT PLATFORM_INT MATCHES "^MAC_CATALYST") - # Newer versions of CMake sets the version min flags correctly, skip this for Mac Catalyst targets - set(CMAKE_OSX_DEPLOYMENT_TARGET ${DEPLOYMENT_TARGET}) -endif() - -if(DEFINED APPLE_TARGET_TRIPLE_INT) - set(APPLE_TARGET_TRIPLE ${APPLE_TARGET_TRIPLE_INT} CACHE INTERNAL "") - set(CMAKE_C_COMPILER_TARGET ${APPLE_TARGET_TRIPLE}) - set(CMAKE_CXX_COMPILER_TARGET ${APPLE_TARGET_TRIPLE}) - set(CMAKE_ASM_COMPILER_TARGET ${APPLE_TARGET_TRIPLE}) -endif() - -if(PLATFORM_INT MATCHES "^MAC_CATALYST") - set(C_TARGET_FLAGS "-isystem ${CMAKE_OSX_SYSROOT_INT}/System/iOSSupport/usr/include -iframework ${CMAKE_OSX_SYSROOT_INT}/System/iOSSupport/System/Library/Frameworks") -endif() - -if(ENABLE_BITCODE_INT) - set(BITCODE "-fembed-bitcode") - set(CMAKE_XCODE_ATTRIBUTE_BITCODE_GENERATION_MODE "bitcode") - set(CMAKE_XCODE_ATTRIBUTE_ENABLE_BITCODE "YES") -else() - set(BITCODE "") - set(CMAKE_XCODE_ATTRIBUTE_ENABLE_BITCODE "NO") -endif() - -if(ENABLE_ARC_INT) - set(FOBJC_ARC "-fobjc-arc") - set(CMAKE_XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC "YES") -else() - set(FOBJC_ARC "-fno-objc-arc") - set(CMAKE_XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC "NO") -endif() - -if(NAMED_LANGUAGE_SUPPORT_INT) - set(OBJC_VARS "-fobjc-abi-version=2 -DOBJC_OLD_DISPATCH_PROTOTYPES=0") - set(OBJC_LEGACY_VARS "") -else() - set(OBJC_VARS "") - set(OBJC_LEGACY_VARS "-fobjc-abi-version=2 -DOBJC_OLD_DISPATCH_PROTOTYPES=0") -endif() - -if(NOT ENABLE_VISIBILITY_INT) - foreach(lang ${languages}) - set(CMAKE_${lang}_VISIBILITY_PRESET "hidden" CACHE INTERNAL "") - endforeach() - set(CMAKE_XCODE_ATTRIBUTE_GCC_SYMBOLS_PRIVATE_EXTERN "YES") - set(VISIBILITY "-fvisibility=hidden -fvisibility-inlines-hidden") -else() - foreach(lang ${languages}) - set(CMAKE_${lang}_VISIBILITY_PRESET "default" CACHE INTERNAL "") - endforeach() - set(CMAKE_XCODE_ATTRIBUTE_GCC_SYMBOLS_PRIVATE_EXTERN "NO") - set(VISIBILITY "-fvisibility=default") -endif() - -if(DEFINED APPLE_TARGET_TRIPLE) - set(APPLE_TARGET_TRIPLE_FLAG "-target ${APPLE_TARGET_TRIPLE}") -endif() - -#Check if Xcode generator is used, since that will handle these flags automagically -if(CMAKE_GENERATOR MATCHES "Xcode") - message(STATUS "Not setting any manual command-line buildflags, since Xcode is selected as generator. Modifying the Xcode build-settings directly instead.") -else() - set(CMAKE_C_FLAGS "${C_TARGET_FLAGS} ${APPLE_TARGET_TRIPLE_FLAG} ${SDK_NAME_VERSION_FLAGS} ${OBJC_LEGACY_VARS} ${BITCODE} ${VISIBILITY} ${CMAKE_C_FLAGS}") - set(CMAKE_C_FLAGS_DEBUG "-O0 -g ${CMAKE_C_FLAGS_DEBUG}") - set(CMAKE_C_FLAGS_MINSIZEREL "-DNDEBUG -Os ${CMAKE_C_FLAGS_MINSIZEREL}") - set(CMAKE_C_FLAGS_RELWITHDEBINFO "-DNDEBUG -O2 -g ${CMAKE_C_FLAGS_RELWITHDEBINFO}") - set(CMAKE_C_FLAGS_RELEASE "-DNDEBUG -O3 ${CMAKE_C_FLAGS_RELEASE}") - set(CMAKE_CXX_FLAGS "${C_TARGET_FLAGS} ${APPLE_TARGET_TRIPLE_FLAG} ${SDK_NAME_VERSION_FLAGS} ${OBJC_LEGACY_VARS} ${BITCODE} ${VISIBILITY} ${CMAKE_CXX_FLAGS}") - set(CMAKE_CXX_FLAGS_DEBUG "-O0 -g ${CMAKE_CXX_FLAGS_DEBUG}") - set(CMAKE_CXX_FLAGS_MINSIZEREL "-DNDEBUG -Os ${CMAKE_CXX_FLAGS_MINSIZEREL}") - set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "-DNDEBUG -O2 -g ${CMAKE_CXX_FLAGS_RELWITHDEBINFO}") - set(CMAKE_CXX_FLAGS_RELEASE "-DNDEBUG -O3 ${CMAKE_CXX_FLAGS_RELEASE}") - if(NAMED_LANGUAGE_SUPPORT_INT) - set(CMAKE_OBJC_FLAGS "${C_TARGET_FLAGS} ${APPLE_TARGET_TRIPLE_FLAG} ${SDK_NAME_VERSION_FLAGS} ${BITCODE} ${VISIBILITY} ${FOBJC_ARC} ${OBJC_VARS} ${CMAKE_OBJC_FLAGS}") - set(CMAKE_OBJC_FLAGS_DEBUG "-O0 -g ${CMAKE_OBJC_FLAGS_DEBUG}") - set(CMAKE_OBJC_FLAGS_MINSIZEREL "-DNDEBUG -Os ${CMAKE_OBJC_FLAGS_MINSIZEREL}") - set(CMAKE_OBJC_FLAGS_RELWITHDEBINFO "-DNDEBUG -O2 -g ${CMAKE_OBJC_FLAGS_RELWITHDEBINFO}") - set(CMAKE_OBJC_FLAGS_RELEASE "-DNDEBUG -O3 ${CMAKE_OBJC_FLAGS_RELEASE}") - set(CMAKE_OBJCXX_FLAGS "${C_TARGET_FLAGS} ${APPLE_TARGET_TRIPLE_FLAG} ${SDK_NAME_VERSION_FLAGS} ${BITCODE} ${VISIBILITY} ${FOBJC_ARC} ${OBJC_VARS} ${CMAKE_OBJCXX_FLAGS}") - set(CMAKE_OBJCXX_FLAGS_DEBUG "-O0 -g ${CMAKE_OBJCXX_FLAGS_DEBUG}") - set(CMAKE_OBJCXX_FLAGS_MINSIZEREL "-DNDEBUG -Os ${CMAKE_OBJCXX_FLAGS_MINSIZEREL}") - set(CMAKE_OBJCXX_FLAGS_RELWITHDEBINFO "-DNDEBUG -O2 -g ${CMAKE_OBJCXX_FLAGS_RELWITHDEBINFO}") - set(CMAKE_OBJCXX_FLAGS_RELEASE "-DNDEBUG -O3 ${CMAKE_OBJCXX_FLAGS_RELEASE}") - endif() - set(CMAKE_C_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_C_LINK_FLAGS}") - set(CMAKE_CXX_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_CXX_LINK_FLAGS}") - if(NAMED_LANGUAGE_SUPPORT_INT) - set(CMAKE_OBJC_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_OBJC_LINK_FLAGS}") - set(CMAKE_OBJCXX_LINK_FLAGS "${C_TARGET_FLAGS} ${SDK_NAME_VERSION_FLAGS} -Wl,-search_paths_first ${CMAKE_OBJCXX_LINK_FLAGS}") - endif() - set(CMAKE_ASM_FLAGS "${CMAKE_C_FLAGS} -x assembler-with-cpp -arch ${CMAKE_OSX_ARCHITECTURES} ${APPLE_TARGET_TRIPLE_FLAG}") -endif() - -## Print status messages to inform of the current state -message(STATUS "Configuring ${SDK_NAME} build for platform: ${PLATFORM_INT}, architecture(s): ${ARCHS}") -message(STATUS "Using SDK: ${CMAKE_OSX_SYSROOT_INT}") -message(STATUS "Using C compiler: ${CMAKE_C_COMPILER}") -message(STATUS "Using CXX compiler: ${CMAKE_CXX_COMPILER}") -message(STATUS "Using libtool: ${BUILD_LIBTOOL}") -message(STATUS "Using install name tool: ${CMAKE_INSTALL_NAME_TOOL}") -if(DEFINED APPLE_TARGET_TRIPLE) - message(STATUS "Autoconf target triple: ${APPLE_TARGET_TRIPLE}") -endif() -message(STATUS "Using minimum deployment version: ${DEPLOYMENT_TARGET}" - " (SDK version: ${SDK_VERSION})") -if(MODERN_CMAKE) - message(STATUS "Merging integrated CMake 3.14+ iOS,tvOS,watchOS,macOS toolchain(s) with this toolchain!") - if(PLATFORM_INT MATCHES ".*COMBINED") - message(STATUS "Will combine built (static) artifacts into FAT lib...") - endif() -endif() -if(CMAKE_GENERATOR MATCHES "Xcode") - message(STATUS "Using Xcode version: ${XCODE_VERSION_INT}") -endif() -message(STATUS "CMake version: ${CMAKE_VERSION}") -if(DEFINED SDK_NAME_VERSION_FLAGS) - message(STATUS "Using version flags: ${SDK_NAME_VERSION_FLAGS}") -endif() -message(STATUS "Using a data_ptr size of: ${CMAKE_CXX_SIZEOF_DATA_PTR}") -if(ENABLE_BITCODE_INT) - message(STATUS "Bitcode: Enabled") -else() - message(STATUS "Bitcode: Disabled") -endif() - -if(ENABLE_ARC_INT) - message(STATUS "ARC: Enabled") -else() - message(STATUS "ARC: Disabled") -endif() - -if(ENABLE_VISIBILITY_INT) - message(STATUS "Hiding symbols: Disabled") -else() - message(STATUS "Hiding symbols: Enabled") -endif() - -# Set global properties -set_property(GLOBAL PROPERTY PLATFORM "${PLATFORM}") -set_property(GLOBAL PROPERTY APPLE_TARGET_TRIPLE "${APPLE_TARGET_TRIPLE_INT}") -set_property(GLOBAL PROPERTY SDK_VERSION "${SDK_VERSION}") -set_property(GLOBAL PROPERTY XCODE_VERSION "${XCODE_VERSION_INT}") -set_property(GLOBAL PROPERTY OSX_ARCHITECTURES "${CMAKE_OSX_ARCHITECTURES}") - -# Export configurable variables for the try_compile() command. -set(CMAKE_TRY_COMPILE_PLATFORM_VARIABLES - PLATFORM - XCODE_VERSION_INT - SDK_VERSION - NAMED_LANGUAGE_SUPPORT - DEPLOYMENT_TARGET - CMAKE_DEVELOPER_ROOT - CMAKE_OSX_SYSROOT_INT - ENABLE_BITCODE - ENABLE_ARC - CMAKE_ASM_COMPILER - CMAKE_C_COMPILER - CMAKE_C_COMPILER_TARGET - CMAKE_CXX_COMPILER - CMAKE_CXX_COMPILER_TARGET - BUILD_LIBTOOL - CMAKE_INSTALL_NAME_TOOL - CMAKE_C_FLAGS - CMAKE_C_DEBUG - CMAKE_C_MINSIZEREL - CMAKE_C_RELWITHDEBINFO - CMAKE_C_RELEASE - CMAKE_CXX_FLAGS - CMAKE_CXX_FLAGS_DEBUG - CMAKE_CXX_FLAGS_MINSIZEREL - CMAKE_CXX_FLAGS_RELWITHDEBINFO - CMAKE_CXX_FLAGS_RELEASE - CMAKE_C_LINK_FLAGS - CMAKE_CXX_LINK_FLAGS - CMAKE_ASM_FLAGS -) - -if(NAMED_LANGUAGE_SUPPORT_INT) - list(APPEND CMAKE_TRY_COMPILE_PLATFORM_VARIABLES - CMAKE_OBJC_FLAGS - CMAKE_OBJC_DEBUG - CMAKE_OBJC_MINSIZEREL - CMAKE_OBJC_RELWITHDEBINFO - CMAKE_OBJC_RELEASE - CMAKE_OBJCXX_FLAGS - CMAKE_OBJCXX_DEBUG - CMAKE_OBJCXX_MINSIZEREL - CMAKE_OBJCXX_RELWITHDEBINFO - CMAKE_OBJCXX_RELEASE - CMAKE_OBJC_LINK_FLAGS - CMAKE_OBJCXX_LINK_FLAGS - ) -endif() - -set(CMAKE_PLATFORM_HAS_INSTALLNAME 1) -set(CMAKE_SHARED_LINKER_FLAGS "-rpath @executable_path/Frameworks -rpath @loader_path/Frameworks") -set(CMAKE_SHARED_LIBRARY_CREATE_C_FLAGS "-dynamiclib -Wl,-headerpad_max_install_names") -set(CMAKE_SHARED_MODULE_CREATE_C_FLAGS "-bundle -Wl,-headerpad_max_install_names") -set(CMAKE_SHARED_MODULE_LOADER_C_FLAG "-Wl,-bundle_loader,") -set(CMAKE_SHARED_MODULE_LOADER_CXX_FLAG "-Wl,-bundle_loader,") -set(CMAKE_FIND_LIBRARY_SUFFIXES ".tbd" ".dylib" ".so" ".a") -set(CMAKE_SHARED_LIBRARY_SONAME_C_FLAG "-install_name") - -# Set the find root to the SDK developer roots. -# Note: CMAKE_FIND_ROOT_PATH is only useful when cross-compiling. Thus, do not set on macOS builds. -if(NOT PLATFORM_INT MATCHES "^MAC.*$") - list(APPEND CMAKE_FIND_ROOT_PATH "${CMAKE_OSX_SYSROOT_INT}" CACHE INTERNAL "") - set(CMAKE_IGNORE_PATH "/System/Library/Frameworks;/usr/local/lib" CACHE INTERNAL "") -endif() - -# Default to searching for frameworks first. -set(CMAKE_FIND_FRAMEWORK FIRST) - -# Set up the default search directories for frameworks. -if(PLATFORM_INT MATCHES "^MAC_CATALYST") - set(CMAKE_FRAMEWORK_PATH - ${CMAKE_DEVELOPER_ROOT}/Library/PrivateFrameworks - ${CMAKE_OSX_SYSROOT_INT}/System/Library/Frameworks - ${CMAKE_OSX_SYSROOT_INT}/System/iOSSupport/System/Library/Frameworks - ${CMAKE_FRAMEWORK_PATH} CACHE INTERNAL "") -else() - set(CMAKE_FRAMEWORK_PATH - ${CMAKE_DEVELOPER_ROOT}/Library/PrivateFrameworks - ${CMAKE_OSX_SYSROOT_INT}/System/Library/Frameworks - ${CMAKE_FRAMEWORK_PATH} CACHE INTERNAL "") -endif() - -# By default, search both the specified iOS SDK and the remainder of the host filesystem. -if(NOT CMAKE_FIND_ROOT_PATH_MODE_PROGRAM) - set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH CACHE INTERNAL "") -endif() -if(NOT CMAKE_FIND_ROOT_PATH_MODE_LIBRARY) - set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH CACHE INTERNAL "") -endif() -if(NOT CMAKE_FIND_ROOT_PATH_MODE_INCLUDE) - set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH CACHE INTERNAL "") -endif() -if(NOT CMAKE_FIND_ROOT_PATH_MODE_PACKAGE) - set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE BOTH CACHE INTERNAL "") -endif() - -# -# Some helper-macros below to simplify and beautify the CMakeFile -# - -# This little macro lets you set any Xcode specific property. -macro(set_xcode_property TARGET XCODE_PROPERTY XCODE_VALUE XCODE_RELVERSION) - set(XCODE_RELVERSION_I "${XCODE_RELVERSION}") - if(XCODE_RELVERSION_I STREQUAL "All") - set_property(TARGET ${TARGET} PROPERTY XCODE_ATTRIBUTE_${XCODE_PROPERTY} "${XCODE_VALUE}") - else() - set_property(TARGET ${TARGET} PROPERTY XCODE_ATTRIBUTE_${XCODE_PROPERTY}[variant=${XCODE_RELVERSION_I}] "${XCODE_VALUE}") - endif() -endmacro(set_xcode_property) - -# This macro lets you find executable programs on the host system. -macro(find_host_package) - set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) - set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY NEVER) - set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE NEVER) - set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE NEVER) - set(_TOOLCHAIN_IOS ${IOS}) - set(IOS OFF) - find_package(${ARGN}) - set(IOS ${_TOOLCHAIN_IOS}) - set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM BOTH) - set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY BOTH) - set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE BOTH) - set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE BOTH) -endmacro(find_host_package) From e0244c69a3b1f84457b39b9a8d1459411a76191c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 9 Aug 2022 13:35:05 +0300 Subject: [PATCH 098/131] add CMake presets for iOS --- .gitignore | 1 + CMakeLists.txt | 1 + CMakePresets.json | 68 +++++++++++++++++++++++++++++++++++++++++++---- configure_ios.sh | 19 ------------- 4 files changed, 65 insertions(+), 24 deletions(-) delete mode 100755 configure_ios.sh diff --git a/.gitignore b/.gitignore index 3cc5ecc37..c91559bcd 100644 --- a/.gitignore +++ b/.gitignore @@ -40,6 +40,7 @@ VCMI_VS11.sdf *.ipch VCMI_VS11.opensdf .DS_Store +CMakeUserPresets.json # Visual Studio *.suo diff --git a/CMakeLists.txt b/CMakeLists.txt index 7d5789772..1c57c3f00 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -160,6 +160,7 @@ set(CMAKE_MAP_IMPORTED_CONFIG_RELEASE Release RelWithDebInfo MinSizeRel "") set(CMAKE_XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC YES) set(CMAKE_XCODE_ATTRIBUTE_DEBUG_INFORMATION_FORMAT[variant=Debug] dwarf) set(CMAKE_XCODE_ATTRIBUTE_ENABLE_BITCODE NO) +set(CMAKE_XCODE_ATTRIBUTE_GCC_WARN_64_TO_32_BIT_CONVERSION NO) set(CMAKE_XCODE_ATTRIBUTE_MARKETING_VERSION ${APP_SHORT_VERSION}) set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH NO) set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH[variant=Debug] YES) diff --git a/CMakePresets.json b/CMakePresets.json index 20a5a23ed..8626fc6c1 100644 --- a/CMakePresets.json +++ b/CMakePresets.json @@ -2,19 +2,31 @@ "version": 2, "configurePresets": [ { - "name": "default-release", + "name": "release-binary-dir", + "hidden": true, + "binaryDir": "${sourceDir}/out/build/${presetName}" + }, + { + "name": "base-release", + "inherits": "release-binary-dir", "hidden": true, - "binaryDir": "${sourceDir}/out/build/${presetName}", - "generator": "Ninja", "cacheVariables": { "CMAKE_INSTALL_PREFIX": "${sourceDir}/out/install/${presetName}", "PACKAGE_FILE_NAME" : "$env{VCMI_PACKAGE_FILE_NAME}", "PACKAGE_NAME_SUFFIX" : "$env{VCMI_PACKAGE_NAME_SUFFIX}", "CMAKE_BUILD_TYPE": "RelWithDebInfo", - "FORCE_BUNDLED_FL": "OFF", "ENABLE_TEST": "OFF" } }, + { + "name": "default-release", + "inherits": "base-release", + "hidden": true, + "generator": "Ninja", + "cacheVariables": { + "FORCE_BUNDLED_FL": "OFF" + } + }, { "name" : "linux-release", "inherits" : "default-release", @@ -87,6 +99,41 @@ "description": "VCMI MacOS Xcode", "inherits": "default-release", "generator": "Xcode" + }, + { + "name": "ios-device", + "displayName": "Base iOS device", + "description": "Base VCMI preset for iOS device", + "generator": "Xcode", + "binaryDir": "../build-${presetName}", + "cacheVariables": { + "CMAKE_SYSTEM_NAME": "iOS", + "FORCE_BUNDLED_FL": "ON", + "FORCE_BUNDLED_MINIZIP": "ON" + } + }, + { + "name": "ios-simulator", + "displayName": "Base iOS simulator", + "description": "Base VCMI preset for iOS simulator", + "inherits": "ios-device", + "cacheVariables": { + "CMAKE_OSX_SYSROOT": "iphonesimulator" + } + }, + { + "name": "ios-release", + "displayName": "iOS release", + "description": "VCMI iOS release", + "inherits": [ + "base-release", + "ios-device", + "release-binary-dir" + ], + "cacheVariables": { + "BUNDLE_IDENTIFIER_PREFIX": "eu.vcmi", + "CMAKE_PREFIX_PATH": "TODO" + } } ], "buildPresets": [ @@ -135,6 +182,17 @@ "name": "windows-msvc-relwithdebinfo", "configurePreset": "windows-msvc-release", "inherits": "default-release" + }, + { + "name": "ios-release", + "configurePreset": "ios-release", + "inherits": "default-release", + "targets": ["vcmiclient"], + "nativeToolOptions": [ + "-quiet", + "CODE_SIGNING_ALLOWED_FOR_APPS=NO", + "GCC_OPTIMIZATION_LEVEL=3" + ] } ], "testPresets": [ @@ -172,4 +230,4 @@ "inherits": "default-release" } ] -} \ No newline at end of file +} diff --git a/configure_ios.sh b/configure_ios.sh deleted file mode 100755 index a27ef6c33..000000000 --- a/configure_ios.sh +++ /dev/null @@ -1,19 +0,0 @@ -#!/usr/bin/env bash - -prefixPath=~/dev/vcmi/vcmi-ios-depends/build/iphoneos -if [[ "$1" ]]; then - prefixPath=~/dev/vcmi/vcmi-ios-depends/build/iphonesimulator -fi - -# -DCMAKE_OSX_SYSROOT=iphonesimulator - -cmake ../vcmi -G Xcode \ - -DCMAKE_SYSTEM_NAME=iOS \ - -DFORCE_BUNDLED_MINIZIP=ON \ - -DBUNDLE_IDENTIFIER_PREFIX=com.kambala \ - -Wno-dev \ - -DCMAKE_CXX_COMPILER_LAUNCHER=ccache \ - -DCMAKE_PREFIX_PATH="$prefixPath" \ - -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY='Apple Development' \ - -DCMAKE_XCODE_ATTRIBUTE_DEVELOPMENT_TEAM='4XHN44TEVG' - # -DCMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED=NO From 8dcd3146e7b628b8fb29c1f5ede1e64e239a1681 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 11 Aug 2022 12:12:33 +0300 Subject: [PATCH 099/131] generate zip with ipa structure using cpack fix kambala-decapitator/vcmi#6 --- CMakeLists.txt | 10 +++++++--- client/CMakeLists.txt | 5 +++-- apple_codesign.sh => ios/codesign.sh | 0 ios/zip2ipa.sh | 9 +++++++++ 4 files changed, 19 insertions(+), 5 deletions(-) rename apple_codesign.sh => ios/codesign.sh (100%) create mode 100755 ios/zip2ipa.sh diff --git a/CMakeLists.txt b/CMakeLists.txt index 1c57c3f00..bf5a331c9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -439,9 +439,9 @@ endif() # Installation section # ####################################### -install(DIRECTORY config DESTINATION ${DATA_DIR} COMPONENT core) -install(DIRECTORY scripts DESTINATION ${DATA_DIR} COMPONENT core) -install(DIRECTORY Mods DESTINATION ${DATA_DIR} COMPONENT core) +install(DIRECTORY config DESTINATION ${DATA_DIR}) +install(DIRECTORY scripts DESTINATION ${DATA_DIR}) +install(DIRECTORY Mods DESTINATION ${DATA_DIR}) # that script is useless for Windows if(NOT WIN32 AND NOT APPLE_IOS) @@ -584,6 +584,10 @@ elseif(APPLE_MACOS AND NOT ENABLE_MONOLITHIC_INSTALL) # Bundle fixing code must be in separate directory to be executed after all other install code add_subdirectory(osx) +elseif(APPLE_IOS) + set(CPACK_GENERATOR ZIP) + set(CPACK_INCLUDE_TOPLEVEL_DIRECTORY OFF) + set(CPACK_INSTALL_CMAKE_PROJECTS "${CMAKE_CURRENT_BINARY_DIR};${CMAKE_PROJECT_NAME};app;/") else() set(CPACK_GENERATOR TGZ) endif() diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 90f279776..e0f38ee2f 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -264,9 +264,10 @@ enable_pch(vcmiclient) if(APPLE_IOS) add_custom_command(TARGET vcmiclient POST_BUILD - COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --config "$" --prefix "$" - COMMAND ${CMAKE_SOURCE_DIR}/apple_codesign.sh + COMMAND ${CMAKE_COMMAND} --install "${CMAKE_BINARY_DIR}" --component "${CMAKE_INSTALL_DEFAULT_COMPONENT_NAME}" --config "$" --prefix "$" + COMMAND ${CMAKE_SOURCE_DIR}/ios/codesign.sh ) + install(TARGETS vcmiclient DESTINATION Payload COMPONENT app) # for ipa generation with cpack else() install(TARGETS vcmiclient DESTINATION ${BIN_DIR}) endif() diff --git a/apple_codesign.sh b/ios/codesign.sh similarity index 100% rename from apple_codesign.sh rename to ios/codesign.sh diff --git a/ios/zip2ipa.sh b/ios/zip2ipa.sh new file mode 100755 index 000000000..2c37459d1 --- /dev/null +++ b/ios/zip2ipa.sh @@ -0,0 +1,9 @@ +#!/usr/bin/env bash + +generatedZip="$1" +if [[ -z "$generatedZip" ]]; then + echo 'generated zip not provided as param' + exit 1 +fi + +mv "$generatedZip" "$(basename "$generatedZip" .zip).ipa" From d3e33b096f252eac3e075ffa1ff6035bb137487f Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 11 Aug 2022 13:14:02 +0300 Subject: [PATCH 100/131] prepare CI for iOS --- .github/workflows/github.yml | 8 ++++++++ CI/ios/before_install.sh | 7 +++++++ CI/ios/post_pack.sh | 3 +++ CMakePresets.json | 6 +++--- 4 files changed, 21 insertions(+), 3 deletions(-) create mode 100755 CI/ios/before_install.sh create mode 100755 CI/ios/post_pack.sh diff --git a/.github/workflows/github.yml b/.github/workflows/github.yml index 2220e982e..0a29cdcef 100644 --- a/.github/workflows/github.yml +++ b/.github/workflows/github.yml @@ -90,6 +90,12 @@ jobs: preset: macos-arm-conan-ninja-release conan_profile: macos-arm artifact_platform: arm + - platform: ios + os: macos-12 + test: 0 + pack: 1 + extension: ipa + preset: ios-release - platform: mxe os: ubuntu-20.04 mxe: i686-w64-mingw32.shared @@ -189,6 +195,8 @@ jobs: cd '${{github.workspace}}/out/build/${{matrix.preset}}' CPACK_PATH=`which -a cpack | grep -m1 -v -i chocolatey` "$CPACK_PATH" -C ${{env.BUILD_TYPE}} ${{ matrix.cpack_args }} + test -f '${{github.workspace}}/CI/${{matrix.platform}}/post_pack.sh' \ + && '${{github.workspace}}/CI/${{matrix.platform}}/post_pack.sh' '${{github.workspace}}' "$(ls '${{ env.VCMI_PACKAGE_FILE_NAME }}'.*)" rm -rf _CPack_Packages - name: Additional logs diff --git a/CI/ios/before_install.sh b/CI/ios/before_install.sh new file mode 100755 index 000000000..137b3063f --- /dev/null +++ b/CI/ios/before_install.sh @@ -0,0 +1,7 @@ +#!/usr/bin/env bash + +echo DEVELOPER_DIR=/Applications/Xcode_13.4.1.app >> $GITHUB_ENV + +curl -L 'https://github.com/kambala-decapitator/vcmi-ios-depends/releases/latest/download/vcmi-ios-depends-xc13.2.1.txz' \ + | tar -xf - +build/fix_install_paths.command diff --git a/CI/ios/post_pack.sh b/CI/ios/post_pack.sh new file mode 100755 index 000000000..8fc66bd3d --- /dev/null +++ b/CI/ios/post_pack.sh @@ -0,0 +1,3 @@ +#!/usr/bin/env bash + +"$1/ios/zip2ipa.sh" "$2" diff --git a/CMakePresets.json b/CMakePresets.json index 8626fc6c1..14991651c 100644 --- a/CMakePresets.json +++ b/CMakePresets.json @@ -132,7 +132,7 @@ ], "cacheVariables": { "BUNDLE_IDENTIFIER_PREFIX": "eu.vcmi", - "CMAKE_PREFIX_PATH": "TODO" + "CMAKE_PREFIX_PATH": "${sourceDir}/build/iphoneos" } } ], @@ -187,11 +187,11 @@ "name": "ios-release", "configurePreset": "ios-release", "inherits": "default-release", + "configuration": "Release", "targets": ["vcmiclient"], "nativeToolOptions": [ "-quiet", - "CODE_SIGNING_ALLOWED_FOR_APPS=NO", - "GCC_OPTIMIZATION_LEVEL=3" + "CODE_SIGNING_ALLOWED_FOR_APPS=NO" ] } ], From dab9d206f1a09bd9457dd35a91cf459c6999386d Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 12 Aug 2022 11:29:36 +0300 Subject: [PATCH 101/131] Revert "don't build Nullkiller for 32-bit" This reverts commit 0a5c5c3e1da76f0e202c61e9abfca9603ca7af7c. --- AI/Nullkiller/CMakeLists.txt | 6 ------ 1 file changed, 6 deletions(-) diff --git a/AI/Nullkiller/CMakeLists.txt b/AI/Nullkiller/CMakeLists.txt index 39d4adee0..0ccf0a281 100644 --- a/AI/Nullkiller/CMakeLists.txt +++ b/AI/Nullkiller/CMakeLists.txt @@ -127,12 +127,6 @@ if(ANDROID) # android compiles ai libs into main lib directly, so we skip this l endif() add_library(Nullkiller SHARED ${Nullkiller_SRCS} ${Nullkiller_HEADERS}) -if(APPLE_IOS) - # Nullkiller dependencies - TBB and LuaJIT - can only be built for 64-bit - set_target_properties(Nullkiller PROPERTIES - XCODE_ATTRIBUTE_EXCLUDED_ARCHS "$(ARCHS_STANDARD_32_BIT)" - ) -endif() target_include_directories(Nullkiller PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) From 4452ddb4043f8ef73d201d993b15c89a02da8252 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Sun, 14 Aug 2022 12:34:14 +0300 Subject: [PATCH 102/131] fix typo in FindFFmpeg --- cmake_modules/Findffmpeg.cmake | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmake_modules/Findffmpeg.cmake b/cmake_modules/Findffmpeg.cmake index 4cd749c67..2e813d9a9 100644 --- a/cmake_modules/Findffmpeg.cmake +++ b/cmake_modules/Findffmpeg.cmake @@ -175,7 +175,7 @@ foreach (_ffmpeg_component IN LISTS ffmpeg_FIND_COMPONENTS) "${ffmpeg_${_ffmpeg_component}_INCLUDE_DIRS}") list(APPEND ffmpeg_LIBRARIES "${ffmpeg_${_ffmpeg_component}_LIBRARIES}") - if (FFMEG_FIND_REQUIRED_${_ffmpeg_component}) + if (FFMPEG_FIND_REQUIRED_${_ffmpeg_component}) list(APPEND _ffmpeg_required_vars "ffmpeg_${_ffmpeg_required_vars}_INCLUDE_DIRS" "ffmpeg_${_ffmpeg_required_vars}_LIBRARIES") From 7631e7ef06ce037a2fffa6557e41785a787f8554 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 10:43:06 +0300 Subject: [PATCH 103/131] move linking to system frameworks to appropriate Find* scripts --- client/CMakeLists.txt | 22 ++++------------------ cmake_modules/FindSDL2.cmake | 18 ++++++++++++++++++ cmake_modules/FindSDL2_image.cmake | 9 +++++++++ cmake_modules/FindSDL2_mixer.cmake | 6 ++++++ 4 files changed, 37 insertions(+), 18 deletions(-) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index e0f38ee2f..5345d7fff 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -189,23 +189,14 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE - "-lbz2" + # FFmpeg + bz2 + iconv + z "-framework AudioToolbox" "-framework AVFoundation" - "-framework CoreGraphics" "-framework CoreMedia" - "-framework CoreMotion" - "-framework CoreServices" - "-framework CoreVideo" - "-framework Foundation" - "-framework GameController" - "-framework ImageIO" - "-framework Metal" - "-framework OpenGLES" - "-framework QuartzCore" - "-framework UIKit" "-framework VideoToolbox" - "-weak_framework CoreHaptics" ) set_target_properties(vcmiclient PROPERTIES @@ -247,11 +238,6 @@ if(ffmpeg_LIBRARIES) target_link_libraries(vcmiclient PRIVATE ${ffmpeg_LIBRARIES} ) - if(APPLE_IOS) - target_link_libraries(vcmiclient PRIVATE - iconv - ) - endif() else() target_compile_definitions(vcmiclient PRIVATE DISABLE_VIDEO) endif() diff --git a/cmake_modules/FindSDL2.cmake b/cmake_modules/FindSDL2.cmake index fde86e409..c3c537a42 100644 --- a/cmake_modules/FindSDL2.cmake +++ b/cmake_modules/FindSDL2.cmake @@ -345,6 +345,24 @@ if(SDL2_FOUND) if (APPLE_MACOS) set_property(TARGET SDL2::SDL2 APPEND PROPERTY INTERFACE_LINK_OPTIONS -framework Cocoa) + elseif (APPLE_IOS) + target_link_libraries(SDL2::SDL2 INTERFACE + "-framework AudioToolbox" + "-framework AVFoundation" + "-framework CoreAudio" + "-framework CoreBluetooth" + "-framework CoreFoundation" + "-framework CoreGraphics" + "-framework CoreMotion" + "-framework CoreVideo" + "-framework GameController" + "-framework IOKit" + "-framework Metal" + "-framework OpenGLES" + "-framework QuartzCore" + "-framework UIKit" + "-weak_framework CoreHaptics" + ) endif() else() # For threads, as mentioned Apple doesn't need this. diff --git a/cmake_modules/FindSDL2_image.cmake b/cmake_modules/FindSDL2_image.cmake index 7373818fb..96fa819c9 100644 --- a/cmake_modules/FindSDL2_image.cmake +++ b/cmake_modules/FindSDL2_image.cmake @@ -227,5 +227,14 @@ if(SDL2_IMAGE_FOUND) IMPORTED_LOCATION "${SDL2_IMAGE_LIBRARY}" INTERFACE_INCLUDE_DIRECTORIES "${SDL2_IMAGE_INCLUDE_DIR}" INTERFACE_LINK_LIBRARIES SDL2::SDL2) + if (APPLE_IOS) + target_link_libraries(SDL2::Image INTERFACE + "-framework CoreGraphics" + "-framework Foundation" + "-framework ImageIO" + "-framework MobileCoreServices" + "-framework UIKit" + ) + endif() endif() endif() diff --git a/cmake_modules/FindSDL2_mixer.cmake b/cmake_modules/FindSDL2_mixer.cmake index 89e246846..8e9c9ac10 100644 --- a/cmake_modules/FindSDL2_mixer.cmake +++ b/cmake_modules/FindSDL2_mixer.cmake @@ -216,5 +216,11 @@ if(SDL2_MIXER_FOUND) IMPORTED_LOCATION "${SDL2_MIXER_LIBRARY}" INTERFACE_INCLUDE_DIRECTORIES "${SDL2_MIXER_INCLUDE_DIR}" INTERFACE_LINK_LIBRARIES SDL2::SDL2) + if (APPLE_IOS) + target_link_libraries(SDL2::Mixer INTERFACE + "-framework AudioToolbox" + "-framework CoreServices" + ) + endif() endif() endif() From 902de3af7cc289843a970a69d454c418bdcd7fdb Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 10:44:45 +0300 Subject: [PATCH 104/131] CMake cleanup --- CMakeLists.txt | 17 ++++++++--------- client/CMakeLists.txt | 2 +- 2 files changed, 9 insertions(+), 10 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index bf5a331c9..1b1866f3e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -32,7 +32,7 @@ if(APPLE) else() set(APPLE_IOS 1) endif() -endif(APPLE) +endif() if(APPLE_IOS) set(BUILD_SINGLE_APP 1) @@ -52,11 +52,10 @@ endif() set(VCMI_VERSION_MAJOR 1) set(VCMI_VERSION_MINOR 0) set(VCMI_VERSION_PATCH 0) -if(APPLE_IOS) - set(APP_SHORT_VERSION "${VCMI_VERSION_MAJOR}.${VCMI_VERSION_MINOR}") - if(NOT VCMI_VERSION_PATCH EQUAL 0) - string(APPEND APP_SHORT_VERSION ".${VCMI_VERSION_PATCH}") - endif() + +set(APP_SHORT_VERSION "${VCMI_VERSION_MAJOR}.${VCMI_VERSION_MINOR}") +if(NOT VCMI_VERSION_PATCH EQUAL 0) + string(APPEND APP_SHORT_VERSION ".${VCMI_VERSION_PATCH}") endif() option(ENABLE_ERM "Enable compilation of ERM scripting module" OFF) @@ -177,7 +176,7 @@ if(APPLE_IOS) set(CMAKE_XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED_FOR_APPS YES) set(CMAKE_XCODE_ATTRIBUTE_PRODUCT_BUNDLE_IDENTIFIER "${BUNDLE_IDENTIFIER_PREFIX}.$(PRODUCT_NAME)") set(CMAKE_XCODE_ATTRIBUTE_TARGETED_DEVICE_FAMILY "1,2") -endif(APPLE_IOS) +endif() if(MINGW OR MSVC) # Windows Vista or newer for FuzzyLite 6 to compile @@ -369,7 +368,7 @@ elseif(APPLE) else() set(LIB_DIR "Frameworks") set(DATA_DIR ".") - endif(APPLE_MACOS) + endif() endif() else() # includes lib path which determines where to install shared libraries (either /lib or /lib64) @@ -443,7 +442,7 @@ install(DIRECTORY config DESTINATION ${DATA_DIR}) install(DIRECTORY scripts DESTINATION ${DATA_DIR}) install(DIRECTORY Mods DESTINATION ${DATA_DIR}) -# that script is useless for Windows +# that script is useless for Windows and iOS if(NOT WIN32 AND NOT APPLE_IOS) install(FILES vcmibuilder DESTINATION ${BIN_DIR} PERMISSIONS OWNER_WRITE OWNER_READ OWNER_EXECUTE diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 5345d7fff..ae382dee3 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -212,7 +212,7 @@ elseif(APPLE_IOS) set_source_files_properties(${XCODE_RESOURCE_PATH} PROPERTIES MACOSX_PACKAGE_LOCATION Resources) # workaround to prevent CMAKE_SKIP_PRECOMPILE_HEADERS being added as compile flag - # add max version condition when https://gitlab.kitware.com/cmake/cmake/-/issues/23821 is fixed + # add max version condition when https://gitlab.kitware.com/cmake/cmake/-/merge_requests/7562 is merged if(CMAKE_VERSION VERSION_GREATER_EQUAL "3.22.0") set_source_files_properties(${XCODE_RESOURCE_PATH} PROPERTIES LANGUAGE CXX) endif() From 5b50d69db19c98c3854308c618322764014548a0 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 10:45:54 +0300 Subject: [PATCH 105/131] use Android's letterboxing code and code style cleanup --- client/CMT.cpp | 57 ++++++++++++++++++++++++-------------------------- 1 file changed, 27 insertions(+), 30 deletions(-) diff --git a/client/CMT.cpp b/client/CMT.cpp index da184f672..3b7a4f696 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -1101,40 +1101,38 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn if(nullptr == mainWindow) { - #if defined(VCMI_ANDROID) || defined(VCMI_IOS) - auto createWindow = [displayIndex](Uint32 extraFlags) -> bool { - mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN | extraFlags); - return mainWindow != nullptr; - }; +#if defined(VCMI_ANDROID) || defined(VCMI_IOS) + auto createWindow = [displayIndex](Uint32 extraFlags) -> bool { + mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), SDL_WINDOWPOS_UNDEFINED_DISPLAY(displayIndex), 0, 0, SDL_WINDOW_FULLSCREEN | extraFlags); + return mainWindow != nullptr; + }; -#ifdef VCMI_IOS - SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); - SDL_SetHint(SDL_HINT_RETURN_KEY_HIDES_IME, "1"); +# ifdef VCMI_IOS + SDL_SetHint(SDL_HINT_IOS_HIDE_HOME_INDICATOR, "1"); + SDL_SetHint(SDL_HINT_RETURN_KEY_HIDES_IME, "1"); SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "best"); - Uint32 windowFlags = SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI; - if(!createWindow(windowFlags | SDL_WINDOW_METAL)) - { - logGlobal->warn("Metal unavailable, using OpenGLES"); - createWindow(windowFlags); - } + Uint32 windowFlags = SDL_WINDOW_BORDERLESS | SDL_WINDOW_ALLOW_HIGHDPI; + if(!createWindow(windowFlags | SDL_WINDOW_METAL)) + { + logGlobal->warn("Metal unavailable, using OpenGLES"); + createWindow(windowFlags); + } +# else + createWindow(0); +# endif // VCMI_IOS - // TODO: can android use this too? - auto shouldFixAspectRatio = true; - int screenWidth, screenHeight; - SDL_GetWindowSize(mainWindow, &screenWidth, &screenHeight); -#else - createWindow(0); - - SDL_Rect screenRect; - auto shouldFixAspectRatio = SDL_GetDisplayBounds(0, &screenRect) == 0; - int screenWidth = screenRect.w, screenHeight = screenRect.h; -#endif // SDL on mobile doesn't do proper letterboxing, and will show an annoying flickering in the blank space in case you're not using the full screen estate // That's why we need to make sure our width and height we'll use below have the same aspect ratio as the screen itself to ensure we fill the full screen estate - if(shouldFixAspectRatio) + + SDL_Rect screenRect; + + if(SDL_GetDisplayBounds(0, &screenRect) == 0) { - auto aspect = static_cast(screenWidth) / screenHeight; + const auto screenWidth = screenRect.w; + const auto screenHeight = screenRect.h; + + const auto aspect = static_cast(screenWidth) / screenHeight; logGlobal->info("Screen size and aspect ratio: %dx%d (%lf)", screenWidth, screenHeight, aspect); @@ -1153,8 +1151,7 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn { logGlobal->error("Can't fix aspect ratio for screen"); } - #else - +#else if(fullscreen) { if(realFullscreen) @@ -1167,7 +1164,7 @@ static bool recreateWindow(int w, int h, int bpp, bool fullscreen, int displayIn { mainWindow = SDL_CreateWindow(NAME.c_str(), SDL_WINDOWPOS_CENTERED_DISPLAY(displayIndex),SDL_WINDOWPOS_CENTERED_DISPLAY(displayIndex), w, h, 0); } - #endif +#endif // defined(VCMI_ANDROID) || defined(VCMI_IOS) if(nullptr == mainWindow) { From 35e1b86683d78de09a294f0a976d331bd8b715ab Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 12:18:52 +0300 Subject: [PATCH 106/131] remove no longer needed adjustments --- lib/filesystem/AdapterLoaders.cpp | 4 +--- lib/serializer/Connection.cpp | 3 +-- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/lib/filesystem/AdapterLoaders.cpp b/lib/filesystem/AdapterLoaders.cpp index 361bcf6c6..4a9e18614 100644 --- a/lib/filesystem/AdapterLoaders.cpp +++ b/lib/filesystem/AdapterLoaders.cpp @@ -156,9 +156,7 @@ std::vector CFilesystemList::getResourcesWithName std::vector ret; for (auto & loader : loaders) - // todo ios - if (loader) - boost::range::copy(loader->getResourcesWithName(resourceName), std::back_inserter(ret)); + boost::range::copy(loader->getResourcesWithName(resourceName), std::back_inserter(ret)); return ret; } diff --git a/lib/serializer/Connection.cpp b/lib/serializer/Connection.cpp index bce54123f..40bb302a9 100644 --- a/lib/serializer/Connection.cpp +++ b/lib/serializer/Connection.cpp @@ -73,8 +73,7 @@ CConnection::CConnection(std::string host, ui16 port, std::string Name, std::str boost::system::error_code error = asio::error::host_not_found; socket = std::make_shared(*io_service); tcp::resolver resolver(*io_service); - // todo ios: is new param really needed? - tcp::resolver::iterator end, pom, endpoint_iterator = resolver.resolve(tcp::resolver::query(host, std::to_string(port), resolver_query_base::numeric_service), error); + tcp::resolver::iterator end, pom, endpoint_iterator = resolver.resolve(tcp::resolver::query(host, std::to_string(port)),error); if(error) { logNetwork->error("Problem with resolving: \n%s", error.message()); From 0503993b8d1cdb36a7614a44b7b0e9007c2aec07 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 12:20:38 +0300 Subject: [PATCH 107/131] avoid reloading server's filesystem stuff --- lib/filesystem/Filesystem.cpp | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/lib/filesystem/Filesystem.cpp b/lib/filesystem/Filesystem.cpp index 45e423a56..5d1c60620 100644 --- a/lib/filesystem/Filesystem.cpp +++ b/lib/filesystem/Filesystem.cpp @@ -172,8 +172,11 @@ void CResourceHandler::initialize() // |-saves // |-config + // when built as single process, server can be started multiple times + if (globalResourceHandler.rootLoader) + return; + globalResourceHandler.rootLoader = vstd::make_unique(); - knownLoaders.clear(); knownLoaders["root"] = globalResourceHandler.rootLoader.get(); knownLoaders["saves"] = new CFilesystemLoader("SAVES/", VCMIDirs::get().userSavePath()); knownLoaders["config"] = new CFilesystemLoader("CONFIG/", VCMIDirs::get().userConfigPath()); From f115a49926e5a59944e786f5739b6369a774d234 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 14:33:46 +0300 Subject: [PATCH 108/131] update app icon fix kambala-decapitator/vcmi#41 --- .../AppIcon.appiconset/Icon-App-20x20@1x.png | Bin 517 -> 1335 bytes .../AppIcon.appiconset/Icon-App-20x20@2x.png | Bin 811 -> 3599 bytes .../AppIcon.appiconset/Icon-App-20x20@3x.png | Bin 1132 -> 6294 bytes .../AppIcon.appiconset/Icon-App-29x29@1x.png | Bin 636 -> 2310 bytes .../AppIcon.appiconset/Icon-App-29x29@2x.png | Bin 1101 -> 6022 bytes .../AppIcon.appiconset/Icon-App-29x29@3x.png | Bin 1600 -> 10581 bytes .../AppIcon.appiconset/Icon-App-40x40@1x.png | Bin 811 -> 3599 bytes .../AppIcon.appiconset/Icon-App-40x40@2x.png | Bin 1450 -> 9270 bytes .../AppIcon.appiconset/Icon-App-40x40@3x.png | Bin 2234 -> 17311 bytes .../AppIcon.appiconset/Icon-App-60x60@2x.png | Bin 2234 -> 17311 bytes .../AppIcon.appiconset/Icon-App-60x60@3x.png | Bin 3679 -> 32216 bytes .../AppIcon.appiconset/Icon-App-76x76@1x.png | Bin 1396 -> 8740 bytes .../AppIcon.appiconset/Icon-App-76x76@2x.png | Bin 3017 -> 24617 bytes .../Icon-App-83.5x83.5@2x.png | Bin 3325 -> 28669 bytes 14 files changed, 0 insertions(+), 0 deletions(-) diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@1x.png index cf9b70eb3ab38e6f413d8c1dd5b888fa43fcf971..aee9354ef91e09371b9b8cf4927e13c5cfe89bda 100644 GIT binary patch delta 1327 zcmV+~1Y|4N-)_5MUndNPE1S-AxKJ3PZx9$R#{oR-R{s3(G>1L z3~>#Z9tvaluND+69YRTIDU_s4c%HN1aOjA}T##ih7BBMR?gO{=J!K^%p_Me5_pLgU+)|C3iQ+ z@S*0d@3dA5Ayftck(i#8mu0-Up(vv1WW%z;d04eV!pYMi_UqB{*XUE83&f zV8okKNHZ$O+7~kLa#b#hS9qanKq#c*PJaS+2S-cmxG+r>qod=EF;z;6#w7^=SZyuv zbwhV_G@N|6r!VsEx;4xDD!0CYj@z1*k$IBUNn zX%EL9o(PP&j|3yZ7yvx+s0@IG#>Ok3En8Z!@2zc{j6__O00CJN&~*dh$uKl^28kKn zl;`I$T~2Q4_IGT2@|W48q^71qs;L1xdi2Ptj@zBavNdbD#C14b3W#yYiVSb27k?@4 zR6M^V4?B15rko7-F#xn@Po?cK9OjUO5s`K1(~r-kxs$hE`r(+#0B#8Z%d`LpOihHW zLnqHr=E8z|uWu+{?i(6P%o0gFgmz!sN8#v^(FiK4 zwwSBSE6Cqp3eiDTdVvT4(n)AjZBoQTYSz2Ot0R(*Xv|MvU31OCp=vnk#TWzm{)UR?1K zD_UKqT=V&^f3Sb=E+GW@{r-Q@mgY7d^@R{1B2-nr__in2ynQ{QnOl_#2w_CtNWZVv+y=002ovPDHLkV1jSFT_XSh delta 502 zcmV< z$YBy-V93oYDRK{TjEsnkQeeNzz|O$P00xQ4#RZN50X_^k!MAG=wU>24X5m(c6|khF z7AFJgEkInFTu@ZPz`&>jWUH5#6oA+vK( zf_qV7rGj&QPJU5wL1J<$iLM|5l%!UafN1CZg36-I^o$Y(N1$(0fp+E=l$N9x=_q*S zCF?OTfWi-=<8vT5To}d9B$pPIL5*Q#GG<@^01;g@#gGra)&Kwi?ny*JRCt_qkj+X$ z0T6}1nQKKBCVvHywkU#9ih|bRGJFEJZCdp{;Y$QPK|!mcowNvp3PQLgii^;U;LfzT zH-E}zGw{tB&Y2PCZ|MYv0)}I_8*UgN4!A%R#2p}ITDv*9C^Y=j!=u(&`SMsr)i)oy z*~jaH?c90quC~w!9L45J)#B?Cxz$Q_W+%!3igNfoUvGN459@pVbmzToiP6Wbv|oyS zTkeI6osA%dL*J3`j(Fr|xcMOG?@E!Zztw~6uIbqA(dpLyG%~7m={EBeeqgK=%dB6u snj{8;NME-rYf~}?|9P_8a6D1@4FKn0T7NUym;e9(07*qoM6N<$g7VMkNB{r; diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@2x.png index d4ff894857686b080cf2dcf19a5999fa56326a2a..e5583f4b795b7be4509784cc5d1b9ef4976b11fd 100644 GIT binary patch literal 3599 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 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-20x20@3x.png index c5aa51fca527896abd19ae0844532eaa350ed040..6c58aa09fba28e9a36e747111fc1c5a1d0320681 100644 GIT binary patch literal 6294 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 M07*qoM6N<$f|)l{;Q#;t delta 1122 zcmV-o1fBbqG3*GC8Gir(001AChOPhr0McngLr_UWLm*IcZ)Rz1WdHzpoMT{MtVk>< z$YBy-V93oYDRK{TjEsnkQeeNzz|O$P00xQ4#RZN50X_^k!MAG=wU>24X5m(c6|khF z7AFJgEkInFTu@ZPz`&>jWUH5#6oA+vK( zf_qV7rGj&QPJU5wL1J<$iLM|5l%!UafN1CZg36-I^o$Y(N1$(0fp+E=l$N9x=_q*S zCF?OTfWi-=<8vT5To}d9B$pPIL5*Q#GG<@^01;g@#gGra)&KwlRY^oaRCt{2mThR2 zWf;f**Zn+uwtuyAmW&x^x}XA~G96MQGMn^5(kP7u4IwcZl47NV(icAkqoN{0@=HV! ztcWtO23FF+A}N>eOlk<8&0uWJ<<55Ya<=Eb{(U%a&Yk<@?2DBb58U^2bN{%n`+vPW zj}TXH<{z-v;r|KjXGa2nWF`UtBt$5=*UTOPamj)dPk&E^0bso=J9$JZ(=#=|OtLx^ z3Dn?xfBBL~sxs*Z70ezrH6Hk5)fla=$U>PrlieFvv~-b}d~aEMN=?r*uN;ZD@7m4o zwuZf;0En%3y)`h>(YUg63^{j6lC(UEHMF!mbN2{&Xu<1Bj&Hd``2lWCs?zc}i*T(%aE448X|pad3%%E9GnjocO*Mt&2-lj zH1GehU9IOSwm_2Wn%3>NiX>OBB-J_$4VdrfAeknmEEEq{L1`hAHTB)(fd_s zH7_S*T6P?Z%ZCrkj2jk>K6kkH;3`j9dE4+s5&*>q44z%^PU_V9BAHxR5wun8Jh>L0 z%G2Q?3018OUm%6Go4?t%x|RYW`^gG#wy z0e=xcD5#A>$V2_Usz)tp*>`W)1B5VF{>~p zKHFdbfD(QZH+4%NkJ_J)+lG}vZ`tCBA9`>@Q#3xr*h6*MY%g9_xl-Wek)3U`Va-WE zg&~cA3NauAnwcp~{?d+mzB2olHo*TR%zx5>ECpK?p)J9eND?)e)T&ZB>V_%b?vDoM zp8n=~C(h!gR-eD~;ON9}FL()B$0iqSxf|z5lC3|@7q(1bGpETJJ<{cb{o+l@=3#QI=abKZ)1poj507*qoM6N<$g3!Pg^Z)<= diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@1x.png index c85a55b785e22dcf2802ae20bba45e051586bd9f..045a0bc8983aeda71803e5a43ca116481448c18c 100644 GIT binary patch delta 2309 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 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@2x.png index 892cdbd546a85c578cd59b0f032be6dd53cb3b53..704fc98159cc7ea29f2c29619ccc39bfbfb9ce7f 100644 GIT binary patch literal 6022 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 JPDHLkV1nVm1!w>O diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-29x29@3x.png index 3c9928e6d012abaa733a288fd1767b6342a03fef..3fb265c48f51c710805e2bfaafebbc4547d560cd 100644 GIT binary patch literal 10581 zcmV-bDXP|qP)xr?{&{$W-uTIAROi|;zhl# zs#lfy&0qfR%!VJ+kLkzsV>*Mx4{`tSH@^D(k3izA<0b98kWzB4kM~~e-Md!;l6CN3 z>!7_AXk**u-o41Zd-qBq#Hgy1m8Ir&b>N_9I_xwOW4yWUr+mqia%1 z@0_dOdFP$K`78hIpZ%}%o91LT$Z*c$J*=**(C&1KR;yjKTJ4oyue-RqwzhESz`>)3 zj~?2;w$?elxVYE@mVrf}M*zJ9%-PtU8|&9bVeI^dzenE%0lc_6&H-DdrlzJQCnu+O z?%aOO=Wmp%kRAN&JWMb%*Z20j~S(;^xosWLn$TaH_fH<^Yba*Pk8UIG)7Yt zCC)qg{eHjQZnfKMoz~Lo>T=f4vc<*4mBmx1P98XL=*ZI2sZ+p!0D8}R-vL^L0kGBk zE#S`4E!h0C18l{v_N(%1*;e~fN=d9nlWz!CzQGxpk058b7m2A?b)(#Me zGe<^B2~rA$!bcwOz3|Rqtwnl^G1dT935`XD!BBuS<<{9#3eza}I>?3;`72odb^u6VBs2 z;2ojA9`N2dhY$ki9NxPyz~NGOMqsxJ03iYwD&g_qe2_QccWk_~LN+j1bv}Fve>vwl zv9NFi=%0gWUlrUT^%oWvRyv&ygFGiqQ{p%#iXxO!>vm1m2!ud*3DTp4#CeC13Mm~b zQaEdgoDfJ<@wTvbr9|f5>4$g86msW+T^)1|wV_4yqIg z?-4?t$$Ql^Ty+%H?}ZP)lL(B_965I4Adordgb?C~QfS%96DNosPK8OlyEw%z&DK(n98$osfWTX%kSA%yRA*%0Z09b+G zKq-eihuRx)T{Qqg2xKIPMI6rgstwj-jKLT)oJG{rWMs05;5dMDK8|Ctyt0~gyZzu6*7-b3Hy-g;%>L+>-CyQ(;5?#lk9u)2_F37=TRQgnq;BTWPf9f z=J+_1v-32krWu=@W^87bxYi`DH5eZsXMAFUMstj`mLP>h#R?V2qjx)NvDRRRVq?Sf zK6APUUF+P2*dN$KF{*pZoMu8Iq(lk{QdZMnRL9`|M>4ceNr6&|C{;u%CXQm_BqoUyl#&}lSV34g?>dFg1_k1GZRl(grtF2aRX>wxxZCYyq z0x1D0QE7^dHYl&E@kLQ!j766Px+p1&f?_Zr9}F0uoMdcbf+R_h0)!MODUnhkB}f&8 zfgN=^9EXD~WCidrIwvH^b?_0Q5(_y(2Ch?5A(aTGVr4c;DMGuY1m|#-><)&Ar#Bc7 z$7$ejV*&3Y6^mYf#hf~QdOu*!XDM71xYfvXP8>V2fBUv=?={u}8YzQXiP98g1h#xd zq{3RmAhQ@9I9ThFvMeZyf+EkEn4F;A7(+!0?;Wzz%ECDW5~T!U1BgP(^?R@t*9C41 z_latN#E2V(mmoaOJFo&FJx<69&+0zbXX(&x)>@P01!EI4c+bfCi6TWm%UWy8tH5-B_qh4TjQ12+do^av*qsuDGbk+(Mz z2?SfW@*t5ypv#i}pk!|A7#@P@D1?_viC(|IG$_mcQVN_qzg)N&u^<7Lb-O2fy>5mV zjnZhZq!iw{Fy-n^bgz3ZY)53RWiS|2^0-8oI*5wAAkXt4i<@IaaRd^C6%0cuqfnu* z&Q&IntiT8$22)K4i43#5GTs89QuxY>6G-V9GMo?+;e(iSL!gynP?T7p-l$U+MHMm) z?O0h}IRUJ`8gLgYb6IV-U+ndIr{gHTBFp;3ag4PV5yi-K?Bb%Z6&D+0&^nk&Wm#0B zB4>O&h>BXhUUj4sC@5>Bkw_%!E7_S0=FzEijq7Zkmr+(PfSv; z*9p;^_4JFVw7ZZ|IC?6M3{yIs3!^RMQ2$Guum~^l!lP8M%cT#VofC2tCox)68p}+* z5k!hqIB$KuUKa-r99lkdh8(LD!WgK`wV=#= zP;f)}T$y0jRs$j!aWg)EUKAx>D$+C!3a%QQD2iEHSzakiyI(2A-FM%8L0)<-oXe@D zrNcXR?#zW0HLZ=8G6d$OQV^$jQ*xe+$E%Vt2G{Qgkjs){Xd4$fgG%Am>va?n&O5yD zm5haTc^PcxpzK6tLJcFCB4kO01Fx!cVPJ+)yx^cfQEG&WNYfOA50-}#qSPgaj~sg$ zSi6w(@S4CKPRB!s4n23%7BTXsWptz3h+L7Z&X|?CBk`R&}hNLt7d`| zj=~t4bHPo|guq$r<2V+Fj~wlsJbCH>;Jo*ebLaL(B+qxjhd{Kb>JNsemrtBnc(&1O ztcM4ENU5kK#jDEZyZ~)X>0Iywltn?W*P+{Lv9_|x>dG=JOQ%^rb&A&V3PqlS4-sHr zMbEr5@LA5-_~kM3)9oHs3;~)Y9vYO$C_g-udJT3);=># z1-%-bk8`C!1RpdEfZ4luue|&2yL&6kO9!vH>PjmRa+po=*2FwSuJ$dMyj>xIhvdR2hW1+D<LSi~Yf1rCzVkx7%%BYJ?=h+B!O#L6s{+=a~4pFPLd==7X?y9EG;jJea{@=k%bER>|4jPTu*;FaBdGvje@s;Dy0puv$x#`6Hd2fBLi6 z@V7s(ijb18Jp4ZX&2RlTwoOU2SrqE&2H+jXPqz8}fB9ivJdLM;^Nu)iJoVDG{MSbo_{fcW5QJb)Jx+P_v8VZKm!IJ8{)^5X z$ng(-<>76Ie&x5G`lyn$tvkPY^h(bCA_5rOGQB3Qx%>r>>3QdB9z@+*gbh1>8*lu}qnm5YL`@U(JI3&S;A53}oxj5Vc6L4zr zW)`}Z29B8qq%os}m?;Z-x#XJdi|o4cDSW?*8AY(E)x+7hkrxrodJXTy$Xk<2kQW-f z;pVIMgMDtuP>33=wVU+wS)wGND2l2sLo>)V*X=yXwO2eNkoX-hd`JKdW069fU#Yzk z+>eJK(4dsUbnC+EjDDs>B&B@t!4IgtJhb|ScKhl1xtTkalwy!8bSFirn86@I#t~5* zW4%T?PcPHV?znMtjEG^u^pcq34S7pO04#(rXqS0wHGhXsbfAnIr^y}(KjVp!YYX?GI54Fx;S zdzz)E-SJo-koSV7*ms7gUd=_s_rA?S3vl%*v}V(RsjA|H5T zofwoZxXKqaz+N5PGKr^a(^J=qZttkV7xwzAuYc#}xy}E4|Dl6VF143pn+rcZK8=!w zB$=i;HpfJBGg`bznx;4}@!q0hi7}d$8Q4-@(WQAvt!=MNnJEXDCN=pktE%6kC0l)g&%V4LG5ga_SN-ZH&+-#tt zgiarfQ+)5atNHRnj$itpC42wTDl)o^Kf8a12OfTkMjUbQbc^@hemy^P$0_>#V;os* z^7*e_#Yf&#aP?)+((Y+WEwIkfZneq!IdKw`_4}+YpUR6;)_Vh#QUYzcD0&6Bci)W% z+TVEev48N5N15L=edYi1fj#5DJdr+a8wpmaLINq{Zv_vwBD_+YN2$fN_j(2RHcT}go?yr zy_pOi&?^d`jdfV-G1i?ESW$sn>hQ4^ob_aboPK60N{u$KQd$;HEwRwbD2=DkhF)eF z*o*M-5osKAZ3!G$kPhSfjac}feU(WXOnT^nbNJx z|ovO}}!x$>%Om`Ma~*3)QMq-wI|vKdx;SE7rP7-K1n2m|Cou1{-&tY+Bi z^6FtIk7(;v5h|=+x3w@L2b3jVdwdZJT!h36qa}sL4+jX7Qe)A8X zq}_A8f6or?xOI_Ru1S!Q!dpu%d6_SNd!EOh>Cvnorp#M77l17^SQEf4bx9OT9L4F= zi%$cmjS;e_9N5moI`8v zm5k)-+S=gw!om}fM%soFOCb^V5^-)(Sf3w0b)|?^y&UK@e)^934W*vil@+Vy;_9ue z^e#_SJjRt*U5;>&=NaQuGaP>INm>V=u3S%nwvti{e5HIM8Ii^bQKYKUO^wxtqAXC! zB%l7&hsd*o)EnEm_nZ4zI`R_r^i0#uR$@Vglo|q<8jqMOEpaRhW$j`zsiGr?DPy!UTHV;8yt|wQv73U-*@O z`^+JTcK*`ex#geUam&lwjO}w`<@Wr4|DC`5%(k7YSO4~J{l>?x+<66qJghNr9q6cQE4Wy-@M`tB9(Y+wUQQ+NmNNe3{y(dzAOz|C;r5V z#pl2O{qMhU^UXKk=D}NQMOhZybmNU&x%(DY7mjlL#1jAdj|OA|$LKTDv4Fj(ZvbA_J}};1FS49GuDVhHH-&OPjW3TUv(Aki6?}vr!_g=tc#*_BDc-q^#fn|%2%HF93vU_-aYLeihQbfU~RTjyO6`n#4r$)hsN$KtuFs#1Yies_fr_Gk84X&2fZj z5JxffTBB;MrxruGvcTa}oFPjDki=E^vO3+YHyN)t5yD|b9ej_XDCl&%PXha^-@EbV zxF|$j*3!DD*P0SAcin}*`|j5VF8ADn6GC^6FV_dn=FP^s+^lrQ1mry-MESr24}53e zzGpsh>#chx0AH)sgp`tZzURH%yLk)kQzw|29H&=y*?)9`G=4Y6`1Ou&U|(N>yWDOv zJ6U5qNif=CbSQ%oQX;IR78SgBBq3FAN2r)%rxdaDBdL)lf?9f3V5oZCP$?!699WPT za}#-))9R0TrA~=F&&|rp%0oaq{IY02f4HUvw^*g>(aEJ~0Q96B=9$kOEWg-9xFD=b z+)Y^43D5`jDW#UJwQu{(XFl`CpZ@fx_ZVZmQc4IR(AM&={`s%)=vV)YTBFIJC^@~> z!?^Xh?8f6piWJOE)QFYBS5@Rj>#%mh7z(Xf?&QJ2@eoUxs=tPs6c2gYByVoQyHINr zDg36n8PV%>UVQ$gmp%df6(MdrTlIZ7T~7ng5kmg2yPU}bnGoW!jb5sAUQ~;d58r?P z{onb8U--nHX0s`b)d&P}6!VVve~8Dvd2g7mNz4_Sr$Am_ao0Z=cT^OCC63D6Hb@W6xn_C4G2&QT0c0G;!4)c1=3_O*fw>*krK@=ApW!I{<7 z)h8Z*?D1!{(PaJ17gf!{md%^F`Q7iwSXZrO02l(cUZ=o0>K4wt#>ktClY}I#kt7L8 zk`N_H2n5A(aILE~6zA=P2bVU9(%MKI4d2!6^i@00br-2VO#P@kN|I~(e5#fF0BjX<&vq}X^o>pm$ViWF(B zMw|vNj+2BaiHR$K)wwsN7{w~o#2jg)Hlif7*1p|p-47hD`t-VLhb{%U-Z>|vl=kai z|N6I{eDbMN)*8`nw|uYHr?tAu*6rK5^7c~0Hopt|N=aVE3qM`yh zieuu6lSf>9Mq|M>r?bV)dO1O4F7zx3yi zw%aXw-LCI;JFKG#2Ots3WU0D0vEC_CO3+Vvo4%*|N0T63bHs&Ya~ekc*wy~6os`G z-cz5Q=lYx9&ZfCJHf`F(%*>3RotqO$k_?vD*1im^UJ8)_udzP&LNr`EaQgJ=2lnlI z{)M?sv+u~Vj9RTmzt?ACa+0^b{WcyuaU_%|FZ9G<{ zol+_+nNkv~LMT&6IWpIF?Rhu5uHQ|!-6GF(`u#r6IgTGY_Jb_T9<1K`suheELzfI( z)<^pAcOHH8YkS^t%R7dZg;EaCy5O2!*R$`jEtIQ^$SB^p6~KrC!&64E;`c#JeY-ty{OUW9LrM?Q{;DK7IPj zLI@`=mB8iFE41M>e(LLA|JFCkqQDv>%CfA=@pG=a_Iheln;5QPyXbn|b1J|MO7LvO zH(buDBD`~4ann2a`A_~m=4NKNZ1ZJo-m;nP+qa8}$w~G-_uRd}zN!naThB8sB$+8DBIz~tlv+jiZEaXu_r8k$$HFu53=XLQR3MK?U2 z<&21-NjEgt@DRoP^e6uzH|*X`v)N?RrcKPw&blkFx|)TB6Nevpq_!V8qxu`C@;=b^O(Qyc{ zl!~&*x#_(h;%|KPZy}{%Yg^d>&>kAI1Y z@o}7U#BofL#J<^Vh=(3}=-~bL-+zyka$v0uW$2fX-Ux8RgQXnOtwZ;BS5M7uoZUTPcftSU~NS zQgk{U_qoq~?n}FO?|!_p(Jv{m@Wz2VTo~BC@4m18$LC*q;b^^H6L~)Hx(py&Q*!MM zH=?HI@ixR9Mw)*Qnk6N8>E|p@a+>9|~S;qFAJGpGv&Ez)J z*vPXYXXjL2BXLl<-b&)F!6$Xz_tBqa=gu9RTs%p)+ojWK(OPSH>#V%*FaF}x@BQBI z{ehJ7$QvbVhxCSx+QxTOTg7hq&<8*GnZN#%ANZMWr{k20gj7-pDN#ZYCn<*y9$<0* zb0n?|<)zM5u5n2Jj5cwDD#cy}y1hqhjhfuVo)3JO-8bBT)fyGYq;Z0ZBHwH_(OSE` zcmMkDKK$^*|EH94P-RixFmNwrY~g$~RBk69c<{mB-LiSp?(43-dRMpCcS#%zAq7^1 zN|zm%?Q^v$iV{)mQNzfLABrFdVnS@DGgO|syWThYj(5yrWAlmd^N zn4FMb|K>Li{_z*S@S9S~m);Cu;mr{Xqj!n0ID6*C8+ZTuNB;VUf6-YJIp!Q7JwN&3zxF$~+_dYCL6&Jmo(GGQ2emoluKP($#l z^mz~yvf2?ZTpR76hxd&}L$o_x{rUg$Uq1KDGtcjpQZBw(;$YO#H|s@bzqjJx_kQpL z@BfWkZ@%Ft@xel1zuruEJ|EU;qYdEi@!sFdoqbb|nuKwbm{Mo;M z`q_PV3n5OtnH)Rnl0a#Ui&P|~JnNrdY!DlxEe9*$ ztBuyYlFHW`b$ROaQud`U-}||jUq1M+rIaV$Y>pju@XdbV+3&9azV3$I*Zt~EH(dX7 zGt-k3Wm$T_E2V^#a)YR-#Kh>kL`dO`j-S7BEm+#oVCypXE?BwT#kbbylqf}BTsfZ#aq9`I#5vyyh!4psY z;A@Y6|H*#`d{YQveiWkMjE?=NUVIh}0S0*cl~-Q=vsYiSQsgDQet-4E$;HQ>d3N8I*48>-7D6mQh->g81Qy;p;6mkwZAfkJnwgw@@67DX zEmJd-x1@109mh&}kJqIw^Kx)8u+}~foUDHPBL{UzZzXVtBt*4^U&YBW zp+2@r@F+du-_LY`mFfq>%rm@2fQ7dvxI?Ov4#Kbh5iXpuJ-~X%@GS%CklxDR4(UQ| je9Hm)WBM`u_fP*n>RvkUOBxx(00000NkvXXu0mjf6sXs~ delta 1594 zcmV-A2F3Z+Qosz58Gir(002~@hOhtt0McngLr_UWLm*IcZ)Rz1WdHzpoMT{MtVk>< z$YBy-V93oYDRK{TjEsnkQeeNzz|O$P00xQ4#RZN50X_^k!MAG=wU>24X5m(c6|khF z7AFJgEkInFTu@ZPz`&>jWUH5#6oA+vK( zf_qV7rGj&QPJU5wL1J<$iLM|5l%!UafN1CZg36-I^o$Y(N1$(0fp+E=l$N9x=_q*S zCF?OTfWi-=<8vT5To}d9B$pPIL5*Q#GG<@^01;g@#gGra)&KwnDM>^@RCt{2m}_iQ zMHI*XXLc9*)PFu`c~uK2u@$0XBBB8diU`H4u}h1sDH*?)B|TaGdgkeU-&^Adsoe?JL7JUbJgG!RhE!aa+eL`X_71hb}&N1xHj7-nWA7Pn?(h*ZT)91J|sKcJr-IFBabYA0Zrks!v{n`xmvNo(;IhFE`XJBzZ?*y9BX_5;zFH_ z8GqY7zhUVB#GCVsU95(bop;Q<-Ve1G*Kq1=-L3{Gojy_pz9yy(@2MsLvAND&Qzt6E zuL@y1<3e3)Q1h#p%ZFDIfWHOtVFz7;_Lx1>R{}_-f5`yeC9=kF&XkTa;G0p?Ab>jo z9i6>82;vH*@}#kgmnZjY-QHYb@+y@7iGSS%q5>vl%cYL)N`{WSE_|r%bE$1wGmvZP zGn2)4HSRreH4g@&@;Dn$QM(2WX=f#`#qPhh&&#l!bB&J8N7=h`Q&j*#{>VVN1ob4m zwHmZAmW;o=zJA?+p0KawS0o*+T^$-^{3h(Eb z0aXsfHJmb^3vz?!TeRqv_NCRv<#M^&-g7@ow`uDzZg5q4;!B|0_+5UNh|5?aFs=v? zdx^zrR5Rp5l!2`ocxvm;viDbhLAB0*moV<&->O`jM_Vr*oD6I^)6sG~4|x9PmT*j; zctN@L(Z;kcPfEer>bi@`qjMJB1AkaG4L&5^H;XtM$b}p^-R@B{YW9_*t!{LtJvuqe z|3-^LL61jq7=8xiMiP`pz+kvk0wNL`jwApvp{EQgZUO)YI9P+wcPQj`%Xebj7&pf4 zEAHq`LK4dD9Qq)qen*2dQ>PPjsIMCMFI-8^PJ-8;;>5!{@+MRrP zqa$wg<)zqfd-HN^kBAtf>ysR9iRkM_bF2I>r0u zC+5XPV@%V*woO@s{l7C17>7#hZlsP*nV%o0jv|J$I7A4%t%2kbjx+beVB?!O%-o&l s>m-~)2gMzn+-~_!j2q*|xc?pZUtvnl_dy)!#Q*>R07*qoM6N<$f-0r_{Qv*} diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@1x.png index d4ff894857686b080cf2dcf19a5999fa56326a2a..e5583f4b795b7be4509784cc5d1b9ef4976b11fd 100644 GIT binary patch literal 3599 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 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@2x.png index c9d55a80a3fd303a6a089e77df9682e0cfb3005e..244512b032ee61a19f785438dec2d04c5bd7aab1 100644 GIT binary patch literal 9270 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 U^Xr27ze_u6N?MB53YHQ7113o8Gynhq delta 1443 zcmV;U1zh^JNU95v8Gir(0066ct#JSV0McngLr_UWLm*IcZ)Rz1WdHzpoMT{MtVk>< z$YBy-V93oYDRK{TjEsnkQeeNzz|O$P00xQ4#RZN50X_^k!MAG=wU>24X5m(c6|khF z7AFJgEkInFTu@ZPz`&>jWUH5#6oA+vK( zf_qV7rGj&QPJU5wL1J<$iLM|5l%!UafN1CZg36-I^o$Y(N1$(0fp+E=l$N9x=_q*S zCF?OTfWi-=<8vT5To}d9B$pPIL5*Q#GG<@^01;g@#gGra)&KwmlSxEDRCt{2m|JXA zRTPH*wa*!35Pu33Vha(hA|!ws0ZWl05t=G$5n_Z0B%(wVP##Qt;7OxzDEdHR2p7X8 zTnZ#@@Ipl@V2KF?BTyg#T4_avO1ZaX+L^Q0@53;i8Kj)kSQCS@Ugpf4m2a=T_S*m2 zdxYp(GhNKf05iZ0@P7kj=k&-;J}Lnb0RSps1OQbGpnnjFzjso-MTF!{&xFYx$5#V* zH+mX?awosrL`XTiy`ej$pahiIw(5H#Q;MKQzbTJ}oPjTO-~G<9$_p5@z$D!FRk&HB z$L~Ab;_!h9BT~j=+>|#CO$0tXZ%NwP+4!JAEo+MMK0Wel^_nR;(|G;J6Tp6YB&ixH zK(C6+(SOGB9++Cw#H1nRxwfxUNspw*rO%QckLL}lB}rb&FQD>s!5mtW^tc1gGo+G} zovqXqNOF~FhrDRFLI60iibaf>>u=Pr8WL4%EPG`*3T1w7*)gL4jJIy0H6*C8LQTnG z5-7ktx2(=6l>5D6h-^AgSgau5 z)jzB-EsqpmTn{RKuAS4;LD`tJ=aS(kzY<01$UF)fnvtE%FaRhQ%Gy5-Wkqq%)&M}! z-hZ!RZOm=kIfn`~d(tiW4gic4KY6xPOx?k^IxO^C67fpEs{Q!Rog|K+cZgThBNT)e zVD(j5Id+%?0vgSm>8+P7C9Z{FNRFIIj}XvlBTnpW{dOS{Fha}?ReX7F1_YwHllVR3 zd!1-&5&*DS^RZ#suram++^s;v{G!JB1%Ct80KnpK)z`+es#f%iONIc2v+l3_Y%!FK z>ssQoqX^Z^$F*6!311dlcrfG`<3vBn&9lO&ILvw778cSKaUlRiTsJ+ROfzN6gOd|` z({e?2Xwj~tKW%<{3vHzSsllgjSgq+(MlW)9Ih#7v&He5hHglw!qkDg`4~?4uluzn|<9koR4#=PI!=VcfhZa4WtfIdOESWL`H9(8k z(}4!=J$F`YC>;O_1ArPAdliW{2{G}$(1{j+ctr=5|3JXb+TGCTGr$b+-v_$>E&!+y z8tJ%`BrV8ZPMm-OX;=WD8vOC&Ie#5EF7NlI;l2k?|0%1v^3kr*V|$#~o^xjUaCQ9r z>0`=MW3sDA^76Y_&X}LSA5itmC>)^YS&uAv&mZWQXUfNi=N7~q$2gWt#DAH6a!Av- zPNv3(buik(H-$b^_P7=I*2E9i!OXX`YNc0G8B~Jo)~Lv|HWn%|9z@PA@I%HFS^{E}0hK)*MU^&mU{(G5GOrL2lte6kBf| xLAy$^0gz1m9nm$wPS}6HFC1rp8Q@(B{0o-~rkZ=?%U%Eg002ovPDHLkV1j&?rg8uP diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-40x40@3x.png index 90981f0f9419513b849f5208d48e493e7b376422..ca7b489be0646c32b05936199b16cbef80997c01 100644 GIT binary patch literal 17311 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 literal 2234 zcmV;r2u1gaP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$2ctF%Q+>3bATrAmwDat2$&MPZUGepLYb*vrU?McpOO_j%`QVI`!}Dq3?N^cu&BM^ z@T+I(3KT7Uf&vPT)NJz>q?sF;6Q`8^Hsb}W=0L-(6#tkP)7Yt4&Ay-cjh2;8DcgRy z;g(B61?3MtlfoD@yGZMSAEyGCvF}p2;rjlSz=T~_Nh(`c56YNRRo{4g&)SO8$8uKD zYCg8w09k*h)u}^6-vjXUhZowcmXCj#3KVWS+p3Ha#5VAGxXq@h>tlK4CrMIyaz2Wy z!i45EZmc9p>q(P}c0tN#?@cYC0p+i2WyrJa7+^HxJL!G^VikYegLgg=4J$xZ>k1FrolPJT$A{yA zAsGD>Zf*&5tlf^51pp|4*KcuLxkUO4Ck$@}0SP`m2B)@!)l)8Qd}?f4Jk*`Qnl>j5 zI}Zv0P<&NmM?pXwtP^>ZQK3i*m*+qL2^G%=ww`I9DN%jq*>tr5hT!q9;nG$J0OCLO z^HNnHc>f}^9_kWq%vZueMrRI_qubFwQ|}vJAMfiyP>Ta*-nSq%4WgiMOaI9bP^=R` zVZW|DJM1qwa4vQ8WupLO_rYau%N7{K)S*0H0|BM6wz7}{z<&wI_QXsvGGfmCa;O>r zC9r^-_L97$600PoF2 zTKMo3`ZoHE9DaB4fZl*p=4E2{hr+k-e4SlmgkW_q%$9$AAbc}pL84XZ0T_bu z<8ZYK$97isqW}eRu8sD>KMYN9}2BRsL3A?OlT2fB{SzfitgcnfPG1gJ8sD%Fa{L8Ivfx_D7~Ae6oTqtJhB* z8Q<`G3Ko{k0$(|_2pyrHuIEa4{AF~IX-VCmiy{lp5Ts& zS;e^i$hauYqgH3~jdd_oRaJ2vdU?)$3Nmn02?(Ympq(5F0-<>D1Yp6i z=}eiKqmhLZE?JXt?FTQO7h{Yup_&(_Kc+@Rny;z|gaZ~JeQ_EEA~ymia7_##qSuV^ zO5A7>Uo7tS3_jf@m11b)NZ`RAR{!gxT^klmuBDRxmTkFs>0+Bwd3w;J*HvlVY*-GU z^2Cjh`Yykg4wU@qqQ6_tl_;;Kv^_Iq9ivT!f|GxI_sESeu;bSUev&`Eh^dDsoi|I^(_juElU_o(t zF4O?L67;yCZOC^6uwVr6wYoe4z!%E#T(LYZ0G2N$FV@(Tt0X#CfIW4aL~6v*a16W2kd|yumisLVE3K7Born%!s?OO&bbsO^4o`C zH2~UALef(&2$$Wj4tkaD9MAB7ZxD*4;`2OHOTlkLwx}bei!D~ zv@BJshN#Q1yDz}X4K7o0E%GYBVnhB`29pLSYZNMHe{SiD&Z7duA#*R-@TcUhapwss zdL+sh$l19zz)6Non&1}UhzFuhH4MHHv@!o=!P0nuD05q`sK(UPq_H-Z`dk~3A3L4T zA52`lB`An_rgrwIr0@7D4YF*2dJRqk;O%>`punxTZ0o7^5?r1~d=~Rm`@pz>Awva+ znoTq-`OP?auxQFWnokZO>RlS;qLp~WT>?WeYq*Bi1v(Q5mAcn#r7=m0#kbSoew7+h zlGG5-EUxRDL_mKE^#46cRaNrH>dk98ZZsQ>@~07*qo IM6N<$f>28+ZvX%Q diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@2x.png index 90981f0f9419513b849f5208d48e493e7b376422..ca7b489be0646c32b05936199b16cbef80997c01 100644 GIT binary patch literal 17311 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 literal 2234 zcmV;r2u1gaP)4Tx0C=2ZU|_6BEGWof5@2A+%_}K#4|0r*h>TKTzskVQz{mgwiOIzUjsXEa z3^>8JYY?@UbwOs~R)-a^q@)%n1L-Y5T$)@^RKmc(r~_oHmzNZP*dai+NOnk&GmxDD zWb;AQgMhSiVoqjKQDRAIih_GlVx@v}eolT-aY15oDv7Qj0+ggylz?dG{DR7&%=C;B z1xKK7Q-OBo7L=Bx7U?K><|XSfFo41jqT_QQI9wRT&Lo!>l|hYRWHM%8000qPG{uk) zzSaN$2ctF%Q+>3bATrAmwDat2$&MPZUGepLYb*vrU?McpOO_j%`QVI`!}Dq3?N^cu&BM^ z@T+I(3KT7Uf&vPT)NJz>q?sF;6Q`8^Hsb}W=0L-(6#tkP)7Yt4&Ay-cjh2;8DcgRy z;g(B61?3MtlfoD@yGZMSAEyGCvF}p2;rjlSz=T~_Nh(`c56YNRRo{4g&)SO8$8uKD zYCg8w09k*h)u}^6-vjXUhZowcmXCj#3KVWS+p3Ha#5VAGxXq@h>tlK4CrMIyaz2Wy z!i45EZmc9p>q(P}c0tN#?@cYC0p+i2WyrJa7+^HxJL!G^VikYegLgg=4J$xZ>k1FrolPJT$A{yA zAsGD>Zf*&5tlf^51pp|4*KcuLxkUO4Ck$@}0SP`m2B)@!)l)8Qd}?f4Jk*`Qnl>j5 zI}Zv0P<&NmM?pXwtP^>ZQK3i*m*+qL2^G%=ww`I9DN%jq*>tr5hT!q9;nG$J0OCLO z^HNnHc>f}^9_kWq%vZueMrRI_qubFwQ|}vJAMfiyP>Ta*-nSq%4WgiMOaI9bP^=R` zVZW|DJM1qwa4vQ8WupLO_rYau%N7{K)S*0H0|BM6wz7}{z<&wI_QXsvGGfmCa;O>r zC9r^-_L97$600PoF2 zTKMo3`ZoHE9DaB4fZl*p=4E2{hr+k-e4SlmgkW_q%$9$AAbc}pL84XZ0T_bu z<8ZYK$97isqW}eRu8sD>KMYN9}2BRsL3A?OlT2fB{SzfitgcnfPG1gJ8sD%Fa{L8Ivfx_D7~Ae6oTqtJhB* z8Q<`G3Ko{k0$(|_2pyrHuIEa4{AF~IX-VCmiy{lp5Ts& zS;e^i$hauYqgH3~jdd_oRaJ2vdU?)$3Nmn02?(Ympq(5F0-<>D1Yp6i z=}eiKqmhLZE?JXt?FTQO7h{Yup_&(_Kc+@Rny;z|gaZ~JeQ_EEA~ymia7_##qSuV^ zO5A7>Uo7tS3_jf@m11b)NZ`RAR{!gxT^klmuBDRxmTkFs>0+Bwd3w;J*HvlVY*-GU z^2Cjh`Yykg4wU@qqQ6_tl_;;Kv^_Iq9ivT!f|GxI_sESeu;bSUev&`Eh^dDsoi|I^(_juElU_o(t zF4O?L67;yCZOC^6uwVr6wYoe4z!%E#T(LYZ0G2N$FV@(Tt0X#CfIW4aL~6v*a16W2kd|yumisLVE3K7Born%!s?OO&bbsO^4o`C zH2~UALef(&2$$Wj4tkaD9MAB7ZxD*4;`2OHOTlkLwx}bei!D~ zv@BJshN#Q1yDz}X4K7o0E%GYBVnhB`29pLSYZNMHe{SiD&Z7duA#*R-@TcUhapwss zdL+sh$l19zz)6Non&1}UhzFuhH4MHHv@!o=!P0nuD05q`sK(UPq_H-Z`dk~3A3L4T zA52`lB`An_rgrwIr0@7D4YF*2dJRqk;O%>`punxTZ0o7^5?r1~d=~Rm`@pz>Awva+ znoTq-`OP?auxQFWnokZO>RlS;qLp~WT>?WeYq*Bi1v(Q5mAcn#r7=m0#kbSoew7+h zlGG5-EUxRDL_mKE^#46cRaNrH>dk98ZZsQ>@~07*qo IM6N<$f>28+ZvX%Q diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-60x60@3x.png index 4d22e1617b22451ef0b34de942311ae31eebd8a2..aa20b6471aa05309bce4789f3fe9449d148dbe1e 100644 GIT binary patch literal 32216 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 diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-76x76@1x.png index 37f8228413e95e31262dcdc2ffad15f287fcb4d1..1fbffde17f43b636529090170aa643b6d507be64 100644 GIT binary patch literal 8740 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 O0000< z$YBy-V93oYDRK{TjEsnkQeeNzz|O$P00xQ4#RZN50X_^k!MAG=wU>24X5m(c6|khF z7AFJgEkInFTu@ZPz`&>jWUH5#6oA+vK( zf_qV7rGj&QPJU5wL1J<$iLM|5l%!UafN1CZg36-I^o$Y(N1$(0fp+E=l$N9x=_q*S zCF?OTfWi-=<8vT5To}d9B$pPIL5*Q#GG<@^01;g@#gGra)&KwmT}ebiRCt{2ms@O9 zRTPH*wa;`IEPrxo2bxkEE{#<*5S7r_Qj8)RQ9&*?pon5nZax@{F(Hr`FTD8Rn+B~> z5Var(rWFz}K_eg`S`|S2Zw!po*c2K&U-~0DnLQjCfW=O%jzLjf>Y z_eTdyB>S-trK{pXF!K0#LK@5d*0j;H!{04Bb|j)x3!*gQ+#Uq(ntbq-1B{)X-n$38 zO;4@^9{RnDr2BIrK4?t~>wyBb&!-(Nv?uyr%TdmRi-HkX_V z9b*E_ThJ(`t)%F{k7A*6{@}|BBM|An^d9SliGK!{q0|~0?py>bhbzNVM533pI7~#c zR`GorP(HbP3j5Wk@w#)z?mr?fercXXgG$W}Bf75)2@ zeBOQvkuPQrR-hUqg0U+HARVD)of`ou8+~VsFATuqTX$4BwUtjpfX*l*x(@&tF3tGr zgn!dnwt@pF-3v3!pWpPk?8uv-1{j07PH$uo$$O@yRLVn-h?7KQie+X?)4qiufC4#v zR-+-rB>qz9vx{4w9RL*vGb}2uTI0;1fniZWYq_xmXyy1h0|4&iC+nAX%u~-24hR!< zmSfYbK`Ic2HiX_imL{Y)f9@G>38=;D;D5fS(p?o}piqc0>c!D(%FE-j8rYqIn+9ck z*-Ey3^ZLIeA6!qWEgsXN%C9k@nU=>L=cqTG;!2R3wU;(pr`!K&!=dpLGThsjXYlyG zjoB~G$dPT;ud-qP=0BX0xswiU-H&ODW)6uRX&j8Gw^`j%g&LeW(VCf`12v7ULx0^X z;dFqIj@r;5w4`O!np@EBW~KEWQ^MjHO{eZ3f9nGyyepLu5%ef6HpjEnGd*EsS8F%# zQOa#zH?0FSxFZdy0~Y^eVQOkVt{f52+vb$do*3V-#Tyfw zWkvQAKh$0N=e_*kQQE|lePEWmuzxV>9!Nh(_j+KeXGUh$FrsR^xMrIlEb$?zl-A7~ zWdkC{(HAn|Q@#U<2I;izlH#by3?^AWAtf9p&Yxv=>^bpMh99iH%^BwR=aPg00_{T5 zZ%#s(AZIvhdszO=gfPS0d*rah^;OphgUSl-tPi*(T{*MYH#naRu+L#hRAs6c)}Qir zJXfCqRK2nU#pVB9I=}suU;S9|EmhyZ1v@@GJ2ZFj-AB@)k u1FR7w*HA| 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 literal 3017 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 G?Ee5tdbp4P diff --git a/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png b/client/ios/Images.xcassets/AppIcon.appiconset/Icon-App-83.5x83.5@2x.png index 1058d3a700aeda626fe1564e2b39597aa3785b58..c08e869640fdbe2b4dfff07d1497af30af2fe75b 100644 GIT binary patch literal 28669 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 Tg)aTC_nxYvrb4xxRrvn_=u?>A literal 3325 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 Ge*7N{uw1GD From cd88f3fa9ebe40138bbcb8c64dd076b730c9e44f Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 14:36:30 +0300 Subject: [PATCH 109/131] add vcmiLua headers to CMake --- scripting/lua/CMakeLists.txt | 45 +++++++++++++++++++++++++++++++++++- 1 file changed, 44 insertions(+), 1 deletion(-) diff --git a/scripting/lua/CMakeLists.txt b/scripting/lua/CMakeLists.txt index 13c927c8c..ed4aa93f7 100644 --- a/scripting/lua/CMakeLists.txt +++ b/scripting/lua/CMakeLists.txt @@ -39,7 +39,50 @@ set(lib_SRCS api/StackInstance.cpp ) -add_library(vcmiLua SHARED ${lib_SRCS}) +set(lib_HDRS + StdInc.h + LuaCallWrapper.h + LuaFunctor.h + LuaReference.h + LuaScriptModule.h + LuaScriptingContext.h + LuaSpellEffect.h + LuaStack.h + LuaWrapper.h + + api/battle/UnitProxy.h + + api/events/BattleEvents.h + api/events/EventBusProxy.h + api/events/GenericEvents.h + api/events/SubscriptionRegistryProxy.h + + api/netpacks/BattleLogMessage.h + api/netpacks/BattleStackMoved.h + api/netpacks/BattleUnitsChanged.h + api/netpacks/EntitiesChanged.h + api/netpacks/InfoWindow.h + api/netpacks/PackForClient.h + api/netpacks/SetResources.h + + api/Artifact.h + api/BattleCb.h + api/BonusSystem.h + api/Creature.h + api/Faction.h + api/GameCb.h + api/HeroClass.h + api/HeroInstance.h + api/HeroType.h + api/Registry.h + api/ServerCb.h + api/Services.h + api/Skill.h + api/Spell.h + api/StackInstance.h +) + +add_library(vcmiLua SHARED ${lib_SRCS} ${lib_HDRS}) target_link_libraries(vcmiLua Boost::boost luajit::luajit vcmi) vcmi_set_output_dir(vcmiLua "scripting") From 7b411a5fc457f9a8f9ce5c9ea20e7ea0c100cd8e Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 14:38:03 +0300 Subject: [PATCH 110/131] fix building vcmiERM for iOS --- CMakeLists.txt | 18 ++++++++++-------- client/CMakeLists.txt | 12 +++++++++--- launcher/CMakeLists.txt | 5 ----- scripting/erm/CMakeLists.txt | 8 ++++++-- scripting/erm/StdInc.h | 1 + 5 files changed, 26 insertions(+), 18 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 1b1866f3e..649a5a1c8 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -404,6 +404,16 @@ set(SCRIPTING_LIB_DIR "${LIB_DIR}/scripting") # Add subdirectories # ####################################### +include(VCMI_lib) +if(BUILD_SINGLE_APP) + add_subdirectory(lib_client) + add_subdirectory(lib_server) + set(VCMI_LIB_TARGET vcmi_lib_client) +else() + add_subdirectory(lib) + set(VCMI_LIB_TARGET vcmi) +endif() + if(ENABLE_ERM) add_subdirectory(scripting/erm) endif() @@ -415,14 +425,6 @@ if(NOT TARGET minizip::minizip) add_library(minizip::minizip ALIAS minizip) endif() -include(VCMI_lib) -if(BUILD_SINGLE_APP) - add_subdirectory(lib_client) - add_subdirectory(lib_server) -else() - add_subdirectory(lib) -endif() - if(ENABLE_LAUNCHER) add_subdirectory(launcher) endif() diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index ae382dee3..07d3674e6 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -174,7 +174,16 @@ if(ENABLE_DEBUG_CONSOLE) else() add_executable(vcmiclient WIN32 ${client_SRCS} ${client_HEADERS} ${client_ICON}) endif(ENABLE_DEBUG_CONSOLE) + add_dependencies(vcmiclient vcmiserver BattleAI StupidAI VCAI Nullkiller) +if(APPLE_IOS) + if(ENABLE_ERM) + add_dependencies(vcmiclient vcmiERM) + endif() + if(ENABLE_LUA) + add_dependencies(vcmiclient vcmiLua) + endif() +endif() if(WIN32) set_target_properties(vcmiclient @@ -226,9 +235,6 @@ if(BUILD_SINGLE_APP) if(ENABLE_LAUNCHER) target_link_libraries(vcmiclient PRIVATE vcmilauncher) endif() - set(VCMI_LIB_TARGET vcmi_lib_client) -else() - set(VCMI_LIB_TARGET vcmi) endif() target_link_libraries(vcmiclient PRIVATE ${VCMI_LIB_TARGET} SDL2::SDL2 SDL2::Image SDL2::Mixer SDL2::TTF diff --git a/launcher/CMakeLists.txt b/launcher/CMakeLists.txt index 7042f0fec..695d1524a 100644 --- a/launcher/CMakeLists.txt +++ b/launcher/CMakeLists.txt @@ -110,11 +110,6 @@ if(APPLE) set_property(GLOBAL PROPERTY AUTOGEN_TARGETS_FOLDER vcmilauncher) endif() -if(BUILD_SINGLE_APP) - set(VCMI_LIB_TARGET vcmi_lib_client) -else() - set(VCMI_LIB_TARGET vcmi) -endif() target_link_libraries(vcmilauncher ${VCMI_LIB_TARGET} Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network) target_include_directories(vcmilauncher PUBLIC ${CMAKE_CURRENT_SOURCE_DIR} diff --git a/scripting/erm/CMakeLists.txt b/scripting/erm/CMakeLists.txt index cb501c2a6..99da95142 100644 --- a/scripting/erm/CMakeLists.txt +++ b/scripting/erm/CMakeLists.txt @@ -15,9 +15,13 @@ set(lib_HDRS ) add_library(vcmiERM SHARED ${lib_SRCS} ${lib_HDRS}) -target_link_libraries(vcmiERM Boost::boost vcmi) +target_link_libraries(vcmiERM Boost::boost ${VCMI_LIB_TARGET}) vcmi_set_output_dir(vcmiERM "scripting") enable_pch(vcmiERM) -install(TARGETS vcmiERM LIBRARY DESTINATION ${SCRIPTING_LIB_DIR} OPTIONAL) +if(APPLE_IOS) + install(TARGETS vcmiERM LIBRARY DESTINATION ${SCRIPTING_LIB_DIR}) +else() + install(TARGETS vcmiERM DESTINATION ${SCRIPTING_LIB_DIR}) +endif() diff --git a/scripting/erm/StdInc.h b/scripting/erm/StdInc.h index 76f778c6e..02b2c08f3 100644 --- a/scripting/erm/StdInc.h +++ b/scripting/erm/StdInc.h @@ -6,3 +6,4 @@ // Here you can add specific libraries and macros which are specific to this project. +VCMI_LIB_USING_NAMESPACE From a851e630d57b6824fda471be96f47f7fc5d6dedd Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 14:38:17 +0300 Subject: [PATCH 111/131] fix building vcmiLua for iOS --- scripting/lua/CMakeLists.txt | 8 ++++++-- scripting/lua/LuaCallWrapper.h | 4 ++++ scripting/lua/LuaFunctor.h | 4 ++++ scripting/lua/LuaReference.cpp | 4 ++++ scripting/lua/LuaReference.h | 3 +++ scripting/lua/LuaScriptModule.cpp | 4 ++++ scripting/lua/LuaScriptModule.h | 4 ++++ scripting/lua/LuaScriptingContext.cpp | 4 ++++ scripting/lua/LuaScriptingContext.h | 4 ++++ scripting/lua/LuaSpellEffect.cpp | 4 ++++ scripting/lua/LuaSpellEffect.h | 8 ++++++-- scripting/lua/LuaStack.cpp | 4 ++++ scripting/lua/LuaStack.h | 4 ++++ scripting/lua/LuaWrapper.h | 4 ++++ scripting/lua/StdInc.cpp | 2 +- scripting/lua/StdInc.h | 1 + scripting/lua/api/Artifact.cpp | 4 ++++ scripting/lua/api/Artifact.h | 4 ++++ scripting/lua/api/BattleCb.cpp | 4 ++++ scripting/lua/api/BattleCb.h | 4 ++++ scripting/lua/api/BonusSystem.cpp | 4 ++++ scripting/lua/api/BonusSystem.h | 4 ++++ scripting/lua/api/Creature.cpp | 4 ++++ scripting/lua/api/Creature.h | 4 ++++ scripting/lua/api/Faction.cpp | 4 ++++ scripting/lua/api/Faction.h | 4 ++++ scripting/lua/api/GameCb.cpp | 4 ++++ scripting/lua/api/GameCb.h | 4 ++++ scripting/lua/api/HeroClass.cpp | 4 ++++ scripting/lua/api/HeroClass.h | 4 ++++ scripting/lua/api/HeroInstance.cpp | 3 +++ scripting/lua/api/HeroInstance.h | 3 +++ scripting/lua/api/HeroType.cpp | 4 ++++ scripting/lua/api/HeroType.h | 4 ++++ scripting/lua/api/ObjectInstance.cpp | 2 ++ scripting/lua/api/ObjectInstance.h | 2 ++ scripting/lua/api/Player.cpp | 2 ++ scripting/lua/api/Player.h | 2 ++ scripting/lua/api/Registry.cpp | 4 ++++ scripting/lua/api/Registry.h | 4 ++++ scripting/lua/api/ServerCb.cpp | 5 +++++ scripting/lua/api/ServerCb.h | 4 ++++ scripting/lua/api/Services.cpp | 4 ++++ scripting/lua/api/Services.h | 4 ++++ scripting/lua/api/Skill.cpp | 4 ++++ scripting/lua/api/Skill.h | 4 ++++ scripting/lua/api/Spell.cpp | 4 ++++ scripting/lua/api/Spell.h | 4 ++++ scripting/lua/api/StackInstance.cpp | 3 +++ scripting/lua/api/StackInstance.h | 3 +++ scripting/lua/api/battle/UnitProxy.cpp | 4 ++++ scripting/lua/api/battle/UnitProxy.h | 4 ++++ scripting/lua/api/events/AdventureEvents.cpp | 2 ++ scripting/lua/api/events/AdventureEvents.h | 2 ++ scripting/lua/api/events/BattleEvents.cpp | 4 ++++ scripting/lua/api/events/BattleEvents.h | 4 +++- scripting/lua/api/events/EventBusProxy.cpp | 3 +++ scripting/lua/api/events/EventBusProxy.h | 4 ++++ scripting/lua/api/events/GenericEvents.cpp | 4 ++++ scripting/lua/api/events/GenericEvents.h | 4 +++- scripting/lua/api/events/SubscriptionRegistryProxy.cpp | 4 ++++ scripting/lua/api/events/SubscriptionRegistryProxy.h | 4 ++++ scripting/lua/api/netpacks/BattleLogMessage.cpp | 4 ++++ scripting/lua/api/netpacks/BattleLogMessage.h | 4 ++++ scripting/lua/api/netpacks/BattleStackMoved.cpp | 4 ++++ scripting/lua/api/netpacks/BattleStackMoved.h | 4 ++++ scripting/lua/api/netpacks/BattleUnitsChanged.cpp | 4 ++++ scripting/lua/api/netpacks/BattleUnitsChanged.h | 4 ++++ scripting/lua/api/netpacks/EntitiesChanged.cpp | 4 ++++ scripting/lua/api/netpacks/EntitiesChanged.h | 5 ++++- scripting/lua/api/netpacks/InfoWindow.cpp | 4 ++++ scripting/lua/api/netpacks/InfoWindow.h | 4 ++++ scripting/lua/api/netpacks/PackForClient.h | 4 ++++ scripting/lua/api/netpacks/SetResources.cpp | 4 ++++ scripting/lua/api/netpacks/SetResources.h | 4 ++++ 75 files changed, 279 insertions(+), 8 deletions(-) diff --git a/scripting/lua/CMakeLists.txt b/scripting/lua/CMakeLists.txt index ed4aa93f7..a376c62c7 100644 --- a/scripting/lua/CMakeLists.txt +++ b/scripting/lua/CMakeLists.txt @@ -83,12 +83,16 @@ set(lib_HDRS ) add_library(vcmiLua SHARED ${lib_SRCS} ${lib_HDRS}) -target_link_libraries(vcmiLua Boost::boost luajit::luajit vcmi) +target_link_libraries(vcmiLua Boost::boost luajit::luajit ${VCMI_LIB_TARGET}) vcmi_set_output_dir(vcmiLua "scripting") enable_pch(vcmiLua) -install(TARGETS vcmiLua LIBRARY DESTINATION ${SCRIPTING_LIB_DIR} OPTIONAL) +if(APPLE_IOS) + install(TARGETS vcmiLua LIBRARY DESTINATION ${SCRIPTING_LIB_DIR}) +else() + install(TARGETS vcmiLua DESTINATION ${SCRIPTING_LIB_DIR}) +endif() #manually copy lua dll from vcpkg folder to build directory on windows since vcpkg deps copy feature has flaws, using hardcoded paths based on vcmi windows deps package 1.1 from github if(MSVC) diff --git a/scripting/lua/LuaCallWrapper.h b/scripting/lua/LuaCallWrapper.h index d3f674a42..c098116a3 100644 --- a/scripting/lua/LuaCallWrapper.h +++ b/scripting/lua/LuaCallWrapper.h @@ -13,6 +13,8 @@ #include "api/Registry.h" #include "LuaStack.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { @@ -329,3 +331,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/LuaFunctor.h b/scripting/lua/LuaFunctor.h index 148062e91..5daab6262 100644 --- a/scripting/lua/LuaFunctor.h +++ b/scripting/lua/LuaFunctor.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { @@ -21,3 +23,5 @@ public: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/LuaReference.cpp b/scripting/lua/LuaReference.cpp index 3cc0f7d42..a5b8c2f44 100644 --- a/scripting/lua/LuaReference.cpp +++ b/scripting/lua/LuaReference.cpp @@ -11,6 +11,8 @@ #include "LuaReference.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { @@ -42,3 +44,5 @@ void LuaReference::push() } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/LuaReference.h b/scripting/lua/LuaReference.h index c28bac405..22290aa55 100644 --- a/scripting/lua/LuaReference.h +++ b/scripting/lua/LuaReference.h @@ -10,6 +10,8 @@ #pragma once +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { @@ -31,3 +33,4 @@ private: } +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/LuaScriptModule.cpp b/scripting/lua/LuaScriptModule.cpp index 302d30762..ab2f350b2 100644 --- a/scripting/lua/LuaScriptModule.cpp +++ b/scripting/lua/LuaScriptModule.cpp @@ -19,6 +19,8 @@ const char *g_cszAiName = "Lua interpreter"; +VCMI_LIB_NAMESPACE_BEGIN + extern "C" DLL_EXPORT void GetAiName(char * name) { strcpy_s(name, strlen(g_cszAiName) + 1, g_cszAiName); @@ -54,3 +56,5 @@ void LuaScriptModule::registerSpellEffect(spells::effects::Registry * registry, } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/LuaScriptModule.h b/scripting/lua/LuaScriptModule.h index 7bdfbc4b3..af64c3ebe 100644 --- a/scripting/lua/LuaScriptModule.h +++ b/scripting/lua/LuaScriptModule.h @@ -12,6 +12,8 @@ #include "../../lib/CScriptingModule.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { @@ -31,3 +33,5 @@ private: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/LuaScriptingContext.cpp b/scripting/lua/LuaScriptingContext.cpp index 1b438b3e8..8fe13d813 100644 --- a/scripting/lua/LuaScriptingContext.cpp +++ b/scripting/lua/LuaScriptingContext.cpp @@ -26,6 +26,8 @@ #include "../../lib/CGameInfoCallback.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { @@ -605,3 +607,5 @@ int LuaContext::logErrorImpl() } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/LuaScriptingContext.h b/scripting/lua/LuaScriptingContext.h index 5ea346883..b563f8f1e 100644 --- a/scripting/lua/LuaScriptingContext.h +++ b/scripting/lua/LuaScriptingContext.h @@ -16,6 +16,8 @@ #include "../../lib/ScriptHandler.h" #include "../../lib/CScriptingModule.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { @@ -88,3 +90,5 @@ private: }; } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/LuaSpellEffect.cpp b/scripting/lua/LuaSpellEffect.cpp index d082cffe6..e698e52eb 100644 --- a/scripting/lua/LuaSpellEffect.cpp +++ b/scripting/lua/LuaSpellEffect.cpp @@ -24,6 +24,8 @@ static const std::string APPLICABLE_GENERAL = "applicable"; static const std::string APPLICABLE_TARGET = "applicableTarget"; static const std::string APPLY = "apply"; +VCMI_LIB_NAMESPACE_BEGIN + namespace spells { namespace effects @@ -184,3 +186,5 @@ void LuaSpellEffect::setContextVariables(const Mechanics * m, std::shared_ptr ArtifactProxy::REGISTER_CUSTOM = } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Artifact.h b/scripting/lua/api/Artifact.h index bc26998bb..b20d8ad7a 100644 --- a/scripting/lua/api/Artifact.h +++ b/scripting/lua/api/Artifact.h @@ -14,6 +14,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -29,3 +31,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/BattleCb.cpp b/scripting/lua/api/BattleCb.cpp index 0f8127797..098012ed4 100644 --- a/scripting/lua/api/BattleCb.cpp +++ b/scripting/lua/api/BattleCb.cpp @@ -19,6 +19,8 @@ #include "../../../lib/battle/Unit.h" #include "../../../lib/BattleFieldHandler.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -114,3 +116,5 @@ int BattleCbProxy::getUnitByPos(lua_State * L) } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/BattleCb.h b/scripting/lua/api/BattleCb.h index 1f3edfd7a..44bff6679 100644 --- a/scripting/lua/api/BattleCb.h +++ b/scripting/lua/api/BattleCb.h @@ -15,6 +15,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -34,3 +36,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/BonusSystem.cpp b/scripting/lua/api/BonusSystem.cpp index 5aa67db9f..cb03f6481 100644 --- a/scripting/lua/api/BonusSystem.cpp +++ b/scripting/lua/api/BonusSystem.cpp @@ -18,6 +18,8 @@ #include "../LuaStack.h" #include "../LuaCallWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -253,3 +255,5 @@ int BonusBearerProxy::getBonuses(lua_State * L) } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/BonusSystem.h b/scripting/lua/api/BonusSystem.h index a6baa4ecb..657243670 100644 --- a/scripting/lua/api/BonusSystem.h +++ b/scripting/lua/api/BonusSystem.h @@ -12,6 +12,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + struct Bonus; class BonusList; class IBonusBearer; @@ -70,3 +72,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Creature.cpp b/scripting/lua/api/Creature.cpp index 17d9a81d6..0b4713a83 100644 --- a/scripting/lua/api/Creature.cpp +++ b/scripting/lua/api/Creature.cpp @@ -17,6 +17,8 @@ #include "../LuaCallWrapper.h" #include "../../../lib/HeroBonus.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -60,3 +62,5 @@ const std::vector CreatureProxy::REGISTER_CUSTOM = } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Creature.h b/scripting/lua/api/Creature.h index e69f60231..f13a81296 100644 --- a/scripting/lua/api/Creature.h +++ b/scripting/lua/api/Creature.h @@ -14,6 +14,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -30,3 +32,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Faction.cpp b/scripting/lua/api/Faction.cpp index d1fa96010..358c43dcb 100644 --- a/scripting/lua/api/Faction.cpp +++ b/scripting/lua/api/Faction.cpp @@ -16,6 +16,8 @@ #include "../LuaStack.h" #include "../LuaCallWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -34,3 +36,5 @@ const std::vector FactionProxy::REGISTER_CUSTOM = } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Faction.h b/scripting/lua/api/Faction.h index 19b8f170d..1c11ae1fa 100644 --- a/scripting/lua/api/Faction.h +++ b/scripting/lua/api/Faction.h @@ -14,6 +14,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -28,3 +30,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/GameCb.cpp b/scripting/lua/api/GameCb.cpp index 7387fe9cf..5bf19b3df 100644 --- a/scripting/lua/api/GameCb.cpp +++ b/scripting/lua/api/GameCb.cpp @@ -17,6 +17,8 @@ #include "../../../lib/mapObjects/CGHeroInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -39,3 +41,5 @@ const std::vector GameCbProxy::REGISTER_CUSTOM = } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/GameCb.h b/scripting/lua/api/GameCb.h index d485b0c06..5374de6b9 100644 --- a/scripting/lua/api/GameCb.h +++ b/scripting/lua/api/GameCb.h @@ -15,6 +15,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -31,3 +33,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/HeroClass.cpp b/scripting/lua/api/HeroClass.cpp index 874b72a63..03835c4e5 100644 --- a/scripting/lua/api/HeroClass.cpp +++ b/scripting/lua/api/HeroClass.cpp @@ -16,6 +16,8 @@ #include "../LuaStack.h" #include "../LuaCallWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -32,3 +34,5 @@ const std::vector HeroClassProxy::REGISTER_CUSTOM } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/HeroClass.h b/scripting/lua/api/HeroClass.h index 9c228a21e..0e95ecdfd 100644 --- a/scripting/lua/api/HeroClass.h +++ b/scripting/lua/api/HeroClass.h @@ -14,6 +14,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -29,3 +31,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/HeroInstance.cpp b/scripting/lua/api/HeroInstance.cpp index ba1e77630..c00d2c7de 100644 --- a/scripting/lua/api/HeroInstance.cpp +++ b/scripting/lua/api/HeroInstance.cpp @@ -16,6 +16,8 @@ #include "../LuaStack.h" #include "../LuaCallWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -31,3 +33,4 @@ const std::vector HeroInstanceProxy::REGISTER_ } } +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/HeroInstance.h b/scripting/lua/api/HeroInstance.h index a446e4ede..0b1503a84 100644 --- a/scripting/lua/api/HeroInstance.h +++ b/scripting/lua/api/HeroInstance.h @@ -16,6 +16,8 @@ #include "../../../lib/mapObjects/CGHeroInstance.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -32,3 +34,4 @@ public: } } +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/HeroType.cpp b/scripting/lua/api/HeroType.cpp index f7630731e..c48ee8f48 100644 --- a/scripting/lua/api/HeroType.cpp +++ b/scripting/lua/api/HeroType.cpp @@ -16,6 +16,8 @@ #include "../LuaStack.h" #include "../LuaCallWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -34,3 +36,5 @@ const std::vector HeroTypeProxy::REGISTER_CUSTOM = } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/HeroType.h b/scripting/lua/api/HeroType.h index d41f695e6..558ee4d4b 100644 --- a/scripting/lua/api/HeroType.h +++ b/scripting/lua/api/HeroType.h @@ -14,6 +14,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -29,3 +31,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/ObjectInstance.cpp b/scripting/lua/api/ObjectInstance.cpp index dd13c3f15..34feb946a 100644 --- a/scripting/lua/api/ObjectInstance.cpp +++ b/scripting/lua/api/ObjectInstance.cpp @@ -34,3 +34,5 @@ const std::vector ObjectInstanceProxy::REGIS } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/ObjectInstance.h b/scripting/lua/api/ObjectInstance.h index 5e4513886..a5542a650 100644 --- a/scripting/lua/api/ObjectInstance.h +++ b/scripting/lua/api/ObjectInstance.h @@ -32,3 +32,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Player.cpp b/scripting/lua/api/Player.cpp index c80ab8407..f5d0c12ef 100644 --- a/scripting/lua/api/Player.cpp +++ b/scripting/lua/api/Player.cpp @@ -36,3 +36,5 @@ const std::vector PlayerProxy::REGISTER_CUSTOM = } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Player.h b/scripting/lua/api/Player.h index 71aa808a4..74a7e6f8b 100644 --- a/scripting/lua/api/Player.h +++ b/scripting/lua/api/Player.h @@ -29,3 +29,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Registry.cpp b/scripting/lua/api/Registry.cpp index 10eabb014..5af09bc55 100644 --- a/scripting/lua/api/Registry.cpp +++ b/scripting/lua/api/Registry.cpp @@ -11,6 +11,8 @@ #include "api/Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -86,3 +88,5 @@ const char * TypeRegistry::getKeyForType(const std::type_info & type) } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Registry.h b/scripting/lua/api/Registry.h index c3148412c..d9a168c37 100644 --- a/scripting/lua/api/Registry.h +++ b/scripting/lua/api/Registry.h @@ -27,6 +27,8 @@ RegisterCoreAPI _register ## Type (Name);\ }\ \ +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -108,3 +110,5 @@ private: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/ServerCb.cpp b/scripting/lua/api/ServerCb.cpp index 10887d60b..f448efb54 100644 --- a/scripting/lua/api/ServerCb.cpp +++ b/scripting/lua/api/ServerCb.cpp @@ -15,6 +15,9 @@ #include "../LuaStack.h" #include "../../../lib/NetPacks.h" + +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -100,3 +103,5 @@ int ServerCbProxy::apply(lua_State * L) } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/ServerCb.h b/scripting/lua/api/ServerCb.h index fc2ec656a..b0c069d85 100644 --- a/scripting/lua/api/ServerCb.h +++ b/scripting/lua/api/ServerCb.h @@ -14,6 +14,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -33,3 +35,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Services.cpp b/scripting/lua/api/Services.cpp index 78bfcbde6..5782f3b30 100644 --- a/scripting/lua/api/Services.cpp +++ b/scripting/lua/api/Services.cpp @@ -26,6 +26,8 @@ #include "../LuaCallWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -95,3 +97,5 @@ const std::vector SpellServiceProxy::REGISTER_ } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Services.h b/scripting/lua/api/Services.h index 192caa41c..55392fe1a 100644 --- a/scripting/lua/api/Services.h +++ b/scripting/lua/api/Services.h @@ -22,6 +22,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -87,3 +89,5 @@ public: } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Skill.cpp b/scripting/lua/api/Skill.cpp index f322bf3bd..bf00a0cca 100644 --- a/scripting/lua/api/Skill.cpp +++ b/scripting/lua/api/Skill.cpp @@ -16,6 +16,8 @@ #include "../LuaStack.h" #include "../LuaCallWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -32,3 +34,5 @@ const std::vector SkillProxy::REGISTER_CUSTOM = } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Skill.h b/scripting/lua/api/Skill.h index 8fa107ab8..28296f9bd 100644 --- a/scripting/lua/api/Skill.h +++ b/scripting/lua/api/Skill.h @@ -14,6 +14,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -29,3 +31,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Spell.cpp b/scripting/lua/api/Spell.cpp index 78ebc8444..cd3eb9a3f 100644 --- a/scripting/lua/api/Spell.cpp +++ b/scripting/lua/api/Spell.cpp @@ -16,6 +16,8 @@ #include "../LuaStack.h" #include "../LuaCallWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -51,3 +53,5 @@ const std::vector SpellProxy::REGISTER_CUSTOM = } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/Spell.h b/scripting/lua/api/Spell.h index 18fe7c2dd..1e0e9c88f 100644 --- a/scripting/lua/api/Spell.h +++ b/scripting/lua/api/Spell.h @@ -14,6 +14,8 @@ #include "../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -28,3 +30,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/StackInstance.cpp b/scripting/lua/api/StackInstance.cpp index 05c608693..b413a823f 100644 --- a/scripting/lua/api/StackInstance.cpp +++ b/scripting/lua/api/StackInstance.cpp @@ -17,6 +17,8 @@ #include "../LuaCallWrapper.h" #include +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -33,3 +35,4 @@ const std::vector StackInstanceProxy::REGISTE } } +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/StackInstance.h b/scripting/lua/api/StackInstance.h index b9f8b6fa5..47e0f5ea1 100644 --- a/scripting/lua/api/StackInstance.h +++ b/scripting/lua/api/StackInstance.h @@ -16,6 +16,8 @@ #include "../../../lib/CCreatureSet.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -32,3 +34,4 @@ public: } } +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/battle/UnitProxy.cpp b/scripting/lua/api/battle/UnitProxy.cpp index f99c2d63a..472861bad 100644 --- a/scripting/lua/api/battle/UnitProxy.cpp +++ b/scripting/lua/api/battle/UnitProxy.cpp @@ -16,6 +16,8 @@ #include "../../LuaCallWrapper.h" #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -38,3 +40,5 @@ const std::vector UnitProxy::REGISTER_CUSTOM = } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/battle/UnitProxy.h b/scripting/lua/api/battle/UnitProxy.h index 732b89148..e654b36cf 100644 --- a/scripting/lua/api/battle/UnitProxy.h +++ b/scripting/lua/api/battle/UnitProxy.h @@ -15,6 +15,8 @@ #include "../../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -34,3 +36,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/AdventureEvents.cpp b/scripting/lua/api/events/AdventureEvents.cpp index b51beb163..f09081a85 100644 --- a/scripting/lua/api/events/AdventureEvents.cpp +++ b/scripting/lua/api/events/AdventureEvents.cpp @@ -38,3 +38,5 @@ const std::vector ObjectVisitStartedProx } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/AdventureEvents.h b/scripting/lua/api/events/AdventureEvents.h index a1f60e081..3a4beccbc 100644 --- a/scripting/lua/api/events/AdventureEvents.h +++ b/scripting/lua/api/events/AdventureEvents.h @@ -38,3 +38,5 @@ public: } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/BattleEvents.cpp b/scripting/lua/api/events/BattleEvents.cpp index d89a0af1b..6196f3c90 100644 --- a/scripting/lua/api/events/BattleEvents.cpp +++ b/scripting/lua/api/events/BattleEvents.cpp @@ -17,6 +17,8 @@ #include "../../../../lib/battle/Unit.h" #include "SubscriptionRegistryProxy.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -66,3 +68,5 @@ const std::vector ApplyDamageProxy::REGISTER_CU } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/BattleEvents.h b/scripting/lua/api/events/BattleEvents.h index 6d03cca0e..172f23fec 100644 --- a/scripting/lua/api/events/BattleEvents.h +++ b/scripting/lua/api/events/BattleEvents.h @@ -16,6 +16,8 @@ #include "EventBusProxy.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -34,4 +36,4 @@ public: } } - +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/EventBusProxy.cpp b/scripting/lua/api/events/EventBusProxy.cpp index 64f57c47d..8806d2fcd 100644 --- a/scripting/lua/api/events/EventBusProxy.cpp +++ b/scripting/lua/api/events/EventBusProxy.cpp @@ -16,6 +16,8 @@ #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -30,3 +32,4 @@ const std::vector EventBusProxy::REGISTER_CUSTOM = } } +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/EventBusProxy.h b/scripting/lua/api/events/EventBusProxy.h index 6930b71d9..fb53210d9 100644 --- a/scripting/lua/api/events/EventBusProxy.h +++ b/scripting/lua/api/events/EventBusProxy.h @@ -14,6 +14,8 @@ #include "../../LuaWrapper.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -31,3 +33,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/GenericEvents.cpp b/scripting/lua/api/events/GenericEvents.cpp index efa398ef5..8b42dcfc4 100644 --- a/scripting/lua/api/events/GenericEvents.cpp +++ b/scripting/lua/api/events/GenericEvents.cpp @@ -16,6 +16,8 @@ #include "../Registry.h" #include "SubscriptionRegistryProxy.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -86,3 +88,5 @@ const std::vector TurnStartedProxy::REGISTER_CU } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/GenericEvents.h b/scripting/lua/api/events/GenericEvents.h index 63294651b..bcd51dc50 100644 --- a/scripting/lua/api/events/GenericEvents.h +++ b/scripting/lua/api/events/GenericEvents.h @@ -16,6 +16,8 @@ #include "EventBusProxy.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -48,4 +50,4 @@ public: } } - +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/SubscriptionRegistryProxy.cpp b/scripting/lua/api/events/SubscriptionRegistryProxy.cpp index 0dd1c4602..cef1fcca0 100644 --- a/scripting/lua/api/events/SubscriptionRegistryProxy.cpp +++ b/scripting/lua/api/events/SubscriptionRegistryProxy.cpp @@ -13,6 +13,8 @@ #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -25,3 +27,5 @@ const std::vector EventSubscriptionProxy: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/events/SubscriptionRegistryProxy.h b/scripting/lua/api/events/SubscriptionRegistryProxy.h index 430f7a0a4..b84002051 100644 --- a/scripting/lua/api/events/SubscriptionRegistryProxy.h +++ b/scripting/lua/api/events/SubscriptionRegistryProxy.h @@ -18,6 +18,8 @@ #include "../../LuaStack.h" #include "../../LuaReference.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -128,3 +130,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/BattleLogMessage.cpp b/scripting/lua/api/netpacks/BattleLogMessage.cpp index dbd03f4c5..77f87fe1b 100644 --- a/scripting/lua/api/netpacks/BattleLogMessage.cpp +++ b/scripting/lua/api/netpacks/BattleLogMessage.cpp @@ -15,6 +15,8 @@ #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -56,3 +58,5 @@ int BattleLogMessageProxy::addText(lua_State * L) } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/BattleLogMessage.h b/scripting/lua/api/netpacks/BattleLogMessage.h index bf0c240d8..ebe6f049e 100644 --- a/scripting/lua/api/netpacks/BattleLogMessage.h +++ b/scripting/lua/api/netpacks/BattleLogMessage.h @@ -12,6 +12,8 @@ #include "PackForClient.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -32,3 +34,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/BattleStackMoved.cpp b/scripting/lua/api/netpacks/BattleStackMoved.cpp index 8661223da..888b1422e 100644 --- a/scripting/lua/api/netpacks/BattleStackMoved.cpp +++ b/scripting/lua/api/netpacks/BattleStackMoved.cpp @@ -15,6 +15,8 @@ #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -82,3 +84,5 @@ int BattleStackMovedProxy::setTeleporting(lua_State * L) } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/BattleStackMoved.h b/scripting/lua/api/netpacks/BattleStackMoved.h index e46346119..3926a737e 100644 --- a/scripting/lua/api/netpacks/BattleStackMoved.h +++ b/scripting/lua/api/netpacks/BattleStackMoved.h @@ -12,6 +12,8 @@ #include "PackForClient.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -35,3 +37,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/BattleUnitsChanged.cpp b/scripting/lua/api/netpacks/BattleUnitsChanged.cpp index 07dc93cf4..5a938a396 100644 --- a/scripting/lua/api/netpacks/BattleUnitsChanged.cpp +++ b/scripting/lua/api/netpacks/BattleUnitsChanged.cpp @@ -15,6 +15,8 @@ #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -112,3 +114,5 @@ int BattleUnitsChangedProxy::remove(lua_State * L) } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/BattleUnitsChanged.h b/scripting/lua/api/netpacks/BattleUnitsChanged.h index 269db559e..2344076e3 100644 --- a/scripting/lua/api/netpacks/BattleUnitsChanged.h +++ b/scripting/lua/api/netpacks/BattleUnitsChanged.h @@ -12,6 +12,8 @@ #include "PackForClient.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -35,3 +37,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/EntitiesChanged.cpp b/scripting/lua/api/netpacks/EntitiesChanged.cpp index fa62eb2a9..2765d9480 100644 --- a/scripting/lua/api/netpacks/EntitiesChanged.cpp +++ b/scripting/lua/api/netpacks/EntitiesChanged.cpp @@ -15,6 +15,8 @@ #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -61,3 +63,5 @@ int EntitiesChangedProxy::update(lua_State * L) } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/EntitiesChanged.h b/scripting/lua/api/netpacks/EntitiesChanged.h index 362fe4134..4b7e0f0b8 100644 --- a/scripting/lua/api/netpacks/EntitiesChanged.h +++ b/scripting/lua/api/netpacks/EntitiesChanged.h @@ -10,9 +10,10 @@ #pragma once - #include "PackForClient.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -33,3 +34,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/InfoWindow.cpp b/scripting/lua/api/netpacks/InfoWindow.cpp index 5ae41afb0..41899448c 100644 --- a/scripting/lua/api/netpacks/InfoWindow.cpp +++ b/scripting/lua/api/netpacks/InfoWindow.cpp @@ -15,6 +15,8 @@ #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + using scripting::api::netpacks::InfoWindowProxy; using scripting::api::RegisterAPI; @@ -126,3 +128,5 @@ int InfoWindowProxy::setPlayer(lua_State * L) } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/InfoWindow.h b/scripting/lua/api/netpacks/InfoWindow.h index 099ce923b..f941761f8 100644 --- a/scripting/lua/api/netpacks/InfoWindow.h +++ b/scripting/lua/api/netpacks/InfoWindow.h @@ -12,6 +12,8 @@ #include "PackForClient.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -33,3 +35,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/PackForClient.h b/scripting/lua/api/netpacks/PackForClient.h index 71618b68b..c81732ce3 100644 --- a/scripting/lua/api/netpacks/PackForClient.h +++ b/scripting/lua/api/netpacks/PackForClient.h @@ -14,6 +14,8 @@ #include "../../../../lib/NetPacks.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -43,3 +45,5 @@ public: } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/SetResources.cpp b/scripting/lua/api/netpacks/SetResources.cpp index 37ae5ac83..af09837f9 100644 --- a/scripting/lua/api/netpacks/SetResources.cpp +++ b/scripting/lua/api/netpacks/SetResources.cpp @@ -15,6 +15,8 @@ #include "../Registry.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -157,3 +159,5 @@ int SetResourcesProxy::clear(lua_State * L) } } } + +VCMI_LIB_NAMESPACE_END diff --git a/scripting/lua/api/netpacks/SetResources.h b/scripting/lua/api/netpacks/SetResources.h index b555e71f2..d58908240 100644 --- a/scripting/lua/api/netpacks/SetResources.h +++ b/scripting/lua/api/netpacks/SetResources.h @@ -12,6 +12,8 @@ #include "PackForClient.h" +VCMI_LIB_NAMESPACE_BEGIN + namespace scripting { namespace api @@ -38,3 +40,5 @@ public: } } } + +VCMI_LIB_NAMESPACE_END From 84111d99ca5bbc39c0d14a009abec33af65f5999 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 14:55:39 +0300 Subject: [PATCH 112/131] add VCMI logo to splash screen fix kambala-decapitator/vcmi#42 --- client/CMakeLists.txt | 2 +- client/ios/LaunchScreen.storyboard | 16 ++++++++++++++-- client/ios/vcmi_logo.png | Bin 0 -> 16783 bytes 3 files changed, 15 insertions(+), 3 deletions(-) create mode 100644 client/ios/vcmi_logo.png diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index 07d3674e6..cd9b76ad0 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -215,7 +215,7 @@ elseif(APPLE_IOS) XCODE_ATTRIBUTE_ASSETCATALOG_COMPILER_APPICON_NAME AppIcon ) - foreach(XCODE_RESOURCE LaunchScreen.storyboard Images.xcassets Settings.bundle) + foreach(XCODE_RESOURCE LaunchScreen.storyboard Images.xcassets Settings.bundle vcmi_logo.png) set(XCODE_RESOURCE_PATH ios/${XCODE_RESOURCE}) target_sources(vcmiclient PRIVATE ${XCODE_RESOURCE_PATH}) set_source_files_properties(${XCODE_RESOURCE_PATH} PROPERTIES MACOSX_PACKAGE_LOCATION Resources) diff --git a/client/ios/LaunchScreen.storyboard b/client/ios/LaunchScreen.storyboard index 14b2fa354..5b159219d 100644 --- a/client/ios/LaunchScreen.storyboard +++ b/client/ios/LaunchScreen.storyboard @@ -1,9 +1,9 @@ - + - + @@ -15,8 +15,17 @@ + + + + + + + + + @@ -24,4 +33,7 @@ + + + diff --git a/client/ios/vcmi_logo.png b/client/ios/vcmi_logo.png new file mode 100644 index 0000000000000000000000000000000000000000..1762c14aaf2b82034ca02966732f7905d7ab6f71 GIT binary patch literal 16783 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%0Alkcp6yB>^jx#8opd+wo@IRsCABGLCGGQdcRDF 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 Date: Mon, 15 Aug 2022 16:22:49 +0300 Subject: [PATCH 113/131] update AUTHORS --- AUTHORS | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/AUTHORS b/AUTHORS index c58bbfd79..079f813e3 100644 --- a/AUTHORS +++ b/AUTHORS @@ -78,6 +78,9 @@ Andrii Danylchenko Dmitry Orlov, * special buildings support in fan towns, new features and bug fixes - -Andrey Cherkas aka nordsoft, - * new terrain support, random map generator features and various bug fixes \ No newline at end of file + +Andrey Cherkas aka nordsoft, + * new terrain support, random map generator features and various bug fixes + +Andrey Filipenkov aka kambala-decapitator, + * iOS support, macOS improvements, various bug fixes From e1c9903a45a70bd813f5979bd95042a8d2312e25 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 16:29:11 +0300 Subject: [PATCH 114/131] extract iOS helpers into a shared lib --- CMakeLists.txt | 4 +++ client/CMakeLists.txt | 2 ++ client/gui/SDL_Extensions.cpp | 6 ++-- client/ios/startSDL.mm | 3 -- cmake_modules/VCMI_lib.cmake | 8 ++---- ios/CMakeLists.txt | 11 ++++++++ ios/iOS_utils.h | 31 +++++++++++++++++++++ ios/iOS_utils.mm | 52 +++++++++++++++++++++++++++++++++++ lib/CIOSUtils.h | 36 ------------------------ lib/CIOSUtils.m | 42 ---------------------------- lib/VCMIDirs.cpp | 20 ++++++++------ lib/logging/CLogger.cpp | 4 +-- 12 files changed, 120 insertions(+), 99 deletions(-) create mode 100644 ios/CMakeLists.txt create mode 100644 ios/iOS_utils.h create mode 100644 ios/iOS_utils.mm delete mode 100644 lib/CIOSUtils.h delete mode 100644 lib/CIOSUtils.m diff --git a/CMakeLists.txt b/CMakeLists.txt index 649a5a1c8..79779e2f7 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -404,6 +404,10 @@ set(SCRIPTING_LIB_DIR "${LIB_DIR}/scripting") # Add subdirectories # ####################################### +if(APPLE_IOS) + add_subdirectory(ios) +endif() + include(VCMI_lib) if(BUILD_SINGLE_APP) add_subdirectory(lib_client) diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index cd9b76ad0..d88841c3e 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -198,6 +198,8 @@ if(WIN32) target_compile_definitions(vcmiclient PRIVATE WINDOWS_IGNORE_PACKING_MISMATCH) elseif(APPLE_IOS) target_link_libraries(vcmiclient PRIVATE + iOS_utils + # FFmpeg bz2 iconv diff --git a/client/gui/SDL_Extensions.cpp b/client/gui/SDL_Extensions.cpp index 69ddb72d2..e0bf6cad7 100644 --- a/client/gui/SDL_Extensions.cpp +++ b/client/gui/SDL_Extensions.cpp @@ -18,8 +18,10 @@ #ifdef VCMI_APPLE #include +#endif -extern double ios_screenScale(); // TODO ios: move to appropriate file +#ifdef VCMI_IOS +#include "iOS_utils.h" #endif const SDL_Color Colors::YELLOW = { 229, 215, 123, 0 }; @@ -813,7 +815,7 @@ void CSDL_Ext::startTextInput(SDL_Rect * where) SDL_RenderGetScale(renderer, &scaleX, &scaleY); SDL_RenderGetViewport(renderer, &viewport); - auto nativeScale = ios_screenScale(); + const auto nativeScale = iOS_utils::screenScale(); auto rectInScreenCoordinates = *where; rectInScreenCoordinates.x = (viewport.x + rectInScreenCoordinates.x) * scaleX / nativeScale; rectInScreenCoordinates.y = (viewport.y + rectInScreenCoordinates.y) * scaleY / nativeScale; diff --git a/client/ios/startSDL.mm b/client/ios/startSDL.mm index f6969c384..3dec2f3b6 100644 --- a/client/ios/startSDL.mm +++ b/client/ios/startSDL.mm @@ -22,9 +22,6 @@ #import - -double ios_screenScale() { return UIScreen.mainScreen.nativeScale; } - @interface SDLViewObserver : NSObject @property (nonatomic, strong) GameChatKeyboardHanlder * gameChatHandler; @end diff --git a/cmake_modules/VCMI_lib.cmake b/cmake_modules/VCMI_lib.cmake index ec688e307..b143c860e 100644 --- a/cmake_modules/VCMI_lib.cmake +++ b/cmake_modules/VCMI_lib.cmake @@ -441,11 +441,6 @@ macro(add_main_lib TARGET_NAME LIBRARY_TYPE) ${MAIN_LIB_DIR}/VCMI_Lib.h ) - if(APPLE_IOS) - set(lib_SRCS ${lib_SRCS} ${MAIN_LIB_DIR}/CIOSUtils.m) - set(lib_HEADERS ${lib_HEADERS} ${MAIN_LIB_DIR}/CIOSUtils.h) - endif(APPLE_IOS) - assign_source_group(${lib_SRCS} ${lib_HEADERS}) add_library(${TARGET_NAME} ${LIBRARY_TYPE} ${lib_SRCS} ${lib_HEADERS}) @@ -454,6 +449,9 @@ macro(add_main_lib TARGET_NAME LIBRARY_TYPE) minizip::minizip ZLIB::ZLIB ${SYSTEM_LIBS} Boost::boost Boost::thread Boost::filesystem Boost::program_options Boost::locale Boost::date_time ) + if(APPLE_IOS) + target_link_libraries(${TARGET_NAME} PUBLIC iOS_utils) + endif() target_include_directories(${TARGET_NAME} PUBLIC ${CMAKE_CURRENT_SOURCE_DIR} diff --git a/ios/CMakeLists.txt b/ios/CMakeLists.txt new file mode 100644 index 000000000..c3d6537c9 --- /dev/null +++ b/ios/CMakeLists.txt @@ -0,0 +1,11 @@ +add_library(iOS_utils SHARED + iOS_utils.h + iOS_utils.mm +) +target_link_libraries(iOS_utils PRIVATE + "-framework Foundation" + "-framework UIKit" +) +target_include_directories(iOS_utils PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) + +vcmi_set_output_dir(iOS_utils "") diff --git a/ios/iOS_utils.h b/ios/iOS_utils.h new file mode 100644 index 000000000..c56f82f7d --- /dev/null +++ b/ios/iOS_utils.h @@ -0,0 +1,31 @@ +/* + * iOS_utils.h, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#pragma once + +#include + +#pragma GCC visibility push(default) +namespace iOS_utils +{ +const char *documentsPath(); +const char *cachesPath(); + +#if TARGET_OS_SIMULATOR +const char *hostApplicationSupportPath(); +#endif + +const char *bundlePath(); +const char *frameworksPath(); + +const char *bundleIdentifier(); + +double screenScale(); +} +#pragma GCC visibility pop diff --git a/ios/iOS_utils.mm b/ios/iOS_utils.mm new file mode 100644 index 000000000..50fe76f3e --- /dev/null +++ b/ios/iOS_utils.mm @@ -0,0 +1,52 @@ +/* + * iOS_utils.mm, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ + +#include "iOS_utils.h" + +#import +#import + +namespace +{ +NSString *standardPathNative(NSSearchPathDirectory directory) +{ + return [NSFileManager.defaultManager URLForDirectory:directory inDomain:NSUserDomainMask appropriateForURL:nil create:NO error:NULL].path; +} +const char *standardPath(NSSearchPathDirectory directory) { return standardPathNative(directory).fileSystemRepresentation; } +} + + +namespace iOS_utils +{ +const char *documentsPath() { return standardPath(NSDocumentDirectory); } +const char *cachesPath() { return standardPath(NSCachesDirectory); } + +#if TARGET_OS_SIMULATOR +const char *hostApplicationSupportPath() +{ + static NSString *applicationSupportPath; + static dispatch_once_t onceToken; + dispatch_once(&onceToken, ^{ + auto cachesPath = standardPathNative(NSCachesDirectory); + auto afterMacOsHomeDirPos = [cachesPath rangeOfString:@"Library/Developer"].location; + NSCAssert(afterMacOsHomeDirPos != NSNotFound, @"simulator directory location is not under user's home directory: %@", cachesPath); + applicationSupportPath = [[cachesPath substringToIndex:afterMacOsHomeDirPos] stringByAppendingPathComponent:@"Library/Application Support/vcmi"].stringByResolvingSymlinksInPath; + }); + return applicationSupportPath.fileSystemRepresentation; +} +#endif + +const char *bundlePath() { return NSBundle.mainBundle.bundlePath.fileSystemRepresentation; } +const char *frameworksPath() { return NSBundle.mainBundle.privateFrameworksPath.fileSystemRepresentation; } + +const char *bundleIdentifier() { return NSBundle.mainBundle.bundleIdentifier.UTF8String; } + +double screenScale() { return UIScreen.mainScreen.nativeScale; } +} diff --git a/lib/CIOSUtils.h b/lib/CIOSUtils.h deleted file mode 100644 index 1eb34cab6..000000000 --- a/lib/CIOSUtils.h +++ /dev/null @@ -1,36 +0,0 @@ -/* - * CIOSUtils.h, part of VCMI engine - * - * Authors: listed in file AUTHORS in main folder - * - * License: GNU General Public License v2.0 or later - * Full text of license available in license.txt file, in main folder - * - */ -#pragma once - -#ifdef __cplusplus -extern "C" { -#endif - -#include - -#ifdef __OBJC__ -@class NSURL; -#endif - -extern const char *ios_documentsPath(); -extern const char *ios_cachesPath(); - -#if TARGET_OS_SIMULATOR -extern const char *ios_hostApplicationSupportPath(); -#endif - -extern const char *ios_bundlePath(); -extern const char *ios_frameworksPath(); - -extern const char *ios_bundleIdentifier(); - -#ifdef __cplusplus -} -#endif diff --git a/lib/CIOSUtils.m b/lib/CIOSUtils.m deleted file mode 100644 index 905e5d62c..000000000 --- a/lib/CIOSUtils.m +++ /dev/null @@ -1,42 +0,0 @@ -/* - * CIOSUtils.m, part of VCMI engine - * - * Authors: listed in file AUTHORS in main folder - * - * License: GNU General Public License v2.0 or later - * Full text of license available in license.txt file, in main folder - * - */ - -#import "CIOSUtils.h" - -#import - -static NSString *standardPathNative(NSSearchPathDirectory directory) -{ - return [NSFileManager.defaultManager URLForDirectory:directory inDomain:NSUserDomainMask appropriateForURL:nil create:NO error:NULL].path; -} -static const char *standardPath(NSSearchPathDirectory directory) { return standardPathNative(directory).fileSystemRepresentation; } - -const char *ios_documentsPath() { return standardPath(NSDocumentDirectory); } -const char *ios_cachesPath() { return standardPath(NSCachesDirectory); } - -#if TARGET_OS_SIMULATOR -const char *ios_hostApplicationSupportPath() -{ - static NSString *applicationSupportPath; - static dispatch_once_t onceToken; - dispatch_once(&onceToken, ^{ - __auto_type cachesPath = standardPathNative(NSCachesDirectory); - __auto_type afterMacOsHomeDirPos = [cachesPath rangeOfString:@"Library/Developer"].location; - NSCAssert(afterMacOsHomeDirPos != NSNotFound, @"simulator directory location is not under user's home directory: %@", cachesPath); - applicationSupportPath = [[cachesPath substringToIndex:afterMacOsHomeDirPos] stringByAppendingPathComponent:@"Library/Application Support/vcmi"].stringByResolvingSymlinksInPath; - }); - return applicationSupportPath.fileSystemRepresentation; -} -#endif - -const char *ios_bundlePath() { return NSBundle.mainBundle.bundlePath.fileSystemRepresentation; } -const char *ios_frameworksPath() { return NSBundle.mainBundle.privateFrameworksPath.fileSystemRepresentation; } - -const char *ios_bundleIdentifier() { return NSBundle.mainBundle.bundleIdentifier.UTF8String; } diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index 1086a6955..4916ad6ef 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -11,6 +11,10 @@ #include "StdInc.h" #include "VCMIDirs.h" +#ifdef VCMI_IOS +#include "iOS_utils.h" +#endif + VCMI_LIB_NAMESPACE_BEGIN namespace bfs = boost::filesystem; @@ -377,8 +381,6 @@ bfs::path VCMIDirsApple::userConfigPath() const { return userDataPath() / "confi std::string VCMIDirsApple::libraryName(const std::string& basename) const { return "lib" + basename + ".dylib"; } #ifdef VCMI_IOS -#import "CIOSUtils.h" - class VCMIDirsIOS final : public VCMIDirsApple { public: @@ -392,25 +394,25 @@ class VCMIDirsIOS final : public VCMIDirsApple bfs::path binaryPath() const override; }; -bfs::path VCMIDirsIOS::userDataPath() const { return {ios_documentsPath()}; } -bfs::path VCMIDirsIOS::userCachePath() const { return {ios_cachesPath()}; } -bfs::path VCMIDirsIOS::userLogsPath() const { return {ios_documentsPath()}; } +bfs::path VCMIDirsIOS::userDataPath() const { return {iOS_utils::documentsPath()}; } +bfs::path VCMIDirsIOS::userCachePath() const { return {iOS_utils::cachesPath()}; } +bfs::path VCMIDirsIOS::userLogsPath() const { return {iOS_utils::documentsPath()}; } std::vector VCMIDirsIOS::dataPaths() const { std::vector paths; paths.reserve(4); #ifdef VCMI_IOS_SIM - paths.emplace_back(ios_hostApplicationSupportPath()); + paths.emplace_back(iOS_utils::hostApplicationSupportPath()); #endif paths.emplace_back(userDataPath()); - paths.emplace_back(ios_documentsPath()); + paths.emplace_back(iOS_utils::documentsPath()); paths.emplace_back(binaryPath()); return paths; } -bfs::path VCMIDirsIOS::libraryPath() const { return {ios_frameworksPath()}; } -bfs::path VCMIDirsIOS::binaryPath() const { return {ios_bundlePath()}; } +bfs::path VCMIDirsIOS::libraryPath() const { return {iOS_utils::frameworksPath()}; } +bfs::path VCMIDirsIOS::binaryPath() const { return {iOS_utils::bundlePath()}; } #elif defined(VCMI_MAC) class VCMIDirsOSX final : public VCMIDirsApple { diff --git a/lib/logging/CLogger.cpp b/lib/logging/CLogger.cpp index 9799c4bb5..4aeca9d76 100644 --- a/lib/logging/CLogger.cpp +++ b/lib/logging/CLogger.cpp @@ -31,7 +31,7 @@ namespace ELogLevel } } #elif defined(VCMI_IOS) -#import "../CIOSUtils.h" +#import "iOS_utils.h" extern "C" { #include } @@ -391,7 +391,7 @@ void CLogConsoleTarget::write(const LogRecord & record) currentLog = logIt->second; else { - currentLog = os_log_create(ios_bundleIdentifier(), domainName.c_str()); + currentLog = os_log_create(iOS_utils::bundleIdentifier(), domainName.c_str()); logs.insert({domainName, currentLog}); } os_log_with_type(currentLog, type, "%{public}s", message.c_str()); From 031ba967d32b0935837856c3a9e324d438dfbf2c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Mon, 15 Aug 2022 16:31:58 +0300 Subject: [PATCH 115/131] fix indentation --- client/CServerHandler.cpp | 38 +++++++++++------------ lib/VCMIDirs.cpp | 50 +++++++++++++++--------------- lib/logging/CLogger.cpp | 64 +++++++++++++++++++-------------------- vcmibuilder | 12 ++++---- 4 files changed, 82 insertions(+), 82 deletions(-) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index d2bc4218a..acdfe95a6 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -185,18 +185,18 @@ void CServerHandler::startLocalServerAndConnect() envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true); } #elif defined(VCMI_IOS) - // todo ios: hide keyboard - logNetwork->info("[ios] create server thread"); - boost::condition_variable cond; - threadRunLocalServer = std::make_shared([&cond, this] { - setThreadName("CVCMIServer"); - CVCMIServer::create(&cond, uuid); - // todo ios copypaste - threadRunLocalServer.reset(); - CSH->campaignServerRestartLock.setn(false); - }); - threadRunLocalServer->detach(); - logNetwork->info("[ios] detach server thread"); + // todo ios: hide keyboard + logNetwork->info("[ios] create server thread"); + boost::condition_variable cond; + threadRunLocalServer = std::make_shared([&cond, this] { + setThreadName("CVCMIServer"); + CVCMIServer::create(&cond, uuid); + // todo ios copypaste + threadRunLocalServer.reset(); + CSH->campaignServerRestartLock.setn(false); + }); + threadRunLocalServer->detach(); + logNetwork->info("[ios] detach server thread"); #else threadRunLocalServer = std::make_shared(&CServerHandler::threadRunServer, this); //runs server executable; #endif @@ -215,13 +215,13 @@ void CServerHandler::startLocalServerAndConnect() androidTestServerReadyFlag = false; #elif defined(VCMI_IOS) // todo ios - { - boost::mutex m; - boost::unique_lock lock{m}; - logNetwork->info("[ios] wait for server"); - cond.wait(lock); - logNetwork->info("[ios] server ready"); - } + { + boost::mutex m; + boost::unique_lock lock{m}; + logNetwork->info("waiting for server"); + cond.wait(lock); + logNetwork->info("server is ready"); + } #else if(shm) shm->sr->waitTillReady(); diff --git a/lib/VCMIDirs.cpp b/lib/VCMIDirs.cpp index 4916ad6ef..86749fb17 100644 --- a/lib/VCMIDirs.cpp +++ b/lib/VCMIDirs.cpp @@ -370,10 +370,10 @@ bfs::path IVCMIDirsUNIX::serverPath() const { return binaryPath() / "vcmiserver" #ifdef VCMI_APPLE class VCMIDirsApple : public IVCMIDirsUNIX { - public: - bfs::path userConfigPath() const override; +public: + bfs::path userConfigPath() const override; - std::string libraryName(const std::string& basename) const override; + std::string libraryName(const std::string& basename) const override; }; bfs::path VCMIDirsApple::userConfigPath() const { return userDataPath() / "config"; } @@ -383,15 +383,15 @@ std::string VCMIDirsApple::libraryName(const std::string& basename) const { retu #ifdef VCMI_IOS class VCMIDirsIOS final : public VCMIDirsApple { - public: - bfs::path userDataPath() const override; - bfs::path userCachePath() const override; - bfs::path userLogsPath() const override; +public: + bfs::path userDataPath() const override; + bfs::path userCachePath() const override; + bfs::path userLogsPath() const override; - std::vector dataPaths() const override; + std::vector dataPaths() const override; - bfs::path libraryPath() const override; - bfs::path binaryPath() const override; + bfs::path libraryPath() const override; + bfs::path binaryPath() const override; }; bfs::path VCMIDirsIOS::userDataPath() const { return {iOS_utils::documentsPath()}; } @@ -400,15 +400,15 @@ bfs::path VCMIDirsIOS::userLogsPath() const { return {iOS_utils::documentsPath() std::vector VCMIDirsIOS::dataPaths() const { - std::vector paths; - paths.reserve(4); + std::vector paths; + paths.reserve(4); #ifdef VCMI_IOS_SIM - paths.emplace_back(iOS_utils::hostApplicationSupportPath()); + paths.emplace_back(iOS_utils::hostApplicationSupportPath()); #endif - paths.emplace_back(userDataPath()); - paths.emplace_back(iOS_utils::documentsPath()); - paths.emplace_back(binaryPath()); - return paths; + paths.emplace_back(userDataPath()); + paths.emplace_back(iOS_utils::documentsPath()); + paths.emplace_back(binaryPath()); + return paths; } bfs::path VCMIDirsIOS::libraryPath() const { return {iOS_utils::frameworksPath()}; } @@ -416,17 +416,17 @@ bfs::path VCMIDirsIOS::binaryPath() const { return {iOS_utils::bundlePath()}; } #elif defined(VCMI_MAC) class VCMIDirsOSX final : public VCMIDirsApple { - public: - boost::filesystem::path userDataPath() const override; - boost::filesystem::path userCachePath() const override; - boost::filesystem::path userLogsPath() const override; +public: + boost::filesystem::path userDataPath() const override; + boost::filesystem::path userCachePath() const override; + boost::filesystem::path userLogsPath() const override; - std::vector dataPaths() const override; + std::vector dataPaths() const override; - boost::filesystem::path libraryPath() const override; - boost::filesystem::path binaryPath() const override; + boost::filesystem::path libraryPath() const override; + boost::filesystem::path binaryPath() const override; - void init() override; + void init() override; }; void VCMIDirsOSX::init() diff --git a/lib/logging/CLogger.cpp b/lib/logging/CLogger.cpp index 4aeca9d76..2fa3a933c 100644 --- a/lib/logging/CLogger.cpp +++ b/lib/logging/CLogger.cpp @@ -361,40 +361,40 @@ void CLogConsoleTarget::write(const LogRecord & record) #ifdef VCMI_ANDROID __android_log_write(ELogLevel::toAndroid(record.level), ("VCMI-" + record.domain.getName()).c_str(), message.c_str()); #elif defined(VCMI_IOS) - os_log_type_t type; - switch (record.level) - { - case ELogLevel::TRACE: - type = OS_LOG_TYPE_DEBUG; - break; - case ELogLevel::DEBUG: - type = OS_LOG_TYPE_DEFAULT; - break; - case ELogLevel::INFO: - type = OS_LOG_TYPE_INFO; - break; - case ELogLevel::WARN: - type = OS_LOG_TYPE_ERROR; - break; - case ELogLevel::ERROR: - type = OS_LOG_TYPE_FAULT; - break; - default: - return; - } + os_log_type_t type; + switch (record.level) + { + case ELogLevel::TRACE: + type = OS_LOG_TYPE_DEBUG; + break; + case ELogLevel::DEBUG: + type = OS_LOG_TYPE_DEFAULT; + break; + case ELogLevel::INFO: + type = OS_LOG_TYPE_INFO; + break; + case ELogLevel::WARN: + type = OS_LOG_TYPE_ERROR; + break; + case ELogLevel::ERROR: + type = OS_LOG_TYPE_FAULT; + break; + default: + return; + } - os_log_t currentLog; - static std::unordered_map logs; - const auto& domainName = record.domain.getName(); - auto logIt = logs.find(domainName); - if (logIt != logs.end()) - currentLog = logIt->second; - else - { + os_log_t currentLog; + static std::unordered_map logs; + const auto& domainName = record.domain.getName(); + auto logIt = logs.find(domainName); + if (logIt != logs.end()) + currentLog = logIt->second; + else + { currentLog = os_log_create(iOS_utils::bundleIdentifier(), domainName.c_str()); - logs.insert({domainName, currentLog}); - } - os_log_with_type(currentLog, type, "%{public}s", message.c_str()); + logs.insert({domainName, currentLog}); + } + os_log_with_type(currentLog, type, "%{public}s", message.c_str()); #else const bool printToStdErr = record.level >= ELogLevel::WARN; diff --git a/vcmibuilder b/vcmibuilder index af4df023a..cdd1b337f 100755 --- a/vcmibuilder +++ b/vcmibuilder @@ -116,10 +116,10 @@ if [[ -n "$gog_file" ]] then currentver="$(innoextract --version | head -n1 | cut -d ' ' -f2)" requiredver="1.6" - if verlt $currentver $requiredver; - then - fail "innoextract version is $currentver, update it to version $requiredver or higher" - fi + if verlt $currentver $requiredver; + then + fail "innoextract version is $currentver, update it to version $requiredver or higher" + fi fi if [[ -n "$useffmpeg" ]] @@ -182,7 +182,7 @@ then # innoextract always reports error (iconv 84 error). Just test file for presence test -f "$gog_file" || fail "Error: gog.com executable was not found!" - gog_file="$(cd "$(dirname "$gog_file")"; pwd)/$(basename "$gog_file")" + gog_file="$(cd "$(dirname "$gog_file")"; pwd)/$(basename "$gog_file")" cd "$data_dir" && innoextract "$gog_file" fi @@ -190,7 +190,7 @@ if [[ -n "$cd1_dir" ]] then data_dir="$temp_dir"/cddir mkdir -p "$data_dir" - unshield -d "$data_dir" x "$cd1_dir"/_setup/data1.cab || fail "Error: failed to extract from Install Shield installer!" "rm -rf $data_dir" + unshield -d "$data_dir" x "$cd1_dir"/_setup/data1.cab || fail "Error: failed to extract from Install Shield installer!" "rm -rf $data_dir" # a bit tricky - different releases have different root directory. Move extracted files to data_dir if [ -d "$data_dir"/Heroes3 ] From 2af7c291632b7d4a201a03e0308eb42019c3384c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 16 Aug 2022 12:25:36 +0300 Subject: [PATCH 116/131] enable Foundation assertions only in Debug build --- CMakeLists.txt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 79779e2f7..b8fddb52e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -159,6 +159,8 @@ set(CMAKE_MAP_IMPORTED_CONFIG_RELEASE Release RelWithDebInfo MinSizeRel "") set(CMAKE_XCODE_ATTRIBUTE_CLANG_ENABLE_OBJC_ARC YES) set(CMAKE_XCODE_ATTRIBUTE_DEBUG_INFORMATION_FORMAT[variant=Debug] dwarf) set(CMAKE_XCODE_ATTRIBUTE_ENABLE_BITCODE NO) +set(CMAKE_XCODE_ATTRIBUTE_ENABLE_NS_ASSERTIONS NO) +set(CMAKE_XCODE_ATTRIBUTE_ENABLE_NS_ASSERTIONS[variant=Debug] YES) set(CMAKE_XCODE_ATTRIBUTE_GCC_WARN_64_TO_32_BIT_CONVERSION NO) set(CMAKE_XCODE_ATTRIBUTE_MARKETING_VERSION ${APP_SHORT_VERSION}) set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH NO) From 3ab21d84916f0746cd3a19c440267decc9e49d76 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 16 Aug 2022 12:54:44 +0300 Subject: [PATCH 117/131] show loading indicator when starting local server single player or hosting a multiplayer game --- client/CMT.cpp | 2 -- client/CMakeLists.txt | 2 ++ client/CPlayerInterface.cpp | 1 - client/CServerHandler.cpp | 16 ++++++++---- client/gui/SDL_Extensions.cpp | 2 +- client/ios/utils.h | 18 ++++++++++++++ client/ios/utils.mm | 46 +++++++++++++++++++++++++++++++++++ ios/CMakeLists.txt | 1 - ios/iOS_utils.h | 2 -- ios/iOS_utils.mm | 3 --- 10 files changed, 78 insertions(+), 15 deletions(-) create mode 100644 client/ios/utils.h create mode 100644 client/ios/utils.mm diff --git a/client/CMT.cpp b/client/CMT.cpp index 3b7a4f696..9a9139085 100644 --- a/client/CMT.cpp +++ b/client/CMT.cpp @@ -441,7 +441,6 @@ int main(int argc, char * argv[]) #ifndef VCMI_NO_THREADED_LOAD - // todo ios #ifdef VCMI_ANDROID // android loads the data quite slowly so we display native progressbar to prevent having only black screen for few seconds { CAndroidVMHelper vmHelper; @@ -1322,7 +1321,6 @@ static void handleEvent(SDL_Event & ev) { if((ev.type==SDL_QUIT) ||(ev.type == SDL_KEYDOWN && ev.key.keysym.sym==SDLK_F4 && (ev.key.keysym.mod & KMOD_ALT))) { - // todo ios #ifdef VCMI_ANDROID handleQuit(false); #else diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt index d88841c3e..1f487d175 100644 --- a/client/CMakeLists.txt +++ b/client/CMakeLists.txt @@ -151,11 +151,13 @@ if(APPLE_IOS) ios/GameChatKeyboardHanlder.m ios/main.m ios/startSDL.mm + ios/utils.mm ) set(client_HEADERS ${client_HEADERS} CFocusableHelper.h ios/GameChatKeyboardHanlder.h ios/startSDL.h + ios/utils.h ) endif() diff --git a/client/CPlayerInterface.cpp b/client/CPlayerInterface.cpp index 481893bb1..62463f048 100644 --- a/client/CPlayerInterface.cpp +++ b/client/CPlayerInterface.cpp @@ -364,7 +364,6 @@ void CPlayerInterface::heroMoved(const TryMoveHero & details, bool verbose) for(int i = 1; i < 32; i += 2 * speed) { movementPxStep(details, i, hp, hero); - // todo ios #ifndef VCMI_ANDROID // currently android doesn't seem to be able to handle all these full redraws here, so let's disable it so at least it looks less choppy; // most likely this is connected with the way that this manual animation+framerate handling is solved diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index acdfe95a6..fe509ada3 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -24,8 +24,10 @@ #ifdef VCMI_ANDROID #include "../lib/CAndroidVMHelper.h" #elif defined(VCMI_IOS) +#include "ios/utils.h" #include "../server/CVCMIServer.h" -// todo ios + +#include #else #include "../lib/Interprocess.h" #endif @@ -185,8 +187,6 @@ void CServerHandler::startLocalServerAndConnect() envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true); } #elif defined(VCMI_IOS) - // todo ios: hide keyboard - logNetwork->info("[ios] create server thread"); boost::condition_variable cond; threadRunLocalServer = std::make_shared([&cond, this] { setThreadName("CVCMIServer"); @@ -196,7 +196,6 @@ void CServerHandler::startLocalServerAndConnect() CSH->campaignServerRestartLock.setn(false); }); threadRunLocalServer->detach(); - logNetwork->info("[ios] detach server thread"); #else threadRunLocalServer = std::make_shared(&CServerHandler::threadRunServer, this); //runs server executable; #endif @@ -214,13 +213,20 @@ void CServerHandler::startLocalServerAndConnect() logNetwork->info("waiting for server finished..."); androidTestServerReadyFlag = false; #elif defined(VCMI_IOS) - // todo ios { + dispatch_sync(dispatch_get_main_queue(), ^{ + iOS_utils::showLoadingIndicator(); + }); + boost::mutex m; boost::unique_lock lock{m}; logNetwork->info("waiting for server"); cond.wait(lock); logNetwork->info("server is ready"); + + dispatch_sync(dispatch_get_main_queue(), ^{ + iOS_utils::hideLoadingIndicator(); + }); } #else if(shm) diff --git a/client/gui/SDL_Extensions.cpp b/client/gui/SDL_Extensions.cpp index e0bf6cad7..410ddb4b8 100644 --- a/client/gui/SDL_Extensions.cpp +++ b/client/gui/SDL_Extensions.cpp @@ -21,7 +21,7 @@ #endif #ifdef VCMI_IOS -#include "iOS_utils.h" +#include "ios/utils.h" #endif const SDL_Color Colors::YELLOW = { 229, 215, 123, 0 }; diff --git a/client/ios/utils.h b/client/ios/utils.h new file mode 100644 index 000000000..f3a643d83 --- /dev/null +++ b/client/ios/utils.h @@ -0,0 +1,18 @@ +/* + * utils.h, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ +#pragma once + +namespace iOS_utils +{ +double screenScale(); + +void showLoadingIndicator(); +void hideLoadingIndicator(); +} diff --git a/client/ios/utils.mm b/client/ios/utils.mm new file mode 100644 index 000000000..41cb65f4f --- /dev/null +++ b/client/ios/utils.mm @@ -0,0 +1,46 @@ +/* + * utils.mm, part of VCMI engine + * + * Authors: listed in file AUTHORS in main folder + * + * License: GNU General Public License v2.0 or later + * Full text of license available in license.txt file, in main folder + * + */ + +#include "utils.h" + +#import + +namespace +{ +UIActivityIndicatorView *indicator; +} + +namespace iOS_utils +{ +double screenScale() +{ + return UIScreen.mainScreen.nativeScale; +} + +void showLoadingIndicator() +{ + NSCAssert(!indicator, @"activity indicator must be hidden before attempting to show it again"); + indicator = [[UIActivityIndicatorView alloc] initWithActivityIndicatorStyle:UIActivityIndicatorViewStyleWhiteLarge]; + [indicator startAnimating]; + + auto mainView = UIApplication.sharedApplication.keyWindow.rootViewController.view; + mainView.userInteractionEnabled = NO; + [mainView addSubview:indicator]; + indicator.center = {CGRectGetMidX(mainView.bounds), CGRectGetMidY(mainView.bounds)}; +} + +void hideLoadingIndicator() +{ + indicator.superview.userInteractionEnabled = YES; + [indicator stopAnimating]; + [indicator removeFromSuperview]; + indicator = nil; +} +} diff --git a/ios/CMakeLists.txt b/ios/CMakeLists.txt index c3d6537c9..0f8359c1c 100644 --- a/ios/CMakeLists.txt +++ b/ios/CMakeLists.txt @@ -4,7 +4,6 @@ add_library(iOS_utils SHARED ) target_link_libraries(iOS_utils PRIVATE "-framework Foundation" - "-framework UIKit" ) target_include_directories(iOS_utils PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/ios/iOS_utils.h b/ios/iOS_utils.h index c56f82f7d..666644789 100644 --- a/ios/iOS_utils.h +++ b/ios/iOS_utils.h @@ -25,7 +25,5 @@ const char *bundlePath(); const char *frameworksPath(); const char *bundleIdentifier(); - -double screenScale(); } #pragma GCC visibility pop diff --git a/ios/iOS_utils.mm b/ios/iOS_utils.mm index 50fe76f3e..40772519c 100644 --- a/ios/iOS_utils.mm +++ b/ios/iOS_utils.mm @@ -11,7 +11,6 @@ #include "iOS_utils.h" #import -#import namespace { @@ -47,6 +46,4 @@ const char *bundlePath() { return NSBundle.mainBundle.bundlePath.fileSystemRepre const char *frameworksPath() { return NSBundle.mainBundle.privateFrameworksPath.fileSystemRepresentation; } const char *bundleIdentifier() { return NSBundle.mainBundle.bundleIdentifier.UTF8String; } - -double screenScale() { return UIScreen.mainScreen.nativeScale; } } From ef2e45a977ca7f17a6b0bbf393139b2fba806a59 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 16 Aug 2022 13:16:27 +0300 Subject: [PATCH 118/131] stop text input on connection start --- client/mainmenu/CMainMenu.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/client/mainmenu/CMainMenu.cpp b/client/mainmenu/CMainMenu.cpp index 85f4a9be4..da9171f7a 100644 --- a/client/mainmenu/CMainMenu.cpp +++ b/client/mainmenu/CMainMenu.cpp @@ -492,6 +492,7 @@ void CSimpleJoinScreen::connectToServer() { textTitle->setText("Connecting..."); buttonOk->block(true); + CSDL_Ext::stopTextInput(); boost::thread(&CSimpleJoinScreen::connectThread, this, inputAddress->text, boost::lexical_cast(inputPort->text)); } From beaa1dd17c4a1d83332ad5f27fba674b27bc7e86 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 16 Aug 2022 16:01:43 +0300 Subject: [PATCH 119/131] add instructions for iOS --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 76a9ea11a..ea125e563 100644 --- a/README.md +++ b/README.md @@ -20,6 +20,7 @@ To use VCMI you need to own original data files. * [Linux](https://wiki.vcmi.eu/Installation_on_Linux) * [macOS](https://wiki.vcmi.eu/Installation_on_macOS) * [Windows](https://wiki.vcmi.eu/Installation_on_Windows) + * [iOS](https://wiki.vcmi.eu/Installation_on_iOS) ## Building from source @@ -29,6 +30,7 @@ Platform support is constantly tested by continuous integration and CMake config * [On Linux for Windows with MXE](https://wiki.vcmi.eu/How_to_build_VCMI_(Linux/Cmake/MXE)) * [On macOS](https://wiki.vcmi.eu/How_to_build_VCMI_(macOS)) * [On Windows using MSVC and Vcpkg](https://wiki.vcmi.eu/How_to_build_VCMI_(Windows/Vcpkg)) + * [iOS on macOS](https://wiki.vcmi.eu/How_to_build_VCMI_(iOS)) ## Copyright and license From 44174da9a26e13bffabcf5e47e362bbcde25e3c2 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Tue, 16 Aug 2022 16:42:27 +0300 Subject: [PATCH 120/131] fix MXE build --- Version.h | 4 +++- launcher/modManager/cmodlist.h | 2 ++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/Version.h b/Version.h index 3d929696c..a1f1b97d5 100644 --- a/Version.h +++ b/Version.h @@ -1,7 +1,9 @@ #pragma once +#include "StdInc.h" + VCMI_LIB_NAMESPACE_BEGIN - + namespace GameConstants { extern const char GIT_SHA1[]; diff --git a/launcher/modManager/cmodlist.h b/launcher/modManager/cmodlist.h index 88e9043bb..0b3cc76b8 100644 --- a/launcher/modManager/cmodlist.h +++ b/launcher/modManager/cmodlist.h @@ -9,6 +9,8 @@ */ #pragma once +#include "StdInc.h" + #include #include #include From a5f9efb3dfd6b57bd497fffa665ca7d55f85b44e Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 17 Aug 2022 15:31:19 +0300 Subject: [PATCH 121/131] workaround GCC < 7.0 bug template specialization from namespace must be enclosed in the namespace https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56480 --- lib/filesystem/ResourceID.h | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/lib/filesystem/ResourceID.h b/lib/filesystem/ResourceID.h index d30fb4288..f53e40e69 100644 --- a/lib/filesystem/ResourceID.h +++ b/lib/filesystem/ResourceID.h @@ -142,7 +142,9 @@ public: VCMI_LIB_NAMESPACE_END -template <> struct std::hash +namespace std +{ +template <> struct hash { size_t operator()(const VCMI_LIB_WRAP_NAMESPACE(ResourceID) & resourceIdent) const { @@ -151,3 +153,4 @@ template <> struct std::hash return stringHasher(resourceIdent.getName()) ^ intHasher(static_cast(resourceIdent.getType())); } }; +} From 011f303397a244c99e8a26295a0d9bf49390e96a Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 17 Aug 2022 14:32:32 +0300 Subject: [PATCH 122/131] code style improvement --- lib/JsonNode.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/JsonNode.cpp b/lib/JsonNode.cpp index 0014ae3a5..06d93d49a 100644 --- a/lib/JsonNode.cpp +++ b/lib/JsonNode.cpp @@ -33,7 +33,7 @@ Node & resolvePointer(Node & in, const std::string & pointer) size_t splitPos = pointer.find('/', 1); - std::string entry = pointer.substr(1, splitPos -1); + std::string entry = pointer.substr(1, splitPos - 1); std::string remainer = splitPos == std::string::npos ? "" : pointer.substr(splitPos); if (in.getType() == VCMI_LIB_WRAP_NAMESPACE(JsonNode)::JsonType::DATA_VECTOR) From 2a50fb487f4b2a7c8da2c9e1985751bb6308730b Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Wed, 17 Aug 2022 16:27:04 +0300 Subject: [PATCH 123/131] [CI] produce full iOS build log --- CMakePresets.json | 1 - 1 file changed, 1 deletion(-) diff --git a/CMakePresets.json b/CMakePresets.json index 14991651c..dc9db320c 100644 --- a/CMakePresets.json +++ b/CMakePresets.json @@ -190,7 +190,6 @@ "configuration": "Release", "targets": ["vcmiclient"], "nativeToolOptions": [ - "-quiet", "CODE_SIGNING_ALLOWED_FOR_APPS=NO" ] } From f56acf8a801cc8a8551a8df4267d1d7832e6eda3 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 15 Sep 2022 21:07:37 +0300 Subject: [PATCH 124/131] fix crash on exiting Custom Campaign fix kambala-decapitator/vcmi#46 --- client/lobby/SelectionTab.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/client/lobby/SelectionTab.cpp b/client/lobby/SelectionTab.cpp index e1d6226c3..6f65dc57c 100644 --- a/client/lobby/SelectionTab.cpp +++ b/client/lobby/SelectionTab.cpp @@ -275,7 +275,7 @@ void SelectionTab::clickLeft(tribool down, bool previousState) } #ifdef VCMI_IOS // focus input field if clicked inside it - else if(inputName->active && inputNameRect.isIn(GH.current->button.x, GH.current->button.y)) + else if(inputName && inputName->active && inputNameRect.isIn(GH.current->button.x, GH.current->button.y)) inputName->giveFocus(); #endif } From 605d5b648172d6c2774f136a38bdc733ee8d2346 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 16 Sep 2022 16:43:21 +0300 Subject: [PATCH 125/131] add dedicated macro when building as single process fix kambala-decapitator/vcmi#40 --- CMakeLists.txt | 4 ++++ client/CServerHandler.cpp | 19 +++++++++++++------ client/CServerHandler.h | 1 + server/CVCMIServer.cpp | 10 +++++----- server/CVCMIServer.h | 2 +- 5 files changed, 24 insertions(+), 12 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index b8fddb52e..6c84e97fb 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -166,6 +166,10 @@ set(CMAKE_XCODE_ATTRIBUTE_MARKETING_VERSION ${APP_SHORT_VERSION}) set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH NO) set(CMAKE_XCODE_ATTRIBUTE_ONLY_ACTIVE_ARCH[variant=Debug] YES) +if(BUILD_SINGLE_APP) + add_compile_definitions(SINGLE_PROCESS_APP=1) +endif() + if(APPLE_IOS) set(CMAKE_MACOSX_RPATH 1) set(CMAKE_OSX_DEPLOYMENT_TARGET 10.0) diff --git a/client/CServerHandler.cpp b/client/CServerHandler.cpp index fe509ada3..88d28067e 100644 --- a/client/CServerHandler.cpp +++ b/client/CServerHandler.cpp @@ -186,14 +186,12 @@ void CServerHandler::startLocalServerAndConnect() CAndroidVMHelper envHelper; envHelper.callStaticVoidMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "startServer", true); } -#elif defined(VCMI_IOS) +#elif defined(SINGLE_PROCESS_APP) boost::condition_variable cond; threadRunLocalServer = std::make_shared([&cond, this] { setThreadName("CVCMIServer"); CVCMIServer::create(&cond, uuid); - // todo ios copypaste - threadRunLocalServer.reset(); - CSH->campaignServerRestartLock.setn(false); + onServerFinished(); }); threadRunLocalServer->detach(); #else @@ -212,11 +210,13 @@ void CServerHandler::startLocalServerAndConnect() } logNetwork->info("waiting for server finished..."); androidTestServerReadyFlag = false; -#elif defined(VCMI_IOS) +#elif defined(SINGLE_PROCESS_APP) { +#ifdef VCMI_IOS dispatch_sync(dispatch_get_main_queue(), ^{ iOS_utils::showLoadingIndicator(); }); +#endif boost::mutex m; boost::unique_lock lock{m}; @@ -224,9 +224,11 @@ void CServerHandler::startLocalServerAndConnect() cond.wait(lock); logNetwork->info("server is ready"); +#ifdef VCMI_IOS dispatch_sync(dispatch_get_main_queue(), ^{ iOS_utils::hideLoadingIndicator(); }); +#endif } #else if(shm) @@ -771,9 +773,14 @@ void CServerHandler::threadRunServer() logNetwork->error("Error: server failed to close correctly or crashed!"); logNetwork->error("Check %s for more info", logName); } + onServerFinished(); +#endif +} + +void CServerHandler::onServerFinished() +{ threadRunLocalServer.reset(); CSH->campaignServerRestartLock.setn(false); -#endif } void CServerHandler::sendLobbyPack(const CPackForLobby & pack) const diff --git a/client/CServerHandler.h b/client/CServerHandler.h index 749e46cb7..3b70d4343 100644 --- a/client/CServerHandler.h +++ b/client/CServerHandler.h @@ -83,6 +83,7 @@ class CServerHandler : public IServerAPI, public LobbyInfo void threadHandleConnection(); void threadRunServer(); + void onServerFinished(); void sendLobbyPack(const CPackForLobby & pack) const override; public: diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index 1598c78f1..d4982ebd4 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -856,7 +856,7 @@ void handleLinuxSignal(int sig) static void handleCommandOptions(int argc, char * argv[], boost::program_options::variables_map & options) { namespace po = boost::program_options; -#ifdef VCMI_IOS +#ifdef SINGLE_PROCESS_APP options.emplace("run-by-client", po::variable_value{true, true}); options.emplace("uuid", po::variable_value{std::string{argv[1]}, true}); #else @@ -885,7 +885,7 @@ static void handleCommandOptions(int argc, char * argv[], boost::program_options po::notify(options); -#ifndef VCMI_IOS +#ifndef SINGLE_PROCESS_APP if(options.count("help")) { auto time = std::time(0); @@ -907,7 +907,7 @@ static void handleCommandOptions(int argc, char * argv[], boost::program_options #endif } -#ifdef VCMI_IOS +#ifdef SINGLE_PROCESS_APP #define main server_main #endif int main(int argc, char * argv[]) @@ -936,7 +936,7 @@ int main(int argc, char * argv[]) loadDLLClasses(); srand((ui32)time(nullptr)); -#ifdef VCMI_IOS +#ifdef SINGLE_PROCESS_APP boost::condition_variable * cond = reinterpret_cast(argv[0]); cond->notify_one(); #endif @@ -986,7 +986,7 @@ void CVCMIServer::create() const char * foo[1] = {"android-server"}; main(1, const_cast(foo)); } -#elif defined(VCMI_IOS) +#elif defined(SINGLE_PROCESS_APP) void CVCMIServer::create(boost::condition_variable * cond, const std::string & uuid) { const std::initializer_list argv = { diff --git a/server/CVCMIServer.h b/server/CVCMIServer.h index 55ad15542..3370a0c66 100644 --- a/server/CVCMIServer.h +++ b/server/CVCMIServer.h @@ -108,7 +108,7 @@ public: #ifdef VCMI_ANDROID static void create(); -#elif defined(VCMI_IOS) +#elif defined(SINGLE_PROCESS_APP) static void create(boost::condition_variable * cond, const std::string & uuid); #endif }; From 7b4412758ce9c05c664b244174b729fcbf0fc76c Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 16 Sep 2022 19:53:45 +0300 Subject: [PATCH 126/131] [CI] download dependencies from VCMI repo --- CI/ios/before_install.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CI/ios/before_install.sh b/CI/ios/before_install.sh index 137b3063f..b19cd9828 100755 --- a/CI/ios/before_install.sh +++ b/CI/ios/before_install.sh @@ -2,6 +2,6 @@ echo DEVELOPER_DIR=/Applications/Xcode_13.4.1.app >> $GITHUB_ENV -curl -L 'https://github.com/kambala-decapitator/vcmi-ios-depends/releases/latest/download/vcmi-ios-depends-xc13.2.1.txz' \ +curl -L 'https://github.com/vcmi/vcmi-ios-deps/releases/latest/download/vcmi-ios-depends-xc13.2.1.txz' \ | tar -xf - build/fix_install_paths.command From d2ded404bbb553bfa1c4f134ef86de84cbed6baa Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 22 Sep 2022 14:07:41 +0300 Subject: [PATCH 127/131] use system background color for the keyboard textfield fix kambala-decapitator/vcmi#45 --- client/ios/startSDL.mm | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/client/ios/startSDL.mm b/client/ios/startSDL.mm index 3dec2f3b6..1a89ac4a7 100644 --- a/client/ios/startSDL.mm +++ b/client/ios/startSDL.mm @@ -44,9 +44,13 @@ auto r = textField.frame; r.size.height = 40; textField.frame = r; - textField.backgroundColor = UIColor.whiteColor; self.gameChatHandler.textFieldSDL = textField; + if(@available(iOS 13.0, *)) + textField.backgroundColor = UIColor.systemBackgroundColor; + else + textField.backgroundColor = UIColor.whiteColor; + auto longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)]; longPress.minimumPressDuration = 0.2; [view addGestureRecognizer:longPress]; From b8eef4ce35b34204b1405a25012f017f4b2ebcf5 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 22 Sep 2022 14:31:57 +0300 Subject: [PATCH 128/131] support building against iOS SDK < 13.0 --- Global.h | 9 +++++++++ client/ios/startSDL.mm | 2 ++ launcher/ios/main.m | 2 ++ 3 files changed, 13 insertions(+) diff --git a/Global.h b/Global.h index 965c24d8f..80776b24f 100644 --- a/Global.h +++ b/Global.h @@ -264,6 +264,15 @@ template char (&_ArrayCountObj(const T (&)[N]))[N]; // should be used for variables that becomes unused in release builds (e.g. only used for assert checks) #define UNUSED(VAR) ((void)VAR) +// old iOS SDKs compatibility +#ifdef VCMI_IOS +#include + +#ifndef __IPHONE_13_0 +#define __IPHONE_13_0 130000 +#endif +#endif // VCMI_IOS + // single-process build makes 2 copies of the main lib by wrapping it in a namespace #ifdef VCMI_LIB_NAMESPACE #define VCMI_LIB_NAMESPACE_BEGIN namespace VCMI_LIB_NAMESPACE { diff --git a/client/ios/startSDL.mm b/client/ios/startSDL.mm index 1a89ac4a7..6cf867478 100644 --- a/client/ios/startSDL.mm +++ b/client/ios/startSDL.mm @@ -46,9 +46,11 @@ textField.frame = r; self.gameChatHandler.textFieldSDL = textField; +#if __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_13_0 if(@available(iOS 13.0, *)) textField.backgroundColor = UIColor.systemBackgroundColor; else +#endif textField.backgroundColor = UIColor.whiteColor; auto longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)]; diff --git a/launcher/ios/main.m b/launcher/ios/main.m index 3db701feb..5f14d4ff1 100644 --- a/launcher/ios/main.m +++ b/launcher/ios/main.m @@ -21,8 +21,10 @@ void launchGame(int argc, char * argv[]) { qtNativeWindow.hidden = YES; [qtNativeWindow.rootViewController.view removeFromSuperview]; qtNativeWindow.rootViewController = nil; +#if __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_13_0 if (@available(iOS 13.0, *)) qtNativeWindow.windowScene = nil; +#endif } [NSNotificationCenter.defaultCenter postNotificationName:@"StartGame" object:nil]; } From 5f0a8419d33682ca845df463233c66866cf0f742 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Thu, 22 Sep 2022 17:16:24 +0300 Subject: [PATCH 129/131] install scripts directory only when scripting modules are enabled --- CMakeLists.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 6c84e97fb..7b56ad53f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -451,8 +451,10 @@ endif() ####################################### install(DIRECTORY config DESTINATION ${DATA_DIR}) -install(DIRECTORY scripts DESTINATION ${DATA_DIR}) install(DIRECTORY Mods DESTINATION ${DATA_DIR}) +if(ENABLE_LUA) + install(DIRECTORY scripts DESTINATION ${DATA_DIR}) +endif() # that script is useless for Windows and iOS if(NOT WIN32 AND NOT APPLE_IOS) From 9f46bf5bff8f2127937e53698efdc3c594e9cbf6 Mon Sep 17 00:00:00 2001 From: Andrey Filipenkov Date: Fri, 23 Sep 2022 19:22:37 +0300 Subject: [PATCH 130/131] Apply suggestions from code review Co-authored-by: Nordsoft91 --- client/lobby/SelectionTab.h | 2 +- lib/CThreadHelper.cpp | 2 +- lib/JsonNode.cpp | 8 ++++---- lib/StartInfo.h | 3 --- server/CVCMIServer.cpp | 2 +- 5 files changed, 7 insertions(+), 10 deletions(-) diff --git a/client/lobby/SelectionTab.h b/client/lobby/SelectionTab.h index ebcdec668..b9eb15599 100644 --- a/client/lobby/SelectionTab.h +++ b/client/lobby/SelectionTab.h @@ -90,7 +90,7 @@ private: std::shared_ptr labelTabTitle; std::shared_ptr labelMapSizes; ESelectionScreen tabType; - Rect inputNameRect; + Rect inputNameRect; void parseMaps(const std::unordered_set & files); void parseSaves(const std::unordered_set & files); diff --git a/lib/CThreadHelper.cpp b/lib/CThreadHelper.cpp index 0394d60d5..94ab6d541 100644 --- a/lib/CThreadHelper.cpp +++ b/lib/CThreadHelper.cpp @@ -87,7 +87,7 @@ void setThreadName(const std::string &name) #elif defined(__linux__) prctl(PR_SET_NAME, name.c_str(), 0, 0, 0); #elif defined(VCMI_APPLE) - pthread_setname_np(name.c_str()); + pthread_setname_np(name.c_str()); #endif } diff --git a/lib/JsonNode.cpp b/lib/JsonNode.cpp index 06d93d49a..bab8a4645 100644 --- a/lib/JsonNode.cpp +++ b/lib/JsonNode.cpp @@ -27,7 +27,7 @@ namespace template Node & resolvePointer(Node & in, const std::string & pointer) { - if (pointer.empty()) + if(pointer.empty()) return in; assert(pointer[0] == '/'); @@ -36,12 +36,12 @@ Node & resolvePointer(Node & in, const std::string & pointer) std::string entry = pointer.substr(1, splitPos - 1); std::string remainer = splitPos == std::string::npos ? "" : pointer.substr(splitPos); - if (in.getType() == VCMI_LIB_WRAP_NAMESPACE(JsonNode)::JsonType::DATA_VECTOR) + if(in.getType() == VCMI_LIB_WRAP_NAMESPACE(JsonNode)::JsonType::DATA_VECTOR) { - if (entry.find_first_not_of("0123456789") != std::string::npos) // non-numbers in string + if(entry.find_first_not_of("0123456789") != std::string::npos) // non-numbers in string throw std::runtime_error("Invalid Json pointer"); - if (entry.size() > 1 && entry[0] == '0') // leading zeros are not allowed + if(entry.size() > 1 && entry[0] == '0') // leading zeros are not allowed throw std::runtime_error("Invalid Json pointer"); size_t index = boost::lexical_cast(entry); diff --git a/lib/StartInfo.h b/lib/StartInfo.h index 35db7ca66..1bda6a40d 100644 --- a/lib/StartInfo.h +++ b/lib/StartInfo.h @@ -177,8 +177,5 @@ struct DLL_LINKAGE LobbyInfo : public LobbyState TeamID getPlayerTeamId(PlayerColor color); }; -class ExceptionMapMissing : public std::exception {}; -class ExceptionNoHuman : public std::exception {}; -class ExceptionNoTemplate : public std::exception {}; VCMI_LIB_NAMESPACE_END diff --git a/server/CVCMIServer.cpp b/server/CVCMIServer.cpp index d4982ebd4..ea7ab5eca 100644 --- a/server/CVCMIServer.cpp +++ b/server/CVCMIServer.cpp @@ -927,7 +927,7 @@ int main(int argc, char * argv[]) logConfig.configureDefault(); logGlobal->info(SERVER_NAME); - boost::program_options::variables_map opts; + boost::program_options::variables_map opts; handleCommandOptions(argc, argv, opts); preinitDLL(console); settings.init(); From 4205701f96a872dface1504e4d7f2e7be81a67f4 Mon Sep 17 00:00:00 2001 From: Andrii Danylchenko Date: Sat, 24 Sep 2022 15:04:11 +0300 Subject: [PATCH 131/131] #973 - use ship battleground for favorable winds --- config/battlefields.json | 4 ---- config/objects/generic.json | 2 +- 2 files changed, 1 insertion(+), 5 deletions(-) diff --git a/config/battlefields.json b/config/battlefields.json index f67281311..78224cc9b 100644 --- a/config/battlefields.json +++ b/config/battlefields.json @@ -124,10 +124,6 @@ } ] }, - "favorable_winds": { - "graphics": "CMBKFW.BMP", - "isSpecial" : true - }, "cursed_ground": { "graphics": "CMBKCUR.BMP", "isSpecial" : true, diff --git a/config/objects/generic.json b/config/objects/generic.json index 5f4bec39b..12ec81e17 100644 --- a/config/objects/generic.json +++ b/config/objects/generic.json @@ -970,7 +970,7 @@ "favorableWinds" : { "index" :225, "handler": "terrain", - "types" : { "object" : { "index" : 0, "battleground": "favorable_winds" } } + "types" : { "object" : { "index" : 0, "battleground": "ship" } } }, "fieryFields": { "index" :226,