cmake_minimum_required (VERSION 3.20)

project ("kwa.fr")

set(CMAKE_C_STANDARD 23)
set(CMAKE_C_STANDARD_REQUIRED ON)
set(CMAKE_C_EXTENSIONS OFF)                 # Ensure only standard features are enabled (forces ISO C23, not GNU23)

set(CMAKE_CXX_STANDARD 23)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS OFF)               # Ensure only standard features are enabled (forces ISO C++23, not GNU++23)

if(MSVC)
  string(APPEND CMAKE_C_FLAGS " /W3 /GR")
  string(APPEND CMAKE_CXX_FLAGS " /W3 /GR")

  string(APPEND CMAKE_C_FLAGS_DEBUG " /MDd /RTC1")
  string(APPEND CMAKE_CXX_FLAGS_DEBUG " /MDd /RTC1")

  string(APPEND CMAKE_C_FLAGS_RELEASE " /MD")
  string(APPEND CMAKE_CXX_FLAGS_RELEASE " /MD")
endif()

# Set default build type to Release if not specified
if(NOT CMAKE_BUILD_TYPE)
  set(CMAKE_BUILD_TYPE "Release" CACHE STRING "Build type (Debug or Release)" FORCE)
endif()

# Global library environment variable
if(DEFINED ENV{DEV_LIB})
  set(DEV_LIB $ENV{DEV_LIB})
else()
  message(FATAL_ERROR "DEV_LIB environment variable must be defined")
endif()

# Project Headers
set(PROJECT_INCLUDES
  "src"
  #"src/misc/SQLite3"
)

# Third-Party Headers (SYSTEM)
list(APPEND SYSTEM_INCLUDES
  "src"
  "sdi_toolBox_1.0.x/toolBox"
  "${DEV_LIB}/wxWidgets-3.2.7/include/msvc"
  "${DEV_LIB}/wxWidgets-3.2.7/include"
  "${DEV_LIB}/boost_1_87_0"
  "${DEV_LIB}/openssl-3.5.0/include"
)


# Libraries directories
#$(OutDir);  
link_directories("${DEV_LIB}/wxWidgets-3.2.7/lib/vc_x64_lib") 
link_directories("${DEV_LIB}/boost_1_87_0/stage/lib")
link_directories("${DEV_LIB}/openssl-3.5.0/lib")

# Preprocessor definitions
if(CMAKE_BUILD_TYPE STREQUAL "Debug")
  list(APPEND PREPROCESSOR_DEFINITIONS
    "_CRT_SECURE_NO_DEPRECATE"
    "_CRT_NONSTDC_NO_DEPRECATE"
    "_DEBUG"
    "_UNICODE"
    "_WINDOWS"
    "DEBUG"
    "NOMINMAX"
    "UNICODE"
    "WIN32"
    "WIN32_LEAN_AND_MEAN"
    "WXDEBUG"
  )
elseif(CMAKE_BUILD_TYPE STREQUAL "Release")
  list(APPEND PREPROCESSOR_DEFINITIONS
    "_CRT_SECURE_NO_DEPRECATE"
    "_CRT_NONSTDC_NO_DEPRECATE"
    "_UNICODE"
    "_WINDOWS"
    "NDEBUG"
    "NOMINMAX"
    "UNICODE"
    "WIN32"
    "WIN32_LEAN_AND_MEAN"
  )
else()
  message(FATAL_ERROR "Invalid build type")
endif()

# External libraries
if(CMAKE_BUILD_TYPE STREQUAL "Debug")
  set(EXTERNAL_LIB
    "libssl.lib"
    "libcrypto.lib"
  )
  list(APPEND EXTERNAL_BIN
#    "${CMAKE_SOURCE_DIR}/dependencies/Debug/thromboSoft_lib.dll"
  )
elseif(CMAKE_BUILD_TYPE STREQUAL "Release")
  set(EXTERNAL_LIB
    "libssl.lib"
    "libcrypto.lib"
  )
  list(APPEND EXTERNAL_BIN
#    "${CMAKE_SOURCE_DIR}/dependencies/Release/thromboSoft_lib.dll"
  )
else()
  message(FATAL_ERROR "Invalid build type")
endif()

list(APPEND EXTERNAL_BIN
  "${DEV_LIB}/openssl-3.5.0/bin/libcrypto-3-x64.dll"
  "${DEV_LIB}/openssl-3.5.0/bin/libssl-3-x64.dll"
)

# External resources
set(RESOURCE_FILES "src/kwaFr.rc")

# Activez Rechargement à chaud pour les compilateurs MSVC si cela est pris en charge.
if (POLICY CMP0141)
  cmake_policy(SET CMP0141 NEW)
  set(CMAKE_MSVC_DEBUG_INFORMATION_FORMAT "$<IF:$<AND:$<C_COMPILER_ID:MSVC>,$<CXX_COMPILER_ID:MSVC>>,$<$<CONFIG:Debug,RelWithDebInfo>:EditAndContinue>,$<$<CONFIG:Debug,RelWithDebInfo>:ProgramDatabase>>")
endif()

#------------------------------
#--- Project files
#---------------
file(GLOB_RECURSE SOURCES_C "src/*.c")
file(GLOB_RECURSE SOURCES_CPP "src/*.cpp")

if(NOT DEFINED TESTS_MODE)
  add_executable (${PROJECT_NAME} WIN32 ${SOURCES_C} ${SOURCES_CPP} ${RESOURCE_FILES})
