Beispiel #1
0
 def _get_explorer_config(self):
     from ibvpy.api import TLine, RTraceGraph, BCDof
     ec = super(MATS1DDamage, self)._get_explorer_config()
     ec['mats_eval'] = MATS1DDamage(E=1.0, epsilon_0=1.0, epsilon_f=5)
     ec['bcond_list'] = [
         BCDof(var='u',
               dof=0,
               value=1.7,
               time_function=lambda t: (1 + 0.1 * t) * sin(t))
     ]
     ec['tline'] = TLine(step=0.1, max=10)
     ec['rtrace_list'] = [
         RTraceGraph(name='strain - stress',
                     var_x='eps_app',
                     idx_x=0,
                     var_y='sig_app',
                     idx_y=0,
                     record_on='update'),
         RTraceGraph(name='time - damage',
                     var_x='time',
                     idx_x=0,
                     var_y='omega',
                     idx_y=0,
                     record_on='update')
     ]
     return ec
Beispiel #2
0
 def _get_explorer_config(self):
     from ibvpy.api import TLine, BCDof, RTraceGraph
     c = super(MATS1DPlastic, self)._get_explorer_config()
     # overload the default configuration
     c['bcond_list'] = [
         BCDof(var='u', dof=0, value=2.0, time_function=lambda t: sin(t))
     ]
     c['rtrace_list'] = [
         RTraceGraph(name='strain - stress',
                     var_x='eps_app',
                     idx_x=0,
                     var_y='sig_app',
                     idx_y=0,
                     record_on='update'),
         RTraceGraph(name='time - plastic_strain',
                     var_x='time',
                     idx_x=0,
                     var_y='eps_p',
                     idx_y=0,
                     record_on='update'),
         RTraceGraph(name='time - back stress',
                     var_x='time',
                     idx_x=0,
                     var_y='q',
                     idx_y=0,
                     record_on='update'),
         RTraceGraph(name='time - hardening',
                     var_x='time',
                     idx_x=0,
                     var_y='alpha',
                     idx_y=0,
                     record_on='update')
     ]
     c['tline'] = TLine(step=0.3, max=10)
     return c
Beispiel #3
0
    def _get_rt_list(self):
        '''Prepare the list of tracers
        '''
        right_dof = self.fe_grid[-1, -1].dofs[0, 0, 0]

        eps_app = RTraceDomainListField(name='Strain',
                                        position='int_pnts',
                                        var='eps_app',
                                        warp=False)

        damage = RTraceDomainListField(name='Damage',
                                       position='int_pnts',
                                       var='omega',
                                       warp=False)

        disp = RTraceDomainListField(name='Displacement',
                                     position='int_pnts',
                                     var='u',
                                     warp=False)

        sig_app = RTraceDomainListField(name='Stress',
                                        position='int_pnts',
                                        var='sig_app')

        rt_fu = RTraceGraph(name='Fi,right over u_right (iteration)',
                            var_y='F_int',
                            idx_y=right_dof,
                            var_x='U_k',
                            idx_x=right_dof)

        return [rt_fu, eps_app, damage, sig_app, disp]
Beispiel #4
0
def test_bar2():
    '''Clamped bar composed of two linked bars loaded at the right end
    [00]-[01]-[02]-[03]-[04]-[05]-[06]-[07]-[08]-[09]-[10]
    [11]-[12]-[13]-[14]-[15]-[16]-[17]-[18]-[19]-[20]-[21]
    u[0] = 0, u[5] = u[16], R[-1] = R[21] = 10
    '''
    fets_eval = FETS1D2L(mats_eval=MATS1DElastic(E=10., A=1.))

    # Discretization
    fe_domain1 = FEGrid(coord_max=(10., 0., 0.),
                        shape=(10, ),
                        n_nodal_dofs=1,
                        dof_r=fets_eval.dof_r,
                        geo_r=fets_eval.geo_r)

    fe_domain2 = FEGrid(coord_min=(10., 0., 0.),
                        coord_max=(20., 0., 0.),
                        shape=(10, ),
                        n_nodal_dofs=1,
                        dof_r=fets_eval.dof_r,
                        geo_r=fets_eval.geo_r)

    ts = TS(iterms=[(fets_eval, fe_domain1), (fets_eval, fe_domain2)],
            dof_resultants=True,
            bcond_list=[
                BCDof(var='u', dof=0, value=0.),
                BCDof(var='u',
                      dof=5,
                      link_dofs=[16],
                      link_coeffs=[1.],
                      value=0.),
                BCDof(var='f', dof=21, value=10)
            ],
            rtrace_list=[
                RTraceGraph(name='Fi,right over u_right (iteration)',
                            var_y='F_int',
                            idx_y=0,
                            var_x='U_k',
                            idx_x=1),
            ])

    # Add the time-loop control
    tloop = TLoop(tstepper=ts, tline=TLine(min=0.0, step=1, max=1.0))
    u = tloop.eval()
    print 'u', u
    #
    # '---------------------------------------------------------------'
    # 'Clamped bar composed of two linked bars control displ at right'
    # 'u[0] = 0, u[5] = u[16], u[21] = 1'
    # Remove the load and put a unit displacement at the right end
    # Note, the load is irrelevant in this case and will be rewritten
    #
    ts.bcond_list = [
        BCDof(var='u', dof=0, value=0.),
        BCDof(var='u', dof=5, link_dofs=[16], link_coeffs=[1.], value=0.),
        BCDof(var='u', dof=21, value=1.)
    ]
    # system solver
    u = tloop.eval()
    print 'u', u
Beispiel #5
0
 def _get_f_dof(self):
     return RTraceGraph(name='Fi,right over u_right (iteration)',
                        var_y='F_int',
                        idx_y=self.dof,
                        var_x='U_k',
                        idx_x=self.dof + 2,
                        record_on='update')
Beispiel #6
0
    def test_bar1(self):
        '''Clamped bar loaded at the right end with unit displacement
        [00]-[01]-[02]-[03]-[04]-[05]-[06]-[07]-[08]-[09]-[10]
        'u[0] = 0, u[10] = 1'''

        self.domain.coord_max = (10, 0, 0)
        self.domain.shape = (10, )
        self.ts.bcond_list = [
            BCDof(var='u', dof=0, value=0.),
            BCDof(var='u', dof=10, value=1.)
        ]
        self.ts.rtrace_list = [
            RTraceGraph(name='Fi,right over u_right (iteration)',
                        var_y='F_int',
                        idx_y=10,
                        var_x='U_k',
                        idx_x=10)
        ]

        u = self.tloop.eval()
        # expected solution
        u_ex = array([0., 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.],
                     dtype=float)
        difference = sqrt(norm(u - u_ex))
        self.assertAlmostEqual(difference, 0)
        # compare the reaction at the left end
        F = self.ts.F_int[0]
        self.assertAlmostEqual(F, -1)
Beispiel #7
0
    def example_3d():
        from ibvpy.mats.mats3D.mats3D_elastic.mats3D_elastic import MATS3DElastic
        from ibvpy.fets.fets3D.fets3D8h import FETS3D8H

        fets_eval = FETS3D8H(mats_eval=MATS3DElastic())

        fe_domain = FEDomain()
        fe_level1 = FERefinementGrid(domain=fe_domain, fets_eval=fets_eval)

        # Discretization
        fe_domain1 = FEGrid(coord_max=(2., 5., 3.),
                            shape=(2, 3, 2),
                            level=fe_level1,
                            fets_eval=fets_eval)

        fe_child_domain = FERefinementGrid(parent=fe_domain1,
                                           fine_cell_shape=(2, 2, 2))

        fe_child_domain.refine_elem((1, 1, 0))
        fe_child_domain.refine_elem((0, 1, 0))
        fe_child_domain.refine_elem((1, 1, 1))
        fe_child_domain.refine_elem((0, 1, 1))

        ts = TS(
            dof_resultants=True,
            sdomain=fe_domain,
            bcond_list=[
                BCDofGroup(var='f',
                           value=1.,
                           dims=[0],
                           get_dof_method=fe_domain1.get_top_dofs),
                BCDofGroup(var='u',
                           value=0.,
                           dims=[0, 1],
                           get_dof_method=fe_domain1.get_bottom_dofs),
            ],
            rtrace_list=[
                RTraceGraph(name='Fi,right over u_right (iteration)',
                            var_y='F_int',
                            idx_y=0,
                            var_x='U_k',
                            idx_x=1),
                #                            RTraceDomainListField(name = 'Stress' ,
                #                                 var = 'sig_app', idx = 0, warp = True ),
                #                             RTraceDomainField(name = 'Displacement' ,
                #                                        var = 'u', idx = 0),
                #                                 RTraceDomainField(name = 'N0' ,
                #                                              var = 'N_mtx', idx = 0,
                # record_on = 'update')
            ])

        # Add the time-loop control
        tloop = TLoop(tstepper=ts, tline=TLine(min=0.0, step=1, max=1.0))

        print tloop.eval()
        from ibvpy.plugins.ibvpy_app import IBVPyApp
        ibvpy_app = IBVPyApp(ibv_resource=tloop)
        ibvpy_app.main()
Beispiel #8
0
    def _get_explorer_config(self):
        from ibvpy.api import BCDof, TLine, RTraceGraph
        return {'bcond_list': [BCDof(var='u',
                                     dof=0, value=0.01,
                                     time_function=lambda t: t)],
                'rtrace_list': [RTraceGraph(name='strain - stress',
                                            var_x='eps_app', idx_x=0,
                                            var_y='sig_app', idx_y=0,
                                            record_on='update'),
                                RTraceGraph(name='strain - strain',
                                            var_x='eps_app', idx_x=0,
                                            var_y='eps_app', idx_y=1,
                                            record_on='update'),
                                RTraceGraph(name='stress - stress',
                                            var_x='sig_app', idx_x=0,
                                            var_y='sig_app', idx_y=1,
                                            record_on='update'),
                                RTraceGraph(name='Stress - Strain',
                                            var_x='F_int', idx_x=0,
                                            var_y='U_k', idx_y=0,
                                            record_on='update'),
                                RTraceGraph(name='Strain - Strain',
                                            var_x='U_k', idx_x=0,
                                            var_y='U_k', idx_y=1,
                                            record_on='update'),
                                RTraceGraph(name='Stress - Stress',
                                            var_x='F_int', idx_x=0,
                                            var_y='F_int', idx_y=1,
                                            record_on='update'),
                                RTraceGraph(name='sig1 - eps1',
                                            var_x='F_int', idx_x=0,
                                            var_y='U_k', idx_y=0,
                                            record_on='update'),
                                RTraceGraph(name='sig2 - sig3',
                                            var_x='F_int', idx_x=1,
                                            var_y='F_int', idx_y=2,
                                            record_on='update'),
                                RTraceGraph(name='eps2 - eps3',
                                            var_x='U_k', idx_x=1,
                                            var_y='U_k', idx_y=2,
                                            record_on='update')
                                ],
                'tline': TLine(step=0.1, max=1.0)
                }

        def _set_explorer_config(self, value):
            self._explorer_config = value
Beispiel #9
0
 def _get_explorer_rtrace_list(self):
     '''Return the list of relevant tracers to be used in mats_explorer.
     '''
     return [
         RTraceGraph(name='strain - stress',
                     var_x='eps_app',
                     idx_x=0,
                     var_y='sig_app',
                     idx_y=0,
                     record_on='update')
     ]
Beispiel #10
0
    def example_2d():
        from ibvpy.mats.mats2D.mats2D_elastic.mats2D_elastic import MATS2DElastic
        from ibvpy.fets.fets2D.fets2D4q import FETS2D4Q

        fets_eval = FETS2D4Q(mats_eval=MATS2DElastic(E=2.1e5))

        # Discretization
        fe_domain1 = FEGrid(coord_max=(2., 5., 0.),
                            shape=(10, 10),
                            fets_eval=fets_eval)

        fe_subgrid1 = FERefinementLevel(parent=fe_domain1,
                                        fine_cell_shape=(1, 1))

        print 'children'
        print fe_domain1.children

        fe_subgrid1.refine_elem((5, 5))
        fe_subgrid1.refine_elem((6, 5))
        fe_subgrid1.refine_elem((7, 5))
        fe_subgrid1.refine_elem((8, 5))
        fe_subgrid1.refine_elem((9, 5))

        fe_domain = FEDomain(subdomains=[fe_domain1])

        ts = TS(dof_resultants=True,
                sdomain=fe_domain,
                bcond_list=[BCDofGroup(var='f', value=0.1, dims=[0],
                                       get_dof_method=fe_domain1.get_top_dofs),
                            BCDofGroup(var='u', value=0., dims=[0, 1],
                                       get_dof_method=fe_domain1.get_bottom_dofs),
                            ],
                rtrace_list=[RTraceGraph(name='Fi,right over u_right (iteration)',
                                         var_y='F_int', idx_y=0,
                                         var_x='U_k', idx_x=1),
                             RTraceDomainListField(name='Stress',
                                                   var='sig_app', idx=0, warp=True),
                             #                           RTraceDomainField(name = 'Displacement' ,
                             #                                        var = 'u', idx = 0),
                             #                                 RTraceDomainField(name = 'N0' ,
                             #                                              var = 'N_mtx', idx = 0,
                             # record_on = 'update')

                             ]
                )

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      tline=TLine(min=0.0, step=1, max=1.0))
#
        print tloop.eval()
        from ibvpy.plugins.ibvpy_app import IBVPyApp
        ibvpy_app = IBVPyApp(ibv_resource=tloop)
        ibvpy_app.main()
Beispiel #11
0
def __demo__():

    from ibvpy.api import \
        TStepper as TS, RTraceGraph, RTraceDomainListField, TLoop, \
        TLine, BCDof
    from ibvpy.mats.mats1D.mats1D_elastic.mats1D_elastic import MATS1DElastic

    fets_eval = FETS1D2L(mats_eval=MATS1DElastic(E=10.))
    from ibvpy.mesh.fe_grid import FEGrid

    # Discretization
    domain = FEGrid(coord_max=(3., ), shape=(3, ), fets_eval=fets_eval)

    ts = TS(dof_resultants=True,
            sdomain=domain,
            bcond_list=[
                BCDof(var='u', dof=0, value=0.),
                BCDof(
                    var='f',
                    dof=3,
                    value=1,
                )
            ],
            rtrace_list=[
                RTraceGraph(name='Fi,right over u_right (iteration)',
                            var_y='F_int',
                            idx_y=0,
                            var_x='U_k',
                            idx_x=1),
                RTraceDomainListField(name='Stress', var='sig_app', idx=0),
                RTraceDomainListField(name='Displacement',
                                      var='u',
                                      idx=0,
                                      warp=True),
                RTraceDomainListField(name='N0',
                                      var='N_mtx',
                                      idx=0,
                                      record_on='update')
            ])

    # Add the time-loop control
    tloop = TLoop(tstepper=ts, tline=TLine(min=0.0, step=0.5, max=1.0))

    print '---- result ----'
    print tloop.eval()
    print ts.F_int
    print ts.rtrace_list[0].trace.ydata

    # Put the whole stuff into the simulation-framework to map the
    # individual pieces of definition into the user interface.
    #
    app = IBVPyApp(ibv_resource=tloop)
    app.main()
Beispiel #12
0
 def _get_f_w_diagram(self):
     domain = self.fe_grid_roof
     w_z = domain[-1, -1, -1, -1, -1, -1].dofs[0, 0, 2]
     return RTraceGraph(
         name='load - corner deflection',
         var_x='U_k',
         idx_x=w_z,
         transform_x='-x',
         var_y='time',
         idx_y=0,
         # transform_y='y * %g' % self.lambda_factor,
         record_on='update')
Beispiel #13
0
    def test_bar4(self):
        '''Clamped bar 3 domains, each with 2 elems (displ at right end)
        [0]-[1]-[2] [3]-[4]-[5] [6]-[7]-[8]
        u[0] = 0, u[2] = u[3], u[5] = u[6], u[8] = 1'''

        self.fe_domain1.set(coord_min=(0, 0, 0),
                            coord_max=(2, 0, 0),
                            shape=(2, ))
        self.fe_domain2.set(coord_min=(2, 0, 0),
                            coord_max=(4, 0, 0),
                            shape=(2, ))
        self.fe_domain3.set(coord_min=(4, 0, 0),
                            coord_max=(6, 0, 0),
                            shape=(2, ))

        self.ts.set(
            sdomain=[self.fe_domain1, self.fe_domain2, self.fe_domain3],
            dof_resultants=True,
            bcond_list=[
                BCDof(var='u', dof=0, value=0.),
                BCDof(var='u',
                      dof=2,
                      link_dofs=[3],
                      link_coeffs=[1.],
                      value=0.),
                BCDof(var='u',
                      dof=5,
                      link_dofs=[6],
                      link_coeffs=[1.],
                      value=0.),
                BCDof(var='u', dof=8, value=1)
            ],
            rtrace_list=[
                RTraceGraph(name='Fi,right over u_right (iteration)',
                            var_y='F_int',
                            idx_y=0,
                            var_x='U_k',
                            idx_x=1),
            ])
        # system solver
        u = self.tloop.eval()
        # expected solution
        u_ex = array(
            [0., 1 / 6., 1 / 3., 1 / 3., 1 / 2., 2 / 3., 2 / 3., 5 / 6., 1.],
            dtype=float)
        for u_, u_ex_ in zip(u, u_ex):
            self.assertAlmostEqual(u_, u_ex_)
Beispiel #14
0
    def setUp(self):

        self.fets_eval = FETS1D2L(mats_eval=MATS1DElastic(E=10.))

        # Discretization
        self.fe_domain1 = FEGrid(coord_max=(3., 0., 0.),
                                 shape=(3, ),
                                 fets_eval=self.fets_eval)

        self.fe_domain2 = FEGrid(coord_min=(3., 0., 0.),
                                 coord_max=(6., 0., 0.),
                                 shape=(3, ),
                                 fets_eval=self.fets_eval)

        self.fe_domain3 = FEGrid(coord_min=(3., 0., 0.),
                                 coord_max=(6., 0., 0.),
                                 shape=(3, ),
                                 fets_eval=self.fets_eval)

        self.ts = TS(
            dof_resultants=True,
            sdomain=[self.fe_domain1, self.fe_domain2, self.fe_domain3],
            bcond_list=[
                BCDof(var='u', dof=0, value=0.),
                BCDof(var='u',
                      dof=4,
                      link_dofs=[3],
                      link_coeffs=[1.],
                      value=0.),
                BCDof(var='f', dof=7, value=1, link_dofs=[2], link_coeffs=[2])
            ],
            rtrace_list=[
                RTraceGraph(name='Fi,right over u_right (iteration)',
                            var_y='F_int',
                            idx_y=0,
                            var_x='U_k',
                            idx_x=1),
            ])

        # Add the time-loop control
        self.tloop = TLoop(tstepper=self.ts,
                           tline=TLine(min=0.0, step=1, max=1.0))
Beispiel #15
0
    def peval(self):
        """Evaluation procedure.
        """
        # mv = MATS1DDamageView( model = mats_eval )
        # mv.configure_traits()

        right_dof_m = self.fe_grid_m[-1, -1].dofs[0, 0, 0]

        right_dof_fb = self.fe_grid_fb[-1, -1, -1, -1].dofs[0, 0, 0]
        # Response tracers
        A = self.A_m + self.A_f
        self.sig_eps_m = RTraceGraph(
            name="F_u_m", var_y="F_int", idx_y=right_dof_m, var_x="U_k", idx_x=right_dof_m, transform_y="y / %g" % A
        )

        # Response tracers
        self.sig_eps_f = RTraceGraph(
            name="F_u_f", var_y="F_int", idx_y=right_dof_fb, var_x="U_k", idx_x=right_dof_fb, transform_y="y / %g" % A
        )

        self.eps_m_field = RTraceDomainListField(name="eps_m", position="int_pnts", var="eps_app", warp=False)

        self.eps_f_field = RTraceDomainListField(
            name="eps_f", position="int_pnts", var="mats_phase2_eps_app", warp=False
        )
        # Response tracers
        self.sig_m_field = RTraceDomainListField(name="sig_m", position="int_pnts", var="sig_app")

        self.sig_f_field = RTraceDomainListField(name="sig_f", position="int_pnts", var="mats_phase2_sig_app")

        self.omega_m_field = RTraceDomainListField(name="omega_m", position="int_pnts", var="omega", warp=False)

        self.shear_flow_field = RTraceDomainListField(
            name="shear flow", position="int_pnts", var="shear_flow", warp=False
        )

        self.slip_field = RTraceDomainListField(name="slip", position="int_pnts", var="slip", warp=False)

        avg_processor = None
        if self.avg_radius > 0.0:
            n_dofs = self.fe_domain.n_dofs
            avg_processor = RTUAvg(sd=self.fe_m_level, n_dofs=n_dofs, avg_fn=QuarticAF(radius=self.avg_radius))

        ts = TStepper(
            u_processor=avg_processor,
            dof_resultants=True,
            sdomain=self.fe_domain,
            bcond_list=[  # define the left clamping
                BCSlice(var="u", value=0.0, dims=[0], slice=self.fe_grid_fb[0, 0, 0, :]),
                #                                BCSlice( var = 'u', value = 0., dims = [0], slice = self.fe_grid_m[ 0, 0 ] ),
                # loading at the right edge
                #                                 BCSlice( var = 'f', value = 1, dims = [0], slice = domain[-1, -1, -1, 0],
                #                                         time_function = ls ),
                BCSlice(
                    var="u",
                    value=self.final_displ,
                    dims=[0],
                    slice=self.fe_grid_fb[-1, -1, -1, :],
                    time_function=self.time_function,
                ),
                #                                 BCSlice( var = 'u', value = self.final_displ, dims = [0], slice = self.fe_grid_m[-1, -1],
                #                                         time_function = self.time_function ),
                # fix horizontal displacement in the top layer
                #                                 BCSlice( var = 'u', value = 0., dims = [0], slice = domain[:, -1, :, -1] ),
                # fix the vertical displacement all over the domain
                BCSlice(var="u", value=0.0, dims=[1], slice=self.fe_grid_fb[:, :, :, :]),
                #                            # Connect bond and matrix domains
                BCDofGroup(
                    var="u",
                    value=0.0,
                    dims=[0],
                    get_link_dof_method=self.fe_grid_fb.get_bottom_dofs,
                    get_dof_method=self.fe_grid_m.get_all_dofs,
                    link_coeffs=[1.0],
                ),
            ],
            rtrace_list=[
                self.sig_eps_m,
                self.sig_eps_f,
                self.eps_m_field,
                self.eps_f_field,
                self.sig_m_field,
                self.sig_f_field,
                self.omega_m_field,
                self.shear_flow_field,
                self.slip_field,
            ],
        )

        # Add the time-loop control
        tloop = TLoop(
            tstepper=ts,
            KMAX=300,
            tolerance=1e-5,
            debug=False,
            verbose_iteration=True,
            verbose_time=False,
            tline=TLine(min=0.0, step=self.step_size, max=1.0),
        )

        tloop.on_accept_time_step = self.plot

        U = tloop.eval()

        self.sig_eps_f.refresh()
        max_sig_m = max(self.sig_eps_m.trace.ydata)
        return array([U[right_dof_m], max_sig_m], dtype="float_")
Beispiel #16
0
                        fets_eval=fets_eval)

    fe_domain2 = FEGrid(coord_min=(10., 0., 0.),
                        coord_max=(20., 0., 0.),
                        shape=(10,),
                        fets_eval=fets_eval)

    fe_domain = FEDomain(subdomains=[fe_domain1, fe_domain2])
    ts = TS(dof_resultants=True,
            sdomain=fe_domain,
            bcond_list=[BCDof(var='u', dof=0, value=0.),
                        BCDof(
                            var='u', dof=5, link_dofs=[16], link_coeffs=[1.], value=0.),
                        BCDof(var='f', dof=21, value=10)],
            rtrace_list=[RTraceGraph(name='Fi,right over u_right (iteration)',
                                     var_y='F_int', idx_y=0,
                                     var_x='U_k', idx_x=1),
                         ]
            )

    # Add the time-loop control
    tloop = TLoop(tstepper=ts, tline=TLine(min=0.0, step=1, max=1.0))

    ts.set(sdomain=FEDomain(subdomains=[fe_domain1, fe_domain2]))

    ts.set(bcond_list=[BCDof(var='u', dof=0, value=0.),
                       BCDof(
                           var='u', dof=5, link_dofs=[16], link_coeffs=[1.], value=0.),
                       BCDof(var='f', dof=21, value=10)])
    print tloop.eval()
