Main Content

Visualize Battery Simulation Output Data

Since R2023b

This example shows how to visualize battery simulation data using a dynamic battery chart from the output of a Simulink™ model that contains Simscape™ Battery™ generated blocks. In real-world battery applications, battery cells develop temperature and state of charge differences that depend on the design of the cooling system and on the electrical design of the current collectors, busbars, and other connectors.

You can select which battery variable or state to plot over time by using the batterySimulationLog object. You can then use this object as an input to the batterySimulationChart object. This action overlays the values that the variable takes over time and maps them on a batteryChart object.

Create Battery Pack Object in MATLAB

To create a battery Pack object, you must first design and create the foundational elements of the battery pack.

Create Cell Object and Define Visualization Variables

First create and define the geometry of a battery cell. The CylindricalGeometry object defines the cylindrical geometrical arrangement of the battery cell. To create a CylindricalGeometry object, use the batteryCylindricalGeometry function. To create a cell object, use the batteryCell function and specify the CylindricalGeometry object as the first argument.

cylindricalGeometry = batteryCylindricalGeometry();
cylindricalCell = batteryCell(cylindricalGeometry);

Change the fundamental cell model block of the Pack object to use the Battery Equivalent Circuit block. Specify the CellModelBlockPath property of the CellModelOptions property inside the batterycell object.

cylindricalCell.CellModelOptions.CellModelBlockPath = "batt_lib/Cells/Battery Equivalent Circuit";

You can use the Cell object to simulate the thermal effects of the battery cell by using a simple 1-D model. To simulate the thermal effects of the battery cell, in the BlockParameters property of the CellModelOptions object of the Cell object, set the ThermalModel property to "LumpedThermalMass". You can define the thermal boundary conditions for battery parallel assemblies and modules only if you first define a thermal model at the cell level.

cylindricalCell.CellModelOptions.BlockParameters.ThermalModel = "LumpedThermalMass";

Create ParallelAssembly Object

A parallel assembly comprises multiple battery cells connected electrically in parallel under a specific topological configuration or geometrical arrangement. In this example, you create a parallel assembly of eight cylindrical cells.

To create the ParallelAssembly object, use the batteryParallelAssembly function. Specify the Cell object as the first argument and the number of cells in parallel as the second argument.

parallelAssembly = batteryParallelAssembly(cylindricalCell,8, ...
    Rows=1, ...
    Topology="Square");

Create Module Object

A battery module comprises multiple parallel assemblies connected in series. In this example, you create three battery modules of two parallel assemblies each. The first two modules have a grouped model resolution. The third module has a lumped model resolution.

To create this Module object, use the batteryModule function. Specify the ParallelAssembly object as the first argument and the number of parallel assemblies in series as the second argument. To define the additional properties, use the name-value arguments InterParallelAssemblyGap and StackingAxis.

groupedModule1 = batteryModule(parallelAssembly,2, ...
    SeriesGrouping=[1 1], ...
    ParallelGrouping=[8 1], ...
    InterParallelAssemblyGap=simscape.Value(0.005,"m"), ...
    StackingAxis="X");

groupedModule2 = batteryModule(parallelAssembly,2, ...
    SeriesGrouping=[1 1], ...
    ParallelGrouping=[1 8], ...
    InterParallelAssemblyGap=simscape.Value(0.005,"m"), ...
    StackingAxis="X");

lumpedModule = batteryModule(parallelAssembly,2, ...
    InterParallelAssemblyGap=simscape.Value(0.005,"m"), ...
    StackingAxis="X");

Create ModuleAssembly Object

A battery module assembly comprises multiple battery modules connected in series or in parallel. In this example, you create a battery module assembly of five modules, with a gap of 0.001 m between each module assembly. By default, the ModuleAssembly object electrically connects the modules in series.

To create the ModuleAssembly object, use the batteryModuleAssembly function and specify the Module objects as the first argument. To define the additional properties, use the name-value arguments InterModuleGap and StackingAxis.

moduleAssembly = batteryModuleAssembly([groupedModule1,repmat(lumpedModule,1,3),groupedModule2], ...
    InterModuleGap = simscape.Value(0.001,"m"), ...
    StackingAxis="X");

Create Pack Object

You now have all the foundational elements to create your battery pack. A battery pack comprises multiple battery module assemblies connected in series or in parallel. In this example, you create a battery pack with one module assembly. By default, the Pack object electrically connects the modules in series.

To create the Pack object, use the batteryPack function and specify the ModuleAssembly object as the first argument. To define the additional properties, use the name-value arguments CoolantThermalPath and AmbientThermalPath.

pack = batteryPack(moduleAssembly, ...
    AmbientThermalPath="CellBasedThermalResistance", ...
    CoolantThermalPath="CellBasedThermalResistance");

Visualize Battery Pack and Check Model Resolution

To obtain the number of Battery Equivalent Circuit blocks for the simulation, use the NumModels property of your pack object.

disp(pack.NumModels)
    21

