controls-kt/demo/notebooks/constructor.ipynb

4.9 KiB

In [ ]:
//import space.kscience.controls.jupyter.ControlsJupyter

//USE(ControlsJupyter())
USE{
    repositories{
        maven("https://repo.kotlin.link")
    }
    dependencies{
        implementation("space.kscience:controls-jupyter-jvm:0.3.0-dev-2")
    }
}
In [ ]:
class LinearDrive(
    context: Context,
    state: DoubleRangeState,
    mass: Double,
    pidParameters: PidParameters,
    meta: Meta = Meta.EMPTY,
) : DeviceConstructor(context.request(DeviceManager), meta) {

    val drive by device(VirtualDrive.factory(mass, state))
    val pid by device(PidRegulator(drive, pidParameters))

    val start by device(LimitSwitch.factory(state.atStartState))
    val end by device(LimitSwitch.factory(state.atEndState))


    val position by property(state)
    var target by mutableProperty(pid.mutablePropertyAsState(Regulator.target, 0.0))
}
In [ ]:
import kotlin.time.Duration.Companion.milliseconds
import kotlin.time.Duration.Companion.seconds

val state = DoubleRangeState(0.0, -5.0..5.0)

val pidParameters = PidParameters(
    kp = 2.5,
    ki = 0.0,
    kd = -0.1,
    timeStep = 0.005.seconds
)

val device = context.install("device", LinearDrive(context, state, 0.005, pidParameters))
In [ ]:
val job = device.run {
    val clock = context.clock
    val clockStart = clock.now()
    doRecurring(10.milliseconds) {
        val timeFromStart = clock.now() - clockStart
        val t = timeFromStart.toDouble(DurationUnit.SECONDS)
        val freq = 0.1

        target = 5 * sin(2.0 * PI * freq * t) +
                sin(2 * PI * 21 * freq * t + 0.02 * (timeFromStart / pidParameters.timeStep))
    }
}
In [ ]:
val maxAge = 10.seconds


VisionForge.fragment {
    vision {
        plotly {
            
            plotDeviceProperty(device.pid, Regulator.target.name, maxAge = maxAge) {
                name = "target"
            }
            
            plotNumberState(context, state, maxAge = maxAge) {
                name = "real position"
            }
            
            plotDeviceProperty(device.pid, Regulator.position.name, maxAge = maxAge) {
                name = "read position"
            }
        }
    }

    vision {
        plotly {
            plotDeviceProperty(device.start, LimitSwitch.locked.name, maxAge = maxAge) {
                name = "start measured"
                mode = ScatterMode.markers
            }
            plotDeviceProperty(device.end, LimitSwitch.locked.name, maxAge = maxAge) {
                name = "end measured"
                mode = ScatterMode.markers
            }
        }
    }
}
In [ ]:
import kotlinx.coroutines.cancel

job.cancel()
In [ ]:

In [ ]: