Ejemplo n.º 1
0
    def test_case_compute_geomerty_from_state(self, n_elem, nu=0):
        """
        This test case, tests compute_geometry_from_state
        function by comparing with analytical solution.
        :param n_elem:
        :param nu:
        :return:
        """

        initial, test_rod = constructor(n_elem, nu)
        position, rest_lengths, tangents, radius = compute_geometry_analytically(
            n_elem)
        # Compute geometry from state
        _compute_geometry_from_state(
            test_rod.position_collection,
            test_rod.volume,
            test_rod.lengths,
            test_rod.tangents,
            test_rod.radius,
        )

        assert_allclose(test_rod.rest_lengths,
                        rest_lengths,
                        atol=Tolerance.atol())
        assert_allclose(test_rod.lengths, rest_lengths,
                        atol=Tolerance.atol())  # no dilatation
        assert_allclose(test_rod.tangents, tangents, atol=Tolerance.atol())
        assert_allclose(test_rod.radius, radius, atol=Tolerance.atol())
    def test_case_compute_all_dilatations(self, n_elem, dilatation):
        """
        This test case, tests compute_all_dilatations
        function by comparing with analytical solution.
        :param n_elem:
        :param dilatation:
        :return:
        """

        initial, test_rod = constructor(n_elem)

        (
            dilatation_collection,
            voronoi_dilatation,
            lengths,
            rest_voronoi_lengths,
        ) = compute_all_dilatations_analytically(n_elem, dilatation)

        test_rod.position_collection *= dilatation
        # Compute dilatation using compute_all_dilatations
        # Compute geometry again because node positions changed.
        # But compute geometry will be done inside compute_all_dilatations.
        test_rod._compute_all_dilatations()

        assert_allclose(test_rod.lengths, lengths, atol=Tolerance.atol())
        assert_allclose(test_rod.rest_voronoi_lengths,
                        rest_voronoi_lengths,
                        atol=Tolerance.atol())
        assert_allclose(test_rod.dilatation,
                        dilatation_collection,
                        atol=Tolerance.atol())
        assert_allclose(test_rod.voronoi_dilatation,
                        voronoi_dilatation,
                        atol=Tolerance.atol())
Ejemplo n.º 3
0
    def test_explicit_steppers(self, explicit_stepper):
        collective_system = ScalarExponentialDampedHarmonicOscillatorCollectiveSystem(
        )
        final_time = 1.0
        n_steps = 500
        stepper = explicit_stepper()

        dt = np.float64(float(final_time) / n_steps)
        time = np.float64(0.0)
        tol = Tolerance.atol()

        # Before stepping, let's extend the interface of the stepper
        # while providing memory slots
        from elastica.systems import make_memory_for_explicit_stepper

        memory_collection = make_memory_for_explicit_stepper(
            stepper, collective_system)
        from elastica.timestepper import extend_stepper_interface

        extend_stepper_interface(stepper, collective_system)

        while np.abs(final_time - time) > 1e5 * tol:
            time = stepper.do_step(collective_system, memory_collection, time,
                                   dt)

        for system in collective_system:
            assert_allclose(
                system.state,
                system.analytical_solution(final_time),
                rtol=Tolerance.rtol(),
                atol=Tolerance.atol(),
            )
Ejemplo n.º 4
0
def test_cylinder_compute_internal_forces_and_torques():
    """
    This is test is checking the validity of _compute_internal_forces_and_torques function.

    Returns
    -------

    """
    start = np.random.rand(3)
    direction = 5 * np.random.rand(3)
    direction_norm = np.linalg.norm(direction)
    direction /= direction_norm
    normal = np.array((direction[1], -direction[0], 0))
    base_length = 10
    base_radius = np.random.uniform(1, 10)
    density = np.random.uniform(1, 10)
    test_cylinder = Cylinder(start, direction, normal, base_length,
                             base_radius, density)

    test_cylinder._compute_internal_forces_and_torques(time=0)

    assert_allclose(np.zeros((3, 1)),
                    test_cylinder.internal_forces,
                    atol=Tolerance.atol())
    assert_allclose(np.zeros((3, 1)),
                    test_cylinder.internal_torques,
                    atol=Tolerance.atol())