elseif(TESTS_MODE STREQUAL "True")
  add_executable (${PROJECT_NAME} ${SOURCES_C} ${SOURCES_CPP} ${RESOURCE_FILES})
else()
  message(FATAL_ERROR "Invalid build type")
endif()

target_compile_definitions(${PROJECT_NAME}        PRIVATE ${PREPROCESSOR_DEFINITIONS})
target_link_libraries(${PROJECT_NAME}             PRIVATE ${EXTERNAL_LIB})
target_link_options(${PROJECT_NAME}               PRIVATE "/ignore:4099")
target_include_directories(${PROJECT_NAME}        PRIVATE ${PROJECT_INCLUDES})
target_include_directories(${PROJECT_NAME} SYSTEM PRIVATE ${SYSTEM_INCLUDES})

# Copy required DLL
foreach(DLL ${EXTERNAL_BIN})
  add_custom_command(TARGET ${PROJECT_NAME} POST_BUILD 
                     COMMAND ${CMAKE_COMMAND} -E copy_if_different
                     "${DLL}"
                     "${CMAKE_BINARY_DIR}"
  )
endforeach()

if(MSVC)
  target_compile_options(${PROJECT_NAME} PRIVATE /MP)
  target_link_options(${PROJECT_NAME} PRIVATE /PROFILE)
endif()





#----------------------------------------------
#--- Compiler specific information ------------
#----------------------------------------------
message(STATUS "--------------------------------------------------------")
message(STATUS "┏(-_-)┛┗(-_-)┓┗(-_-)┛┏(-_-)┓┏(-_-)┓┗(-_-)┛┏(-_-)┛┗(-_-)┓")
message(STATUS "--------------------------------------------------------")
message(STATUS "--- Platform Information -------------------------------")
message(STATUS "System Name:     ${CMAKE_SYSTEM_NAME}")
message(STATUS "Processor:       ${CMAKE_SYSTEM_PROCESSOR}")
message(STATUS "CMake Version:   ${CMAKE_VERSION}")
message(STATUS "CMake Generator: ${CMAKE_GENERATOR}")
#message(STATUS "Install Prefix:  ${CMAKE_INSTALL_PREFIX}")
message(STATUS "--------------------------------------------------------")
message(STATUS "--- Compiler/Language Settings -------------------------")
message(STATUS "Build Type:                 ${CMAKE_BUILD_TYPE}")
message(STATUS "C Standard:                 ${CMAKE_C_STANDARD}")
message(STATUS "C Compiler ID:              ${CMAKE_C_COMPILER_ID}")
message(STATUS "C Common Compiler Flags:    ${CMAKE_C_FLAGS}")
message(STATUS "C Debug Compiler Flags:     ${CMAKE_C_FLAGS_DEBUG}")
message(STATUS "C Release Compiler Flags:   ${CMAKE_C_FLAGS_RELEASE}")
message(STATUS "C++ Standard:               ${CMAKE_CXX_STANDARD}")
message(STATUS "C++ Compiler ID:            ${CMAKE_CXX_COMPILER_ID}")
message(STATUS "C++ Common Compiler Flags:  ${CMAKE_CXX_FLAGS}")
message(STATUS "C++ Debug Compiler Flags:   ${CMAKE_CXX_FLAGS_DEBUG}")
message(STATUS "C++ Release Compiler Flags: ${CMAKE_CXX_FLAGS_RELEASE}")
message(STATUS "Common Linker Flags:        ${CMAKE_EXE_LINKER_FLAGS}")
message(STATUS "Debug Linker Flags:         ${CMAKE_EXE_LINKER_FLAGS_DEBUG}")
message(STATUS "Release Linker Flags:       ${CMAKE_EXE_LINKER_FLAGS_RELEASE}")
message(STATUS "--------------------------------------------------------")
message(STATUS "--- Path Information -----------------------------------")
message(STATUS "Source Dir: ${CMAKE_CURRENT_SOURCE_DIR}")
message(STATUS "Binary Dir: ${CMAKE_CURRENT_BINARY_DIR}")
if(MSVC)
  message(STATUS "--------------------------------------------------------")
  message(STATUS "--- Microsoft Visual C++ (MSVC) Information ------------")
  # Check the major compiler version
  if(MSVC_VERSION GREATER_EQUAL 1950)
    message(STATUS "MSVC Compiler Version: ${MSVC_VERSION} (Visual Studio 2026 or newer)")
  elseif(MSVC_VERSION GREATER_EQUAL 1930)
    message(STATUS "MSVC Compiler Version: ${MSVC_VERSION} (Visual Studio 2022)")
  endif()
message(STATUS "MSVC Toolset Version:  ${MSVC_TOOLSET_VERSION}")
message(STATUS "CPP Compiler Version:  ${CMAKE_CXX_COMPILER_VERSION}")
message(STATUS "C Compiler Version:    ${CMAKE_C_COMPILER_VERSION}")
endif()
message(STATUS "--------------------------------------------------------")
message(STATUS "--- Project Information --------------------------------")
message(STATUS "Project Name: ${PROJECT_NAME}")
message(STATUS "Preset Name:  ${PRESET_NAME}")
message(STATUS "--------------------------------------------------------")
message(STATUS "┏(-_-)┛┗(-_-)┓┗(-_-)┛┏(-_-)┓┏(-_-)┓┗(-_-)┛┏(-_-)┛┗(-_-)┓")
message(STATUS "--------------------------------------------------------")