Beispiel #17
0
class SimBT4PT(IBVModel):
    '''Simulation: four point bending test.
    '''

    input_change = Event
    @on_trait_change('+input,ccs_unit_cell.input_change')
    def _set_input_change(self):
        self.input_change = True

    implements(ISimModel)

    #-----------------
    # discretization:
    #-----------------

    # specify weather the elastomer is to be modeled or if the load is
    # introduced as line load
    #
    elstmr_flag = Bool(True)

    # discretization in x-direction (longitudinal):
    #
    outer_zone_shape_x = Int(6, input=True,
                             ps_levels=(4, 12, 3))

    # discretization in x-direction (longitudinal):
    #
    load_zone_shape_x = Int(2, input=True,
                            ps_levels=(1, 4, 1))

    # middle part discretization in x-direction (longitudinal):
    #
    mid_zone_shape_x = Int(3, input=True,
                           ps_levels=(1, 4, 1))

    # discretization in y-direction (width):
    #
    shape_y = Int(2, input=True,
                     ps_levels=(1, 4, 2))

    # discretization in z-direction:
    #
    shape_z = Int(2, input=True,
                     ps_levels=(1, 3, 3))

    #-----------------
    # geometry:
    #-----------------
    #
    # edge length of the bending specimen (beam) (entire length without symmetry)
    #
    length = Float(1.50, input=True)

    elstmr_length = Float(0.05, input=True)
    mid_zone_length = Float(0.50, input=True)
    elstmr_thickness = Float(0.005, input=True)
    width = Float(0.20, input=True)
    thickness = Float(0.06, input=True)

    #-----------------
    # derived geometric parameters
    #-----------------
    #
    # half the length of the elastomer (load introduction 
    # with included symmetry)
    #
    sym_specmn_length = Property
    def _get_sym_specmn_length(self):
        return self.length / 2.

    sym_mid_zone_specmn_length = Property
    def _get_sym_mid_zone_specmn_length(self):
        return self.mid_zone_length / 2.

    # half the length of the elastomer (load introduction
    # with included symmetry
    #
    sym_elstmr_length = Property
    def _get_sym_elstmr_length(self):
        return self.elstmr_length / 2.

    # half the specimen width
    #
    sym_width = Property
    def _get_sym_width(self):
        return self.width / 2.

    #----------------------------------------------------------------------------------
    # mats_eval
    #----------------------------------------------------------------------------------

    # age of the plate at the time of testing
    # NOTE: that the same phi-function is used independent of age. This assumes a 
    # an afine/proportional damage evolution for different ages. 
    #
    age = Int(28, input=True)

    # time stepping params 
    #  
    tstep = Float(0.05, auto_set=False, enter_set=True, input=True)
    tmax = Float(1.0, auto_set=False, enter_set=True, input=True)
    tolerance = Float(0.001, auto_set=False, enter_set=True, input=True)

    # specify type of 'linalg.norm'
    # default value 'None' sets norm to 2-norm,
    # i.e "norm = sqrt(sum(x_i**2))
    #
    # set 'ord=np.inf' to switch norm to
    # "norm = max(abs(x_i))"
    # 
    ord = Enum(np.inf, None)

    n_mp = Int(30, input=True)

    # @todo: for mats_eval the information of the unit cell should be used
    # in order to use the same number of microplanes and model version etc...
    #
    specmn_mats = Property(Instance(MATS2D5MicroplaneDamage),
                          depends_on='input_change')
    @cached_property
    def _get_specmn_mats(self):
        return MATS2D5MicroplaneDamage(
                                E=self.E_c,
#                                 E=self.E_m,
                                nu=self.nu,
                                # corresponding to settings in "MatsCalib"
                                n_mp=self.n_mp,
                                symmetrization='sum-type',
                                model_version='compliance',
                                phi_fn=self.phi_fn)

    if elstmr_flag:
        elstmr_mats = Property(Instance(MATS3DElastic),
                               depends_on='input_change')
        @cached_property
        def _get_elstmr_mats(self):
            # specify a small elastomer stiffness (approximation)
            E_elast = self.E_c / 10.
            print 'effective elastomer E_modulus', E_elast
            return MATS3DElastic(E=E_elast,
                                 nu=0.4)

    #-----------------
    # fets:
    #-----------------

    # specify element shrink factor in plot of fe-model
    #
    vtk_r = Float(0.95)

    # use quadratic serendipity elements
    #
    specmn_fets = Property(Instance(FETSEval),
                           depends_on='input_change')
    @cached_property
    def _get_specmn_fets(self):
        fets = FETS2D58H20U(mats_eval=self.specmn_mats)
        fets.vtk_r *= self.vtk_r
        return fets

    # use quadratic serendipity elements
    #
    elstmr_fets = Property(Instance(FETSEval),
                           depends_on='input_change')
    @cached_property
    def _get_elstmr_fets(self):
        fets = FETS2D58H20U(mats_eval=self.elstmr_mats)
        fets.vtk_r *= self.vtk_r
        return fets

    fe_domain = Property(depends_on='+ps_levels, +input')
    @cached_property
    def _get_fe_domain(self):
        return FEDomain()

    #===========================================================================
    # fe level 
    #===========================================================================

    outer_zone_specmn_fe_level = Property(depends_on='+ps_levels, +input')
    def _get_outer_zone_specmn_fe_level(self):
        return  FERefinementGrid(name='outer zone specimen patch',
                                 fets_eval=self.specmn_fets,
                                 domain=self.fe_domain)

    load_zone_specmn_fe_level = Property(depends_on='+ps_levels, +input')
    def _get_load_zone_specmn_fe_level(self):
        return  FERefinementGrid(name='load zone specimen patch',
                                 fets_eval=self.specmn_fets,
                                 domain=self.fe_domain)

    mid_zone_specmn_fe_level = Property(depends_on='+ps_levels, +input')
    def _get_mid_zone_specmn_fe_level(self):
        return  FERefinementGrid(name='mid zone specimen patch',
                                 fets_eval=self.specmn_fets,
                                 domain=self.fe_domain)

    elstmr_fe_level = Property(depends_on='+ps_levels, +input')
    def _get_elstmr_fe_level(self):
        return  FERefinementGrid(name='elastomer patch',
                                 fets_eval=self.elstmr_fets,
                                 domain=self.fe_domain)

    #===========================================================================
    # Grid definition 
    #===========================================================================

    mid_zone_specmn_fe_grid = Property(Instance(FEGrid), depends_on='+ps_levels, +input')
    @cached_property
    def _get_mid_zone_specmn_fe_grid(self):
        # only a quarter of the beam is simulated due to symmetry:
        fe_grid = FEGrid(coord_min=(0.,
                                      0.,
                                      0.),
                         coord_max=(self.sym_mid_zone_specmn_length - self.sym_elstmr_length,
                                      self.sym_width,
                                      self.thickness),
                         shape=(self.mid_zone_shape_x, self.shape_y, self.shape_z),
                         level=self.mid_zone_specmn_fe_level,
                         fets_eval=self.specmn_fets)
        return fe_grid

    load_zone_specmn_fe_grid = Property(Instance(FEGrid), depends_on='+ps_levels, +input')
    @cached_property
    def _get_load_zone_specmn_fe_grid(self):
        # only a quarter of the beam is simulated due to symmetry:
        fe_grid = FEGrid(coord_min=(self.sym_mid_zone_specmn_length - self.sym_elstmr_length,
                                      0.,
                                      0.),
                         coord_max=(self.sym_mid_zone_specmn_length + self.sym_elstmr_length,
                                      self.sym_width,
                                      self.thickness),
                         shape=(self.load_zone_shape_x, self.shape_y, self.shape_z),
                         level=self.load_zone_specmn_fe_level,
                         fets_eval=self.specmn_fets)
        return fe_grid

#    if elstmr_flag:
    elstmr_fe_grid = Property(Instance(FEGrid), depends_on='+ps_levels, +input')
    @cached_property
    def _get_elstmr_fe_grid(self):
        fe_grid = FEGrid(coord_min=(self.sym_mid_zone_specmn_length - self.sym_elstmr_length,
                                      0.,
                                      self.thickness),
                         coord_max=(self.sym_mid_zone_specmn_length + self.sym_elstmr_length,
                                      self.sym_width,
                                      self.thickness + self.elstmr_thickness),
                         level=self.elstmr_fe_level,
                         shape=(self.load_zone_shape_x, self.shape_y, 1),
                         fets_eval=self.elstmr_fets)
        return fe_grid

    outer_zone_specmn_fe_grid = Property(Instance(FEGrid), depends_on='+ps_levels, +input')
    @cached_property
    def _get_outer_zone_specmn_fe_grid(self):
        # only a quarter of the plate is simulated due to symmetry:
        fe_grid = FEGrid(coord_min=(self.sym_mid_zone_specmn_length + self.sym_elstmr_length,
                                      0.,
                                      0.),
                         coord_max=(self.sym_specmn_length,
                                      self.sym_width,
                                      self.thickness),
                         shape=(self.outer_zone_shape_x, self.shape_y, self.shape_z),
                         level=self.outer_zone_specmn_fe_level,
                         fets_eval=self.specmn_fets)
        return fe_grid

    #===========================================================================
    # Boundary conditions
    #===========================================================================
    w_max = Float(-0.030, input=True) # [m]

    w_max = Float(-0.030, input=True)  # [m]

    bc_list = Property(depends_on='+ps_levels, +input')
    @cached_property
    def _get_bc_list(self):
        mid_zone_specimen = self.mid_zone_specmn_fe_grid
        load_zone_specimen = self.load_zone_specmn_fe_grid
        outer_zone_specimen = self.outer_zone_specmn_fe_grid

        if self.elstmr_flag:
            elastomer = self.elstmr_fe_grid

        #--------------------------------------------------------------
        # boundary conditions for the symmetry 
        #--------------------------------------------------------------
        # symmetry in the xz-plane
        # (Note: the x-axis corresponds to the axis of symmetry along the longitudinal axis of the beam)
        #
        bc_outer_zone_symplane_xz = BCSlice(var='u', value=0., dims=[1],
                                            slice=outer_zone_specimen[:, 0, :, :, 0, :])
        bc_load_zone_symplane_xz = BCSlice(var='u', value=0., dims=[1],
                                           slice=load_zone_specimen[:, 0, :, :, 0, :])
        bc_mid_zone_symplane_xz = BCSlice(var='u', value=0., dims=[1],
                                          slice=mid_zone_specimen[:, 0, :, :, 0, :])

        if self.elstmr_flag:
            bc_el_symplane_xz = BCSlice(var='u', value=0., dims=[1],
                                        slice=elastomer[:, 0, :, :, 0, :])
        # symmetry in the yz-plane
        #
        bc_mid_zone_symplane_yz = BCSlice(var='u', value=0., dims=[0],
                                          slice=mid_zone_specimen[0, :, :, 0, :, :])

        #--------------------------------------------------------------
        # boundary conditions for the support
        #--------------------------------------------------------------
        bc_support_0y0 = BCSlice(var='u', value=0., dims=[2],
                                 slice=outer_zone_specimen[-1, :, 0, -1, :, 0])

        #--------------------------------------------------------------
        # connect all grids 
        #--------------------------------------------------------------
        link_loadzn_outerzn = BCDofGroup(var='u', value=0., dims=[0, 1, 2],
                                get_dof_method=load_zone_specimen.get_right_dofs,
                                get_link_dof_method=outer_zone_specimen.get_left_dofs,
                                link_coeffs=[1.])
        link_midzn_loadzn = BCDofGroup(var='u', value=0., dims=[0, 1, 2],
                                get_dof_method=mid_zone_specimen.get_right_dofs,
                                get_link_dof_method=load_zone_specimen.get_left_dofs,
                                link_coeffs=[1.])

        if self.elstmr_flag:
            link_elstmr_loadzn_z = BCDofGroup(var='u', value=0., dims=[2],
                                    get_dof_method=elastomer.get_back_dofs,
                                    get_link_dof_method=load_zone_specimen.get_front_dofs,
                                    link_coeffs=[1.])

            # hold elastomer in a single point in order to avoid kinematic movement yielding singular K_mtx 
            #
            bc_elstmr_fix = BCSlice(var='u', value=0., dims=[0],
                                 slice=elastomer[0, 0, 0, 0, 0, 0])

        #--------------------------------------------------------------
        # loading
        #--------------------------------------------------------------
        # w_max = center displacement:
        w_max = self.w_max

        if self.elstmr_flag:
            # apply displacement at all top nodes of the elastomer (surface load)
            #
            bc_w = BCSlice(var='u', value=w_max, dims=[2],
                           slice=elastomer[:, :, -1, :, :, -1])
        else:
            bc_w = BCSlice(var='u', value=w_max, dims=[2],
                           # slice is only exactly in the center of the loading zone for 'load_zone_shape_x' = 2
                           # center line of the load zone
                           slice=load_zone_specimen[0, :, -1, -1, :, -1])

#        f_max = 0.010 / 4. / self.sym_width 
#        bc_line_f = BCSlice(var = 'f', value = f_max, dims = [2],
#                            # slice is only valid for 'load_zone_shape_x' = 2
#                            # center line of the load zone
#                            slice = load_zone_specimen[0, :, -1, -1, :, -1])

        bc_list = [bc_outer_zone_symplane_xz,
                   bc_load_zone_symplane_xz,
                   bc_mid_zone_symplane_xz,
                   bc_mid_zone_symplane_yz,
                   #
                   link_midzn_loadzn,
                   link_loadzn_outerzn,
                   bc_support_0y0,
                   #
                   bc_w,
                   ]

        if self.elstmr_flag:
            bc_list += [ bc_el_symplane_xz, link_elstmr_loadzn_z, bc_elstmr_fix ]

        return bc_list

    #----------------------
    # tloop
    #----------------------

    tloop = Property(depends_on='input_change')
    @cached_property
    def _get_tloop(self):

        #--------------------------------------------------------------
        # ts 
        #--------------------------------------------------------------

        mid_zone_spec = self.mid_zone_specmn_fe_grid
        load_zone_spec = self.load_zone_specmn_fe_grid
        outer_zone_spec = self.outer_zone_specmn_fe_grid

        if self.elstmr_flag:
            # ELSTRMR TOP SURFACE
            # dofs at elastomer top surface (used to integrate the force)
            #
            elastomer = self.elstmr_fe_grid
            elstmr_top_dofs_z = elastomer[:, :, -1, :, :, -1].dofs[:, :, 2].flatten()
            load_dofs_z = np.unique(elstmr_top_dofs_z)
            print 'load_dofs_z', load_dofs_z
        else:
            # LINE LOAD TOP OF LOAD ZONE
            # dofs at center line of the specmn load zone (used to integrate the force)
            # note slice index in x-direction is only valid for load_zone_shape_x = 2 !
            #
            load_zone_spec_topline_dofs_z = load_zone_spec[0, :, -1, -1, :, -1].dofs[:, :, 2].flatten()
            load_dofs_z = np.unique(load_zone_spec_topline_dofs_z)
            print 'load_dofs_z', load_dofs_z

        # SUPPRT LINE
        # dofs at support line of the specmn (used to integrate the force)
        #
        outer_zone_spec_supprtline_dofs_z = outer_zone_spec[-1, :, 0, -1, :, 0].dofs[:, :, 2].flatten()
        supprt_dofs_z = np.unique(outer_zone_spec_supprtline_dofs_z)
        print 'supprt_dofs_z', supprt_dofs_z

        # CENTER DOF (used for tracing of the displacement)
        #
        center_bottom_dof = mid_zone_spec[0, 0, 0, 0, 0, 0].dofs[0, 0, 2]
        print 'center_bottom_dof', center_bottom_dof

        # THIRDPOINT DOF (used for tracing of the displacement) 
        # dofs at center middle of the laod zone at the bottom side
        #
        # NOTE: slice index in x-direction is only valid for load_zone_shape_x = 2 !
        thirdpoint_bottom_dof = load_zone_spec[0, 0, 0, -1, 0, 0].dofs[0, 0, 2]
        print 'thirdpoint_bottom_dof', thirdpoint_bottom_dof

        # force-displacement-diagram (CENTER) 
        # 
        self.f_w_diagram_center = RTraceGraph(name='displacement_elasttop (center) - force',
                                       var_x='U_k'  , idx_x=center_bottom_dof,
                                       var_y='F_int', idx_y_arr=load_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='-4000. * y')

        # force-displacement-diagram_supprt (SUPPRT)
        # 
        self.f_w_diagram_supprt = RTraceGraph(name='displacement_supprtline (center) - force',
                                       var_x='U_k'  , idx_x=center_bottom_dof,
                                       var_y='F_int', idx_y_arr=supprt_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='4000. * y')

        # force-displacement-diagram (THIRDPOINT) 
        # 
        self.f_w_diagram_thirdpoint = RTraceGraph(name='displacement_elasttop (thirdpoint) - force',
                                       var_x='U_k'  , idx_x=thirdpoint_bottom_dof,
                                       var_y='F_int', idx_y_arr=load_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='-4000. * y')

        ts = TS(
                sdomain=self.fe_domain,
                bcond_list=self.bc_list,
                rtrace_list=[
                             self.f_w_diagram_center,
                             self.f_w_diagram_thirdpoint,
                             self.f_w_diagram_supprt,
                             RTraceDomainListField(name='Displacement' ,
                                            var='u', idx=0, warp=True),
#                             RTraceDomainListField(name = 'Stress' ,
#                                            var = 'sig_app', idx = 0, warp = True,
#                                            record_on = 'update'),
#                             RTraceDomainListField(name = 'Strain' ,
#                                        var = 'eps_app', idx = 0, warp = True,
#                                        record_on = 'update'),
#                             RTraceDomainListField(name = 'Damage' ,
#                                        var = 'omega_mtx', idx = 0, warp = True,
#                                        record_on = 'update'),
                             RTraceDomainListField(name='max_omega_i', warp=True,
                                        var='max_omega_i', idx=0,
                                        record_on='update'),
#                             RTraceDomainListField(name = 'IStress' ,
#                                            position = 'int_pnts',
#                                            var = 'sig_app', idx = 0,
#                                            record_on = 'update'),
#                             RTraceDomainListField(name = 'IStrain' ,
#                                            position = 'int_pnts',
#                                            var = 'eps_app', idx = 0,
#                                            record_on = 'update'),
                              ]
                )

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      KMAX=50,
                      tolerance=self.tolerance,
                      RESETMAX=0,
                      tline=TLine(min=0.0, step=self.tstep, max=self.tmax),
                      ord=self.ord
                      )

        return tloop

    def peval(self):
        '''
        Evaluate the model and return the array of results specified
        in the method get_sim_outputs.
        '''
        U = self.tloop.eval()

        self.f_w_diagram_center.refresh()
        F_max = max(self.f_w_diagram_center.trace.ydata)

        u_center_top_z = U[ self.center_top_dofs ][0, 0, 2]
        return array([ u_center_top_z, F_max ],
                        dtype='float_')

    def get_sim_outputs(self):
        '''
        Specifies the results and their order returned by the model
        evaluation.
        '''
        return [ SimOut(name='u_center_top_z', unit='m'),
                 SimOut(name='F_max', unit='kN') ]