def test_free_rod():
    test_rod = TestRod()
    free_rod = FreeRod()
    test_position_collection = np.random.rand(3, 20)
    test_rod.position_collection = (
        test_position_collection.copy()
    )  # We need copy of the list not a reference to this array
    test_director_collection = np.random.rand(3, 3, 20)
    test_rod.director_collection = (
        test_director_collection.copy()
    )  # We need copy of the list not a reference to this array
    free_rod.constrain_values(test_rod, time=0)
    assert_allclose(test_position_collection,
                    test_rod.position_collection,
                    atol=Tolerance.atol())
    assert_allclose(test_director_collection,
                    test_rod.director_collection,
                    atol=Tolerance.atol())

    test_velocity_collection = np.random.rand(3, 20)
    test_rod.velocity_collection = (
        test_velocity_collection.copy()
    )  # We need copy of the list not a reference to this array
    test_omega_collection = np.random.rand(3, 20)
    test_rod.omega_collection = (
        test_omega_collection.copy()
    )  # We need copy of the list not a reference to this array
    free_rod.constrain_rates(test_rod, time=0)
    assert_allclose(test_velocity_collection,
                    test_rod.velocity_collection,
                    atol=Tolerance.atol())
    assert_allclose(test_omega_collection,
                    test_rod.omega_collection,
                    atol=Tolerance.atol())
Ejemplo n.º 6
0
def test_muscle_torques(n_elem):
    # tests muscle torques
    dim = 3

    mock_rod = MockRod()
    mock_rod.external_torques = np.zeros((dim, n_elem))
    mock_rod.n_elems = n_elem
    mock_rod.director_collection = np.repeat(
        np.identity(3)[:, :, np.newaxis], n_elem, axis=2
    )

    base_length = 1.0
    mock_rod.rest_lengths = np.ones(n_elem) * base_length / n_elem

    # We wont need beta coefficients, thus we are setting them to zero.
    # The reason is that, we wont use beta spline for this test case.
    # Beta spline function does not have any pytest, It is compared with
    # Elastica cpp beta spline and coefficients are optimized using CMA-ES.
    b_coeff = np.zeros((n_elem))

    # Torque = sin(2pi*t/T + 2pi*s/lambda + phi)
    # Torque = sin(pi/2 + s) = cos(s) using the below variables
    # we will make torque as function of position only nothing else!
    period = 8.0
    wave_length = 2.0 * np.pi
    wave_number = 2.0 * np.pi / (wave_length)
    phase_shift = np.pi / 4
    ramp_up_time = 0.5  # this has to be smaller than 1. Since I will set t equal to 1
    time = 1.0

    position = np.linspace(0, base_length, n_elem + 1)
    torque = np.array([np.cos(position), np.cos(position), np.cos(position)])[..., 1:-1]
    # Torque function is opposite direction in elastica cpp. Thus we need to invert the torque profile.
    torque = torque[..., ::-1]
    correct_torque = np.zeros((dim, n_elem))
    correct_torque[..., :-1] -= torque
    correct_torque[..., 1:] += torque

    # Set an a non-physical direction to check math
    direction = np.array([1.0, 1.0, 1.0])

    # Apply torques
    muscletorques = MuscleTorques(
        base_length,
        b_coeff,
        period,
        wave_number,
        phase_shift,
        direction,
        mock_rod.rest_lengths,
        ramp_up_time,
        with_spline=False,
    )
    muscletorques.apply_torques(mock_rod, time)

    # Total torque has to be zero on the body
    assert_allclose(mock_rod.external_torques[..., :].sum(), 0.0, atol=Tolerance.atol())

    # Torques on elements
    assert_allclose(mock_rod.external_torques, correct_torque, atol=Tolerance.atol())
Ejemplo n.º 7
0
    def test_call_back_base_class(self):
        """
        This test case tests, base class for call functions. make_callback
        does not do anything, but for completion this test case is here.
        Returns
        -------

        """

        mock_rod = MockRod()

        time = 0.0
        current_step = 0
        callbackbase = CallBackBaseClass()
        callbackbase.make_callback(mock_rod, time, current_step)

        assert_allclose(mock_rod.position_collection,
                        0.0,
                        atol=Tolerance.atol())
        assert_allclose(mock_rod.velocity_collection,
                        0.0,
                        atol=Tolerance.atol())
        assert_allclose(mock_rod.director_collection,
                        0.0,
                        atol=Tolerance.atol())
        assert_allclose(mock_rod.external_forces, 0.0, atol=Tolerance.atol())
        assert_allclose(mock_rod.external_torques, 0.0, atol=Tolerance.atol())
