Cylinders modeled as multi-domain assemblies#

A MultiDomain assembly connects Shell domains, see panels.multidomain.connections. The function create_cylinder() creates a cylinder with panels along its circumference, connecting the last panel to the first one to close the cylinder.

The connections are imposed exactly with the default conn_method='null-space', see Exact connections with the null-space method, or with penalty stiffnesses with conn_method='penalty'. The closed cylinder below gives -47113.0 N/m with the null-space method and -47056.0 N/m with the default penalty constants, see tests/multidomain/test_null_space.py and tests/multidomain/test_cylinder.py.

Linear buckling with a constant axial compression Nxx in each panel, calculated with cylinder_compression_lb_Nxx_cte():

def test_cylinder_compression_lb_Nxx_cte():
    print('Testing assembly function: cylinder_compression_lb_Nxx_cte')
    height = 0.500
    r = 0.250
    npanels = 5
    Nxxs = [-100.]*npanels
    assy, eigvals, eigvecs = cylinder_compression_lb_Nxx_cte(
        height=height,
        r=r,
        plyt=0.125e-3,
        stack=[0, 45, -45, 90, -45, 45],
        laminaprop=(142.5e9, 8.7e9, 0.28, 5.1e9, 5.1e9, 5.1e9),
        npanels=npanels,
        Nxxs=Nxxs,
        m=8, n=12,
        num_eigvalues=10, conn_method='penalty')

    assy.plot(eigvecs[:, 0], 'skin', filename='tmp_cylinder_compression_lb_Nxx_cte.png')

    #NOTE Sanders kinematics, the default for cylinders, the Donnell
    #     kinematics gave -47319.181
    assert np.isclose(Nxxs[0]*eigvals[0], -47055.984, atol=0.01, rtol=0.001)

Linear buckling with the pre-buckling stress state calculated from a static analysis, with cylinder_compression_lb_Nxx_from_static():

def test_cylinder_compression_lb_Nxx_from_static():
    print('Testing assembly function: cylinder_compression_lb_Nxx_from_static')
    height = 0.500
    r = 0.250
    npanels = 5
    Nxxs = [-100.]*npanels
    assy, c, eigvals, eigvecs = cylinder_compression_lb_Nxx_from_static(
        height=height,
        r=r,
        plyt=0.125e-3,
        stack=[0, 45, -45, 90, -45, 45],
        laminaprop=(142.5e9, 8.7e9, 0.28, 5.1e9, 5.1e9, 5.1e9),
        npanels=npanels,
        Nxxs=Nxxs,
        m=8, n=12,
        num_eigvalues=10, conn_method='penalty')

    assy.plot(c, 'skin', filename='tmp_cylinder_compression_lb_Nxx_from_static_c.png')
    assy.plot(eigvecs[:, 0], 'skin', filename='tmp_cylinder_compression_lb_Nxx_from_static_eigvec.png')

    #NOTE Sanders kinematics, the default for cylinders, the Donnell
    #     kinematics gave -47417.912
    assert np.isclose(Nxxs[0]*eigvals[0], -47162.406, atol=0.01, rtol=0.001)

Blade stiffeners can be added along the length of the cylinder, modeled as additional domains connected to the skin, see create_cylinder_blade_stiffened():

def test_cylinder_blade_stiffened_compression_lb_Nxx_from_static():
    print('Testing assembly function: cylinder_blade_stiffened_compression_lb_Nxx_from_static')
    height = 0.500
    r = 0.250
    npanels = 5
    Nxxs = [-100.]*npanels
    assy, c, eigvals, eigvecs = cylinder_blade_stiffened_compression_lb_Nxx_from_static(
        height=height,
        r=r,
        plyt=0.125e-3,
        stack=[0, 45, -45, 90, -45, 45],
        stack_blades=[[0, 90, 0]*4]*npanels,
        width_blades=[0.02]*npanels,
        laminaprop=(142.5e9, 8.7e9, 0.28, 5.1e9, 5.1e9, 5.1e9),
        npanels=npanels,
        Nxxs_skin=Nxxs,
        Nxxs_blade=Nxxs,
        m=8, n=12,
        num_eigvalues=10, conn_method='penalty')

    assy.plot(c, 'skin', vec='u', filename='tmp_cylinder_blade_stiffened_compression_lb_Nxx_from_static_u.png', colorbar=True)
    assy.plot(c, 'skin', vec='w', filename='tmp_cylinder_blade_stiffened_compression_lb_Nxx_from_static_w.png', colorbar=True)
    assy.plot(c, 'skin', vec='Nxx', filename='tmp_cylinder_blade_stiffened_compression_lb_Nxx_from_static_Nxx.png', colorbar=True)
    assy.plot(c, 'skin', vec='Nyy', filename='tmp_cylinder_blade_stiffened_compression_lb_Nxx_from_static_Nyy.png', colorbar=True)
    assy.plot(eigvecs[:, 0], 'skin', filename='tmp_cylinder_blade_stiffened_compression_lb_Nxx_from_static_eigvec.png')

    #NOTE Sanders kinematics, the default for cylinders, the Donnell
    #     kinematics gave -40003, and -39921.838 with the rotation of
    #     'BFycte' without the term v/r of the Sanders kinematics
    assert np.isclose(Nxxs[0]*eigvals[0], -39993.838, atol=0.01, rtol=0.001)