Beispiel #18
0
class SimCrackLoc(IBVModel):
    """Model assembling the components for studying the restrained crack localization.
    """

    geo_transform = Instance(FlawCenteredGeoTransform)

    def _geo_transform_default(self):
        return FlawCenteredGeoTransform()

    shape = Int(10, desc="Number of finite elements", ps_levsls=(10, 40, 4), input=True)

    length = Float(1000, desc="Length of the simulated region", unit="mm", input=True)

    flaw_position = Float(500, input=True, unit="mm")

    flaw_radius = Float(100, input=True, unit="mm")

    reduction_factor = Float(0.9, input=True)

    elastic_fraction = Float(0.9, input=True)

    avg_radius = Float(400, input=True, unit="mm")

    # tensile strength of concrete
    f_m_t = Float(3.0, input=True, unit="MPa")

    epsilon_0 = Property(unit="-")

    def _get_epsilon_0(self):
        return self.f_m_t / self.E_m

    epsilon_f = Float(10, input=True, unit="-")

    h_m = Float(10, input=True, unit="mm")

    b_m = Float(8, input=True, unit="mm")

    A_m = Property(unit="m^2")

    def _get_A_m(self):
        return self.b_m * self.h_m

    E_m = Float(30.0e5, input=True, unit="MPa")

    E_f = Float(70.0e6, input=True, unit="MPa")

    A_f = Float(1.0, input=True, unit="mm^2")

    s_crit = Float(0.009, input=True, unit="mm")

    P_f = Property(depends_on="+input")

    @cached_property
    def _get_P_f(self):
        return sqrt(4 * self.A_f * pi)

    K_b = Property(depends_on="+input")

    @cached_property
    def _get_K_b(self):
        return self.T_max / self.s_crit

    tau_max = Float(0.0, input=True, unit="MPa")

    T_max = Property(depends_on="+input", unit="N/mm")

    @cached_property
    def _get_T_max(self):
        return self.tau_max * self.P_f

    rho = Property(depends_on="+input")

    @cached_property
    def _get_rho(self):
        return self.A_f / (self.A_f + self.A_m)

    # -------------------------------------------------------
    # Material model for the matrix
    # -------------------------------------------------------
    mats_m = Property(Instance(MATS1DDamageWithFlaw), depends_on="+input")

    @cached_property
    def _get_mats_m(self):
        mats_m = MATS1DDamageWithFlaw(
            E=self.E_m * self.A_m,
            flaw_position=self.flaw_position,
            flaw_radius=self.flaw_radius,
            reduction_factor=self.reduction_factor,
            epsilon_0=self.epsilon_0,
            epsilon_f=self.epsilon_f,
        )
        return mats_m

    mats_f = Instance(MATS1DElastic)

    def _mats_f_default(self):
        mats_f = MATS1DElastic(E=self.E_f * self.A_f)
        return mats_f

    mats_b = Instance(MATS1DEval)

    def _mats_b_default(self):
        mats_b = MATS1DElastic(E=self.K_b)
        mats_b = MATS1DPlastic(E=self.K_b, sigma_y=self.T_max, K_bar=0.0, H_bar=0.0)  # plastic function of slip
        return mats_b

    mats_fb = Property(Instance(MATS1D5Bond), depends_on="+input")

    @cached_property
    def _get_mats_fb(self):

        # Material model construction
        return MATS1D5Bond(
            mats_phase1=MATS1DElastic(E=0),
            mats_phase2=self.mats_f,
            mats_ifslip=self.mats_b,
            mats_ifopen=MATS1DElastic(E=0),  # elastic function of open - inactive
        )

    # -------------------------------------------------------
    # Finite element type
    # -------------------------------------------------------
    fets_m = Property(depends_on="+input")

    @cached_property
    def _get_fets_m(self):
        fets_eval = FETS1D2L(mats_eval=self.mats_m)
        # fets_eval = FETS1D2L3U( mats_eval = self.mats_m )
        return fets_eval

    fets_fb = Property(depends_on="+input")

    @cached_property
    def _get_fets_fb(self):
        return FETS1D52L4ULRH(mats_eval=self.mats_fb)
        # return FETS1D52L6ULRH( mats_eval = self.mats_fb )
        # return FETS1D52L8ULRH( mats_eval = self.mats_fb )

    # --------------------------------------------------------------------------------------
    # Mesh integrator
    # --------------------------------------------------------------------------------------
    fe_domain_structure = Property(depends_on="+input")

    @cached_property
    def _get_fe_domain_structure(self):
        """Root of the domain hierarchy
        """
        elem_length = self.length / float(self.shape)

        fe_domain = FEDomain()

        fe_m_level = FERefinementGrid(name="matrix domain", domain=fe_domain, fets_eval=self.fets_m)

        fe_grid_m = FEGrid(
            name="matrix grid",
            coord_max=(self.length,),
            shape=(self.shape,),
            level=fe_m_level,
            fets_eval=self.fets_m,
            geo_transform=self.geo_transform,
        )

        fe_fb_level = FERefinementGrid(name="fiber bond domain", domain=fe_domain, fets_eval=self.fets_fb)

        fe_grid_fb = FEGrid(
            coord_min=(0.0, length / 5.0),
            coord_max=(length, 0.0),
            shape=(self.shape, 1),
            level=fe_fb_level,
            fets_eval=self.fets_fb,
            geo_transform=self.geo_transform,
        )

        return fe_domain, fe_grid_m, fe_grid_fb, fe_m_level, fe_fb_level

    fe_domain = Property

    def _get_fe_domain(self):
        return self.fe_domain_structure[0]

    fe_grid_m = Property

    def _get_fe_grid_m(self):
        return self.fe_domain_structure[1]

    fe_grid_fb = Property

    def _get_fe_grid_fb(self):
        return self.fe_domain_structure[2]

    fe_m_level = Property

    def _get_fe_m_level(self):
        return self.fe_domain_structure[3]

    fe_fb_level = Property

    def _get_fe_fb_level(self):
        return self.fe_domain_structure[4]

    # ---------------------------------------------------------------------------
    # Load scaling adapted to the elastic and inelastic regime
    # ---------------------------------------------------------------------------
    final_displ = Property(depends_on="+input")

    @cached_property
    def _get_final_displ(self):
        damage_onset_displ = self.mats_m.epsilon_0 * self.length
        return damage_onset_displ / self.elastic_fraction

    step_size = Property(depends_on="+input")

    @cached_property
    def _get_step_size(self):
        n_steps = self.n_steps
        return 1.0 / float(n_steps)

    time_function = Property(depends_on="+input")

    @cached_property
    def _get_time_function(self):
        """Get the time function so that the elastic regime 
        is skipped in a single step.
        """
        step_size = self.step_size

        elastic_value = self.elastic_fraction * 0.98 * self.reduction_factor
        inelastic_value = 1.0 - elastic_value

        def ls(t):
            if t <= step_size:
                return (elastic_value / step_size) * t
            else:
                return elastic_value + (t - step_size) * (inelastic_value) / (1 - step_size)

        return ls

    def plot_time_function(self, p):
        """Plot the time function.
        """
        n_steps = self.n_steps
        mats = self.mats
        step_size = self.step_size

        ls_t = linspace(0, step_size * n_steps, n_steps + 1)
        ls_fn = frompyfunc(self.time_function, 1, 1)
        ls_v = ls_fn(ls_t)

        p.subplot(321)
        p.plot(ls_t, ls_v, "ro-")

        final_epsilon = self.final_displ / self.length

        kappa = linspace(mats.epsilon_0, final_epsilon, 10)
        omega_fn = frompyfunc(lambda kappa: mats._get_omega(None, kappa), 1, 1)
        omega = omega_fn(kappa)
        kappa_scaled = step_size + (1 - step_size) * (kappa - mats.epsilon_0) / (final_epsilon - mats.epsilon_0)
        xdata = hstack([array([0.0], dtype=float), kappa_scaled])
        ydata = hstack([array([0.0], dtype=float), omega])
        p.plot(xdata, ydata, "g")
        p.xlabel("regular time [-]")
        p.ylabel("scaled time [-]")

    run = Button

    @on_trait_change("run")
    def peval(self):
        """Evaluation procedure.
        """
        # mv = MATS1DDamageView( model = mats_eval )
        # mv.configure_traits()

        right_dof_m = self.fe_grid_m[-1, -1].dofs[0, 0, 0]

        right_dof_fb = self.fe_grid_fb[-1, -1, -1, -1].dofs[0, 0, 0]
        # Response tracers
        A = self.A_m + self.A_f
        self.sig_eps_m = RTraceGraph(
            name="F_u_m", var_y="F_int", idx_y=right_dof_m, var_x="U_k", idx_x=right_dof_m, transform_y="y / %g" % A
        )

        # Response tracers
        self.sig_eps_f = RTraceGraph(
            name="F_u_f", var_y="F_int", idx_y=right_dof_fb, var_x="U_k", idx_x=right_dof_fb, transform_y="y / %g" % A
        )

        self.eps_m_field = RTraceDomainListField(name="eps_m", position="int_pnts", var="eps_app", warp=False)

        self.eps_f_field = RTraceDomainListField(
            name="eps_f", position="int_pnts", var="mats_phase2_eps_app", warp=False
        )
        # Response tracers
        self.sig_m_field = RTraceDomainListField(name="sig_m", position="int_pnts", var="sig_app")

        self.sig_f_field = RTraceDomainListField(name="sig_f", position="int_pnts", var="mats_phase2_sig_app")

        self.omega_m_field = RTraceDomainListField(name="omega_m", position="int_pnts", var="omega", warp=False)

        self.shear_flow_field = RTraceDomainListField(
            name="shear flow", position="int_pnts", var="shear_flow", warp=False
        )

        self.slip_field = RTraceDomainListField(name="slip", position="int_pnts", var="slip", warp=False)

        avg_processor = None
        if self.avg_radius > 0.0:
            n_dofs = self.fe_domain.n_dofs
            avg_processor = RTUAvg(sd=self.fe_m_level, n_dofs=n_dofs, avg_fn=QuarticAF(radius=self.avg_radius))

        ts = TStepper(
            u_processor=avg_processor,
            dof_resultants=True,
            sdomain=self.fe_domain,
            bcond_list=[  # define the left clamping
                BCSlice(var="u", value=0.0, dims=[0], slice=self.fe_grid_fb[0, 0, 0, :]),
                #                                BCSlice( var = 'u', value = 0., dims = [0], slice = self.fe_grid_m[ 0, 0 ] ),
                # loading at the right edge
                #                                 BCSlice( var = 'f', value = 1, dims = [0], slice = domain[-1, -1, -1, 0],
                #                                         time_function = ls ),
                BCSlice(
                    var="u",
                    value=self.final_displ,
                    dims=[0],
                    slice=self.fe_grid_fb[-1, -1, -1, :],
                    time_function=self.time_function,
                ),
                #                                 BCSlice( var = 'u', value = self.final_displ, dims = [0], slice = self.fe_grid_m[-1, -1],
                #                                         time_function = self.time_function ),
                # fix horizontal displacement in the top layer
                #                                 BCSlice( var = 'u', value = 0., dims = [0], slice = domain[:, -1, :, -1] ),
                # fix the vertical displacement all over the domain
                BCSlice(var="u", value=0.0, dims=[1], slice=self.fe_grid_fb[:, :, :, :]),
                #                            # Connect bond and matrix domains
                BCDofGroup(
                    var="u",
                    value=0.0,
                    dims=[0],
                    get_link_dof_method=self.fe_grid_fb.get_bottom_dofs,
                    get_dof_method=self.fe_grid_m.get_all_dofs,
                    link_coeffs=[1.0],
                ),
            ],
            rtrace_list=[
                self.sig_eps_m,
                self.sig_eps_f,
                self.eps_m_field,
                self.eps_f_field,
                self.sig_m_field,
                self.sig_f_field,
                self.omega_m_field,
                self.shear_flow_field,
                self.slip_field,
            ],
        )

        # Add the time-loop control
        tloop = TLoop(
            tstepper=ts,
            KMAX=300,
            tolerance=1e-5,
            debug=False,
            verbose_iteration=True,
            verbose_time=False,
            tline=TLine(min=0.0, step=self.step_size, max=1.0),
        )

        tloop.on_accept_time_step = self.plot

        U = tloop.eval()

        self.sig_eps_f.refresh()
        max_sig_m = max(self.sig_eps_m.trace.ydata)
        return array([U[right_dof_m], max_sig_m], dtype="float_")

    # --------------------------------------------------------------------------------------
    # Tracers
    # --------------------------------------------------------------------------------------

    def plot_sig_eps(self, p):
        p.set_xlabel("control displacement [mm]")
        p.set_ylabel("stress [MPa]")

        self.sig_eps_m.refresh()
        self.sig_eps_m.trace.plot(p, "o-")

        self.sig_eps_f.refresh()
        self.sig_eps_f.trace.plot(p, "o-")

        p.plot(self.sig_eps_m.trace.xdata, self.sig_eps_m.trace.ydata + self.sig_eps_f.trace.ydata, "o-")

    def plot_eps(self, p):
        eps_m = self.eps_m_field.subfields[0]
        xdata = eps_m.vtk_X[:, 0]
        ydata = eps_m.field_arr[:, 0, 0]
        idata = argsort(xdata)
        p.plot(xdata[idata], ydata[idata], "o-")

        eps_f = self.eps_f_field.subfields[1]
        xdata = eps_f.vtk_X[:, 0]
        ydata = eps_f.field_arr[:, 0, 0]
        idata = argsort(xdata)
        p.plot(xdata[idata], ydata[idata], "o-")

        p.set_ylim(ymin=0)
        p.set_xlabel("bar axis [mm]")
        p.set_ylabel("strain [-]")

    def plot_omega(self, p):
        omega_m = self.omega_m_field.subfields[0]
        xdata = omega_m.vtk_X[:, 0]
        ydata = omega_m.field_arr[:]
        idata = argsort(xdata)
        p.fill(xdata[idata], ydata[idata], facecolor="gray", alpha=0.2)

        print "max omega", max(ydata[idata])

        p.set_ylim(ymin=0, ymax=1.0)
        p.set_xlabel("bar axis [mm]")
        p.set_ylabel("omega [-]")

    def plot_sig(self, p):
        sig_m = self.sig_m_field.subfields[0]
        xdata = sig_m.vtk_X[:, 0]
        ydata = sig_m.field_arr[:, 0, 0]
        idata = argsort(xdata)
        ymax = max(ydata)
        p.plot(xdata[idata], ydata[idata], "o-")

        sig_f = self.sig_f_field.subfields[1]
        xdata = sig_f.vtk_X[:, 0]
        ydata = sig_f.field_arr[:, 0, 0]
        idata = argsort(xdata)
        p.plot(xdata[idata], ydata[idata], "o-")

        xdata = sig_f.vtk_X[:, 0]
        ydata = sig_f.field_arr[:, 0, 0] + sig_m.field_arr[:, 0, 0]
        p.plot(xdata[idata], ydata[idata], "ro-")

        p.set_ylim(ymin=0)  # , ymax = 1.2 * ymax )
        p.set_xlabel("bar axis [mm]")
        p.set_ylabel("stress [MPa]")

    def plot_shear_flow(self, p):
        shear_flow = self.shear_flow_field.subfields[1]
        xdata = shear_flow.vtk_X[:, 0]
        ydata = shear_flow.field_arr[:, 0] / self.P_f
        idata = argsort(xdata)
        ymax = max(ydata)
        p.plot(xdata[idata], ydata[idata], "o-")

        p.set_xlabel("bar axis [mm]")
        p.set_ylabel("shear flow [N/m]")

    def plot_slip(self, p):
        slip = self.slip_field.subfields[1]
        xdata = slip.vtk_X[:, 0]
        ydata = slip.field_arr[:, 0]
        idata = argsort(xdata)
        ymax = max(ydata)
        p.plot(xdata[idata], ydata[idata], "ro-")

        p.set_xlabel("bar axis [mm]")
        p.set_ylabel("slip [N/m]")

    def plot_tracers(self, p=p):

        p.subplot(221)
        self.plot_sig_eps(p)

        p.subplot(223)
        self.plot_eps(p)

        p.subplot(224)
        self.plot_sig(p)

    # ---------------------------------------------------------------
    # PLOT OBJECT
    # -------------------------------------------------------------------
    figure_ld = Instance(Figure)

    def _figure_ld_default(self):
        figure = Figure(facecolor="white")
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    # ---------------------------------------------------------------
    # PLOT OBJECT
    # -------------------------------------------------------------------
    figure_eps = Instance(Figure)

    def _figure_eps_default(self):
        figure = Figure(facecolor="white")
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    # ---------------------------------------------------------------
    # PLOT OBJECT
    # -------------------------------------------------------------------
    figure_shear_flow = Instance(Figure)

    def _figure_shear_flow_default(self):
        figure = Figure(facecolor="white")
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    # ---------------------------------------------------------------
    # PLOT OBJECT
    # -------------------------------------------------------------------
    figure_sig = Instance(Figure)

    def _figure_sig_default(self):
        figure = Figure(facecolor="white")
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    # ---------------------------------------------------------------
    # PLOT OBJECT
    # -------------------------------------------------------------------
    figure_shear_flow = Instance(Figure)

    def _figure_shear_flow_default(self):
        figure = Figure(facecolor="white")
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    def plot(self):

        self.figure_ld.clear()
        ax = self.figure_ld.gca()
        self.plot_sig_eps(ax)

        self.figure_eps.clear()
        ax = self.figure_eps.gca()
        self.plot_eps(ax)
        ax2 = ax.twinx()
        self.plot_omega(ax2)

        self.figure_sig.clear()
        ax = self.figure_sig.gca()
        self.plot_sig(ax)
        ax2 = ax.twinx()
        self.plot_omega(ax2)

        self.figure_shear_flow.clear()
        ax = self.figure_shear_flow.gca()
        self.plot_shear_flow(ax)
        ax2 = ax.twinx()
        self.plot_slip(ax2)

        self.data_changed = True

    def get_sim_outputs(self):
        """
        Specifies the results and their order returned by the model
        evaluation.
        """
        return [SimOut(name="right end displacement", unit="m"), SimOut(name="peak load", uni="MPa")]

    data_changed = Event

    toolbar = (
        ToolBar(
            Action(name="Run", tooltip="Start computation", image=ImageResource("kt-start"), action="start_study"),
            Action(name="Pause", tooltip="Pause computation", image=ImageResource("kt-pause"), action="pause_study"),
            Action(name="Stop", tooltip="Stop computation", image=ImageResource("kt-stop"), action="stop_study"),
            image_size=(32, 32),
            show_tool_names=False,
            show_divider=True,
            name="view_toolbar",
        ),
    )

    traits_view = View(
        HSplit(
            VSplit(
                Item("run", show_label=False),
                VGroup(
                    Item("shape"),
                    Item("n_steps"),
                    Item("length"),
                    label="parameters",
                    id="crackloc.viewmodel.factor.geometry",
                    dock="tab",
                    scrollable=True,
                ),
                VGroup(
                    Item("E_m"),
                    Item("f_m_t"),
                    Item("avg_radius"),
                    Item("h_m"),
                    Item("b_m"),
                    Item("A_m", style="readonly"),
                    Item("mats_m", show_label=False),
                    label="Matrix",
                    dock="tab",
                    id="crackloc.viewmodel.factor.matrix",
                    scrollable=True,
                ),
                VGroup(
                    Item("E_f"),
                    Item("A_f"),
                    Item("mats_f", show_label=False),
                    label="Fiber",
                    dock="tab",
                    id="crackloc.viewmodel.factor.fiber",
                    scrollable=True,
                ),
                VGroup(
                    Group(
                        Item("tau_max"),
                        Item("s_crit"),
                        Item("P_f", style="readonly", show_label=True),
                        Item("K_b", style="readonly", show_label=True),
                        Item("T_max", style="readonly", show_label=True),
                    ),
                    Item("mats_b", show_label=False),
                    label="Bond",
                    dock="tab",
                    id="crackloc.viewmodel.factor.bond",
                    scrollable=True,
                ),
                VGroup(
                    Item("rho", style="readonly", show_label=True),
                    label="Composite",
                    dock="tab",
                    id="crackloc.viewmodel.factor.jcomposite",
                    scrollable=True,
                ),
                id="crackloc.viewmodel.left",
                label="studied factors",
                layout="tabbed",
                dock="tab",
            ),
            VSplit(
                VGroup(
                    Item("figure_ld", editor=MPLFigureEditor(), resizable=True, show_label=False),
                    label="stress-strain",
                    id="crackloc.viewmode.figure_ld_window",
                    dock="tab",
                ),
                VGroup(
                    Item("figure_eps", editor=MPLFigureEditor(), resizable=True, show_label=False),
                    label="strains profile",
                    id="crackloc.viewmode.figure_eps_window",
                    dock="tab",
                ),
                VGroup(
                    Item("figure_sig", editor=MPLFigureEditor(), resizable=True, show_label=False),
                    label="stress profile",
                    id="crackloc.viewmode.figure_sig_window",
                    dock="tab",
                ),
                VGroup(
                    Item("figure_shear_flow", editor=MPLFigureEditor(), resizable=True, show_label=False),
                    label="bond shear and slip profiles",
                    id="crackloc.viewmode.figure_shear_flow_window",
                    dock="tab",
                ),
                id="crackloc.viewmodel.right",
            ),
            id="crackloc.viewmodel.splitter",
        ),
        title="SimVisage Component: Crack localization",
        id="crackloc.viewmodel",
        dock="tab",
        resizable=True,
        height=0.8,
        width=0.8,
        buttons=[OKButton],
    )
Beispiel #19
0
def run():
    #-------------------------------------------------------------------------
    # Example using the mats2d_explore
    #-------------------------------------------------------------------------
    from ibvpy.mats.mats2D.mats2D_explore import MATS2DExplore
    from ibvpy.mats.mats2D.mats2D_rtrace_cylinder import MATS2DRTraceCylinder

    from ibvpy.mats.mats2D.mats2D_cmdm.mats2D_cmdm_rtrace_Gf_mic import \
        MATS2DMicroplaneDamageTraceGfmic, \
        MATS2DMicroplaneDamageTraceEtmic, MATS2DMicroplaneDamageTraceUtmic

    from ibvpy.mats.mats2D.mats2D_cmdm.mats2D_cmdm_rtrace_Gf_mac import \
        MATS2DMicroplaneDamageTraceGfmac, \
        MATS2DMicroplaneDamageTraceEtmac, MATS2DMicroplaneDamageTraceUtmac

    from ibvpy.mats.mats2D.mats2D_cmdm.mats2D_cmdm import \
        MATS2DMicroplaneDamage, MATS1DMicroplaneDamage

    from ibvpy.mats.matsXD.matsXD_cmdm import \
        PhiFnGeneral, PhiFnStrainHardening

    from ibvpy.api import RTraceGraph, RTraceArraySnapshot

    from mathkit.mfn import MFnLineArray
    from numpy import array, hstack

    from ibvpy.mats.mats2D.mats2D_explorer_bcond import BCDofProportional
    from os.path import join

    ec = {
        # overload the default configuration
        'bcond_list': [BCDofProportional(max_strain=1.0, alpha_rad=0.0)],
        'rtrace_list': [
            RTraceGraph(name='stress - strain',
                        var_x='eps_app',
                        idx_x=0,
                        var_y='sig_app',
                        idx_y=0,
                        record_on='iteration'),
        ],
    }

    mats_eval = MATS2DMicroplaneDamage(
        n_mp=15,
        # mats_eval = MATS1DMicroplaneDamage(
        elastic_debug=False,
        stress_state='plane_stress',
        symmetrization='sum-type',
        model_version='compliance',
        phi_fn=PhiFnGeneral,
    )

    #    print 'normals', mats_eval._MPN
    #    print 'weights', mats_eval._MPW

    fitter = MATSCalibDamageFn(
        KMAX=300,
        tolerance=5e-4,  # 0.01,
        RESETMAX=0,
        dim=MATS2DExplore(
            mats_eval=mats_eval,
            explorer_config=ec,
        ),
        store_fitted_phi_fn=True,
        log=False)

    #-------------------------------------------
    # run fitter for entire available test data:
    #-------------------------------------------

    calibrate_all = False

    if calibrate_all:
        from matresdev.db.exdb.ex_run_table import \
            ExRunClassExt


#         from matresdev.db.exdb.ex_composite_tensile_test import \
#             ExCompositeTensileTest
#         ex = ExRunClassExt(klass=ExCompositeTensileTest)
#         for ex_run in ex.ex_run_list:
#             if ex_run.ready_for_calibration:
#                 print 'FITTING', ex_run.ex_type.key
#                 # 'E_c' of each test is different, therefore 'mats_eval'
#                 # needs to be defined for each test separately.
#                 #
#                 E_c = ex_run.ex_type.E_c
#                 nu = ex_run.ex_type.ccs.concrete_mixture_ref.nu
#
#                 # run calibration
#                 #
#                 fitter.ex_run = ex_run
#                 fitter.dim.mats_eval.E = E_c
#                 fitter.dim.mats_eval.nu = nu
#                 fitter.init()
#                 fitter.fit_response()

    else:

        test_file = join(
            simdb.exdata_dir,
            'tensile_tests',
            'dog_bone',
            #                              'buttstrap_clamping',
            '2010-02-09_TT-10g-3cm-a-TR_TRC11',
            #                              'TT11-10a-average.DAT' )
            'TT-10g-3cm-a-TR-average.DAT')

        #-----------------------------------
        # tests for 'BT-3PT-12c-6cm-TU_ZiE'
        #-----------------------------------
        # 'ZiE-S1': test series no. 1 (age = 11d)
        #
        #                                 '2011-05-23_TT-12c-6cm-0-TU_ZiE',
        #                                 'TT-12c-6cm-0-TU-V2.DAT')

        # 'ZiE-S2': test series no. 2 (age = 9d)
        #
        #                                 '2011-06-10_TT-12c-6cm-0-TU_ZiE',
        #                                 'TT-12c-6cm-0-TU-V2.DAT')

        #-----------------------------------
        # tests for 'BT-4PT-12c-6cm-TU_SH4'
        # tests for 'ST-12c-6cm-TU' (fresh)
        #-----------------------------------
        # @todo: add missing front strain information from Aramis3d testing
        #
        #                               '2012-04-12_TT-12c-6cm-0-TU_SH4-Aramis3d',
        #                               'TT-12c-6cm-0-TU-SH4-V2.DAT')

        #                                '2012-02-14_TT-12c-6cm-0-TU_SH2',
        #                                'TT-12c-6cm-0-TU-SH2-V2.DAT')

        #                                '2012-02-14_TT-12c-6cm-0-TU_SH2',
        #                                'TT-12c-6cm-0-TU-SH2F-V3.DAT')

        # used for suco(!)
        #                                '2012-02-14_TT-12c-6cm-0-TU_SH2',
        #                                'TT-12c-6cm-0-TU-SH2-V1.DAT')

        #-----------------------------------
        # tests for 'BT-3PT-6c-2cm-TU_bs'
        #-----------------------------------
        # barrelshell
        #
        #                                 # TT-bs1
        #                                 '2013-05-17_TT-6c-2cm-0-TU_bs1',
        #                                 'TT-6c-2cm-0-TU-V3_bs1.DAT')
        #                                 # TT-bs2
        #                                 '2013-05-21-TT-6c-2cm-0-TU_bs2',
        #                                 'TT-6c-2cm-0-TU-V1_bs2.DAT')
        #                                 # TT-bs3
        #                                 '2013-06-12_TT-6c-2cm-0-TU_bs3',
        #                                 'TT-6c-2cm-0-TU-V1_bs3.DAT')
        #                                 # TTb-bs4-Aramis3d
        #                                  '2013-07-09_TTb-6c-2cm-0-TU_bs4-Aramis3d',
        #                                  'TTb-6c-2cm-0-TU-V2_bs4.DAT')

        #-----------------------------------
        # tests for 'TT-6c-2cm-90-TU'
        #-----------------------------------
        #
        #                                '2013-05-22_TTb-6c-2cm-90-TU-V3_bs1',
        #                                'TTb-6c-2cm-90-TU-V3_bs1.DAT')

        #                               '2013-05-17_TT-6c-2cm-0-TU_bs1',
        #                               'TT-6c-2cm-90-TU-V3_bs1.DAT')

        #        test_file = join(simdb.exdata_dir,
        #                               'tensile_tests',
        #                               'buttstrap_clamping',
        #                               '2013-07-18_TTb-6c-2cm-0-TU_bs5',
        #                               'TTb-6c-2cm-0-TU-V1_bs5.DAT')
        # #                               'TTb-6c-2cm-0-TU-V3_bs5.DAT')
        #
        #        test_file = join(simdb.exdata_dir,
        #                               'tensile_tests',
        #                               'buttstrap_clamping',
        #                               '2013-07-09_TTb-6c-2cm-0-TU_bs4-Aramis3d',
        #                               'TTb-6c-2cm-0-TU-V2_bs4.DAT')

        #-----------------------------------
        # tests for 'TT-6g-2cm-0-TU' (ARG-1200-TU)
        #-----------------------------------
        #
        # test series no.1
        #
        #        test_file = join(simdb.exdata_dir,
        #                               'tensile_tests',
        #                               'dog_bone',
        #                               '2012-12-10_TT-6g-2cm-0-TU_bs',
        #                               'TT-6g-2cm-0-V2.DAT')
        # test series no.3
        #
        #        test_file = join(simdb.exdata_dir,
        #                               'tensile_tests',
        #                               'buttstrap_clamping',
        #                               '2013-07-09_TTb-6g-2cm-0-TU_bs4-Aramis3d',
        #                               'TTb-6g-2cm-0-TU-V1_bs4.DAT')

        # test series NxM_1
        #
        #        test_file = join(simdb.exdata_dir,
        #                          'tensile_tests',
        #                          'buttstrap_clamping',
        #                          '2014-04-30_TTb-6c-2cm-0-TU_NxM1',
        #                          'TTb-6c-2cm-0-TU-V16_NxM1.DAT')

        #------------------------------------------------------------------
        # set 'ex_run' of 'fitter' to selected calibration test
        #------------------------------------------------------------------
        #
        ex_run = ExRun(data_file=test_file)
        fitter.ex_run = ex_run

        #------------------------------------------------------------------
        # specify the parameters used within the calibration
        #------------------------------------------------------------------
        #
        # get the composite E-modulus and Poisson's ratio as stored
        # in the experiment data base for the specified age of the tensile test
        #
        E_c = ex_run.ex_type.E_c
        print('E_c', E_c)

        #        # use the value as graphically determined from the tensile test (= initial stiffness for tension)
        #        E_c = 28000.

        # age, Em(age), and nu of the slab test or bending test determines the
        # calibration parameters. Those are used for calibration and are store in the 'param_key'
        # appendet to the calibration-test-key
        #
        age = 28

        # E-modulus of the concrete matrix at the age of testing
        # NOTE: value is more relevant as compression behavior is determined by it in the bending tests and slab tests;
        # behavior in the tensile zone is defined by calibrated 'phi_fn' with the predefined 'E_m'
        #        E_m = ex_run.ex_type.ccs.get_E_m_time(age)
        E_c = ex_run.ex_type.ccs.get_E_c_time(age)

        # use average E-modul from 0- and 90-degree direction for fitter in both directions
        # this yields the correct tensile behavior and returns the best average compressive behavior
        #
        #        E_c = 22313.4

        # alternatively use maximum E-modul from 90-direction also for 0-degree direction for fitting
        # this yields the correct tensile behavior also in the linear elastic regime for both directions corresponding to the
        # tensile test behavior (note that the compressive E-Modulus in this case is overestimated in 0-degree direction; minor influence
        # assumed as behavior is governed by inelastic tensile behavior and anisotropic redistrirbution;
        #
        #        E_c = 29940.2
        #        E_c = 29100.
        #        E_c = 22390.4
        #        E_c = 18709.5
        E_c = 28700.

        # smallest value for matrix E-modulus obtained from cylinder tests (d=150mm)
        #        E_m = 18709.5

        # set 'nu'
        # @todo: check values stored in 'mat_db'
        #
        nu = 0.20
        ex_run.ex_type.ccs.concrete_mixture_ref.nu = nu

        n_steps = 200
        fitter.n_steps = n_steps

        fitter.format_ticks = True

        fitter.ex_run.ex_type.age = age
        print('age = %g used for calibration' % age)
        fitter.ex_run = ex_run

        #        print 'E_m(age) = %g used for calibration' % E_m
        #        fitter.dim.mats_eval.E = E_m

        print('E_c(age) = %g used for calibration' % E_c)
        fitter.dim.mats_eval.E = E_c

        print('nu = %g used for calibration' % nu)
        fitter.dim.mats_eval.nu = nu

        print('n_steps = %g used for calibration' % n_steps)

        max_eps = fitter.max_eps
        print('max_eps = %g used for calibration' % max_eps)

        #------------------------------------------------------------------
        # set 'param_key' of 'fitter' to store calibration params in the name
        #------------------------------------------------------------------
        #
        #        param_key = '_age%g_Em%g_nu%g_nsteps%g' % (age, E_m, nu, n_steps)
        #        param_key = '_age%g_Ec%g_nu%g_nsteps%g__smoothed' % (age, E_c, nu, n_steps, max_eps)
        param_key = '_age%g_Ec%g_nu%g_nsteps%g_smoothed' % (age, E_c, nu,
                                                            n_steps)

        fitter.param_key = param_key
        print('param_key = %s used in calibration name' % param_key)

        #------------------------------------------------------------------
        # run fitting procedure
        #------------------------------------------------------------------
        #
        import pylab as p
        ax = p.subplot(111)
        fitter.mfn_line_array_target.mpl_plot(ax)
        p.show()

        fitter.init()
        fitter.fit_response()
        fitter.store()
        fitter.plot_trial_steps()

    return

    #---------------------------
    # basic testing of fitter methods:
    #---------------------------

    # set to True for basic testing of the methods:
    basic_tests = False

    if basic_tests:
        fitter.run_through()
        #    fitter.tloop.rtrace_mngr.rtrace_bound_list[0].configure_traits()
        fitter.tloop.rtrace_mngr.rtrace_bound_list[0].redraw()
        last_strain_run_through = fitter.tloop.rtrace_mngr.rtrace_bound_list[
            0].trace.xdata[:]
        last_stress_run_through = fitter.tloop.rtrace_mngr.rtrace_bound_list[
            0].trace.ydata[:]
        print('last strain (run-through) value', last_strain_run_through)
        print('last stress (run-through) value', last_stress_run_through)

        fitter.tloop.reset()
        fitter.run_step_by_step()
        # fitter.tloop.rtrace_mngr.rtrace_bound_list[0].configure_traits()
        fitter.tloop.rtrace_mngr.rtrace_bound_list[0].redraw()
        last_strain_step_by_step = fitter.tloop.rtrace_mngr.rtrace_bound_list[
            0].trace.xdata[:]
        last_stress_step_by_step = fitter.tloop.rtrace_mngr.rtrace_bound_list[
            0].trace.ydata[:]
        print('last stress (step-by-step) value', last_stress_step_by_step)

        fitter.run_trial_step()
        fitter.run_trial_step()
        fitter.tloop.rtrace_mngr.rtrace_bound_list[0].redraw()
        strain_after_trial_steps = fitter.tloop.rtrace_mngr.rtrace_bound_list[
            0].trace.xdata[:]
        stress_after_trial_steps = fitter.tloop.rtrace_mngr.rtrace_bound_list[
            0].trace.ydata[:]
        print('stress after trial', stress_after_trial_steps)

        fitter.init()
        # fitter.mats2D_eval.configure_traits()
        lof = fitter.get_lack_of_fit(1.0)
        print('1', lof)
        lof = fitter.get_lack_of_fit(0.9)
        print('2', lof)

        # fitter.tloop.rtrace_mngr.configure_traits()
        fitter.run_trial_step()

    else:
        from ibvpy.plugins.ibvpy_app import IBVPyApp
        ibvpy_app = IBVPyApp(ibv_resource=fitter)
        ibvpy_app.main()