Ejemplo n.º 8
0
    def test_compute_damping_forces_torques(self, n_elem, nu):
        """
        In this test case, we initialize a straight rod and modify
        velocities of nodes and angular velocities of elements.
        By doing that we can test damping forces on nodes and
        damping torques on elements.
        This test function tests
            _compute_damping_forces
            _compute_damping_torques
        """
        # This is an artificial test, this part exists just to
        # keep our coverage percentage.

        initial, test_rod = constructor(n_elem, nu)
        # Construct velocity and omega
        test_rod.velocity_collection[:] = 1.0
        test_rod.omega_collection[:] = 1.0
        # Compute damping forces and torques
        damping_forces = (np.repeat(
            np.array([1.0, 1.0, 1.0])[:, np.newaxis], n_elem + 1, axis=1) *
                          nu * (1.0 / n_elem))
        damping_forces[..., 0] *= 0.5
        damping_forces[..., -1] *= 0.5
        damping_torques = (np.repeat(
            np.array([1.0, 1.0, 1.0])[:, np.newaxis], n_elem, axis=1) * nu *
                           (1.0 / n_elem))
        # Compute geometry from state
        _compute_geometry_from_state(
            test_rod.position_collection,
            test_rod.volume,
            test_rod.lengths,
            test_rod.tangents,
            test_rod.radius,
        )
        # Compute damping forces and torques using in class functions
        _compute_damping_forces(
            test_rod.damping_forces,
            test_rod.velocity_collection,
            test_rod.dissipation_constant_for_forces,
            test_rod.lengths,
            test_rod.ghost_elems_idx,
        )
        _compute_damping_torques(
            test_rod.damping_torques,
            test_rod.omega_collection,
            test_rod.dissipation_constant_for_torques,
            test_rod.lengths,
        )

        test_damping_forces = test_rod.damping_forces
        test_damping_torques = test_rod.damping_torques
        # Compare damping forces and torques computed using in class functions and above
        assert_allclose(test_damping_forces,
                        damping_forces,
                        atol=Tolerance.atol())
        assert_allclose(test_damping_torques,
                        damping_torques,
                        atol=Tolerance.atol())
Ejemplo n.º 9
0
 def test_nodes_to_elements(self, n_elem):
     random_vector = np.random.rand(3).reshape(3, 1)
     input = np.repeat(random_vector, n_elem + 1, axis=1)
     input[..., 0] *= 0.5
     input[..., -1] *= 0.5
     correct_output = np.repeat(random_vector, n_elem, axis=1)
     output = nodes_to_elements(input)
     assert_allclose(correct_output, output, atol=Tolerance.atol())
     assert_allclose(np.sum(input), np.sum(output), atol=Tolerance.atol())
Ejemplo n.º 10
0
    def test_update_acceleration(self, n_elem):
        """
        In this test case, we initialize a straight rod.
        We set correct parameters for rod mass, dilatation, mass moment of inertia
        and call the function update_accelerations and compare the angular and
        translational acceleration with the correct values.
        This test case tests,
            update_accelerations
            _update_accelerations

        """

        initial, test_rod = constructor(n_elem, nu=0.0)
        mass = test_rod.mass

        external_forces = np.zeros(3 * (n_elem + 1)).reshape(3, n_elem + 1)
        external_torques = np.zeros(3 * n_elem).reshape(3, n_elem)

        for i in range(0, n_elem):
            external_torques[..., i] = np.random.rand(3)

        for i in range(0, n_elem + 1):
            external_forces[..., i] = np.random.rand(3)

        test_rod.external_forces[:] = external_forces
        test_rod.external_torques[:] = external_torques

        # No dilatation in the rods
        dilatations = np.ones(n_elem)

        # Set mass moment of inertia matrix to identity matrix for convenience.
        # Inverse of identity = identity
        inv_mass_moment_of_inertia = np.repeat(np.identity(3)[:, :,
                                                              np.newaxis],
                                               n_elem,
                                               axis=2)
        test_rod.inv_mass_second_moment_of_inertia[:] = inv_mass_moment_of_inertia

        # Compute acceleration
        test_rod.update_accelerations(time=0)

        correct_acceleration = external_forces / mass
        assert_allclose(
            test_rod.acceleration_collection,
            correct_acceleration,
            atol=Tolerance.atol(),
        )

        correct_angular_acceleration = (
            _batch_matvec(inv_mass_moment_of_inertia, external_torques) *
            dilatations)

        assert_allclose(
            test_rod.alpha_collection,
            correct_angular_acceleration,
            atol=Tolerance.atol(),
        )
