Main Content

Simulation Callbacks for Deployable Applications

With certain functions in Simulink® Compiler™, you can register callbacks during simulation. The simulink.compiler.setExternalInputsFcn and simulink.compiler.setExternalOutputsFcn functions enable you to set the values at the root inport blocks and to obtain the values at the root outport blocks at every simulation step. With the simulink.compiler.setPostStepFcn function, you can register a callback that is invoked after every simulation step, thus using it to post process the outputs.

The following example uses the simulink.compiler.setExternalOutputsFcn and the simulink.compiler.setPostStepFcn, to provide an ongoing tracing of the simulation outputs.

Deploy App with Live Simulation Results of Lorenz System

This example shows how to develop an app that uses callbacks for simulation inputs and outputs to view the simulation of a Simulink® model of the Lorenz system. You can then deploy the app with Simulink Compiler™.

Open the Lorenz System App

This example uses a Simulink model of the Lorenz System, and an app that is created in the MATLAB® App Designer that simulates the model with different input and output values. To learn more about how to create an app using the App Designer, see Create and Run a Simple App Using App Designer. To open the app, type the following at the MATLAB command window.

LorenzSystemApp

Figure Lorenz System App contains an axes object and another object of type uigridlayout. The axes object contains 3 objects of type line, animatedline. One or more of the lines displays its values using only markers

App Details

Open the LorenzSystemApp.mlapp file. You can view the code written to create this app in the Code View section of App Designer. The essential part of building this app is the behavior of the Simulate button. It has the following salient parts: creating the SimulationInput object, configuring it for deployment, using simulation callbacks to read the output port data and plot the data at each time step. These three functions allow you to see the live results of the simulation in the deployed app.

Create the Simulink.SimulationInput Object

In the function createSimulationInput, define an empty Simulink.SimulationInput object for the model. Use this Simulink.SimulationInput object to set simulation callbacks and variables for the model.

Use the simulation callback functions register the callback operations. The simulink.compiler.setPostStepFcn function registers a callback that is invoked after every simulation step. The simulink.compiler.setExternalOuputsFcn registers a callback that dynamically processes the values for every output port at the root level of a model during simulation.

Use the setVariable function to provide the parameter values to the app through the Simulink.SimulationInput object. Values for the simulation are obtained from the edit fields of the UI of the app. To deploy the app, use the simulink.compiler.configureForDeployment function. (Comment the line of code that calls simulink.compiler.configureForDeployment function for faster debugging.)

function simInp = createSimulationInput(app)
            % Create an empty SimulationInput object
            simInp = Simulink.SimulationInput('LorenzSystemModel');
            
            simInp = simulink.compiler.setSimulationStatusChangeFcn(simInp, ...
                @(simStatus) app.simStatusChangedFcn(simStatus));

            % PostStepFcn is used to update plots
            simInp = simulink.compiler.setPostStepFcn(simInp, ...
                @(simTime) app.postStepFcn(simTime), ...
                'Decimation',app.postStepFcnDecimation);
            
            % Load the parameters values from the ui edit fields
            simInp = simInp.setVariable('rho',app.rhoUIC.Value);
            simInp = simInp.setVariable('beta',app.betaUIC.Value);
            simInp = simInp.setVariable('sigma',app.sigmaUIC.Value);
            simInp = simInp.setVariable('x0',app.x0UIC.Value);
            simInp = simInp.setVariable('y0',app.y0UIC.Value);
            simInp = simInp.setVariable('z0',app.z0UIC.Value);
            
            % Configure simInp for deployment
            simInp = simulink.compiler.configureForDeployment(simInp);
        end % createSimulationInput

Simulation Callback Functions

The simulation callback functions register callbacks that allow you to read values from the output ports and to write values to the root input ports. These functions register callbacks at every simulation time step, which allows you to view live results of the simulation.

The postStepFcn Callback

The postStepFcn callback function is invoked after every simulation step. The time argument is the time for the previous simulation step. The postStepFcn function obtains the cached outport block values for every simTime and uses those values to the plot the cached values at simulation time.

function postStepFcn(app, simTime)
            app.SimTime.Text = sprintf('%0.5g',simTime); % 0.1234e+56
            wcTime = toc(app.wallClockTimeAtSimStart);
            app.SimPace.Text = sprintf('%7.2f', simTime/wcTime); % 1234.56
            app.adjustPostStepFcnDecimation();
            simOut = simulink.compiler.getSimulationOutput(app.modelName);
            ts = extractTimetable(simOut.yout);
            xv = []; yv = []; zv = [];
            for its = 1:length(ts)
                idx = find(ts{its}.Time >= app.simTimeAtLastPostStep);
                switch ts{its}.Name
                    case 'x'
                        xv = ts{its}.Data(idx);
                    case 'y'
                        yv = ts{its}.Data(idx);
                    case 'z'
                        zv = ts{its}.Data(idx);
                end
            end
            addpoints(app.hLine,xv,yv,zv);
            [xv, yv, zv] = getpoints(app.hLine);
            set(app.hTail,'XData',xv(1),'YData',yv(1),'ZData',zv(1));
            set(app.hHead,'XData',xv(end),'YData',yv(end),'ZData',zv(end));
            drawnow limitrate;
            app.simTimeAtLastPostStep = simTime;
end

Test in App Designer

Before deploying the application, ensure that the app runs in the App Designer. Click Simulate to verify that the application works by simulating the model for different values.

Compile App for Deployment

You can use the App Designer to compile and deploy the app. You can also use the deploytool function. For more information on compiling and deploying with the App Designer, see Develop Apps Using App Designer, Web Apps and Application Compiler.

To compile the app in this example, use the mcc command followed by the app name.

mcc -m LorenzSystemApp

See Also

| | | | | | | |

Related Topics