cmake_minimum_required(VERSION 3.25)

set(ARCHEUS_STD_VERSION 0.0.0)
project(archeus_std LANGUAGES C VERSION ${ARCHEUS_STD_VERSION} DESCRIPTION "libarcheus_std standard archeus c library")

set(CMAKE_EXPORT_COMPILE_COMMANDS ON)

include(GNUInstallDirs)

function(print var)
    message("${var} = ${${var}}")
endfunction()

#TODO: Might want to remove this
if(NOT CMAKE_BUILD_TYPE)
    message("[Archeus C STD] Build Type not set, defaulting to Debug")
    set(CMAKE_BUILD_TYPE "Debug" CACHE STRING "Default to Debug" FORCE)
endif()

add_compile_options(
  "-Wall" "-Werror" "-fexceptions"
  "$<$<CONFIG:DEBUG>:-O0;-g3;-ggdb;-DARC_DEBUG;>"
  "$<$<CONFIG:RELEASE>:-02;-g;>"
)

# ~ OPTIONS ~ #
option(ARCHEUS_STD_DEFAULT_CONFIG "Build with default config keys" ON)
option(ARCHEUS_STD_TESTS "Build with tests" OFF)

set(ARCHEUS_STD_CONSOLE_BACKEND "NONE" CACHE STRING "Console Backend to build with")
set_property(CACHE ARCHEUS_STD_CONSOLE_BACKEND PROPERTY STRINGS NONE NCURSES)

set(ARCHEUS_STD_WINDOW_BACKEND "NONE" CACHE STRING "Window Backend to build with")
set_property(CACHE ARCHEUS_STD_WINDOW_BACKEND PROPERTY STRINGS NONE SDL2 GLFW)

set(ARCHEUS_STD_INPUT_BACKEND "NONE" CACHE STRING "Input Backend to build with, most likely should match Window Backend")
set_property(CACHE ARCHEUS_STD_INPUT_BACKEND PROPERTY STRINGS NONE SDL2 GLFW)

set(ARCHEUS_STD_GRAPHICS_BACKEND "NONE" CACHE STRING "Graphics Backend to build with")
set_property(CACHE ARCHEUS_STD_GRAPHICS_BACKEND PROPERTY STRINGS NONE SDL2 OPENGL)

set(ARCHEUS_STD_SSH_BACKEND "NONE" CACHE STRING "SSH Backend to build with")
set_property(CACHE ARCHEUS_STD_GRAPHICS_BACKEND PROPERTY STRINGS NONE LIBSSH)


# ~ INIT VARIABLES ~ #
set(ARCHEUS_STD_FLAGS "")
set(ARCHEUS_STD_LIBRARIES "")

set(ARCHEUS_STD_INCLUDE_DIRECTORIES
    PUBLIC $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include>
)

set(ARCHEUS_STD_LINK_LIBRARIES
    PUBLIC m
)

# ~ ARCHEUS_SOURCES ~ #
set(ARCHEUS_STD_SOURCES
    src/std/chemical.c
    src/std/errno.c
    src/std/handler.c
    src/std/hashtable.c
    src/std/io.c
    src/std/lexer.c
    src/std/parser.c
    src/std/parser/csv.c
    src/std/parser/helpers.c
    src/std/parser/parserlang.c
    src/std/queue.c
    src/std/stack.c
    src/std/string.c
    src/std/time.c
    src/std/vector.c

    src/math/circle.c
    src/math/obround.c
    src/math/point.c
    src/math/rectangle.c
    src/math/vector2.c

    src/engine/engine.c
    src/engine/state.c
)

if(CMAKE_BUILD_TYPE STREQUAL "Debug")
    string(APPEND ARCHEUS_STD_FLAGS "-Wall -Werror -g -ggdb -DARC_DEBUG ")
endif()

# TODO: replace this with a better system
if(ARCHEUS_STD_DEFAULT_CONFIG)
    string(APPEND ARCHEUS_STD_FLAGS "-DARC_DEFAULT_CONFIG ")
endif()

# ~ NONE ~ #
include(${CMAKE_CURRENT_SOURCE_DIR}/cmake/archeus_none.cmake)
none_check_and_init_needed(ARCHEUS_STD_FLAGS ARCHEUS_STD_SOURCES ${ARCHEUS_STD_WINDOW_BACKEND} ${ARCHEUS_STD_INPUT_BACKEND} ${ARCHEUS_STD_GRAPHICS_BACKEND})