def test_block_structure_dynamic_state_references(n_rods):
    """
    This function is testing validity of dynamic state views and compare them
    with the block structure vectors.

    Parameters
    ----------
    n_rods

    Returns
    -------

    """
    world_rods = [
        MockRod(np.random.randint(10, 30 + 1)) for _ in range(n_rods)
    ]
    block_structure = BlockStructureWithSymplecticStepper(world_rods)

    assert_allclose(
        block_structure.velocity_collection,
        block_structure.dynamic_states.velocity_collection,
        atol=Tolerance.atol(),
    )
    assert np.shares_memory(
        block_structure.velocity_collection,
        block_structure.dynamic_states.velocity_collection,
    )

    assert_allclose(
        block_structure.omega_collection,
        block_structure.dynamic_states.omega_collection,
        atol=Tolerance.atol(),
    )
    assert np.shares_memory(
        block_structure.omega_collection,
        block_structure.dynamic_states.omega_collection,
    )

    assert_allclose(
        block_structure.v_w_collection,
        block_structure.dynamic_states.rate_collection,
        atol=Tolerance.atol(),
    )
    assert np.shares_memory(block_structure.v_w_collection,
                            block_structure.dynamic_states.rate_collection)

    assert_allclose(
        block_structure.dvdt_dwdt_collection,
        block_structure.dynamic_states.dvdt_dwdt_collection,
        atol=Tolerance.atol(),
    )
    assert np.shares_memory(
        block_structure.dvdt_dwdt_collection,
        block_structure.dynamic_states.dvdt_dwdt_collection,
    )
Ejemplo n.º 12
0
    def test_symplectic_against_undamped_harmonic_oscillator(self, stepper):
        system = SymplecticUndampedSimpleHarmonicOscillatorSystem()
        final_time = 4.0 * np.pi
        n_steps = 2000
        integrate(stepper(), system, final_time=final_time, n_steps=n_steps)

        # Symplectic systems conserve energy to a certain extent
        assert_allclose(
            *system.compute_energy(final_time),
            rtol=Tolerance.rtol() * 1e1,
            atol=Tolerance.atol(),
        )
Ejemplo n.º 13
0
    def initializer(
            self,
            n_elem,
            static_mu_array=np.array([0.0, 0.0, 0.0]),
            kinetic_mu_array=np.array([0.0, 0.0, 0.0]),
            force_mag_long=0.0,  # forces along the rod
            force_mag_side=0.0,  # side forces on the rod
    ):

        rod = BaseRodClass(n_elem)

        origin_plane = np.array([0.0, -rod.radius[0], 0.0])
        normal_plane = np.array([0.0, 1.0, 0.0])
        slip_velocity_tol = 1e-2
        friction_plane = AnisotropicFrictionalPlane(
            0.0,
            0.0,
            origin_plane,
            normal_plane,
            slip_velocity_tol,
            static_mu_array,  # forward, backward, sideways
            kinetic_mu_array,  # forward, backward, sideways
        )
        fnormal = (10.0 - 5.0) * np.random.random_sample(
            1).item() + 5.0  # generates random numbers [5.0,10)
        external_forces = np.array([force_mag_side, -fnormal, force_mag_long])

        external_forces_collection = np.repeat(external_forces.reshape(3, 1),
                                               n_elem + 1,
                                               axis=1)
        external_forces_collection[..., 0] *= 0.5
        external_forces_collection[..., -1] *= 0.5
        rod.external_forces = external_forces_collection.copy()

        # Velocities has to be set to zero
        assert_allclose(np.zeros((3, n_elem)),
                        rod.omega_collection,
                        atol=Tolerance.atol())
        assert_allclose(np.zeros((3, n_elem + 1)),
                        rod.velocity_collection,
                        atol=Tolerance.atol())

        # We have not changed torques also, they have to be zero as well
        assert_allclose(np.zeros((3, n_elem)),
                        rod.external_torques,
                        atol=Tolerance.atol())
        assert_allclose(
            np.zeros((3, n_elem)),
            rod._compute_internal_torques(),
            atol=Tolerance.atol(),
        )

        return rod, friction_plane, external_forces_collection
