-
Notifications
You must be signed in to change notification settings - Fork 32
/
CMakeLists.txt
218 lines (176 loc) · 7.67 KB
/
CMakeLists.txt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
cmake_minimum_required(VERSION 3.15)
project(kengine)
cmake_policy(VERSION 3.15) # options shouldn't clear variables
set(CMAKE_CXX_STANDARD 20)
add_library(kengine_include INTERFACE)
target_include_directories(kengine_include INTERFACE .)
if(MSVC)
target_compile_options(kengine_include INTERFACE /bigobj)
endif()
add_library(kengine INTERFACE)
target_link_libraries(kengine INTERFACE kengine_include)
# Include this here so sub-libraries can use helpers
add_subdirectory(putils/reflection/meta/cmake_helpers kengine_cmake_helpers)
if (NOT CMAKE_RUNTIME_OUTPUT_DIRECTORY)
# These must be set before processing sub-libraries, as vcpkg DLLs need to be copied next to executables
putils_set_output_directories(bin lib lib)
endif()
find_package(EnTT CONFIG REQUIRED)
target_link_libraries(kengine_include INTERFACE EnTT::EnTT)
option(KENGINE_GENERATE_REFLECTION "Generate reflection headers for kengine data types")
option(KENGINE_ALL_LIBRARIES "Build all libraries")
option(KENGINE_TESTS "Build tests")
if(KENGINE_TESTS)
enable_testing()
endif()
set(
default_dependencies
kengine_core
kengine_core_assert
kengine_core_log
kengine_core_profiling
)
function(add_kengine_library path)
file(RELATIVE_PATH relative_path ${CMAKE_CURRENT_LIST_DIR} ${path})
# Convert kengine/render/kreogl to kengine_render_kreogl
string(REPLACE "/" "_" kengine_library_name ${relative_path})
# Convert kengine_render_kreogl to KENGINE_RENDER_KREOGL
string(TOUPPER ${kengine_library_name} kengine_library_upper_name)
# If the plugin isn't one of the default dependencies, add an option to enable it
list(FIND default_dependencies ${kengine_library_name} default_dependencies_index)
if(${default_dependencies_index} EQUAL -1)
set(default_enabled ${KENGINE_ALL_LIBRARIES})
else()
set(default_enabled ON)
endif()
option(${kengine_library_upper_name} "Build ${kengine_library_name}" ${default_enabled})
if(NOT ${${kengine_library_upper_name}})
return()
endif()
file(GLOB sources
${path}/data/*.cpp
${path}/functions/*.cpp
${path}/helpers/*.cpp
${path}/systems/*.cpp)
list(LENGTH sources sources_length)
if(sources_length GREATER 0)
set(link_type PUBLIC)
add_library(${kengine_library_name} ${sources})
putils_export_symbols(${kengine_library_name})
else()
set(link_type INTERFACE)
add_library(${kengine_library_name} INTERFACE)
endif()
if(KENGINE_TESTS)
file(GLOB test_sources
${path}/helpers/tests/*.tests.cpp
${path}/systems/tests/*.tests.cpp)
list(LENGTH test_sources test_sources_length)
if(test_sources_length GREATER 0)
set(kengine_library_tests_name ${kengine_library_name}_tests)
putils_add_test_executable(${kengine_library_tests_name} ${test_sources})
target_link_libraries(${kengine_library_tests_name} PRIVATE ${kengine_library_name})
endif()
endif()
# Expose link type so that the system's CMakeLists can use it
set(link_type ${link_type} PARENT_SCOPE)
target_link_libraries(kengine INTERFACE ${kengine_library_name})
target_compile_definitions(${kengine_library_name} ${link_type} ${kengine_library_upper_name})
target_link_libraries(${kengine_library_name} ${link_type} kengine_include)
# Link against the default dependencies
if(${default_dependencies_index} EQUAL -1)
target_link_libraries(${kengine_library_name} ${link_type} ${default_dependencies})
endif()
if(NOT "${parent_system_name}" STREQUAL "")
target_link_libraries(${kengine_library_name} ${link_type} ${parent_system_name})
endif()
# Headers for which we'll generate reflection headers and/or type registration code
file(GLOB system_headers
${path}/data/*.hpp
${path}/functions/*.hpp
${path}/systems/*.hpp)
if(EXISTS ${path}/CMakeLists.txt)
# Helpers for the system CMakeLists
macro(subdirectory_is_not_kengine_library path)
set(ignored_subdirectories ${ignored_subdirectories} ${CMAKE_CURRENT_LIST_DIR}/${path} PARENT_SCOPE)
endmacro()
function(kengine_library_link_public_libraries)
target_link_libraries(${kengine_library_name} ${link_type} ${ARGN})
endfunction()
function(kengine_library_link_private_libraries)
target_link_libraries(${kengine_library_name} PRIVATE ${ARGN})
endfunction()
macro(register_types_from_headers)
foreach(header ${ARGN})
set(system_headers ${system_headers} ${path}/${header} PARENT_SCOPE)
endforeach()
endmacro()
add_subdirectory(${path})
endif()
# Generate reflection headers
list(LENGTH system_headers headers_length)
if(headers_length GREATER 0)
get_target_property(cxx_standard ${kengine_library_name} CXX_STANDARD)
if(${cxx_standard} STREQUAL cxx_standard-NOTFOUND)
set_target_properties(${kengine_library_name} PROPERTIES CXX_STANDARD ${CMAKE_CXX_STANDARD})
endif()
include(putils/reflection/scripts/generate_reflection_headers.cmake)
if(KENGINE_GENERATE_REFLECTION)
putils_generate_reflection_headers(
TARGET ${kengine_library_name}
SOURCES ${system_headers}
)
endif()
endif()
set(parent_system_name ${kengine_library_name})
add_systems_in_directory(${path})
# Add our headers to the ones we'll want to generate type registration for
set(headers_to_register ${headers_to_register} ${system_headers} PARENT_SCOPE)
endfunction()
function(add_systems_in_directory root)
file(GLOB children ${root}/*)
foreach(child ${children})
if(NOT IS_DIRECTORY ${child})
continue()
endif()
list(FIND ignored_subdirectories ${child} ignored_index)
if(NOT ${ignored_index} EQUAL -1)
continue()
endif()
add_kengine_library(${child})
endforeach()
set(headers_to_register ${headers_to_register} PARENT_SCOPE)
endfunction()
# Add core first so other systems can link against it
add_kengine_library(${CMAKE_CURRENT_LIST_DIR}/kengine/core)
set(ignored_subdirectories ${CMAKE_CURRENT_LIST_DIR}/kengine/core)
# Then add the other systems
add_systems_in_directory(${CMAKE_CURRENT_LIST_DIR}/kengine)
# putils
add_subdirectory(putils)
target_link_libraries(kengine_include INTERFACE putils)
option(KENGINE_NDEBUG "Disable debug")
if (KENGINE_NDEBUG)
target_compile_definitions(kengine_include INTERFACE KENGINE_NDEBUG)
endif()
option(KENGINE_TYPE_REGISTRATION "Generate kengine type registration")
if (KENGINE_TYPE_REGISTRATION)
include(scripts/generate_type_registration.cmake)
list(LENGTH headers_to_register headers_to_register_length)
if(headers_to_register_length GREATER 0)
get_target_property(cxx_standard kengine CXX_STANDARD)
if(${cxx_standard} STREQUAL cxx_standard-NOTFOUND)
set_target_properties(kengine PROPERTIES CXX_STANDARD ${CMAKE_CXX_STANDARD})
endif()
kengine_generate_type_registration(
TARGET kengine
INCLUDE_DIR kengine/type_registration
SOURCES ${headers_to_register}
REGISTRATIONS_JSON ${CMAKE_CURRENT_LIST_DIR}/scripts/registrations.json
NAMESPACE kengine::types
)
target_compile_definitions(kengine_type_registration PUBLIC KENGINE_TYPE_REGISTRATION)
target_link_libraries(kengine_type_registration PUBLIC kengine)
target_link_libraries(kengine INTERFACE kengine_type_registration)
endif()
endif()