# ~ NCURSES ~ #
include(${CMAKE_CURRENT_SOURCE_DIR}/cmake/archeus_ncurses.cmake)
ncurses_check_and_init_needed(ARCHEUS_STD_FLAGS ARCHEUS_STD_SOURCES ${ARCHEUS_STD_CONSOLE_BACKEND})

# ~ SDL2 ~ #
include(${CMAKE_CURRENT_SOURCE_DIR}/cmake/archeus_sdl2.cmake)
sdl2_check_and_init_needed(ARCHEUS_STD_SOURCES ARCHEUS_STD_INCLUDE_DIRECTORIES ARCHEUS_STD_LINK_LIBRARIES ${ARCHEUS_STD_WINDOW_BACKEND} ${ARCHEUS_STD_INPUT_BACKEND} ${ARCHEUS_STD_GRAPHICS_BACKEND})

# ~ OPENGL ~ #
include(${CMAKE_CURRENT_SOURCE_DIR}/cmake/archeus_opengl.cmake)
opengl_check_and_init_needed(ARCHEUS_STD_FLAGS ARCHEUS_STD_SOURCES ${ARCHEUS_STD_GRAPHICS_BACKEND})

# ~ GLFW ~ #
include(${CMAKE_CURRENT_SOURCE_DIR}/cmake/archeus_glfw.cmake)
glfw_check_and_init_needed(ARCHEUS_STD_FLAGS ARCHEUS_STD_SOURCES ${ARCHEUS_STD_WINDOW_BACKEND} ${ARCHEUS_STD_INPUT_BACKEND})

# ~ LIBSSH ~ #
include(${CMAKE_CURRENT_SOURCE_DIR}/cmake/archeus_libssh.cmake)
libssh_check_and_init_needed(ARCHEUS_STD_FLAGS ARCHEUS_STD_SOURCES ${ARCHEUS_STD_SSH_BACKEND})

#if(ARCHEUS_STD_GLEW)
#    string(APPEND ARCHEUS_STD_FLAGS "-DARC_GLEW ")
#endif()

set(CMAKE_C_FLAGS ${ARCHEUS_STD_FLAGS})

if(ARCHEUS_STD_TESTS)
    add_executable(tests
        tests/test.c

        tests/std/chemical.c
        #tests/std/vector.c
        #tests/std/lexer.c
        #tests/std/parser.c
        tests/std/parser/csv.c
        tests/std/parser/parserlang.c

        ${ARCHEUS_STD_SOURCES}
    )

    target_compile_options(tests PUBLIC "-DARC_DEBUG_LOG_STREAM_OVERRIDE")
    target_include_directories(tests ${ARCHEUS_STD_INCLUDE_DIRECTORIES})
    target_link_libraries(tests ${ARCHEUS_STD_LINK_LIBRARIES})
endif()

if(WIN32 AND NOT MSVC)
    add_library(archeus_std STATIC ${ARCHEUS_STD_SOURCES})
else()
    add_library(archeus_std SHARED ${ARCHEUS_STD_SOURCES})
endif()

target_include_directories(archeus_std ${ARCHEUS_STD_INCLUDE_DIRECTORIES})

target_link_libraries(archeus_std ${ARCHEUS_STD_LINK_LIBRARIES})

install(TARGETS archeus_std EXPORT archeus_std_Exports
    LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
    ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
    RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
)

install(EXPORT archeus_std_Exports
    DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/archeus_std-${PROJECT_VERSION}
)

install(DIRECTORY ${CMAKE_CURRENT_LIST_DIR}/include/
    DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
    FILES_MATCHING
    PATTERN *.h
)

include(CMakePackageConfigHelpers)
set(INCLUDE_INSTALL_DIR ${CMAKE_INSTALL_INCLUDEDIR})
set(LIBRARY_INSTALL_BIN ${CMAKE_INSTALL_LIBDIR})

configure_package_config_file(
    "${PROJECT_SOURCE_DIR}/cmake/archeus_std-config.cmake.in"
    "${PROJECT_BINARY_DIR}/archeus_std-config.cmake"

    INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/archeus_std-${PROJECT_VERSION}
    PATH_VARS INCLUDE_INSTALL_DIR LIBRARY_INSTALL_BIN
)

write_basic_package_version_file(
    "archeus_std-ConfigVersion.cmake"
    VERSION {PROJECT_VERSION}
    COMPATIBILITY SameMajorVersion
)

install(FILES
    ${CMAKE_CURRENT_BINARY_DIR}/archeus_std-config.cmake
    ${CMAKE_CURRENT_BINARY_DIR}/archeus_std-ConfigVersion.cmake
DESTINATION
    ${CMAKE_INSTALL_LIBDIR}/cmake/archeus_std-${PROJECT_VERSION}
)