Ejemplo n.º 14
0
    def test_against_scalar_exponential(self, stepper):
        system = ScalarExponentialDecaySystem(-1, 1)
        final_time = 1
        n_steps = 1000
        integrate(stepper(), system, final_time=final_time, n_steps=n_steps)

        assert_allclose(
            system.state,
            system.analytical_solution(final_time),
            rtol=Tolerance.rtol() * 1e3,
            atol=Tolerance.atol(),
        )
Ejemplo n.º 15
0
    def test_against_damped_harmonic_oscillator(self, stepper):
        system = DampedSimpleHarmonicOscillatorSystem()
        final_time = 4.0 * np.pi
        n_steps = 2000
        integrate(stepper(), system, final_time=final_time, n_steps=n_steps)

        assert_allclose(
            system.state,
            system.analytical_solution(final_time),
            rtol=Tolerance.rtol(),
            atol=Tolerance.atol(),
        )
def test_block_structure_kinematic_update(n_rods):
    """
    This function is testing validity __iadd__ operation of kinematic_states.

    Parameters
    ----------
    n_rods

    Returns
    -------

    """

    world_rods = [
        MockRod(np.random.randint(10, 30 + 1)) for _ in range(n_rods)
    ]
    block_structure = BlockStructureWithSymplecticStepper(world_rods)

    position = block_structure.position_collection.copy()
    velocity = block_structure.velocity_collection.copy()

    directors = block_structure.director_collection.copy()
    omega = block_structure.omega_collection.copy()

    prefac = np.random.randn()

    correct_position = position + prefac * velocity
    correct_director = np.zeros(directors.shape)
    np.einsum(
        "ijk,jlk->ilk",
        _get_rotation_matrix(1.0, prefac * omega),
        directors.copy(),
        out=correct_director,
    )

    # block_structure.kinematic_states += block_structure.kinematic_rates(0, prefac)

    overload_operator_kinematic_numba(
        block_structure.n_nodes,
        prefac,
        block_structure.position_collection,
        block_structure.director_collection,
        block_structure.velocity_collection,
        block_structure.omega_collection,
    )

    assert_allclose(correct_position,
                    block_structure.position_collection,
                    atol=Tolerance.atol())
    assert_allclose(correct_director,
                    block_structure.director_collection,
                    atol=Tolerance.atol())
Ejemplo n.º 17
0
def test_get_rotation_matrix_gives_orthonormal_matrices():
    dim = 3
    blocksize = 16
    dt = np.random.random_sample()
    rot_mat = _get_rotation_matrix(dt, np.random.randn(dim, blocksize))

    r_rt = np.einsum("ijk,ljk->ilk", rot_mat, rot_mat)
    rt_r = np.einsum("jik,jlk->ilk", rot_mat, rot_mat)

    test_mat = np.array([np.eye(dim) for _ in range(blocksize)]).T
    # We can't get there fully, but 1e-15 suffices in precision
    assert_allclose(r_rt, test_mat, atol=Tolerance.atol())
    assert_allclose(rt_r, test_mat, atol=Tolerance.atol())
Ejemplo n.º 18
0
    def test_explicit_against_analytical_system(self, explicit_stepper):
        system = SecondOrderHybridSystem()
        final_time = 1.0
        n_steps = 2000
        integrate(explicit_stepper(),
                  system,
                  final_time=final_time,
                  n_steps=n_steps)

        assert_allclose(
            system.final_solution(final_time),
            system.analytical_solution(final_time),
            rtol=Tolerance.rtol() * 1e2,
            atol=Tolerance.atol(),
        )
