Fix cmake source file generation

pull/400/head
Matteo De Carlo 2020-02-02 20:47:45 +01:00 committed by Roberto Benfatto
parent 55c0a2ea03
commit 0c8dd096c4
2 changed files with 91 additions and 24 deletions

View File

@ -141,23 +141,45 @@ else()
endif() endif()
message(STATUS "Generating Bindings") message(STATUS "Generating Bindings")
execute_process(COMMAND "${PYTHON_EXECUTABLE}" "-c" "import binding_generator; binding_generator.generate_bindings(\"${GODOT_CUSTOM_API_FILE}\", ${GENERATE_BINDING_PARAMETERS})" execute_process(COMMAND "${PYTHON_EXECUTABLE}" "-c" "import binding_generator; binding_generator.print_file_list(\"${GODOT_CUSTOM_API_FILE}\", \"${CMAKE_CURRENT_BINARY_DIR}\", headers=True)"
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
RESULT_VARIABLE GENERATION_RESULT RESULT_VARIABLE HEADERS_FILE_LIST_RESULT
OUTPUT_VARIABLE GENERATION_OUTPUT) OUTPUT_VARIABLE HEADERS_FILE_LIST
message(STATUS ${GENERATION_RESULT} ${GENERATION_OUTPUT}) )
set(HEADERS_FILE_LIST ${HEADERS_FILE_LIST})
execute_process(COMMAND "${PYTHON_EXECUTABLE}" "-c" "import binding_generator; binding_generator.print_file_list(\"${GODOT_CUSTOM_API_FILE}\", \"${CMAKE_CURRENT_BINARY_DIR}\", sources=True)"
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
RESULT_VARIABLE SOURCES_FILE_LIST_RESULT
OUTPUT_VARIABLE SOURCES_FILE_LIST
)
set(SOURCES_FILE_LIST ${SOURCES_FILE_LIST})
add_custom_command(OUTPUT ${HEADERS_FILE_LIST} ${SOURCES_FILE_LIST}
COMMAND "${PYTHON_EXECUTABLE}" "-c" "import binding_generator; binding_generator.generate_bindings(\"${GODOT_CUSTOM_API_FILE}\", \"${GENERATE_BINDING_PARAMETERS}\", \"${CMAKE_CURRENT_BINARY_DIR}\")"
VERBATIM
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
MAIN_DEPENDENCY ${GODOT_CUSTOM_API_FILE}
DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/binding_generator.py
COMMENT Generating Bindings
)
# Get Sources # Get Sources
file(GLOB_RECURSE SOURCES src/*.c**) file(GLOB_RECURSE SOURCES src/*.c**)
file(GLOB_RECURSE HEADERS include/*.h**) file(GLOB_RECURSE HEADERS include/*.h**)
# Define our godot-cpp library # Define our godot-cpp library
add_library(${PROJECT_NAME} ${SOURCES} ${HEADERS}) add_library(${PROJECT_NAME}
${SOURCES}
${SOURCES_FILE_LIST}
${HEADERS}
${HEADERS_FILE_LIST}
)
target_include_directories(${PROJECT_NAME} target_include_directories(${PROJECT_NAME}
PUBLIC PUBLIC
include include
include/core include/core
include/gen ${CMAKE_CURRENT_BINARY_DIR}/include/gen/
) )
# Put godot headers as SYSTEM PUBLIC to exclude warnings from irrelevant headers # Put godot headers as SYSTEM PUBLIC to exclude warnings from irrelevant headers

View File

@ -1,8 +1,8 @@
#!/usr/bin/env python #!/usr/bin/env python
from __future__ import print_function
import json import json
import os
# comment. import errno
# Convenience function for using template get_node # Convenience function for using template get_node
def correct_method_name(method_list): def correct_method_name(method_list):
@ -13,15 +13,56 @@ def correct_method_name(method_list):
classes = [] classes = []
def generate_bindings(path, use_template_get_node):
def print_file_list(api_filepath, output_dir, headers=False, sources=False):
global classes global classes
classes = json.load(open(path)) end = ';'
with open(api_filepath) as api_file:
classes = json.load(api_file)
include_gen_folder = os.path.join(output_dir, 'include', 'gen')
source_gen_folder = os.path.join(output_dir, 'src', 'gen')
for _class in classes:
header_filename = os.path.join(include_gen_folder, strip_name(_class["name"]) + ".hpp")
source_filename = os.path.join(source_gen_folder, strip_name(_class["name"]) + ".cpp")
if headers:
print(header_filename, end=end)
if sources:
print(source_filename, end=end)
icall_header_filename = os.path.join(include_gen_folder, '__icalls.hpp')
register_types_filename = os.path.join(source_gen_folder, '__register_types.cpp')
init_method_bindings_filename = os.path.join(source_gen_folder, '__init_method_bindings.cpp')
if headers:
print(icall_header_filename, end=end)
if sources:
print(register_types_filename, end=end)
print(init_method_bindings_filename, end=end)
def generate_bindings(api_filepath, use_template_get_node, output_dir="."):
global classes
with open(api_filepath) as api_file:
classes = json.load(api_file)
icalls = set() icalls = set()
include_gen_folder = os.path.join(output_dir, 'include', 'gen')
source_gen_folder = os.path.join(output_dir, 'src', 'gen')
try:
os.makedirs(include_gen_folder)
except os.error as e:
if e.errno == errno.EEXIST:
print(include_gen_folder + ": " + os.strerror(e.errno))
else:
exit(1)
try:
os.makedirs(source_gen_folder)
except os.error as e:
if e.errno == errno.EEXIST:
print(source_gen_folder + ": " + os.strerror(e.errno))
else:
exit(1)
for c in classes: for c in classes:
# print c['name'] # print(c['name'])
used_classes = get_used_classes(c) used_classes = get_used_classes(c)
if use_template_get_node and c["name"] == "Node": if use_template_get_node and c["name"] == "Node":
correct_method_name(c["methods"]) correct_method_name(c["methods"])
@ -30,21 +71,25 @@ def generate_bindings(path, use_template_get_node):
impl = generate_class_implementation(icalls, used_classes, c, use_template_get_node) impl = generate_class_implementation(icalls, used_classes, c, use_template_get_node)
header_file = open("include/gen/" + strip_name(c["name"]) + ".hpp", "w+") header_filename = os.path.join(include_gen_folder, strip_name(c["name"]) + ".hpp")
header_file.write(header) with open(header_filename, "w+") as header_file:
header_file.write(header)
source_file = open("src/gen/" + strip_name(c["name"]) + ".cpp", "w+") source_filename = os.path.join(source_gen_folder, strip_name(c["name"]) + ".cpp")
source_file.write(impl) with open(source_filename, "w+") as source_file:
source_file.write(impl)
icall_header_filename = os.path.join(include_gen_folder, '__icalls.hpp')
with open(icall_header_filename, "w+") as icall_header_file:
icall_header_file.write(generate_icall_header(icalls))
icall_header_file = open("include/gen/__icalls.hpp", "w+") register_types_filename = os.path.join(source_gen_folder, '__register_types.cpp')
icall_header_file.write(generate_icall_header(icalls)) with open(register_types_filename, "w+") as register_types_file:
register_types_file.write(generate_type_registry(classes))
register_types_file = open("src/gen/__register_types.cpp", "w+") init_method_bindings_filename = os.path.join(source_gen_folder, '__init_method_bindings.cpp')
register_types_file.write(generate_type_registry(classes)) with open(init_method_bindings_filename, "w+") as init_method_bindings_file:
init_method_bindings_file.write(generate_init_method_bindings(classes))
init_method_bindings_file = open("src/gen/__init_method_bindings.cpp", "w+")
init_method_bindings_file.write(generate_init_method_bindings(classes))
def is_reference_type(t): def is_reference_type(t):
@ -80,7 +125,7 @@ def generate_class_header(used_classes, c, use_template_get_node):
source.append("") source.append("")
source.append("#include <gdnative_api_struct.gen.h>") source.append("#include <gdnative_api_struct.gen.h>")
source.append("#include <stdint.h>") source.append("#include <cstdint>")
source.append("") source.append("")