def ops_material(): # 混凝土 # 抗压强度 抗压应变 初始弹模 # 压缩方程形状参数 # 抗压临界应变 # 抗拉强度 抗拉应变 # 拉伸方程形状参数 # 抗拉临界应变 ops.uniaxialMaterial('ConcreteCM', 1, -31.7, -0.00234, 3.25e4, 7, 0.03, 6.34, 0.001, 1.2, 10000, 1) # GFRP 拉筋 ops.uniaxialMaterial('Steel02', 2, 1255.5, 64.9e3, 1e-20) # SFCB 纵筋 ops.uniaxialMaterial('Steel02', 3, 348.7, 170.931e3, 0.2210) # 箍筋和中部纵筋 ops.uniaxialMaterial('Steel02', 4, 257.5, 131.378e3, 0.320) # 约束区FSAM ops.nDMaterial('FSAM', 5, 2360e-3, 4, 3, 1, 0.02179008664529880590197689450643, 0.04712388980384689857693965074919, 0.1, 0.01) # 中部区域FSAM ops.nDMaterial('FSAM', 6, 2360e-3, 4, 4, 1, 0.00827704944465790858560291110048, 0.00654498469497873591346384038183, 0.1, 0.01)
def test_elastic_isotropic(): opy.wipe() opy.model('basic', '-ndm', 2, '-ndf', 3) v_is_int = 1 v_is_float = 1. # with pytest.raises(opy.error): # TODO: can't find error class # opy.nDMaterial('ElasticIsotropic', 1, 1., v_is_int, 0.0) opy.nDMaterial('ElasticIsotropic', 1, 1., v_is_float, 0.0)
def ops_material(): ''' define material ''' # concrete # 抗压强度 抗压强度/10 残余强度 最大应变 残余应变 拉伸应变 剪切保留因子 ops.nDMaterial('PlaneStressUserMaterial', 1, 40, 7, 31.7e6, 3.17e6, -6.16e6, -0.002, -0.005, 0.001, 0.1) # 平面外剪切模量 ops.nDMaterial('PlateFromPlaneStress', 2, 1, 1.23E15) # 屈服强度 初始弹模 硬化率 # 端部GFRP 20 # 强度 1255.5 MPa 屈服应变 1.98% 弹性模量 63.5GPa ops.uniaxialMaterial('Steel02', 3, 1255.5e6, 63.5e9, 0.0, 15, 0.925, 0.15) # 端部纵筋 S16G2 # 屈服强度 348.7MPa 屈服应变 0.204% # 极限强度 718.4MPa 极限应变 1.823% # 弹性模量 170.931GPa ops.uniaxialMaterial('Steel02', 4, 348.7e6, 170.931e9, 0.2210, 15, 0.925, 0.15) # 中部纵筋 10mm 和 箍筋 8mm S6G2 # 屈服强度 257.5MPa 屈服应变 0.196% # 极限强度 837.2MPa 极限应变 1.658% # 弹性模量 131.378GPa ops.uniaxialMaterial('Steel02', 5, 257.5e6, 131.378e9, 0.320, 15, 0.925, 0.15) # 钢筋层 # 箍筋 ops.nDMaterial('PlateRebar', 6, 5, 0) # 纵筋 ops.nDMaterial('PlateRebar', 7, 5, 90)
def set_uniaxial_metrial(): ''' @Brief set material ''' ops.uniaxialMaterial('Steel02', 1, *(argu.longitudinal_steel)) logger.info("material tag 1 by [steel 02] and used on longitudinal steel") logger.info(argu.longitudinal_steel) ops.uniaxialMaterial('Steel02', 2, *(argu.transverse_steel)) logger.info("material tag 2 by [steel 02] and used on transverse steel") logger.info(argu.transverse_steel) # set nDMaterial ops.nDMaterial('PlaneStressUserMaterial', 3, *(argu.c30_con[0:-1])) logger.info( "material tag 30 by [PlaneStressUserMaterial] and used on C30 concrete" ) logger.info((argu.c30_con[0:-1])) ops.nDMaterial('PlateFromPlaneStress', 30, 3, argu.c30_con[-1]) logger.info( "material tag 30 by [PlateFromPlaneStress] and used on C30 concrete OutofPlaneModulus %d", argu.c30_con[-1]) # logger.info( # "material tag 40 by [PlaneStressUserMaterial] and used on C40 concrete") # ops.nDMaterial('PlaneStressUserMaterial', 4, *(argu.c40_con[0:-1])) # logger.info( # "material tag 40 by [PlateFromPlaneStress] and used on C40 concrete") # ops.nDMaterial('PlateFromPlaneStress', 40, 4, argu.c40_con[-1]) logger.info( "material tag 5 by [PlateRebar] and used on angle 90 d = 10 longitudinal steel" ) ops.nDMaterial('PlateRebar', 5, 1, 90) logger.info( "material tag 6 by [PlateRebar] and used angle 90 d = 6 transverse steel" ) ops.nDMaterial('PlateRebar', 6, 2, 90) logger.info( "material tag 7 by [PlateRebar] and used angle 0 d = 6 transverse steel" ) ops.nDMaterial('PlateRebar', 7, 2, 0)
def ops_material(): # 中部混凝土 ops.nDMaterial('PlaneStressUserMaterial', 1, 40, 7, 31.7, 3.17, -6.34, -0.00234, -0.03, 0.001, 0.05) ops.nDMaterial('PlateFromPlaneStress', 2, 1, 1.23e9) # 端部拉锁 ops.uniaxialMaterial('Steel02', 3, 156.9375, 7937500, 1e-15) # 端部纵筋 ops.uniaxialMaterial('Steel02', 4, 348.7, 170.931e6, 0.2210) # 中部纵筋和箍筋 ops.uniaxialMaterial("Steel02", 5, 257.5, 131.378e6, 0.320) # 中部箍筋层 ops.nDMaterial("PlateRebar", 6, 5, 0) # 中部纵筋层 ops.nDMaterial("PlateRebar", 7, 5, 90) # 边缘区混凝土 ops.uniaxialMaterial('Concrete01', 6, -31.7, -0.00234, 0.0, -0.005) # 中部壳 ops.section('LayeredShell', 1, 12, 2, 20, 6, 0.65345127, 7, 0.6544985, 2, 26.2274, 2, 26.2274, 2, 26.2274, 2, 26.2274, 2, 26.2274, 2, 26.2274, 7, 0.6544985, 6, 0.65345127, 2, 20) # 边缘约束区 ops.section('Fiber', 2, '-GJ', 0) # 混凝土 ops.fiber(100, 0, 40000, 6) # 端部SFCB纵筋 ops.fiber(0, 100, 314, 4) ops.fiber(0, -100, 314, 4) ops.fiber(100, 100, 314, 4) ops.fiber(100, -100, 314, 4) ops.fiber(200, 100, 314, 4) ops.fiber(200, -100, 314, 4) # 端部GFRP拉锁 ops.fiber(200, 70, 314, 3) ops.fiber(200, -70, 314, 3)
ops.node(12, 2., 1.) ops.node(13, 2., 2.) ops.node(14, 2., 3.) ops.node(15, 2., 4.) ops.node(16, 3., 0.) ops.node(17, 3., 1.) ops.node(18, 3., 2.) ops.node(19, 3., 3.) ops.node(20, 3., 4.) ops.node(21, 4., 0.) ops.node(22, 4., 1.) ops.node(23, 4., 2.) ops.node(24, 4., 3.) ops.node(25, 4., 4.) ops.nDMaterial('ElasticIsotropic', 1, 1000, 0.3) ops.element('quad', 1, 1, 6, 7, 2, 1, 'PlaneStress', 1) ops.element('quad', 2, 2, 7, 8, 3, 1, 'PlaneStress', 1) ops.element('quad', 3, 3, 8, 9, 4, 1, 'PlaneStress', 1) ops.element('quad', 4, 4, 9, 10, 5, 1, 'PlaneStress', 1) ops.element('quad', 5, 6, 11, 12, 7, 1, 'PlaneStress', 1) ops.element('quad', 6, 7, 12, 13, 8, 1, 'PlaneStress', 1) ops.element('quad', 7, 8, 13, 14, 9, 1, 'PlaneStress', 1) ops.element('quad', 8, 9, 14, 15, 10, 1, 'PlaneStress', 1) ops.element('quad', 9, 11, 16, 17, 12, 1, 'PlaneStress', 1) ops.element('quad', 10, 12, 17, 18, 13, 1, 'PlaneStress', 1) ops.element('quad', 11, 13, 18, 19, 14, 1, 'PlaneStress', 1) ops.element('quad', 12, 14, 19, 20, 15, 1, 'PlaneStress', 1) ops.element('quad', 13, 16, 21, 22, 17, 1, 'PlaneStress', 1) ops.element('quad', 14, 17, 22, 23, 18, 1, 'PlaneStress', 1)
def analisis_opensees(path, permutaciones): #helper, #win ops.wipe() # bucle para generar los x análisis for i in range(len(permutaciones)): perfil = str(permutaciones[i][0]) nf = permutaciones[i][2] amort = permutaciones[i][3] den = permutaciones[i][4] vel = permutaciones[i][5] capas = len(permutaciones[i][6]) nstep = permutaciones[i][30] dt = float(permutaciones[i][31]) # creación de elementos sElemX = permutaciones[i][1] # elementos en X sElemZ = permutaciones[i][46] # espesor en Z # ============================================================================= # ######## geometría de la columna ###### # ============================================================================= # límite entre capas limite_capa = [] anterior = 0 for j in range(capas): espesor = permutaciones[i][8][j] limite_capa.append(espesor + anterior) anterior = limite_capa[j] print('Límite de capa: ' + str(limite_capa[j])) # creación de elementos y nodos en x nElemX = 1 # elementos en x nNodeX = 2 * nElemX + 1 # nodos en x # creación de elementos y nodos para z nElemZ = 1 # creación de elementos y nodos en Y y totales nElemY = [] # elementos en y sElemY = [] # dimension en y nElemT = 0 for j in range(capas): espesor = permutaciones[i][8][j] nElemY.append(2 * espesor) nElemT += nElemY[j] print('Elementos en capa ' + str(j + 1) + ': ' + str(nElemY[j])) sElemY.append(permutaciones[i][8][j] / nElemY[j]) print('Tamaño de los elementos en capa ' + str(j + 1) + ': ' + str(sElemY[j]) + '\n') # number of nodes in vertical direction in each layer nNodeY = [] # dimension en y nNodeT = 0 s = 0 for j in range(capas - 1): nNodeY.append(4 * nElemY[j]) nNodeT += nNodeY[j] s += 1 print('Nodos en capa ' + str(j + 1) + ': ' + str(nNodeY[j])) nNodeY.append(4 * (nElemY[-1] + 1)) nNodeT += nNodeY[-1] print('Nodos en capa ' + str(s + 1) + ': ' + str(nNodeY[s])) print('Nodos totales: ' + str(nNodeT)) #win.ui.progressBar.setValue(15) # ============================================================================= # ######### Crear nodos del suelo ########## # ============================================================================= # creación de nodos de presión de poros ops.model('basic', '-ndm', 3, '-ndf', 4) with open(path + '/Post-proceso/' + perfil + '/ppNodesInfo.dat', 'w') as f: count = 0.0 yCoord = 0.0 nodos = [] dryNode = [] altura_nf = 10 - nf for k in range(capas): for j in range(0, int(nNodeY[k]), 4): ops.node(j + count + 1, 0.0, yCoord, 0.0) ops.node(j + count + 2, 0.0, yCoord, sElemZ) ops.node(j + count + 3, sElemX, yCoord, sElemZ) ops.node(j + count + 4, sElemX, yCoord, 0.0) f.write( str(int(j + count + 1)) + '\t' + str(0.0) + '\t' + str(yCoord) + '\t' + str(0.0) + '\n') f.write( str(int(j + count + 2)) + '\t' + str(0.0) + '\t' + str(yCoord) + '\t' + str(sElemZ) + '\n') f.write( str(int(j + count + 3)) + '\t' + str(sElemX) + '\t' + str(yCoord) + '\t' + str(sElemZ) + '\n') f.write( str(int(j + count + 4)) + '\t' + str(sElemX) + '\t' + str(yCoord) + '\t' + str(0.0) + '\n') nodos.append(str(j + count + 1)) nodos.append(str(j + count + 2)) nodos.append(str(j + count + 3)) nodos.append(str(j + count + 4)) #designate node sobre la superficie de agua if yCoord >= altura_nf: dryNode.append(j + count + 1) dryNode.append(j + count + 2) dryNode.append(j + count + 3) dryNode.append(j + count + 4) yCoord = (yCoord + sElemY[k]) count = (count + nNodeY[k]) print("Finished creating all soil nodes...") # ============================================================================= # ####### Condiciones de contorno en la base de la columna ######### # ============================================================================= ops.fix(1, *[0, 1, 1, 0]) ops.fix(2, *[0, 1, 1, 0]) ops.fix(3, *[0, 1, 1, 0]) ops.fix(4, *[0, 1, 1, 0]) ops.equalDOF(1, 2, 1) ops.equalDOF(1, 3, 1) ops.equalDOF(1, 4, 1) print('Fin de creación de nodos de la base de la columna\n\n') # ============================================================================= # ####### Condiciones de contorno en los nudos restantes ######### # ============================================================================= count = 0 for k in range(5, int(nNodeT + 1), 4): ops.equalDOF(k, k + 1, *[1, 2, 3]) ops.equalDOF(k, k + 2, *[1, 2, 3]) ops.equalDOF(k, k + 3, *[1, 2, 3]) print('Fin de creación equalDOF para nodos de presión de poros\n\n') for j in range(len(dryNode)): ops.fix(dryNode[j], *[0, 0, 0, 1]) print("Finished creating all soil boundary conditions...") # ============================================================================= # ####### crear elemento y material de suelo ######### # ============================================================================= cargas = [] for j in range(capas): pendiente = permutaciones[i][9][j] slope = math.atan(pendiente / 100) tipo_suelo = permutaciones[i][6][j] rho = permutaciones[i][10][j] Gr = permutaciones[i][12][j] Br = permutaciones[i][13][j] fric = permutaciones[i][15][j] refpress = permutaciones[i][18][j] gmax = permutaciones[i][19][j] presscoef = permutaciones[i][20][j] surf = permutaciones[i][21][j] ev = permutaciones[i][22][j] cc1 = permutaciones[i][23][j] cc3 = permutaciones[i][24][j] cd1 = permutaciones[i][25][j] cd3 = permutaciones[i][26][j] ptang = permutaciones[i][27][j] coh = permutaciones[i][28][j] if tipo_suelo == 'No cohesivo': if float(surf) > 0: ops.nDMaterial('PressureDependMultiYield02', j + 1, 3.0, rho, Gr, Br, fric, gmax, refpress, presscoef, ptang, cc1, cc3, cd1, cd3, float(surf), 5.0, 3.0, *[1.0, 0.0], ev, *[0.9, 0.02, 0.7, 101.0]) else: ops.nDMaterial('PressureDependMultiYield02', j + 1, 3.0, rho, Gr, Br, fric, gmax, refpress, presscoef, ptang, cc1, cc3, cd1, cd3, float(surf), *permutaciones[i][29][j], 5.0, 3.0, *[1.0, 0.0], ev, *[0.9, 0.02, 0.7, 101.0]) cargas.append( [0.0, -9.81 * math.cos(slope), -9.81 * math.sin(slope)]) print('Fin de la creación de material de suelo\n\n') #----------------------------------------------------------------------------------------- # 5. CREATE SOIL ELEMENTS #----------------------------------------------------------------------------------------- count = 0 alpha = 1.5e-6 with open(path + '/Post-proceso/' + perfil + '/ppElemInfo.dat', 'w') as f: # crear elemento de suelo for k in range(capas): for j in range(int(nElemY[k])): nI = 4 * (j + count + 1) - 3 nJ = nI + 1 nK = nI + 2 nL = nI + 3 nM = nI + 4 nN = nI + 5 nO = nI + 6 nP = nI + 7 f.write( str(j + count + 1) + '\t' + str(nI) + '\t' + str(nJ) + '\t' + str(nK) + '\t' + str(nL) + '\t' + str(nM) + '\t' + str(nN) + '\t' + str(nO) + '\t' + str(nP) + '\n') Bc = permutaciones[i][14][k] ev = permutaciones[i][22][k] ops.element('SSPbrickUP', (j + count + 1), *[nI, nJ, nK, nL, nM, nN, nO, nP], (k + 1), float(Bc), 1.0, 1.0, 1.0, 1.0, float(ev), alpha, cargas[k][0], cargas[k][1], cargas[k][2]) count = (count + int(nElemY[k])) print('Fin de la creación del elemento del suelo\n\n') #win.ui.progressBar.setValue(25) # ============================================================================= # ######### Amortiguamiento de Lysmer ########## # ============================================================================= ops.model('basic', '-ndm', 3, '-ndf', 3) # definir nodos y coordenadas del amortiguamiento dashF = nNodeT + 1 dashX = nNodeT + 2 dashZ = nNodeT + 3 ops.node(dashF, 0.0, 0.0, 0.0) ops.node(dashX, 0.0, 0.0, 0.0) ops.node(dashZ, 0.0, 0.0, 0.0) # definir restricciones para los nodos de amortiguamiento ops.fix(dashF, 1, 1, 1) ops.fix(dashX, 0, 1, 1) ops.fix(dashZ, 1, 1, 0) # definir equalDOF para el amortiguamiento en la base del suelo ops.equalDOF(1, dashX, 1) ops.equalDOF(1, dashZ, 3) print( 'Fin de la creación de condiciones de contorno de los nodos de amortiguamiento\n\n' ) # definir el material de amortiguamiento colArea = sElemX * sElemZ dashpotCoeff = vel * den * colArea ops.uniaxialMaterial('Viscous', capas + 1, dashpotCoeff, 1.0) # definir el elemento ops.element('zeroLength', nElemT + 1, *[dashF, dashX], '-mat', capas + 1, '-dir', *[1]) ops.element('zeroLength', nElemT + 2, *[dashF, dashZ], '-mat', capas + 1, '-dir', *[3]) print('Fin de la creación del elemento de amortiguamiento\n\n') #----------------------------------------------------------------------------------------- # 9. DEFINE ANALYSIS PARAMETERS #----------------------------------------------------------------------------------------- # amortiguamiento de Rayleigh # frecuencia menor omega1 = 2 * math.pi * 0.2 # frecuencia mayor omega2 = 2 * math.pi * 20 a0 = 2.0 * (amort / 100) * omega1 * omega2 / (omega1 + omega2) a1 = 2.0 * (amort / 100) / (omega1 + omega2) print('Coeficientes de amortiguamiento' + '\n' + 'a0: ' + format(a0, '.6f') + '\n' + 'a1: ' + format(a1, '.6f') + '\n\n') #win.ui.progressBar.setValue(35) # ============================================================================= # ######## Determinación de análisis estático ######### # ============================================================================= #---DETERMINE STABLE ANALYSIS TIME STEP USING CFL CONDITION # se determina a partir de un análisis transitorio de largo tiempo duration = nstep * dt # tamaño mínimo del elemento y velocidad máxima minSize = sElemY[0] vsMax = permutaciones[i][11][0] for j in range(1, capas): if sElemY[j] < minSize: minSize = sElemY[j] if permutaciones[i][11][j] > vsMax: vsMax = permutaciones[i][11][j] # trial analysis time step kTrial = minSize / (vsMax**0.5) # tiempo de análisis y pasos de tiempo if dt <= kTrial: nStep = nstep dT = dt else: nStep = int(math.floor(duration / kTrial) + 1) dT = duration / nStep print('Número de pasos en el análisis: ' + str(nStep) + '\n') print('Incremento de tiempo: ' + str(dT) + '\n\n') #---------------------------------------------------------------------------------------- # 7. GRAVITY ANALYSIS #----------------------------------------------------------------------------------------- ops.model('basic', '-ndm', 3, '-ndf', 4) ops.updateMaterialStage('-material', int(k + 1), '-stage', 0) # algoritmo de análisis estático ops.constraints(permutaciones[i][32][0], float(permutaciones[i][32][1]), float(permutaciones[i][32][2])) ops.test(permutaciones[i][34][0], float(permutaciones[i][34][1]), int(permutaciones[i][34][2]), int(permutaciones[i][34][3])) ops.algorithm(permutaciones[i][38][0]) ops.numberer(permutaciones[i][33][0]) ops.system(permutaciones[i][36][0]) ops.integrator(permutaciones[i][35][0], float(permutaciones[i][35][1]), float(permutaciones[i][35][2])) ops.analysis(permutaciones[i][37][0]) print('Inicio de análisis estático elástico\n\n') ops.start() ops.analyze(20, 5.0e2) print('Fin de análisis estático elástico\n\n') #win.ui.progressBar.setValue(40) # update materials to consider plastic behavior # ============================================================================= ops.updateMaterialStage('-material', int(k + 1), '-stage', 1) # ============================================================================= # plastic gravity loading print('Inicio de análisis estático plástico\n\n') ok = ops.analyze(40, 5.0e-2) if ok != 0: error = 'Error de convergencia en análisis estático de modelo' + str( perfil) + '\n\n' print(error) break print('Fin de análisis estático plástico\n\n') #----------------------------------------------------------------------------------------- # 11. UPDATE ELEMENT PERMEABILITY VALUES FOR POST-GRAVITY ANALYSIS #----------------------------------------------------------------------------------------- ini = 1 aum = 0 sum = 0 for j in range(capas): #Layer 3 ops.setParameter( '-val', permutaciones[i][16][j], ['-eleRange', int(ini + aum), int(nElemY[j] + sum)], 'xPerm') ops.setParameter( '-val', permutaciones[i][17][j], ['-eleRange', int(ini + aum), int(nElemY[j] + sum)], 'yPerm') ops.setParameter( '-val', permutaciones[i][16][j], ['-eleRange', int(ini + aum), int(nElemY[j] + sum)], 'zPerm') ini = nElemY[j] + sum sum += nElemY[j] aum = 1 print("Finished updating permeabilities for dynamic analysis...") # ============================================================================= # ########### Grabadores dinámicos ########## # ============================================================================= ops.setTime(0.0) ops.wipeAnalysis() ops.remove('recorders') # tiempo de la grabadora recDT = 10 * dt path_acel = path + '/Post-proceso/' + perfil + '/dinamico/aceleraciones/' ops.recorder('Node', '-file', path_acel + 'accelerationx.out', '-time', '-dT', recDT, '-node', *nodos, '-dof', 1, 'accel') print('Fin de creación de grabadores\n\n') #win.ui.progressBar.setValue(50) # ============================================================================= # ######### Determinación de análisis dinámico ########## # ============================================================================= # objeto de serie temporal para el historial de fuerza path_vel = path + '/Pre-proceso/' + perfil + '/TREASISL2.txt' ops.timeSeries('Path', 1, '-dt', dt, '-filePath', path_vel, '-factor', dashpotCoeff) ops.pattern('Plain', 10, 1) ops.load(1, *[1.0, 0.0, 0.0, 0.0]) #CAMBIO REALIZADO OJO print('Fin de creación de carga dinámica\n\n') # algoritmo de análisis dinámico ops.constraints(permutaciones[i][39][0], float(permutaciones[i][39][1]), float(permutaciones[i][39][2])) ops.test(permutaciones[i][41][0], float(permutaciones[i][41][1]), int(permutaciones[i][41][2]), int(permutaciones[i][41][3])) ops.algorithm(permutaciones[i][45][0]) ops.numberer(permutaciones[i][40][0]) ops.system(permutaciones[i][43][0]) ops.integrator(permutaciones[i][42][0], float(permutaciones[i][42][1]), float(permutaciones[i][42][2])) ops.analysis(permutaciones[i][44][0]) # ============================================================================= # ops.rayleigh(a0, a1, 0.0, 0.0) # ============================================================================= print('Inicio de análisis dinámico\n\n') #win.ui.progressBar.setValue(85) ok = ops.analyze(nStep, dT) if ok != 0: error = 'Error de convergencia en análisis dinámico de modelo' + str( permutaciones[i][0]) + '\n\n' print(error) curTime = ops.getTime() mTime = curTime print('cursTime:' + str(curTime)) curStep = (curTime / dT) print('cursStep:' + str(curStep)) rStep = (nStep - curStep) * 2.0 remStep = int(nStep - curStep) * 2.0 print('remSTep:' + str(curStep)) dT = (dT / 2) print('dT:' + str(dT)) ops.analyze(remStep, dT) if ok != 0: error = 'Error de convergencia en análisis dinámico de modelo' + str( permutaciones[i][0]) + '\n\n' print(error) curTime = ops.getTime() print('cursTime:' + str(curTime)) curStep = (curTime - mTime) / dT print('cursStep:' + str(curStep)) remStep = int(rStep - curStep) * 2 print('remSTep:' + str(curStep)) dT = (dT / 2) print('dT:' + str(dT)) ops.analyze(remStep, dT) print('Fin de análisis dinámico\n\n') ops.wipe()
import openseespy.opensees as op import openseespytools.model as opm import numpy as np op.wipe() op.model('basic', '-ndm', 3, '-ndf', 6) mat1 = 1 op.nDMaterial('ElasticIsotropic', mat1, 1., 0.1) mat2 = 2 op.uniaxialMaterial('Elastic', mat2, 1.) nodeCoordsx = np.array([0, 1, 2, 3, 4]) * 1. nodeCoordsy = np.array([0, 1]) * 1. nodeCoordsz = np.array([0, 1]) * 1. # Element connectivity element1D = np.array([[1, 1, 11], [2, 2, 12], [3, 3, 13], [4, 4, 14], [5, 5, 15], [6, 6, 16], [7, 7, 17], [8, 8, 18], [9, 9, 19], [10, 10, 20]]) element4D = np.array([[21, 12, 13, 18, 17], [22, 13, 14, 19, 18]]) element8D = np.array([[30, 1, 2, 7, 6, 11, 12, 17, 16], [31, 4, 5, 10, 9, 14, 15, 20, 19]]) elements = [element1D, element4D, element8D] # Define Nodes tag = 0 for z in nodeCoordsz:
def Model_2D(): op.wipe() op.model('basic', '-ndm', 2, '-ndf', 2) mat1 = 1 op.nDMaterial('ElasticIsotropic', mat1, 1., 0.1) mat2 = 2 op.uniaxialMaterial('Elastic', mat2, 1.) linTransform = 1 # op.geomTransf('Linear', linTransform) nodeCoordsx = np.array([0, 1, 2, 3]) * 1. nodeCoordsy = np.array([0, 1]) * 1. # Element 1D connectivity element1D = np.array([[1, 1, 5], [2, 2, 6], [3, 3, 7], [4, 4, 8], [5, 5, 6], [6, 6, 7], [7, 7, 8]]) element3D = np.array([[10, 2, 3, 6], [11, 3, 6, 7]]) element4D = np.array([[20, 1, 2, 6, 5], [21, 3, 4, 8, 7]]) elements = [element1D, element3D, element4D] # Define Nodes tag = 0 for y in nodeCoordsy: for x in nodeCoordsx: tag += 1 op.node(tag, x, y) # Define Elements 2node for element in element1D: eleTag = int(element[0]) nodej = int(element[1]) nodek = int(element[2]) # op. element('Truss', eleTag, *eleNodes, A, matTag[, '-rho', rho][, '-cMass', cFlag][, '-doRayleigh', rFlag]) op.element('Truss', eleTag, nodej, nodek, 1., 2) # Define Elements 3node for element in element3D: eleTag = int(element[0]) nodej = int(element[1]) nodek = int(element[2]) nodel = int(element[3]) # op. element('Tri31', eleTag, *eleNodes, thick, type, matTag[, pressure, rho, b1, b2]) op.element('Tri31', eleTag, nodej, nodek, nodel, 1., 'PlaneStress', mat1) # Define Elements 4node for element in element4D: eleTag = int(element[0]) nodej = int(element[1]) nodek = int(element[2]) nodel = int(element[3]) nodem = int(element[4]) # op.element('quad', eleTag, *eleNodes, thick, type, matTag[, pressure=0.0, rho=0.0, b1=0.0, b2=0.0]) op.element('quad', eleTag, nodej, nodek, nodel, nodem, 1., 'PlaneStrain', mat1)
def test_PinchedCylinder(): P = 1 R = 300. L = 600. E = 3e6 thickness = R / 100. uExact = -164.24 * P / (E * thickness) formatString = '{:>20s}{:>15.5e}' print("\n Displacement Under Applied Load:\n") formatString = '{:>20s}{:>10s}{:>15s}{:>15s}{:>15s}' print( formatString.format("Element Type", " mesh ", "OpenSees", "Exact", "%Error")) for shellType in ['ShellMITC4', 'ShellDKGQ', 'ShellNLDKGQ']: for numEle in [4, 16, 32]: ops.wipe() # ---------------------------- # Start of model generation # ---------------------------- ops.model('basic', '-ndm', 3, '-ndf', 6) radius = R length = L / 2. E = 3.0e6 v = 0.3 PI = 3.14159 ops.nDMaterial('ElasticIsotropic', 1, E, v) ops.nDMaterial('PlateFiber', 2, 1) ops.section('PlateFiber', 1, 2, thickness) #section ElasticMembranePlateSection 1 E v thickness 0. nR = numEle nY = numEle tipNode = (nR + 1) * (nY + 1) #create nodes nodeTag = 1 for i in range(nR + 1): theta = i * PI / (2.0 * nR) xLoc = 300 * cos(theta) zLoc = 300 * sin(theta) for j in range(nY + 1): yLoc = j * length / (1.0 * nY) ops.node(nodeTag, xLoc, yLoc, zLoc) nodeTag += 1 #create elements eleTag = 1 for i in range(nR): iNode = i * (nY + 1) + 1 jNode = iNode + 1 lNode = iNode + (nY + 1) kNode = lNode + 1 for j in range(nY): ops.element(shellType, eleTag, iNode, jNode, kNode, lNode, 1) eleTag += 1 iNode += 1 jNode += 1 kNode += 1 lNode += 1 # define the boundary conditions ops.fixX(radius, 0, 0, 1, 1, 1, 0, '-tol', 1.0e-2) ops.fixZ(radius, 1, 0, 0, 0, 1, 1, '-tol', 1.0e-2) ops.fixY(0., 1, 0, 1, 0, 0, 0, '-tol', 1.0e-2) ops.fixY(length, 0, 1, 0, 1, 0, 1, '-tol', 1.0e-2) #define loads ops.timeSeries('Linear', 1) ops.pattern('Plain', 1, 1) ops.load(tipNode, 0., 0., -1. / 4.0, 0., 0., 0.) ops.integrator('LoadControl', 1.0) ops.test('EnergyIncr', 1.0e-10, 20, 0) ops.algorithm('Newton') ops.numberer('RCM') ops.constraints('Plain') ops.system('Umfpack') ops.analysis('Static') ops.analyze(1) res = ops.nodeDisp(tipNode, 3) err = abs(100 * (uExact - res) / uExact) formatString = '{:>20s}{:>5d}{:>3s}{:>2d}{:>15.5e}{:>15.5e}{:>15.2f}' print( formatString.format(shellType, numEle, " x ", numEle, res, uExact, err)) tol = 5.0 if abs(100 * (uExact - res) / uExact) > tol: testOK = 1 else: testOK = 0 assert testOK == 0
time = time.strftime("%Y-%m-%d-%H-%M-%S", time.localtime()) log_init(True, "output\\", time, '') ops.reset() ops.wipe() ops.start() logger.info("opensees begin") ndm: int = 3 ndf: int = ndm * (ndm - 1) / 2 ops.model('basic', '-ndm', 3, '-ndf', 6) # set concrete ops.nDMaterial('PlaneStressUserMaterial', 1, 40, 7, 30.8e6, 3.08e6, -6.16e6, -0.002, -0.005, 0.001, 0.05) ops.nDMaterial('PlateFromPlaneStress', 4, 1, 1.283e10) # set steel ops.uniaxialMaterial('Steel02', 7, 379e6, 202.7e9, 0.01, 18.5, 0.925, 0.15) ops.uniaxialMaterial('Steel02', 8, 392e6, 200.6e9, 0.01, 18.5, 0.925, 0.15) ops.nDMaterial('PlateRebar', 9, 7, 90) ops.nDMaterial('PlateRebar', 10, 8, 90) ops.nDMaterial('PlateRebar', 11, 8, 0) # set section ops.section('LayeredShell', 1, 10, 4, 0.0125, 11, 0.0003023, 11, 0.0004367, 4, 0.0246305, 4, 0.0246305, 4, 0.0246305, 4, 0.0246305, 11, 0.0004367, 11, 0.0003023, 4, 0.0125) ops.section('LayeredShell', 2, 8, 4, 0.0125, 11, 0.0003023, 10, 0.0002356, 4, 0.0494621, 4, 0.0494621, 10, 0.0002356, 11, 0.0003023, 4, 0.0125)
def test_DynAnal_BeamWithQuadElements(): ops.wipe() # clear opensees model # create data directory # file mkdir Data #----------------------------- # Define the model # ---------------------------- # Create ModelBuilder with 2 dimensions and 2 DOF/node ops.model('BasicBuilder', '-ndm', 2, '-ndf', 2) # create the material ops.nDMaterial('ElasticIsotropic', 1, 1000.0, 0.25, 3.0) # set type of quadrilateral element (uncomment one of the three options) Quad = 'quad' #set Quad bbarQuad #set Quad enhancedQuad # set up the arguments for the three considered elements if Quad == "enhancedQuad": eleArgs = "PlaneStress2D 1" if Quad == "quad": eleArgs = "1 PlaneStress2D 1" if Quad == "bbarQuad": eleArgs = "1" # set up the number of elements in x (nx) and y (ny) direction nx = 16 # NOTE: nx MUST BE EVEN FOR THIS EXAMPLE ny = 4 # define numbering of node at the left support (bn), and the two nodes at load application (l1, l2) bn = nx + 1 l1 = int(nx / 2 + 1) l2 = int(l1 + ny * (nx + 1)) # create the nodes and elements using the block2D command ops.block2D(nx, ny, 1, 1, Quad, 1., 'PlaneStress2D', 1, 1, 0., 0., 2, 40., 0., 3, 40., 10., 4, 0., 10.) # define boundary conditions ops.fix(1, 1, 1) ops.fix(bn, 0, 1) # define the recorder #--------------------- # recorder Node -file Data/Node.out -time -node l1 -dof 2 disp # define load pattern #--------------------- ops.timeSeries('Linear', 1) ops.pattern('Plain', 1, 1) ops.load(l1, 0.0, -1.0) ops.load(l2, 0.0, -1.0) # -------------------------------------------------------------------- # Start of static analysis (creation of the analysis & analysis itself) # -------------------------------------------------------------------- # Load control with variable load steps # init Jd min max ops.integrator('LoadControl', 1.0, 1, 1.0, 10.0) # Convergence test # tolerance maxIter displayCode ops.test('EnergyIncr', 1.0e-12, 10, 0) # Solution algorithm ops.algorithm('Newton') # DOF numberer ops.numberer('RCM') # Cosntraint handler ops.constraints('Plain') # System of equations solver ops.system('ProfileSPD') # Type of analysis analysis ops.analysis('Static') # Perform the analysis ops.analyze(10) # -------------------------- # End of static analysis # -------------------------- # ------------------------------------- # create display for transient analysis #-------------------------------------- # windowTitle xLoc yLoc xPixels yPixels # recorder display "Simply Supported Beam" 10 10 800 200 -wipe # prp 20 5.0 1.0 # projection reference point (prp) defines the center of projection (viewer eye) # vup 0 1 0 # view-up vector (vup) # vpn 0 0 1 # view-plane normal (vpn) # viewWindow -30 30 -10 10 # coordiantes of the window relative to prp # display 10 0 5 # the 1st arg. is the tag for display mode # the 2nd arg. is magnification factor for nodes, the 3rd arg. is magnif. factor of deformed shape # --------------------------------------- # Create and Perform the dynamic analysis # --------------------------------------- #define damping evals = ops.eigen(1) ops.rayleigh(0., 0., 0., 2 * 0.02 / sqrt(evals[0])) # Remove the static analysis & reset the time to 0.0 ops.wipeAnalysis() ops.setTime(0.0) # Now remove the loads and let the beam vibrate ops.remove('loadPattern', 1) uy1 = ops.nodeDisp(9, 2) print("uy(9) = ", uy1) # Create the transient analysis ops.test('EnergyIncr', 1.0e-12, 10, 0) ops.algorithm('Newton') ops.numberer('RCM') ops.constraints('Plain') ops.integrator('Newmark', 0.5, 0.25) ops.system('BandGeneral') ops.analysis('Transient') # Perform the transient analysis (50 sec) ops.analyze(1500, 0.5) uy2 = ops.nodeDisp(9, 2) print("uy(9) = ", uy2) assert abs(uy1 + 0.39426414168933876514) < 1e-12 and abs( uy2 + 0.00736847273806807632) < 1e-12 print("========================================")
def model_3D(): op.wipe() op.model('basic', '-ndm', 3, '-ndf', 6) mat1 = 1 op.nDMaterial('ElasticIsotropic', mat1, 1., 0.1) mat2 = 2 op.uniaxialMaterial('Elastic', mat2, 1.) nodeCoordsx = np.array([0, 1, 2, 3, 4]) * 1. nodeCoordsy = np.array([0, 1]) * 1. nodeCoordsz = np.array([0, 1]) * 1. # Element connectivity element1D = np.array([[1, 1, 11], [2, 2, 12], [3, 3, 13], [4, 4, 14], [5, 5, 15], [6, 6, 16], [7, 7, 17], [8, 8, 18], [9, 9, 19], [10, 10, 20]]) element4D = np.array([[21, 12, 13, 18, 17], [22, 13, 14, 19, 18]]) element8D = np.array([[30, 1, 2, 7, 6, 11, 12, 17, 16], [31, 4, 5, 10, 9, 14, 15, 20, 19]]) elements = [element1D, element4D, element8D] # Define Nodes tag = 0 for z in nodeCoordsz: for y in nodeCoordsy: for x in nodeCoordsx: tag += 1 op.node(tag, x, y, z) # Define Elements 2node for element in element1D: eleTag = int(element[0]) nodei = int(element[1]) nodej = int(element[2]) # op.element('elasticBeamColumn', eleTag, *eleNodes, Area, E_mod, Iz, transfTag[, '-mass', massPerLength][, '-cMass'][, '-release', releaseCode]) # op. element('Truss', eleTag, *eleNodes, A, matTag[, '-rho', rho][, '-cMass', cFlag][, '-doRayleigh', rFlag]) op.element('Truss', eleTag, nodei, nodej, 1., 2) # Define Elements 4node for element in element4D: eleTag = int(element[0]) nodei = int(element[1]) nodej = int(element[2]) nodek = int(element[3]) nodel = int(element[4]) eleNodes = [nodei, nodej, nodek, nodel] # op.element('FourNodeTetrahedron', eleTag, *eleNodes, matTag[, b1, b2, b3]) op.element('FourNodeTetrahedron', eleTag, *eleNodes, mat1) # op.element('quad', eleTag, nodei, nodej, nodek, nodel, 1., 'PlaneStrain', mat1) # Define Elements 3node for element in element8D: eleTag = int(element[0]) nodei = int(element[1]) nodej = int(element[2]) nodek = int(element[3]) nodel = int(element[4]) nodeii = int(element[5]) nodejj = int(element[6]) nodekk = int(element[7]) nodell = int(element[8]) eleNodes = [nodei, nodej, nodek, nodel, nodeii, nodejj, nodekk, nodell] op.element('stdBrick', eleTag, *eleNodes, mat1) # opp.plot_model() fig, ax = opm.plot_active_model() return fig, ax
import time import openseespy.opensees as ops from liblog import logger, log_init time = time.strftime("%Y-%m-%d-%H-%M-%S", time.localtime()) log_init(True, "output\\", time, '') ops.reset() ops.wipe() ops.start() logger.info("----- start -----") ops.model('basic', '-ndm', 3, '-ndf', 6) ops.nDMaterial('PlaneStressUserMaterial', 1, 40, 7, 20.7e6, 2.07e6, -4.14e6, -0.002, -0.006, 0.001, 0.08) ops.nDMaterial('PlateFromPlaneStress', 4, 1, 1.25e10) ops.uniaxialMaterial('Steel02', 7, 379e6, 202.7e9, 0.01, 18.5, 0.925, 0.15) ops.uniaxialMaterial('Steel02', 8, 392e6, 200.6e9, 0.01, 18.5, 0.925, 0.15) ops.nDMaterial('PlateRebar', 9, 7, 90) ops.nDMaterial('PlateRebar', 10, 8, 90) ops.nDMaterial('PlateRebar', 11, 8, 0) ops.section('LayeredShell', 1, 10, 4, 0.0125, 11, 0.0002403, 11, 0.0003676, 4, 0.024696, 4, 0.024696, 4, 0.024696, 4, 0.024696, 11, 0.0003676, 11, 0.0002403, 4, 0.0125)
# ---------------------------- # Start of model generation # ---------------------------- ops.wipe() ops.model("BasicBuilder", "-ndm", 3, "-ndf", 3) # set default units ops.defaultUnits("-force", "kip", "-length", "in", "-time", "sec", "-temp", "F") # Define the material # ------------------- # matTag E nu rho ops.nDMaterial("ElasticIsotropic", 1, 10000.0, 0.25, 1.27) # Define geometry # --------------- Brick = "stdBrick" # Brick = "bbarBrick" # Brick = "SSPbrick" nz = 10 nx = 4 ny = 4 nn = int((nz + 1) * (nx + 1) * (ny + 1)) # mesh generation # numX numY numZ startNode startEle eleType eleArgs? coords?
nodeDic = {(0,1): 1,(0,4): 1, (0,2): 2, (0,3): 2, (1,4): 1, (1,2): 2} eleDic = {(2,1): 1} Node, Ele = readMesh(meshName, nodeDic, eleDic) nNode = len(Node) nEle = len(Ele) # paraview out # https://openseespydoc.readthedocs.io/en/latest/src/pvdRecorder.html outPV('out/Beam_1') # definir y construir el material mTg = 1 nu = 0.15 # Poisson's ratio of soil E = 2460000*N/cm**2 ops.nDMaterial('ElasticIsotropic', mTg, E, nu) # espesor de los elementos B = 0.25*m # construccion de nodos for i in range(nNode): ops.node(i+1, *Node[i][1:]) # construccion de elementos for i in range(nEle): if (Ele[i][0] == 1): ops.element('quad', i+1, *Ele[i][2:], B, 'PlaneStress', Ele[i][0]) # condiciones de frontera boundFix(nNode, Node)
ops.logFile('output.log') # set model ops.start() ops.model('basic', '-ndm', 3, '-ndf', 6) ops.node(1, 0, 0, 0) ops.node(2, 0, 1, 0) ops.node(3, 1, 0, 0) ops.node(4, 1, 1, 0) ops.fix(1, 1, 1, 1, 0, 0, 0) ops.fix(3, 1, 1, 1, 0, 0, 0) ops.nDMaterial('PlaneStressUserMaterial', 3, 40, 7, 20.7e6, 2.07e6, -4.14e6, -0.002, -0.005, 0.001, 0.08) ops.nDMaterial('PlateFromPlaneStress', 30, 3, 1.25e10) ops.section('LayeredShell', 1, 3, 30, 0.015, 30, 0.015, 30, 0.015) # ops.uniaxialMaterial('Elastic', 1, 202.7e9) # ops.element('Truss', 1, 1, 2, 0.1, 1) ops.element('ShellMITC4', 1, 1, 3, 4, 2, 1) ops.recorder('Node', '-file', 'disp.out', '-node', 2, '-time', '-dof', 1, 'disp') ops.recorder('Node', '-file', 'reac.out', '-node', 2, '-time', '-dof', 1, 'reaction') # set timeSeries ops.timeSeries('Linear', 1) ops.pattern('Plain', 1, 1) ops.load(2, 1, 0, 0, 0, 0, 0)