To visualize the battery pack before you build the system model and to view its model resolution, create the figure where you want to visualize your pack and then use the batteryChart function. To view the model resolution of the batterypack object, specify the SimulationStrategyVisible name-value argument as"On".

f = uifigure(Color="w");
tl = tiledlayout(1,2,Parent=f,TileSpacing="Compact");
nexttile(tl)
packChart1 = batteryChart( tl,pack);
nexttile(tl)
packChart2 = batteryChart(tl,pack,SimulationStrategyVisible="On");

Build Simscape Model for Battery Pack Object

After you create your battery objects, you need to convert them into Simscape models to use them in block diagrams. You can then use these models as references for system integration and requirement evaluation, cooling system design, control strategy development, hardware-in-the-loop, and many more applications.

To create a library that contains the Simscape Battery model of the Pack object, use the buildBattery function. To create a script where you can individually define all the battery parameters, set the MaskParameters argument of the buildBattery function to "VariableNamesByType". To include the initial targets as part of the script, set the MaskInitialTargets argument of the buildBattery function to "VariableNamesByInstance".

Create the packVisualization_lib and packVisualization SLX library files in your working folder. The packVisualization_lib library contains the Modules and ParallelAssemblies sublibraries. This function also creates a packVisualization_param script with the .m extension, which contains all of the necessary parameters for running the battery simulation.

libraryname = "packVisualization";
buildBattery(pack,LibraryName=libraryname, ...
    MaskParameters="VariableNamesByType", ...
    MaskInitialTargets="VariableNamesByInstance");

Create and Simulate Battery Model

After you create your battery library with the required battery models, you must create a Simulink model. You then simulate this model to obtain the logged simulation data.

Create Simulink Model

Create and open a Simulink model. Define the name of your model and use the open_system function.

modelname = "packVisualizationModel";
open_system(new_system(modelname));

This example programmatically adds all the blocks required to simulate the battery module model. To add these blocks, define their block paths as variables in your workspace.

batteryBlockPath = strcat(modelname,"/",pack.Name);
electricalRefBlockPath = strcat(modelname,"/","ElectricalReference");
solverConfigBlockPath = strcat(modelname,"/","Solver");
currentSourceBlockPath = strcat(modelname,"/","Controlled Current Source");
ambientTemperatureSourceBlockPath = strcat(modelname,"/","Temperature Source");
coolantTemperatureSourceBlockPath = strcat(modelname,"/","Temperature Source Clnt");

Add the blocks to the model. Use the add_block function.

add_block(strcat(libraryname,"/",pack.Name),batteryBlockPath,position=[150,100,300,250]);
add_block("fl_lib/Electrical/Electrical Elements/Electrical Reference",electricalRefBlockPath,position=[165,320,185,340],orientation="down",ShowName="off");
add_block("nesl_utility/Solver Configuration",solverConfigBlockPath,position=[-80,280,-30,320]);
add_block("fl_lib/Thermal/Thermal Sources/Temperature Source",ambientTemperatureSourceBlockPath,position=[205,300,245,340],ShowName="off");
add_block("fl_lib/Thermal/Thermal Sources/Temperature Source",coolantTemperatureSourceBlockPath,position=[255,300,295,340],ShowName="off");

To define the electrical load case, add a DC Current Source block and set the current to 160 amperes in the discharge direction.

add_block( "fl_lib/Electrical/Electrical Sources/DC Current Source",currentSourceBlockPath,position=[-30,150,0,200],orientation="down",i0=num2str(-160));

Get the handles to the block ports and connect all blocks.

batteryBlockPortHandles = get_param(batteryBlockPath,"PortHandles");
electricalRefBlockPortHandles = get_param(electricalRefBlockPath,"PortHandles");
solverConfigBlockPortHandles = get_param(solverConfigBlockPath,"PortHandles");
currentSourceBlockPortHandles = get_param(currentSourceBlockPath,"PortHandles");
ambientTemperatureSourceBlockPortHandles = get_param(ambientTemperatureSourceBlockPath,"PortHandles");
coolantTemperatureSourceBlockPortHandles = get_param(coolantTemperatureSourceBlockPath,"PortHandles");

add_line(modelname,batteryBlockPortHandles.RConn(1),currentSourceBlockPortHandles.RConn,autorouting="smart");
add_line(modelname,batteryBlockPortHandles.LConn,currentSourceBlockPortHandles.LConn,autorouting="smart");
add_line(modelname,batteryBlockPortHandles.RConn(1),electricalRefBlockPortHandles.LConn,autorouting="smart");
add_line(modelname,batteryBlockPortHandles.RConn(1),solverConfigBlockPortHandles.RConn,autorouting="smart");
add_line(modelname,batteryBlockPortHandles.RConn(2),ambientTemperatureSourceBlockPortHandles.LConn,autorouting="smart");
add_line(modelname,batteryBlockPortHandles.RConn(3),coolantTemperatureSourceBlockPortHandles.LConn,autorouting="smart");