Beispiel #20
0
class SimCrackLoc( IBVModel ):
    '''Model assembling the components for studying the restrained crack localization.
    '''
    shape = Int( 1, desc = 'Number of finite elements',
                   ps_levsls = ( 10, 40, 4 ) )
    length = Float( 1, desc = 'Length of the simulated region' )

    #-------------------------------------------------------
    # Material model for the matrix
    #-------------------------------------------------------
    mats_m = Instance( MATS1DCrackLoc )
    def _mats_m_default( self ):
        E_m = 1
        mats_m = MATS1DCrackLoc( E = E_m,
                                 R = 0.5,
                                 epsilon_0 = 0.001,
                                 epsilon_f = 0.01 )
        return mats_m

    mats_f = Instance( MATS1DElastic )
    def _mats_f_default( self ):
        E_f = 0
        mats_f = MATS1DElastic( E = E_f )
        return mats_f

    mats_b = Instance( MATS1DElastic )
    def _mats_b_default( self ):
        E_b = 0
        mats_b = MATS1DElastic( E = E_b )
        return mats_b

    mats = Instance( MATS1D5Bond )
    def _mats_default( self ):

        # Material model construction
        mats = MATS1D5Bond( mats_phase1 = self.mats_m,
                            mats_phase2 = self.mats_f,
                            mats_ifslip = self.mats_b,
                            mats_ifopen = MATS1DElastic( E = 0 )   # elastic function of open - inactive
                            )
        return mats
    #-------------------------------------------------------
    # Finite element type
    #-------------------------------------------------------
    fets = Instance( FETSEval )
    def _fets_default( self ):
        #return FETS1D52L8ULRH( mats_eval = self.mats )        
        return FETS1D52L4ULRH( mats_eval = self.mats )
        #return FETS1D2L3U( mats_eval = self.mats ) 

    run = Button

    @on_trait_change( 'run' )
    def peval( self ):
        '''Evaluation procedure.
        '''
        #mv = MATS1DDamageView( model = mats_eval )
        #mv.configure_traits()

        self.mats_m.reset_state()
        # Discretization
        #
        length = self.length
        domain = FEGrid( coord_min = ( 0., length / 5. ),
                          coord_max = ( length, 0. ),
                          shape = ( self.shape, 1 ),
                          fets_eval = self.fets )

        right_dofs = domain[-1, -1, -1, :].dofs[0, :, 0]
        print 'concrete_dofs', id( domain ), domain[:, 0, :, 0].dofs
        # Response tracers
        self.stress_strain = RTraceGraph( name = 'Fi,right over u_right (iteration)' ,
                                   var_y = 'F_int', idx_y = right_dofs[0],
                                   var_x = 'U_k', idx_x = right_dofs[0] )
        self.eps_m_field = RTraceDomainListField( name = 'eps_m' , position = 'int_pnts',
                                           var = 'eps1', idx = 0,
                                           warp = True )

        self.eps_f_field = RTraceDomainListField( name = 'eps_f' , position = 'int_pnts',
                                           var = 'eps2', idx = 0,
                                           warp = True )

        # Response tracers
        self.sig_m_field = RTraceDomainListField( name = 'sig_m' , position = 'int_pnts',
                                              var = 'mats_phase1_sig_app', idx = 0 )
        self.sig_f_field = RTraceDomainListField( name = 'sig_f' , position = 'int_pnts',
                                              var = 'mats_phase2_sig_app', idx = 0 )
        self.omega_m_field = RTraceDomainListField( name = 'omega_m' , position = 'int_pnts',
                                           var = 'mats_phase1_omega', idx = 0,
                                           warp = True )
        # 

        damage_onset_displ = self.mats_m.epsilon_0 * self.length
        go_behind = 1.5
        finish_displ = go_behind * damage_onset_displ
        n_steps = 20
        step_size = ( finish_displ - damage_onset_displ ) / n_steps
        tmax = 1 + n_steps

        def ls( t ):
            if t <= 1:
                return t
            else:
                return 1.0 + ( t - 1.0 ) / n_steps * ( go_behind - 1 )

        ts = TSCrackLoc( 
                 dof_resultants = True,
                 on_update = self.plot,
                 sdomain = domain,
                 bcond_list = [# define the left clamping 
                                BCSlice( var = 'u', value = 0., dims = [0], slice = domain[ 0, 0, 0, :] ),
                                # loading at the right edge
                                 BCSlice( var = 'f', value = 1, dims = [0], slice = domain[-1, -1, -1, 0],
                                         time_function = ls ),
#                                 BCSlice(var='u', value = finish_displ, dims = [0], slice = domain[-1,-1,-1, 0],
#                                         time_function = ls ),
                                # fix horizontal displacement in the top layer
                                 BCSlice( var = 'u', value = 0., dims = [0], slice = domain[:, -1, :, -1] ),
                                # fix the vertical displacement all over the domain
                                 BCSlice( var = 'u', value = 0., dims = [1], slice = domain[ :, :, :, :] )
                                ],
                 rtrace_list = [ self.stress_strain,
                                  self.eps_m_field,
                                  self.eps_f_field,
                                  self.sig_m_field,
                                  self.sig_f_field,
                                  self.omega_m_field ]
                )

        # Add the time-loop control
        tloop = TLoop( tstepper = ts, KMAX = 200, debug = True, tolerance = 1e-5,
                       tline = TLine( min = 0.0, step = 1.0, max = 1.0 ) )

        print ts.rte_dict.keys()
        U = tloop.eval()

        self.plot()

        return array( [ U[right_dofs[-1]] ], dtype = 'float_' )

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_ld = Instance( Figure )
    def _figure_ld_default( self ):
        figure = Figure( facecolor = 'white' )
        figure.add_axes( [0.12, 0.13, 0.85, 0.74] )
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_eps = Instance( Figure )
    def _figure_eps_default( self ):
        figure = Figure( facecolor = 'white' )
        figure.add_axes( [0.12, 0.13, 0.85, 0.74] )
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_omega = Instance( Figure )
    def _figure_omega_default( self ):
        figure = Figure( facecolor = 'white' )
        figure.add_axes( [0.12, 0.13, 0.85, 0.74] )
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_sig = Instance( Figure )
    def _figure_sig_default( self ):
        figure = Figure( facecolor = 'white' )
        figure.add_axes( [0.12, 0.13, 0.85, 0.74] )
        return figure

    def plot( self ):
        self.stress_strain.refresh()
        t = self.stress_strain.trace
        ax = self.figure_ld.axes[0]
        ax.clear()
        ax.plot( t.xdata, t.ydata, linewidth = 2, color = 'blue' )

        ax = self.figure_eps.axes[0]
        ax.clear()

        ef = self.eps_m_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'grey' )

        ef = self.eps_f_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'red' )
        ax.legend( ['eps_m', 'eps_f'] )

        ax = self.figure_sig.axes[0]
        ax.clear()

        ef = self.sig_m_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'grey' )

        ef = self.sig_f_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'red' )
        ax.legend( ['sig_m', 'sig_f'] )


        ax = self.figure_omega.axes[0]
        ax.clear()

        ef = self.omega_m_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'brown' )
        ax.legend( ['omega_m'] )


        self.data_changed = True

    def get_sim_outputs( self ):
        '''
        Specifies the results and their order returned by the model
        evaluation.
        '''
        return [ SimOut( name = 'right end displacement', unit = 'm' ) ]

    data_changed = Event

    toolbar = ToolBar( 
                      Action( name = "Run",
                             tooltip = 'Start computation',
                             image = ImageResource( 'kt-start' ),
                             action = "start_study" ),
                      Action( name = "Pause",
                             tooltip = 'Pause computation',
                             image = ImageResource( 'kt-pause' ),
                             action = "pause_study" ),
                      Action( name = "Stop",
                             tooltip = 'Stop computation',
                             image = ImageResource( 'kt-stop' ),
                             action = "stop_study" ),
                      image_size = ( 32, 32 ),
                      show_tool_names = False,
                      show_divider = True,
                      name = 'view_toolbar' ),

    traits_view = View( 
                    HSplit( 
                        VSplit( 
                                Item( 'run', show_label = False ),
                            VGroup( 
                                 Item( 'shape' ),
                                 Item( 'n_sjteps' ),
                                 Item( 'length' ),
                                 label = 'parameters',
                                 id = 'crackloc.viewmodel.factor.geometry',
                                 dock = 'tab',
                                 scrollable = True,
                                 ),
                            VGroup( 
                                 Item( 'mats_m@', show_label = False ),
                                 label = 'Matrix',
                                 dock = 'tab',
                                 id = 'crackloc.viewmodel.factor.matrix',
                                 scrollable = True
                                 ),
                            VGroup( 
                                 Item( 'mats_f@', show_label = False ),
                                 label = 'Fiber',
                                 dock = 'tab',
                                 id = 'crackloc.viewmodel.factor.fiber',
                                 scrollable = True
                                 ),
                            VGroup( 
                                 Item( 'mats_b@', show_label = False ),
                                 label = 'Bond',
                                 dock = 'tab',
                                 id = 'crackloc.viewmodel.factor.bond',
                                 scrollable = True
                                ),
                            id = 'crackloc.viewmodel.left',
                            label = 'studied factors',
                            layout = 'tabbed',
                            dock = 'tab',
                            ),
                               VSplit( 
                                    VGroup( 
                                        Item( 'figure_ld', editor = MPLFigureEditor(),
                                             resizable = True, show_label = False ),
                                             label = 'stress-strain',
                                            id = 'crackloc.viewmode.figure_ld_window',
                                            dock = 'tab',
                                    ),
                                    VGroup( 
                                        Item( 'figure_eps', editor = MPLFigureEditor(),
                                             resizable = True, show_label = False ),
                                             label = 'strains profile',
                                            id = 'crackloc.viewmode.figure_eps_window',
                                            dock = 'tab',
                                        ),
                                    VGroup( 
                                        Item( 'figure_sig', editor = MPLFigureEditor(),
                                             resizable = True, show_label = False ),
                                             label = 'stress profile',
                                            id = 'crackloc.viewmode.figure_sig_window',
                                            dock = 'tab',
                                        ),
                                    VGroup( 
                                        Item( 'figure_omega', editor = MPLFigureEditor(),
                                             resizable = True, show_label = False ),
                                             label = 'omega profile',
                                            id = 'crackloc.viewmode.figure_omega_window',
                                            dock = 'tab',
                                        ),
                                   id = 'crackloc.viewmodel.right',
                                 ),
                            id = 'crackloc.viewmodel.splitter',
                        ),
                        title = 'SimVisage Component: Crack localization',
                        id = 'crackloc.viewmodel',
                        dock = 'tab',
                        resizable = True,
                        height = 0.8, width = 0.8,
                        buttons = [OKButton] )
    # Discretization
    domain = FEGrid( coord_max = (L_quater,L_quater,thickness ), 
                     shape   = (n_xy, n_xy, n_z),
                     fets_eval = fets_eval)

    upper_left_corner = domain[-1,-1,-1,-1,-1,-1].dofs[0,0,2]

    bc_symplane_yz  = BCSlice( var = 'u', value = 0., dims = [0], slice = domain[-1,:,:,-1,:,:] )
    bc_symplane_xz  = BCSlice( var = 'u', value = 0., dims = [1], slice = domain[:,-1,:,:,-1,:] )
    bc_support_000  = BCSlice( var = 'u', value = 0., dims = [2], slice = domain[0,0,0,0,0,0] )
    bc_center_w     = BCSlice( var = 'u', value = w_max, dims = [2], slice = domain[-1,-1,-1,-1,-1,-1] )

    f_w_diagram = RTraceGraph(name = 'time - reaction 2',
                                       var_x = 'U_k', idx_x = upper_left_corner,
                                       var_y = 'F_int', idx_y = 2,
                                       record_on = 'update',
                                       transform_x = '-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       transform_y = '4 * 1000 * y' )                                     
    ts = TS(
            sdomain = domain,
            bcond_list = [bc_symplane_yz, bc_symplane_xz, bc_support_000, 
                          bc_center_w,
                        ],
             rtrace_list = [      
                         f_w_diagram,
                         RTraceDomainListField(name = 'Stress' ,
                                        var = 'sig_app', idx = 0, warp = True, 
                                        record_on = 'update'),
                         RTraceDomainListField(name = 'Strain' ,
                                        var = 'eps_app', idx = 0, warp = True, 
                                        record_on = 'update'),                        
Beispiel #22
0
if __name__ == '__main__':

    from ibvpy.api import TLoop, TLine, BCDof, \
        IBVPSolve as IS

    tl = TLoop(tstepper=TS(tse=TSFn1D()),
               tolerance=1e-8,
               # debug = True,
               KMAX=4,
               verbose_iteration=True,
               tline=TLine(min=0.0, step=0.25, max=1.0))
    # tl.tstepper.bcond_list = [ BCDof( var = 'u', dof = 0, value = 1.0 ) ]
    tl.tstepper.bcond_list = [BCDof(var='f', dof=0, value=0.9)]
    tl.tstepper.rtrace_list = [
        RTraceGraph(name='u_update',
                    var_x='U_k', idx_x=0,
                    var_y='F_int', idx_y=0,
                    record_on='update'),
        RTraceGraph(name='u_iter',
                    var_x='U_k', idx_x=0,
                    var_y='F_int', idx_y=0,
                    record_on='iteration')
    ]

    tl.eval()

    for rt in tl.tstepper.rtrace_list:
        rt.refresh()
        rt.trace.plot(p, 'o-')
    p.show()
Beispiel #23
0
    def _get_tloop(self):

        #--------------------------------------------------------------
        # ts 
        #--------------------------------------------------------------

        mid_zone_spec = self.mid_zone_specmn_fe_grid
        load_zone_spec = self.load_zone_specmn_fe_grid
        outer_zone_spec = self.outer_zone_specmn_fe_grid

        if self.elstmr_flag:
            # ELSTRMR TOP SURFACE
            # dofs at elastomer top surface (used to integrate the force)
            #
            elastomer = self.elstmr_fe_grid
            elstmr_top_dofs_z = elastomer[:, :, -1, :, :, -1].dofs[:, :, 2].flatten()
            load_dofs_z = np.unique(elstmr_top_dofs_z)
            print 'load_dofs_z', load_dofs_z
        else:
            # LINE LOAD TOP OF LOAD ZONE
            # dofs at center line of the specmn load zone (used to integrate the force)
            # note slice index in x-direction is only valid for load_zone_shape_x = 2 !
            #
            load_zone_spec_topline_dofs_z = load_zone_spec[0, :, -1, -1, :, -1].dofs[:, :, 2].flatten()
            load_dofs_z = np.unique(load_zone_spec_topline_dofs_z)
            print 'load_dofs_z', load_dofs_z

        # SUPPRT LINE
        # dofs at support line of the specmn (used to integrate the force)
        #
        outer_zone_spec_supprtline_dofs_z = outer_zone_spec[-1, :, 0, -1, :, 0].dofs[:, :, 2].flatten()
        supprt_dofs_z = np.unique(outer_zone_spec_supprtline_dofs_z)
        print 'supprt_dofs_z', supprt_dofs_z

        # CENTER DOF (used for tracing of the displacement)
        #
        center_bottom_dof = mid_zone_spec[0, 0, 0, 0, 0, 0].dofs[0, 0, 2]
        print 'center_bottom_dof', center_bottom_dof

        # THIRDPOINT DOF (used for tracing of the displacement) 
        # dofs at center middle of the laod zone at the bottom side
        #
        # NOTE: slice index in x-direction is only valid for load_zone_shape_x = 2 !
        thirdpoint_bottom_dof = load_zone_spec[0, 0, 0, -1, 0, 0].dofs[0, 0, 2]
        print 'thirdpoint_bottom_dof', thirdpoint_bottom_dof

        # force-displacement-diagram (CENTER) 
        # 
        self.f_w_diagram_center = RTraceGraph(name='displacement_elasttop (center) - force',
                                       var_x='U_k'  , idx_x=center_bottom_dof,
                                       var_y='F_int', idx_y_arr=load_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='-4000. * y')

        # force-displacement-diagram_supprt (SUPPRT)
        # 
        self.f_w_diagram_supprt = RTraceGraph(name='displacement_supprtline (center) - force',
                                       var_x='U_k'  , idx_x=center_bottom_dof,
                                       var_y='F_int', idx_y_arr=supprt_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='4000. * y')

        # force-displacement-diagram (THIRDPOINT) 
        # 
        self.f_w_diagram_thirdpoint = RTraceGraph(name='displacement_elasttop (thirdpoint) - force',
                                       var_x='U_k'  , idx_x=thirdpoint_bottom_dof,
                                       var_y='F_int', idx_y_arr=load_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='-4000. * y')

        ts = TS(
                sdomain=self.fe_domain,
                bcond_list=self.bc_list,
                rtrace_list=[
                             self.f_w_diagram_center,
                             self.f_w_diagram_thirdpoint,
                             self.f_w_diagram_supprt,
                             RTraceDomainListField(name='Displacement' ,
                                            var='u', idx=0, warp=True),
#                             RTraceDomainListField(name = 'Stress' ,
#                                            var = 'sig_app', idx = 0, warp = True,
#                                            record_on = 'update'),
#                             RTraceDomainListField(name = 'Strain' ,
#                                        var = 'eps_app', idx = 0, warp = True,
#                                        record_on = 'update'),
#                             RTraceDomainListField(name = 'Damage' ,
#                                        var = 'omega_mtx', idx = 0, warp = True,
#                                        record_on = 'update'),
                             RTraceDomainListField(name='max_omega_i', warp=True,
                                        var='max_omega_i', idx=0,
                                        record_on='update'),
#                             RTraceDomainListField(name = 'IStress' ,
#                                            position = 'int_pnts',
#                                            var = 'sig_app', idx = 0,
#                                            record_on = 'update'),
#                             RTraceDomainListField(name = 'IStrain' ,
#                                            position = 'int_pnts',
#                                            var = 'eps_app', idx = 0,
#                                            record_on = 'update'),
                              ]
                )

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      KMAX=50,
                      tolerance=self.tolerance,
                      RESETMAX=0,
                      tline=TLine(min=0.0, step=self.tstep, max=self.tmax),
                      ord=self.ord
                      )

        return tloop
Beispiel #24
0
class SimCrackLoc( IBVModel ):
    '''Model assembling the components for studying the restrained crack localization.
    '''
    shape = Int( 1, desc = 'Number of finite elements',
                   ps_levsls = ( 10, 40, 4 ) )
    length = Float( 1, desc = 'Length of the simulated region' )

    #-------------------------------------------------------
    # Material model for the matrix
    #-------------------------------------------------------
    mats_m = Instance( MATS1DCrackLoc )
    def _mats_m_default( self ):
        E_m = 1
        mats_m = MATS1DCrackLoc( E = E_m,
                                 R = 0.5,
                                 epsilon_0 = 0.001,
                                 epsilon_f = 0.01 )
        return mats_m

    mats_f = Instance( MATS1DElastic )
    def _mats_f_default( self ):
        E_f = 0
        mats_f = MATS1DElastic( E = E_f )
        return mats_f

    mats_b = Instance( MATS1DElastic )
    def _mats_b_default( self ):
        E_b = 0
        mats_b = MATS1DElastic( E = E_b )
        return mats_b

    mats = Instance( MATS1D5Bond )
    def _mats_default( self ):

        # Material model construction
        mats = MATS1D5Bond( mats_phase1 = self.mats_m,
                            mats_phase2 = self.mats_f,
                            mats_ifslip = self.mats_b,
                            mats_ifopen = MATS1DElastic( E = 0 )   # elastic function of open - inactive
                            )
        return mats
    #-------------------------------------------------------
    # Finite element type
    #-------------------------------------------------------
    fets = Instance( FETSEval )
    def _fets_default( self ):
        #return FETS1D52L8ULRH( mats_eval = self.mats )        
        return FETS1D52L4ULRH( mats_eval = self.mats )
        #return FETS1D2L3U( mats_eval = self.mats ) 

    run = Button

    @on_trait_change( 'run' )
    def peval( self ):
        '''Evaluation procedure.
        '''
        #mv = MATS1DDamageView( model = mats_eval )
        #mv.configure_traits()

        self.mats_m.reset_state()
        # Discretization
        #
        length = self.length
        domain = FEGrid( coord_min = ( 0., length / 5. ),
                          coord_max = ( length, 0. ),
                          shape = ( self.shape, 1 ),
                          fets_eval = self.fets )

        right_dofs = domain[-1, -1, -1, :].dofs[0, :, 0]
        print 'concrete_dofs', id( domain ), domain[:, 0, :, 0].dofs
        # Response tracers
        self.stress_strain = RTraceGraph( name = 'Fi,right over u_right (iteration)' ,
                                   var_y = 'F_int', idx_y = right_dofs[0],
                                   var_x = 'U_k', idx_x = right_dofs[0] )
        self.eps_m_field = RTraceDomainListField( name = 'eps_m' , position = 'int_pnts',
                                           var = 'eps1', idx = 0,
                                           warp = True )

        self.eps_f_field = RTraceDomainListField( name = 'eps_f' , position = 'int_pnts',
                                           var = 'eps2', idx = 0,
                                           warp = True )

        # Response tracers
        self.sig_m_field = RTraceDomainListField( name = 'sig_m' , position = 'int_pnts',
                                              var = 'mats_phase1_sig_app', idx = 0 )
        self.sig_f_field = RTraceDomainListField( name = 'sig_f' , position = 'int_pnts',
                                              var = 'mats_phase2_sig_app', idx = 0 )
        self.omega_m_field = RTraceDomainListField( name = 'omega_m' , position = 'int_pnts',
                                           var = 'mats_phase1_omega', idx = 0,
                                           warp = True )
        # 

        damage_onset_displ = self.mats_m.epsilon_0 * self.length
        go_behind = 1.5
        finish_displ = go_behind * damage_onset_displ
        n_steps = 20
        step_size = ( finish_displ - damage_onset_displ ) / n_steps
        tmax = 1 + n_steps

        def ls( t ):
            if t <= 1:
                return t
            else:
                return 1.0 + ( t - 1.0 ) / n_steps * ( go_behind - 1 )

        ts = TSCrackLoc( 
                 dof_resultants = True,
                 on_update = self.plot,
                 sdomain = domain,
                 bcond_list = [# define the left clamping 
                                BCSlice( var = 'u', value = 0., dims = [0], slice = domain[ 0, 0, 0, :] ),
                                # loading at the right edge
                                 BCSlice( var = 'f', value = 1, dims = [0], slice = domain[-1, -1, -1, 0],
                                         time_function = ls ),
#                                 BCSlice(var='u', value = finish_displ, dims = [0], slice = domain[-1,-1,-1, 0],
#                                         time_function = ls ),
                                # fix horizontal displacement in the top layer
                                 BCSlice( var = 'u', value = 0., dims = [0], slice = domain[:, -1, :, -1] ),
                                # fix the vertical displacement all over the domain
                                 BCSlice( var = 'u', value = 0., dims = [1], slice = domain[ :, :, :, :] )
                                ],
                 rtrace_list = [ self.stress_strain,
                                  self.eps_m_field,
                                  self.eps_f_field,
                                  self.sig_m_field,
                                  self.sig_f_field,
                                  self.omega_m_field ]
                )

        # Add the time-loop control
        tloop = TLoop( tstepper = ts, KMAX = 200, debug = True, tolerance = 1e-5,
                       tline = TLine( min = 0.0, step = 1.0, max = 1.0 ) )

        print ts.rte_dict.keys()
        U = tloop.eval()

        self.plot()

        return array( [ U[right_dofs[-1]] ], dtype = 'float_' )

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_ld = Instance( Figure )
    def _figure_ld_default( self ):
        figure = Figure( facecolor = 'white' )
        figure.add_axes( [0.12, 0.13, 0.85, 0.74] )
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_eps = Instance( Figure )
    def _figure_eps_default( self ):
        figure = Figure( facecolor = 'white' )
        figure.add_axes( [0.12, 0.13, 0.85, 0.74] )
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_omega = Instance( Figure )
    def _figure_omega_default( self ):
        figure = Figure( facecolor = 'white' )
        figure.add_axes( [0.12, 0.13, 0.85, 0.74] )
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_sig = Instance( Figure )
    def _figure_sig_default( self ):
        figure = Figure( facecolor = 'white' )
        figure.add_axes( [0.12, 0.13, 0.85, 0.74] )
        return figure

    def plot( self ):
        self.stress_strain.refresh()
        t = self.stress_strain.trace
        ax = self.figure_ld.axes[0]
        ax.clear()
        ax.plot( t.xdata, t.ydata, linewidth = 2, color = 'blue' )

        ax = self.figure_eps.axes[0]
        ax.clear()

        ef = self.eps_m_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'grey' )

        ef = self.eps_f_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'red' )
        ax.legend( ['eps_m', 'eps_f'] )

        ax = self.figure_sig.axes[0]
        ax.clear()

        ef = self.sig_m_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'grey' )

        ef = self.sig_f_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'red' )
        ax.legend( ['sig_m', 'sig_f'] )


        ax = self.figure_omega.axes[0]
        ax.clear()

        ef = self.omega_m_field.subfields[0]
        xdata = ef.vtk_X[:, 0]
        ydata = ef.field_arr[:, 0]
        idata = argsort( xdata )
        ax.plot( xdata[idata], ydata[idata], linewidth = 2, color = 'brown' )
        ax.legend( ['omega_m'] )


        self.data_changed = True

    def get_sim_outputs( self ):
        '''
        Specifies the results and their order returned by the model
        evaluation.
        '''
        return [ SimOut( name = 'right end displacement', unit = 'm' ) ]

    data_changed = Event

    toolbar = ToolBar( 
                      Action( name = "Run",
                             tooltip = 'Start computation',
                             image = ImageResource( 'kt-start' ),
                             action = "start_study" ),
                      Action( name = "Pause",
                             tooltip = 'Pause computation',
                             image = ImageResource( 'kt-pause' ),
                             action = "pause_study" ),
                      Action( name = "Stop",
                             tooltip = 'Stop computation',
                             image = ImageResource( 'kt-stop' ),
                             action = "stop_study" ),
                      image_size = ( 32, 32 ),
                      show_tool_names = False,
                      show_divider = True,
                      name = 'view_toolbar' ),

    traits_view = View( 
                    HSplit( 
                        VSplit( 
                                Item( 'run', show_label = False ),
                            VGroup( 
                                 Item( 'shape' ),
                                 Item( 'n_sjteps' ),
                                 Item( 'length' ),
                                 label = 'parameters',
                                 id = 'crackloc.viewmodel.factor.geometry',
                                 dock = 'tab',
                                 scrollable = True,
                                 ),
                            VGroup( 
                                 Item( 'mats_m@', show_label = False ),
                                 label = 'Matrix',
                                 dock = 'tab',
                                 id = 'crackloc.viewmodel.factor.matrix',
                                 scrollable = True
                                 ),
                            VGroup( 
                                 Item( 'mats_f@', show_label = False ),
                                 label = 'Fiber',
                                 dock = 'tab',
                                 id = 'crackloc.viewmodel.factor.fiber',
                                 scrollable = True
                                 ),
                            VGroup( 
                                 Item( 'mats_b@', show_label = False ),
                                 label = 'Bond',
                                 dock = 'tab',
                                 id = 'crackloc.viewmodel.factor.bond',
                                 scrollable = True
                                ),
                            id = 'crackloc.viewmodel.left',
                            label = 'studied factors',
                            layout = 'tabbed',
                            dock = 'tab',
                            ),
                               VSplit( 
                                    VGroup( 
                                        Item( 'figure_ld', editor = MPLFigureEditor(),
                                             resizable = True, show_label = False ),
                                             label = 'stress-strain',
                                            id = 'crackloc.viewmode.figure_ld_window',
                                            dock = 'tab',
                                    ),
                                    VGroup( 
                                        Item( 'figure_eps', editor = MPLFigureEditor(),
                                             resizable = True, show_label = False ),
                                             label = 'strains profile',
                                            id = 'crackloc.viewmode.figure_eps_window',
                                            dock = 'tab',
                                        ),
                                    VGroup( 
                                        Item( 'figure_sig', editor = MPLFigureEditor(),
                                             resizable = True, show_label = False ),
                                             label = 'stress profile',
                                            id = 'crackloc.viewmode.figure_sig_window',
                                            dock = 'tab',
                                        ),
                                    VGroup( 
                                        Item( 'figure_omega', editor = MPLFigureEditor(),
                                             resizable = True, show_label = False ),
                                             label = 'omega profile',
                                            id = 'crackloc.viewmode.figure_omega_window',
                                            dock = 'tab',
                                        ),
                                   id = 'crackloc.viewmodel.right',
                                 ),
                            id = 'crackloc.viewmodel.splitter',
                        ),
                        title = 'SimVisage Component: Crack localization',
                        id = 'crackloc.viewmodel',
                        dock = 'tab',
                        resizable = True,
                        height = 0.8, width = 0.8,
                        buttons = [OKButton] )
