VTK  9.0.1
vtkModuleWrapPython.cmake
Go to the documentation of this file.
1 #[==[
2 @defgroup module-wrapping-python Module Python CMake APIs
3 #]==]
4 
5 #[==[
6 @file vtkModuleWrapPython.cmake
7 @brief APIs for wrapping modules for Python
8 
9 @section Limitations
10 
11 Known limitations include:
12 
13  - Shared Python modules only really support shared builds of modules. VTK
14  does not provide mangling facilities for itself, so statically linking VTK
15  into its Python modules precludes using VTK's C++ interface anywhere else
16  within the Python environment.
17  - Only supports CPython. Other implementations are not supported by the
18  `VTK::WrapPython` executable.
19  - Links directly to a Python library. See the `VTK::Python` module for more
20  details.
21 #]==]
22 
23 #[==[
24 @ingroup module-wrapping-python
25 @brief Determine Python module destination
26 
27 Some projects may need to know where Python expects its modules to be placed in
28 the install tree (assuming a shared prefix). This function computes the default
29 and sets the passed variable to the value in the calling scope.
30 
31 ~~~
32 vtk_module_python_default_destination(<var>
33  [MAJOR_VERSION <major>])
34 ~~~
35 
36 By default, the destination is `${CMAKE_INSTALL_BINDIR}/Lib/site-packages` on
37 Windows and `${CMAKE_INSTALL_LIBDIR}/python<VERSION>/site-packages` otherwise.
38 
39 `<MAJOR_VERSION>` must be one of `2` or `3`. If not specified, it defaults to
40 the value of `${VTK_PYTHON_VERSION}`.
41 #]==]
42 function (vtk_module_python_default_destination var)
43  cmake_parse_arguments(_vtk_module_python
44  ""
45  "MAJOR_VERSION"
46  ""
47  ${ARGN})
48 
49  if (_vtk_module_python_UNPARSED_ARGUMENTS)
50  message(FATAL_ERROR
51  "Unparsed arguments for vtk_module_python_default_destination: "
52  "${_vtk_module_python_UNPARSED_ARGUMENTS}")
53  endif ()
54 
55  if (NOT _vtk_module_python_MAJOR_VERSION)
56  if (NOT DEFINED VTK_PYTHON_VERSION)
57  message(FATAL_ERROR
58  "A major version of Python must be specified (or `VTK_PYTHON_VERSION` "
59  "be set).")
60  endif ()
61 
62  set(_vtk_module_python_MAJOR_VERSION "${VTK_PYTHON_VERSION}")
63  endif ()
64 
65  if (NOT _vtk_module_python_MAJOR_VERSION STREQUAL "2" AND
66  NOT _vtk_module_python_MAJOR_VERSION STREQUAL "3")
67  message(FATAL_ERROR
68  "Only Python2 and Python3 are supported right now.")
69  endif ()
70 
71  if (WIN32 AND NOT CYGWIN)
72  set(destination "${CMAKE_INSTALL_BINDIR}/Lib/site-packages")
73  else ()
74  if (NOT DEFINED "Python${_vtk_module_python_MAJOR_VERSION}_VERSION_MAJOR" OR
75  NOT DEFINED "Python${_vtk_module_python_MAJOR_VERSION}_VERSION_MINOR")
76  find_package("Python${_vtk_module_python_MAJOR_VERSION}" QUIET COMPONENTS Development.Module)
77  endif ()
78 
79  if (Python${_vtk_module_python_MAJOR_VERSION}_VERSION_MAJOR AND Python${_vtk_module_python_MAJOR_VERSION}_VERSION_MINOR)
80  set(_vtk_python_version_suffix "${Python${VTK_PYTHON_VERSION}_VERSION_MAJOR}.${Python${VTK_PYTHON_VERSION}_VERSION_MINOR}")
81  else ()
82  message(WARNING
83  "The version of Python is unknown; not using a versioned directory "
84  "for Python modules.")
85  set(_vtk_python_version_suffix)
86  endif ()
87  set(destination "${CMAKE_INSTALL_LIBDIR}/python${_vtk_python_version_suffix}/site-packages")
88  endif ()
89 
90  set("${var}" "${destination}" PARENT_SCOPE)
91 endfunction ()
92 
93 #[==[
94 @ingroup module-impl
95 @brief Generate sources for using a module's classes from Python
96 
97 This function generates the wrapped sources for a module. It places the list of
98 generated source files and classes in variables named in the second and third
99 arguments, respectively.
100 
101 ~~~
102 _vtk_module_wrap_python_sources(<module> <sources> <classes>)
103 ~~~
104 #]==]
105 function (_vtk_module_wrap_python_sources module sources classes)
107  PROPERTY "exclude_wrap"
108  VARIABLE _vtk_python_exclude_wrap)
109  if (_vtk_python_exclude_wrap)
110  return ()
111  endif ()
112 
113  file(MAKE_DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${_vtk_python_library_name}Python")
114 
115  set(_vtk_python_args_file "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${_vtk_python_library_name}Python/${_vtk_python_library_name}-python.$<CONFIGURATION>.args")
116 
117  set(_vtk_python_hierarchy_depends "${module}")
118  _vtk_module_get_module_property("${module}"
119  PROPERTY "private_depends"
120  VARIABLE _vtk_python_private_depends)
121  list(APPEND _vtk_python_hierarchy_depends ${_vtk_python_private_depends})
122 
123  set(_vtk_python_command_depends)
124  foreach (_vtk_python_hierarchy_depend IN LISTS _vtk_python_hierarchy_depends)
125  _vtk_module_get_module_property("${_vtk_python_hierarchy_depend}"
126  PROPERTY "hierarchy"
127  VARIABLE _vtk_python_hierarchy_file)
128  if (_vtk_python_hierarchy_file)
129  list(APPEND _vtk_python_hierarchy_files "${_vtk_python_hierarchy_file}")
130  get_property(_vtk_python_is_imported
131  TARGET "${_vtk_python_hierarchy_depend}"
132  PROPERTY "IMPORTED")
133  if (_vtk_python_is_imported OR CMAKE_GENERATOR MATCHES "Ninja")
134  list(APPEND _vtk_python_command_depends "${_vtk_python_hierarchy_file}")
135  else ()
136  _vtk_module_get_module_property("${_vtk_python_hierarchy_depend}"
137  PROPERTY "library_name"
138  VARIABLE _vtk_python_hierarchy_library_name)
139  if (TARGET "${_vtk_python_hierarchy_library_name}-hierarchy")
140  list(APPEND _vtk_python_command_depends "${_vtk_python_hierarchy_library_name}-hierarchy")
141  else ()
142  message(FATAL_ERROR
143  "The ${_vtk_python_hierarchy_depend} hierarchy file is attached to a non-imported target "
144  "and a hierarchy target (${_vtk_python_hierarchy_library_name}-hierarchy) is "
145  "missing.")
146  endif ()
147  endif ()
148  endif ()
149  endforeach ()
150 
151  set(_vtk_python_genex_compile_definitions
152  "$<TARGET_PROPERTY:${_vtk_python_target_name},COMPILE_DEFINITIONS>")
153  set(_vtk_python_genex_include_directories
154  "$<TARGET_PROPERTY:${_vtk_python_target_name},INCLUDE_DIRECTORIES>")
155  file(GENERATE
156  OUTPUT "${_vtk_python_args_file}"
157  CONTENT "$<$<BOOL:${_vtk_python_genex_compile_definitions}>:\n-D\'$<JOIN:${_vtk_python_genex_compile_definitions},\'\n-D\'>\'>\n
158 $<$<BOOL:${_vtk_python_genex_include_directories}>:\n-I\'$<JOIN:${_vtk_python_genex_include_directories},\'\n-I\'>\'>\n
159 $<$<BOOL:${_vtk_python_hierarchy_files}>:\n--types \'$<JOIN:${_vtk_python_hierarchy_files},\'\n--types \'>\'>\n")
160 
161  set(_vtk_python_sources)
162 
163  # Get the list of public headers from the module.
164  _vtk_module_get_module_property("${module}"
165  PROPERTY "headers"
166  VARIABLE _vtk_python_headers)
167  set(_vtk_python_classes)
168  foreach (_vtk_python_header IN LISTS _vtk_python_headers)
169  # Assume the class name matches the basename of the header. This is VTK
170  # convention.
171  get_filename_component(_vtk_python_basename "${_vtk_python_header}" NAME_WE)
172  list(APPEND _vtk_python_classes
173  "${_vtk_python_basename}")
174 
175  set(_vtk_python_source_output
176  "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${_vtk_python_library_name}Python/${_vtk_python_basename}Python.cxx")
177  list(APPEND _vtk_python_sources
178  "${_vtk_python_source_output}")
179 
180  set(_vtk_python_wrap_target "VTK::WrapPython")
181  set(_vtk_python_macros_args)
182  if (TARGET VTKCompileTools::WrapPython)
183  set(_vtk_python_wrap_target "VTKCompileTools::WrapPython")
184  if (TARGET VTKCompileTools_macros)
185  list(APPEND _vtk_python_command_depends
186  "VTKCompileTools_macros")
187  list(APPEND _vtk_python_macros_args
188  -undef
189  -imacros "${_VTKCompileTools_macros_file}")
190  endif ()
191  endif ()
192 
193  add_custom_command(
194  OUTPUT "${_vtk_python_source_output}"
195  COMMAND ${CMAKE_CROSSCOMPILING_EMULATOR}
196  "$<TARGET_FILE:${_vtk_python_wrap_target}>"
197  "@${_vtk_python_args_file}"
198  -o "${_vtk_python_source_output}"
199  "${_vtk_python_header}"
200  ${_vtk_python_macros_args}
201  IMPLICIT_DEPENDS
202  CXX "${_vtk_python_header}"
203  COMMENT "Generating Python wrapper sources for ${_vtk_python_basename}"
204  DEPENDS
205  "${_vtk_python_header}"
206  "${_vtk_python_args_file}"
207  "$<TARGET_FILE:${_vtk_python_wrap_target}>"
208  ${_vtk_python_command_depends})
209  endforeach ()
210 
211  set("${sources}"
212  "${_vtk_python_sources}"
213  PARENT_SCOPE)
214  set("${classes}"
215  "${_vtk_python_classes}"
216  PARENT_SCOPE)
217 endfunction ()
218 
219 #[==[
220 @ingroup module-impl
221 @brief Generate a CPython library for a set of modules
222 
223 A Python module library may consist of the Python wrappings of multiple
224 modules. This is useful for kit-based builds where the modules part of the same
225 kit belong to the same Python module as well.
226 
227 ~~~
228 _vtk_module_wrap_python_library(<name> <module>...)
229 ~~~
230 
231 The first argument is the name of the Python module. The remaining arguments
232 are modules to include in the Python module.
233 
234 The remaining information it uses is assumed to be provided by the
235 @ref vtk_module_wrap_python function.
236 #]==]
237 function (_vtk_module_wrap_python_library name)
238  set(_vtk_python_library_sources)
239  set(_vtk_python_library_classes)
240  foreach (_vtk_python_module IN LISTS ARGN)
241  _vtk_module_get_module_property("${_vtk_python_module}"
242  PROPERTY "exclude_wrap"
243  VARIABLE _vtk_python_exclude_wrap)
244  if (_vtk_python_exclude_wrap)
245  continue ()
246  endif ()
247  _vtk_module_real_target(_vtk_python_target_name "${_vtk_python_module}")
248  _vtk_module_get_module_property("${_vtk_python_module}"
249  PROPERTY "library_name"
250  VARIABLE _vtk_python_library_name)
251 
252  # Wrap the module independently of the other VTK modules in the Python
253  # module.
254  _vtk_module_wrap_python_sources("${_vtk_python_module}" _vtk_python_sources _vtk_python_classes)
255  list(APPEND _vtk_python_library_sources
256  ${_vtk_python_sources})
257  list(APPEND _vtk_python_library_classes
258  ${_vtk_python_classes})
259 
260  # Make sure the module doesn't already have an associated Python package.
261  vtk_module_get_property("${_vtk_python_module}"
262  PROPERTY "INTERFACE_vtk_module_python_package"
263  VARIABLE _vtk_python_current_python_package)
264  if (DEFINED _vtk_python_current_python_package)
265  message(FATAL_ERROR
266  "It appears as though the ${_vtk_python_module} has already been "
267  "wrapped in Python in the ${_vtk_python_current_python_package} "
268  "package.")
269  endif ()
270  vtk_module_set_property("${_vtk_python_module}"
271  PROPERTY "INTERFACE_vtk_module_python_package"
272  VALUE "${_vtk_python_PYTHON_PACKAGE}")
273 
274  if (_vtk_python_INSTALL_HEADERS)
275  _vtk_module_export_properties(
276  BUILD_FILE "${_vtk_python_properties_build_file}"
277  INSTALL_FILE "${_vtk_python_properties_install_file}"
278  MODULE "${_vtk_python_module}"
279  PROPERTIES
280  # Export the wrapping hints file.
281  INTERFACE_vtk_module_python_package)
282  endif ()
283  endforeach ()
284 
285  # The foreach needs to be split so that dependencies are guaranteed to have
286  # the INTERFACE_vtk_module_python_package property set.
287  foreach (_vtk_python_module IN LISTS ARGN)
288  _vtk_module_get_module_property("${_vtk_python_module}"
289  PROPERTY "exclude_wrap"
290  VARIABLE _vtk_python_exclude_wrap)
291  if (_vtk_python_exclude_wrap)
292  continue ()
293  endif ()
294 
295  _vtk_module_get_module_property("${_vtk_python_module}"
296  PROPERTY "library_name"
297  VARIABLE _vtk_python_library_name)
298 
299  _vtk_module_get_module_property("${_vtk_python_module}"
300  PROPERTY "depends"
301  VARIABLE _vtk_python_module_depends)
302  set(_vtk_python_module_load_depends)
303  foreach (_vtk_python_module_depend IN LISTS _vtk_python_module_depends)
304  _vtk_module_get_module_property("${_vtk_python_module_depend}"
305  PROPERTY "exclude_wrap"
306  VARIABLE _vtk_python_module_depend_exclude_wrap)
307  if (_vtk_python_module_depend_exclude_wrap)
308  continue ()
309  endif ()
310 
311  _vtk_module_get_module_property("${_vtk_python_module_depend}"
312  PROPERTY "python_package"
313  VARIABLE _vtk_python_depend_module_package)
314  _vtk_module_get_module_property("${_vtk_python_module_depend}"
315  PROPERTY "library_name"
316  VARIABLE _vtk_python_depend_library_name)
317 
318  # XXX(kits): This doesn't work for kits.
319  list(APPEND _vtk_python_module_load_depends
320  "${_vtk_python_depend_module_package}.${_vtk_python_depend_library_name}")
321  endforeach ()
322 
323  if (_vtk_python_BUILD_STATIC)
324  # If static, we use .py modules that grab the contents from the baked-in modules.
325  set(_vtk_python_module_file
326  "${CMAKE_BINARY_DIR}/${_vtk_python_MODULE_DESTINATION}/${_vtk_python_package_path}/${_vtk_python_library_name}.py")
327  set(_vtk_python_module_contents
328  "from ${_vtk_python_import_prefix}${_vtk_python_library_name} import *\n")
329 
330  file(GENERATE
331  OUTPUT "${_vtk_python_module_file}"
332  CONTENT "${_vtk_python_module_contents}")
333 
334  # Set `python_modules` to provide the list of python files that go along with
335  # this module
336  _vtk_module_set_module_property("${_vtk_python_module}" APPEND
337  PROPERTY "python_modules"
338  VALUE "${_vtk_python_module_file}")
339  endif ()
340  endforeach ()
341 
342  if (NOT _vtk_python_library_sources)
343  return ()
344  endif ()
345 
346  set(_vtk_python_init_data_file "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${name}Python/${name}-init.data")
347 
348  file(GENERATE
349  OUTPUT "${_vtk_python_init_data_file}"
350  CONTENT "${_vtk_python_library_name}\n$<JOIN:${_vtk_python_classes},\n>\nDEPENDS\n$<JOIN:${_vtk_python_module_load_depends},\n>\n")
351 
352  set(_vtk_python_init_output
353  "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${name}Python/${name}Init.cxx")
354  set(_vtk_python_init_impl_output
355  "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${name}Python/${name}InitImpl.cxx")
356  list(APPEND _vtk_python_library_sources
357  "${_vtk_python_init_output}"
358  "${_vtk_python_init_impl_output}")
359 
360  set(_vtk_python_wrap_target "VTK::WrapPythonInit")
361  if (TARGET VTKCompileTools::WrapPythonInit)
362  set(_vtk_python_wrap_target "VTKCompileTools::WrapPythonInit")
363  endif ()
364 
365  if(_vtk_python_BUILD_STATIC)
366  set(additonal_options "${_vtk_python_import_prefix}")
367  endif()
368  add_custom_command(
369  OUTPUT "${_vtk_python_init_output}"
370  "${_vtk_python_init_impl_output}"
371  COMMAND "${_vtk_python_wrap_target}"
372  "${_vtk_python_init_data_file}"
373  "${_vtk_python_init_output}"
374  "${_vtk_python_init_impl_output}"
375  "${additonal_options}"
376  COMMENT "Generating the Python module initialization sources for ${name}"
377  DEPENDS
378  "${_vtk_python_init_data_file}"
379  "$<TARGET_FILE:${_vtk_python_wrap_target}>")
380 
381  if (_vtk_python_BUILD_STATIC)
382  set(_vtk_python_module_header_file
383  "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${name}/static_python/${name}.h")
384  set(_vtk_python_module_header_content
385 "#ifndef ${name}_h
386 #define ${name}_h
387 
388 #include <vtkPython.h>
389 
390 #ifdef __cplusplus
391 extern \"C\" {
392 #endif
393 #if PY_VERSION_HEX < 0x03000000
394 extern void init${_vtk_python_library_name}();
395 #else
396 extern PyObject* PyInit_${_vtk_python_library_name}();
397 #endif
398 #ifdef __cplusplus
399 }
400 #endif
401 
402 #endif
403 ")
404 
405  file(GENERATE
406  OUTPUT "${_vtk_python_module_header_file}"
407  CONTENT "${_vtk_python_module_header_content}")
408  # XXX(cmake): Why is this necessary? One would expect that `file(GENERATE)`
409  # would do this automatically.
410  set_property(SOURCE "${_vtk_python_module_header_file}"
411  PROPERTY
412  GENERATED 1)
413 
414  add_library("${name}" STATIC
415  ${_vtk_python_library_sources}
416  "${_vtk_python_module_header_file}")
417  target_include_directories("${name}"
418  INTERFACE
419  "$<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${name}/static_python>")
420  target_link_libraries("${name}"
421  PUBLIC
422  VTK::Python)
423  set_property(TARGET "${name}"
424  PROPERTY
425  LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${_vtk_python_STATIC_MODULE_DESTINATION}")
426  else ()
427  add_library("${name}" MODULE
428  ${_vtk_python_library_sources})
429  if (WIN32 AND NOT CYGWIN)
430  # XXX(python-debug): This is disabled out because there's no reliable way
431  # to tell whether we're using a debug build of Python or not. Since using
432  # a debug Python build is so rare, just assume we're always using a
433  # non-debug build of Python itself.
434  #
435  # The proper fix is to dig around and ask the backing `PythonN::Python`
436  # target used by `VTK::Python` for its properties to find out, per
437  # configuration, whether it is a debug build. If it is, add the postfix
438  # (regardless of VTK's build type). Otherwise, no postfix.
439  if (FALSE)
440  set_property(TARGET "${name}"
441  APPEND_STRING
442  PROPERTY
443  DEBUG_POSTFIX "_d")
444  endif ()
445  set_property(TARGET "${name}"
446  PROPERTY
447  SUFFIX ".pyd")
448  endif ()
449  set_property(TARGET "${name}"
450  PROPERTY
451  LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/${_vtk_python_MODULE_DESTINATION}/${_vtk_python_package_path}")
452  get_property(_vtk_python_is_multi_config GLOBAL
453  PROPERTY GENERATOR_IS_MULTI_CONFIG)
454  if (_vtk_python_is_multi_config)
455  # XXX(MultiNinja): This isn't going to work in general since MultiNinja
456  # will error about overlapping output paths.
457  foreach (_vtk_python_config IN LISTS CMAKE_CONFIGURATION_TYPES)
458  string(TOUPPER "${_vtk_python_config}" _vtk_python_config_upper)
459  set_property(TARGET "${name}"
460  PROPERTY
461  "LIBRARY_OUTPUT_DIRECTORY_${_vtk_python_config_upper}" "${CMAKE_BINARY_DIR}/${_vtk_python_MODULE_DESTINATION}/${_vtk_python_package_path}")
462  endforeach ()
463  endif ()
464  set_target_properties("${name}"
465  PROPERTIES
466  PREFIX ""
467  OUTPUT_NAME "${_vtk_python_library_name}"
468  ARCHIVE_OUTPUT_NAME "${name}")
469  endif ()
470 
471  vtk_module_autoinit(
472  MODULES ${ARGN}
473  TARGETS "${name}")
474 
475  # The wrapper code will expand PYTHON_PACKAGE as needed
476  target_compile_definitions("${name}"
477  PRIVATE
478  "-DPYTHON_PACKAGE=\"${_vtk_python_PYTHON_PACKAGE}\"")
479 
480  target_link_libraries("${name}"
481  PRIVATE
482  ${ARGN}
483  VTK::WrappingPythonCore
484  VTK::Python)
485 
486  set(_vtk_python_export)
487  if (_vtk_python_INSTALL_EXPORT)
488  set(_vtk_python_export
489  EXPORT "${_vtk_python_INSTALL_EXPORT}")
490  endif ()
491 
492  install(
493  TARGETS "${name}"
494  ${_vtk_python_export}
495  COMPONENT "${_vtk_python_COMPONENT}"
496  RUNTIME DESTINATION "${_vtk_python_MODULE_DESTINATION}/${_vtk_python_package_path}"
497  LIBRARY DESTINATION "${_vtk_python_MODULE_DESTINATION}/${_vtk_python_package_path}"
498  ARCHIVE DESTINATION "${_vtk_python_STATIC_MODULE_DESTINATION}")
499 endfunction ()
500 
501 #[==[
502 @ingroup module-wrapping-python
503 @brief Wrap a set of modules for use in Python
504 
505 ~~~
507  MODULES <module>...
508  [TARGET <target>]
509  [WRAPPED_MODULES <varname>]
510 
511  [BUILD_STATIC <ON|OFF>]
512  [INSTALL_HEADERS <ON|OFF>]
513 
514  [DEPENDS <target>...]
515 
516  [MODULE_DESTINATION <destination>]
517  [STATIC_MODULE_DESTINATION <destination>]
518  [CMAKE_DESTINATION <destination>]
519  [LIBRARY_DESTINATION <destination>]
520 
521  [PYTHON_PACKAGE <package>]
522  [SOABI <soabi>]
523 
524  [INSTALL_EXPORT <export>]
525  [COMPONENT <component>])
526 ~~~
527 
528  * `MODULES`: (Required) The list of modules to wrap.
529  * `TARGET`: (Recommended) The target to create which represents all wrapped
530  Python modules. This is mostly useful when supporting static Python modules
531  in order to add the generated modules to the built-in table.
532  * `WRAPPED_MODULES`: (Recommended) Not all modules are wrappable. This
533  variable will be set to contain the list of modules which were wrapped.
534  These modules will have a `INTERFACE_vtk_module_python_package` property
535  set on them which is the name that should be given to `import` statements
536  in Python code.
537  * `BUILD_STATIC`: Defaults to `${BUILD_SHARED_LIBS}`. Note that shared
538  modules with a static build is not completely supported. For static Python
539  module builds, a header named `<TARGET>.h` will be available with a
540  function `void <TARGET>_load()` which will add all Python modules created
541  by this call to the imported module table. For shared Python module builds,
542  the same function is provided, but it is a no-op.
543  * `INSTALL_HEADERS` (Defaults to `ON`): If unset, CMake properties will not
544  be installed.
545  * `DEPENDS`: This is list of other Python modules targets i.e. targets
546  generated from previous calls to `vtk_module_wrap_python` that this new
547  target depends on. This is used when `BUILD_STATIC` is true to ensure that
548  the `void <TARGET>_load()` is correctly called for each of the dependencies.
549  * `MODULE_DESTINATION`: Modules will be placed in this location in the
550  build tree. The install tree should remove `$<CONFIGURATION>` bits, but it
551  currently does not. See `vtk_module_python_default_destination` for the
552  default value.
553  * `STATIC_MODULE_DESTINATION`: Defaults to `${CMAKE_INSTALL_LIBDIR}`. This
554  default may change in the future since the best location for these files is
555  not yet known. Static libraries containing Python code will be installed to
556  the install tree under this path.
557  * `CMAKE_DESTINATION`: (Required if `INSTALL_HEADERS` is `ON`) Where to
558  install Python-related module property CMake files.
559  * `LIBRARY_DESTINATION` (Recommended): If provided, dynamic loader
560  information will be added to modules for loading dependent libraries.
561  * `PYTHON_PACKAGE`: (Recommended) All generated modules will be added to this
562  Python package. The format is in Python syntax (e.g.,
563  `package.subpackage`).
564  * `SOABI`: (Required for wheel support): If given, generate libraries with
565  the SOABI tag in the module filename.
566  * `INSTALL_EXPORT`: If provided, static installs will add the installed
567  libraries to the provided export set.
568  * `COMPONENT`: Defaults to `python`. All install rules created by this
569  function will use this installation component.
570 #]==]
572  cmake_parse_arguments(_vtk_python
573  ""
574  "MODULE_DESTINATION;STATIC_MODULE_DESTINATION;LIBRARY_DESTINATION;PYTHON_PACKAGE;BUILD_STATIC;INSTALL_HEADERS;INSTALL_EXPORT;TARGET;COMPONENT;WRAPPED_MODULES;CMAKE_DESTINATION;DEPENDS;SOABI"
575  "MODULES"
576  ${ARGN})
577 
578  if (_vtk_python_UNPARSED_ARGUMENTS)
579  message(FATAL_ERROR
580  "Unparsed arguments for vtk_module_wrap_python: "
581  "${_vtk_python_UNPARSED_ARGUMENTS}")
582  endif ()
583 
584  if (NOT _vtk_python_MODULES)
585  message(WARNING
586  "No modules were requested for Python wrapping.")
587  return ()
588  endif ()
589 
590  _vtk_module_split_module_name("${_vtk_python_TARGET}" _vtk_python)
591 
592  set(_vtk_python_depends)
593  foreach (_vtk_python_depend IN LISTS _vtk_python_DEPENDS)
594  _vtk_module_split_module_name("${_vtk_python_depend}" _vtk_python_depends)
595  list(APPEND _vtk_python_depends
596  "${_vtk_python_depends_TARGET_NAME}")
597  endforeach ()
598 
599  if (NOT DEFINED _vtk_python_MODULE_DESTINATION)
600  vtk_module_python_default_destination(_vtk_python_MODULE_DESTINATION)
601  endif ()
602 
603  if (NOT DEFINED _vtk_python_INSTALL_HEADERS)
604  set(_vtk_python_INSTALL_HEADERS ON)
605  endif ()
606 
607  if (_vtk_python_SOABI)
608  get_property(_vtk_python_is_multi_config GLOBAL
609  PROPERTY GENERATOR_IS_MULTI_CONFIG)
610  if (_vtk_python_is_multi_config)
611  foreach (_vtk_python_config IN LISTS CMAKE_CONFIGURATION_TYPES)
612  string(TOUPPER "${_vtk_python_config}" _vtk_python_upper_config)
613  set("CMAKE_${_vtk_python_upper_config}_POSTFIX"
614  ".${_vtk_python_SOABI}")
615  endforeach ()
616  else ()
617  string(TOUPPER "${CMAKE_BUILD_TYPE}" _vtk_python_upper_config)
618  set("CMAKE_${_vtk_python_upper_config}_POSTFIX"
619  ".${_vtk_python_SOABI}")
620  endif ()
621  endif ()
622 
623  if (_vtk_python_INSTALL_HEADERS AND NOT DEFINED _vtk_python_CMAKE_DESTINATION)
624  message(FATAL_ERROR
625  "No CMAKE_DESTINATION set, but headers from the Python wrapping were "
626  "requested for install and the CMake files are required to work with "
627  "them.")
628  endif ()
629 
630  if (NOT DEFINED _vtk_python_BUILD_STATIC)
631  if (BUILD_SHARED_LIBS)
632  set(_vtk_python_BUILD_STATIC OFF)
633  else ()
634  set(_vtk_python_BUILD_STATIC ON)
635  endif ()
636  else ()
637  if (NOT _vtk_python_BUILD_STATIC AND NOT BUILD_SHARED_LIBS)
638  message(WARNING
639  "Building shared Python modules against static VTK modules only "
640  "supports consuming the VTK modules via their Python interfaces due "
641  "to the lack of support for an SDK to use the same static libraries.")
642  endif ()
643  endif ()
644 
645  if (NOT DEFINED _vtk_python_STATIC_MODULE_DESTINATION)
646  # TODO: Is this correct?
647  set(_vtk_python_STATIC_MODULE_DESTINATION "${CMAKE_INSTALL_LIBDIR}")
648  endif ()
649 
650  if (NOT DEFINED _vtk_python_COMPONENT)
651  set(_vtk_python_COMPONENT "python")
652  endif ()
653 
654  if (NOT _vtk_python_PYTHON_PACKAGE)
655  message(FATAL_ERROR
656  "No `PYTHON_PACKAGE` was given; Python modules must be placed into a "
657  "package.")
658  endif ()
659  string(REPLACE "." "/" _vtk_python_package_path "${_vtk_python_PYTHON_PACKAGE}")
660 
661  if(_vtk_python_BUILD_STATIC)
662  # When doing static builds we want the statically initialized built-ins to be
663  # used. It is unclear in the Python-C API how to construct `namespace.module`
664  # so instead at the C++ level we import "namespace_module" during startup
665  # and than the python modules moving those imports into the correct python
666  # module.
667  string(REPLACE "." "_" _vtk_python_import_prefix "${_vtk_python_PYTHON_PACKAGE}_")
668  else()
669  # We are building dynamic libraries therefore the prefix is simply '.'
670  set(_vtk_python_import_prefix ".")
671  endif()
672 
673  _vtk_module_check_destinations(_vtk_python_
674  MODULE_DESTINATION
675  STATIC_MODULE_DESTINATION
676  CMAKE_DESTINATION
677  LIBRARY_DESTINATION)
678 
679  if (_vtk_python_INSTALL_HEADERS)
680  set(_vtk_python_properties_filename "${_vtk_python_PYTHON_PACKAGE}-vtk-python-module-properties.cmake")
681  set(_vtk_python_properties_install_file "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${_vtk_python_TARGET_NAME}/${_vtk_python_properties_filename}.install")
682  set(_vtk_python_properties_build_file "${CMAKE_BINARY_DIR}/${_vtk_python_CMAKE_DESTINATION}/${_vtk_python_properties_filename}")
683 
684  file(WRITE "${_vtk_python_properties_build_file}")
685  file(WRITE "${_vtk_python_properties_install_file}")
686  endif ()
687 
688  if (DEFINED _vtk_python_LIBRARY_DESTINATION)
689  # Set up rpaths
690  set(CMAKE_BUILD_RPATH_USE_ORIGIN 1)
691  if (UNIX)
692  file(RELATIVE_PATH _vtk_python_relpath
693  "/prefix/${_vtk_python_MODULE_DESTINATION}/${_vtk_python_package_path}"
694  "/prefix/${_vtk_python_LIBRARY_DESTINATION}")
695 
696  if (APPLE)
697  set(_vtk_python_origin_stem "@loader_path")
698  else ()
699  set(_vtk_python_origin_stem "$ORIGIN")
700  endif()
701 
702  list(APPEND CMAKE_INSTALL_RPATH
703  "${_vtk_python_origin_stem}/${_vtk_python_relpath}")
704  endif ()
705  endif ()
706 
707  set(_vtk_python_sorted_modules ${_vtk_python_MODULES})
708  foreach (_vtk_python_module IN LISTS _vtk_python_MODULES)
709  _vtk_module_get_module_property("${_vtk_python_module}"
710  PROPERTY "depends"
711  VARIABLE "_vtk_python_${_vtk_python_module}_depends")
712  endforeach ()
713  vtk_topological_sort(_vtk_python_sorted_modules "_vtk_python_" "_depends")
714 
715  set(_vtk_python_sorted_modules_filtered)
716  foreach (_vtk_python_module IN LISTS _vtk_python_sorted_modules)
717  if (_vtk_python_module IN_LIST _vtk_python_MODULES)
718  list(APPEND _vtk_python_sorted_modules_filtered
719  "${_vtk_python_module}")
720  endif ()
721  endforeach ()
722 
723  set(_vtk_python_all_modules)
724  set(_vtk_python_all_wrapped_modules)
725  foreach (_vtk_python_module IN LISTS _vtk_python_sorted_modules_filtered)
726  _vtk_module_get_module_property("${_vtk_python_module}"
727  PROPERTY "library_name"
728  VARIABLE _vtk_python_library_name)
729  _vtk_module_wrap_python_library("${_vtk_python_library_name}Python" "${_vtk_python_module}")
730 
731  if (TARGET "${_vtk_python_library_name}Python")
732  list(APPEND _vtk_python_all_modules
733  "${_vtk_python_library_name}Python")
734  list(APPEND _vtk_python_all_wrapped_modules
735  "${_vtk_python_module}")
736  endif ()
737  endforeach ()
738 
739  if (NOT _vtk_python_all_modules)
740  message(FATAL_ERROR
741  "No modules given could be wrapped.")
742  endif ()
743 
744  if (_vtk_python_INSTALL_HEADERS)
745  install(
746  FILES "${_vtk_python_properties_install_file}"
747  DESTINATION "${_vtk_python_CMAKE_DESTINATION}"
748  RENAME "${_vtk_python_properties_filename}"
749  COMPONENT "development")
750  endif ()
751 
752  if (DEFINED _vtk_python_WRAPPED_MODULES)
753  set("${_vtk_python_WRAPPED_MODULES}"
754  "${_vtk_python_all_wrapped_modules}"
755  PARENT_SCOPE)
756  endif ()
757 
758  if (_vtk_python_TARGET)
759  add_library("${_vtk_python_TARGET_NAME}" INTERFACE)
760  target_include_directories("${_vtk_python_TARGET_NAME}"
761  INTERFACE
762  "$<BUILD_INTERFACE:${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${_vtk_python_TARGET_NAME}/static_python>")
763  target_link_libraries("${_vtk_python_TARGET_NAME}"
764  INTERFACE
765  ${_vtk_python_DEPENDS})
766  if (NOT _vtk_python_TARGET STREQUAL _vtk_python_TARGET_NAME)
767  add_library("${_vtk_python_TARGET}" ALIAS
768  "${_vtk_python_TARGET_NAME}")
769  endif ()
770 
771  if (_vtk_python_INSTALL_EXPORT)
772  install(
773  TARGETS "${_vtk_python_TARGET_NAME}"
774  EXPORT "${_vtk_python_INSTALL_EXPORT}"
775  COMPONENT "development")
776  endif ()
777 
778  set(_vtk_python_all_modules_include_file
779  "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${_vtk_python_TARGET_NAME}/static_python/${_vtk_python_TARGET_NAME}.h")
780  set(_vtk_python_all_modules_include_content
781  "#ifndef ${_vtk_python_TARGET_NAME}_h\n#define ${_vtk_python_TARGET_NAME}_h\n")
782 
783  if (_vtk_python_BUILD_STATIC)
784  foreach (_vtk_python_module IN LISTS _vtk_python_all_modules)
785  string(APPEND _vtk_python_all_modules_include_content
786  "#include \"${_vtk_python_module}.h\"\n")
787  endforeach ()
788  endif ()
789 
790  foreach (_vtk_python_depend IN LISTS _vtk_python_depends)
791  string(APPEND _vtk_python_all_modules_include_content
792  "#include \"${_vtk_python_depend}.h\"\n")
793  endforeach ()
794 
795  string(APPEND _vtk_python_all_modules_include_content
796 "#if PY_VERSION_HEX < 0x03000000
797 #define PY_APPEND_INIT(module) PyImport_AppendInittab(\"${_vtk_python_import_prefix}\" #module, init ## module)
798 #define PY_IMPORT(module) init ## module();
799 #else
800 #define PY_APPEND_INIT(module) PyImport_AppendInittab(\"${_vtk_python_import_prefix}\" #module, PyInit_ ## module)
801 #define PY_IMPORT(module) { \\
802  PyObject* var_ ## module = PyInit_ ## module(); \\
803  PyDict_SetItemString(PyImport_GetModuleDict(), \"${_vtk_python_import_prefix}\" #module,var_ ## module); \\
804  Py_DECREF(var_ ## module); }
805 #endif
806 
807 #define PY_APPEND_INIT_OR_IMPORT(module, do_import) \\
808  if (do_import) { PY_IMPORT(module); } else { PY_APPEND_INIT(module); }
809 
810 static void ${_vtk_python_TARGET_NAME}_load() {\n")
811 
812  foreach (_vtk_python_depend IN LISTS _vtk_python_depends)
813  string(APPEND _vtk_python_all_modules_include_content
814  " ${_vtk_python_depend}_load();\n")
815  endforeach ()
816 
817  if (_vtk_python_BUILD_STATIC)
818  string(APPEND _vtk_python_all_modules_include_content
819  " int do_import = Py_IsInitialized();\n")
820  foreach (_vtk_python_module IN LISTS _vtk_python_sorted_modules_filtered)
821  _vtk_module_get_module_property("${_vtk_python_module}"
822  PROPERTY "library_name"
823  VARIABLE _vtk_python_library_name)
824  if (TARGET "${_vtk_python_library_name}Python")
825  string(APPEND _vtk_python_all_modules_include_content
826  " PY_APPEND_INIT_OR_IMPORT(${_vtk_python_library_name}, do_import);\n")
827  endif ()
828  endforeach ()
829  endif ()
830 
831  string(APPEND _vtk_python_all_modules_include_content
832  "}\n#undef PY_APPEND_INIT\n#undef PY_IMPORT\n#undef PY_APPEND_INIT_OR_IMPORT\n#endif\n")
833 
834  # TODO: Install this header.
835  file(GENERATE
836  OUTPUT "${_vtk_python_all_modules_include_file}"
837  CONTENT "${_vtk_python_all_modules_include_content}")
838 
839  if (_vtk_python_BUILD_STATIC)
840  # TODO: Install these targets.
841  target_link_libraries("${_vtk_python_TARGET_NAME}"
842  INTERFACE
843  ${_vtk_python_all_modules})
844  endif ()
845 
846  if (_vtk_python_BUILD_STATIC)
847  # Next, we generate a Python module that can be imported to import any
848  # static artifacts e.g. all wrapping Python modules in static builds,
849  # (eventually, frozen modules etc.)
850  string(REPLACE "." "_" _vtk_python_static_importer_name "_${_vtk_python_PYTHON_PACKAGE}_static")
851  set(_vtk_python_static_importer_file
852  "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/${_vtk_python_TARGET_NAME}/static_python/${_vtk_python_static_importer_name}.c")
853  set(_vtk_python_static_importer_content "// generated file, do not edit!
854 #include <vtkPython.h>
855 #include \"${_vtk_python_TARGET_NAME}.h\"
856 
857  static PyMethodDef Py${_vtk_python_static_importer_name}_Methods[] = {
858  {NULL, NULL, 0, NULL}};
859 #if PY_VERSION_HEX >= 0x03000000
860  static PyModuleDef ${_vtk_python_static_importer_name}Module = {
861  PyModuleDef_HEAD_INIT,
862  \"${_vtk_python_static_importer_name}\", // m_name
863  \"module to import static components for ${_vtk_python_TARGET_NAME}\", // m_doc
864  0, // m_size
865  Py${_vtk_python_static_importer_name}_Methods, // m_methods
866  NULL, // m_reload
867  NULL, // m_traverse
868  NULL, // m_clear
869  NULL // m_free
870  };
871 #endif
872 
873 #if PY_VERSION_HEX >= 0x03000000
874  PyMODINIT_FUNC PyInit_${_vtk_python_static_importer_name}(void)
875 #else
876  PyMODINIT_FUNC init${_vtk_python_static_importer_name}(void)
877 #endif
878  {
879  // since this gets called after `Py_Initialize`, this will import the static
880  // modules and not just update the init table.
881  ${_vtk_python_TARGET_NAME}_load();
882 #if PY_VERSION_HEX >= 0x03000000
883  return PyModule_Create(&${_vtk_python_static_importer_name}Module);
884 #else
885  Py_InitModule(\"${_vtk_python_static_importer_name}\", Py${_vtk_python_static_importer_name}_Methods);
886 #endif
887  }\n")
888 
889  # TODO: Install this header.
890  file(GENERATE
891  OUTPUT "${_vtk_python_static_importer_file}"
892  CONTENT "${_vtk_python_static_importer_content}")
893 
894  add_library("${_vtk_python_static_importer_name}" MODULE
895  ${_vtk_python_static_importer_file})
896  if (WIN32 AND NOT CYGWIN)
897  set_property(TARGET "${_vtk_python_static_importer_name}"
898  PROPERTY
899  SUFFIX ".pyd")
900  endif()
901  set_property(TARGET "${_vtk_python_static_importer_name}"
902  PROPERTY
903  LIBRARY_OUTPUT_DIRECTORY "${_vtk_python_MODULE_DESTINATION}")
904  get_property(_vtk_python_is_multi_config GLOBAL
905  PROPERTY GENERATOR_IS_MULTI_CONFIG)
906  if (_vtk_python_is_multi_config)
907  # XXX(MultiNinja): This isn't going to work in general since MultiNinja
908  # will error about overlapping output paths.
909  foreach (_vtk_python_config IN LISTS CMAKE_CONFIGURATION_TYPES)
910  string(TOUPPER "${_vtk_python_config}" _vtk_python_config_upper)
911  set_property(TARGET "${_vtk_python_static_importer_name}"
912  PROPERTY
913  "LIBRARY_OUTPUT_DIRECTORY_${_vtk_python_config_upper}" "${CMAKE_BINARY_DIR}/${_vtk_python_MODULE_DESTINATION}")
914  endforeach ()
915  endif ()
916  set_property(TARGET "${_vtk_python_static_importer_name}"
917  PROPERTY
918  PREFIX "")
919  target_link_libraries("${_vtk_python_static_importer_name}"
920  PRIVATE
921  ${_vtk_python_TARGET_NAME}
922  VTK::WrappingPythonCore
923  VTK::Python)
924  install(
925  TARGETS "${_vtk_python_static_importer_name}"
926  COMPONENT "${_vtk_python_COMPONENT}"
927  RUNTIME DESTINATION "${_vtk_python_MODULE_DESTINATION}"
928  LIBRARY DESTINATION "${_vtk_python_MODULE_DESTINATION}"
929  ARCHIVE DESTINATION "${_vtk_python_STATIC_MODULE_DESTINATION}")
930  endif () # if (_vtk_python_BUILD_STATIC)
931  endif ()
932 endfunction ()
933 
934 #[==[
935 @ingroup module-wrapping-python
936 @brief Install Python packages with a module
937 
938 Some modules may have associated Python code. This function should be used to
939 install them.
940 
941 ~~~
942 vtk_module_add_python_package(<module>
943  PACKAGE <package>
944  FILES <files>...
945  [MODULE_DESTINATION <destination>]
946  [COMPONENT <component>])
947 ~~~
948 
949 The `<module>` argument must match the associated VTK module that the package
950 is with. Each package is independent and should be installed separately. That
951 is, `package` and `package.subpackage` should each get their own call to this
952 function.
953 
954  * `PACKAGE`: (Required) The package installed by this call. Currently,
955  subpackages must have their own call to this function.
956  * `FILES`: (Required) File paths should be relative to the source directory
957  of the calling `CMakeLists.txt`. Upward paths are not supported (nor are
958  checked for). Absolute paths are assumed to be in the build tree and their
959  relative path is computed relative to the current binary directory.
960  * `MODULE_DESTINATION`: Modules will be placed in this location in the
961  build tree. The install tree should remove `$<CONFIGURATION>` bits, but it
962  currently does not. See `vtk_module_python_default_destination` for the
963  default value.
964  * `COMPONENT`: Defaults to `python`. All install rules created by this
965  function will use this installation component.
966 
967 A `<module>-<package>` target is created which ensures that all Python modules
968 have been copied to the correct location in the build tree.
969 
970 @todo Support a tree of modules with a single call.
971 
972 @todo Support freezing the Python package. This should create a header and the
973 associated target should provide an interface for including this header. The
974 target should then be exported and the header installed properly.
975 #]==]
976 function (vtk_module_add_python_package name)
977  if (NOT name STREQUAL _vtk_build_module)
978  message(FATAL_ERROR
979  "Python modules must match their module names.")
980  endif ()
981 
982  cmake_parse_arguments(_vtk_add_python_package
983  ""
984  "PACKAGE;MODULE_DESTINATION;COMPONENT"
985  "FILES"
986  ${ARGN})
987 
988  if (_vtk_add_python_package_UNPARSED_ARGUMENTS)
989  message(FATAL_ERROR
990  "Unparsed arguments for vtk_module_add_python_package: "
991  "${_vtk_add_python_package_UNPARSED_ARGUMENTS}")
992  endif ()
993 
994  if (NOT _vtk_add_python_package_PACKAGE)
995  message(FATAL_ERROR
996  "The `PACKAGE` argument is required.")
997  endif ()
998  string(REPLACE "." "/" _vtk_add_python_package_path "${_vtk_add_python_package_PACKAGE}")
999 
1000  if (NOT _vtk_add_python_package_FILES)
1001  message(FATAL_ERROR
1002  "The `FILES` argument is required.")
1003  endif ()
1004 
1005  if (NOT DEFINED _vtk_add_python_package_MODULE_DESTINATION)
1006  vtk_module_python_default_destination(_vtk_add_python_package_MODULE_DESTINATION)
1007  endif ()
1008 
1009  if (NOT DEFINED _vtk_add_python_package_COMPONENT)
1010  set(_vtk_add_python_package_COMPONENT "python")
1011  endif ()
1012 
1013  set(_vtk_add_python_package_file_outputs)
1014  foreach (_vtk_add_python_package_file IN LISTS _vtk_add_python_package_FILES)
1015  if (IS_ABSOLUTE "${_vtk_add_python_package_file}")
1016  file(RELATIVE_PATH _vtk_add_python_package_name
1017  "${CMAKE_CURRENT_BINARY_DIR}"
1018  "${_vtk_add_python_package_name}")
1019  else ()
1020  set(_vtk_add_python_package_name
1021  "${_vtk_add_python_package_file}")
1022  set(_vtk_add_python_package_file
1023  "${CMAKE_CURRENT_SOURCE_DIR}/${_vtk_add_python_package_file}")
1024  endif ()
1025 
1026  set(_vtk_add_python_package_file_output
1027  "${CMAKE_BINARY_DIR}/${_vtk_add_python_package_MODULE_DESTINATION}/${_vtk_add_python_package_name}")
1028  add_custom_command(
1029  OUTPUT "${_vtk_add_python_package_file_output}"
1030  DEPENDS "${_vtk_add_python_package_file}"
1031  COMMAND "${CMAKE_COMMAND}" -E copy_if_different
1032  "${_vtk_add_python_package_file}"
1033  "${_vtk_add_python_package_file_output}"
1034  COMMENT "Copying ${_vtk_add_python_package_name} to the binary directory")
1035  list(APPEND _vtk_add_python_package_file_outputs
1036  "${_vtk_add_python_package_file_output}")
1037  # XXX
1038  if (BUILD_SHARED_LIBS)
1039  install(
1040  FILES "${_vtk_add_python_package_name}"
1041  DESTINATION "${_vtk_add_python_package_MODULE_DESTINATION}/${_vtk_add_python_package_path}"
1042  COMPONENT "${_vtk_add_python_package_COMPONENT}")
1043  endif()
1044  endforeach ()
1045 
1046  get_property(_vtk_add_python_package_module GLOBAL
1047  PROPERTY "_vtk_module_${_vtk_build_module}_target_name")
1048  add_custom_target("${_vtk_add_python_package_module}-${_vtk_add_python_package_PACKAGE}" ALL
1049  DEPENDS
1050  ${_vtk_add_python_package_file_outputs})
1051 
1052  # Set `python_modules` to provide the list of python files that go along with
1053  # this module
1054  set_property(TARGET "${_vtk_add_python_package_module}-${_vtk_add_python_package_PACKAGE}"
1055  PROPERTY
1056  "python_modules" "${_vtk_add_python_package_file_outputs}")
1057 endfunction ()
1058 
1059 #[==[
1060 @ingroup module-wrapping-python
1061 @brief Use a Python package as a module
1062 
1063 If a module is a Python package, this function should be used instead of
1064 @ref vtk_module_add_module.
1065 
1066 ~~~
1067 vtk_module_add_python_module(<name>
1068  PACKAGES <packages>...)
1069 ~~~
1070 
1071  * `PACKAGES`: (Required) The list of packages installed by this module.
1072  These must have been created by the @ref vtk_module_add_python_package
1073  function.
1074 #]==]
1075 function (vtk_module_add_python_module name)
1076  if (NOT name STREQUAL _vtk_build_module)
1077  message(FATAL_ERROR
1078  "Python modules must match their module names.")
1079  endif ()
1080 
1081  cmake_parse_arguments(_vtk_add_python_module
1082  ""
1083  ""
1084  "PACKAGES"
1085  ${ARGN})
1086 
1087  if (_vtk_add_python_module_UNPARSED_ARGUMENTS)
1088  message(FATAL_ERROR
1089  "Unparsed arguments for vtk_module_add_python_module: "
1090  "${_vtk_add_python_module_UNPARSED_ARGUMENTS}")
1091  endif ()
1092 
1093  get_property(_vtk_add_python_module_depends GLOBAL
1094  PROPERTY "_vtk_module_${_vtk_build_module}_depends")
1095  get_property(_vtk_add_python_module_target_name GLOBAL
1096  PROPERTY "_vtk_module_${_vtk_build_module}_target_name")
1097  add_library("${_vtk_add_python_module_target_name}" INTERFACE)
1098  target_link_libraries("${_vtk_add_python_module_target_name}"
1099  INTERFACE
1100  ${_vtk_add_python_module_depends})
1101  if (NOT _vtk_build_module STREQUAL _vtk_add_python_module_target_name)
1102  add_library("${_vtk_build_module}" ALIAS
1103  "${_vtk_add_python_module_target_name}")
1104  endif ()
1105  foreach (_vtk_add_python_module_package IN LISTS _vtk_add_python_module_PACKAGES)
1106  add_dependencies("${_vtk_add_python_module_target_name}"
1107  "${_vtk_build_module}-${_vtk_add_python_module_package}")
1108 
1109  # get the list of python files and add them on the module.
1110  get_property(_vtk_module_python_modules
1111  TARGET "${_vtk_add_python_module_target_name}-${_vtk_add_python_module_package}"
1112  PROPERTY "python_modules")
1113  _vtk_module_set_module_property("${_vtk_build_module}" APPEND
1114  PROPERTY "python_modules"
1115  VALUE "${_vtk_module_python_modules}")
1116  endforeach ()
1117 
1118  _vtk_module_apply_properties("${_vtk_add_python_module_target_name}")
1119  _vtk_module_install("${_vtk_add_python_module_target_name}")
1120 endfunction ()
boost::graph_traits< vtkGraph * >::vertex_descriptor target(boost::graph_traits< vtkGraph *>::edge_descriptor e, vtkGraph *)
function _vtk_module_get_module_property(module)
Get a module property
function vtk_module_add_python_module(name)
Use a Python package as a module
Specialization of tuple ranges and iterators for vtkAOSDataArrayTemplate.
boost::graph_traits< vtkGraph * >::vertex_descriptor source(boost::graph_traits< vtkGraph *>::edge_descriptor e, vtkGraph *)
function _vtk_module_wrap_python_sources(module, sources, classes)
Generate sources for using a module&#39;s classes from Python
function vtk_module_wrap_python()
Wrap a set of modules for use in Python
function vtk_module_get_property(module)
Get a property from a module
function _vtk_module_split_module_name(name, prefix)
Split a module name into a namespace and target component
function vtk_module_set_property(module)
Set a property on a module
function vtk_module_add_python_package(name)
Install Python packages with a module
function vtk_module_python_default_destination(var)
Determine Python module destination