This figure shows the resulting battery model:

This figure shows the internal layout of the Module Assembly block:

Simulate Model

To visualize battery simulation outputs in the BatterySimulationChart object, you must first enable Simscape signal logging. To enable logging, set the SimscapeLogType property to "all" in the Simulink model.

set_param(modelname,"SimscapeLogType","all")

To run the simulation, you must first run the parameterization script.

run(strcat(libraryname,"_param.m"));

Initialize the battery temperatures and states of charge to different values by modifying the initial targets of the Module blocks. Modify the initial states of charge.

ModuleAssembly1.Module1.socCell = [repmat(0.8, 8, 1);0.7]; % Cell state of charge of module 1
ModuleAssembly1.Module2.socCell = 0.8, 1, 1; % Cell state of charge of module 2
ModuleAssembly1 = struct with fields:
    Module1: [1×1 struct]
    Module2: [1×1 struct]
    Module3: [1×1 struct]
    Module4: [1×1 struct]
    Module5: [1×1 struct]

ans = 1
ModuleAssembly1.Module3.socCell = 0.8; % Cell state of charge of module 3
ModuleAssembly1.Module4.socCell = 0.8; % Cell state of charge of module 4
ModuleAssembly1.Module5.socCell = [0.9;repmat(0.8, 8, 1)]; % Cell state of charge of module 5

Modify the initial temperatures.

ModuleAssembly1.Module1.batteryTemperature = [repmat(305, 8, 1);302]; % Temperature of module 1, K
ModuleAssembly1.Module2.batteryTemperature = 305; % Temperature of module 2, K
ModuleAssembly1.Module3.batteryTemperature = 306; % Temperature of module 3, K
ModuleAssembly1.Module4.batteryTemperature = 304; % Temperature of module 4, K
ModuleAssembly1.Module5.batteryTemperature = [308; 309; 310; 310; 310; 311; 312; 314; 314]; % Temperature of module 5, K

Modify the thermal resistance parameters.

ModuleType1.CoolantResistance = [12,14,16,18,20,22,24,26,20];
ModuleType2.CoolantResistance = 25;
ModuleType3.CoolantResistance = [22,24,26,28,30,32,34,36,30];

ModuleType1.AmbientResistance = repmat(200,1,9);
ModuleType2.AmbientResistance = 200;
ModuleType3.AmbientResistance = ModuleType1.AmbientResistance;

Run the simulation. Use the sim function and define the StartTime and StopTime arguments.

out = sim(modelname,StartTime="0",StopTime="600");

Create Dynamic Battery Visualization

To select the variable to plot in the BatterySimulationChart and the variable unit, you must first create a BatterySimulationLog object. To create a BatterySimulationLog object, use the batterySimulationLog function. Specify the battery object you used to create the battery model library as the first argument and the simulation output data of that battery block from the Simulink model as the second argument.

batterySimLog = batterySimulationLog(pack,out.simlog.Pack1);

To display which variables you can plot, access the ModelVariables property of the BatterySimulationLog object. These variables correspond to the public variables in the fundamental cell model block.

disp(batterySimLog.ModelVariables)
    "socCell"    "batteryVoltage"    "batteryTemperature"    "numCycles"    "batteryCurrent"

To select another variable, specify the SelectedVariable property. The software automatically selects the default unit for a variable. You can then define a commensurate unit in the SelectedVariableUnit property.

batteryCurrentSimLog = batterySimLog;
batteryCurrentSimLog.SelectedVariable = "batteryCurrent";

batteryStateOfChargeSimLog = batterySimLog;
batteryStateOfChargeSimLog.SelectedVariable = "socCell";

To visualize the value of the temperature variable, use the batterySimulationChart function.

f = uifigure(Color="w");
g = uigridlayout(f,[1 1]);
packChart = batterySimulationChart(g,batterySimLog);
packChartColorBar = colorbar(packChart);
ylabel(packChartColorBar, strcat("Cell temperature"," (",batterySimLog.SelectedVariableUnit,")"),FontSize=14);

Visualize the current and the state of charge.

f = uifigure(Color="w");
g = uigridlayout(f,[1 2]);
packCurrentChart = batterySimulationChart(g,batteryCurrentSimLog);
packCurrentChartColorBar=colorbar(packCurrentChart);
ylabel(packCurrentChartColorBar,strcat("Cell current"," (",batteryCurrentSimLog.SelectedVariableUnit,")"),FontSize=14);
packCurrentChartColorBar = colormap(packCurrentChart);

packStateOfChargeChart = batterySimulationChart(g,batteryStateOfChargeSimLog);
packStateOfChargeChartColorBar = colorbar(packStateOfChargeChart);
ylabel(packStateOfChargeChartColorBar,strcat("Cell state of charge", " (",batteryStateOfChargeSimLog.SelectedVariableUnit,")"),"FontSize",14 );
packStateOfChargeChartColorBar = colormap(packChart);

See Also

| | |

Related Topics