Beispiel #25
0
class SimCrackLoc(IBVModel):
    '''Model assembling the components for studying the restrained crack localization.
    '''

    geo_transform = Instance(FlawCenteredGeoTransform)

    def _geo_transform_default(self):
        return FlawCenteredGeoTransform()

    shape = Int(10,
                desc='Number of finite elements',
                ps_levsls=(10, 40, 4),
                input=True)

    length = Float(1000,
                   desc='Length of the simulated region',
                   unit='mm',
                   input=True)

    flaw_position = Float(500, input=True, unit='mm')

    flaw_radius = Float(100, input=True, unit='mm')

    reduction_factor = Float(0.9, input=True)

    elastic_fraction = Float(0.9, input=True)

    avg_radius = Float(400, input=True, unit='mm')

    # tensile strength of concrete
    f_m_t = Float(3.0, input=True, unit='MPa')

    epsilon_0 = Property(unit='-')

    def _get_epsilon_0(self):
        return self.f_m_t / self.E_m

    epsilon_f = Float(10, input=True, unit='-')

    h_m = Float(10, input=True, unit='mm')

    b_m = Float(8, input=True, unit='mm')

    A_m = Property(unit='m^2')

    def _get_A_m(self):
        return self.b_m * self.h_m

    E_m = Float(30.0e5, input=True, unit='MPa')

    E_f = Float(70.0e6, input=True, unit='MPa')

    A_f = Float(1.0, input=True, unit='mm^2')

    s_crit = Float(0.009, input=True, unit='mm')

    P_f = Property(depends_on='+input')

    @cached_property
    def _get_P_f(self):
        return sqrt(4 * self.A_f * pi)

    K_b = Property(depends_on='+input')

    @cached_property
    def _get_K_b(self):
        return self.T_max / self.s_crit

    tau_max = Float(0.0, input=True, unit='MPa')

    T_max = Property(depends_on='+input', unit='N/mm')

    @cached_property
    def _get_T_max(self):
        return self.tau_max * self.P_f

    rho = Property(depends_on='+input')

    @cached_property
    def _get_rho(self):
        return self.A_f / (self.A_f + self.A_m)

    #-------------------------------------------------------
    # Material model for the matrix
    #-------------------------------------------------------
    mats_m = Property(Instance(MATS1DDamageWithFlaw), depends_on='+input')

    @cached_property
    def _get_mats_m(self):
        mats_m = MATS1DDamageWithFlaw(E=self.E_m * self.A_m,
                                      flaw_position=self.flaw_position,
                                      flaw_radius=self.flaw_radius,
                                      reduction_factor=self.reduction_factor,
                                      epsilon_0=self.epsilon_0,
                                      epsilon_f=self.epsilon_f)
        return mats_m

    mats_f = Instance(MATS1DElastic)

    def _mats_f_default(self):
        mats_f = MATS1DElastic(E=self.E_f * self.A_f)
        return mats_f

    mats_b = Instance(MATS1DEval)

    def _mats_b_default(self):
        mats_b = MATS1DElastic(E=self.K_b)
        mats_b = MATS1DPlastic(E=self.K_b,
                               sigma_y=self.T_max,
                               K_bar=0.,
                               H_bar=0.)  # plastic function of slip
        return mats_b

    mats_fb = Property(Instance(MATS1D5Bond), depends_on='+input')

    @cached_property
    def _get_mats_fb(self):

        # Material model construction
        return MATS1D5Bond(
            mats_phase1=MATS1DElastic(E=0),
            mats_phase2=self.mats_f,
            mats_ifslip=self.mats_b,
            mats_ifopen=MATS1DElastic(
                E=0)  # elastic function of open - inactive
        )

    #-------------------------------------------------------
    # Finite element type
    #-------------------------------------------------------
    fets_m = Property(depends_on='+input')

    @cached_property
    def _get_fets_m(self):
        fets_eval = FETS1D2L(mats_eval=self.mats_m)
        #fets_eval = FETS1D2L3U( mats_eval = self.mats_m )
        return fets_eval

    fets_fb = Property(depends_on='+input')

    @cached_property
    def _get_fets_fb(self):
        return FETS1D52L4ULRH(mats_eval=self.mats_fb)
        #return FETS1D52L6ULRH( mats_eval = self.mats_fb )
        #return FETS1D52L8ULRH( mats_eval = self.mats_fb )

    #--------------------------------------------------------------------------------------
    # Mesh integrator
    #--------------------------------------------------------------------------------------
    fe_domain_structure = Property(depends_on='+input')

    @cached_property
    def _get_fe_domain_structure(self):
        '''Root of the domain hierarchy
        '''
        elem_length = self.length / float(self.shape)

        fe_domain = FEDomain()

        fe_m_level = FERefinementGrid(name='matrix domain',
                                      domain=fe_domain,
                                      fets_eval=self.fets_m)

        fe_grid_m = FEGrid(name='matrix grid',
                           coord_max=(self.length, ),
                           shape=(self.shape, ),
                           level=fe_m_level,
                           fets_eval=self.fets_m,
                           geo_transform=self.geo_transform)

        fe_fb_level = FERefinementGrid(name='fiber bond domain',
                                       domain=fe_domain,
                                       fets_eval=self.fets_fb)

        fe_grid_fb = FEGrid(coord_min=(0., length / 5.),
                            coord_max=(length, 0.),
                            shape=(self.shape, 1),
                            level=fe_fb_level,
                            fets_eval=self.fets_fb,
                            geo_transform=self.geo_transform)

        return fe_domain, fe_grid_m, fe_grid_fb, fe_m_level, fe_fb_level

    fe_domain = Property

    def _get_fe_domain(self):
        return self.fe_domain_structure[0]

    fe_grid_m = Property

    def _get_fe_grid_m(self):
        return self.fe_domain_structure[1]

    fe_grid_fb = Property

    def _get_fe_grid_fb(self):
        return self.fe_domain_structure[2]

    fe_m_level = Property

    def _get_fe_m_level(self):
        return self.fe_domain_structure[3]

    fe_fb_level = Property

    def _get_fe_fb_level(self):
        return self.fe_domain_structure[4]

    #---------------------------------------------------------------------------
    # Load scaling adapted to the elastic and inelastic regime
    #---------------------------------------------------------------------------
    final_displ = Property(depends_on='+input')

    @cached_property
    def _get_final_displ(self):
        damage_onset_displ = self.mats_m.epsilon_0 * self.length
        return damage_onset_displ / self.elastic_fraction

    step_size = Property(depends_on='+input')

    @cached_property
    def _get_step_size(self):
        n_steps = self.n_steps
        return 1.0 / float(n_steps)

    time_function = Property(depends_on='+input')

    @cached_property
    def _get_time_function(self):
        '''Get the time function so that the elastic regime 
        is skipped in a single step.
        '''
        step_size = self.step_size

        elastic_value = self.elastic_fraction * 0.98 * self.reduction_factor
        inelastic_value = 1.0 - elastic_value

        def ls(t):
            if t <= step_size:
                return (elastic_value / step_size) * t
            else:
                return elastic_value + (t - step_size) * (inelastic_value) / (
                    1 - step_size)

        return ls

    def plot_time_function(self, p):
        '''Plot the time function.
        '''
        n_steps = self.n_steps
        mats = self.mats
        step_size = self.step_size

        ls_t = linspace(0, step_size * n_steps, n_steps + 1)
        ls_fn = frompyfunc(self.time_function, 1, 1)
        ls_v = ls_fn(ls_t)

        p.subplot(321)
        p.plot(ls_t, ls_v, 'ro-')

        final_epsilon = self.final_displ / self.length

        kappa = linspace(mats.epsilon_0, final_epsilon, 10)
        omega_fn = frompyfunc(lambda kappa: mats._get_omega(None, kappa), 1, 1)
        omega = omega_fn(kappa)
        kappa_scaled = (step_size + (1 - step_size) *
                        (kappa - mats.epsilon_0) /
                        (final_epsilon - mats.epsilon_0))
        xdata = hstack([array([0.0], dtype=float), kappa_scaled])
        ydata = hstack([array([0.0], dtype=float), omega])
        p.plot(xdata, ydata, 'g')
        p.xlabel('regular time [-]')
        p.ylabel('scaled time [-]')

    run = Button

    @on_trait_change('run')
    def peval(self):
        '''Evaluation procedure.
        '''
        #mv = MATS1DDamageView( model = mats_eval )
        #mv.configure_traits()

        right_dof_m = self.fe_grid_m[-1, -1].dofs[0, 0, 0]

        right_dof_fb = self.fe_grid_fb[-1, -1, -1, -1].dofs[0, 0, 0]
        # Response tracers
        A = self.A_m + self.A_f
        self.sig_eps_m = RTraceGraph(name='F_u_m',
                                     var_y='F_int',
                                     idx_y=right_dof_m,
                                     var_x='U_k',
                                     idx_x=right_dof_m,
                                     transform_y='y / %g' % A)

        # Response tracers
        self.sig_eps_f = RTraceGraph(name='F_u_f',
                                     var_y='F_int',
                                     idx_y=right_dof_fb,
                                     var_x='U_k',
                                     idx_x=right_dof_fb,
                                     transform_y='y / %g' % A)

        self.eps_m_field = RTraceDomainListField(name='eps_m',
                                                 position='int_pnts',
                                                 var='eps_app',
                                                 warp=False)

        self.eps_f_field = RTraceDomainListField(name='eps_f',
                                                 position='int_pnts',
                                                 var='mats_phase2_eps_app',
                                                 warp=False)
        # Response tracers
        self.sig_m_field = RTraceDomainListField(name='sig_m',
                                                 position='int_pnts',
                                                 var='sig_app')

        self.sig_f_field = RTraceDomainListField(name='sig_f',
                                                 position='int_pnts',
                                                 var='mats_phase2_sig_app')

        self.omega_m_field = RTraceDomainListField(name='omega_m',
                                                   position='int_pnts',
                                                   var='omega',
                                                   warp=False)

        self.shear_flow_field = RTraceDomainListField(name='shear flow',
                                                      position='int_pnts',
                                                      var='shear_flow',
                                                      warp=False)

        self.slip_field = RTraceDomainListField(name='slip',
                                                position='int_pnts',
                                                var='slip',
                                                warp=False)

        avg_processor = None
        if self.avg_radius > 0.0:
            n_dofs = self.fe_domain.n_dofs
            avg_processor = RTUAvg(sd=self.fe_m_level,
                                   n_dofs=n_dofs,
                                   avg_fn=QuarticAF(radius=self.avg_radius))

        ts = TStepper(
            u_processor=avg_processor,
            dof_resultants=True,
            sdomain=self.fe_domain,
            bcond_list=[  # define the left clamping 
                BCSlice(var='u',
                        value=0.,
                        dims=[0],
                        slice=self.fe_grid_fb[0, 0, 0, :]),
                #                                BCSlice( var = 'u', value = 0., dims = [0], slice = self.fe_grid_m[ 0, 0 ] ),
                # loading at the right edge
                #                                 BCSlice( var = 'f', value = 1, dims = [0], slice = domain[-1, -1, -1, 0],
                #                                         time_function = ls ),
                BCSlice(var='u',
                        value=self.final_displ,
                        dims=[0],
                        slice=self.fe_grid_fb[-1, -1, -1, :],
                        time_function=self.time_function),
                #                                 BCSlice( var = 'u', value = self.final_displ, dims = [0], slice = self.fe_grid_m[-1, -1],
                #                                         time_function = self.time_function ),
                # fix horizontal displacement in the top layer
                #                                 BCSlice( var = 'u', value = 0., dims = [0], slice = domain[:, -1, :, -1] ),
                # fix the vertical displacement all over the domain
                BCSlice(var='u',
                        value=0.,
                        dims=[1],
                        slice=self.fe_grid_fb[:, :, :, :]),
                #                            # Connect bond and matrix domains
                BCDofGroup(var='u',
                           value=0.,
                           dims=[0],
                           get_link_dof_method=self.fe_grid_fb.get_bottom_dofs,
                           get_dof_method=self.fe_grid_m.get_all_dofs,
                           link_coeffs=[1.])
            ],
            rtrace_list=[
                self.sig_eps_m,
                self.sig_eps_f,
                self.eps_m_field,
                self.eps_f_field,
                self.sig_m_field,
                self.sig_f_field,
                self.omega_m_field,
                self.shear_flow_field,
                self.slip_field,
            ])

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      KMAX=300,
                      tolerance=1e-5,
                      debug=False,
                      verbose_iteration=True,
                      verbose_time=False,
                      tline=TLine(min=0.0, step=self.step_size, max=1.0))

        tloop.on_accept_time_step = self.plot

        U = tloop.eval()

        self.sig_eps_f.refresh()
        max_sig_m = max(self.sig_eps_m.trace.ydata)
        return array([U[right_dof_m], max_sig_m], dtype='float_')

    #--------------------------------------------------------------------------------------
    # Tracers
    #--------------------------------------------------------------------------------------

    def plot_sig_eps(self, p):
        p.set_xlabel('control displacement [mm]')
        p.set_ylabel('stress [MPa]')

        self.sig_eps_m.refresh()
        self.sig_eps_m.trace.plot(p, 'o-')

        self.sig_eps_f.refresh()
        self.sig_eps_f.trace.plot(p, 'o-')

        p.plot(self.sig_eps_m.trace.xdata,
               self.sig_eps_m.trace.ydata + self.sig_eps_f.trace.ydata, 'o-')

    def plot_eps(self, p):
        eps_m = self.eps_m_field.subfields[0]
        xdata = eps_m.vtk_X[:, 0]
        ydata = eps_m.field_arr[:, 0, 0]
        idata = argsort(xdata)
        p.plot(xdata[idata], ydata[idata], 'o-')

        eps_f = self.eps_f_field.subfields[1]
        xdata = eps_f.vtk_X[:, 0]
        ydata = eps_f.field_arr[:, 0, 0]
        idata = argsort(xdata)
        p.plot(xdata[idata], ydata[idata], 'o-')

        p.set_ylim(ymin=0)
        p.set_xlabel('bar axis [mm]')
        p.set_ylabel('strain [-]')

    def plot_omega(self, p):
        omega_m = self.omega_m_field.subfields[0]
        xdata = omega_m.vtk_X[:, 0]
        ydata = omega_m.field_arr[:]
        idata = argsort(xdata)
        p.fill(xdata[idata], ydata[idata], facecolor='gray', alpha=0.2)

        print 'max omega', max(ydata[idata])

        p.set_ylim(ymin=0, ymax=1.0)
        p.set_xlabel('bar axis [mm]')
        p.set_ylabel('omega [-]')

    def plot_sig(self, p):
        sig_m = self.sig_m_field.subfields[0]
        xdata = sig_m.vtk_X[:, 0]
        ydata = sig_m.field_arr[:, 0, 0]
        idata = argsort(xdata)
        ymax = max(ydata)
        p.plot(xdata[idata], ydata[idata], 'o-')

        sig_f = self.sig_f_field.subfields[1]
        xdata = sig_f.vtk_X[:, 0]
        ydata = sig_f.field_arr[:, 0, 0]
        idata = argsort(xdata)
        p.plot(xdata[idata], ydata[idata], 'o-')

        xdata = sig_f.vtk_X[:, 0]
        ydata = sig_f.field_arr[:, 0, 0] + sig_m.field_arr[:, 0, 0]
        p.plot(xdata[idata], ydata[idata], 'ro-')

        p.set_ylim(ymin=0)  # , ymax = 1.2 * ymax )
        p.set_xlabel('bar axis [mm]')
        p.set_ylabel('stress [MPa]')

    def plot_shear_flow(self, p):
        shear_flow = self.shear_flow_field.subfields[1]
        xdata = shear_flow.vtk_X[:, 0]
        ydata = shear_flow.field_arr[:, 0] / self.P_f
        idata = argsort(xdata)
        ymax = max(ydata)
        p.plot(xdata[idata], ydata[idata], 'o-')

        p.set_xlabel('bar axis [mm]')
        p.set_ylabel('shear flow [N/m]')

    def plot_slip(self, p):
        slip = self.slip_field.subfields[1]
        xdata = slip.vtk_X[:, 0]
        ydata = slip.field_arr[:, 0]
        idata = argsort(xdata)
        ymax = max(ydata)
        p.plot(xdata[idata], ydata[idata], 'ro-')

        p.set_xlabel('bar axis [mm]')
        p.set_ylabel('slip [N/m]')

    def plot_tracers(self, p=p):

        p.subplot(221)
        self.plot_sig_eps(p)

        p.subplot(223)
        self.plot_eps(p)

        p.subplot(224)
        self.plot_sig(p)

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_ld = Instance(Figure)

    def _figure_ld_default(self):
        figure = Figure(facecolor='white')
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_eps = Instance(Figure)

    def _figure_eps_default(self):
        figure = Figure(facecolor='white')
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_shear_flow = Instance(Figure)

    def _figure_shear_flow_default(self):
        figure = Figure(facecolor='white')
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_sig = Instance(Figure)

    def _figure_sig_default(self):
        figure = Figure(facecolor='white')
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    #---------------------------------------------------------------
    # PLOT OBJECT
    #-------------------------------------------------------------------
    figure_shear_flow = Instance(Figure)

    def _figure_shear_flow_default(self):
        figure = Figure(facecolor='white')
        figure.add_axes([0.12, 0.13, 0.85, 0.74])
        return figure

    def plot(self):

        self.figure_ld.clear()
        ax = self.figure_ld.gca()
        self.plot_sig_eps(ax)

        self.figure_eps.clear()
        ax = self.figure_eps.gca()
        self.plot_eps(ax)
        ax2 = ax.twinx()
        self.plot_omega(ax2)

        self.figure_sig.clear()
        ax = self.figure_sig.gca()
        self.plot_sig(ax)
        ax2 = ax.twinx()
        self.plot_omega(ax2)

        self.figure_shear_flow.clear()
        ax = self.figure_shear_flow.gca()
        self.plot_shear_flow(ax)
        ax2 = ax.twinx()
        self.plot_slip(ax2)

        self.data_changed = True

    def get_sim_outputs(self):
        '''
        Specifies the results and their order returned by the model
        evaluation.
        '''
        return [
            SimOut(name='right end displacement', unit='m'),
            SimOut(name='peak load', uni='MPa')
        ]

    data_changed = Event

    toolbar = ToolBar(Action(name="Run",
                             tooltip='Start computation',
                             image=ImageResource('kt-start'),
                             action="start_study"),
                      Action(name="Pause",
                             tooltip='Pause computation',
                             image=ImageResource('kt-pause'),
                             action="pause_study"),
                      Action(name="Stop",
                             tooltip='Stop computation',
                             image=ImageResource('kt-stop'),
                             action="stop_study"),
                      image_size=(32, 32),
                      show_tool_names=False,
                      show_divider=True,
                      name='view_toolbar'),

    traits_view = View(HSplit(
        VSplit(
            Item('run', show_label=False),
            VGroup(
                Item('shape'),
                Item('n_steps'),
                Item('length'),
                label='parameters',
                id='crackloc.viewmodel.factor.geometry',
                dock='tab',
                scrollable=True,
            ),
            VGroup(Item('E_m'),
                   Item('f_m_t'),
                   Item('avg_radius'),
                   Item('h_m'),
                   Item('b_m'),
                   Item('A_m', style='readonly'),
                   Item('mats_m', show_label=False),
                   label='Matrix',
                   dock='tab',
                   id='crackloc.viewmodel.factor.matrix',
                   scrollable=True),
            VGroup(Item('E_f'),
                   Item('A_f'),
                   Item('mats_f', show_label=False),
                   label='Fiber',
                   dock='tab',
                   id='crackloc.viewmodel.factor.fiber',
                   scrollable=True),
            VGroup(Group(
                Item('tau_max'),
                Item('s_crit'),
                Item('P_f', style='readonly', show_label=True),
                Item('K_b', style='readonly', show_label=True),
                Item('T_max', style='readonly', show_label=True),
            ),
                   Item('mats_b', show_label=False),
                   label='Bond',
                   dock='tab',
                   id='crackloc.viewmodel.factor.bond',
                   scrollable=True),
            VGroup(Item('rho', style='readonly', show_label=True),
                   label='Composite',
                   dock='tab',
                   id='crackloc.viewmodel.factor.jcomposite',
                   scrollable=True),
            id='crackloc.viewmodel.left',
            label='studied factors',
            layout='tabbed',
            dock='tab',
        ),
        VSplit(
            VGroup(
                Item('figure_ld',
                     editor=MPLFigureEditor(),
                     resizable=True,
                     show_label=False),
                label='stress-strain',
                id='crackloc.viewmode.figure_ld_window',
                dock='tab',
            ),
            VGroup(
                Item('figure_eps',
                     editor=MPLFigureEditor(),
                     resizable=True,
                     show_label=False),
                label='strains profile',
                id='crackloc.viewmode.figure_eps_window',
                dock='tab',
            ),
            VGroup(
                Item('figure_sig',
                     editor=MPLFigureEditor(),
                     resizable=True,
                     show_label=False),
                label='stress profile',
                id='crackloc.viewmode.figure_sig_window',
                dock='tab',
            ),
            VGroup(
                Item('figure_shear_flow',
                     editor=MPLFigureEditor(),
                     resizable=True,
                     show_label=False),
                label='bond shear and slip profiles',
                id='crackloc.viewmode.figure_shear_flow_window',
                dock='tab',
            ),
            id='crackloc.viewmodel.right',
        ),
        id='crackloc.viewmodel.splitter',
    ),
                       title='SimVisage Component: Crack localization',
                       id='crackloc.viewmodel',
                       dock='tab',
                       resizable=True,
                       height=0.8,
                       width=0.8,
                       buttons=[OKButton])
    def eval( self ):

        elem_length = self.length / float( self.shape )
        flaw_radius = self.flaw_radius

        mats = MATS1DElasticWithFlaw( E = 10.,
                                     flaw_position = self.flaw_position,
                                     flaw_radius = flaw_radius,
                                     reduction_factor = self.reduction_factor )

        #fets_eval = FETS1D2L( mats_eval = mats )
        fets_eval = FETS1D2L3U( mats_eval = mats )

        domain = FEGrid( coord_max = ( self.length, 0., 0. ),
                               shape = ( self.shape, ),
                               fets_eval = fets_eval )

        avg_processor = RTNonlocalAvg( avg_fn = QuarticAF( radius = self.avg_radius,
                                                           correction = True ) )

        eps_app = RTraceDomainListField( name = 'Strain' ,
                                         position = 'int_pnts',
                                         var = 'eps_app',
                                         warp = False )

        damage = RTraceDomainListField( name = 'Damage' ,
                                        position = 'int_pnts',
                                      var = 'omega',
                                        warp = False )

        disp = RTraceDomainListField( name = 'Displacement' ,
                                      position = 'int_pnts',
                                      var = 'u',
                                      warp = False )

        sig_app = RTraceDomainListField( name = 'Stress' ,
                                         position = 'int_pnts',
                                         var = 'sig_app' )

        right_dof = domain[-1, -1].dofs[0, 0, 0]
        rt_fu = RTraceGraph( name = 'Fi,right over u_right (iteration)' ,
                             var_y = 'F_int', idx_y = right_dof,
                             var_x = 'U_k', idx_x = right_dof )

        ts = TS( u_processor = avg_processor,
                 dof_resultants = True,
                 sdomain = domain,
             # conversion to list (square brackets) is only necessary for slicing of 
             # single dofs, e.g "get_left_dofs()[0,1]"
    #         bcond_list =  [ BCDof(var='u', dof = 0, value = 0.)     ] +  
    #                    [ BCDof(var='u', dof = 2, value = 0.001 ) ]+
    #                    [ )     ],
             bcond_list = [BCDof( var = 'u', dof = 0, value = 0. ),
    #                        BCDof(var='u', dof = 1, link_dofs = [2], link_coeffs = [0.5],
    #                              value = 0. ),
    #                        BCDof(var='u', dof = 2, link_dofs = [3], link_coeffs = [1.],
    #                              value = 0. ),
                            BCDof( var = 'u', dof = right_dof, value = 0.01,
                                       ) ],
             rtrace_list = [ rt_fu,
                             eps_app,
                             # damage,
                             sig_app,
                             disp,
                    ]
                )

        # Add the time-loop control
        tloop = TLoop( tstepper = ts, KMAX = 100, tolerance = 1e-5,
                       verbose_iteration = False,
                       tline = TLine( min = 0.0, step = 1.0, max = 1.0 ) )

        U = tloop.eval()

        p.subplot( 221 )
        rt_fu.refresh()
        rt_fu.trace.plot( p )

        eps = eps_app.subfields[0]
        xdata = eps.vtk_X[:, 0]
        ydata = eps.field_arr[:, 0, 0]
        idata = argsort( xdata )

        p.subplot( 222 )
        p.plot( xdata[idata], ydata[idata], 'o-' )

        disp = disp.subfields[0]
        xdata = disp.vtk_X[:, 0]
        ydata = disp.field_arr[:, 0]
        idata = argsort( xdata )

        p.subplot( 223 )
        p.plot( xdata[idata], ydata[idata], 'o-' )

        sig = sig_app.subfields[0]
        xdata = sig.vtk_X[:, 0]
        ydata = sig.field_arr[:, 0, 0]
        idata = argsort( xdata )

        p.subplot( 224 )
        p.plot( xdata[idata], ydata[idata], 'o-' )
