From 524240d6025e3fe132df8a642ca2d7329908450e Mon Sep 17 00:00:00 2001 From: Tom Lynch Date: Sat, 14 Mar 2026 11:24:20 +1100 Subject: [PATCH 1/8] base-vr: remove unneeded offset of vr camera position --- .../Templates/base-vr/Sources/__TMP__CameraManager.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Tools/ProjectGenerator/Templates/base-vr/Sources/__TMP__CameraManager.cpp b/Tools/ProjectGenerator/Templates/base-vr/Sources/__TMP__CameraManager.cpp index 847189aee..f4632ba4c 100644 --- a/Tools/ProjectGenerator/Templates/base-vr/Sources/__TMP__CameraManager.cpp +++ b/Tools/ProjectGenerator/Templates/base-vr/Sources/__TMP__CameraManager.cpp @@ -148,7 +148,7 @@ namespace __TMP__ if(_vrCamera) { - _vrCamera->SetWorldPosition(RN::Vector3(0.0f, -1.8f, 0.0f)); + _vrCamera->SetWorldPosition(RN::Vector3(0.0f, 0.0f, 0.0f)); _vrCamera->SetWorldRotation(RN::Quaternion()); } else if(_headCamera) From 7f638125c417f13ac729c6b3f20e32cb05b1b044 Mon Sep 17 00:00:00 2001 From: Tom Lynch Date: Sat, 14 Mar 2026 11:26:22 +1100 Subject: [PATCH 2/8] base-vr: explicitely use python3 in regenerate script for compatability --- .../ProjectGenerator/Templates/base-vr/regenerate-project.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Tools/ProjectGenerator/Templates/base-vr/regenerate-project.sh b/Tools/ProjectGenerator/Templates/base-vr/regenerate-project.sh index 664dd5893..7ed544dcf 100755 --- a/Tools/ProjectGenerator/Templates/base-vr/regenerate-project.sh +++ b/Tools/ProjectGenerator/Templates/base-vr/regenerate-project.sh @@ -1,8 +1,8 @@ if [ -z "$3" ] then rm -rf Builds\$1_%$2 - python ../../Rayne/Tools/BuildHelper/CreateBuildProject.py build-config.json $1 $2 + python3 ../../Rayne/Tools/BuildHelper/CreateBuildProject.py build-config.json $1 $2 else rm -rf Builds\$1_%$2_%$3 - python ../../Rayne/Tools/BuildHelper/CreateBuildProject.py build-config.json $1 $2 $3 + python3 ../../Rayne/Tools/BuildHelper/CreateBuildProject.py build-config.json $1 $2 $3 fi From b35f1fae4a5bf6e18fe4b02b48c1369d610577af Mon Sep 17 00:00:00 2001 From: Tom Lynch Date: Sat, 14 Mar 2026 11:28:14 +1100 Subject: [PATCH 3/8] base-vr: fix issues breaking compiling use stdc++20 instead of 14 enable UI to fix FlexUI not compiling --- Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt b/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt index a044c95ff..97da46376 100644 --- a/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt +++ b/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt @@ -20,7 +20,7 @@ option(RN_BUILD_SAMPLES "Enable building the sample projects" OFF) option(RN_BUILD_RECAST_MODULE "Build the Recast pathfinding module" OFF) option(RN_BUILD_OGG_MODULE "Build the ogg audio file module" OFF) option(RN_BUILD_OPENAL_MODULE "Build the OpenAL module" OFF) -option(RN_BUILD_UI_MODULE "Build the UI module" OFF) +option(RN_BUILD_UI_MODULE "Build the UI module" ON) option(RN_BUILD_OPENXR_MODULE "Build the OpenXR module" ON) option(RN_BUILD_APPLEXR_MODULE "Build the AppleXR module" ON) option(RN_BUILD_VRSTUB_MODULE "Build the VRStub module" ON) @@ -82,7 +82,7 @@ if(IOS OR VISIONOS) set(SOURCES_SWIFT Sources/main-apple.swift) endif() -set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++14") +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++20") if(ANDROID) add_library(__TMP_APPLICATION_TARGET__ SHARED "${SOURCES}" "${HEADERS}") From 0db8c938a49a9728aad7c923cdcceeceff2413bd Mon Sep 17 00:00:00 2001 From: Tom Lynch Date: Sat, 14 Mar 2026 11:29:38 +1100 Subject: [PATCH 4/8] base-vr: update xcode signing identity and remove hardcoded id --- Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt b/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt index 97da46376..7ad7b0f43 100644 --- a/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt +++ b/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt @@ -151,8 +151,8 @@ if(APPLE) set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES MACOSX_BUNDLE_INFO_PLIST ${CMAKE_CURRENT_SOURCE_DIR}/Other/Info.plist.in) set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES MACOSX_BUNDLE_GUI_IDENTIFIER __TMP_BUNDLE_ID__) - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY "iPhone Developer") - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES XCODE_ATTRIBUTE_DEVELOPMENT_TEAM "LDF4CM9KT3") + set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY "Apple Development") + set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES XCODE_ATTRIBUTE_DEVELOPMENT_TEAM "YOUR_TEAM_HERE") endif() if(MSVC) From 90391728541658dedc6a99301065350a74319b2d Mon Sep 17 00:00:00 2001 From: Tom Lynch Date: Sat, 14 Mar 2026 11:31:03 +1100 Subject: [PATCH 5/8] Templates: refactor CreateProject script --- Tools/ProjectGenerator/CreateProject.py | 78 +++++++++++++++---------- 1 file changed, 46 insertions(+), 32 deletions(-) diff --git a/Tools/ProjectGenerator/CreateProject.py b/Tools/ProjectGenerator/CreateProject.py index c3abdb08d..ff563cf69 100755 --- a/Tools/ProjectGenerator/CreateProject.py +++ b/Tools/ProjectGenerator/CreateProject.py @@ -3,47 +3,61 @@ import datetime def main(): - templateName = input("Template name? ") - projectNameString = input("Project name? ") - projectName = projectNameString.encode() - projectTarget = projectNameString.replace(" ", "").encode() - prefixString = input("Project prefix? ") - prefix = prefixString.encode() - companyName = input("Company name? ").encode() - bundleID = input("Bundle ID? ").encode() - year = str(datetime.datetime.now().year).encode() - - fromdir = os.path.join(os.path.dirname(sys.argv[0]), "Templates") - fromdir = os.path.join(fromdir, templateName) - - for root, subdirs, files in os.walk(fromdir): - relativeRoot = os.path.relpath(root, fromdir) + template = input("Template name? ") + # project info + project_name = input("Project name? ") + project_prefix = input("Project prefix? ") + company_name = input("Company name? ") + bundle_id = input("Bundle ID? ") + + project_target = bundle_id.split(".")[-1] + bundle_domain = ".".join(bundle_id.split(".")[:-1]) + year = str(datetime.datetime.now().year) + + # template source + from_dir = os.path.join(os.path.dirname(sys.argv[0]), "Templates") + from_dir = os.path.join(from_dir, template) + + # traverse template + for root, subdirs, files in os.walk(from_dir): + relative_root = os.path.relpath(root, from_dir) + + # copy dirs for subdir in subdirs: - os.makedirs(os.path.join(relativeRoot, subdir)) + os.makedirs(os.path.join(relative_root, subdir)) + # copy files for filename in files: if filename == ".DS_Store": continue - readFilePath = os.path.join(root, filename) + + read_file_path = os.path.join(root, filename) if filename == "gitattributes": filename = ".gitattributes" - filename = filename.replace("__TMP__", prefixString) - filename = filename.replace("__TMP_APPLICATION_TARGET__", projectTarget.decode("utf-8")) - writeFilePath = os.path.join(relativeRoot, filename) - - with open(readFilePath, 'rb') as readFile: - fileContent = readFile.read() - fileContent = fileContent.replace("__TMP__".encode(), prefix) - fileContent = fileContent.replace("__TMP_BUNDLE_ID__".encode(), bundleID) - fileContent = fileContent.replace("__TMP_APPLICATION_NAME__".encode(), projectName) - fileContent = fileContent.replace("__TMP_APPLICATION_TARGET__".encode(), projectTarget) - fileContent = fileContent.replace("__TMP_COMPANY__".encode(), companyName) - fileContent = fileContent.replace("__TMP_YEAR__".encode(), year) - - with open(writeFilePath, 'wb') as writeFile: - writeFile.write(fileContent) + + # replace filename variables + filename = filename.replace("__TMP__", project_prefix) + filename = filename.replace("__TMP_APPLICATION_TARGET__", project_target) + + write_file_path = os.path.join(relative_root, filename) + + # copy content + with open(read_file_path, 'rb') as read_file: + file_content = read_file.read() + + # replace content variables + file_content = file_content.replace(b"__TMP__", project_prefix.encode()) + file_content = file_content.replace(b"__TMP_BUNDLE_ID__", bundle_id.encode()) + file_content = file_content.replace(b"__TMP_BUNDLE_DOMAIN__", bundle_domain.encode()) + file_content = file_content.replace(b"__TMP_APPLICATION_NAME__", project_name.encode()) + file_content = file_content.replace(b"__TMP_APPLICATION_TARGET__", project_target.encode()) + file_content = file_content.replace(b"__TMP_COMPANY__", company_name.encode()) + file_content = file_content.replace(b"__TMP_YEAR__", year.encode()) + + with open(write_file_path, 'wb') as write_file: + write_file.write(file_content) if __name__ == '__main__': main() From 36f268c51fb4252c5c6a27a50d88e7e911e2a746 Mon Sep 17 00:00:00 2001 From: Tom Lynch Date: Sat, 14 Mar 2026 11:31:34 +1100 Subject: [PATCH 6/8] base-vr: remove hardcoded bundle domain and add to CreateProject script --- Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt b/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt index 7ad7b0f43..a77b21cc2 100644 --- a/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt +++ b/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt @@ -89,7 +89,7 @@ if(ANDROID) elseif(IOS OR VISIONOS) add_library(__TMP_APPLICATION_TARGET__Lib STATIC "${SOURCES}" "${HEADERS}") set_target_properties(__TMP_APPLICATION_TARGET__Lib PROPERTIES FRAMEWORK TRUE) - set_target_properties(__TMP_APPLICATION_TARGET__Lib PROPERTIES MACOSX_FRAMEWORK_IDENTIFIER com.slindev.__TMP_APPLICATION_TARGET__Lib) + set_target_properties(__TMP_APPLICATION_TARGET__Lib PROPERTIES MACOSX_FRAMEWORK_IDENTIFIER __TMP_BUNDLE_DOMAIN__.__TMP_APPLICATION_TARGET__Lib) set_property(TARGET __TMP_APPLICATION_TARGET__Lib PROPERTY PUBLIC_HEADER ${HEADERS}) set_target_properties(__TMP_APPLICATION_TARGET__Lib PROPERTIES XCODE_ATTRIBUTE_DEFINES_MODULE YES) target_compile_options(__TMP_APPLICATION_TARGET__Lib PRIVATE -xobjective-c++) From c487f52f3549398c75145684d36d6f0a420a068d Mon Sep 17 00:00:00 2001 From: Tom Lynch Date: Sat, 14 Mar 2026 11:38:30 +1100 Subject: [PATCH 7/8] base-vr: modernise gitignore --- .../Templates/base-vr/.gitignore | 27 ++++++++++++++++--- 1 file changed, 24 insertions(+), 3 deletions(-) diff --git a/Tools/ProjectGenerator/Templates/base-vr/.gitignore b/Tools/ProjectGenerator/Templates/base-vr/.gitignore index 510d17781..c97362b4f 100644 --- a/Tools/ProjectGenerator/Templates/base-vr/.gitignore +++ b/Tools/ProjectGenerator/Templates/base-vr/.gitignore @@ -1,5 +1,26 @@ +# editor configs +/.vscode +/.idea +/.zed +/.nvim.lua + +# OS specific .DS_Store +*:Zone.Identifier + +# clang cache +/.cache + +# lsp config +/build +/buildServer.json + +# blender backups *.blend1 -Other/build-secrets.json -Builds -Releases + +# build output +/Builds +/Releases + +# secrets +/Other/build-secrets.json From 9ba1c2c508461d84dad0b613ce7c5c803f215027 Mon Sep 17 00:00:00 2001 From: Tom Lynch Date: Sat, 14 Mar 2026 12:08:29 +1100 Subject: [PATCH 8/8] base-vr: clean up cmakelists making use of cmake variables --- .../Templates/base-vr/CMakeLists.txt | 83 ++++++++++--------- 1 file changed, 45 insertions(+), 38 deletions(-) diff --git a/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt b/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt index a77b21cc2..92a41fa8e 100644 --- a/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt +++ b/Tools/ProjectGenerator/Templates/base-vr/CMakeLists.txt @@ -2,6 +2,9 @@ cmake_minimum_required(VERSION 3.21) include(ExternalProject) project(__TMP_APPLICATION_TARGET__) +set(LIBRARY_NAME ${PROJECT_NAME}Lib) +set(BUNDLE_DOMAIN __TMP_BUNDLE_DOMAIN__) +set(BUNDLE_ID __TMP_BUNDLE_ID__) include(${CMAKE_CURRENT_SOURCE_DIR}/../../Rayne/CMake/Rayne.cmake) set(CMAKE_XCODE_GENERATE_TOP_LEVEL_PROJECT_ONLY ON) @@ -85,76 +88,80 @@ endif() set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++20") if(ANDROID) - add_library(__TMP_APPLICATION_TARGET__ SHARED "${SOURCES}" "${HEADERS}") + add_library(${PROJECT_NAME} SHARED "${SOURCES}" "${HEADERS}") elseif(IOS OR VISIONOS) - add_library(__TMP_APPLICATION_TARGET__Lib STATIC "${SOURCES}" "${HEADERS}") - set_target_properties(__TMP_APPLICATION_TARGET__Lib PROPERTIES FRAMEWORK TRUE) - set_target_properties(__TMP_APPLICATION_TARGET__Lib PROPERTIES MACOSX_FRAMEWORK_IDENTIFIER __TMP_BUNDLE_DOMAIN__.__TMP_APPLICATION_TARGET__Lib) - set_property(TARGET __TMP_APPLICATION_TARGET__Lib PROPERTY PUBLIC_HEADER ${HEADERS}) - set_target_properties(__TMP_APPLICATION_TARGET__Lib PROPERTIES XCODE_ATTRIBUTE_DEFINES_MODULE YES) - target_compile_options(__TMP_APPLICATION_TARGET__Lib PRIVATE -xobjective-c++) - - add_executable(__TMP_APPLICATION_TARGET__ "${SOURCES_SWIFT}") - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES XCODE_ATTRIBUTE_SWIFT_OBJC_INTEROP_MODE objcxx) - target_link_libraries(__TMP_APPLICATION_TARGET__ PUBLIC __TMP_APPLICATION_TARGET__Lib) + add_library(${LIBRARY_NAME} STATIC "${SOURCES}" "${HEADERS}") + set_property(TARGET ${LIBRARY_NAME} PROPERTY PUBLIC_HEADER ${HEADERS}) + target_compile_options(${LIBRARY_NAME} PRIVATE -xobjective-c++) + set_target_properties(${LIBRARY_NAME} PROPERTIES + FRAMEWORK TRUE + MACOSX_FRAMEWORK_IDENTIFIER ${BUNDLE_DOMAIN}.${LIBRARY_NAME} + XCODE_ATTRIBUTE_DEFINES_MODULE YES + ) + + add_executable(${PROJECT_NAME} "${SOURCES_SWIFT}") + set_target_properties(${PROJECT_NAME} PROPERTIES XCODE_ATTRIBUTE_SWIFT_OBJC_INTEROP_MODE objcxx) + target_link_libraries(${PROJECT_NAME} PUBLIC ${LIBRARY_NAME}) else() - add_executable(__TMP_APPLICATION_TARGET__ "${SOURCES}" "${HEADERS}") + add_executable(${PROJECT_NAME} "${SOURCES}" "${HEADERS}") endif() -target_include_directories(__TMP_APPLICATION_TARGET__ PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/Sources) +target_include_directories(${PROJECT_NAME} PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/Sources) set(ADDITIONAL_RESOURCE_COPY_PARAMS "--resourcespec=${CMAKE_CURRENT_SOURCE_DIR}/resources.json") -rayne_copy_resources(__TMP_APPLICATION_TARGET__ "${RESOURCES}" "${ADDITIONAL_RESOURCE_COPY_PARAMS}") +rayne_copy_resources(${PROJECT_NAME} "${RESOURCES}" "${ADDITIONAL_RESOURCE_COPY_PARAMS}") -rayne_link_with(__TMP_APPLICATION_TARGET__) -rayne_use_modules(__TMP_APPLICATION_TARGET__ RayneJolt) -rayne_use_modules(__TMP_APPLICATION_TARGET__ RayneVR) +rayne_link_with(${PROJECT_NAME}) +rayne_use_modules(${PROJECT_NAME} RayneJolt) +rayne_use_modules(${PROJECT_NAME} RayneVR) if(NOT APPLE) - rayne_use_modules(__TMP_APPLICATION_TARGET__ RayneOpenXR) + rayne_use_modules(${PROJECT_NAME} RayneOpenXR) endif() if(VISIONOS) - rayne_use_modules(__TMP_APPLICATION_TARGET__ RayneAppleXR) + rayne_use_modules(${PROJECT_NAME} RayneAppleXR) endif() if(NOT APPLE AND ${RN_BUILD_VULKAN_MODULE}) - rayne_use_modules(__TMP_APPLICATION_TARGET__ RayneVulkan) + rayne_use_modules(${PROJECT_NAME} RayneVulkan) endif() if(APPLE AND ${RN_BUILD_METAL_MODULE}) - rayne_use_modules(__TMP_APPLICATION_TARGET__ RayneMetal) + rayne_use_modules(${PROJECT_NAME} RayneMetal) endif() if(${RN_BUILD_CONFIGURATION} STREQUAL "oculus") - set(__TMP___COMPILE_DEFINITIONS ${__TMP___COMPILE_DEFINITIONS} -DBUILD_FOR_OCULUS) + target_compile_definitions(${PROJECT_NAME} PRIVATE -DBUILD_FOR_OCULUS) elseif(${RN_BUILD_CONFIGURATION} STREQUAL "steam") - set(__TMP___COMPILE_DEFINITIONS ${__TMP___COMPILE_DEFINITIONS} -DBUILD_FOR_STEAM) + target_compile_definitions(${PROJECT_NAME} PRIVATE -DBUILD_FOR_STEAM) elseif(${RN_BUILD_CONFIGURATION} STREQUAL "pico") - set(__TMP___COMPILE_DEFINITIONS ${__TMP___COMPILE_DEFINITIONS} -DBUILD_FOR_PICO) + target_compile_definitions(${PROJECT_NAME} PRIVATE -DBUILD_FOR_PICO) elseif(WIN32) - add_custom_command(TARGET __TMP_APPLICATION_TARGET__ POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/Other/RunPancake-windows.bat $/RunPancake-windows.bat) - add_custom_command(TARGET GRAB POST_BUILD - COMMAND ${CMAKE_COMMAND} -E copy -t $ $ - COMMAND_EXPAND_LISTS) + add_custom_command(TARGET ${PROJECT_NAME} POST_BUILD + COMMAND ${CMAKE_COMMAND} -E copy ${CMAKE_CURRENT_SOURCE_DIR}/Other/RunPancake-windows.bat $/RunPancake-windows.bat) + add_custom_command(TARGET ${PROJECT_NAME} POST_BUILD + COMMAND ${CMAKE_COMMAND} -E copy -t $ $ + COMMAND_EXPAND_LISTS) endif() -target_compile_definitions(__TMP_APPLICATION_TARGET__ PRIVATE ${__TMP___COMPILE_DEFINITIONS}) - if(APPLE) if(IOS OR VISIONOS) - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES MACOSX_BUNDLE_SHORT_VERSION_STRING 0.0.1) - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES MACOSX_BUNDLE_BUNDLE_VERSION 1) + set_target_properties(${PROJECT_NAME} PROPERTIES + MACOSX_BUNDLE_SHORT_VERSION_STRING 0.0.1 + MACOSX_BUNDLE_BUNDLE_VERSION 1 + ) endif() - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES MACOSX_BUNDLE TRUE) - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES MACOSX_BUNDLE_INFO_PLIST ${CMAKE_CURRENT_SOURCE_DIR}/Other/Info.plist.in) - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES MACOSX_BUNDLE_GUI_IDENTIFIER __TMP_BUNDLE_ID__) + set_target_properties(${PROJECT_NAME} PROPERTIES MACOSX_BUNDLE TRUE + MACOSX_BUNDLE_INFO_PLIST ${CMAKE_CURRENT_SOURCE_DIR}/Other/Info.plist.in + MACOSX_BUNDLE_GUI_IDENTIFIER ${BUNDLE_ID} - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY "Apple Development") - set_target_properties(__TMP_APPLICATION_TARGET__ PROPERTIES XCODE_ATTRIBUTE_DEVELOPMENT_TEAM "YOUR_TEAM_HERE") + XCODE_ATTRIBUTE_CODE_SIGN_IDENTITY "Apple Development" + XCODE_ATTRIBUTE_DEVELOPMENT_TEAM "YOUR_TEAM_HERE" + ) endif() if(MSVC) - set_property(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} PROPERTY VS_STARTUP_PROJECT __TMP_APPLICATION_TARGET__) + set_property(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} PROPERTY VS_STARTUP_PROJECT ${PROJECT_NAME}) endif()