Ejemplo n.º 19
0
    def test_hybrid_symplectic_against_analytical_system(
            self, symplectic_stepper):
        system = SecondOrderHybridSystem()
        final_time = 1.0
        n_steps = 2000
        stepper = SymplecticCosseratRodStepper(
            symplectic_stepper=symplectic_stepper())
        integrate(stepper, system, final_time=final_time, n_steps=n_steps)

        assert_allclose(
            system.final_solution(final_time),
            system.analytical_solution(final_time),
            rtol=Tolerance.rtol() * 1e2,
            atol=Tolerance.atol(),
        )
Ejemplo n.º 20
0
    def test_explicit_steppers(self, explicit_stepper):
        collective_system = ScalarExponentialDampedHarmonicOscillatorCollectiveSystem(
        )
        final_time = 1.0
        if explicit_stepper == EulerForward:
            # Euler requires very small time-steps and in order not to slow down test,
            # we are scaling the difference between analytical and numerical solution.
            n_steps = 25000
            scale = 1e3
        else:
            n_steps = 500
            scale = 1

        stepper = explicit_stepper()

        dt = np.float64(float(final_time) / n_steps)
        time = np.float64(0.0)
        tol = Tolerance.atol()

        # Before stepping, let's extend the interface of the stepper
        # while providing memory slots
        from elastica._elastica_numpy._systems import make_memory_for_explicit_stepper

        memory_collection = make_memory_for_explicit_stepper(
            stepper, collective_system)
        from elastica._elastica_numpy._timestepper import extend_stepper_interface

        do_step, stagets_and_updates = extend_stepper_interface(
            stepper, collective_system)

        while np.abs(final_time - time) > 1e5 * tol:
            # time = stepper.do_step(collective_system, memory_collection, time, dt)
            time = do_step(
                stepper,
                stagets_and_updates,
                collective_system,
                memory_collection,
                time,
                dt,
            )

        for system in collective_system:
            assert_allclose(
                system.state,
                system.analytical_solution(final_time),
                rtol=Tolerance.rtol() * scale,
                atol=Tolerance.atol() * scale,
            )
Ejemplo n.º 21
0
    def test_axial_kinetic_friction(self, n_elem, velocity):
        """
        This function tests kinetic friction in forward and backward direction.
        All other friction coefficients set to zero.
        Parameters
        ----------
        n_elem
        velocity

        Returns
        -------

        """

        [rod, friction_plane, external_forces_collection
         ] = self.initializer(n_elem,
                              kinetic_mu_array=np.array([1.0, 1.0, 0.0]))

        rod.velocity_collection += np.array([0.0, 0.0, velocity]).reshape(3, 1)

        friction_plane.apply_forces(rod)

        direction_collection = np.repeat(np.array([0.0, 0.0,
                                                   1.0]).reshape(3, 1),
                                         n_elem + 1,
                                         axis=1)
        correct_forces = (-1.0 * np.sign(velocity) *
                          np.linalg.norm(external_forces_collection, axis=0) *
                          direction_collection)
        assert_allclose(correct_forces,
                        rod.external_forces,
                        atol=Tolerance.atol())
Ejemplo n.º 22
0
    def test_case_compute_translational_energy(self, n_elem, nu=0):
        """
        This function tests compute translational energy function. We
        take an initial input energy for the rod and compute the velocity and
        set the velocity of rod elements. We call compute_translational_energy
        function and compare the result with output energy.
        Note here we are only setting the y velocity of the rod, x and z velocity
        are zero.
        Parameters
        ----------
        n_elem
        nu

        Returns
        -------

        """

        initial, test_rod = constructor(n_elem, nu)
        base_length = 1.0
        base_radius = 0.25
        density = 1.0
        mass = base_length * np.pi * base_radius * base_radius * density

        input_energy = 10
        velocity = np.sqrt(2 * input_energy / mass)

        test_rod.velocity_collection[1, :] = velocity

        output_energy = test_rod.compute_translational_energy()

        assert_allclose(output_energy, input_energy, atol=Tolerance.atol())