Beispiel #27
0
            'sig_norm': self.get_sig_norm,
            'eps_p': self.get_eps_p
        }


if __name__ == '__main__':
    #-------------------------------------------------------------------------
    # Example using the mats2d_explore
    #-------------------------------------------------------------------------
    from ibvpy.api import RTraceGraph
    from ibvpy.mats.mats2D.mats2D_explore import MATS2DExplore
    from yield_face2D import J2
    mats2D_explore = \
        MATS2DExplore(mats2D_eval=MATS2DPlastic(yf=J2()),
                      rtrace_list=[RTraceGraph(name='strain 0 - stress 0',
                                               var_x='eps_app', idx_x=0,
                                               var_y='sig_app', idx_y=0,
                                               record_on='update'),
                                   RTraceGraph(name='strain 0 - strain 1',
                                               var_x='eps_app', idx_x=0,
                                               var_y='eps_app', idx_y=1,
                                               record_on='update'),
                                   RTraceGraph(name='stress 0 - stress 1',
                                               var_x='sig_app', idx_x=0,
                                               var_y='sig_app', idx_y=1,
                                               record_on='update'),
                                   RTraceGraph(name='time - sig_norm',
                                               var_x='time', idx_x=0,
                                               var_y='sig_norm', idx_y=0,
                                               record_on='update')

                                   ])
Beispiel #28
0
def simgrid(
    fets_eval,
    cube_size,
    shape,
    support_slices,
    support_dirs,
    loading_slice,
    load_dir=0,
    load_max=0.01,
    n_load_steps=1,
    vars=[],
    ivars=[],
    var_type='u',
):
    '''Construct an idealization and run simulation with primary variable 
    fixed on support slices and with unit load on loading slices applied in load dir.
    Return the solution vector and the fields specified in vars.
    '''
    # Discretization
    domain = FEGrid(coord_max=cube_size, shape=shape, fets_eval=fets_eval)

    u_max = load_max

    support_bcond = [
        BCSlice(var='u',
                value=0,
                dims=support_dir,
                slice=domain[support_slice])
        for support_slice, support_dir in zip(support_slices, support_dirs)
    ]
    load_bcond = [
        BCSlice(var=var_type,
                value=u_max,
                dims=[load_dir],
                slice=domain[loading_slice])
    ]

    bcond = support_bcond + load_bcond

    loading_dofs = domain[loading_slice].dofs[:, :, load_dir].flatten()

    graphs = [
        RTraceGraph(name='Force in one node / Displ.',
                    var_y='F_int',
                    idx_x=loading_dof,
                    var_x='U_k',
                    idx_y=loading_dof) for loading_dof in loading_dofs
    ]

    rtrace_list = [
        RTraceDomainListField(
            name=var,
            var=var,
            warp=True,
            #position = 'int_pnts',
            record_on='update') for var in vars
    ]
    irtrace_list = [
        RTraceDomainListInteg(name='Integ(' + var + ')',
                              var=var,
                              record_on='update') for var in ivars
    ]

    ts = TS(sdomain=domain,
            bcond_list=bcond,
            rtrace_list=graphs + rtrace_list + irtrace_list)

    load_step = 1. / float(n_load_steps)
    # Add the time-loop control
    tloop = TLoop(tstepper=ts,
                  KMAX=15,
                  RESETMAX=0,
                  tolerance=1e-5,
                  tline=TLine(min=0.0, step=load_step, max=1.0))

    u = tloop.eval()

    fields = [rtrace.subfields[0].field_arr for rtrace in rtrace_list]
    integs = [rtrace.integ_val for rtrace in irtrace_list]
    for graph in graphs:
        graph.redraw()
    traces = [graph.trace for graph in graphs]
    xydata = (traces[0].xdata, column_stack([trace.ydata for trace in traces]))

    return tloop, u, fields, integs, xydata
Beispiel #29
0
def example_with_new_domain():
    from ibvpy.api import \
        TStepper as TS, RTraceGraph, RTraceDomainListField, TLoop, \
        TLine, BCDof, IBVPSolve as IS, DOTSEval
    from ibvpy.mats.mats1D.mats1D_elastic.mats1D_elastic import MATS1DElastic

    fets_eval = FETS1D2L3U(mats_eval=MATS1DElastic(E=10.))

    from ibvpy.mesh.fe_grid import FEGrid

    # Discretization
    domain = FEGrid(coord_max=(3., ), shape=(3, ), fets_eval=fets_eval)

    ts = TS(
        dof_resultants=True,
        sdomain=domain,
        # conversion to list (square brackets) is only necessary for slicing of
        # single dofs, e.g "get_left_dofs()[0,1]"
        #         bcond_list =  [ BCDof(var='u', dof = 0, value = 0.)     ] +
        #                    [ BCDof(var='u', dof = 2, value = 0.001 ) ]+
        #                    [ )     ],
        bcond_list=[
            BCDof(var='u', dof=0, value=0.),
            #                        BCDof(var='u', dof = 1, link_dofs = [2], link_coeffs = [0.5],
            #                              value = 0. ),
            #                        BCDof(var='u', dof = 2, link_dofs = [3], link_coeffs = [1.],
            #                              value = 0. ),
            BCDof(
                var='f',
                dof=6,
                value=1,
                #link_dofs = [2], link_coeffs = [2]
            )
        ],
        rtrace_list=[
            RTraceGraph(name='Fi,right over u_right (iteration)',
                        var_y='F_int',
                        idx_y=0,
                        var_x='U_k',
                        idx_x=1),
            RTraceDomainListField(name='Stress', var='sig_app', idx=0),
            RTraceDomainListField(name='Displacement', var='u', idx=0),
            RTraceDomainListField(name='N0',
                                  var='N_mtx',
                                  idx=0,
                                  record_on='update')
        ])

    # Add the time-loop control
    tloop = TLoop(tstepper=ts, tline=TLine(min=0.0, step=1, max=1.0))

    print '---- result ----'
    print tloop.eval()
    print ts.F_int
    print ts.rtrace_list[0].trace.ydata

    # Put the whole stuff into the simulation-framework to map the
    # individual pieces of definition into the user interface.
    #
    from ibvpy.plugins.ibvpy_app import IBVPyApp
    app = IBVPyApp(ibv_resource=tloop)
    app.main()
Beispiel #30
0
    def _get_tloop(self):

        #--------------------------------------------------------------
        # ts
        #--------------------------------------------------------------

        mid_zone_spec = self.mid_zone_specmn_fe_grid
        load_zone_spec = self.load_zone_specmn_fe_grid
        outer_zone_spec = self.outer_zone_specmn_fe_grid

        if self.elstmr_flag:
            # ELSTRMR TOP SURFACE
            # dofs at elastomer top surface (used to integrate the force)
            #
            elastomer = self.elstmr_fe_grid
            elstmr_top_dofs_z = elastomer[:, :, -1, :, :,
                                          -1].dofs[:, :, 2].flatten()
            load_dofs_z = np.unique(elstmr_top_dofs_z)
            print 'load_dofs_z', load_dofs_z
        else:
            # LINE LOAD TOP OF LOAD ZONE
            # dofs at center line of the specmn load zone (used to integrate the force)
            # note slice index in x-direction is only valid for load_zone_shape_x = 2 !
            #
            load_zone_spec_topline_dofs_z = load_zone_spec[
                0, :, -1, -1, :, -1].dofs[:, :, 2].flatten()
            load_dofs_z = np.unique(load_zone_spec_topline_dofs_z)
            print 'load_dofs_z', load_dofs_z

        # SUPPRT LINE
        # dofs at support line of the specmn (used to integrate the force)
        #
        outer_zone_spec_supprtline_dofs_z = outer_zone_spec[
            -1, :, 0, -1, :, 0].dofs[:, :, 2].flatten()
        supprt_dofs_z = np.unique(outer_zone_spec_supprtline_dofs_z)
        print 'supprt_dofs_z', supprt_dofs_z

        # CENTER DOF (used for tracing of the displacement)
        #
        center_bottom_dof = mid_zone_spec[0, 0, 0, 0, 0, 0].dofs[0, 0, 2]
        print 'center_bottom_dof', center_bottom_dof

        # THIRDPOINT DOF (used for tracing of the displacement)
        # dofs at center middle of the laod zone at the bottom side
        #
        # NOTE: slice index in x-direction is only valid for load_zone_shape_x = 2 !
        thirdpoint_bottom_dof = load_zone_spec[0, 0, 0, -1, 0, 0].dofs[0, 0, 2]
        print 'thirdpoint_bottom_dof', thirdpoint_bottom_dof

        # force-displacement-diagram (CENTER)
        #
        self.f_w_diagram_center = RTraceGraph(
            name='displacement_elasttop (center) - force',
            var_x='U_k',
            idx_x=center_bottom_dof,
            var_y='F_int',
            idx_y_arr=load_dofs_z,
            record_on='update',
            transform_x='-x * 1000',  # %g * x' % ( fabs( w_max ),),
            # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
            #
            transform_y='-4000. * y')

        # force-displacement-diagram_supprt (SUPPRT)
        #
        self.f_w_diagram_supprt = RTraceGraph(
            name='displacement_supprtline (center) - force',
            var_x='U_k',
            idx_x=center_bottom_dof,
            var_y='F_int',
            idx_y_arr=supprt_dofs_z,
            record_on='update',
            transform_x='-x * 1000',  # %g * x' % ( fabs( w_max ),),
            # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
            #
            transform_y='4000. * y')

        # force-displacement-diagram (THIRDPOINT)
        #
        self.f_w_diagram_thirdpoint = RTraceGraph(
            name='displacement_elasttop (thirdpoint) - force',
            var_x='U_k',
            idx_x=thirdpoint_bottom_dof,
            var_y='F_int',
            idx_y_arr=load_dofs_z,
            record_on='update',
            transform_x='-x * 1000',  # %g * x' % ( fabs( w_max ),),
            # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
            #
            transform_y='-4000. * y')

        ts = TS(
            sdomain=self.fe_domain,
            bcond_list=self.bc_list,
            rtrace_list=[
                self.f_w_diagram_center,
                self.f_w_diagram_thirdpoint,
                self.f_w_diagram_supprt,
                RTraceDomainListField(name='Displacement',
                                      var='u',
                                      idx=0,
                                      warp=True),
                #                             RTraceDomainListField(name = 'Stress' ,
                #                                            var = 'sig_app', idx = 0, warp = True,
                #                                            record_on = 'update'),
                #                             RTraceDomainListField(name = 'Strain' ,
                #                                        var = 'eps_app', idx = 0, warp = True,
                #                                        record_on = 'update'),
                #                             RTraceDomainListField(name = 'Damage' ,
                #                                        var = 'omega_mtx', idx = 0, warp = True,
                #                                        record_on = 'update'),
                RTraceDomainListField(name='max_omega_i',
                                      warp=True,
                                      var='max_omega_i',
                                      idx=0,
                                      record_on='update'),
                #                             RTraceDomainListField(name = 'IStress' ,
                #                                            position = 'int_pnts',
                #                                            var = 'sig_app', idx = 0,
                #                                            record_on = 'update'),
                #                             RTraceDomainListField(name = 'IStrain' ,
                #                                            position = 'int_pnts',
                #                                            var = 'eps_app', idx = 0,
                #                                            record_on = 'update'),
            ])

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      KMAX=50,
                      tolerance=self.tolerance,
                      RESETMAX=0,
                      tline=TLine(min=0.0, step=self.tstep, max=self.tmax),
                      ord=self.ord)

        return tloop
Beispiel #31
0
def combined_fe2D4q_with_fe2D4q8u():

    fets_eval_4u_conc = FETS2D4Q(mats_eval=MATS2DElastic(E=28500, nu=0.2))
    fets_eval_4u_steel = FETS2D4Q(mats_eval=MATS2DElastic(E=210000, nu=0.25))
    fets_eval_8u = FETS2D4Q8U(mats_eval=MATS2DElastic())

    # Discretization
    fe_domain = FEDomain()

    fe_grid_level1 = FERefinementGrid(name='master grid',
                                      fets_eval=fets_eval_4u_conc,
                                      domain=fe_domain)

    fe_grid = FEGrid(level=fe_grid_level1,
                     coord_max=(2., 6., 0.),
                     shape=(11, 30),
                     fets_eval=fets_eval_4u_conc)

    fe_grid_level2 = FERefinementGrid(name='refinement grid',
                                      parent=fe_grid_level1,
                                      fets_eval=fets_eval_4u_steel,
                                      fine_cell_shape=(1, 1))

    # fe_grid_level1[ 5, :5 ].refine_using( fe_grid_level2 )
    # 1. first get the slice for the level - distinguish it from the slice at the subgrid
    #    this includes slicing in the subgrids. what if the subgrid does not exist?
    #
    #    Each subgrid must hold its own slice within the level. The index operator fills
    #    the grid [...] instanciates the whole grid and returns the instance of
    #    FEGridLevelSlice. The expanded subgrid contains its constructor slice.
    #
    # 2. If the slice is within an existing slice no change in the FESubgrid is required
    #    only the instance of the slice is returned. The FEGridLevelSlice goes always into
    #    an expanded part of FEGrid.
    #
    # 3. If the slice does not fit into any existing slice - all domain with an intersection
    #    of the existing slice must be constructed as well.
    #
    # 2. deactivate elements
    # 3.
    # BUT how to impose the boundary conditions on the particular refinement? The
    # slice has an attribute

    fe_grid_level2.refine_elem((5, 0))
    fe_grid_level2.refine_elem((5, 1))
    fe_grid_level2.refine_elem((5, 2))
    fe_grid_level2.refine_elem((5, 3))
    fe_grid_level2.refine_elem((5, 4))
    fe_grid_level2.refine_elem((5, 5))

    # apply the boundary condition on a subgrid
    #
    print fe_grid_level2.fe_subgrids
    fe_first_grid = fe_grid_level2.fe_subgrids[0]

    ts = TS(
        dof_resultants=True,
        sdomain=fe_domain,
        bcond_list=[
            BCSlice(var='f', value=1., dims=[0], slice=fe_grid[:, -1, :, -1]),
            BCSlice(var='u',
                    value=0.,
                    dims=[0, 1],
                    slice=fe_first_grid[:, 0, :, 0])
        ],
        rtrace_list=[
            RTraceGraph(name='Fi,right over u_right (iteration)',
                        var_y='F_int',
                        idx_y=0,
                        var_x='U_k',
                        idx_x=1),
            RTraceDomainListField(name='Stress',
                                  var='sig_app',
                                  idx=0,
                                  warp=True),
            #                             RTraceDomainField(name = 'Displacement' ,
            #                                        var = 'u', idx = 0),
            #                                 RTraceDomainField(name = 'N0' ,
            #                                              var = 'N_mtx', idx = 0,
            #                                              record_on = 'update')
        ])

    # Add the time-loop control
    tloop = TLoop(tstepper=ts, tline=TLine(min=0.0, step=1, max=1.0))

    print tloop.eval()
    from ibvpy.plugins.ibvpy_app import IBVPyApp
    ibvpy_app = IBVPyApp(ibv_resource=tloop)
    ibvpy_app.main()
Beispiel #32
0
def example_with_new_domain():
    from ibvpy.api import \
        TStepper as TS, RTraceGraph, RTraceDomainListField, \
        RTraceDomainListInteg, TLoop, \
        TLine, BCDof, IBVPSolve as IS, DOTSEval
    from ibvpy.mats.mats2D.mats2D_elastic.mats2D_elastic import MATS2DElastic
    from ibvpy.mats.mats2D.mats2D_sdamage.mats2D_sdamage import MATS2DScalarDamage

    from ibvpy.api import BCDofGroup

    mats_eval = MATS2DElastic()
    fets_eval = FETS2D4Q(mats_eval=mats_eval)
    #fets_eval = FETS2D4Q(mats_eval = MATS2DScalarDamage())

    print fets_eval.vtk_node_cell_data

    from ibvpy.mesh.fe_grid import FEGrid
    from ibvpy.mesh.fe_refinement_grid import FERefinementGrid
    from ibvpy.mesh.fe_domain import FEDomain
    from mathkit.mfn import MFnLineArray

    # Discretization
    fe_grid = FEGrid(coord_max=(10., 4., 0.),
                     shape=(10, 3),
                     fets_eval=fets_eval)

    bcg = BCDofGroup(var='u',
                     value=0.,
                     dims=[0],
                     get_dof_method=fe_grid.get_left_dofs)
    bcg.setup(None)
    print 'labels', bcg._get_labels()
    print 'points', bcg._get_mvpoints()

    mf = MFnLineArray(  # xdata = arange(10),
        ydata=array([0, 1, 2, 3]))

    right_dof = 2
    tstepper = TS(
        sdomain=fe_grid,
        bcond_list=[
            BCDofGroup(var='u',
                       value=0.,
                       dims=[0, 1],
                       get_dof_method=fe_grid.get_left_dofs),
            #                                   BCDofGroup( var='u', value = 0., dims = [1],
            # get_dof_method = fe_grid.get_bottom_dofs ),
            BCDofGroup(var='u',
                       value=.005,
                       dims=[1],
                       time_function=mf.get_value,
                       get_dof_method=fe_grid.get_right_dofs)
        ],
        rtrace_list=[
            RTraceGraph(name='Fi,right over u_right (iteration)',
                        var_y='F_int',
                        idx_y=right_dof,
                        var_x='U_k',
                        idx_x=right_dof,
                        record_on='update'),
            RTraceDomainListField(name='Stress',
                                  var='sig_app',
                                  idx=0,
                                  position='int_pnts',
                                  record_on='update'),
            #                     RTraceDomainListField(name = 'Damage' ,
            #                                    var = 'omega', idx = 0,
            #
            #                    record_on = 'update',
            #                                    warp = True),
            RTraceDomainListField(name='Displacement',
                                  var='u',
                                  idx=0,
                                  record_on='update',
                                  warp=True),
            RTraceDomainListField(name='Strain energy',
                                  var='strain_energy',
                                  idx=0,
                                  record_on='update',
                                  warp=False),
            RTraceDomainListInteg(name='Integ strain energy',
                                  var='strain_energy',
                                  idx=0,
                                  record_on='update',
                                  warp=False),
            #                    RTraceDomainListField(name = 'N0' ,
            #                                      var = 'N_mtx', idx = 0,
            # record_on = 'update')
        ])

    # Add the time-loop control
    #global tloop
    tloop = TLoop(tstepper=tstepper,
                  KMAX=300,
                  tolerance=1e-4,
                  tline=TLine(min=0.0, step=1.0, max=1.0))

    #import cProfile
    #cProfile.run('tloop.eval()', 'tloop_prof' )
    # print tloop.eval()
    #import pstats
    #p = pstats.Stats('tloop_prof')
    # p.strip_dirs()
    # print 'cumulative'
    # p.sort_stats('cumulative').print_stats(20)
    # print 'time'
    # p.sort_stats('time').print_stats(20)

    tloop.eval()
    # Put the whole thing into the simulation-framework to map the
    # individual pieces of definition into the user interface.
    #
    from ibvpy.plugins.ibvpy_app import IBVPyApp
    app = IBVPyApp(ibv_resource=tloop)
    app.main()
Beispiel #33
0
    def peval( self ):
        '''Evaluation procedure.
        '''
        #mv = MATS1DDamageView( model = mats_eval )
        #mv.configure_traits()

        self.mats_m.reset_state()
        # Discretization
        #
        length = self.length
        domain = FEGrid( coord_min = ( 0., length / 5. ),
                          coord_max = ( length, 0. ),
                          shape = ( self.shape, 1 ),
                          fets_eval = self.fets )

        right_dofs = domain[-1, -1, -1, :].dofs[0, :, 0]
        print 'concrete_dofs', id( domain ), domain[:, 0, :, 0].dofs
        # Response tracers
        self.stress_strain = RTraceGraph( name = 'Fi,right over u_right (iteration)' ,
                                   var_y = 'F_int', idx_y = right_dofs[0],
                                   var_x = 'U_k', idx_x = right_dofs[0] )
        self.eps_m_field = RTraceDomainListField( name = 'eps_m' , position = 'int_pnts',
                                           var = 'eps1', idx = 0,
                                           warp = True )

        self.eps_f_field = RTraceDomainListField( name = 'eps_f' , position = 'int_pnts',
                                           var = 'eps2', idx = 0,
                                           warp = True )

        # Response tracers
        self.sig_m_field = RTraceDomainListField( name = 'sig_m' , position = 'int_pnts',
                                              var = 'mats_phase1_sig_app', idx = 0 )
        self.sig_f_field = RTraceDomainListField( name = 'sig_f' , position = 'int_pnts',
                                              var = 'mats_phase2_sig_app', idx = 0 )
        self.omega_m_field = RTraceDomainListField( name = 'omega_m' , position = 'int_pnts',
                                           var = 'mats_phase1_omega', idx = 0,
                                           warp = True )
        # 

        damage_onset_displ = self.mats_m.epsilon_0 * self.length
        go_behind = 1.5
        finish_displ = go_behind * damage_onset_displ
        n_steps = 20
        step_size = ( finish_displ - damage_onset_displ ) / n_steps
        tmax = 1 + n_steps

        def ls( t ):
            if t <= 1:
                return t
            else:
                return 1.0 + ( t - 1.0 ) / n_steps * ( go_behind - 1 )

        ts = TSCrackLoc( 
                 dof_resultants = True,
                 on_update = self.plot,
                 sdomain = domain,
                 bcond_list = [# define the left clamping 
                                BCSlice( var = 'u', value = 0., dims = [0], slice = domain[ 0, 0, 0, :] ),
                                # loading at the right edge
                                 BCSlice( var = 'f', value = 1, dims = [0], slice = domain[-1, -1, -1, 0],
                                         time_function = ls ),
#                                 BCSlice(var='u', value = finish_displ, dims = [0], slice = domain[-1,-1,-1, 0],
#                                         time_function = ls ),
                                # fix horizontal displacement in the top layer
                                 BCSlice( var = 'u', value = 0., dims = [0], slice = domain[:, -1, :, -1] ),
                                # fix the vertical displacement all over the domain
                                 BCSlice( var = 'u', value = 0., dims = [1], slice = domain[ :, :, :, :] )
                                ],
                 rtrace_list = [ self.stress_strain,
                                  self.eps_m_field,
                                  self.eps_f_field,
                                  self.sig_m_field,
                                  self.sig_f_field,
                                  self.omega_m_field ]
                )

        # Add the time-loop control
        tloop = TLoop( tstepper = ts, KMAX = 200, debug = True, tolerance = 1e-5,
                       tline = TLine( min = 0.0, step = 1.0, max = 1.0 ) )

        print ts.rte_dict.keys()
        U = tloop.eval()

        self.plot()

        return array( [ U[right_dofs[-1]] ], dtype = 'float_' )
