Skip to content

Commit

Permalink
adding event support and docs, test
Browse files Browse the repository at this point in the history
  • Loading branch information
cgutsche committed Jan 17, 2024
1 parent fbcb985 commit 42c1e0f
Show file tree
Hide file tree
Showing 3 changed files with 96 additions and 8 deletions.
57 changes: 56 additions & 1 deletion docs/src/basics/MTKModel_Connector.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,8 @@ equations.
- `@parameters`: for specifying the symbolic parameters
- `@structural_parameters`: for specifying non-symbolic parameters
- `@variables`: for specifying the states
- `@continuous_events`: for specifying a list of continuous events
- `@discrete_events`: for specifying a list of discrete events

Let's explore these in more detail with the following example:

Expand Down Expand Up @@ -162,6 +164,59 @@ getdefault(model_c4.model_a.k_array[2])

- List all the equations here

#### `@continuous_events` begin block

- Defining continuous events as described [here](https://docs.sciml.ai/ModelingToolkit/stable/basics/Events/#Continuous-Events).
- If this block is not defined in the model, no continuous events will be added.

```@example mtkmodel-example
using ModelingToolkit
@mtkmodel M begin
@parameters begin
k
end
@variables begin
x(t)
y(t)
end
@equations begin
x ~ k * D(x)
D(y) ~ -k
end
@continuous_events begin
[x ~ 1.5] => [x ~ 5, y ~ 5]
[t ~ 4] => [x ~ 10]
end
end
```

#### `@discrete_events` begin block

- Defining discrete events as described [here](https://docs.sciml.ai/ModelingToolkit/stable/basics/Events/#Discrete-events-support).
- If this block is not defined in the model, no discrete events will be added.

```@example mtkmodel-example
using ModelingToolkit
@mtkmodel M begin
@parameters begin
k
end
@variables begin
x(t)
y(t)
end
@equations begin
x ~ k * D(x)
D(y) ~ -k
end
@discrete_events begin
(t == 1.5) => [x ~ x + 5, y ~ 5]
end
end
```

#### A begin block

- Any other Julia operations can be included with dedicated begin blocks.
Expand Down Expand Up @@ -351,4 +406,4 @@ Using ternary operator or if-elseif-else statement, conditional initial guesses
p = flag ? 1 : 2
end
end
```
```
15 changes: 9 additions & 6 deletions src/systems/model_parsing.jl
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,6 @@ function _model_macro(mod, name, expr, isconnector)
gui_metadata = isassigned(icon) > 0 ? GUIMetadata(GlobalRef(mod, name), icon[]) :
GUIMetadata(GlobalRef(mod, name))


sys = :($ODESystem($Equation[equations...], $iv, variables, parameters;
name, systems, gui_metadata = $gui_metadata))

Expand All @@ -105,12 +104,15 @@ function _model_macro(mod, name, expr, isconnector)
isconnector && push!(exprs.args,
:($Setfield.@set!(var"#___sys___".connector_type=$connector_type(var"#___sys___"))))

!(c_evts==[]) && push!(exprs.args,
:($Setfield.@set!(var"#___sys___".continuous_events=$SymbolicContinuousCallback.([$(c_evts...)]))))

!(d_evts==[]) && push!(exprs.args,
:($Setfield.@set!(var"#___sys___".discrete_events=$SymbolicDiscreteCallback.([$(d_evts...)]))))
!(c_evts == []) && push!(exprs.args,
:($Setfield.@set!(var"#___sys___".continuous_events=$SymbolicContinuousCallback.([
$(c_evts...),
]))))

!(d_evts == []) && push!(exprs.args,
:($Setfield.@set!(var"#___sys___".discrete_events=$SymbolicDiscreteCallback.([
$(d_evts...),
]))))

f = :($(Symbol(:__, name, :__))(; name, $(kwargs...)) = $exprs)
:($name = $Model($f, $dict, $isconnector))
Expand Down Expand Up @@ -636,6 +638,7 @@ function parse_discrete_events!(d_evts, dict, body)
dict[:discrete_events] = []
Base.remove_linenums!(body)
for arg in body.args
push!(d_evts, arg)
push!(dict[:discrete_events], readable_code.(d_evts)...)
end
end
Expand Down
32 changes: 31 additions & 1 deletion test/model_parsing.jl
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,36 @@ end
@test A.structure[:components] == [[:cc, :C]]
end

@testset "Event handeling in MTKModel" begin
@mtkmodel M begin
@variables begin
x(t)
y(t)
z(t)
end
@equations begin
x ~ -D(x)
D(y) ~ 0
D(z) ~ 0
end
@continuous_events begin
[x ~ 1.5] => [x ~ 5, y ~ 1]
end
@discrete_events begin
(t == 1.5) => [x ~ x + 5, z ~ 2]
end
end

@mtkbuild model = M()
u0 = [model.x => 10, model.y => 0, model.z => 0]

prob = ODEProblem(model, u0, (0, 5.0))
sol = solve(prob, tstops = [1.5])

@test isequal(sol[model.y][end], 1.0)
@test isequal(sol[model.z][end], 2.0)
end

# Ensure that modules consisting MTKModels with component arrays and icons of
# `Expr` type and `unit` metadata can be precompiled.
module PrecompilationTest
Expand Down Expand Up @@ -538,4 +568,4 @@ end

@test Equation[ternary_true.ternary_parameter_true ~ 0] == equations(ternary_true)
@test Equation[ternary_false.ternary_parameter_false ~ 0] == equations(ternary_false)
end
end

0 comments on commit 42c1e0f

Please sign in to comment.