Coverage for src/beamme/mesh_creation_functions/nurbs_utils.py: 100%
20 statements
« prev ^ index » next coverage.py v7.10.3, created at 2025-08-11 12:17 +0000
« prev ^ index » next coverage.py v7.10.3, created at 2025-08-11 12:17 +0000
1# The MIT License (MIT)
2#
3# Copyright (c) 2018-2025 BeamMe Authors
4#
5# Permission is hereby granted, free of charge, to any person obtaining a copy
6# of this software and associated documentation files (the "Software"), to deal
7# in the Software without restriction, including without limitation the rights
8# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9# copies of the Software, and to permit persons to whom the Software is
10# furnished to do so, subject to the following conditions:
11#
12# The above copyright notice and this permission notice shall be included in
13# all copies or substantial portions of the Software.
14#
15# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21# THE SOFTWARE.
22"""This file has utility functions for handling NURBS."""
24import numpy as _np
26from beamme.core.conf import bme as _bme
27from beamme.core.rotation import Rotation as _Rotation
30def translate_splinepy(splinepy_obj, vector) -> None:
31 """Translate a splinepy object by a vector.
33 Args:
34 vector: _np.array, list
35 2D/3D vector to translate the splinepy object.
36 """
38 if not len(vector) == splinepy_obj.control_points.shape[1]:
39 raise ValueError(
40 f"Dimensions of translation vector and splinepy object do not match: {len(vector)} != {splinepy_obj.control_points.shape[1]}"
41 )
43 for point in splinepy_obj.control_points:
44 point += vector
47def rotate_splinepy(splinepy_obj, rotation: _Rotation, origin=None) -> None:
48 """Rotate a splinepy object by a rotation object."""
50 rotation_matrix = rotation.get_rotation_matrix()
52 dimension = splinepy_obj.control_points.shape[1]
53 if dimension == 2:
54 if not _np.allclose(
55 rotation_matrix[2, :], [0, 0, 1], rtol=0, atol=_bme.eps_quaternion
56 ) or not _np.allclose(
57 rotation_matrix[:, 2], [0, 0, 1], rtol=0, atol=_bme.eps_quaternion
58 ):
59 raise ValueError(
60 "Rotation vector must be in the x-y plane for 2D splinepy objects."
61 )
62 rotation_matrix = rotation_matrix[:2, :2]
64 if origin is None:
65 origin = _np.zeros(dimension)
67 for i_point, point in enumerate(splinepy_obj.control_points):
68 point_new = _np.dot(rotation_matrix, point - origin) + origin
69 splinepy_obj.control_points[i_point] = point_new