Beispiel #34
0
    def peval(self):
        '''Evaluation procedure.
        '''
        #mv = MATS1DDamageView( model = mats_eval )
        #mv.configure_traits()

        right_dof_m = self.fe_grid_m[-1, -1].dofs[0, 0, 0]

        right_dof_fb = self.fe_grid_fb[-1, -1, -1, -1].dofs[0, 0, 0]
        # Response tracers
        A = self.A_m + self.A_f
        self.sig_eps_m = RTraceGraph(name='F_u_m',
                                     var_y='F_int',
                                     idx_y=right_dof_m,
                                     var_x='U_k',
                                     idx_x=right_dof_m,
                                     transform_y='y / %g' % A)

        # Response tracers
        self.sig_eps_f = RTraceGraph(name='F_u_f',
                                     var_y='F_int',
                                     idx_y=right_dof_fb,
                                     var_x='U_k',
                                     idx_x=right_dof_fb,
                                     transform_y='y / %g' % A)

        self.eps_m_field = RTraceDomainListField(name='eps_m',
                                                 position='int_pnts',
                                                 var='eps_app',
                                                 warp=False)

        self.eps_f_field = RTraceDomainListField(name='eps_f',
                                                 position='int_pnts',
                                                 var='mats_phase2_eps_app',
                                                 warp=False)
        # Response tracers
        self.sig_m_field = RTraceDomainListField(name='sig_m',
                                                 position='int_pnts',
                                                 var='sig_app')

        self.sig_f_field = RTraceDomainListField(name='sig_f',
                                                 position='int_pnts',
                                                 var='mats_phase2_sig_app')

        self.omega_m_field = RTraceDomainListField(name='omega_m',
                                                   position='int_pnts',
                                                   var='omega',
                                                   warp=False)

        self.shear_flow_field = RTraceDomainListField(name='shear flow',
                                                      position='int_pnts',
                                                      var='shear_flow',
                                                      warp=False)

        self.slip_field = RTraceDomainListField(name='slip',
                                                position='int_pnts',
                                                var='slip',
                                                warp=False)

        avg_processor = None
        if self.avg_radius > 0.0:
            n_dofs = self.fe_domain.n_dofs
            avg_processor = RTUAvg(sd=self.fe_m_level,
                                   n_dofs=n_dofs,
                                   avg_fn=QuarticAF(radius=self.avg_radius))

        ts = TStepper(
            u_processor=avg_processor,
            dof_resultants=True,
            sdomain=self.fe_domain,
            bcond_list=[  # define the left clamping 
                BCSlice(var='u',
                        value=0.,
                        dims=[0],
                        slice=self.fe_grid_fb[0, 0, 0, :]),
                #                                BCSlice( var = 'u', value = 0., dims = [0], slice = self.fe_grid_m[ 0, 0 ] ),
                # loading at the right edge
                #                                 BCSlice( var = 'f', value = 1, dims = [0], slice = domain[-1, -1, -1, 0],
                #                                         time_function = ls ),
                BCSlice(var='u',
                        value=self.final_displ,
                        dims=[0],
                        slice=self.fe_grid_fb[-1, -1, -1, :],
                        time_function=self.time_function),
                #                                 BCSlice( var = 'u', value = self.final_displ, dims = [0], slice = self.fe_grid_m[-1, -1],
                #                                         time_function = self.time_function ),
                # fix horizontal displacement in the top layer
                #                                 BCSlice( var = 'u', value = 0., dims = [0], slice = domain[:, -1, :, -1] ),
                # fix the vertical displacement all over the domain
                BCSlice(var='u',
                        value=0.,
                        dims=[1],
                        slice=self.fe_grid_fb[:, :, :, :]),
                #                            # Connect bond and matrix domains
                BCDofGroup(var='u',
                           value=0.,
                           dims=[0],
                           get_link_dof_method=self.fe_grid_fb.get_bottom_dofs,
                           get_dof_method=self.fe_grid_m.get_all_dofs,
                           link_coeffs=[1.])
            ],
            rtrace_list=[
                self.sig_eps_m,
                self.sig_eps_f,
                self.eps_m_field,
                self.eps_f_field,
                self.sig_m_field,
                self.sig_f_field,
                self.omega_m_field,
                self.shear_flow_field,
                self.slip_field,
            ])

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      KMAX=300,
                      tolerance=1e-5,
                      debug=False,
                      verbose_iteration=True,
                      verbose_time=False,
                      tline=TLine(min=0.0, step=self.step_size, max=1.0))

        tloop.on_accept_time_step = self.plot

        U = tloop.eval()

        self.sig_eps_f.refresh()
        max_sig_m = max(self.sig_eps_m.trace.ydata)
        return array([U[right_dof_m], max_sig_m], dtype='float_')
Beispiel #35
0
def test_bar4():
    '''Clamped bar 3 domains, each with 2 elems (displ at right end)
    [0]-[1]-[2] [3]-[4]-[5] [6]-[7]-[8]
    u[0] = 0, u[2] = u[3], u[5] = u[6], u[8] = 1'''

    fets_eval = FETS1D2L(mats_eval=MATS1DElastic(E=10., A=1.))

    # Discretization
    fe_domain1 = FEGrid(coord_max=(2., 0., 0.),
                        shape=(2, ),
                        n_nodal_dofs=1,
                        dof_r=fets_eval.dof_r,
                        geo_r=fets_eval.geo_r)

    fe_domain2 = FEGrid(coord_min=(2., 0., 0.),
                        coord_max=(4., 0., 0.),
                        shape=(2, ),
                        n_nodal_dofs=1,
                        dof_r=fets_eval.dof_r,
                        geo_r=fets_eval.geo_r)

    fe_domain3 = FEGrid(coord_min=(4., 0., 0.),
                        coord_max=(6., 0., 0.),
                        shape=(2, ),
                        n_nodal_dofs=1,
                        dof_r=fets_eval.dof_r,
                        geo_r=fets_eval.geo_r)

    ts = TS(iterms=[(fets_eval, fe_domain1), (fets_eval, fe_domain2),
                    (fets_eval, fe_domain3)],
            dof_resultants=True,
            bcond_list=[
                BCDof(var='u', dof=0, value=0.),
                BCDof(var='u',
                      dof=2,
                      link_dofs=[3],
                      link_coeffs=[1.],
                      value=0.),
                BCDof(var='u',
                      dof=5,
                      link_dofs=[6],
                      link_coeffs=[1.],
                      value=0.),
                BCDof(var='u', dof=8, value=1)
            ],
            rtrace_list=[
                RTraceGraph(name='Fi,right over u_right (iteration)',
                            var_y='F_int',
                            idx_y=0,
                            var_x='U_k',
                            idx_x=1),
                RTraceDomainListField(name='Displacement', var='u', idx=0)
            ])

    # Add the time-loop control
    tloop = TLoop(tstepper=ts, tline=TLine(min=0.0, step=1, max=1.0))

    print tloop.eval()
    from ibvpy.plugins.ibvpy_app import IBVPyApp
    app = IBVPyApp(ibv_resource=tloop)
    app.main()
Beispiel #36
0
                       value=0.,
                       dims=[0],
                       get_dof_method=domain.get_left_dofs),
            BCDofGroup(var='u',
                       value=0.,
                       dims=[1],
                       get_dof_method=domain.get_bottom_left_dofs),
            BCDofGroup(var='u',
                       value=0.002,
                       dims=[0],
                       get_dof_method=domain.get_right_dofs)
        ],
        rtrace_list=[
            RTraceGraph(name='Fi,right over u_right (iteration)',
                        var_y='F_int',
                        idx_y=right_dof,
                        var_x='U_k',
                        idx_x=right_dof),
            #                         RTraceDomainListField(name = 'Stress' ,
            #                         var = 'sig_app', idx = 0,
            #                         record_on = 'update'),
            RTraceDomainListField(name='Displacement', var='u', idx=0),
            #                             RTraceDomainListField(name = 'N0' ,
            #                                          var = 'N_mtx', idx = 0,
            # record_on = 'update')
        ])

    # Add the time-loop control

    global tloop
    tloop = TLoop(tstepper=ts, DT=0.5, tline=TLine(min=0.0, max=1.0, step=0.1))
Beispiel #37
0
class SimBT4PT(IBVModel):
    '''Simulation: four point bending test.
    '''

    input_change = Event

    @on_trait_change('+input,ccs_unit_cell.input_change')
    def _set_input_change(self):
        self.input_change = True

    implements(ISimModel)

    #-----------------
    # discretization:
    #-----------------

    # specify weather the elastomer is to be modeled or if the load is
    # introduced as line load
    #
    elstmr_flag = Bool(True)

    # discretization in x-direction (longitudinal):
    #
    outer_zone_shape_x = Int(6, input=True, ps_levels=(4, 12, 3))

    # discretization in x-direction (longitudinal):
    #
    load_zone_shape_x = Int(2, input=True, ps_levels=(1, 4, 1))

    # middle part discretization in x-direction (longitudinal):
    #
    mid_zone_shape_x = Int(3, input=True, ps_levels=(1, 4, 1))

    # discretization in y-direction (width):
    #
    shape_y = Int(2, input=True, ps_levels=(1, 4, 2))

    # discretization in z-direction:
    #
    shape_z = Int(2, input=True, ps_levels=(1, 3, 3))

    #-----------------
    # geometry:
    #-----------------
    #
    # edge length of the bending specimen (beam) (entire length without symmetry)
    #
    length = Float(1.50, input=True)

    elstmr_length = Float(0.05, input=True)
    mid_zone_length = Float(0.50, input=True)
    elstmr_thickness = Float(0.005, input=True)
    width = Float(0.20, input=True)
    thickness = Float(0.06, input=True)

    #-----------------
    # derived geometric parameters
    #-----------------
    #
    # half the length of the elastomer (load introduction
    # with included symmetry)
    #
    sym_specmn_length = Property

    def _get_sym_specmn_length(self):
        return self.length / 2.

    sym_mid_zone_specmn_length = Property

    def _get_sym_mid_zone_specmn_length(self):
        return self.mid_zone_length / 2.

    # half the length of the elastomer (load introduction
    # with included symmetry
    #
    sym_elstmr_length = Property

    def _get_sym_elstmr_length(self):
        return self.elstmr_length / 2.

    # half the specimen width
    #
    sym_width = Property

    def _get_sym_width(self):
        return self.width / 2.

    #----------------------------------------------------------------------------------
    # mats_eval
    #----------------------------------------------------------------------------------

    # age of the plate at the time of testing
    # NOTE: that the same phi-function is used independent of age. This assumes a
    # an afine/proportional damage evolution for different ages.
    #
    age = Int(28, input=True)

    # time stepping params
    #
    tstep = Float(0.05, auto_set=False, enter_set=True, input=True)
    tmax = Float(1.0, auto_set=False, enter_set=True, input=True)
    tolerance = Float(0.001, auto_set=False, enter_set=True, input=True)

    # specify type of 'linalg.norm'
    # default value 'None' sets norm to 2-norm,
    # i.e "norm = sqrt(sum(x_i**2))
    #
    # set 'ord=np.inf' to switch norm to
    # "norm = max(abs(x_i))"
    #
    ord = Enum(np.inf, None)

    n_mp = Int(30, input=True)

    # @todo: for mats_eval the information of the unit cell should be used
    # in order to use the same number of microplanes and model version etc...
    #
    specmn_mats = Property(Instance(MATS2D5MicroplaneDamage),
                           depends_on='input_change')

    @cached_property
    def _get_specmn_mats(self):
        return MATS2D5MicroplaneDamage(
            E=self.E_c,
            #                                 E=self.E_m,
            nu=self.nu,
            # corresponding to settings in "MatsCalib"
            n_mp=self.n_mp,
            symmetrization='sum-type',
            model_version='compliance',
            phi_fn=self.phi_fn)

    if elstmr_flag:
        elstmr_mats = Property(Instance(MATS3DElastic),
                               depends_on='input_change')

        @cached_property
        def _get_elstmr_mats(self):
            # specify a small elastomer stiffness (approximation)
            E_elast = self.E_c / 10.
            print 'effective elastomer E_modulus', E_elast
            return MATS3DElastic(E=E_elast, nu=0.4)

    #-----------------
    # fets:
    #-----------------

    # specify element shrink factor in plot of fe-model
    #
    vtk_r = Float(0.95)

    # use quadratic serendipity elements
    #
    specmn_fets = Property(Instance(FETSEval), depends_on='input_change')

    @cached_property
    def _get_specmn_fets(self):
        fets = FETS2D58H20U(mats_eval=self.specmn_mats)
        fets.vtk_r *= self.vtk_r
        return fets

    # use quadratic serendipity elements
    #
    elstmr_fets = Property(Instance(FETSEval), depends_on='input_change')

    @cached_property
    def _get_elstmr_fets(self):
        fets = FETS2D58H20U(mats_eval=self.elstmr_mats)
        fets.vtk_r *= self.vtk_r
        return fets

    fe_domain = Property(depends_on='+ps_levels, +input')

    @cached_property
    def _get_fe_domain(self):
        return FEDomain()

    #===========================================================================
    # fe level
    #===========================================================================

    outer_zone_specmn_fe_level = Property(depends_on='+ps_levels, +input')

    def _get_outer_zone_specmn_fe_level(self):
        return FERefinementGrid(name='outer zone specimen patch',
                                fets_eval=self.specmn_fets,
                                domain=self.fe_domain)

    load_zone_specmn_fe_level = Property(depends_on='+ps_levels, +input')

    def _get_load_zone_specmn_fe_level(self):
        return FERefinementGrid(name='load zone specimen patch',
                                fets_eval=self.specmn_fets,
                                domain=self.fe_domain)

    mid_zone_specmn_fe_level = Property(depends_on='+ps_levels, +input')

    def _get_mid_zone_specmn_fe_level(self):
        return FERefinementGrid(name='mid zone specimen patch',
                                fets_eval=self.specmn_fets,
                                domain=self.fe_domain)

    elstmr_fe_level = Property(depends_on='+ps_levels, +input')

    def _get_elstmr_fe_level(self):
        return FERefinementGrid(name='elastomer patch',
                                fets_eval=self.elstmr_fets,
                                domain=self.fe_domain)

    #===========================================================================
    # Grid definition
    #===========================================================================

    mid_zone_specmn_fe_grid = Property(Instance(FEGrid),
                                       depends_on='+ps_levels, +input')

    @cached_property
    def _get_mid_zone_specmn_fe_grid(self):
        # only a quarter of the beam is simulated due to symmetry:
        fe_grid = FEGrid(coord_min=(0., 0., 0.),
                         coord_max=(self.sym_mid_zone_specmn_length -
                                    self.sym_elstmr_length, self.sym_width,
                                    self.thickness),
                         shape=(self.mid_zone_shape_x, self.shape_y,
                                self.shape_z),
                         level=self.mid_zone_specmn_fe_level,
                         fets_eval=self.specmn_fets)
        return fe_grid

    load_zone_specmn_fe_grid = Property(Instance(FEGrid),
                                        depends_on='+ps_levels, +input')

    @cached_property
    def _get_load_zone_specmn_fe_grid(self):
        # only a quarter of the beam is simulated due to symmetry:
        fe_grid = FEGrid(coord_min=(self.sym_mid_zone_specmn_length -
                                    self.sym_elstmr_length, 0., 0.),
                         coord_max=(self.sym_mid_zone_specmn_length +
                                    self.sym_elstmr_length, self.sym_width,
                                    self.thickness),
                         shape=(self.load_zone_shape_x, self.shape_y,
                                self.shape_z),
                         level=self.load_zone_specmn_fe_level,
                         fets_eval=self.specmn_fets)
        return fe_grid

#    if elstmr_flag:

    elstmr_fe_grid = Property(Instance(FEGrid),
                              depends_on='+ps_levels, +input')

    @cached_property
    def _get_elstmr_fe_grid(self):
        fe_grid = FEGrid(coord_min=(self.sym_mid_zone_specmn_length -
                                    self.sym_elstmr_length, 0.,
                                    self.thickness),
                         coord_max=(self.sym_mid_zone_specmn_length +
                                    self.sym_elstmr_length, self.sym_width,
                                    self.thickness + self.elstmr_thickness),
                         level=self.elstmr_fe_level,
                         shape=(self.load_zone_shape_x, self.shape_y, 1),
                         fets_eval=self.elstmr_fets)
        return fe_grid

    outer_zone_specmn_fe_grid = Property(Instance(FEGrid),
                                         depends_on='+ps_levels, +input')

    @cached_property
    def _get_outer_zone_specmn_fe_grid(self):
        # only a quarter of the plate is simulated due to symmetry:
        fe_grid = FEGrid(coord_min=(self.sym_mid_zone_specmn_length +
                                    self.sym_elstmr_length, 0., 0.),
                         coord_max=(self.sym_specmn_length, self.sym_width,
                                    self.thickness),
                         shape=(self.outer_zone_shape_x, self.shape_y,
                                self.shape_z),
                         level=self.outer_zone_specmn_fe_level,
                         fets_eval=self.specmn_fets)
        return fe_grid

    #===========================================================================
    # Boundary conditions
    #===========================================================================
    w_max = Float(-0.030, input=True)  # [m]

    w_max = Float(-0.030, input=True)  # [m]

    bc_list = Property(depends_on='+ps_levels, +input')

    @cached_property
    def _get_bc_list(self):
        mid_zone_specimen = self.mid_zone_specmn_fe_grid
        load_zone_specimen = self.load_zone_specmn_fe_grid
        outer_zone_specimen = self.outer_zone_specmn_fe_grid

        if self.elstmr_flag:
            elastomer = self.elstmr_fe_grid

        #--------------------------------------------------------------
        # boundary conditions for the symmetry
        #--------------------------------------------------------------
        # symmetry in the xz-plane
        # (Note: the x-axis corresponds to the axis of symmetry along the longitudinal axis of the beam)
        #
        bc_outer_zone_symplane_xz = BCSlice(var='u',
                                            value=0.,
                                            dims=[1],
                                            slice=outer_zone_specimen[:,
                                                                      0, :, :,
                                                                      0, :])
        bc_load_zone_symplane_xz = BCSlice(var='u',
                                           value=0.,
                                           dims=[1],
                                           slice=load_zone_specimen[:, 0, :, :,
                                                                    0, :])
        bc_mid_zone_symplane_xz = BCSlice(var='u',
                                          value=0.,
                                          dims=[1],
                                          slice=mid_zone_specimen[:, 0, :, :,
                                                                  0, :])

        if self.elstmr_flag:
            bc_el_symplane_xz = BCSlice(var='u',
                                        value=0.,
                                        dims=[1],
                                        slice=elastomer[:, 0, :, :, 0, :])
        # symmetry in the yz-plane
        #
        bc_mid_zone_symplane_yz = BCSlice(var='u',
                                          value=0.,
                                          dims=[0],
                                          slice=mid_zone_specimen[0, :, :,
                                                                  0, :, :])

        #--------------------------------------------------------------
        # boundary conditions for the support
        #--------------------------------------------------------------
        bc_support_0y0 = BCSlice(var='u',
                                 value=0.,
                                 dims=[2],
                                 slice=outer_zone_specimen[-1, :, 0, -1, :, 0])

        #--------------------------------------------------------------
        # connect all grids
        #--------------------------------------------------------------
        link_loadzn_outerzn = BCDofGroup(
            var='u',
            value=0.,
            dims=[0, 1, 2],
            get_dof_method=load_zone_specimen.get_right_dofs,
            get_link_dof_method=outer_zone_specimen.get_left_dofs,
            link_coeffs=[1.])
        link_midzn_loadzn = BCDofGroup(
            var='u',
            value=0.,
            dims=[0, 1, 2],
            get_dof_method=mid_zone_specimen.get_right_dofs,
            get_link_dof_method=load_zone_specimen.get_left_dofs,
            link_coeffs=[1.])

        if self.elstmr_flag:
            link_elstmr_loadzn_z = BCDofGroup(
                var='u',
                value=0.,
                dims=[2],
                get_dof_method=elastomer.get_back_dofs,
                get_link_dof_method=load_zone_specimen.get_front_dofs,
                link_coeffs=[1.])

            # hold elastomer in a single point in order to avoid kinematic movement yielding singular K_mtx
            #
            bc_elstmr_fix = BCSlice(var='u',
                                    value=0.,
                                    dims=[0],
                                    slice=elastomer[0, 0, 0, 0, 0, 0])

        #--------------------------------------------------------------
        # loading
        #--------------------------------------------------------------
        # w_max = center displacement:
        w_max = self.w_max

        if self.elstmr_flag:
            # apply displacement at all top nodes of the elastomer (surface load)
            #
            bc_w = BCSlice(var='u',
                           value=w_max,
                           dims=[2],
                           slice=elastomer[:, :, -1, :, :, -1])
        else:
            bc_w = BCSlice(
                var='u',
                value=w_max,
                dims=[2],
                # slice is only exactly in the center of the loading zone for 'load_zone_shape_x' = 2
                # center line of the load zone
                slice=load_zone_specimen[0, :, -1, -1, :, -1])


#        f_max = 0.010 / 4. / self.sym_width
#        bc_line_f = BCSlice(var = 'f', value = f_max, dims = [2],
#                            # slice is only valid for 'load_zone_shape_x' = 2
#                            # center line of the load zone
#                            slice = load_zone_specimen[0, :, -1, -1, :, -1])

        bc_list = [
            bc_outer_zone_symplane_xz,
            bc_load_zone_symplane_xz,
            bc_mid_zone_symplane_xz,
            bc_mid_zone_symplane_yz,
            #
            link_midzn_loadzn,
            link_loadzn_outerzn,
            bc_support_0y0,
            #
            bc_w,
        ]

        if self.elstmr_flag:
            bc_list += [bc_el_symplane_xz, link_elstmr_loadzn_z, bc_elstmr_fix]

        return bc_list

    #----------------------
    # tloop
    #----------------------

    tloop = Property(depends_on='input_change')

    @cached_property
    def _get_tloop(self):

        #--------------------------------------------------------------
        # ts
        #--------------------------------------------------------------

        mid_zone_spec = self.mid_zone_specmn_fe_grid
        load_zone_spec = self.load_zone_specmn_fe_grid
        outer_zone_spec = self.outer_zone_specmn_fe_grid

        if self.elstmr_flag:
            # ELSTRMR TOP SURFACE
            # dofs at elastomer top surface (used to integrate the force)
            #
            elastomer = self.elstmr_fe_grid
            elstmr_top_dofs_z = elastomer[:, :, -1, :, :,
                                          -1].dofs[:, :, 2].flatten()
            load_dofs_z = np.unique(elstmr_top_dofs_z)
            print 'load_dofs_z', load_dofs_z
        else:
            # LINE LOAD TOP OF LOAD ZONE
            # dofs at center line of the specmn load zone (used to integrate the force)
            # note slice index in x-direction is only valid for load_zone_shape_x = 2 !
            #
            load_zone_spec_topline_dofs_z = load_zone_spec[
                0, :, -1, -1, :, -1].dofs[:, :, 2].flatten()
            load_dofs_z = np.unique(load_zone_spec_topline_dofs_z)
            print 'load_dofs_z', load_dofs_z

        # SUPPRT LINE
        # dofs at support line of the specmn (used to integrate the force)
        #
        outer_zone_spec_supprtline_dofs_z = outer_zone_spec[
            -1, :, 0, -1, :, 0].dofs[:, :, 2].flatten()
        supprt_dofs_z = np.unique(outer_zone_spec_supprtline_dofs_z)
        print 'supprt_dofs_z', supprt_dofs_z

        # CENTER DOF (used for tracing of the displacement)
        #
        center_bottom_dof = mid_zone_spec[0, 0, 0, 0, 0, 0].dofs[0, 0, 2]
        print 'center_bottom_dof', center_bottom_dof

        # THIRDPOINT DOF (used for tracing of the displacement)
        # dofs at center middle of the laod zone at the bottom side
        #
        # NOTE: slice index in x-direction is only valid for load_zone_shape_x = 2 !
        thirdpoint_bottom_dof = load_zone_spec[0, 0, 0, -1, 0, 0].dofs[0, 0, 2]
        print 'thirdpoint_bottom_dof', thirdpoint_bottom_dof

        # force-displacement-diagram (CENTER)
        #
        self.f_w_diagram_center = RTraceGraph(
            name='displacement_elasttop (center) - force',
            var_x='U_k',
            idx_x=center_bottom_dof,
            var_y='F_int',
            idx_y_arr=load_dofs_z,
            record_on='update',
            transform_x='-x * 1000',  # %g * x' % ( fabs( w_max ),),
            # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
            #
            transform_y='-4000. * y')

        # force-displacement-diagram_supprt (SUPPRT)
        #
        self.f_w_diagram_supprt = RTraceGraph(
            name='displacement_supprtline (center) - force',
            var_x='U_k',
            idx_x=center_bottom_dof,
            var_y='F_int',
            idx_y_arr=supprt_dofs_z,
            record_on='update',
            transform_x='-x * 1000',  # %g * x' % ( fabs( w_max ),),
            # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
            #
            transform_y='4000. * y')

        # force-displacement-diagram (THIRDPOINT)
        #
        self.f_w_diagram_thirdpoint = RTraceGraph(
            name='displacement_elasttop (thirdpoint) - force',
            var_x='U_k',
            idx_x=thirdpoint_bottom_dof,
            var_y='F_int',
            idx_y_arr=load_dofs_z,
            record_on='update',
            transform_x='-x * 1000',  # %g * x' % ( fabs( w_max ),),
            # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
            #
            transform_y='-4000. * y')

        ts = TS(
            sdomain=self.fe_domain,
            bcond_list=self.bc_list,
            rtrace_list=[
                self.f_w_diagram_center,
                self.f_w_diagram_thirdpoint,
                self.f_w_diagram_supprt,
                RTraceDomainListField(name='Displacement',
                                      var='u',
                                      idx=0,
                                      warp=True),
                #                             RTraceDomainListField(name = 'Stress' ,
                #                                            var = 'sig_app', idx = 0, warp = True,
                #                                            record_on = 'update'),
                #                             RTraceDomainListField(name = 'Strain' ,
                #                                        var = 'eps_app', idx = 0, warp = True,
                #                                        record_on = 'update'),
                #                             RTraceDomainListField(name = 'Damage' ,
                #                                        var = 'omega_mtx', idx = 0, warp = True,
                #                                        record_on = 'update'),
                RTraceDomainListField(name='max_omega_i',
                                      warp=True,
                                      var='max_omega_i',
                                      idx=0,
                                      record_on='update'),
                #                             RTraceDomainListField(name = 'IStress' ,
                #                                            position = 'int_pnts',
                #                                            var = 'sig_app', idx = 0,
                #                                            record_on = 'update'),
                #                             RTraceDomainListField(name = 'IStrain' ,
                #                                            position = 'int_pnts',
                #                                            var = 'eps_app', idx = 0,
                #                                            record_on = 'update'),
            ])

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      KMAX=50,
                      tolerance=self.tolerance,
                      RESETMAX=0,
                      tline=TLine(min=0.0, step=self.tstep, max=self.tmax),
                      ord=self.ord)

        return tloop

    def peval(self):
        '''
        Evaluate the model and return the array of results specified
        in the method get_sim_outputs.
        '''
        U = self.tloop.eval()

        self.f_w_diagram_center.refresh()
        F_max = max(self.f_w_diagram_center.trace.ydata)

        u_center_top_z = U[self.center_top_dofs][0, 0, 2]
        return array([u_center_top_z, F_max], dtype='float_')

    def get_sim_outputs(self):
        '''
        Specifies the results and their order returned by the model
        evaluation.
        '''
        return [
            SimOut(name='u_center_top_z', unit='m'),
            SimOut(name='F_max', unit='kN')
        ]
