void NonlocalMaterialExtensionInterface :: endIPNonlocalAverage(GaussPoint *gp) { NonlocalMaterialStatusExtensionInterface *statusExt = static_cast< NonlocalMaterialStatusExtensionInterface * >( gp->giveMaterialStatus()-> giveInterface(NonlocalMaterialStatusExtensionInterfaceType) ); if ( !statusExt ) { OOFEM_ERROR("local material status encountered"); } if ( ( !this->hasBoundedSupport() ) || ( !permanentNonlocTableFlag ) ) { statusExt->clear(); } }
void NonlocalMaterialWTP :: giveNonlocalDepArryElementPlugin(GaussPoint *gp, std :: set< int > &s) { int remoteElemNum; NonlocalMaterialStatusExtensionInterface *interface = static_cast< NonlocalMaterialStatusExtensionInterface * >( gp->giveMaterialStatus()-> giveInterface(NonlocalMaterialStatusExtensionInterfaceType) ); if ( interface ) { std :: list< localIntegrationRecord > *lir = interface->giveIntegrationDomainList(); for ( auto &intdom: *lir ) { remoteElemNum = ( intdom.nearGp )->giveElement()->giveGlobalNumber(); s.insert(remoteElemNum); } } }
void NonlocalMaterialExtensionInterface :: buildNonlocalPointTable(GaussPoint *gp) { double weight, elemVolume, integrationVolume = 0.; NonlocalMaterialStatusExtensionInterface *statusExt = static_cast< NonlocalMaterialStatusExtensionInterface * >( gp->giveMaterialStatus()-> giveInterface(NonlocalMaterialStatusExtensionInterfaceType) ); std :: list< localIntegrationRecord > *iList; Element *ielem; IntegrationRule *iRule; if ( !statusExt ) { OOFEM_ERROR("local material status encountered"); } if ( !statusExt->giveIntegrationDomainList()->empty() ) { return; // already done } iList = statusExt->giveIntegrationDomainList(); FloatArray gpCoords, jGpCoords, shiftedGpCoords; SpatialLocalizer :: elementContainerType elemSet; if ( gp->giveElement()->computeGlobalCoordinates( gpCoords, gp->giveNaturalCoordinates() ) == 0 ) { OOFEM_ERROR("computeGlobalCoordinates of target failed"); } // If nonlocal variation is set to the distance-based approach, a new nonlocal radius // is calculated as a function of the distance from the Gauss point to the nonlocal boundaries if ( nlvar == NLVT_DistanceBasedLinear || nlvar == NLVT_DistanceBasedExponential ) { // cl=cl0; cl = giveDistanceBasedInteractionRadius(gpCoords); suprad = evaluateSupportRadius(); } // If the mesh represents a periodic cell, nonlocal interaction is considered not only for the real neighbors // but also for their periodic images, shifted by +px or -px in the x-direction. In the implementation, // instead of shifting the potential neighbors, we shift the receiver point gp. In the non-periodic case (typical), // px=0 and the following loop is executed only once. int ix, nx = 0; // typical case if ( px > 0. ) nx = 1; // periodicity taken into account for (ix=-nx; ix<=nx; ix++) { // loop over periodic images shifted in x-direction shiftedGpCoords = gpCoords; shiftedGpCoords.at(1) += ix*px; // ask domain spatial localizer for list of elements with IP within this zone #ifdef NMEI_USE_ALL_ELEMENTS_IN_SUPPORT this->giveDomain()->giveSpatialLocalizer()->giveAllElementsWithNodesWithinBox(elemSet, shiftedGpCoords, suprad); // insert element containing given gp elemSet.insert( gp->giveElement()->giveNumber() ); #else this->giveDomain()->giveSpatialLocalizer()->giveAllElementsWithIpWithinBox_EvenIfEmpty(elemSet, shiftedGpCoords, suprad); #endif // initialize iList for ( auto elindx: elemSet ) { ielem = this->giveDomain()->giveElement(elindx); if ( regionMap.at( ielem->giveRegionNumber() ) == 0 ) { iRule = ielem->giveDefaultIntegrationRulePtr(); for ( GaussPoint *jGp: *iRule ) { if ( ielem->computeGlobalCoordinates( jGpCoords, jGp->giveNaturalCoordinates() ) ) { weight = this->computeWeightFunction(shiftedGpCoords, jGpCoords); //manipulate weights for a special averaging of strain (OFF by default) this->manipulateWeight(weight, gp, jGp); this->applyBarrierConstraints(shiftedGpCoords, jGpCoords, weight); #ifdef NMEI_USE_ALL_ELEMENTS_IN_SUPPORT if ( 1 ) { #else if ( weight > 0. ) { #endif localIntegrationRecord ir; ir.nearGp = jGp; // store gp elemVolume = weight * jGp->giveElement()->computeVolumeAround(jGp); ir.weight = elemVolume; // store gp weight iList->push_back(ir); // store own copy in list integrationVolume += elemVolume; } } else { OOFEM_ERROR("computeGlobalCoordinates of target failed"); } } } } // loop over elements } statusExt->setIntegrationScale(integrationVolume); // store scaling factor /* * // Old implementation without spatial localizer * * FloatArray jGpCoords; * for (i=1; i<=nelem; i++) { * ielem = this->giveDomain()->giveElement(i); * if (regionMap.at(ielem->giveRegionNumber()) == 0) { * iRule = ielem->giveDefaultIntegrationRulePtr (); * for (GaussPoint *jGp: *iRule ) { * if (ielem->computeGlobalCoordinates (jGpCoords, *(jGp->giveCoordinates()))) { * weight = this->computeWeightFunction (gpCoords, jGpCoords); * if (weight > NonlocalMaterialZeroWeight) { * localIntegrationRecord ir; * ir.nearGp = jGp; // store gp * elemVolume = weight * jGp->giveElement()->computeVolumeAround (jGp); * ir.weight = elemVolume; // store gp weight * iList->append(ir); // store own copy in list * integrationVolume += elemVolume; * } * } else OOFEM_ERROR("computeGlobalCoordinates failed"); * } * } * } // loop over elements * statusExt->setIntegrationScale (integrationVolume); // remember scaling factor */ } void NonlocalMaterialExtensionInterface :: rebuildNonlocalPointTable(GaussPoint *gp, IntArray *contributingElems) { double weight, elemVolume, integrationVolume = 0.; NonlocalMaterialStatusExtensionInterface *statusExt = static_cast< NonlocalMaterialStatusExtensionInterface * >( gp->giveMaterialStatus()-> giveInterface(NonlocalMaterialStatusExtensionInterfaceType) ); std :: list< localIntegrationRecord > *iList; Element *ielem; IntegrationRule *iRule; if ( !statusExt ) { OOFEM_ERROR("local material status encountered"); } iList = statusExt->giveIntegrationDomainList(); iList->clear(); if ( contributingElems == NULL ) { // no element table provided, use standard method this->buildNonlocalPointTable(gp); } else { FloatArray gpCoords, jGpCoords; int _size = contributingElems->giveSize(); if ( gp->giveElement()->computeGlobalCoordinates( gpCoords, gp->giveNaturalCoordinates() ) == 0 ) { OOFEM_ERROR("computeGlobalCoordinates of target failed"); } //If nonlocal variation is set to the distance-based approach calculates new nonlocal radius // based on the distance from the nonlocal boundaries if ( nlvar == NLVT_DistanceBasedLinear || nlvar == NLVT_DistanceBasedExponential ) { cl = cl0; cl = giveDistanceBasedInteractionRadius(gpCoords); suprad = evaluateSupportRadius(); } // initialize iList for ( int _e = 1; _e <= _size; _e++ ) { ielem = this->giveDomain()->giveElement( contributingElems->at(_e) ); if ( regionMap.at( ielem->giveRegionNumber() ) == 0 ) { iRule = ielem->giveDefaultIntegrationRulePtr(); for ( GaussPoint *jGp: *iRule ) { if ( ielem->computeGlobalCoordinates( jGpCoords, jGp->giveNaturalCoordinates() ) ) { weight = this->computeWeightFunction(gpCoords, jGpCoords); //manipulate weights for a special averaging of strain (OFF by default) this->manipulateWeight(weight, gp, jGp); this->applyBarrierConstraints(gpCoords, jGpCoords, weight); #ifdef NMEI_USE_ALL_ELEMENTS_IN_SUPPORT if ( 1 ) { #else if ( weight > 0. ) { #endif localIntegrationRecord ir; ir.nearGp = jGp; // store gp elemVolume = weight * jGp->giveElement()->computeVolumeAround(jGp); ir.weight = elemVolume; // store gp weight iList->push_back(ir); // store own copy in list integrationVolume += elemVolume; } } else { OOFEM_ERROR("computeGlobalCoordinates of target failed"); } } } } // loop over elements statusExt->setIntegrationScale(integrationVolume); // remember scaling factor #ifdef __PARALLEL_MODE #ifdef __VERBOSE_PARALLEL fprintf( stderr, "%d(%d):", gp->giveElement()->giveGlobalNumber(), gp->giveNumber() ); for ( auto &lir: iList ) { fprintf(stderr, "%d,%d(%e)", lir.nearGp->giveElement()->giveGlobalNumber(), lir.nearGp->giveNumber(), lir.weight); } fprintf(stderr, "\n"); #endif #endif } } std :: list< localIntegrationRecord > * NonlocalMaterialExtensionInterface :: giveIPIntegrationList(GaussPoint *gp) { NonlocalMaterialStatusExtensionInterface *statusExt = static_cast< NonlocalMaterialStatusExtensionInterface * >( gp->giveMaterialStatus()-> giveInterface(NonlocalMaterialStatusExtensionInterfaceType) ); if ( !statusExt ) { OOFEM_ERROR("local material status encountered"); } if ( statusExt->giveIntegrationDomainList()->empty() ) { this->buildNonlocalPointTable(gp); } return statusExt->giveIntegrationDomainList(); }