Ejemplo n.º 23
0
    def test_interaction_plane_without_k_with_nu(self, n_elem, nu_w):
        """
        Here wall damping coefficient are changed parametrically and
        wall response functions tested.
        Parameters
        ----------
        n_elem
        nu_w

        Returns
        -------

        """

        [rod, interaction_plane, external_forces] = self.initializer(n_elem,
                                                                     nu_w=nu_w)

        normal_velocity = np.random.random_sample(1).item()
        rod.velocity_collection[..., :] += np.array(
            [0.0, -normal_velocity, 0.0]).reshape(3, 1)

        correct_forces = np.repeat(
            (nu_w * np.array([0.0, normal_velocity, 0.0])).reshape(3, 1),
            n_elem + 1,
            axis=1,
        )

        correct_forces[..., 0] *= 0.5
        correct_forces[..., -1] *= 0.5

        interaction_plane.apply_normal_force(rod)

        assert_allclose(correct_forces,
                        rod.external_forces,
                        atol=Tolerance.atol())
Ejemplo n.º 24
0
    def test_case_compute_internal_shear_stretch_stresses_from_model(
            self, n_elem, dilatation):
        """
        This test case initializes a straight rod. We modify node positions
        and compress the rod numerically. By doing that we impose shear stress
        in the rod and check, computation stresses.
        This test function tests
            _compute_internal_shear_stretch_stresses_from_model
        """

        initial, test_rod = constructor(n_elem)
        test_rod.position_collection *= dilatation
        internal_stress = compute_stress_analytically(n_elem, dilatation)

        _compute_internal_shear_stretch_stresses_from_model(
            test_rod.position_collection,
            test_rod.volume,
            test_rod.lengths,
            test_rod.tangents,
            test_rod.radius,
            test_rod.rest_lengths,
            test_rod.rest_voronoi_lengths,
            test_rod.dilatation,
            test_rod.voronoi_dilatation,
            test_rod.director_collection,
            test_rod.sigma,
            test_rod.rest_sigma,
            test_rod.shear_matrix,
            test_rod.internal_stress,
        )

        assert_allclose(test_rod.internal_stress,
                        internal_stress,
                        atol=Tolerance.atol())
Ejemplo n.º 25
0
    def test_interaction_when_rod_is_under_plane(self, n_elem):
        """
        This test case tests plane response forces on the rod
        in the case rod is under the plane and pushed towards
        the plane.
        Parameters
        ----------
        n_elem

        Returns
        -------

        """

        # we move plane on top of the rod. Note that 0.25 is radius of the rod.
        offset_of_plane_with_respect_to_rod = 2.0 * 0.25

        # plane normal changed, it is towards the negative direction, because rod
        # is under the rod.
        plane_normal = np.array([0.0, -1.0, 0.0])

        [rod, interaction_plane, external_forces
         ] = self.initializer(n_elem,
                              shift=offset_of_plane_with_respect_to_rod,
                              plane_normal=plane_normal)

        interaction_plane.apply_normal_force(rod)
        correct_forces = np.zeros((3, n_elem + 1))
        assert_allclose(correct_forces,
                        rod.external_forces,
                        atol=Tolerance.atol())
Ejemplo n.º 26
0
    def test_case_compute_position_center_of_mass(self, n_elem, nu=0.0):
        """
        This function tests compute position center of mass function. We initialize a
        random position vector and copy this vector to position_collection array. We call
        the compute_position_center_of_mass function and compare the output vector with
        our correct position vector which we initialize at the beginning.
        randomly the a vector for position
        Parameters
        ----------
        n_elem
        nu

        Returns
        -------

        """

        correct_position = np.random.rand(3) / (n_elem + 1)

        initial, test_rod = constructor(n_elem, nu)

        test_rod.position_collection[..., :] = np.array(
            correct_position).reshape(3, 1)
        output_position = test_rod.compute_position_center_of_mass()

        assert_allclose(output_position,
                        correct_position,
                        atol=Tolerance.atol())