Beispiel #38
0
class SimBT3PT(IBVModel):
    '''Simulation: Bending Test Three Point
    '''

    input_change = Event
    @on_trait_change('+input,ccs_unit_cell.input_change')
    def _set_input_change(self):
        self.input_change = True

    implements(ISimModel)

    #-----------------
    # discretization:
    #-----------------
    #
    # discretization in x-direction (longitudinal):
    shape_x = Int(10, input=True,
                      ps_levels=(4, 12, 3))

    # discretization in x-direction (longitudinal):
    mid_shape_x = Int(1, input=True,
                      ps_levels=(1, 4, 1))


    # discretization in y-direction (width):
    shape_y = Int(3, input=True,
                      ps_levels=(1, 4, 2))

    # discretization in z-direction:
    shape_z = Int(2, input=True,
                      ps_levels=(1, 3, 3))

    # support discretization in xy-direction:
    # NOTE: chose '2' for 2x2-grid or '4' for 4x4-grid
    #
    shape_supprt_x = Int(2, input=True,
                      ps_levels=(2, 4, 2))

    #-----------------
    # geometry:
    #-----------------
    #
    # edge length of the bending specimen (beam) (entire length without symmetry)
    length = Float(1.15, input=True)
    elstmr_length = Float(0.05, input=True)
    elstmr_thickness = Float(0.005, input=True,
                                enter_set=True, auto_set=False)
    width = Float(0.20, input=True)
    thickness = Float(0.06, input=True,
                      ps_levels=(0.054, 0.060, 0.066))

    # thickness of the tappered support
    #
    thickness_supprt = Float(0.02, input=True)
    #-----------------
    # derived geometric parameters
    #-----------------
    #
    # half the length of the elastomer (load introduction
    # with included symmetry)
    #
    sym_specmn_length = Property
    def _get_sym_specmn_length(self):
        return self.length / 2.

    # half the length of the elastomer (load introduction
    # with included symmetry
    #
    sym_elstmr_length = Property
    def _get_sym_elstmr_length(self):
        return (self.elstmr_length) / 2.

    # half the specimen width
    #
    sym_width = Property
    def _get_sym_width(self):
        return self.width / 2.

    #-----------------
    # specify the refinement of the idealization
    #-----------------

    # specify weather elastomer is to be modeled for load introduction
    #
    elstmr_flag = True

    # specify weather steel support is to be modeled
    #
    supprt_flag = False

    #-----------------
    # 'geo_transform'
    #-----------------

    # geometry transformation for four sided tappered support with reduced stiffness towards the edges (if modeled)
    #
    geo_supprt = Property(Instance(GeoSUPPRT), depends_on='+ps_levels, +input')
    @cached_property
    def _get_geo_supprt(self):
        # element length within the range of the slab without the area of the
        # load introduction plate
        #
        elem_size = self.sym_specmn_length / self.shape_x
        width_supprt = self.shape_supprt_x * elem_size
        print 'width_supprt = ', width_supprt
        return GeoSUPPRT(thickness_supprt=self.thickness_supprt,
                         width_supprt=width_supprt,
                         xyoffset=0.,
                         zoffset= -self.thickness_supprt)

    #----------------------------------------------------------------------------------
    # mats_eval
    #----------------------------------------------------------------------------------

    # age of the specimen at the time of testing
    # determines the E-modulus and nu based on the time dependent function stored
    # in 'CCSUniteCell' if params are not explicitly set
    #
    age = Int(28, input=True)

    # composite E-modulus / Poisson's ratio
    # NOTE 1: value are retrieved from the database
    #         same values are used for calibration (as taken from tensile test) and for slab test
    # NOTE 2: alternatively the same phi-function could be used independent of age. This would assume
    #         an afine/proportional damage evolution for different ages, i.e. a different E would be
    #         used in the simulation of the slab test and within the calibration procedure.

    # time stepping params
    #
    tstep = Float(0.05, auto_set=False, enter_set=True, input=True)
    tmax = Float(1.0, auto_set=False, enter_set=True, input=True)
    tolerance = Float(0.001, auto_set=False, enter_set=True, input=True)

    # specify type of 'linalg.norm'
    # default value 'None' sets norm to 2-norm,
    # i.e "norm = sqrt(sum(x_i**2))
    #
    # set 'ord=np.inf' to switch norm to
    # "norm = max(abs(x_i))"
    #
    ord = Enum(None, np.inf)

    # number of microplanes
    #
    n_mp = Int(30., auto_set=False, enter_set=True, input=True)

    #----------------------------------------------------------------------------------
    # mats_eval
    #----------------------------------------------------------------------------------

    # @todo: for mats_eval the information of the unit cell should be used
    # in order to use the same number of microplanes and model version etc...
    #
    specmn_mats = Property(Instance(MATS2D5MicroplaneDamage),
                          depends_on='input_change')
    @cached_property
    def _get_specmn_mats(self):
        return MATS2D5MicroplaneDamage(
                                E=self.E_c,
#                                 E=self.E_m,  # relevant for compressive behavior/used for calibration of phi_fn
                                nu=self.nu,
                                # corresponding to settings in "MatsCalib"
                                n_mp=30,
                                symmetrization='sum-type',
                                model_version='compliance',
                                phi_fn=self.phi_fn)

    E_elstmr = Float(3000., input=True)

    elstmr_mats = Property(Instance(MATS3DElastic),
                                   depends_on='input_change')
    @cached_property
    def _get_elstmr_mats(self):
        E_elstmr = self.E_elstmr
        print 'effective elastomer E_modulus', E_elstmr
        return MATS3DElastic(E=E_elstmr,
                             nu=0.4)

    # E-modulus and nu of steel support
    E_s = Float(210000., auto_set=False, enter_set=True, input=True)
    nu_s = Float(0.20, auto_set=False, enter_set=True, input=True)

    supprt_mats = Property(Instance(MATS3DElastic),
                                    depends_on='input_change')
    @cached_property
    def _get_supprt_mats(self):
        return MATS3DElastic(E=self.E_s,
                             nu=self.nu_s)

    #-----------------
    # fets:
    #-----------------

    # specify element shrink factor in plot of fe-model
    #
    vtk_r = Float(0.95)

    # use quadratic serendipity elements
    # NOTE: 2D5 elements behave linear elastic in out of plane direction!
    #
    specmn_fets = Property(Instance(FETSEval),
                             depends_on='input_change')
    @cached_property
    def _get_specmn_fets(self):
        fets = FETS2D58H20U(mats_eval=self.specmn_mats)
        fets.vtk_r *= self.vtk_r
        return fets

    # use quadratic serendipity elements
    #
    elstmr_fets = Property(Instance(FETSEval),
                             depends_on='input_change')
    @cached_property
    def _get_elstmr_fets(self):
        fets = FETS2D58H20U(mats_eval=self.elstmr_mats)
        fets.vtk_r *= self.vtk_r
        return fets

    supprt_fets = Property(Instance(FETSEval),
                           depends_on='input_change')
    @cached_property
    def _get_supprt_fets(self):
        # linear-elastic behavior quadratic serendipity elements
        fets = FETS3D8H20U(mats_eval=self.supprt_mats)
        fets.vtk_r *= self.vtk_r
        return fets

    #-----------------
    # fe_grid:
    #-----------------

    fe_domain = Property(depends_on='+ps_levels, +input')
    @cached_property
    def _get_fe_domain(self):
        return FEDomain()

    mid_specmn_fe_level = Property(depends_on='+ps_levels, +input')
    @cached_property
    def _get_mid_specmn_fe_level(self):
        return  FERefinementGrid(name='middle specimen patch',
                                 fets_eval=self.specmn_fets,
                                 domain=self.fe_domain)

    mid_specmn_fe_grid = Property(Instance(FEGrid), depends_on='+ps_levels, +input')
    @cached_property
    def _get_mid_specmn_fe_grid(self):
        # only a quarter of the beam is simulated due to symmetry:
        fe_grid = FEGrid(coord_min=(0., 0., 0.),
                         coord_max=(self.sym_elstmr_length,
                                      self.width / 2,
                                      self.thickness),
                         shape=(self.mid_shape_x, self.shape_y, self.shape_z),
                         level=self.mid_specmn_fe_level,
                         fets_eval=self.specmn_fets)
        return fe_grid

    specmn_fe_level = Property(depends_on='+ps_levels, +input')
    @cached_property
    def _get_specmn_fe_level(self):
        return  FERefinementGrid(name='specimen patch',
                                 fets_eval=self.specmn_fets,
                                 domain=self.fe_domain)

    specmn_fe_grid = Property(Instance(FEGrid), depends_on='+ps_levels, +input')
    @cached_property
    def _get_specmn_fe_grid(self):
        # only a quarter of the beam is simulated due to symmetry:
        fe_grid = FEGrid(coord_min=(self.sym_elstmr_length,
                                      0.,
                                      0.),
                         coord_max=(self.sym_specmn_length,
                                      self.sym_width,
                                      self.thickness),
                         shape=(self.shape_x, self.shape_y, self.shape_z),
                         level=self.specmn_fe_level,
                         fets_eval=self.specmn_fets)
        return fe_grid

#    if elstmr_flag:
    elstmr_fe_level = Property(depends_on='+ps_levels, +input')
    @cached_property
    def _get_elstmr_fe_level(self):
        return  FERefinementGrid(name='elastomer patch',
                                 fets_eval=self.elstmr_fets,
                                 domain=self.fe_domain)

    elstmr_fe_grid = Property(Instance(FEGrid), depends_on='+ps_levels, +input')
    @cached_property
    def _get_elstmr_fe_grid(self):
        x_max = self.sym_elstmr_length
        y_max = self.width / 2.
        z_max = self.thickness + self.elstmr_thickness
        fe_grid = FEGrid(coord_min=(0, 0, self.thickness),
                         coord_max=(x_max, y_max, z_max),
                         level=self.elstmr_fe_level,
                         shape=(self.mid_shape_x, self.shape_y, 1),
                         fets_eval=self.elstmr_fets)
        return fe_grid

    if supprt_flag:
        supprt_fe_level = Property(depends_on='+ps_levels, +input')
        @cached_property
        def _get_supprt_fe_level(self):
            return  FERefinementGrid(name='elastomer patch',
                                     fets_eval=self.supprt_fets,
                                     domain=self.fe_domain)

        supprt_fe_grid = Property(Instance(FEGrid), depends_on='+ps_levels, +input')
        @cached_property
        def _get_supprt_fe_grid(self):
            return FEGrid(coord_min=(0, 0, 0),
                          coord_max=(1, 1, 1),
                          level=self.supprt_fe_level,
                          # use shape (2,2) in order to place support in the center of the steel support
                          # corresponding to 4 elements of the slab mesh
                          #
                          shape=(self.shape_supprt_x, self.shape_supprt_x, 1),
                          geo_transform=self.geo_supprt,
                          fets_eval=self.supprt_fets)

    #===========================================================================
    # Boundary conditions
    #===========================================================================

    # w_max = center displacement:
    #
    w_max = Float(-0.010, input=True)  # [m]

    bc_list = Property(depends_on='+ps_levels, +input')
    @cached_property
    def _get_bc_list(self):
        specmn = self.specmn_fe_grid
        mid_specmn = self.mid_specmn_fe_grid
        if self.elstmr_flag:
            elstmr = self.elstmr_fe_grid

        #--------------------------------------------------------------
        # boundary conditions for the symmetry
        #--------------------------------------------------------------
        # the x-axis corresponds to the axis of symmetry along the longitudinal axis of the beam:
        bc_symplane_xz = BCSlice(var='u', value=0., dims=[1],
                                 slice=specmn[:, 0, :, :, 0, :])

        bc_mid_symplane_xz = BCSlice(var='u', value=0., dims=[1],
                                 slice=mid_specmn[:, 0, :, :, 0, :])

        bc_mid_symplane_yz = BCSlice(var='u', value=0., dims=[0],
                                 slice=mid_specmn[0, :, :, 0, :, :])

        if self.elstmr_flag:
            bc_el_symplane_xz = BCSlice(var='u', value=0., dims=[1],
                                        slice=elstmr[:, 0, :, :, 0, :])
            bc_el_symplane_yz = BCSlice(var='u', value=0., dims=[0],
                                        slice=elstmr[0, :, :, 0, :, :])

        #--------------------------------------------------------------
        # boundary conditions for the support
        #--------------------------------------------------------------
        bc_support_0y0 = BCSlice(var='u', value=0., dims=[2],
                                 slice=specmn[-1, :, 0, -1, :, 0])

        #--------------------------------------------------------------
        # link domains
        #--------------------------------------------------------------
        link_msp_sp = BCDofGroup(var='u', value=0., dims=[0, 1, 2],
                                 get_dof_method=mid_specmn.get_right_dofs,
                                 get_link_dof_method=specmn.get_left_dofs,
                                 link_coeffs=[1.])

#        link_msp_sp_xyz = BCSlice(var = 'u', value = 0., dims = [0, 1, 2],
#                             slice = specmn[0, :, :, 0, :, :],
#                             link_slice = mid_specmn[-1 :, :, -1, :, :],
#                             link_dims = [0, 1, 2],
#                             link_coeffs = [1.])

#        link_msp_sp_y = BCSlice(var = 'u', value = 0., dims = [1],
#                             slice = specmn[0, :, :, 0, :, :],
#                             link_slice = mid_specmn[-1 :, :, -1, :, :],
#                             link_dims = [1],
#                             link_coeffs = [1.])
#
#        link_msp_sp_z = BCSlice(var = 'u', value = 0., dims = [2],
#                             slice = specmn[0, :, :, 0, :, :],
#                             link_slice = mid_specmn[-1 :, :, -1, :, :],
#                             link_dims = [2],
#                             link_coeffs = [1.])

#        link_msp_sp = [ link_msp_sp_xyz ]

        if self.elstmr_flag:
            link_el_sp = BCDofGroup(var='u', value=0., dims=[2],
                                    get_dof_method=elstmr.get_back_dofs,
                                    get_link_dof_method=mid_specmn.get_front_dofs,
                                    link_coeffs=[1.])

        #--------------------------------------------------------------
        # loading
        #--------------------------------------------------------------
        w_max = self.w_max
#        f_max = -0.010 / 0.10 # [MN/m]

        if self.elstmr_flag:
            # apply displacement at all top node (surface load)
            #
            bc_w = BCSlice(var='u', value=w_max, dims=[2],
                           slice=elstmr[:, :, -1, :, :, -1])
            # apply a single force at the center of the beam (system origin at top of the elastomer
            # and us elastomer-domain as load distribution plate with a high stiffness (e.g. steel)
#            F_max = -0.010 #[MN]
#            bc_F = BCSlice(var = 'f', value = F_max, dims = [2],
#                           slice = elstmr[0, 0, -1, 0, 0, -1])
        else:
            # center top nodes (line load)
            #
            bc_w = BCSlice(var='u', value=w_max, dims=[2],
                            slice=mid_specmn[0, :, -1, 0, :, -1])
            # NOTE: the entire symmetry axis (yz)-plane is moved downwards
            # in order to avoid large indentations at the top nodes
            #
#          bc_center_w = BCSlice( var = 'w', value = w_max, dims = [2], slice = mid_specmn[0, :, :, 0, :, :] )

        bc_list = [bc_symplane_xz, bc_mid_symplane_xz, bc_mid_symplane_yz,
                   bc_support_0y0, link_msp_sp, bc_w ]

        if self.elstmr_flag:
            bc_list_elstmr = [ link_el_sp, bc_el_symplane_xz, bc_el_symplane_yz ]
            bc_list += bc_list_elstmr

        return bc_list

    tloop = Property(depends_on='input_change')
    @cached_property
    def _get_tloop(self):

        #--------------------------------------------------------------
        # ts
        #--------------------------------------------------------------

        specmn = self.specmn_fe_grid
        mid_specmn = self.mid_specmn_fe_grid

        if self.supprt_flag:
            supprt = self.supprt_fe_grid
            supprt_dofs_z = np.unique(supprt[self.shape_supprt_x / 2, self.shape_y / 2, 0, 0, 0, 0].dofs[:, :, 2].flatten())
        else:
            supprt_dofs_z = np.unique(specmn[-1, :, 0, -1, :, 0].dofs[:, :, 2].flatten())
        print 'supprt_dofs_z (unique)', supprt_dofs_z

        if self.elstmr_flag:
            elstmr = self.elstmr_fe_grid
            load_dofs_z = np.unique(elstmr[:, :, -1, :, :, -1].dofs[:, :, 2].flatten())
        else:
            # center_top_line_dofs
            #
            load_dofs_z = np.unique(mid_specmn[0, :, -1, 0, :, -1].dofs[:, :, 2].flatten())
        print 'load_dofs_z used for integration of force: ', load_dofs_z

        # center top z-dof
        #
        center_top_dof_z = mid_specmn[0, 0, 0, 0, 0, 0].dofs[0, 0, 2]
        print 'center_top_dof used for displacement tracing: ', center_top_dof_z

        # force-displacement-diagram (LOAD)
        # (surface load on the elstmr or line load at specimen center)
        #
        self.f_w_diagram_center = RTraceGraph(name='displacement (center) - reaction 2',
                                       var_x='U_k'  , idx_x=center_top_dof_z,
                                       var_y='F_int', idx_y_arr=load_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='-4000. * y')

        # force-displacement-diagram (SUPPORT)
        # (dofs at support line of the specmn used to integrate the force)
        #
        self.f_w_diagram_supprt = RTraceGraph(name='displacement (center) - reaction 2',
                                       var_x='U_k'  , idx_x=center_top_dof_z,
                                       var_y='F_int', idx_y_arr=supprt_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='4000. * y')

        ts = TS(
                sdomain=self.fe_domain,
                bcond_list=self.bc_list,
                rtrace_list=[
                             self.f_w_diagram_center,
                             self.f_w_diagram_supprt,
                             RTraceDomainListField(name='Displacement' ,
                                            var='u', idx=0, warp=True),
#                             RTraceDomainListField(name = 'Stress' ,
#                                            var = 'sig_app', idx = 0, warp = True,
#                                            record_on = 'update'),
#                             RTraceDomainListField(name = 'Strain' ,
#                                        var = 'eps_app', idx = 0, warp = True,
#                                        record_on = 'update'),
#                             RTraceDomainListField(name = 'Damage' ,
#                                        var = 'omega_mtx', idx = 0, warp = True,
#                                        record_on = 'update'),
                             RTraceDomainListField(name='max_omega_i', warp=True,
                                        var='max_omega_i', idx=0,
                                        record_on='update'),
#                             RTraceDomainListField(name = 'IStress' ,
#                                            position = 'int_pnts',
#                                            var = 'sig_app', idx = 0,
#                                            record_on = 'update'),
#                             RTraceDomainListField(name = 'IStrain' ,
#                                            position = 'int_pnts',
#                                            var = 'eps_app', idx = 0,
#                                            record_on = 'update')
                             ])

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      KMAX=50,
                      tolerance=self.tolerance,
                      RESETMAX=0,
                      tline=TLine(min=0.0, step=self.tstep, max=self.tmax)
                      )

        return tloop

    #--------------------------------------------------------------
    # prepare pstudy
    #--------------------------------------------------------------

    def peval(self):
        '''
        Evaluate the model and return the array of results specified
        in the method get_sim_outputs.
        '''
        U = self.tloop.eval()

        self.f_w_diagram_center.refresh()
        F_max = max(self.f_w_diagram_center.trace.ydata)

        u_center_top_z = U[ self.center_top_dofs ][0, 0, 2]
        return array([ u_center_top_z, F_max ],
                        dtype='float_')
    def get_sim_outputs(self):
        '''
        Specifies the results and their order returned by the model
        evaluation.
        '''
        return [ SimOut(name='u_center_top_z', unit='m'),
                 SimOut(name='F_max', unit='kN') ]
Beispiel #39
0
    def peval( self ):
        '''Evaluation procedure.
        '''
        #mv = MATS1DDamageView( model = mats_eval )
        #mv.configure_traits()

        self.mats_m.reset_state()
        # Discretization
        #
        length = self.length
        domain = FEGrid( coord_min = ( 0., length / 5. ),
                          coord_max = ( length, 0. ),
                          shape = ( self.shape, 1 ),
                          fets_eval = self.fets )

        right_dofs = domain[-1, -1, -1, :].dofs[0, :, 0]
        print 'concrete_dofs', id( domain ), domain[:, 0, :, 0].dofs
        # Response tracers
        self.stress_strain = RTraceGraph( name = 'Fi,right over u_right (iteration)' ,
                                   var_y = 'F_int', idx_y = right_dofs[0],
                                   var_x = 'U_k', idx_x = right_dofs[0] )
        self.eps_m_field = RTraceDomainListField( name = 'eps_m' , position = 'int_pnts',
                                           var = 'eps1', idx = 0,
                                           warp = True )

        self.eps_f_field = RTraceDomainListField( name = 'eps_f' , position = 'int_pnts',
                                           var = 'eps2', idx = 0,
                                           warp = True )

        # Response tracers
        self.sig_m_field = RTraceDomainListField( name = 'sig_m' , position = 'int_pnts',
                                              var = 'mats_phase1_sig_app', idx = 0 )
        self.sig_f_field = RTraceDomainListField( name = 'sig_f' , position = 'int_pnts',
                                              var = 'mats_phase2_sig_app', idx = 0 )
        self.omega_m_field = RTraceDomainListField( name = 'omega_m' , position = 'int_pnts',
                                           var = 'mats_phase1_omega', idx = 0,
                                           warp = True )
        # 

        damage_onset_displ = self.mats_m.epsilon_0 * self.length
        go_behind = 1.5
        finish_displ = go_behind * damage_onset_displ
        n_steps = 20
        step_size = ( finish_displ - damage_onset_displ ) / n_steps
        tmax = 1 + n_steps

        def ls( t ):
            if t <= 1:
                return t
            else:
                return 1.0 + ( t - 1.0 ) / n_steps * ( go_behind - 1 )

        ts = TSCrackLoc( 
                 dof_resultants = True,
                 on_update = self.plot,
                 sdomain = domain,
                 bcond_list = [# define the left clamping 
                                BCSlice( var = 'u', value = 0., dims = [0], slice = domain[ 0, 0, 0, :] ),
                                # loading at the right edge
                                 BCSlice( var = 'f', value = 1, dims = [0], slice = domain[-1, -1, -1, 0],
                                         time_function = ls ),
#                                 BCSlice(var='u', value = finish_displ, dims = [0], slice = domain[-1,-1,-1, 0],
#                                         time_function = ls ),
                                # fix horizontal displacement in the top layer
                                 BCSlice( var = 'u', value = 0., dims = [0], slice = domain[:, -1, :, -1] ),
                                # fix the vertical displacement all over the domain
                                 BCSlice( var = 'u', value = 0., dims = [1], slice = domain[ :, :, :, :] )
                                ],
                 rtrace_list = [ self.stress_strain,
                                  self.eps_m_field,
                                  self.eps_f_field,
                                  self.sig_m_field,
                                  self.sig_f_field,
                                  self.omega_m_field ]
                )

        # Add the time-loop control
        tloop = TLoop( tstepper = ts, KMAX = 200, debug = True, tolerance = 1e-5,
                       tline = TLine( min = 0.0, step = 1.0, max = 1.0 ) )

        print ts.rte_dict.keys()
        U = tloop.eval()

        self.plot()

        return array( [ U[right_dofs[-1]] ], dtype = 'float_' )
Beispiel #40
0
    def _get_tloop(self):

        #--------------------------------------------------------------
        # ts
        #--------------------------------------------------------------

        specmn = self.specmn_fe_grid
        mid_specmn = self.mid_specmn_fe_grid

        if self.supprt_flag:
            supprt = self.supprt_fe_grid
            supprt_dofs_z = np.unique(supprt[self.shape_supprt_x / 2, self.shape_y / 2, 0, 0, 0, 0].dofs[:, :, 2].flatten())
        else:
            supprt_dofs_z = np.unique(specmn[-1, :, 0, -1, :, 0].dofs[:, :, 2].flatten())
        print 'supprt_dofs_z (unique)', supprt_dofs_z

        if self.elstmr_flag:
            elstmr = self.elstmr_fe_grid
            load_dofs_z = np.unique(elstmr[:, :, -1, :, :, -1].dofs[:, :, 2].flatten())
        else:
            # center_top_line_dofs
            #
            load_dofs_z = np.unique(mid_specmn[0, :, -1, 0, :, -1].dofs[:, :, 2].flatten())
        print 'load_dofs_z used for integration of force: ', load_dofs_z

        # center top z-dof
        #
        center_top_dof_z = mid_specmn[0, 0, 0, 0, 0, 0].dofs[0, 0, 2]
        print 'center_top_dof used for displacement tracing: ', center_top_dof_z

        # force-displacement-diagram (LOAD)
        # (surface load on the elstmr or line load at specimen center)
        #
        self.f_w_diagram_center = RTraceGraph(name='displacement (center) - reaction 2',
                                       var_x='U_k'  , idx_x=center_top_dof_z,
                                       var_y='F_int', idx_y_arr=load_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='-4000. * y')

        # force-displacement-diagram (SUPPORT)
        # (dofs at support line of the specmn used to integrate the force)
        #
        self.f_w_diagram_supprt = RTraceGraph(name='displacement (center) - reaction 2',
                                       var_x='U_k'  , idx_x=center_top_dof_z,
                                       var_y='F_int', idx_y_arr=supprt_dofs_z,
                                       record_on='update',
                                       transform_x='-x * 1000', # %g * x' % ( fabs( w_max ),),
                                       # due to symmetry the total force sums up from four parts of the beam (2 symmetry axis):
                                       #
                                       transform_y='4000. * y')

        ts = TS(
                sdomain=self.fe_domain,
                bcond_list=self.bc_list,
                rtrace_list=[
                             self.f_w_diagram_center,
                             self.f_w_diagram_supprt,
                             RTraceDomainListField(name='Displacement' ,
                                            var='u', idx=0, warp=True),
#                             RTraceDomainListField(name = 'Stress' ,
#                                            var = 'sig_app', idx = 0, warp = True,
#                                            record_on = 'update'),
#                             RTraceDomainListField(name = 'Strain' ,
#                                        var = 'eps_app', idx = 0, warp = True,
#                                        record_on = 'update'),
#                             RTraceDomainListField(name = 'Damage' ,
#                                        var = 'omega_mtx', idx = 0, warp = True,
#                                        record_on = 'update'),
                             RTraceDomainListField(name='max_omega_i', warp=True,
                                        var='max_omega_i', idx=0,
                                        record_on='update'),
#                             RTraceDomainListField(name = 'IStress' ,
#                                            position = 'int_pnts',
#                                            var = 'sig_app', idx = 0,
#                                            record_on = 'update'),
#                             RTraceDomainListField(name = 'IStrain' ,
#                                            position = 'int_pnts',
#                                            var = 'eps_app', idx = 0,
#                                            record_on = 'update')
                             ])

        # Add the time-loop control
        tloop = TLoop(tstepper=ts,
                      KMAX=50,
                      tolerance=self.tolerance,
                      RESETMAX=0,
                      tline=TLine(min=0.0, step=self.tstep, max=self.tmax)
                      )

        return tloop