Skip to content
LIBRARY
Sources.Tests.IntegerStep.md

Sources.Tests.IntegerStep

Test that validates the IntegerStep source.

An Integer step source is converted to Real via IntegerToReal so its step trajectory can be snapshotted. The step occurs at startTime = 0.5:

  • case1: offset = 1, height = 2, so toReal.y steps 1.0 -> 3.0.

  • case2: offset = 1, height = -3, so toReal.y steps 1.0 -> -2.0.

Usage

BlockComponents.Sources.Tests.IntegerStep()

Behavior

julia
using BlockComponents #hide
using ModelingToolkit #hide
@named sys = BlockComponents.Sources.Tests.IntegerStep() #hide
let eqs = full_equations(sys); Base.length(eqs) > 25 ? nothing : eqs end #hide
<< @example-block not executed in draft mode >>

Source

dyad
"""
Test that validates the IntegerStep source.

An Integer step source is converted to Real via `IntegerToReal` so its step
trajectory can be snapshotted. The step occurs at `startTime = 0.5`:
- `case1`: `offset = 1`, `height = 2`, so `toReal.y` steps 1.0 -> 3.0.
- `case2`: `offset = 1`, `height = -3`, so `toReal.y` steps 1.0 -> -2.0.
"""
test component IntegerStep
  "Generates an Integer step signal"
  signal = BlockComponents.Sources.IntegerStep(startTime = 0.5, offset = 1, height = 2) {
    "Dyad": {
      "placement": {
        "diagram": {"iconName": "default", "x1": 20, "y1": 20, "x2": 120, "y2": 120, "rot": 0}
      }
    }
  }
  "Converts the Integer output to Real"
  toReal = BlockComponents.Math.IntegerToReal() {
    "Dyad": {
      "placement": {
        "diagram": {"iconName": "default", "x1": 155, "y1": 20, "x2": 255, "y2": 120, "rot": 0}
      }
    }
  }
relations
  "Connects the Integer step output to the converter"
  connect(signal.y, toReal.u) {"Dyad": {"edges": [{"S": 1, "M": [], "E": 2}], "renderStyle": "standard"}}
metadata {
  "Dyad": {
    "icons": {"default": "dyad://BlockComponents/Example.svg"},
    "tests": {
      "case1": {"stop": 1, "expect": {"signals": ["toReal.y"]}},
      "case2": {
        "stop": 1,
        "params": {"signal.height": -3},
        "expect": {"signals": ["toReal.y"]}
      }
    }
  }
}
end
Flattened Source
dyad
"""
Test that validates the IntegerStep source.

An Integer step source is converted to Real via `IntegerToReal` so its step
trajectory can be snapshotted. The step occurs at `startTime = 0.5`:
- `case1`: `offset = 1`, `height = 2`, so `toReal.y` steps 1.0 -> 3.0.
- `case2`: `offset = 1`, `height = -3`, so `toReal.y` steps 1.0 -> -2.0.
"""
test component IntegerStep
  "Generates an Integer step signal"
  signal = BlockComponents.Sources.IntegerStep(startTime = 0.5, offset = 1, height = 2) {
    "Dyad": {
      "placement": {
        "diagram": {"iconName": "default", "x1": 20, "y1": 20, "x2": 120, "y2": 120, "rot": 0}
      }
    }
  }
  "Converts the Integer output to Real"
  toReal = BlockComponents.Math.IntegerToReal() {
    "Dyad": {
      "placement": {
        "diagram": {"iconName": "default", "x1": 155, "y1": 20, "x2": 255, "y2": 120, "rot": 0}
      }
    }
  }
relations
  "Connects the Integer step output to the converter"
  connect(signal.y, toReal.u) {"Dyad": {"edges": [{"S": 1, "M": [], "E": 2}], "renderStyle": "standard"}}
metadata {
  "Dyad": {
    "icons": {"default": "dyad://BlockComponents/Example.svg"},
    "tests": {
      "case1": {"stop": 1, "expect": {"signals": ["toReal.y"]}},
      "case2": {
        "stop": 1,
        "params": {"signal.height": -3},
        "expect": {"signals": ["toReal.y"]}
      }
    }
  }
}
end


Test Cases

julia
using BlockComponents
using DyadInterface: TransientAnalysis, rebuild_sol, ODEAlg
using ModelingToolkit: toggle_namespacing, get_initial_conditions, @named
using CSV, DataFrames, Plots

snapshotsdir = joinpath(dirname(dirname(pathof(BlockComponents))), "test", "snapshots")
<< @setup-block not executed in draft mode >>

Test Case case1

julia
@named model_case1 = BlockComponents.Sources.Tests.IntegerStep()
model_case1 = toggle_namespacing(model_case1, false)

model_case1 = toggle_namespacing(model_case1, true)
result_case1 = TransientAnalysis(; model = model_case1, alg = ODEAlg.Auto(), start = 0e+0, stop = 1e+0, abstol=1e-6, reltol=1e-6)
sol_case1 = rebuild_sol(result_case1)
<< @setup-block not executed in draft mode >>
julia
df_case1 = DataFrame(:t => sol_case1[:t], :actual => sol_case1[model_case1.toReal.y])
dfr_case1 = try CSV.read(joinpath(snapshotsdir, "BlockComponents.Sources.Tests.IntegerStep_case1_sig0.ref"), DataFrame); catch e; nothing; end
plt = plot(sol_case1, idxs=[model_case1.toReal.y], width=2, label="Actual value of toReal.y")
if !isnothing(dfr_case1)
  scatter!(plt, dfr_case1.t, dfr_case1.expected, mc=:red, ms=3, label="Expected value of toReal.y")
end
<< @setup-block not executed in draft mode >>
julia
plt
<< @example-block not executed in draft mode >>

Test Case case2

julia
@named model_case2 = BlockComponents.Sources.Tests.IntegerStep(signal.height=-3)
model_case2 = toggle_namespacing(model_case2, false)

model_case2 = toggle_namespacing(model_case2, true)
result_case2 = TransientAnalysis(; model = model_case2, alg = ODEAlg.Auto(), start = 0e+0, stop = 1e+0, abstol=1e-6, reltol=1e-6)
sol_case2 = rebuild_sol(result_case2)
<< @setup-block not executed in draft mode >>
julia
df_case2 = DataFrame(:t => sol_case2[:t], :actual => sol_case2[model_case2.toReal.y])
dfr_case2 = try CSV.read(joinpath(snapshotsdir, "BlockComponents.Sources.Tests.IntegerStep_case2_sig0.ref"), DataFrame); catch e; nothing; end
plt = plot(sol_case2, idxs=[model_case2.toReal.y], width=2, label="Actual value of toReal.y")
if !isnothing(dfr_case2)
  scatter!(plt, dfr_case2.t, dfr_case2.expected, mc=:red, ms=3, label="Expected value of toReal.y")
end
<< @setup-block not executed in draft mode >>
julia
plt
<< @example-block not executed in draft mode >>