Ejemplo n.º 27
0
    def test_slender_body_matrix_product_only_xy(self, n_elem):
        """
        This function test x and y component of the hydrodynamic force. Here tangents are
        set such that z component of 1/2*t`t matrix removed, and only x and y component
        is left. Also non-diagonal components of matrix are zero, since we choose tangent
        vector to remove non-diagonal components
        Parameters
        ----------
        n_elem

        Returns
        -------

        """
        dynamic_viscosity = 0.1
        [rod, slender_body_theory] = self.initializer(n_elem,
                                                      dynamic_viscosity)
        factor = -4 * np.pi * dynamic_viscosity / np.log(
            1 / 0.25) * rod.lengths[0]
        correct_forces = np.zeros((3, n_elem + 1))
        correct_forces[0, :] = factor
        correct_forces[1, :] = factor
        correct_forces[..., 0] *= 0.5
        correct_forces[..., -1] *= 0.5

        rod.tangents = np.repeat(np.array([0.0, 0.0,
                                           np.sqrt(2.0)])[:, np.newaxis],
                                 n_elem,
                                 axis=1)
        rod.velocity_collection = np.ones((3, n_elem + 1))
        slender_body_theory.apply_forces(rod)

        assert_allclose(correct_forces,
                        rod.external_forces,
                        atol=Tolerance.atol())
Ejemplo n.º 28
0
    def test_slender_body_theory_only_factor(self, n_elem, dynamic_viscosity):
        """
        This function test factors in front of the slender body theory equation

        factor = -4*pi*mu/log(L/r) * dL

        Parameters
        ----------
        n_elem
        dynamic_viscosity

        Returns
        -------

        """

        [rod, slender_body_theory] = self.initializer(n_elem,
                                                      dynamic_viscosity)
        length = rod.lengths.sum()
        radius = rod.radius[0]
        factor = (-4 * np.pi * dynamic_viscosity / np.log(length / radius) *
                  rod.lengths[0])
        correct_forces = np.ones((3, n_elem + 1)) * factor
        correct_forces[..., 0] *= 0.5
        correct_forces[..., -1] *= 0.5

        rod.tangents = np.zeros((3, n_elem))
        rod.velocity_collection = np.ones((3, n_elem + 1))
        slender_body_theory.apply_forces(rod)

        assert_allclose(correct_forces,
                        rod.external_forces,
                        atol=Tolerance.atol())
Ejemplo n.º 29
0
def test_compute_position_array_using_user_inputs():
    """
    This test checks if the allocate function can compute correctly
    position vector using start, direction and base length inputs.
    Returns
    -------

    """
    n_elems = 4
    start = np.array([0.0, 0.0, 0.0])
    direction = np.array([1.0, 0.0, 0.0])
    normal = np.array([0.0, 0.0, 1.0])
    base_length = 1.0
    base_radius = 0.25
    density = 1000
    nu = 0.1
    youngs_modulus = 1e6
    poisson_ratio = 0.3
    # Check if without input position vector, output position vector is valid
    mockrod = MockRodForTest.straight_rod(
        n_elems,
        start,
        direction,
        normal,
        base_length,
        base_radius,
        density,
        nu,
        youngs_modulus,
        poisson_ratio,
    )
    correct_position = np.zeros((3, n_elems + 1))
    correct_position[0, :] = np.array([0.0, 0.25, 0.5, 0.75, 1.0])
    test_position = mockrod.position_collection
    assert_allclose(correct_position, test_position, atol=Tolerance.atol())
Ejemplo n.º 30
0
    def test_axial_static_friction_total_force_larger_than_static_friction_force(
            self, n_elem, force_mag):
        """
        This test is for static friction when total forces applied
        on the rod is larger than the static friction force.
        Fx > F_normal*mu_s
        Parameters
        ----------
        n_elem
        force_mag

        Returns
        -------

        """

        [rod, frictionplane, external_forces_collection
         ] = self.initializer(n_elem,
                              static_mu_array=np.array([1.0, 1.0, 0.0]),
                              force_mag_long=force_mag)

        frictionplane.apply_forces(rod)
        correct_forces = np.zeros((3, n_elem + 1))
        if np.sign(force_mag) < 0:
            correct_forces[2] = (external_forces_collection[2]
                                 ) - 1.0 * external_forces_collection[1]
        else:
            correct_forces[2] = (external_forces_collection[2]
                                 ) + 1.0 * external_forces_collection[1]

        assert_allclose(correct_forces,
                        rod.external_forces,
                        atol=Tolerance.atol())