A modular sliding mode control toolbox for Python
Project description
OpenSMC — Sliding Mode Control for Python
The first and only pip install-able sliding mode control toolbox.
11 surfaces | 5 reaching laws | 9 plants | 17 controllers | 7 estimators | 5 Gymnasium environments
Install
pip install opensmc # Core (numpy only)
pip install opensmc[viz] # + matplotlib
pip install opensmc[rl] # + gymnasium + stable-baselines3
pip install opensmc[all] # Everything
Quick Start — 6 Lines
import numpy as np
from opensmc.surfaces import LinearSurface
from opensmc.reaching import SuperTwisting
from opensmc.controllers import ClassicalSMC
from opensmc.plants import DoubleIntegrator
from opensmc.simulator import Simulator
from opensmc import metrics
ctrl = ClassicalSMC(surface=LinearSurface(c=10), reaching=SuperTwisting(k1=15, k2=10))
result = Simulator(dt=1e-4, T=5.0).run(ctrl, DoubleIntegrator(),
ref_fn=lambda t: np.array([1.0, 0.0]))
print(f"RMSE: {metrics.rmse(result):.4f}, Settling: {metrics.settling_time(result):.3f}s")
Why OpenSMC?
Before OpenSMC: Every SMC paper reimplements controllers from scratch. No standard benchmarks. No way to compare methods fairly.
After OpenSMC: Swap any surface, reaching law, or plant with a one-line change. Compare 15 controllers on 9 plants with standardized metrics. Bridge SMC with reinforcement learning via Gymnasium.
Surface × Reaching Law × Plant × Estimator = Controller
(11) (5) (9) (7)
Zero competitors. No other Python SMC package exists on PyPI or GitHub.
Components
Sliding Surfaces (11)
| Surface | Type | Key Property |
|---|---|---|
LinearSurface |
Linear | Asymptotic convergence |
TerminalSurface |
Terminal | Finite-time convergence |
NonsingularTerminalSurface |
Nonsingular | Singularity-free finite-time |
FastTerminalSurface |
Fast Terminal | Fast + finite-time |
IntegralTerminalSurface |
Integral Terminal | Integral compensation |
IntegralSlidingSurface |
Integral | Eliminates reaching phase |
PIDSurface |
PID-like | PID action on sliding surface |
HierarchicalSurface |
Hierarchical | For underactuated systems |
NonlinearDampingSurface |
Nonlinear Damping | Enhanced stability margin |
GlobalSurface |
Global | No reaching phase, no overshoot |
PredefinedTimeSurface |
Predefined-Time | User-set convergence time |
Reaching Laws (5)
| Reaching Law | Continuity | Chattering |
|---|---|---|
ConstantRate |
Discontinuous | Yes |
ExponentialRate |
Discontinuous | Reduced |
PowerRate |
Discontinuous | Reduced |
SuperTwisting |
Continuous | No |
Saturation |
Continuous | No |
Plants (9)
| Plant | States | Inputs | DOF | Underactuated |
|---|---|---|---|---|
DoubleIntegrator |
2 | 1 | 1 | No |
InvertedPendulum |
4 | 1 | 2 | Yes |
SinglePendulumCrane |
4 | 1 | 2 | Yes |
DoublePendulumCrane |
6 | 1 | 3 | Yes |
Quadrotor6DOF |
12 | 4 | 6 | Yes |
DualStageNanopositioner |
4 | 1 | 2 | No |
TwoLinkArm |
4 | 2 | 2 | No |
PMSM |
4 | 2 | 2 | No |
SurfaceVessel |
6 | 3 | 3 | No |
Controllers (17)
| Controller | Type | Reference |
|---|---|---|
ClassicalSMC |
Generic | Utkin (1977) |
AdaptiveSMC |
Adaptive gain | Liu & Wang (2013) |
DynamicSMC |
Dynamic | Liu & Wang (2013) |
AggregatedHSMC |
Hierarchical | Qian & Yi (2015) |
IncrementalHSMC |
Hierarchical | Qian & Yi (2015) |
CombiningHSMC |
Hierarchical | Qian & Yi (2015) |
DiscreteSMC |
Discrete-time | Gao (1995) |
FixedTimeSMC |
Fixed-time | Polyakov (2012) |
FuzzySMC |
Fuzzy logic | Khanesar (2021) |
ITSMC |
Learning-based | Al Ghanimi (2026) |
NFTSMC |
Finite-time | Al Ghanimi (2026) |
TwistingSMC |
2nd-order HOSMC | Levant (1993) |
QuasiContinuous2SMC |
Quasi-continuous | Levant (2005) |
NestedHOSMC |
Arbitrary-order | Levant (2003) |
QuasiContinuousHOSMC |
Arbitrary-order | Levant (2005) |
PID |
Baseline | — |
LQR |
Baseline | — |
Estimators (7)
NoEstimator · DisturbanceObserver · ExtendedStateObserver · HighGainObserver · IntegralChainDifferentiator · LevantDifferentiator · RBF_ELM
Gymnasium Environments
5 RL-ready environments, compatible with Stable-Baselines3:
import gymnasium as gym
import opensmc # registers environments
env = gym.make("OpenSMC/DoubleIntegrator-v0") # 2 states, 1 input
env = gym.make("OpenSMC/InvertedPendulum-v0") # 4 states, 1 input
env = gym.make("OpenSMC/Crane-v0") # 4 states, 1 input
env = gym.make("OpenSMC/Quadrotor-v0") # 12 states, 4 inputs
env = gym.make("OpenSMC/PMSM-v0") # 5 obs (4 states + ref), 2 inputs
Train an RL controller in 3 lines
from stable_baselines3 import PPO
env = gym.make("OpenSMC/DoubleIntegrator-v0", disturbance=1.0)
model = PPO("MlpPolicy", env).learn(50_000)
Use RL as a sliding surface
from opensmc.rl import RLDiscoveredSurface
surface = RLDiscoveredSurface("my_trained_model")
ctrl = ClassicalSMC(surface=surface, reaching=SuperTwisting(k1=15, k2=10))
Benchmarking
Compare any controllers on any plant with standardized metrics:
from opensmc import metrics
# 12 metrics: rmse, mae, ise, iae, settling_time, overshoot,
# rise_time, control_effort, chattering_index,
# reaching_time, steady_state_error, energy_efficiency
Modularity — The Core Idea
Every component is interchangeable. Mix any surface with any reaching law:
from opensmc.surfaces import TerminalSurface, FastTerminalSurface
from opensmc.reaching import SuperTwisting, ConstantRate
from opensmc.controllers import ClassicalSMC
# Same controller class, different behaviors:
ctrl_a = ClassicalSMC(surface=TerminalSurface(), reaching=SuperTwisting())
ctrl_b = ClassicalSMC(surface=FastTerminalSurface(), reaching=ConstantRate())
Citation
If you use OpenSMC in your research, please cite:
@article{alghanimi2026opensmc,
title = {OpenSMC: A Modular Open-Source Sliding Mode Control Toolbox},
author = {Al Ghanimi, Ali},
journal = {SoftwareX},
year = {2026},
doi = {10.5281/zenodo.19029180},
note = {Under review}
}
License
MIT License. See LICENSE for details.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file opensmc-2.0.0.tar.gz.
File metadata
- Download URL: opensmc-2.0.0.tar.gz
- Upload date:
- Size: 71.7 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
84070090ce26bb5ff64f81043608e7a99478feec2c145a37e2ae62c7441c3e13
|
|
| MD5 |
9ed4fa24d3ce33c2adcd55c7b0f07323
|
|
| BLAKE2b-256 |
02453f7255bc2a383bf4492aaf0b69b6c909cb2555c4756905361e51e2523441
|
File details
Details for the file opensmc-2.0.0-py3-none-any.whl.
File metadata
- Download URL: opensmc-2.0.0-py3-none-any.whl
- Upload date:
- Size: 91.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.5
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b573d935e9c4e4a3a753f765d8dea9d57fbf606f103147a3755dab3226aeacc4
|
|
| MD5 |
c8dbc052677186a01739938012dfec2b
|
|
| BLAKE2b-256 |
07bbd365820ea7c76599abd28ef55fe4a2c747aa1a12e0e49de55f46a71945de
|