Added generation of CLion projects.
This commit is contained in:
parent
0a29b41639
commit
c6bba0e440
120
SConscript
120
SConscript
@ -1,5 +1,6 @@
|
||||
|
||||
import copy
|
||||
import enum
|
||||
import glob
|
||||
import inspect
|
||||
import json
|
||||
@ -9,6 +10,10 @@ import sys
|
||||
import time
|
||||
|
||||
|
||||
class TargetType(enum.Enum):
|
||||
PROGRAM = 0
|
||||
LIBRARY = 1
|
||||
|
||||
class _VersionSpec:
|
||||
minimum_version = None
|
||||
maximum_version = None
|
||||
@ -31,6 +36,8 @@ class _Dependency:
|
||||
cook_result: dict = {}
|
||||
|
||||
class _Target:
|
||||
name: str
|
||||
target_type: TargetType
|
||||
builder = None
|
||||
args: list = []
|
||||
kwargs: dict = {}
|
||||
@ -192,7 +199,7 @@ def _find_lib(env: Environment, name: str, paths: 'list[str]', type : str = 'sta
|
||||
|
||||
def _error(env: Environment, message: str):
|
||||
print(message, file=sys.stderr)
|
||||
env.Exit(1)
|
||||
Exit(1)
|
||||
|
||||
def _try_merge_dicts(dictA: dict, dictB: dict) -> 'dict|None':
|
||||
result = {}
|
||||
@ -316,7 +323,7 @@ def _find_version(env: Environment, dependency: _Dependency):
|
||||
print(f'Required version: {dependency.version_spec}')
|
||||
raise Exception(f'Could not find a suitable version for dependency {dependency.name}.')
|
||||
|
||||
def _wrap_builder(builder, is_lib: bool = False):
|
||||
def _wrap_builder(builder, target_type: TargetType):
|
||||
def _wrapped(env, dependencies = {}, *args, **kwargs):
|
||||
target_dependencies = []
|
||||
for name, version_spec in dependencies.items():
|
||||
@ -343,6 +350,15 @@ def _wrap_builder(builder, is_lib: bool = False):
|
||||
kwargs['source'] = new_source
|
||||
|
||||
target = _Target()
|
||||
if 'name' in kwargs:
|
||||
target.name = kwargs['name']
|
||||
else:
|
||||
trgt = _target_entry(kwargs.get('target'))
|
||||
if trgt is not None:
|
||||
target.name = str(_target_entry(kwargs['target']).name)
|
||||
else:
|
||||
target.name = 'Unknown target'
|
||||
target.target_type = target_type
|
||||
target.builder = builder
|
||||
target.args = args
|
||||
target.kwargs = kwargs
|
||||
@ -396,6 +412,10 @@ def _version_to_string(version) -> str:
|
||||
return '.'.join([str(v) for v in version])
|
||||
|
||||
def _finalize(env: Environment):
|
||||
if generate_project:
|
||||
_generate_project(generate_project)
|
||||
Exit(0)
|
||||
|
||||
version_requirements = {dep.name: {
|
||||
'min': dep.version_spec.minimum_version and _version_to_string(dep.version_spec.minimum_version),
|
||||
'max': dep.version_spec.maximum_version and _version_to_string(dep.version_spec.maximum_version),
|
||||
@ -441,6 +461,73 @@ def _find_system_cache_dir() -> str:
|
||||
# fallback
|
||||
return _get_fallback_cache_dir()
|
||||
|
||||
def _target_entry(target_value):
|
||||
if target_value is None:
|
||||
return None
|
||||
if not isinstance(target_value, list):
|
||||
target_value = [target_value]
|
||||
if len(target_value) < 1:
|
||||
return None
|
||||
if isinstance(target_value[0], str):
|
||||
target_value[0] = env.Entry(target_value[0])
|
||||
return target_value[0]
|
||||
|
||||
def _generate_project(project_type: str) -> None:
|
||||
source_folder, target_folder = {
|
||||
'clion': (os.path.join(_spp_dir.abspath, 'util', 'clion_project_template'), Dir('#.idea').abspath)
|
||||
}.get(project_type, (None, None))
|
||||
if not source_folder:
|
||||
_error(None, 'Invalid project type option.')
|
||||
|
||||
import uuid
|
||||
def _generate_uuid() -> str:
|
||||
return str(uuid.uuid4())
|
||||
|
||||
import pathlib
|
||||
import shutil
|
||||
import multiprocessing
|
||||
|
||||
root_path = pathlib.Path(env.Dir('#').abspath)
|
||||
def _get_executables() -> list:
|
||||
result = []
|
||||
for target in env['SPP_TARGETS']:
|
||||
if target.target_type == TargetType.PROGRAM:
|
||||
trgt = _target_entry(target.kwargs['target'])
|
||||
exe_path = pathlib.Path(trgt.abspath).relative_to(root_path)
|
||||
result.append({
|
||||
'name': target.name,
|
||||
'filename': str(exe_path)
|
||||
})
|
||||
return result
|
||||
|
||||
import jinja2
|
||||
jinja_env = jinja2.Environment()
|
||||
jinja_env.globals['generate_uuid'] = _generate_uuid
|
||||
jinja_env.globals['project'] = {
|
||||
'name': config['PROJECT_NAME'],
|
||||
'executables': _get_executables(),
|
||||
'build_types': ['debug', 'release_debug', 'release', 'profile']
|
||||
}
|
||||
jinja_env.globals['scons_exe'] = env['ENV']['_']
|
||||
jinja_env.globals['nproc'] = multiprocessing.cpu_count()
|
||||
|
||||
source_path = pathlib.Path(source_folder)
|
||||
target_path = pathlib.Path(target_folder)
|
||||
|
||||
for source_file in source_path.rglob('*'):
|
||||
if source_file.is_file():
|
||||
target_file = target_path / (source_file.relative_to(source_path))
|
||||
target_file.parent.mkdir(parents=True, exist_ok=True)
|
||||
if source_file.suffix != '.jinja':
|
||||
shutil.copyfile(source_file, target_file)
|
||||
continue
|
||||
with source_file.open('r') as f:
|
||||
templ = jinja_env.from_string(f.read())
|
||||
target_file = target_file.with_suffix('')
|
||||
with target_file.open('w') as f:
|
||||
f.write(templ.render())
|
||||
|
||||
|
||||
Import('config')
|
||||
|
||||
if not config.get('PROJECT_NAME'):
|
||||
@ -520,6 +607,17 @@ AddOption(
|
||||
action = 'store_true'
|
||||
)
|
||||
|
||||
AddOption(
|
||||
'--generate_project',
|
||||
dest = 'generate_project',
|
||||
type = 'choice',
|
||||
choices = ('clion',),
|
||||
nargs = 1,
|
||||
action = 'store'
|
||||
)
|
||||
|
||||
_spp_dir = Dir('.')
|
||||
|
||||
build_type = GetOption('build_type')
|
||||
unity_mode = GetOption('unity_mode')
|
||||
variant = GetOption('variant')
|
||||
@ -528,6 +626,7 @@ config_file = GetOption('config_file')
|
||||
compiler = GetOption('compiler')
|
||||
update_repositories = GetOption('update_repositories')
|
||||
dump_env = GetOption('dump_env')
|
||||
generate_project = GetOption('generate_project')
|
||||
|
||||
default_CC = {
|
||||
'gcc': 'gcc',
|
||||
@ -756,17 +855,17 @@ env.AddMethod(_make_interface, 'MakeInterface')
|
||||
env.AddMethod(_lib_filename, 'LibFilename')
|
||||
env.AddMethod(_find_lib, 'FindLib')
|
||||
env.AddMethod(_error, 'Error')
|
||||
env.AddMethod(_wrap_builder(env.Library, is_lib = True), 'Library')
|
||||
env.AddMethod(_wrap_builder(env.StaticLibrary, is_lib = True), 'StaticLibrary')
|
||||
env.AddMethod(_wrap_builder(env.SharedLibrary, is_lib = True), 'SharedLibrary')
|
||||
env.AddMethod(_wrap_builder(env.Program), 'Program')
|
||||
env.AddMethod(_wrap_builder(env.Library, TargetType.LIBRARY), 'Library')
|
||||
env.AddMethod(_wrap_builder(env.StaticLibrary, TargetType.LIBRARY), 'StaticLibrary')
|
||||
env.AddMethod(_wrap_builder(env.SharedLibrary, TargetType.LIBRARY), 'SharedLibrary')
|
||||
env.AddMethod(_wrap_builder(env.Program, TargetType.PROGRAM), 'Program')
|
||||
env.AddMethod(_wrap_default(env.Default), 'Default')
|
||||
env.AddMethod(_wrap_depends(env.Depends), 'Depends')
|
||||
|
||||
env.AddMethod(_wrap_builder(env.UnityProgram), 'UnityProgram')
|
||||
env.AddMethod(_wrap_builder(env.UnityLibrary, is_lib = True), 'UnityLibrary')
|
||||
env.AddMethod(_wrap_builder(env.UnityStaticLibrary, is_lib = True), 'UnityStaticLibrary')
|
||||
env.AddMethod(_wrap_builder(env.UnitySharedLibrary, is_lib = True), 'UnitySharedLibrary')
|
||||
env.AddMethod(_wrap_builder(env.UnityProgram, TargetType.PROGRAM), 'UnityProgram')
|
||||
env.AddMethod(_wrap_builder(env.UnityLibrary, TargetType.LIBRARY), 'UnityLibrary')
|
||||
env.AddMethod(_wrap_builder(env.UnityStaticLibrary, TargetType.LIBRARY), 'UnityStaticLibrary')
|
||||
env.AddMethod(_wrap_builder(env.UnitySharedLibrary, TargetType.LIBRARY), 'UnitySharedLibrary')
|
||||
env.AddMethod(_module, 'Module')
|
||||
env.AddMethod(_finalize, 'Finalize')
|
||||
|
||||
@ -780,5 +879,6 @@ if dump_env:
|
||||
print('==== Begin Environment Dump =====')
|
||||
print(env.Dump())
|
||||
print('==== End Environment Dump =====')
|
||||
Exit(0)
|
||||
|
||||
Return('env')
|
||||
|
@ -1,2 +1,3 @@
|
||||
GitPython
|
||||
psutil
|
||||
Jinja2
|
||||
|
8
util/clion_project_template/.gitignore
vendored
Normal file
8
util/clion_project_template/.gitignore
vendored
Normal file
@ -0,0 +1,8 @@
|
||||
# Default ignored files
|
||||
/shelf/
|
||||
/workspace.xml
|
||||
# Editor-based HTTP Client requests
|
||||
/httpRequests/
|
||||
# Datasource local storage ignored files
|
||||
/dataSources/
|
||||
/dataSources.local.xml
|
20
util/clion_project_template/customTargets.xml.jinja
Normal file
20
util/clion_project_template/customTargets.xml.jinja
Normal file
@ -0,0 +1,20 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="CLionExternalBuildManager">
|
||||
{% for executable in project.executables %}
|
||||
{% for build_type in project.build_types %}
|
||||
{% set build_type_name = build_type | capitalize -%}
|
||||
<target id="{{ generate_uuid() }}" name="{{ executable.name }} {{ build_type_name }}" defaultType="TOOL">
|
||||
<configuration id="{{ generate_uuid() }}" name="{{ executable.name }} {{ build_type_name }}">
|
||||
<build type="TOOL">
|
||||
<tool actionId="Tool_External Tools_{{ executable.name }} {{ build_type_name }}" />
|
||||
</build>
|
||||
<clean type="TOOL">
|
||||
<tool actionId="Tool_External Tools_{{ executable.name }} {{ build_type_name }} Clean" />
|
||||
</clean>
|
||||
</configuration>
|
||||
</target>
|
||||
{% endfor %}
|
||||
{% endfor %}
|
||||
</component>
|
||||
</project>
|
17
util/clion_project_template/misc.xml
Normal file
17
util/clion_project_template/misc.xml
Normal file
@ -0,0 +1,17 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="CompDBSettings">
|
||||
<option name="linkedExternalProjectsSettings">
|
||||
<CompDBProjectSettings>
|
||||
<option name="externalProjectPath" value="$PROJECT_DIR$" />
|
||||
<option name="modules">
|
||||
<set>
|
||||
<option value="$PROJECT_DIR$" />
|
||||
</set>
|
||||
</option>
|
||||
</CompDBProjectSettings>
|
||||
</option>
|
||||
</component>
|
||||
<component name="CompDBWorkspace" PROJECT_DIR="$PROJECT_DIR$" />
|
||||
<component name="ExternalStorageConfigurationManager" enabled="true" />
|
||||
</project>
|
21
util/clion_project_template/tools/External Tools.xml.jinja
Normal file
21
util/clion_project_template/tools/External Tools.xml.jinja
Normal file
@ -0,0 +1,21 @@
|
||||
<toolSet name="External Tools">
|
||||
{% for executable in project.executables %}
|
||||
{% for build_type in project.build_types %}
|
||||
{% set build_type_name = build_type | capitalize -%}
|
||||
<tool name="{{ executable.name }} {{ build_type_name }}" showInMainMenu="false" showInEditor="false" showInProject="false" showInSearchPopup="false" disabled="false" useConsole="true" showConsoleOnStdOut="false" showConsoleOnStdErr="false" synchronizeAfterRun="true">
|
||||
<exec>
|
||||
<option name="COMMAND" value="{{ scons_exe }}" />
|
||||
<option name="PARAMETERS" value="-j{{ nproc }} --build_type={{ build_type }} --unity=disable {{ executable.filename }}" />
|
||||
<option name="WORKING_DIRECTORY" value="$ProjectFileDir$" />
|
||||
</exec>
|
||||
</tool>
|
||||
<tool name="{{ executable.name }} {{ build_type_name }} Clean" showInMainMenu="false" showInEditor="false" showInProject="false" showInSearchPopup="false" disabled="false" useConsole="true" showConsoleOnStdOut="false" showConsoleOnStdErr="false" synchronizeAfterRun="true">
|
||||
<exec>
|
||||
<option name="COMMAND" value="{{ scons_exe }}" />
|
||||
<option name="PARAMETERS" value="--build_type={{ build_type }} --unity=disable {{ executable.filename }} -c" />
|
||||
<option name="WORKING_DIRECTORY" value="$ProjectFileDir$" />
|
||||
</exec>
|
||||
</tool>
|
||||
{% endfor %}
|
||||
{% endfor %}
|
||||
</toolSet>
|
7
util/clion_project_template/vcs.xml
Normal file
7
util/clion_project_template/vcs.xml
Normal file
@ -0,0 +1,7 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="VcsDirectoryMappings">
|
||||
<mapping directory="" vcs="Git" />
|
||||
<mapping directory="$PROJECT_DIR$/external/scons-plus-plus" vcs="Git" />
|
||||
</component>
|
||||
</project>
|
98
util/clion_project_template/workspace.xml.jinja
Normal file
98
util/clion_project_template/workspace.xml.jinja
Normal file
@ -0,0 +1,98 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="AutoImportSettings">
|
||||
<option name="autoReloadType" value="SELECTIVE" />
|
||||
</component>
|
||||
<component name="CMakeRunConfigurationManager">
|
||||
<generated />
|
||||
</component>
|
||||
<component name="CMakeSettings">
|
||||
<configurations>
|
||||
<configuration PROFILE_NAME="Debug" ENABLED="true" CONFIG_NAME="Debug" />
|
||||
</configurations>
|
||||
</component>
|
||||
<component name="ClangdSettings">
|
||||
<option name="formatViaClangd" value="false" />
|
||||
</component>
|
||||
<component name="CompDBLocalSettings">
|
||||
<option name="availableProjects">
|
||||
<map>
|
||||
<entry>
|
||||
<key>
|
||||
<ExternalProjectPojo>
|
||||
<option name="name" value="{{ project.name }}" />
|
||||
<option name="path" value="$PROJECT_DIR$" />
|
||||
</ExternalProjectPojo>
|
||||
</key>
|
||||
<value>
|
||||
<list>
|
||||
<ExternalProjectPojo>
|
||||
<option name="name" value="{{ project.name }}" />
|
||||
<option name="path" value="$PROJECT_DIR$" />
|
||||
</ExternalProjectPojo>
|
||||
</list>
|
||||
</value>
|
||||
</entry>
|
||||
</map>
|
||||
</option>
|
||||
<option name="projectSyncType">
|
||||
<map>
|
||||
<entry key="$PROJECT_DIR$" value="RE_IMPORT" />
|
||||
</map>
|
||||
</option>
|
||||
</component>
|
||||
<component name="ExternalProjectsData">
|
||||
<projectState path="$PROJECT_DIR$">
|
||||
<ProjectState />
|
||||
</projectState>
|
||||
</component>
|
||||
<component name="Git.Settings">
|
||||
<option name="RECENT_GIT_ROOT_PATH" value="$PROJECT_DIR$" />
|
||||
</component>
|
||||
<component name="ProjectColorInfo">{
|
||||
"associatedIndex": 5
|
||||
}</component>
|
||||
<component name="ProjectViewState">
|
||||
<option name="hideEmptyMiddlePackages" value="true" />
|
||||
<option name="showLibraryContents" value="true" />
|
||||
</component>
|
||||
<component name="PropertiesComponent"><![CDATA[{
|
||||
"keyToString": {
|
||||
{% for executable in project.executables %}
|
||||
{% for build_type in project.build_types %}
|
||||
"Custom Build Application.{{ executable.name }} {{ build_type_name }}.executor": "Debug",
|
||||
{% endfor %}
|
||||
{% endfor %}
|
||||
"RunOnceActivity.RadMigrateCodeStyle": "true",
|
||||
"RunOnceActivity.ShowReadmeOnStart": "true",
|
||||
"RunOnceActivity.cidr.known.project.marker": "true",
|
||||
"RunOnceActivity.readMode.enableVisualFormatting": "true",
|
||||
"cf.first.check.clang-format": "false",
|
||||
"cidr.known.project.marker": "true",
|
||||
"git-widget-placeholder": "master",
|
||||
"node.js.detected.package.eslint": "true",
|
||||
"node.js.detected.package.tslint": "true",
|
||||
"node.js.selected.package.eslint": "(autodetect)",
|
||||
"node.js.selected.package.tslint": "(autodetect)",
|
||||
"nodejs_package_manager_path": "npm",
|
||||
"settings.editor.selected.configurable": "CLionExternalConfigurable",
|
||||
"vue.rearranger.settings.migration": "true"
|
||||
}
|
||||
}]]></component>
|
||||
<component name="RunManager" selected="Custom Build Application.{{ project.executables[0].name }} {{ project.build_types[0] }}">
|
||||
{% for executable in project.executables -%}
|
||||
{% for build_type in project.build_types -%}
|
||||
{% set build_type_name = build_type | capitalize -%}
|
||||
<configuration name="{{ executable.name }} {{ build_type_name }}" type="CLionExternalRunConfiguration" factoryName="Application" REDIRECT_INPUT="false" ELEVATE="false" USE_EXTERNAL_CONSOLE="false" EMULATE_TERMINAL="false" PASS_PARENT_ENVS_2="true" PROJECT_NAME="{{ project.name }}" TARGET_NAME="{{ executable.name }} {{ build_type_name }}" CONFIG_NAME="{{ executable.name }} {{ build_type_name }}" RUN_PATH="$PROJECT_DIR$/{{ executable.filename }}">
|
||||
<method v="2">
|
||||
<option name="CLION.EXTERNAL.BUILD" enabled="true" />
|
||||
</method>
|
||||
</configuration>
|
||||
{% endfor %}
|
||||
{% endfor %}
|
||||
</component>
|
||||
<component name="SpellCheckerSettings" RuntimeDictionaries="0" Folders="0" CustomDictionaries="0" DefaultDictionary="application-level" UseSingleDictionary="true" transferred="true" />
|
||||
<component name="TypeScriptGeneratedFilesManager">
|
||||
<option name="version" value="3" />
|
||||
</component>
|
||||
</project>
|
Loading…
x
Reference in New Issue
Block a user