This section contains descriptions of DEFINE
macros for the
MSMD-based battery model. The functions can be hooked up from the Battery
Model dialog box (UDF tab). Table 2.14: Quick Reference Guide for Battery Model-Specific DEFINE
Macros provides a quick reference guide to the
battery model DEFINE
macros, the functions they define, and the
dialog boxes where they are activated in Ansys Fluent. For your convenience, they are listed in
Battery Model DEFINE
Macros. Definitions of each DEFINE macro are
contained in the udf.h header file.
- 2.7.1. DEFINE_BATTERY_ABUSE_RATE
- 2.7.2. DEFINE_BATTERY_CLUSTER
- 2.7.3. DEFINE_BATTERY_ECHEM_MODEL
- 2.7.4. DEFINE_BATTERY_ELOAD_PROFILE
- 2.7.5. DEFINE_BATTERY_ENTROPIC_HEAT
- 2.7.6. DEFINE_BATTERY_NEWMAN_BV_RATE
- 2.7.7. DEFINE_BATTERY_NEWMAN_POSTPROCESSING
- 2.7.8. DEFINE_BATTERY_PARAMETER_ECM
- 2.7.9. DEFINE_BATTERY_PARAMETER_NTGK
- 2.7.10. DEFINE_BATTERY_PROPERTY
- 2.7.11. DEFINE_BATTERY_SWELL_LAYER_N
- 2.7.12. DEFINE_BATTERY_SWELL_STRAIN
Note: All the battery model UDFs can only be compiled and cannot be run in the interpreted mode.
Table 2.14: Quick Reference Guide for Battery Model-Specific DEFINE
Macros
Function |
|
Dialog Box Activated In |
---|---|---|
abuse reaction rate for the 1-eq abuse reaction model |
| Battery Model |
cell clustering target variable |
| Battery Model |
voltage-current relationship for the user-defined electrochemical model |
DEFINE_BATTERY_ECHEM_MODEL
| Battery Model |
electric load type and value |
DEIFNE_BATTERY_ELOAD_PROFILE
| Battery Model |
entropic heat term |
DEFINE_BATTERY_ENTROPIC_HEAT
| Battery Model |
the Butler-Volmer rate for the Newman's P2D model |
DEFINE_BATTERY_NEWMAN_BV_RATE
| Battery Model |
export the Newman's P2D model results |
DEFINE_BATTERY_NEWMAN_POSTPROCESSING
| Battery Model |
parameters for the ECM model |
DEFINE_BATTERY_PARAMETER_ECM
| Battery Model |
U and Y functions for the NTGK
model |
DEFINE_BATTERY_PARAMETER_NTGK
| Battery Model |
material properties for the Newman's P2D model |
DEFINE_BATTERY_PROPERTY
| Battery Model |
normal vector of the battery electrode layer for the battery swelling model |
DEFINE_BATTERY_SWELL_LAYER_N
| Battery Model |
swelling strain for the NTGK or ECM model |
DEFINE_BATTERY_SWELL_STRAIN
| Battery Model |
You can use DEIFNE_BATTERY_ABUSE_RATE
to specify the abuse
rate in the one-equation thermal abuse model.
DEIFNE_BATTERY_ABUSE_RATE
(name, T,
alpha
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Temperature. |
|
Reaction progress variable. |
Function returns
real
There are three arguments to DEIFNE_BATTERY_ABUSE_RATE
:
name
, T
, and
alpha
. You supply name
, the name of
the UDF. T
and alpha
are variables that
are passed by the Ansys Fluent solver to your UDF. Your function will return a value of the
abuse rate.
The example shows the usage of DEFINE_BATTERY_ABUSE_RATE
. The
UDF implements the default Arrhenius rate in Ansys Fluent (see Equation 19–33 in the Fluent Theory Guide).
#include "udf.h" DEFINE_BATTERY_ABUSE_RATE(abuse_rate, T, alpha) { real A =8.3e14 , E =1.54e5 , m = 0.0, n =1.0, R =8.314 ; real value; value = A*exp(E/(R*T))*pow(alpha, m) * pow((1.0-alpha), n); return value; }
After the UDF that you have defined using
DEFINE_BATTERY_ABUSE_RATE
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (Advanced
Options tab). See Hooking Battery Model UDFs for
details.
You can use DEFINE_BATTERY_CLUSTER
to specify the target
variable in cell clustering.
DEFINE_BATTERY_CLUSTER
(name, c, t
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Cell index. |
|
Pointer to the cell thread. |
Function returns
real
There are three arguments to DEFINE_BATTERY_CLUSTER
:
name
, c
, and
t
. You supply name
, the name of the
UDF. c
and t
are variables that are
passed by the Ansys Fluent solver to your UDF. Your function will return a value of the cell
clustering variable.
The example shows the usage of DEFINE_BATTERY_CLUSTER
. In a
jelly roll battery simulation, radius could be used as the target variable. The following
code shows an example of such a UDF.
#include "udf.h" DEFINE_BATTERY_CLUSTER(battery_clustering, c, t) { real value, x[3]; C_CENTROID(x, c, t); value = sqrt(x[0]*x[0] + x[1]*x[1]); /* use radius as the clustering criterion */ return value; }
After the UDF that you have defined using
DEFINE_BATTERY_CLUSTER
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (Model
Options tab). See Hooking Battery Model UDFs for
details.
You can use DEFINE_BATTERY_ECHEM_MODEL
to specify the
voltage-current relationship used in the user-defined electrochemical model. You need to
define both scenarios:
computing voltage when current is specified
computing current when voltage is specified
DEFINE_BATTERY_ECHEM_MODEL
(name, zero_start, mode,
temperature, voltage_in, current_in, dt, current_out, Qe, voltage_out
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Flag to indicate whether or not the submodel is to be initialized. A value of 0 indicates the initial UDF call requesting submodel initialization. A value of 1 indicates the subsequent call. |
|
Flag indicating which electric load boundary type is used:
|
|
Temperature at the time the submodel is called. |
|
A voltage value. This value is used as an input when the voltage load boundary condition is used. |
|
A current value. This value is used as an input when the current load boundary condition is used. |
|
Time step. |
|
Pointer to the computed current value. This value needs to be computed when the voltage input condition is used. |
|
Pointer to the computed voltage value. This value needs to be computed when the current input condition is used. |
|
Heat generation rate. |
Function returns
void
There are ten arguments to DEFINE_BATTERY_ECHEM_MODEL
:
name
, zero_start
,
mode
, temperature
,
voltage_in
, current_in
,
dt
, current_out
,
Qe
, and voltage_out
. You supply
name
, the name of the UDF. zero_start
,
mode
, temperature
,
voltage_in
, current_in
, and
dt
are variables that are passed by the Ansys Fluent solver to your
UDF. Your function will need to compute the values of
current_out
, Qe
, and
voltage_out
.
This example shows the usage of DEFINE_BATTERY_ECHEM_MODEL
.
The NTGK model is reproduced by using the user-defined electrochemical model.
#include "udf.h" DEFINE_BATTERY_ECHEM_MODEL(echem_model, zero_start, mode, temperature, voltage_in, current_in, \ dtime, current_out, Qe, voltage_out) { real DOD, U_fun, Y_fun; real a[] = {4.12, -0.804, 1.075, -1.177, 0.0, 0.0}; real b[] = {1168.59, -8928, 52504.6, -136231, 158531.7, -67578.5}; real T_coef[] = {1800.0, -0.00095}; real T_ref = 298.0; if (zero_start == 0) USER_DEFINED_ECHEM[0] = 0.0; DOD = USER_DEFINED_ECHEM[0]; U_fun = a[0] + a[1] * DOD + a[2] * DOD * DOD + a[3] * DOD * DOD * DOD \ + a[4] * DOD * DOD * DOD * DOD + a[5] * DOD * DOD * DOD * DOD * DOD; U_fun -= T_coef[1] * (temperature - T_ref); Y_fun = b[0] + b[1] * DOD + b[2] * DOD * DOD + b[3] * DOD * DOD * DOD \ + b[4] * DOD * DOD * DOD * DOD + b[5] * DOD * DOD * DOD * DOD * DOD; Y_fun *= exp(T_coef[0] * (1. / T_ref - 1. / temperature)); if (mode == 0) { *current_out = Y_fun * (U_fun - voltage_in); *Qe = *current_out * (U_fun - voltage_in); USER_DEFINED_ECHEM[0] += *current_out * dtime / (3600.0 * 14.6); } else { *voltage_out = U_fun - current_in / Y_fun; } }
After the UDF that you have defined using
DEFINE_BATTERY_ECHEM_MODEL
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (UDF
tab). See Hooking Battery Model UDFs for details.
You can use DEFINE_BATTERY_ELOAD_PROFILE
to specify the
electric load type and value dynamically in a simulation.
DEFINE_BATTERY_ELOAD_PROFILE
(name, time, current,
voltage, power, type, value
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Time. |
|
System electric current. |
|
System electric voltage. |
|
System electric power. |
|
Electric load type (0: C-rate, 1: Current, 2: Voltage, 3: Power, 4: External electric resistance). |
|
Electric load value. |
Function returns
void
There are seven arguments to DEFINE_BATTERY_ELOAD_PROFILE
:
name
, time
,
current
, voltage
,
power
, type
, and
value
. You supply name
, the name of
the UDF. time
, current
,
voltage
, power
, and
type
are variables that are passed by the Ansys Fluent solver to
your UDF. Your function will need to define the electric load type, type and its
value
. These two values will be returned back to the
solver.
The following example shows how to use the
DEFINE_BATTERY_ELOAD_PROFILE
UDF to implement an
event-scheduled profile. The battery is first discharged with a constant rate 1 C until
its voltage is below 3.8 V. It is put at rest for 300 seconds. Then the battery is charged
with a constant rate 1 C until its voltage reaches 4.1 V. After that, the battery
continues charging with a constant voltage of 4.1 V until the current is less than 5 A.
Then the battery is put at rest again.
#include "udf.h" real time0 = 0.0; int flag = 0, flag1 = 0, flag2 = 0, flag3 = 0, flag4 = 0, flag5 = 0; DEFINE_BATTERY_ELOAD_PROFILE(eload_profile_for_event_prof, time, current, voltage, power, eload_type, eload_value) { /* /* Note: 1: eload_type is an integer pointer, only takes the following values *eload_type = 0 C-rate type *eload_type = 1 current type *eload_type = 2 voltage type *eload_type = 3 power type *eload_type = 4 external electric resistance 2: using flags to control events so they get executed sequentially */ real time_duration; time_duration = time - time0; if (N_ITER == 0) { flag = 0; flag1 = 0; flag2 = 0; flag3 = 0; flag4 = 0; flag5 = 0; } if (flag1 == 0 || (voltage > 3.8 && flag2 == 0)) { flag1 = 1; *eload_type = 0; *eload_value = 1; time0 =time; } else if (time_duration < 300 && flag3 == 0) { if (flag == 0) { time0 = time; flag = 1; } flag2 = 1; *eload_type = 1; *eload_value = 0; } else if (voltage < 4.1 && flag4 == 0) { flag3 = 1; *eload_type = 0; *eload_value = -1; } else if (current < -5 && flag5 == 0) { flag4 = 1; *eload_type = 2; *eload_value = 4.1; } else { flag5 = 1; *eload_type = 1; *eload_value = 0.0; } }
Th following example uses the battery's state of charge (SOC) to determine the charging schedule. The battery is first charged with a constant current when SOC is below 0.5. Then the battery is charged with a linearly varying current when SOC is in the range of 0.5 to 0.8. It is followed by a constant current charge in the range of 0.8 to 0.95. After that, the battery is charged with a constant voltage.
DEFINE_BATTERY_ELOAD_PROFILE
function is only called from the
host machine. If you want to use the battery's average temperature or SOC as a load switch
condition, you need to compute average temperature or SOC in an adjust function as shown
below.
#include "udf.h" real soc = 0.0; DEFINE_ADJUST(adjust, domain) { Thread *t; cell_t c; real tmp1, tmp2; tmp1 = tmp2 = 0.0; thread_loop_c (t, domain) { if (battery_fcns->is_active_thread(t)) { begin_c_loop_int(c, t) { tmp1 = C_VOLUME(c, t) * (1.0 - C_BATTERY_DISCHARGE_DEPTH(c, t)); tmp2 = C_VOLUME(c, t); } end_c_loop_int(c, t) } } tmp1 = PRF_GRSUM1(tmp1); tmp2 = PRF_GRSUM1(tmp2); soc = tmp1/ tmp2; node_to_host_real_1(soc); } DEFINE_BATTERY_ELOAD_PROFILE(eload_profile_for_cfd, time, current, voltage, power, eload_type, eload_value) { if (soc < 0.5) { *eload_type = 1; *eload_value = -45.0; } else if (soc >=0.5 && soc <0.8) { *eload_type = 1; *eload_value = -45.0 + (-15.0 + 45.0) / (0.8 - 0.5) * (soc - 0.5); } else if (soc >= 0.8 && soc < 0.95) { *eload_type = 1; *eload_value = -15.0; } else { *eload_type = 2; *eload_value = 4.12; } }
After the UDF that you have defined using
DEFINE_BATTERY_ELOAD_PROFILE
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (Model
Options tab). See Hooking Battery Model UDFs for
details.
You can use DEFINE_BATTERY_ENTROPIC_HEAT
to compute the
entropic heat term in the battery thermal analysis if you want to include the entropic
heat effect in your simulation. The entropic heat can be included in all the battery
submodels including the NTGK, ECM and Newman's P2D models.
DEFINE_BATTERY_ENTROPIC_HEAT
(name, T, soc,
discharge_mode
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Temperature. |
|
State of the charge (SOC). |
|
Flag with a value of 0 or 1. 0 indicates charging, and 1 indicates discharging. |
Function returns
real
There are four arguments to DEFINE_BATTERY_ENTROPIC_HEAT
:
name
, T
, soc
,
and discharge_mode
. You supply name
, the
name of the UDF. T
, soc
, and
discharge_mode
are variables that are passed by the Ansys Fluent
solver to your UDF. Your function will return a value of the term in the entropic heat calculation (see Equation 19–8, Equation 19–13, and
Equation 19–30 in the Fluent Theory Guide).
The entropic heat is ignored in the default Ansys Fluent battery model, which corresponds
to =0. This example shows how to use
DEFINE_BATTERY_ENTROPIC_HEAT
to compute the term in the entropic heat calculation.
#include "udf.h" real interpolate_table(int N_p, real *soc_data, real *value, real SOC) { int i; real result= 0.0; if (SOC < soc_data[0]) result = value[0]; else if (SOC > soc_data[N_p - 1]) result = value[N_p -1]; else { for (i=0; i<N_p-1; i++) if (SOC >= soc_data[i] && SOC <= soc_data[i+1]) { result = value[i] + (value[i+1]-value[i])/(soc_data[i+1]-soc_data[i])*(SOC-soc_data[i]); break; } } return result; } DEFINE_BATTERY_ENTROPIC_HEAT(entropic_heat, T, SOC, discharging_mode) { real tmp1, tmp2, dUdT = 0.0; real T1= 300, T2=320; real soc_data1[] = {0.0, 0.23, 0.28, 0.35, 0.47, 0.56, 0.82, 1.0}; real value1[] = {-0.3, -0.03, 0.14, 0.14, -0.31, 0.05, 0.22, 0.22}; real soc_data2[] = {0.0, 1.0}; real value2[] = {0, 1}; int i, N_p1 = 8, N_p2 = 2; for (i=0; i<N_p1; i++) value1[i] *= 0.0001; for (i=0; i<N_p2; i++) value2[i] *= 0.0001; if (T<T1) dUdT = interpolate_table(N_p1, soc_data1, value1, SOC); else if (T>T2) dUdT = interpolate_table(N_p2, soc_data2, value2, SOC); else { tmp1 = interpolate_table(N_p1, soc_data1, value1, SOC); tmp2 = interpolate_table(N_p2, soc_data2, value2, SOC); dUdT = tmp1 + (tmp2 -tmp1)/(T2 -T1) * (T-T1); } return dUdT; }
After the UDF that you have defined using
DEFINE_BATTERY_ENTROPIC_HEAT
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (UDF
tab). See Hooking Battery Model UDFs for details.
You can use DEFINE_BATTERY_NEWMAN_BV_RATE
to customize the
Butler-Volmer rate used in the Newman's P2D model. See Newman’s P2D Model in the Fluent Theory Guide for more
information.
DEFINE_BATTERY_NEWMAN_BV_RATE
(name, Ce, Cs, Cs_max,
T, eta, k_m, alpha_a, alpha_c, mode
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Lithium ion concentration in electrolyte. |
|
Lithium concentration in electrode. |
|
Maximum lithium concentration in electrode. |
|
Temperature. |
|
Overpotential (). |
|
Rate pre-exponential factor. |
|
Anodic charge transfer coefficient. |
|
Cathodic charge transfer coefficient. |
|
Flag to indicate whether the reaction is in anode or cathode. A value of 0 indicates anode, and a value of 1 indicates cathode. |
Function returns
real
There are ten arguments to DEFINE_BATTERY_NEWMAN_BV_RATE
:
name
, Ce
, Cs
,
Cs_max
, T
,
eta
, k_m
,
alpha_a
, alpha_c
, and
mode
. You supply name
, the name of the
UDF. Ce
, Cs
,
Cs_max
, T
,
eta
, k_m
,
alpha_a
, alpha_c
, and
mode
are variables that are passed by the Ansys Fluent solver to
your UDF. Your function will return the Butler-Volmer rate.
This example shows the usage of DEFINE_BATTERY_NEWMAN_BV_RATE
to compute the electrochemical reaction rate for both cathode and anode using the default
Butler-Volmer equations with the kinetics parameters.
#include "udf.h" DEFINE_BATTERY_NEWMAN_BV_RATE(p2d_bv_rate, Ce, Cs, Cs_max, T, eta, k_m, alpha_a, alpha_c, mode) { real rate, i_0; i_0 = k_m * pow(Ce, alpha_a) * pow(Cs, alpha_c) * pow(Cs_max - Cs, alpha_a); rate = i_0 * (exp(alpha_a * 9.6485e4 / (8.314 * T) * eta) - exp(-alpha_c * 9.6485e4/(8.314*T)*eta)); return rate; }
After the UDF that you have defined using
DEFINE_BATTERY_NEWMAN_BV_RATE
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box
(Advanced tab). See Hooking Battery Model UDFs for
details.
You can use DEFINE_BATTERY_NEWMAN_POSTPROCESSING
to export
the detailed information of the Newman's P2D model results. See Newman’s P2D Model in the Fluent Theory Guide for more
information.
DEFINE_BATTERY_NEWMAN_POSTPROCESSING
(name, c, t, T,
Vp, Vn
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Index of the cell calling the function. |
|
Pointer to the thread of the function calling cell. |
|
Temperature. |
|
Cathode potential of the electrode. |
|
Anode potential of the electrode. |
Function returns
void
There are six arguments to
DEFINE_BATTERY_NEWMAN_POSTPROCESSING
:
name
, c
, t
,
T
, Vp
, and
Vn
. You supply name
, the name of the
UDF. c
, t
, T
,
Vp
, and Vn
are variables that are
passed by the Ansys Fluent solver to your UDF. You can use the UDF to export information such
as potential and lithium concentration to a file or print it in the console window.
This example shows how to use
DEFINE_BATTERY_NEWMAN_POSTPROCESSING
to print some fundamental
variables of the Newman's P2D model to the console window.
The function is called every time the Newman's P2D solver is called. The UDF prints a large amount of information. You may want to add some controls to print or save only selected variables.
#include "udf.h" DEFINE_BATTERY_NEWMAN_POSTPROCESSING(p2d_output, c, t, T, Vp, Vn) { int i, j; Message(" Newman model results for cell %d of Thread_id %d at Time=%f\n", c, \ NNULLP (t) ? THREAD_ID(t) : -1, CURRENT_TIME); Message(" T=%f Vp=%f Vn=%f \n", T, Vp, Vn); Message(" Grid center location\n"); Message("NE\n"); for (i = 0; i < battery_n_XN; i++) Message(" %g\n", battery_X_cv_NE[i]); Message("SP\n"); for (i = 0; i < battery_n_XS; i++) Message(" %g\n", battery_X_cv_SP[i]); Message("PE\n"); for (i = 0; i < battery_n_XP; i++) Message(" %g\n", battery_X_cv_PE[i]); { Message("RP\n"); for (i = 0; i < battery_n_RP; i++) Message(" %g\n", battery_R_cv_PE[i]); Message("RN\n"); for (i = 0; i < battery_n_RN; i++) Message(" %g\n", battery_R_cv_NE[i]); } Message("Positive Electrode: battery_C_CS_P and battery_C_CE_P \n"); for (i = 0; i < battery_n_XP; i++) { for (j = 0; j < battery_n_RP; j++) { Message("%12.5e ", battery_CsPE[i][j]); } Message("\n"); Message("%12.5e\n", battery_CePE[i]); } Message("Separator battery_C_CE \n"); for (i = 0; i < battery_n_XS; i++) { Message(" %12.5e\n", battery_CeSP[i]); } Message("Negative Electrode: battery_C_CS_N and battery_C_CE_N \n"); for (i = 0; i < battery_n_XN; i++) { for (j = 0; j < battery_n_RN; j++) { Message("%12.5e ", battery_CsNE[i][j]); } Message("\n"); Message("%12.5e\n", battery_CeNE[i]); } Message("potential profile in electrolyte\n"); for (i = 0; i < battery_n_XN; i++) Message(" %le \n", battery_PhieNE[i]); for (i = 0; i < battery_n_XS; i++) Message(" %le \n", battery_PhieSP[i]); for (i = 0; i < battery_n_XP; i++) Message(" %le \n", battery_PhiePE[i]); Message("potential profile in electrode\n"); for (i = 0; i < battery_n_XN; i++) Message(" %le \n", battery_PhisNE[i]); for (i = 0; i < battery_n_XP; i++) Message(" %le \n", battery_PhisPE[i]); for (i = 0; i < battery_n_XN; i++) Message(" %12.5e %12.5e %12.5e %12.5e %12.5e %12.5e\n", battery_kappa_NE[i], battery_diff_NE[i], \ battery_t_plus_NE[i], battery_kappa2_NE[i], battery_eta_NE[i], battery_i_NE[i]); for (i = 0; i < battery_n_XS; i++) Message(" %12.5e %12.5e %12.5e %12.5e\n", battery_kappa_SP[i], battery_diff_SP[i], \ battery_t_plus_SP[i], battery_kappa2_SP[i]); for (i = 0; i < battery_n_XP; i++) Message(" %12.5e %12.5e %12.5e %12.5e %12.5e %12.5e\n", battery_kappa_PE[i], battery_diff_PE[i], \ battery_t_plus_PE[i], battery_kappa2_PE[i], battery_eta_PE[i], battery_i_PE[i]); return ; }
After the UDF that you have defined using
DEFINE_BATTERY_NEWMAN_POSTPROCESSING
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (UDF
tab). See Hooking Battery Model UDFs for details.
You can use DEFINE_BATTERY_PARAMETER_ECM
to specify your own
parameters for the ECM model. See ECM Model in the Fluent Theory Guide for details.
DEFINE_BATTERY_PARAMETER_ECM
(name
,
c
, t
, T
,
soc
, mode, Voc, Rs, R1, C1, R2, C2, R3,
C3
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Cell index. |
|
Pointer to the thread of the active zone. |
|
Integer flag that indicates charging/discharging mode. A value of 1 indicates discharging, while a value of 0 indicates charging. |
|
Temperature. |
|
Value of the state of the charge (SOC). |
|
Pointer to the Voc value. |
|
Pointer to the Rs value. |
|
Pointer to the R1 value. |
|
Pointer to the C1 value. |
|
Pointer to the R2 value. |
|
Pointer to the C2 value. |
|
Pointer to the R3 value. |
|
Pointer to the C3 value. |
Function returns
void
There are fourteen arguments to DEFINE_BATTERY_PARAMETER_ECM
:
name
, c
, t
,
T
, soc
, mode
,
Voc
, Rs
, R1
,
C1
, R2
, C2
,
R3
, and C3
. You will supply
name
, the name of the UDF. c
,
t
, T
, soc
,
and mode
are variables that are passed by the Ansys Fluent solver to
your UDF. Your function will need to compute the values of Voc
,
Rs
, R1
, C1
,
R2
, C2
, R3
,
and C3
.
This example shows how to use DEFINE_BATTERY_PARAMETER_ECM
to
reproduce the default polynomial functions in Chen's form.
The UDF uses a 3 RC loop circuit. The default Chen's circuit uses only 2 RC loops. Small values of R3 and C3 are used to skip the third RC loop.
#include "udf.h" DEFINE_BATTERY_PARAMETER_ECM(ecm_model_parameter, c, t, T, soc, mode, Voc, RRs, RR1, CC1, RR2, CC2, RR3, CC3) { *Voc = 3.685 - 1.031*exp(-35.0*soc) + 0.2156*soc - 0.1178*soc*soc + 0.3201*soc*soc*soc; *RRs = 0.07446 + 0.1562*exp(-24.37*soc); *RR1 = 0.04669 + 0.3208*exp(-29.14*soc); *RR2 = 0.04984 + 6.603*exp(-155.2*soc); *CC1 = 703.6 - 752.9*exp(-13.51*soc); *CC2 = 4475.0 - 6056.*exp(-27.12*soc); *RR3 = 1.0e-5; *CC3 = 1.0e-5; }
After the UDF that you have defined using
DEFINE_BATTERY_PARAMETER_ECM
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (UDF
tab). See Hooking Battery Model UDFs for details.
You can use DEFINE_BATTERY_PARAMETER_NTGK
to specify your own
U
and Y
functions used in the NTGK
model. See NTGK/DCIR Model in the Fluent Theory Guide for
details.
DEFINE_BATTERY_PARAMETER_NTGK
(name
,
c
, t
, T
,
soc
, U
, Y
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Cell index. |
|
Pointer to the thread of the active zone. |
|
Temperature. |
|
Value of the state of charge (SOC). |
|
Pointer to the value of |
|
Pointer to the value of |
Function returns
void
There are seven arguments to DEFINE_BATTERY_PARAMETER_NTGK
:
name
, c
, t
,
T
, soc
, U
,
and Y
. You will supply name
, the name of
the UDF. c
, t
,
T
, and soc
are variables that are
passed by the Ansys Fluent solver to your UDF. Your function will need to compute the values
of U
and Y
.
This example shows how to use DEFINE_BATTERY_PARAMETER_NTGK
to reproduce the default polynomial U
and
Y
functions.
#include "udf.h" DEFINE_BATTERY_PARAMETER_NTGK(ntgk_model_parameter, c, t, T, soc, U, Y) { real a[] = {4.12, -0.804, 1.075, -1.177, 0.0, 0.0}; real b[] = {1168.59, -8928, 52504.6, -136231, 158531.7, -67578.5}; real C[] = {1800.0, -0.00095}; real DOD = 1.0 - soc; real T_ref = 298.0; *U = a[0]+a[1]*DOD+a[2]*DOD*DOD+a[3]*DOD*DOD*DOD \ + a[4]*DOD*DOD*DOD*DOD + a[5]*DOD*DOD*DOD*DOD*DOD; *U -= C[1]*(T - T_ref); *Y = b[0]+b[1]*DOD+b[2]*DOD*DOD+b[3]*DOD*DOD*DOD \ + b[4]*DOD*DOD*DOD*DOD+b[5]*DOD*DOD*DOD*DOD*DOD; *Y *= exp(C[0]*(1./T_ref - 1./T))); }
After the UDF that you have defined using
DEFINE_BATTERY_PARAMETER_NTGK
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (UDF
tab). See Hooking Battery Model UDFs for details.
You can use DEFINE_BATTERY_PROPERTY
to specify material
properties used in the Newman's P2D model. See Newman’s P2D Model in the Fluent Theory Guide for more information.
DEFINE_BATTERY_PROPERTY
(name, x, T
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Dependent variable of material property. |
|
Temperature. |
Function returns
real
There are three arguments to DEFINE_BATTERY_PROPERTY
:
name
, x
, and
T
. You supply name
, the name of the
UDF. x
and T
are variables that are
passed by the Ansys Fluent solver to your UDF. These are the variables the material property
depends on. For example, if the UDF is used to define open circuit potential, then
x
will be the state of lithiation (sol) of the electrode, that
is, the ratio of the lithium concentration at the electrode surface and the maximum
electrode concentration. If the UDF is used to define any electrolyte property, then
x
will be the lithium concentration in the electrolyte. If the
UDF is used for any solid electrode property, then x
will be the
lithium concentration in the electrode. Your function will return a value of the material
property.
This example shows the usage of DEFINE_BATTERY_PROPERTY
. The
first two UDFs are used to compute the open circuit potential used for the cathode and
anode electrode. And the last one is used to compute the ionic conductivity of the
electrolyte material. The UDFs are used to reproduce the default settings used in the
Newman's P2D model.
#include "udf.h" DEFINE_BATTERY_PROPERTY(ocp_p, x, T) { real UPE, xx; xx = -14.555 * x + 8.609; xx *= 2.0; UPE = 4.199 + 0.0566 * (exp(xx) - 1.0) / (exp(xx) + 1.0) - 0.0275 * (pow(0.998 - x, -0.492) - 1.901) - 0.1570 * exp(-0.0474 * pow(x, 8.0)) + 0.8100 * exp(-40.0 * (x - 0.134)); return UPE; } DEFINE_BATTERY_PROPERTY(ocp_n, x, T) { real UNE = -0.16 + 1.32 * exp(-3.0 * x) + 10.0 * exp(-2000.0 * x); return UNE; } DEFINE_BATTERY_PROPERTY(kappa, ce, T) { return 1.0793e-2 + (6.7461e-4) * ce - (5.2245e-7) * ce * ce + (1.3605e-10) * ce * ce * ce - (1.1724e-14) * ce * ce * ce * ce; }
After the UDF that you have defined using
DEFINE_BATTERY_PROPERTY
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (Model
Parameter tab). See Hooking Battery Model UDFs for
details.
You can use DEFINE_BATTERY_SWELL_LAYER_N
to specify your own
normal vector to the battery electrode layer for the battery swelling model. See Battery Swelling Model in the Fluent Theory Guide for more
information.
DEFINE_BATTERY_SWELL_LAYER_N
(name, c, t,
N_vec
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Cell index. |
|
Pointer to the thread of the active zone. |
|
Pointer to the normal vector. |
Function returns
void
There are four arguments to DEFINE_BATTERY_SWELL_LAYER_N
:
name
, c
, t
,
and N_vec
. You supply name
, the name of
the UDF. c
, and t
are variables that are
passed by the Ansys Fluent solver to your UDF. Your function will need to specify three
components of the normal vector N_vec
of the battery electrode
layer and pass it back to the solver. The magnitude of the specified normal vector does
not have to be unity as the Ansys Fluent solver automatically performs vector
normalization.
In this example, DEFINE_BATTERY_SWELL_LAYER_N
specifies the
normal vector to the battery electrode layer. The battery cell is cylindrical with its
axis coinciding with the Z axis. The normal vector to the electrode layer is in the radial
direction of the cylinder.
#include "udf.h" DEFINE_BATTERY_SWELL_LAYER_N(myLayer, c, t, N_vec) { real x_cell_center[ND_ND]; C_CENTROID(x_cell_center, c, t); N_vec[0] = x_cell_center[0]; N_vec[1] = x_cell_center[1]; N_vec[2] = 0.0; }
After the UDF that you have defined using
DEFINE_BATTERY_SWELL_LAYER_N
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Battery Model dialog box (Model
Parameters tab). See Hooking Battery Model UDFs for
details.
You can use DEFINE_BATTERY_SWELL_STRAIN
to customize the
swelling strain used in the empirical battery swelling model. See Empirical-Based Swelling Model in the Fluent Theory Guide for more
information.
DEFINE_BATTERY_SWELL_STRAIN
(name, c, t, T, soc,
current
)
Argument Type |
Description |
---|---|
|
UDF name. |
|
Cell index. |
|
Pointer to the thread of the battery active zone. |
|
Temperature. |
|
State of the charge (SOC) in the battery cell. |
|
Current transfer density in a cell. |
Function returns
real
There are six arguments to DEFINE_BATTERY_SWELL_STRAIN
:
name
, c
, t
,
T
, soc
, and
current
. You supply name
, the name of
the UDF. c
, t
,
T
, soc
, and
current
are variables that are passed by the Ansys Fluent solver to
your UDF. These are the variables that you can use to define the swelling strain. Your
function will return a value of the swell strain.
The following example provides the source code of the default equation used in
Ansys Fluent simulations when you do not use a
DEFINE_BATTERY_SWELL_STRAIN
. You can modify this template to
adapt it to your needs.
#include "udf.h" DEFINE_BATTERY_SWELL_STRAIN(swell_rate, c, t, T, soc, current) { real omega = 0.2, soc_ref = 0.25; return omega * (soc - soc_ref) / (1.0 + omega * soc_ref); }
After the UDF that you have defined using
DEFINE_BATTERY_SWELL_STRAIN
is compiled (Compiling UDFs), the name of the argument that you supplied as
the first DEFINE
macro argument will become visible and
selectable in the Swelling Model Parameters dialog box. See Hooking Battery Model UDFs for details.