def testListEntry(self): # Initiate MAP++ for this design mymap = pyMAP() #mymap.ierr = 0 mymap.map_set_sea_depth(self.params['water_depth']) mymap.map_set_gravity(g) mymap.map_set_sea_density(self.params['water_density']) mymap.read_list_input(truth) mymap.init() mymap.displace_vessel(0, 0, 0, 0, 10, 0) mymap.update_states(0.0, 0) mymap.end()
def testListEntry(self): # Initiate MAP++ for this design mymap = pyMAP( ) #mymap.ierr = 0 mymap.map_set_sea_depth(self.params['water_depth']) mymap.map_set_gravity(g) mymap.map_set_sea_density(self.params['water_density']) mymap.read_list_input(truth) mymap.init( ) mymap.displace_vessel(0, 0, 0, 0, 10, 0) mymap.update_states(0.0, 0) mymap.end()
def runMAP(self, params, unknowns): """Writes MAP input file, executes, and then queries MAP to find maximum loading and displacement from vessel displacement around all 360 degrees INPUTS: ---------- params : dictionary of input parameters unknowns : dictionary of output parameters OUTPUTS : none (multiple unknown dictionary values set) """ # Unpack variables rhoWater = params['water_density'] waterDepth = params['water_depth'] fairleadDepth = params['fairlead'] Dmooring = params['mooring_diameter'] offset = params['max_offset'] heel = params['operational_heel'] gamma = params['gamma_f'] n_connect = int(params['number_of_mooring_connections']) n_lines = int(params['mooring_lines_per_connection']) ntotal = n_connect * n_lines # Write the mooring system input file for this design self.write_input_file(params) # Initiate MAP++ for this design mymap = pyMAP() #mymap.ierr = 0 mymap.map_set_sea_depth(waterDepth) mymap.map_set_gravity(gravity) mymap.map_set_sea_density(rhoWater) mymap.read_list_input(self.finput) mymap.init() # Get the stiffness matrix at neutral position mymap.displace_vessel(0, 0, 0, 0, 0, 0) mymap.update_states(0.0, 0) K = mymap.linear(1e-4) # Input finite difference epsilon unknowns['mooring_stiffness'] = np.array(K) mymap.displace_vessel(0, 0, 0, 0, 0, 0) mymap.update_states(0.0, 0) # Get the vertical load on the structure and plotting data F_neutral = np.zeros((NLINES_MAX, 3)) plotMat = np.zeros((NLINES_MAX, NPTS_PLOT, 3)) nptsMOI = 100 xyzpts = np.zeros((ntotal, nptsMOI, 3)) # For MOI calculation for k in range(ntotal): (F_neutral[k, 0], F_neutral[k, 1], F_neutral[k, 2]) = mymap.get_fairlead_force_3d(k) plotMat[k, :, 0] = mymap.plot_x(k, NPTS_PLOT) plotMat[k, :, 1] = mymap.plot_y(k, NPTS_PLOT) plotMat[k, :, 2] = mymap.plot_z(k, NPTS_PLOT) xyzpts[k, :, 0] = mymap.plot_x(k, nptsMOI) xyzpts[k, :, 1] = mymap.plot_y(k, nptsMOI) xyzpts[k, :, 2] = mymap.plot_z(k, nptsMOI) if self.tlpFlag: # Seems to be a bug in the plot arrays from MAP++ for plotting output with taut lines plotMat[k, :, 2] = np.linspace(-fairleadDepth, -waterDepth, NPTS_PLOT) xyzpts[k, :, 2] = np.linspace(-fairleadDepth, -waterDepth, nptsMOI) unknowns['mooring_neutral_load'] = F_neutral unknowns['mooring_plot_matrix'] = plotMat # Fine line segment length, ds = sqrt(dx^2 + dy^2 + dz^2) xyzpts_dx = np.gradient(xyzpts[:, :, 0], axis=1) xyzpts_dy = np.gradient(xyzpts[:, :, 1], axis=1) xyzpts_dz = np.gradient(xyzpts[:, :, 2], axis=1) xyzpts_ds = np.sqrt(xyzpts_dx**2 + xyzpts_dy**2 + xyzpts_dz**2) # Initialize inertia tensor integrands in https://en.wikipedia.org/wiki/Moment_of_inertia#Inertia_tensor # Taking MOI relative to body centerline at fairlead depth r0 = np.array([0.0, 0.0, -fairleadDepth]) R = np.zeros((ntotal, nptsMOI, 6)) for ii in range(nptsMOI): for k in range(ntotal): r = xyzpts[k, ii, :] - r0 R[k, ii, :] = unassembleI( np.dot(r, r) * np.eye(3) - np.outer(r, r)) Imat = self.wet_mass_per_length * np.trapz( R, x=xyzpts_ds[:, :, np.newaxis], axis=1) unknowns['mooring_moments_of_inertia'] = np.abs(Imat.sum(axis=0)) # Get the restoring moment at maximum angle of heel # Since we don't know the substucture CG, have to just get the forces of the lines now and do the cross product later # We also want to allow for arbitraty wind direction and yaw of rotor relative to mooring lines, so we will compare # pitch and roll forces as extremes # TODO: This still isgn't quite the same as clocking the mooring lines in different directions, # which is what we want to do, but that requires multiple input files and solutions Fh = np.zeros((NLINES_MAX, 3)) mymap.displace_vessel(0, 0, 0, 0, heel, 0) mymap.update_states(0.0, 0) for k in range(ntotal): Fh[k][0], Fh[k][1], Fh[k][2] = mymap.get_fairlead_force_3d(k) unknowns['operational_heel_restoring_force'] = Fh # Get angles by which to find the weakest line dangle = 2.0 angles = np.deg2rad(np.arange(0.0, 360.0, dangle)) nangles = len(angles) # Get restoring force at weakest line at maximum allowable offset # Will global minimum always be along mooring angle? max_tension = 0.0 max_angle = None min_angle = None F_max_tension = None F_min = np.inf T = np.zeros((NLINES_MAX, )) F = np.zeros((NLINES_MAX, )) # Loop around all angles to find weakest point for a in angles: # Unit vector and offset in x-y components idir = np.array([np.cos(a), np.sin(a)]) surge = offset * idir[0] sway = offset * idir[1] # Get restoring force of offset at this angle mymap.displace_vessel(surge, sway, 0, 0, 0, 0) # 0s for z, angles mymap.update_states(0.0, 0) for k in range(ntotal): # Force in x-y-z coordinates fx, fy, fz = mymap.get_fairlead_force_3d(k) T[k] = np.sqrt(fx * fx + fy * fy + fz * fz) # Total restoring force F[k] = np.dot([fx, fy], idir) # Check if this is the weakest direction (highest tension) tempMax = T.max() if tempMax > max_tension: max_tension = tempMax F_max_tension = F.sum() max_angle = a if F.sum() < F_min: F_min = F.sum() min_angle = a # Store the weakest restoring force when the vessel is offset the maximum amount unknowns['max_offset_restoring_force'] = F_min # Check for good convergence if (plotMat[0, -1, -1] + fairleadDepth) > 1.0: unknowns['axial_unity'] = 1e30 else: unknowns['axial_unity'] = gamma * max_tension / self.min_break_load mymap.end()
'(-) (m) (kg/m) (N) (-) (Pa-s) (-) (-) (-)', 'steel 0.0766 113.35 7.536e8 1.0 1.0E8 0.6 -1.0 0.05', '---------------------- NODE PROPERTIES -----------------------------------------------------', 'Node Type X Y Z M V FX FY FZ', '(-) (-) (m) (m) (m) (kg) (m^3) (kN) (kN) (kN)', '1 Fix 418.8 725.383 -200 0 0 # # #', '2 Vessel 20.434 35.393 -14.0 0 0 # # #', '---------------------- LINE PROPERTIES -----------------------------------------------------', 'Line LineType UnstrLen NodeAnch NodeFair Flags', '(-) (-) (m) (-) (-) (-)', '1 steel 835.35 1 2 plot ', '---------------------- SOLVER OPTIONS-----------------------------------------', 'Option', '(-)', 'repeat 240 120', 'ref_position 0 0 0' ] mooring_1 = pyMAP() mooring_1.map_set_sea_depth(320) mooring_1.map_set_gravity(9.81) mooring_1.map_set_sea_density(1025.0) mooring_1.read_list_input(nrel5mw_oc4) #mooring_1.read_file("../test/NRELOffshrBsLine5MW_OC4.map") # 200 m depth #mooring_1.summary_file('name_me.txt') mooring_1.init() epsilon = 1e-5 K = mooring_1.linear(epsilon) print( "\nHere is the linearized stiffness matrix with zero vessel displacement:") print(np.array(K))
def runMAP(self, params, unknowns): """Writes MAP input file, executes, and then queries MAP to find maximum loading and displacement from vessel displacement around all 360 degrees INPUTS: ---------- params : dictionary of input parameters unknowns : dictionary of output parameters OUTPUTS : none (multiple unknown dictionary values set) """ # Unpack variables rhoWater = params['water_density'] waterDepth = params['water_depth'] fairleadDepth = params['fairlead'] Dmooring = params['mooring_diameter'] offset = params['max_offset'] heel = params['operational_heel'] gamma = params['gamma_f'] n_connect = int(params['number_of_mooring_connections']) n_lines = int(params['mooring_lines_per_connection']) ntotal = n_connect * n_lines # Write the mooring system input file for this design self.write_input_file(params) # Initiate MAP++ for this design mymap = pyMAP( ) #mymap.ierr = 0 mymap.map_set_sea_depth(waterDepth) mymap.map_set_gravity(gravity) mymap.map_set_sea_density(rhoWater) mymap.read_list_input(self.finput) mymap.init( ) # Get the stiffness matrix at neutral position mymap.displace_vessel(0, 0, 0, 0, 0, 0) mymap.update_states(0.0, 0) K = mymap.linear(1e-4) # Input finite difference epsilon unknowns['mooring_stiffness'] = np.array( K ) mymap.displace_vessel(0, 0, 0, 0, 0, 0) mymap.update_states(0.0, 0) # Get the vertical load on the structure and plotting data F_neutral = np.zeros((NLINES_MAX, 3)) plotMat = np.zeros((NLINES_MAX, NPTS_PLOT, 3)) nptsMOI = 100 xyzpts = np.zeros((ntotal, nptsMOI, 3)) # For MOI calculation for k in range(ntotal): (F_neutral[k,0], F_neutral[k,1], F_neutral[k,2]) = mymap.get_fairlead_force_3d(k) plotMat[k,:,0] = mymap.plot_x(k, NPTS_PLOT) plotMat[k,:,1] = mymap.plot_y(k, NPTS_PLOT) plotMat[k,:,2] = mymap.plot_z(k, NPTS_PLOT) xyzpts[k,:,0] = mymap.plot_x(k, nptsMOI) xyzpts[k,:,1] = mymap.plot_y(k, nptsMOI) xyzpts[k,:,2] = mymap.plot_z(k, nptsMOI) if self.tlpFlag: # Seems to be a bug in the plot arrays from MAP++ for plotting output with taut lines plotMat[k,:,2] = np.linspace(-fairleadDepth, -waterDepth, NPTS_PLOT) xyzpts[k,:,2] = np.linspace(-fairleadDepth, -waterDepth, nptsMOI) unknowns['mooring_neutral_load'] = F_neutral unknowns['mooring_plot_matrix'] = plotMat # Fine line segment length, ds = sqrt(dx^2 + dy^2 + dz^2) xyzpts_dx = np.gradient(xyzpts[:,:,0], axis=1) xyzpts_dy = np.gradient(xyzpts[:,:,1], axis=1) xyzpts_dz = np.gradient(xyzpts[:,:,2], axis=1) xyzpts_ds = np.sqrt(xyzpts_dx**2 + xyzpts_dy**2 + xyzpts_dz**2) # Initialize inertia tensor integrands in https://en.wikipedia.org/wiki/Moment_of_inertia#Inertia_tensor # Taking MOI relative to body centerline at fairlead depth r0 = np.array([0.0, 0.0, -fairleadDepth]) R = np.zeros((ntotal, nptsMOI, 6)) for ii in range(nptsMOI): for k in range(ntotal): r = xyzpts[k,ii,:] - r0 R[k,ii,:] = unassembleI(np.dot(r,r)*np.eye(3) - np.outer(r,r)) Imat = self.wet_mass_per_length * np.trapz(R, x=xyzpts_ds[:,:,np.newaxis], axis=1) unknowns['mooring_moments_of_inertia'] = np.abs( Imat.sum(axis=0) ) # Get the restoring moment at maximum angle of heel # Since we don't know the substucture CG, have to just get the forces of the lines now and do the cross product later # We also want to allow for arbitraty wind direction and yaw of rotor relative to mooring lines, so we will compare # pitch and roll forces as extremes # TODO: This still isgn't quite the same as clocking the mooring lines in different directions, # which is what we want to do, but that requires multiple input files and solutions Fh = np.zeros((NLINES_MAX,3)) mymap.displace_vessel(0, 0, 0, 0, heel, 0) mymap.update_states(0.0, 0) for k in range(ntotal): Fh[k][0], Fh[k][1], Fh[k][2] = mymap.get_fairlead_force_3d(k) unknowns['operational_heel_restoring_force'] = Fh # Get angles by which to find the weakest line dangle = 2.0 angles = np.deg2rad( np.arange(0.0, 360.0, dangle) ) nangles = len(angles) # Get restoring force at weakest line at maximum allowable offset # Will global minimum always be along mooring angle? max_tension = 0.0 max_angle = None min_angle = None F_max_tension = None F_min = np.inf T = np.zeros((NLINES_MAX,)) F = np.zeros((NLINES_MAX,)) # Loop around all angles to find weakest point for a in angles: # Unit vector and offset in x-y components idir = np.array([np.cos(a), np.sin(a)]) surge = offset * idir[0] sway = offset * idir[1] # Get restoring force of offset at this angle mymap.displace_vessel(surge, sway, 0, 0, 0, 0) # 0s for z, angles mymap.update_states(0.0, 0) for k in range(ntotal): # Force in x-y-z coordinates fx,fy,fz = mymap.get_fairlead_force_3d(k) T[k] = np.sqrt(fx*fx + fy*fy + fz*fz) # Total restoring force F[k] = np.dot([fx, fy], idir) # Check if this is the weakest direction (highest tension) tempMax = T.max() if tempMax > max_tension: max_tension = tempMax F_max_tension = F.sum() max_angle = a if F.sum() < F_min: F_min = F.sum() min_angle = a # Store the weakest restoring force when the vessel is offset the maximum amount unknowns['max_offset_restoring_force'] = F_min # Check for good convergence if (plotMat[0,-1,-1] + fairleadDepth) > 1.0: unknowns['axial_unity'] = 1e30 else: unknowns['axial_unity'] = gamma * max_tension / self.min_break_load mymap.end()
def runMAP(self, params, unknowns): """Writes MAP input file, executes, and then queries MAP to find maximum loading and displacement from vessel displacement around all 360 degrees INPUTS: ---------- params : dictionary of input parameters unknowns : dictionary of output parameters OUTPUTS : none (multiple unknown dictionary values set) """ # Unpack variables rhoWater = params['water_density'] waterDepth = params['water_depth'] fairleadDepth = params['fairlead'] Dmooring = params['mooring_diameter'] nlines = int(params['number_of_mooring_lines']) offset = params['max_offset'] heel = params['max_heel'] gamma = params['gamma'] # Write the mooring system input file for this design self.write_input_file(params) # Initiate MAP++ for this design mymap = pyMAP() #mymap.ierr = 0 mymap.map_set_sea_depth(waterDepth) mymap.map_set_gravity(gravity) mymap.map_set_sea_density(rhoWater) mymap.read_list_input(self.finput) mymap.init() # Get the stiffness matrix at neutral position mymap.displace_vessel(0, 0, 0, 0, 0, 0) mymap.update_states(0.0, 0) K = mymap.linear(1e-4) # Input finite difference epsilon unknowns['mooring_stiffness'] = np.array(K) mymap.displace_vessel(0, 0, 0, 0, 0, 0) mymap.update_states(0.0, 0) # Get the vertical load on the spar and plotting data Fz = 0.0 npltpts = 20 plotMat = np.zeros((nlines, npltpts, 3)) for k in xrange(nlines): _, _, fz = mymap.get_fairlead_force_3d(k) Fz += fz plotMat[k, :, 0] = mymap.plot_x(k, npltpts) plotMat[k, :, 1] = mymap.plot_y(k, npltpts) plotMat[k, :, 2] = mymap.plot_z(k, npltpts) unknowns['vertical_load'] = Fz unknowns['mooring_effective_mass'] = Fz / gravity unknowns['plot_matrix'][:nlines, :, :] = plotMat # Get the restoring moment at maximum angle of heel # Since we don't know the substucture CG, have to just get the forces of the lines now and do the cross product later # We also want to allow for arbitraty wind direction and yaw of rotor relative to mooring lines, so we will compare # pitch and roll forces as extremes # TODO: This still isgn't quite the same as clocking the mooring lines in different directions, # which is what we want to do, but that requires multiple input files and solutions Fh1 = np.zeros((10, 3)) mymap.displace_vessel(0, 0, 0, 0, heel, 0) mymap.update_states(0.0, 0) for k in xrange(nlines): Fh1[k][0], Fh1[k][1], Fh1[k][2] = mymap.get_fairlead_force_3d(k) Fh2 = np.zeros((10, 3)) mymap.displace_vessel(0, 0, 0, heel, 0, 0) mymap.update_states(0.0, 0) for k in xrange(nlines): Fh2[k][0], Fh2[k][1], Fh2[k][2] = mymap.get_fairlead_force_3d(k) Fh = Fh2 if Fh1.sum(axis=(0, 1)) > Fh2.sum(axis=(0, 1)) else Fh1 unknowns['max_heel_restoring_force'] = Fh # Get angles by which to find the weakest line dangle = 2.0 angles = np.deg2rad(np.arange(0.0, 360.0, dangle)) nangles = len(angles) # Get restoring force at weakest line at maximum allowable offset # Will global minimum always be along mooring angle? max_tension = 0.0 max_angle = None min_angle = None F_max_tension = None F_min = np.inf T = np.zeros((nlines, )) F = np.zeros((nlines, )) # Loop around all angles to find weakest point for a in angles: # Unit vector and offset in x-y components idir = np.array([np.cos(a), np.sin(a)]) surge = offset * idir[0] sway = offset * idir[1] # Get restoring force of offset at this angle mymap.displace_vessel(surge, sway, 0, 0, 0, 0) # 0s for z, angles mymap.update_states(0.0, 0) for k in xrange(nlines): # Force in x-y-z coordinates fx, fy, fz = mymap.get_fairlead_force_3d(k) T[k] = np.sqrt(fx * fx + fy * fy + fz * fz) # Total restoring force F[k] = np.dot([fx, fy], idir) # Check if this is the weakest direction (highest tension) tempMax = T.max() if tempMax > max_tension: max_tension = tempMax F_max_tension = F.sum() max_angle = a if F.sum() < F_min: F_min = F.sum() min_angle = a # Store the weakest restoring force when the vessel is offset the maximum amount unknowns['max_offset_restoring_force'] = F_min unknowns['axial_unity'] = gamma * max_tension / self.min_break_load mymap.end()