@@ -67,6 +67,37 @@ def assemble_b_multi(self, problem: 'MEEMProblem', m0) -> np.ndarray:
6767 for row , calc_func in cache .m0_dependent_b_indices :
6868 b [row ] = calc_func (problem , m0 , cache .m_k_arr , cache .N_k_arr , I_mk_vals )
6969 return b
70+
71+ def assemble_c_vector (self , problem : 'MEEMProblem' , heaving : List [int ]) -> np .ndarray :
72+ """
73+ Assembles the c_vector based on the heaving state of the domains.
74+ """
75+ cache = self .cache_list [problem ]
76+ int_R1_store , int_R2_store , _ = cache ._get_integration_constants ()
77+
78+ geometry = problem .geometry
79+ domain_keys = list (geometry .domain_list .keys ())
80+ NMK = [geometry .domain_list [idx ].number_harmonics for idx in domain_keys ]
81+ boundary_count = len (NMK ) - 1
82+ size = NMK [0 ] + NMK [- 1 ] + 2 * sum (NMK [1 :len (NMK ) - 1 ])
83+
84+ c_vector = np .zeros ((size - NMK [- 1 ]), dtype = complex )
85+ col = 0
86+
87+ # 1. Inner Region (Index 0)
88+ for n in range (NMK [0 ]):
89+ c_vector [n ] = heaving [0 ] * int_R1_store [(0 , n )] * z_n_d (n )
90+ col += NMK [0 ]
91+
92+ # 2. Outer Regions
93+ for i in range (1 , boundary_count ):
94+ M = NMK [i ]
95+ for m in range (M ):
96+ c_vector [col + m ] = heaving [i ] * int_R1_store [(i , m )] * z_n_d (m )
97+ c_vector [col + M + m ] = heaving [i ] * int_R2_store [(i , m )] * z_n_d (m )
98+ col += 2 * M
99+
100+ return c_vector
70101
71102 def build_problem_cache (self , problem : 'MEEMProblem' ) -> ProblemCache :
72103 """
@@ -319,29 +350,19 @@ def reformat_coeffs(self, x: np.ndarray, NMK, boundary_count) -> list[np.ndarray
319350 return cs
320351
321352 def compute_hydrodynamic_coefficients (self , problem , X , m0 , modes_to_calculate : Optional [np .ndarray ] = None , rho : Optional [float ] = None ):
322- """
323- Computes the hydrodynamic coefficients (Added Mass and Damping) from the solution vector X.
324- """
325353 if rho is None :
326354 rho = default_rho
327355
328356 geometry = problem .geometry
329357 domain_keys = list (geometry .domain_list .keys ())
330358 a = [geometry .domain_list [idx ].a for idx in domain_keys ]
331- d = [
332- domain .di [0 ] if isinstance (domain .di , list ) else domain .di
333- for domain in geometry .domain_list .values ()
334- ]
335- h = geometry .domain_list [0 ].h
359+ h = geometry .h
336360 NMK = [geometry .domain_list [idx ].number_harmonics for idx in domain_keys ]
337361 boundary_count = len (NMK ) - 1
338362
339- size = NMK [0 ] + NMK [- 1 ] + 2 * sum (NMK [1 :len (NMK ) - 1 ])
340-
341363 results_per_mode = []
342-
343364 cache = self .cache_list [problem ]
344- int_R1_store , int_R2_store , int_phi_store = cache ._get_integration_constants ()
365+ _ , _ , int_phi_store = cache ._get_integration_constants ()
345366
346367 if modes_to_calculate is None :
347368 num_bodies = len (geometry .body_arrangement .bodies )
@@ -366,25 +387,8 @@ def compute_hydrodynamic_coefficients(self, problem, X, m0, modes_to_calculate:
366387 if r_idx < len (heaving ):
367388 heaving [r_idx ] = 1
368389
369- c_vector = np .zeros ((size - NMK [- 1 ]), dtype = complex )
370- col = 0
371-
372- # 1. Inner Region (Index 0)
373- for n in range (NMK [0 ]):
374- val = int_R1_store [(0 , n )]
375- c_vector [n ] = heaving [0 ] * val * z_n_d (n )
376- col += NMK [0 ]
377-
378- # 2. Outer Regions
379- for i in range (1 , boundary_count ):
380- M = NMK [i ]
381- for m in range (M ):
382- r1_val = int_R1_store [(i , m )]
383- c_vector [col + m ] = heaving [i ] * r1_val * z_n_d (m )
384-
385- r2_val = int_R2_store [(i , m )]
386- c_vector [col + M + m ] = heaving [i ] * r2_val * z_n_d (m )
387- col += 2 * M
390+ # --- USE YOUR NEW HELPER METHOD ---
391+ c_vector = self .assemble_c_vector (problem , heaving )
388392
389393 hydro_p_term_sum = np .zeros (boundary_count , dtype = complex )
390394 for i in range (boundary_count ):
@@ -403,7 +407,8 @@ def compute_hydrodynamic_coefficients(self, problem, X, m0, modes_to_calculate:
403407 "real" : hydro_coef_real ,
404408 "imag" : hydro_coef_imag ,
405409 "excitation_phase" : excitation_phase (X , NMK , m0 , a ),
406- "excitation_force" : excitation_force (hydro_coef_imag , m0 , h )
410+ "excitation_force" : excitation_force (hydro_coef_imag , m0 , h ),
411+ "c_vector" : c_vector # --- APPEND C_VECTOR TO OUTPUT ---
407412 })
408413
409414 return results_per_mode
@@ -591,6 +596,10 @@ def run_and_store_results(self, problem_index: int) -> Results:
591596 full_excitation_force = np .full ((num_freqs , num_modes ), np .nan )
592597 full_excitation_phase = np .full ((num_freqs , num_modes ), np .nan )
593598
599+ # --- NEW: Initialize full_c_vector ---
600+ c_vector_len = NMK_list [0 ] + 2 * sum (NMK_list [1 :- 1 ])
601+ full_c_vector = np .full ((num_freqs , num_modes , c_vector_len ), np .nan + 1j * np .nan , dtype = complex )
602+
594603 all_potentials_batch_data = []
595604
596605 temp_bodies = []
@@ -659,6 +668,10 @@ def run_and_store_results(self, problem_index: int) -> Results:
659668 if i_idx == j_idx :
660669 full_excitation_force [freq_idx , j_idx ] = coeff_dict .get ('excitation_force' , np .nan )
661670 full_excitation_phase [freq_idx , j_idx ] = coeff_dict .get ('excitation_phase' , np .nan )
671+
672+ # --- NEW: Catch the c_vector from your new dict output ---
673+ if 'c_vector' in coeff_dict :
674+ full_c_vector [freq_idx , j_idx , :] = coeff_dict ['c_vector' ]
662675
663676 Cs = temp_engine .reformat_coeffs (X_i , NMK_list , len (NMK_list ) - 1 )
664677
@@ -685,12 +698,14 @@ def run_and_store_results(self, problem_index: int) -> Results:
685698 full_damping_matrix [freq_idx , :, i_idx ] = np .nan
686699 continue
687700
701+ # --- NEW: Pass the full_c_vector array to the storage function ---
688702 results .store_hydrodynamic_coefficients (
689703 frequencies = omegas_to_run ,
690704 added_mass_matrix = full_added_mass_matrix ,
691705 damping_matrix = full_damping_matrix ,
692706 excitation_force = full_excitation_force ,
693- excitation_phase = full_excitation_phase
707+ excitation_phase = full_excitation_phase ,
708+ c_vector = full_c_vector
694709 )
695710
696711 if all_potentials_batch_data :
0 commit comments