#![allow(dead_code)]
use gridoxide::dynamics::json::{
AvrSpec, DynamicsData, DynamicsDocument, EventSpec, GovSpec, MachineSpec, UnitSpec,
};
use gridoxide::dynamics::models::Limits;
use gridoxide::dynamics::models::avr::SexsParams;
use gridoxide::dynamics::models::gov::Tgov1Params;
use gridoxide::dynamics::models::machine::GenRoundParams;
use gridoxide::json::NetworkData;
use gridoxide::types::{Bus, BusType, Line};
pub const S_BASE: f64 = 100.0;
pub const STATES_PER_UNIT: usize = 10;
fn bus(idx: usize, bus_type: BusType, p: f64, q: f64) -> Bus {
Bus {
idx,
bus_type,
voltage_mag: 1.0,
voltage_ang: 0.0,
p_spec: p,
q_spec: q,
q_min: f64::NEG_INFINITY,
q_max: f64::INFINITY,
u_rated: 1.0,
zip_terms: Vec::new(),
}
}
pub fn ring(n_bus: usize, spread: f64) -> DynamicsDocument {
let mut buses = Vec::with_capacity(n_bus);
let mut units = Vec::new();
for i in 0..n_bus {
let generating = i % 2 == 0;
let kind = if i == 0 {
BusType::Slack
} else if generating {
BusType::PV
} else {
BusType::PQ
};
let p = if generating { 0.30 } else { -0.30 };
buses.push(bus(i, kind, p, if generating { 0.0 } else { -0.08 }));
if generating {
let h = 5.0 * (1.0 + spread * i as f64 / n_bus as f64);
units.push(UnitSpec {
id: format!("G{i}"),
bus: i,
p: None,
q: None,
machine: MachineSpec::GenRound(GenRoundParams {
h,
d: 1.0,
ra: 0.003,
xd: 1.8,
xq: 1.7,
xdp: 0.30,
xqp: 0.55,
xdpp: 0.22,
xqpp: 0.25,
xl: 0.15,
td0p: 8.0,
tq0p: 0.4,
td0pp: 0.03,
tq0pp: 0.05,
mbase: S_BASE,
}),
avr: Some(AvrSpec::Sexs(SexsParams {
k: 200.0,
ta: 0.1,
tb: 1.0,
te: 0.05,
limits: Limits::NONE,
})),
gov: Some(GovSpec::Tgov1(Tgov1Params {
r: 0.05,
t1: 0.5,
t2: 1.0,
t3: 5.0,
dt: 0.0,
limits: Limits::NONE,
rate: Limits::NONE,
})),
pss: None,
});
}
}
let lines = (0..n_bus)
.map(|i| Line {
from: i,
to: (i + 1) % n_bus,
r: 0.002,
x: 0.02,
b_shunt: 0.0,
g_shunt: 0.0,
})
.collect();
DynamicsDocument {
network: NetworkData { buses, lines },
dynamics: DynamicsData {
s_base: S_BASE,
f_nom: 50.0,
speed_voltages: false,
units,
loads: Vec::new(),
fixed_buses: Vec::new(),
events: Vec::new(),
relays: Vec::new(),
},
}
}
pub fn ring_with_fault(n_bus: usize, spread: f64) -> DynamicsDocument {
let mut document = ring(n_bus, spread);
document.dynamics.events = vec![
EventSpec::BusFault {
t: 1.0,
bus: 1,
y: None,
},
EventSpec::ClearFault { t: 1.08, bus: 1 },
];
document
}