Ticket #2738: ActuatorLinearSystemsNoise.mo

File ActuatorLinearSystemsNoise.mo, 107.0 KB (added by Martin Sjölund, 10 years ago)
Line 
1package ModelicaServices
2 package Machine
3 final constant Real eps = 1.e-15;
4 final constant Real small = 1.e-60;
5 final constant Real inf = 1.e+60;
6 final constant Integer Integer_inf = OpenModelica.Internal.Architecture.integerMax();
7 end Machine;
8end ModelicaServices;
9
10package Modelica
11 package Blocks
12 package Continuous
13 block Derivative
14 parameter Real k(unit = "1") = 1;
15 parameter .Modelica.SIunits.Time T(min = Modelica.Constants.small) = 0.01;
16 parameter Modelica.Blocks.Types.Init initType = Modelica.Blocks.Types.Init.NoInit;
17 parameter Real x_start = 0;
18 parameter Real y_start = 0;
19 extends .Modelica.Blocks.Interfaces.SISO;
20 output Real x(start = x_start);
21 protected
22 parameter Boolean zeroGain = abs(k) < Modelica.Constants.eps;
23 initial equation
24 if initType == .Modelica.Blocks.Types.Init.SteadyState then
25 der(x) = 0;
26 elseif initType == .Modelica.Blocks.Types.Init.InitialState then
27 x = x_start;
28 elseif initType == .Modelica.Blocks.Types.Init.InitialOutput then
29 if zeroGain then
30 x = u;
31 else
32 y = y_start;
33 end if;
34 end if;
35 equation
36 der(x) = if zeroGain then 0 else (u - x) / T;
37 y = if zeroGain then 0 else k / T * (u - x);
38 end Derivative;
39
40 block FirstOrder
41 parameter Real k(unit = "1") = 1;
42 parameter .Modelica.SIunits.Time T(start = 1);
43 parameter Modelica.Blocks.Types.Init initType = Modelica.Blocks.Types.Init.NoInit;
44 parameter Real y_start = 0;
45 extends .Modelica.Blocks.Interfaces.SISO(y(start = y_start));
46 initial equation
47 if initType == .Modelica.Blocks.Types.Init.SteadyState then
48 der(y) = 0;
49 elseif initType == .Modelica.Blocks.Types.Init.InitialState or initType == .Modelica.Blocks.Types.Init.InitialOutput then
50 y = y_start;
51 end if;
52 equation
53 der(y) = (k * u - y) / T;
54 end FirstOrder;
55
56 block PI
57 parameter Real k(unit = "1") = 1;
58 parameter .Modelica.SIunits.Time T(start = 1, min = Modelica.Constants.small);
59 parameter Modelica.Blocks.Types.Init initType = Modelica.Blocks.Types.Init.NoInit;
60 parameter Real x_start = 0;
61 parameter Real y_start = 0;
62 extends .Modelica.Blocks.Interfaces.SISO;
63 output Real x(start = x_start);
64 initial equation
65 if initType == .Modelica.Blocks.Types.Init.SteadyState then
66 der(x) = 0;
67 elseif initType == .Modelica.Blocks.Types.Init.InitialState then
68 x = x_start;
69 elseif initType == .Modelica.Blocks.Types.Init.InitialOutput then
70 y = y_start;
71 end if;
72 equation
73 der(x) = u / T;
74 y = k * (x + u);
75 end PI;
76 end Continuous;
77
78 package Interfaces
79 connector RealInput = input Real;
80 connector RealOutput = output Real;
81
82 partial block SO
83 RealOutput y;
84 end SO;
85
86 partial block MO
87 parameter Integer nout(min = 1) = 1;
88 RealOutput[nout] y;
89 end MO;
90
91 partial block SISO
92 RealInput u;
93 RealOutput y;
94 end SISO;
95
96 partial block SI2SO
97 RealInput u1;
98 RealInput u2;
99 RealOutput y;
100 end SI2SO;
101
102 partial block MIMO
103 parameter Integer nin = 1;
104 parameter Integer nout = 1;
105 RealInput[nin] u;
106 RealOutput[nout] y;
107 end MIMO;
108
109 partial block MIMOs
110 parameter Integer n = 1;
111 RealInput[n] u;
112 RealOutput[n] y;
113 end MIMOs;
114
115 partial block SignalSource
116 extends SO;
117 parameter Real offset = 0;
118 parameter .Modelica.SIunits.Time startTime = 0;
119 end SignalSource;
120 end Interfaces;
121
122 package Math
123 block Gain
124 parameter Real k(start = 1, unit = "1");
125 .Modelica.Blocks.Interfaces.RealInput u;
126 .Modelica.Blocks.Interfaces.RealOutput y;
127 equation
128 y = k * u;
129 end Gain;
130
131 block Feedback
132 .Modelica.Blocks.Interfaces.RealInput u1;
133 .Modelica.Blocks.Interfaces.RealInput u2;
134 .Modelica.Blocks.Interfaces.RealOutput y;
135 equation
136 y = u1 - u2;
137 end Feedback;
138
139 block Add
140 extends .Modelica.Blocks.Interfaces.SI2SO;
141 parameter Real k1 = +1;
142 parameter Real k2 = +1;
143 equation
144 y = k1 * u1 + k2 * u2;
145 end Add;
146 end Math;
147
148 package Nonlinear
149 block SlewRateLimiter
150 extends Modelica.Blocks.Interfaces.SISO;
151 parameter Modelica.SIunits.DampingCoefficient Rising(min = .Modelica.Constants.small) = 1;
152 parameter Modelica.SIunits.DampingCoefficient Falling(min = -.Modelica.Constants.small) = -Rising;
153 parameter Modelica.SIunits.Time Td(min = .Modelica.Constants.small) = 0.001;
154 parameter Boolean strict = false;
155 initial equation
156 y = u;
157 equation
158 if strict then
159 der(y) = smooth(1, noEvent(min(max((u - y) / Td, Falling), Rising)));
160 else
161 der(y) = smooth(1, min(max((u - y) / Td, Falling), Rising));
162 end if;
163 end SlewRateLimiter;
164 end Nonlinear;
165
166 package Routing
167 block DeMultiplex2
168 parameter Integer n1 = 1;
169 parameter Integer n2 = 1;
170 Modelica.Blocks.Interfaces.RealInput[n1 + n2] u;
171 Modelica.Blocks.Interfaces.RealOutput[n1] y1;
172 Modelica.Blocks.Interfaces.RealOutput[n2] y2;
173 equation
174 [u] = [y1; y2];
175 end DeMultiplex2;
176 end Routing;
177
178 package Sources
179 block Constant
180 parameter Real k(start = 1);
181 extends .Modelica.Blocks.Interfaces.SO;
182 equation
183 y = k;
184 end Constant;
185
186 block Step
187 parameter Real height = 1;
188 extends .Modelica.Blocks.Interfaces.SignalSource;
189 equation
190 y = offset + (if time < startTime then 0 else height);
191 end Step;
192 end Sources;
193
194 package Types
195 type Init = enumeration(NoInit, SteadyState, InitialState, InitialOutput);
196 end Types;
197 end Blocks;
198
199 package Electrical
200 package Analog
201 package Basic
202 model Ground
203 Interfaces.Pin p;
204 equation
205 p.v = 0;
206 end Ground;
207
208 model Resistor
209 parameter Modelica.SIunits.Resistance R(start = 1);
210 parameter Modelica.SIunits.Temperature T_ref = 300.15;
211 parameter Modelica.SIunits.LinearTemperatureCoefficient alpha = 0;
212 extends Modelica.Electrical.Analog.Interfaces.OnePort;
213 extends Modelica.Electrical.Analog.Interfaces.ConditionalHeatPort(T = T_ref);
214 Modelica.SIunits.Resistance R_actual;
215 equation
216 assert(1 + alpha * (T_heatPort - T_ref) >= Modelica.Constants.eps, "Temperature outside scope of model!");
217 R_actual = R * (1 + alpha * (T_heatPort - T_ref));
218 v = R_actual * i;
219 LossPower = v * i;
220 end Resistor;
221
222 model Inductor
223 extends Interfaces.OnePort(i(start = 0));
224 parameter .Modelica.SIunits.Inductance L(start = 1);
225 equation
226 L * der(i) = v;
227 end Inductor;
228 end Basic;
229
230 package Interfaces
231 connector Pin
232 Modelica.SIunits.Voltage v;
233 flow Modelica.SIunits.Current i;
234 end Pin;
235
236 connector PositivePin
237 Modelica.SIunits.Voltage v;
238 flow Modelica.SIunits.Current i;
239 end PositivePin;
240
241 connector NegativePin
242 Modelica.SIunits.Voltage v;
243 flow Modelica.SIunits.Current i;
244 end NegativePin;
245
246 partial model OnePort
247 .Modelica.SIunits.Voltage v;
248 .Modelica.SIunits.Current i;
249 PositivePin p;
250 NegativePin n;
251 equation
252 v = p.v - n.v;
253 0 = p.i + n.i;
254 i = p.i;
255 end OnePort;
256
257 partial model ConditionalHeatPort
258 parameter Boolean useHeatPort = false;
259 parameter Modelica.SIunits.Temperature T = 293.15;
260 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPort(T(start = T) = T_heatPort, Q_flow = -LossPower) if useHeatPort;
261 Modelica.SIunits.Power LossPower;
262 Modelica.SIunits.Temperature T_heatPort;
263 equation
264 if not useHeatPort then
265 T_heatPort = T;
266 end if;
267 end ConditionalHeatPort;
268 end Interfaces;
269
270 package Sensors
271 model VoltageSensor
272 Interfaces.PositivePin p;
273 Interfaces.NegativePin n;
274 Modelica.Blocks.Interfaces.RealOutput v(unit = "V");
275 equation
276 p.i = 0;
277 n.i = 0;
278 v = p.v - n.v;
279 end VoltageSensor;
280
281 model CurrentSensor
282 Interfaces.PositivePin p;
283 Interfaces.NegativePin n;
284 Modelica.Blocks.Interfaces.RealOutput i(unit = "A");
285 equation
286 p.v = n.v;
287 p.i = i;
288 n.i = -i;
289 end CurrentSensor;
290 end Sensors;
291
292 package Sources
293
294 model SignalCurrent
295 Interfaces.PositivePin p;
296 Interfaces.NegativePin n;
297 .Modelica.SIunits.Voltage v;
298 Modelica.Blocks.Interfaces.RealInput i(unit = "A");
299 equation
300 v = p.v - n.v;
301 0 = p.i + n.i;
302 i = p.i;
303 end SignalCurrent;
304 end Sources;
305 end Analog;
306
307 package Machines
308 package BasicMachines
309 package SynchronousInductionMachines
310 model SM_PermanentMagnet
311 extends Machines.Interfaces.PartialBasicInductionMachine(Lssigma(start = 0.1 / (2 * pi * fsNominal)), final idq_ss = airGapR.i_ss, final idq_sr = airGapR.i_sr, final idq_rs = airGapR.i_rs, final idq_rr = airGapR.i_rr, redeclare final Machines.Thermal.SynchronousInductionMachines.ThermalAmbientSMPM thermalAmbient(final useDamperCage = useDamperCage, final Tr = TrOperational, final Tpm = TpmOperational), redeclare final Machines.Interfaces.InductionMachines.ThermalPortSMPM thermalPort(final useDamperCage = useDamperCage), redeclare final Machines.Interfaces.InductionMachines.ThermalPortSMPM internalThermalPort(final useDamperCage = useDamperCage), redeclare final Machines.Interfaces.InductionMachines.PowerBalanceSMPM powerBalance(final lossPowerRotorWinding = damperCageLossPower, final lossPowerRotorCore = 0, final lossPowerPermanentMagnet = permanentMagnet.lossPower), statorCore(final w = statorCoreParameters.wRef));
312 Modelica.Blocks.Interfaces.RealOutput[2] ir(start = zeros(2), each final quantity = "ElectricCurrent", each final unit = "A") if useDamperCage;
313 Modelica.Blocks.Interfaces.RealOutput[2] idq_dr(each stateSelect = StateSelect.prefer, each final quantity = "ElectricCurrent", each final unit = "A") if useDamperCage;
314 Machines.BasicMachines.Components.AirGapR airGapR(final p = p, final Lmd = Lmd, final Lmq = Lmq, final m = m);
315 final parameter Modelica.SIunits.Temperature TpmOperational = 293.15;
316 parameter Modelica.SIunits.Temperature TrOperational(start = 293.15);
317 parameter Modelica.SIunits.Voltage VsOpenCircuit(start = 112.3);
318 parameter Modelica.SIunits.Inductance Lmd(start = 0.3 / (2 * pi * fsNominal));
319 parameter Modelica.SIunits.Inductance Lmq(start = 0.3 / (2 * pi * fsNominal));
320 parameter Boolean useDamperCage(start = true);
321 parameter Modelica.SIunits.Inductance Lrsigmad(start = 0.05 / (2 * pi * fsNominal));
322 parameter Modelica.SIunits.Inductance Lrsigmaq = Lrsigmad;
323 parameter Modelica.SIunits.Resistance Rrd(start = 0.04);
324 parameter Modelica.SIunits.Resistance Rrq = Rrd;
325 parameter Modelica.SIunits.Temperature TrRef(start = 293.15);
326 parameter Machines.Thermal.LinearTemperatureCoefficient20 alpha20r(start = 0);
327 parameter Machines.Losses.PermanentMagnetLossParameters permanentMagnetLossParameters(IRef(start = 100), wRef(start = 2 * pi * fsNominal / p));
328 Components.PermanentMagnetWithLosses permanentMagnet(final Ie = Ie, final useHeatPort = true, final m = m, final permanentMagnetLossParameters = permanentMagnetLossParameters, final is = is);
329 Machines.BasicMachines.Components.DamperCage damperCage(final Lrsigmad = Lrsigmad, final Lrsigmaq = Lrsigmaq, final Rrd = Rrd, final Rrq = Rrq, final T_ref = TrRef, final alpha = Machines.Thermal.convertAlpha(alpha20r, TrRef), final T = TrRef, final useHeatPort = true) if useDamperCage;
330 protected
331 final parameter Modelica.SIunits.Current Ie = sqrt(2) * VsOpenCircuit / (Lmd * 2 * pi * fsNominal);
332 Modelica.Blocks.Interfaces.RealOutput damperCageLossPower(final quantity = "Power", final unit = "W");
333 equation
334 connect(ir, damperCage.i);
335 connect(idq_dr, damperCage.i);
336 connect(damperCageLossPower, damperCage.lossPower);
337 if not useDamperCage then
338 damperCageLossPower = 0;
339 end if;
340 connect(airGapR.spacePhasor_r, damperCage.spacePhasor_r);
341 connect(airGapR.spacePhasor_r, permanentMagnet.spacePhasor_r);
342 connect(airGapR.support, internalSupport);
343 connect(lssigma.spacePhasor_b, airGapR.spacePhasor_s);
344 connect(airGapR.flange, inertiaRotor.flange_a);
345 connect(permanentMagnet.heatPort, internalThermalPort.heatPortPermanentMagnet);
346 connect(permanentMagnet.flange, inertiaRotor.flange_b);
347 connect(damperCage.heatPort, internalThermalPort.heatPortRotorWinding);
348 connect(internalSupport, permanentMagnet.support);
349 end SM_PermanentMagnet;
350 end SynchronousInductionMachines;
351
352 package Components
353 partial model PartialAirGap
354 parameter Integer m = 3;
355 parameter Integer p(min = 1);
356 output Modelica.SIunits.Torque tauElectrical;
357 Modelica.SIunits.Angle gamma;
358 Modelica.SIunits.Current[2] i_ss;
359 Modelica.SIunits.Current[2] i_sr;
360 Modelica.SIunits.Current[2] i_rs;
361 Modelica.SIunits.Current[2] i_rr;
362 Modelica.SIunits.MagneticFlux[2] psi_ms;
363 Modelica.SIunits.MagneticFlux[2] psi_mr;
364 Real[2, 2] RotationMatrix;
365 Modelica.Mechanics.Rotational.Interfaces.Flange_a flange;
366 Modelica.Mechanics.Rotational.Interfaces.Flange_a support;
367 Machines.Interfaces.SpacePhasor spacePhasor_s;
368 Machines.Interfaces.SpacePhasor spacePhasor_r;
369 equation
370 gamma = p * (flange.phi - support.phi);
371 RotationMatrix = {{+cos(gamma), -sin(gamma)}, {+sin(gamma), +cos(gamma)}};
372 i_ss = spacePhasor_s.i_;
373 i_ss = RotationMatrix * i_sr;
374 i_rr = spacePhasor_r.i_;
375 i_rs = RotationMatrix * i_rr;
376 spacePhasor_s.v_ = der(psi_ms);
377 spacePhasor_r.v_ = der(psi_mr);
378 tauElectrical = m / 2 * p * (spacePhasor_s.i_[2] * psi_ms[1] - spacePhasor_s.i_[1] * psi_ms[2]);
379 flange.tau = -tauElectrical;
380 support.tau = tauElectrical;
381 end PartialAirGap;
382
383 model AirGapR
384 parameter Modelica.SIunits.Inductance Lmd;
385 parameter Modelica.SIunits.Inductance Lmq;
386 extends PartialAirGap;
387 Modelica.SIunits.Current[2] i_mr;
388 protected
389 parameter Modelica.SIunits.Inductance[2, 2] L = {{Lmd, 0}, {0, Lmq}};
390 equation
391 i_mr = i_sr + i_rr;
392 psi_mr = L * i_mr;
393 psi_ms = RotationMatrix * psi_mr;
394 end AirGapR;
395
396 model Inductor
397 parameter Modelica.SIunits.Inductance[2] L;
398 Modelica.SIunits.Voltage[2] v_;
399 Modelica.SIunits.Current[2] i_;
400 Machines.Interfaces.SpacePhasor spacePhasor_a;
401 Machines.Interfaces.SpacePhasor spacePhasor_b;
402 equation
403 spacePhasor_a.i_ + spacePhasor_b.i_ = zeros(2);
404 v_ = spacePhasor_a.v_ - spacePhasor_b.v_;
405 i_ = spacePhasor_a.i_;
406 v_[1] = L[1] * der(i_[1]);
407 v_[2] = L[2] * der(i_[2]);
408 end Inductor;
409
410 model DamperCage
411 parameter Modelica.SIunits.Inductance Lrsigmad;
412 parameter Modelica.SIunits.Inductance Lrsigmaq;
413 parameter Modelica.SIunits.Resistance Rrd;
414 parameter Modelica.SIunits.Resistance Rrq;
415 parameter Modelica.SIunits.Temperature T_ref = 293.15;
416 parameter Modelica.SIunits.LinearTemperatureCoefficient alpha = 0;
417 extends Modelica.Electrical.Analog.Interfaces.ConditionalHeatPort(T = T_ref);
418 Modelica.SIunits.Resistance Rrd_actual;
419 Modelica.SIunits.Resistance Rrq_actual;
420 Modelica.Blocks.Interfaces.RealOutput[2] i(each final quantity = "ElectricCurrent", each final unit = "A") = -spacePhasor_r.i_;
421 Modelica.Blocks.Interfaces.RealOutput lossPower(final quantity = "Power", final unit = "W") = LossPower;
422 Machines.Interfaces.SpacePhasor spacePhasor_r;
423 equation
424 assert(1 + alpha * (T_heatPort - T_ref) >= Modelica.Constants.eps, "Temperature outside scope of model!");
425 Rrd_actual = Rrd * (1 + alpha * (T_heatPort - T_ref));
426 Rrq_actual = Rrq * (1 + alpha * (T_heatPort - T_ref));
427 spacePhasor_r.v_[1] = Rrd_actual * spacePhasor_r.i_[1] + Lrsigmad * der(spacePhasor_r.i_[1]);
428 spacePhasor_r.v_[2] = Rrq_actual * spacePhasor_r.i_[2] + Lrsigmaq * der(spacePhasor_r.i_[2]);
429 2 / 3 * LossPower = Rrd_actual * spacePhasor_r.i_[1] * spacePhasor_r.i_[1] + Rrq_actual * spacePhasor_r.i_[2] * spacePhasor_r.i_[2];
430 end DamperCage;
431
432 model PermanentMagnet
433 parameter Modelica.SIunits.Current Ie;
434 Machines.Interfaces.SpacePhasor spacePhasor_r;
435 equation
436 spacePhasor_r.i_ = {-Ie, 0};
437 end PermanentMagnet;
438
439 model PermanentMagnetWithLosses
440 extends Machines.BasicMachines.Components.PermanentMagnet;
441 extends Machines.Losses.InductionMachines.PermanentMagnetLosses;
442 end PermanentMagnetWithLosses;
443 end Components;
444 end BasicMachines;
445
446 package Sensors
447 model VoltageQuasiRMSSensor
448 constant Integer m(final min = 1) = 3;
449 Modelica.Blocks.Interfaces.RealOutput V(final quantity = "ElectricPotential", final unit = "V");
450 Modelica.Electrical.MultiPhase.Interfaces.PositivePlug plug_p(final m = m);
451 Modelica.Electrical.MultiPhase.Interfaces.NegativePlug plug_n(final m = m);
452 Modelica.Electrical.MultiPhase.Sensors.VoltageSensor VoltageSensor1(final m = m);
453 Modelica.Blocks.Math.Gain Gain1(final k = 1 / sqrt(2));
454 Machines.SpacePhasors.Blocks.ToSpacePhasor ToSpacePhasor1;
455 Machines.SpacePhasors.Blocks.ToPolar ToPolar1;
456 equation
457 connect(plug_p, VoltageSensor1.plug_p);
458 connect(VoltageSensor1.plug_n, plug_n);
459 connect(VoltageSensor1.v, ToSpacePhasor1.u);
460 connect(ToSpacePhasor1.y, ToPolar1.u);
461 connect(ToPolar1.y[1], Gain1.u);
462 connect(Gain1.y, V);
463 end VoltageQuasiRMSSensor;
464
465 model CurrentQuasiRMSSensor
466 constant Integer m(final min = 1) = 3;
467 Modelica.Blocks.Interfaces.RealOutput I(final quantity = "ElectricCurrent", final unit = "A");
468 Modelica.Electrical.MultiPhase.Interfaces.PositivePlug plug_p(final m = m);
469 Modelica.Electrical.MultiPhase.Interfaces.NegativePlug plug_n(final m = m);
470 Modelica.Electrical.MultiPhase.Sensors.CurrentSensor CurrentSensor1(final m = m);
471 Modelica.Blocks.Math.Gain Gain1(final k = 1 / sqrt(2));
472 Machines.SpacePhasors.Blocks.ToSpacePhasor ToSpacePhasor1;
473 Machines.SpacePhasors.Blocks.ToPolar ToPolar1;
474 equation
475 connect(plug_p, CurrentSensor1.plug_p);
476 connect(CurrentSensor1.plug_n, plug_n);
477 connect(CurrentSensor1.i, ToSpacePhasor1.u);
478 connect(ToSpacePhasor1.y, ToPolar1.u);
479 connect(ToPolar1.y[1], Gain1.u);
480 connect(Gain1.y, I);
481 end CurrentQuasiRMSSensor;
482
483 model RotorDisplacementAngle
484 constant Integer m = 3;
485 parameter Integer p(min = 1);
486 parameter Boolean useSupport = false;
487 Modelica.Blocks.Interfaces.RealOutput rotorDisplacementAngle(final quantity = "Angle", final unit = "rad");
488 Modelica.Electrical.MultiPhase.Interfaces.PositivePlug plug_p(final m = m);
489 Modelica.Electrical.MultiPhase.Interfaces.NegativePlug plug_n(final m = m);
490 Modelica.Electrical.MultiPhase.Sensors.VoltageSensor VoltageSensor1(final m = m);
491 Machines.SpacePhasors.Blocks.ToSpacePhasor ToSpacePhasorVS;
492 Modelica.Mechanics.Rotational.Interfaces.Flange_a flange;
493 Modelica.Mechanics.Rotational.Sensors.RelAngleSensor relativeAngleSensor;
494 Modelica.Blocks.Sources.Constant constant_(final k = Modelica.Constants.pi / 2);
495 Modelica.Blocks.Math.Add add(final k2 = 1, final k1 = p);
496 Machines.SpacePhasors.Blocks.Rotator rotatorVS2R;
497 Machines.SpacePhasors.Blocks.ToPolar ToPolarVSR;
498 Modelica.Blocks.Routing.DeMultiplex2 deMultiplex2(final n1 = 1, final n2 = 1);
499 Modelica.Mechanics.Rotational.Interfaces.Flange_a support if useSupport;
500 Modelica.Mechanics.Rotational.Components.Fixed fixed if not useSupport;
501 equation
502 connect(plug_p, VoltageSensor1.plug_p);
503 connect(plug_n, VoltageSensor1.plug_n);
504 connect(relativeAngleSensor.flange_b, flange);
505 connect(relativeAngleSensor.flange_a, support);
506 connect(relativeAngleSensor.flange_a, fixed.flange);
507 connect(relativeAngleSensor.phi_rel, add.u1);
508 connect(constant_.y, add.u2);
509 connect(VoltageSensor1.v, ToSpacePhasorVS.u);
510 connect(ToSpacePhasorVS.y, rotatorVS2R.u);
511 connect(rotatorVS2R.y, ToPolarVSR.u);
512 connect(add.y, rotatorVS2R.angle);
513 connect(ToPolarVSR.y, deMultiplex2.u);
514 connect(deMultiplex2.y2[1], rotorDisplacementAngle);
515 end RotorDisplacementAngle;
516 end Sensors;
517
518 package SpacePhasors
519 package Components
520 model SpacePhasor
521 constant Integer m = 3;
522 constant Real pi = Modelica.Constants.pi;
523 parameter Real turnsRatio = 1;
524 Modelica.SIunits.Voltage[m] v;
525 Modelica.SIunits.Current[m] i;
526 protected
527 parameter Real[2, m] TransformationMatrix = 2 / m * {array(cos(+(k - 1) / m * 2 * pi) for k in 1:m), array(+sin(+(k - 1) / m * 2 * pi) for k in 1:m)};
528 parameter Real[m, 2] InverseTransformation = array({cos(-(k - 1) / m * 2 * pi), -sin(-(k - 1) / m * 2 * pi)} for k in 1:m);
529 public
530 Modelica.Electrical.MultiPhase.Interfaces.PositivePlug plug_p(final m = m);
531 Modelica.Electrical.MultiPhase.Interfaces.NegativePlug plug_n(final m = m);
532 Modelica.Electrical.Analog.Interfaces.PositivePin zero;
533 Modelica.Electrical.Analog.Interfaces.NegativePin ground;
534 Machines.Interfaces.SpacePhasor spacePhasor;
535 equation
536 v / turnsRatio = plug_p.pin.v - plug_n.pin.v;
537 i * turnsRatio = +plug_p.pin.i;
538 i * turnsRatio = -plug_n.pin.i;
539 m * zero.v = sum(v);
540 spacePhasor.v_ = TransformationMatrix * v;
541 -m * zero.i = sum(i);
542 -spacePhasor.i_ = TransformationMatrix * i;
543 ground.v = 0;
544 end SpacePhasor;
545 end Components;
546
547 package Blocks
548 block ToSpacePhasor
549 extends Modelica.Blocks.Interfaces.MIMO(final nin = m, final nout = 2);
550 constant Integer m = 3;
551 constant Real pi = Modelica.Constants.pi;
552 protected
553 parameter Real[2, m] TransformationMatrix = 2 / m * {array(cos(+(k - 1) / m * 2 * pi) for k in 1:m), array(+sin(+(k - 1) / m * 2 * pi) for k in 1:m)};
554 parameter Real[m, 2] InverseTransformation = array({cos(-(k - 1) / m * 2 * pi), -sin(-(k - 1) / m * 2 * pi)} for k in 1:m);
555 public
556 Modelica.Blocks.Interfaces.RealOutput zero;
557 equation
558 m * zero = sum(u);
559 y = TransformationMatrix * u;
560 end ToSpacePhasor;
561
562 block FromSpacePhasor
563 extends Modelica.Blocks.Interfaces.MIMO(final nin = 2, final nout = m);
564 constant Integer m = 3;
565 constant Real pi = Modelica.Constants.pi;
566 protected
567 parameter Real[2, m] TransformationMatrix = 2 / m * {array(cos(+(k - 1) / m * 2 * pi) for k in 1:m), array(+sin(+(k - 1) / m * 2 * pi) for k in 1:m)};
568 parameter Real[m, 2] InverseTransformation = array({cos(-(k - 1) / m * 2 * pi), -sin(-(k - 1) / m * 2 * pi)} for k in 1:m);
569 public
570 Modelica.Blocks.Interfaces.RealInput zero;
571 equation
572 y = fill(zero, m) + InverseTransformation * u;
573 end FromSpacePhasor;
574
575 block Rotator
576 extends Modelica.Blocks.Interfaces.MIMOs(final n = 2);
577 protected
578 Real[2, 2] RotationMatrix = {{+cos(-angle), -sin(-angle)}, {+sin(-angle), +cos(-angle)}};
579 public
580 Modelica.Blocks.Interfaces.RealInput angle;
581 equation
582 y = RotationMatrix * u;
583 end Rotator;
584
585 block ToPolar
586 extends Modelica.Blocks.Interfaces.MIMOs(final n = 2);
587 constant Real small = Modelica.Constants.small;
588 equation
589 y[1] = sqrt(u[1] ^ 2 + u[2] ^ 2);
590 y[2] = if noEvent(y[1] <= small) then 0 else Modelica.Math.atan2(u[2], u[1]);
591 end ToPolar;
592 end Blocks;
593
594 package Functions
595 function activePower
596 input Modelica.SIunits.Voltage[m] v;
597 input Modelica.SIunits.Current[m] i;
598 output Modelica.SIunits.Power p;
599 protected
600 constant Integer m = 3;
601 constant Modelica.SIunits.Angle pi = Modelica.Constants.pi;
602 Modelica.SIunits.Voltage[2] v_;
603 Modelica.SIunits.Current[2] i_;
604 algorithm
605 v_ := zeros(2);
606 i_ := zeros(2);
607 for k in 1:m loop
608 v_ := v_ + 2 / m * {+cos((k - 1) / m * 2 * pi), +sin(+(k - 1) / m * 2 * pi)} * v[k];
609 i_ := i_ + 2 / m * {+cos((k - 1) / m * 2 * pi), +sin(+(k - 1) / m * 2 * pi)} * i[k];
610 end for;
611 p := m / 2 * ((+v_[1] * i_[1]) + v_[2] * i_[2]);
612 end activePower;
613 end Functions;
614 end SpacePhasors;
615
616 package Losses
617 record FrictionParameters
618 parameter Modelica.SIunits.Power PRef(min = 0) = 0;
619 parameter Modelica.SIunits.AngularVelocity wRef(displayUnit = "1/min", min = Modelica.Constants.small);
620 parameter Real power_w(min = Modelica.Constants.small) = 2;
621 final parameter Modelica.SIunits.Torque tauRef = if PRef <= 0 then 0 else PRef / wRef;
622 final parameter Real linear = 0.001;
623 final parameter Modelica.SIunits.AngularVelocity wLinear = linear * wRef;
624 final parameter Modelica.SIunits.Torque tauLinear = if PRef <= 0 then 0 else tauRef * (wLinear / wRef) ^ power_w;
625 end FrictionParameters;
626
627 record StrayLoadParameters
628 parameter Modelica.SIunits.Power PRef(min = 0) = 0;
629 parameter Modelica.SIunits.Current IRef(min = Modelica.Constants.small);
630 parameter Modelica.SIunits.AngularVelocity wRef(displayUnit = "1/min", min = Modelica.Constants.small);
631 parameter Real power_w(min = Modelica.Constants.small) = 1;
632 final parameter Modelica.SIunits.Torque tauRef = if PRef <= 0 then 0 else PRef / wRef;
633 end StrayLoadParameters;
634
635 record CoreParameters
636 parameter Integer m;
637 parameter Modelica.SIunits.Power PRef(min = 0) = 0;
638 parameter Modelica.SIunits.Voltage VRef(min = Modelica.Constants.small);
639 parameter Modelica.SIunits.AngularVelocity wRef(min = Modelica.Constants.small);
640 final parameter Real ratioHysteresis(min = 0, max = 1, start = 0.775) = 0;
641 final parameter Modelica.SIunits.Conductance GcRef = if PRef <= 0 then 0 else PRef / VRef ^ 2 / m;
642 final parameter Modelica.SIunits.AngularVelocity wMin = 1e-6 * wRef;
643 end CoreParameters;
644
645 record PermanentMagnetLossParameters
646 parameter Modelica.SIunits.Power PRef(min = 0) = 0;
647 parameter Real c(min = 0, max = 1) = 0;
648 parameter Modelica.SIunits.Current IRef(min = Modelica.Constants.small);
649 parameter Real power_I(min = Modelica.Constants.small) = 2;
650 parameter Modelica.SIunits.AngularVelocity wRef(displayUnit = "1/min", min = Modelica.Constants.small);
651 parameter Real power_w(min = Modelica.Constants.small) = 1;
652 final parameter Modelica.SIunits.Torque tauRef = if PRef <= 0 then 0 else PRef / wRef;
653 end PermanentMagnetLossParameters;
654
655 model Friction
656 extends Machines.Interfaces.FlangeSupport;
657 parameter FrictionParameters frictionParameters;
658 extends Modelica.Thermal.HeatTransfer.Interfaces.PartialElementaryConditionalHeatPortWithoutT(useHeatPort = false);
659 equation
660 if frictionParameters.PRef <= 0 then
661 tau = 0;
662 else
663 tau = -smooth(1, if w >= (+frictionParameters.wLinear) then +frictionParameters.tauRef * (+w / frictionParameters.wRef) ^ frictionParameters.power_w else if w <= (-frictionParameters.wLinear) then -frictionParameters.tauRef * (-w / frictionParameters.wRef) ^ frictionParameters.power_w else frictionParameters.tauLinear * (w / frictionParameters.wLinear));
664 end if;
665 lossPower = -tau * w;
666 end Friction;
667
668 package InductionMachines
669 model StrayLoad
670 extends Modelica.Electrical.MultiPhase.Interfaces.OnePort;
671 extends Machines.Interfaces.FlangeSupport;
672 parameter Machines.Losses.StrayLoadParameters strayLoadParameters;
673 extends Modelica.Thermal.HeatTransfer.Interfaces.PartialElementaryConditionalHeatPortWithoutT(useHeatPort = false);
674 Modelica.SIunits.Current iRMS = .Modelica.Electrical.MultiPhase.Functions.quasiRMS(i);
675 equation
676 v = zeros(m);
677 if strayLoadParameters.PRef <= 0 then
678 tau = 0;
679 else
680 tau = -strayLoadParameters.tauRef * (iRMS / strayLoadParameters.IRef) ^ 2 * smooth(1, if w >= 0 then +(+w / strayLoadParameters.wRef) ^ strayLoadParameters.power_w else -(-w / strayLoadParameters.wRef) ^ strayLoadParameters.power_w);
681 end if;
682 lossPower = -tau * w;
683 end StrayLoad;
684
685 model PermanentMagnetLosses
686 extends Machines.Interfaces.FlangeSupport;
687 parameter Integer m(min = 1) = 3;
688 parameter Machines.Losses.PermanentMagnetLossParameters permanentMagnetLossParameters;
689 extends Modelica.Thermal.HeatTransfer.Interfaces.PartialElementaryConditionalHeatPortWithoutT(useHeatPort = false);
690 input Modelica.SIunits.Current[m] is;
691 Modelica.SIunits.Current iRMS = .Modelica.Electrical.MultiPhase.Functions.quasiRMS(is);
692 equation
693 if permanentMagnetLossParameters.PRef <= 0 then
694 tau = 0;
695 else
696 tau = -permanentMagnetLossParameters.tauRef * (permanentMagnetLossParameters.c + (1 - permanentMagnetLossParameters.c) * (iRMS / permanentMagnetLossParameters.IRef) ^ permanentMagnetLossParameters.power_I) * smooth(1, if w >= 0 then +(+w / permanentMagnetLossParameters.wRef) ^ permanentMagnetLossParameters.power_w else -(-w / permanentMagnetLossParameters.wRef) ^ permanentMagnetLossParameters.power_w);
697 end if;
698 lossPower = -tau * w;
699 end PermanentMagnetLosses;
700
701 model Core
702 parameter Machines.Losses.CoreParameters coreParameters(final m = m);
703 final parameter Integer m = 3;
704 parameter Real turnsRatio(final min = Modelica.Constants.small);
705 extends Modelica.Thermal.HeatTransfer.Interfaces.PartialElementaryConditionalHeatPortWithoutT(useHeatPort = false);
706 Machines.Interfaces.SpacePhasor spacePhasor;
707 input Modelica.SIunits.AngularVelocity w;
708 Modelica.SIunits.Conductance Gc;
709 protected
710 Modelica.SIunits.AngularVelocity wLimit = noEvent(max(noEvent(abs(w)), coreParameters.wMin));
711 equation
712 if coreParameters.PRef <= 0 then
713 Gc = 0;
714 spacePhasor.i_ = zeros(2);
715 else
716 Gc = coreParameters.GcRef;
717 spacePhasor.i_ = Gc * spacePhasor.v_;
718 end if;
719 lossPower = 3 / 2 * ((+spacePhasor.v_[1] * spacePhasor.i_[1]) + spacePhasor.v_[2] * spacePhasor.i_[2]);
720 end Core;
721 end InductionMachines;
722 end Losses;
723
724 package Thermal
725 type LinearTemperatureCoefficient20 = Modelica.SIunits.LinearTemperatureCoefficient;
726
727 function convertAlpha
728 input Modelica.SIunits.LinearTemperatureCoefficient alpha1;
729 input Modelica.SIunits.Temperature T2;
730 input Modelica.SIunits.Temperature T1 = 293.15;
731 output Modelica.SIunits.LinearTemperatureCoefficient alpha2;
732 algorithm
733 alpha2 := alpha1 / (1 + alpha1 * (T2 - T1));
734 end convertAlpha;
735
736 package SynchronousInductionMachines
737 model ThermalAmbientSMPM
738 parameter Boolean useDamperCage(start = true);
739 extends Machines.Interfaces.InductionMachines.PartialThermalAmbientInductionMachines(redeclare final Machines.Interfaces.InductionMachines.ThermalPortSMPM thermalPort(final useDamperCage = useDamperCage));
740 parameter .Modelica.SIunits.Temperature Tpm(start = TDefault);
741 parameter .Modelica.SIunits.Temperature Tr(start = TDefault);
742 output .Modelica.SIunits.HeatFlowRate Q_flowRotorWinding = temperatureRotorWinding.port.Q_flow;
743 output .Modelica.SIunits.HeatFlowRate Q_flowPermanentMagnet = temperaturePermanentMagnet.port.Q_flow;
744 output .Modelica.SIunits.HeatFlowRate Q_flowTotal = Q_flowStatorWinding + Q_flowRotorWinding + Q_flowPermanentMagnet + Q_flowStatorCore + Q_flowRotorCore + Q_flowStrayLoad + Q_flowFriction;
745 .Modelica.Thermal.HeatTransfer.Sources.PrescribedTemperature temperatureRotorWinding;
746 .Modelica.Blocks.Interfaces.RealInput TRotorWinding if useTemperatureInputs and useDamperCage;
747 .Modelica.Blocks.Sources.Constant constTr(final k = if useDamperCage then Tr else TDefault) if not useTemperatureInputs or not useDamperCage;
748 .Modelica.Thermal.HeatTransfer.Sources.PrescribedTemperature temperaturePermanentMagnet;
749 .Modelica.Blocks.Sources.Constant constTpm(final k = Tpm) if not useTemperatureInputs;
750 .Modelica.Blocks.Interfaces.RealInput TPermanentMagnet if useTemperatureInputs;
751 equation
752 connect(constTr.y, temperatureRotorWinding.T);
753 connect(temperatureRotorWinding.port, thermalPort.heatPortRotorWinding);
754 connect(TRotorWinding, temperatureRotorWinding.T);
755 connect(temperaturePermanentMagnet.port, thermalPort.heatPortPermanentMagnet);
756 connect(constTpm.y, temperaturePermanentMagnet.T);
757 connect(TPermanentMagnet, temperaturePermanentMagnet.T);
758 end ThermalAmbientSMPM;
759 end SynchronousInductionMachines;
760 end Thermal;
761
762 package Interfaces
763 connector SpacePhasor
764 Modelica.SIunits.Voltage[2] v_;
765 flow Modelica.SIunits.Current[2] i_;
766 end SpacePhasor;
767
768 partial model PartialBasicMachine
769 constant Modelica.SIunits.Angle pi = Modelica.Constants.pi;
770 parameter Modelica.SIunits.Inertia Jr;
771 parameter Boolean useSupport = false;
772 parameter Modelica.SIunits.Inertia Js(start = Jr);
773 parameter Boolean useThermalPort = false;
774 parameter Machines.Losses.FrictionParameters frictionParameters;
775 output Modelica.SIunits.Angle phiMechanical(start = 0) = flange.phi - internalSupport.phi;
776 output Modelica.SIunits.AngularVelocity wMechanical(displayUnit = "1/min", start = 0) = der(phiMechanical);
777 output Modelica.SIunits.Torque tauElectrical = inertiaRotor.flange_a.tau;
778 output Modelica.SIunits.Torque tauShaft = -flange.tau;
779 Modelica.Mechanics.Rotational.Interfaces.Flange_a flange;
780 Modelica.Mechanics.Rotational.Components.Inertia inertiaRotor(final J = Jr);
781 Modelica.Mechanics.Rotational.Interfaces.Flange_a support if useSupport;
782 Modelica.Mechanics.Rotational.Components.Inertia inertiaStator(final J = Js);
783 Modelica.Mechanics.Rotational.Components.Fixed fixed if not useSupport;
784 Machines.Losses.Friction friction(final frictionParameters = frictionParameters);
785 protected
786 Modelica.Mechanics.Rotational.Interfaces.Support internalSupport;
787 equation
788 connect(inertiaRotor.flange_b, flange);
789 connect(inertiaStator.flange_b, support);
790 connect(internalSupport, fixed.flange);
791 connect(internalSupport, inertiaStator.flange_a);
792 connect(inertiaRotor.flange_b, friction.flange);
793 connect(friction.support, internalSupport);
794 end PartialBasicMachine;
795
796 partial model PartialBasicInductionMachine
797 final parameter Integer m = 3;
798 parameter Integer p(min = 1, start = 2);
799 parameter Modelica.SIunits.Frequency fsNominal(start = 50);
800 parameter Modelica.SIunits.Temperature TsOperational(start = 293.15);
801 parameter Modelica.SIunits.Resistance Rs(start = 0.03);
802 parameter Modelica.SIunits.Temperature TsRef(start = 293.15);
803 parameter Machines.Thermal.LinearTemperatureCoefficient20 alpha20s(start = 0);
804 parameter Modelica.SIunits.Inductance Lszero = Lssigma;
805 parameter Modelica.SIunits.Inductance Lssigma(start = 3 * (1 - sqrt(1 - 0.0667)) / (2 * pi * fsNominal));
806 extends PartialBasicMachine(Jr(start = 0.29), frictionParameters(wRef = 2 * pi * fsNominal / p), friction(final useHeatPort = true));
807 parameter Machines.Losses.CoreParameters statorCoreParameters(final m = 3, VRef(start = 100), wRef = 2 * pi * fsNominal);
808 parameter Machines.Losses.StrayLoadParameters strayLoadParameters(IRef(start = 100), wRef = 2 * pi * fsNominal / p);
809 replaceable output Machines.Interfaces.InductionMachines.PartialPowerBalanceInductionMachines powerBalance(final powerStator = Machines.SpacePhasors.Functions.activePower(vs, is), final powerMechanical = wMechanical * tauShaft, final powerInertiaStator = inertiaStator.J * inertiaStator.a * inertiaStator.w, final powerInertiaRotor = inertiaRotor.J * inertiaRotor.a * inertiaRotor.w, final lossPowerStatorWinding = sum(rs.resistor.LossPower), final lossPowerStatorCore = statorCore.lossPower, final lossPowerStrayLoad = strayLoad.lossPower, final lossPowerFriction = friction.lossPower);
810 output Modelica.SIunits.Voltage[m] vs = plug_sp.pin.v - plug_sn.pin.v;
811 output Modelica.SIunits.Current[m] is = plug_sp.pin.i;
812 output Modelica.SIunits.Current i_0_s(stateSelect = StateSelect.prefer) = spacePhasorS.zero.i;
813 input Modelica.SIunits.Current[2] idq_ss;
814 input Modelica.SIunits.Current[2] idq_sr(each stateSelect = StateSelect.prefer);
815 input Modelica.SIunits.Current[2] idq_rs;
816 input Modelica.SIunits.Current[2] idq_rr(each stateSelect = StateSelect.prefer);
817 Modelica.Electrical.MultiPhase.Interfaces.PositivePlug plug_sp(final m = m);
818 Modelica.Electrical.MultiPhase.Interfaces.NegativePlug plug_sn(final m = m);
819 Modelica.Electrical.MultiPhase.Basic.Resistor rs(final m = m, final R = fill(Rs, m), final T_ref = fill(TsRef, m), final alpha = fill(Machines.Thermal.convertAlpha(alpha20s, TsRef), m), final useHeatPort = true, final T = fill(TsRef, m));
820 Machines.BasicMachines.Components.Inductor lssigma(final L = fill(Lssigma, 2));
821 Modelica.Electrical.Analog.Basic.Inductor lszero(final L = Lszero);
822 Machines.Losses.InductionMachines.Core statorCore(final coreParameters = statorCoreParameters, final useHeatPort = true, final turnsRatio = 1);
823 Machines.SpacePhasors.Components.SpacePhasor spacePhasorS(final turnsRatio = 1);
824 Machines.Losses.InductionMachines.StrayLoad strayLoad(final strayLoadParameters = strayLoadParameters, final useHeatPort = true, final m = m);
825 replaceable Machines.Interfaces.InductionMachines.PartialThermalPortInductionMachines thermalPort(final m = m) if useThermalPort;
826 replaceable Machines.Interfaces.InductionMachines.PartialThermalAmbientInductionMachines thermalAmbient(final useTemperatureInputs = false, final Ts = TsOperational, final m = m) if not useThermalPort;
827 protected
828 replaceable Machines.Interfaces.InductionMachines.PartialThermalPortInductionMachines internalThermalPort(final m = m);
829 equation
830 connect(spacePhasorS.plug_n, plug_sn);
831 connect(thermalPort, internalThermalPort);
832 connect(thermalAmbient.thermalPort, internalThermalPort);
833 connect(strayLoad.plug_n, rs.plug_p);
834 connect(strayLoad.plug_p, plug_sp);
835 connect(strayLoad.support, internalSupport);
836 connect(spacePhasorS.plug_p, rs.plug_n);
837 connect(spacePhasorS.zero, lszero.p);
838 connect(lszero.n, spacePhasorS.ground);
839 connect(spacePhasorS.spacePhasor, lssigma.spacePhasor_a);
840 connect(statorCore.spacePhasor, lssigma.spacePhasor_a);
841 connect(statorCore.heatPort, internalThermalPort.heatPortStatorCore);
842 connect(strayLoad.heatPort, internalThermalPort.heatPortStrayLoad);
843 connect(rs.heatPort, internalThermalPort.heatPortStatorWinding);
844 connect(friction.heatPort, internalThermalPort.heatPortFriction);
845 connect(strayLoad.flange, inertiaRotor.flange_b);
846 end PartialBasicInductionMachine;
847
848 package InductionMachines
849 connector PartialThermalPortInductionMachines
850 parameter Integer m = 3;
851 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a[m] heatPortStatorWinding;
852 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPortStatorCore;
853 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPortRotorCore;
854 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPortStrayLoad;
855 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPortFriction;
856 end PartialThermalPortInductionMachines;
857
858 model PartialThermalAmbientInductionMachines
859 parameter Integer m = 3;
860 parameter Boolean useTemperatureInputs = false;
861 constant Modelica.SIunits.Temperature TDefault = 293.15;
862 parameter Modelica.SIunits.Temperature Ts(start = TDefault);
863 output Modelica.SIunits.HeatFlowRate Q_flowStatorWinding = temperatureStatorWinding.port.Q_flow;
864 output Modelica.SIunits.HeatFlowRate Q_flowStatorCore = temperatureStatorCore.port.Q_flow;
865 output Modelica.SIunits.HeatFlowRate Q_flowRotorCore = temperatureRotorCore.port.Q_flow;
866 output Modelica.SIunits.HeatFlowRate Q_flowStrayLoad = temperatureStrayLoad.port.Q_flow;
867 output Modelica.SIunits.HeatFlowRate Q_flowFriction = temperatureFriction.port.Q_flow;
868 replaceable Machines.Interfaces.InductionMachines.PartialThermalPortInductionMachines thermalPort(final m = m);
869 Modelica.Thermal.HeatTransfer.Sources.PrescribedTemperature temperatureStatorWinding;
870 Modelica.Thermal.HeatTransfer.Sources.FixedTemperature temperatureStatorCore(final T = TDefault);
871 Modelica.Thermal.HeatTransfer.Sources.FixedTemperature temperatureRotorCore(final T = TDefault);
872 Modelica.Thermal.HeatTransfer.Sources.FixedTemperature temperatureStrayLoad(final T = TDefault);
873 Modelica.Thermal.HeatTransfer.Sources.FixedTemperature temperatureFriction(final T = TDefault);
874 Modelica.Blocks.Interfaces.RealInput TStatorWinding if useTemperatureInputs;
875 Modelica.Blocks.Sources.Constant constTs(final k = Ts) if not useTemperatureInputs;
876 Modelica.Thermal.HeatTransfer.Components.ThermalCollector thermalCollectorStator(final m = m);
877 equation
878 connect(constTs.y, temperatureStatorWinding.T);
879 connect(TStatorWinding, temperatureStatorWinding.T);
880 connect(temperatureStrayLoad.port, thermalPort.heatPortStrayLoad);
881 connect(temperatureFriction.port, thermalPort.heatPortFriction);
882 connect(thermalCollectorStator.port_b, temperatureStatorWinding.port);
883 connect(thermalCollectorStator.port_a, thermalPort.heatPortStatorWinding);
884 connect(temperatureStatorCore.port, thermalPort.heatPortStatorCore);
885 connect(temperatureRotorCore.port, thermalPort.heatPortRotorCore);
886 end PartialThermalAmbientInductionMachines;
887
888 record PartialPowerBalanceInductionMachines
889 Modelica.SIunits.Power powerStator = 0;
890 Modelica.SIunits.Power powerMechanical = 0;
891 Modelica.SIunits.Power powerInertiaStator = 0;
892 Modelica.SIunits.Power powerInertiaRotor = 0;
893 Modelica.SIunits.Power lossPowerTotal = 0;
894 Modelica.SIunits.Power lossPowerStatorWinding = 0;
895 Modelica.SIunits.Power lossPowerStatorCore = 0;
896 Modelica.SIunits.Power lossPowerRotorCore = 0;
897 Modelica.SIunits.Power lossPowerStrayLoad = 0;
898 Modelica.SIunits.Power lossPowerFriction = 0;
899 end PartialPowerBalanceInductionMachines;
900
901 connector ThermalPortSMPM
902 extends Machines.Interfaces.InductionMachines.PartialThermalPortInductionMachines;
903 parameter Boolean useDamperCage(start = true);
904 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPortRotorWinding if useDamperCage;
905 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPortPermanentMagnet;
906 end ThermalPortSMPM;
907
908 record PowerBalanceSMPM
909 extends Machines.Interfaces.InductionMachines.PartialPowerBalanceInductionMachines(final lossPowerTotal = lossPowerStatorWinding + lossPowerStatorCore + lossPowerRotorCore + lossPowerStrayLoad + lossPowerFriction + lossPowerRotorWinding + lossPowerPermanentMagnet);
910 Modelica.SIunits.Power lossPowerRotorWinding;
911 Modelica.SIunits.Power lossPowerPermanentMagnet;
912 end PowerBalanceSMPM;
913 end InductionMachines;
914
915 partial model FlangeSupport
916 Modelica.Mechanics.Rotational.Interfaces.Flange_a flange;
917 Modelica.Mechanics.Rotational.Interfaces.Flange_a support;
918 Modelica.SIunits.Angle phi;
919 Modelica.SIunits.Torque tau;
920 Modelica.SIunits.AngularVelocity w;
921 equation
922 phi = flange.phi - support.phi;
923 w = der(phi);
924 tau = -flange.tau;
925 tau = support.tau;
926 end FlangeSupport;
927 end Interfaces;
928
929 package Utilities
930 package ParameterRecords
931 record InductionMachineData
932 final parameter Integer m = 3;
933 parameter Modelica.SIunits.Inertia Jr = 0.29;
934 parameter Modelica.SIunits.Inertia Js = Jr;
935 parameter Integer p(min = 1) = 2;
936 parameter Modelica.SIunits.Frequency fsNominal = 50;
937 parameter Modelica.SIunits.Resistance Rs = 0.03;
938 parameter Modelica.SIunits.Temperature TsRef = 293.15;
939 parameter Machines.Thermal.LinearTemperatureCoefficient20 alpha20s = 0;
940 parameter Modelica.SIunits.Inductance Lszero = Lssigma;
941 parameter Modelica.SIunits.Inductance Lssigma = 3 * (1 - sqrt(1 - 0.0667)) / (2 * .Modelica.Constants.pi * fsNominal);
942 parameter Machines.Losses.FrictionParameters frictionParameters(PRef = 0, wRef = 2 * .Modelica.Constants.pi * fsNominal / p);
943 parameter Machines.Losses.CoreParameters statorCoreParameters(final m = m, PRef = 0, VRef = 100, wRef = 2 * .Modelica.Constants.pi * fsNominal);
944 parameter Machines.Losses.StrayLoadParameters strayLoadParameters(PRef = 0, IRef = 100, wRef = 2 * .Modelica.Constants.pi * fsNominal / p);
945 end InductionMachineData;
946
947 record SM_PermanentMagnetData
948 extends SM_ReluctanceRotorData(Lmd = 0.3 / (2 * .Modelica.Constants.pi * fsNominal), Lmq = 0.3 / (2 * .Modelica.Constants.pi * fsNominal));
949 parameter Modelica.SIunits.Voltage VsOpenCircuit = 112.3;
950 parameter Machines.Losses.PermanentMagnetLossParameters permanentMagnetLossParameters(PRef = 0, IRef = 100, wRef = 2 * .Modelica.Constants.pi * fsNominal / p);
951 end SM_PermanentMagnetData;
952
953 record SM_ReluctanceRotorData
954 extends InductionMachineData(Lssigma = 0.1 / (2 * .Modelica.Constants.pi * fsNominal));
955 parameter Modelica.SIunits.Inductance Lmd = 2.9 / (2 * .Modelica.Constants.pi * fsNominal);
956 parameter Modelica.SIunits.Inductance Lmq = 0.9 / (2 * .Modelica.Constants.pi * fsNominal);
957 parameter Boolean useDamperCage = true;
958 parameter Modelica.SIunits.Inductance Lrsigmad = 0.05 / (2 * .Modelica.Constants.pi * fsNominal);
959 parameter Modelica.SIunits.Inductance Lrsigmaq = Lrsigmad;
960 parameter Modelica.SIunits.Resistance Rrd = 0.04;
961 parameter Modelica.SIunits.Resistance Rrq = Rrd;
962 parameter Modelica.SIunits.Temperature TrRef = 293.15;
963 parameter Machines.Thermal.LinearTemperatureCoefficient20 alpha20r = 0;
964 end SM_ReluctanceRotorData;
965 end ParameterRecords;
966
967 model CurrentController
968 constant Integer m = 3;
969 parameter Integer p;
970 extends Modelica.Blocks.Interfaces.MO(final nout = m);
971 Modelica.Blocks.Interfaces.RealInput id_rms;
972 Modelica.Blocks.Interfaces.RealInput iq_rms;
973 Modelica.Blocks.Interfaces.RealInput phi;
974 Modelica.Blocks.Math.Gain toPeak_d(k = sqrt(2));
975 Modelica.Blocks.Math.Gain toPeak_q(k = sqrt(2));
976 Modelica.Blocks.Math.Gain toGamma(k = -p);
977 Machines.SpacePhasors.Blocks.Rotator rotator;
978 Modelica.Blocks.Sources.Constant i0(k = 0);
979 Machines.SpacePhasors.Blocks.FromSpacePhasor fromSpacePhasor;
980 equation
981 connect(iq_rms, toPeak_q.u);
982 connect(phi, toGamma.u);
983 connect(rotator.angle, toGamma.y);
984 connect(rotator.y, fromSpacePhasor.u);
985 connect(toPeak_d.u, id_rms);
986 connect(toPeak_d.y, rotator.u[1]);
987 connect(toPeak_q.y, rotator.u[2]);
988 connect(i0.y, fromSpacePhasor.zero);
989 connect(fromSpacePhasor.y, y);
990 end CurrentController;
991
992 model TerminalBox
993 parameter Integer m = 3;
994 parameter String terminalConnection(start = "Y");
995 Modelica.Electrical.MultiPhase.Interfaces.PositivePlug plug_sp(final m = m);
996 Modelica.Electrical.MultiPhase.Interfaces.NegativePlug plug_sn(final m = m);
997 Modelica.Electrical.MultiPhase.Basic.Star star(final m = m) if terminalConnection <> "D";
998 Modelica.Electrical.MultiPhase.Basic.Delta delta(final m = m) if terminalConnection == "D";
999 Modelica.Electrical.MultiPhase.Interfaces.PositivePlug plugSupply(final m = m);
1000 Modelica.Electrical.Analog.Interfaces.NegativePin starpoint if terminalConnection <> "D";
1001 equation
1002 connect(plug_sn, star.plug_p);
1003 connect(plug_sn, delta.plug_n);
1004 connect(delta.plug_p, plug_sp);
1005 connect(plug_sp, plugSupply);
1006 connect(star.pin_n, starpoint);
1007 end TerminalBox;
1008 end Utilities;
1009 end Machines;
1010
1011 package MultiPhase
1012 package Basic
1013 model Star
1014 parameter Integer m(final min = 1) = 3;
1015 Interfaces.PositivePlug plug_p(final m = m);
1016 Modelica.Electrical.Analog.Interfaces.NegativePin pin_n;
1017 equation
1018 for j in 1:m loop
1019 plug_p.pin[j].v = pin_n.v;
1020 end for;
1021 sum(plug_p.pin.i) + pin_n.i = 0;
1022 end Star;
1023
1024 model Delta
1025 parameter Integer m(final min = 2) = 3;
1026 Interfaces.PositivePlug plug_p(final m = m);
1027 Interfaces.NegativePlug plug_n(final m = m);
1028 equation
1029 for j in 1:m loop
1030 if j < m then
1031 plug_n.pin[j].v = plug_p.pin[j + 1].v;
1032 plug_n.pin[j].i + plug_p.pin[j + 1].i = 0;
1033 else
1034 plug_n.pin[j].v = plug_p.pin[1].v;
1035 plug_n.pin[j].i + plug_p.pin[1].i = 0;
1036 end if;
1037 end for;
1038 end Delta;
1039
1040 model Resistor
1041 extends Interfaces.TwoPlug;
1042 parameter Modelica.SIunits.Resistance[m] R(start = fill(1, m));
1043 parameter Modelica.SIunits.Temperature[m] T_ref = fill(300.15, m);
1044 parameter Modelica.SIunits.LinearTemperatureCoefficient[m] alpha = zeros(m);
1045 extends Modelica.Electrical.MultiPhase.Interfaces.ConditionalHeatPort(final mh = m, T = T_ref);
1046 Modelica.Electrical.Analog.Basic.Resistor[m] resistor(final R = R, final T_ref = T_ref, final alpha = alpha, each final useHeatPort = useHeatPort, final T = T);
1047 equation
1048 connect(resistor.p, plug_p.pin);
1049 connect(resistor.n, plug_n.pin);
1050 connect(resistor.heatPort, heatPort);
1051 end Resistor;
1052 end Basic;
1053
1054 package Functions
1055 function quasiRMS
1056 input Real[:] x;
1057 output Real y;
1058 algorithm
1059 y := sqrt(sum(x .^ 2 / size(x, 1)));
1060 end quasiRMS;
1061 end Functions;
1062
1063 package Sensors
1064 model VoltageSensor
1065 parameter Integer m(final min = 1) = 3;
1066 Interfaces.PositivePlug plug_p(final m = m);
1067 Interfaces.NegativePlug plug_n(final m = m);
1068 Modelica.Blocks.Interfaces.RealOutput[m] v;
1069 Modelica.Electrical.Analog.Sensors.VoltageSensor[m] voltageSensor;
1070 equation
1071 connect(voltageSensor.n, plug_n.pin);
1072 connect(voltageSensor.p, plug_p.pin);
1073 connect(voltageSensor.v, v);
1074 end VoltageSensor;
1075
1076 model CurrentSensor
1077 parameter Integer m(final min = 1) = 3;
1078 Interfaces.PositivePlug plug_p(final m = m);
1079 Interfaces.NegativePlug plug_n(final m = m);
1080 Modelica.Blocks.Interfaces.RealOutput[m] i;
1081 Modelica.Electrical.Analog.Sensors.CurrentSensor[m] currentSensor;
1082 equation
1083 connect(plug_p.pin, currentSensor.p);
1084 connect(currentSensor.n, plug_n.pin);
1085 connect(currentSensor.i, i);
1086 end CurrentSensor;
1087 end Sensors;
1088
1089 package Sources
1090 model SignalCurrent
1091 parameter Integer m(min = 1) = 3;
1092 Modelica.SIunits.Voltage[m] v = plug_p.pin.v - plug_n.pin.v;
1093 Interfaces.PositivePlug plug_p(final m = m);
1094 Interfaces.NegativePlug plug_n(final m = m);
1095 Modelica.Blocks.Interfaces.RealInput[m] i(each unit = "A");
1096 Modelica.Electrical.Analog.Sources.SignalCurrent[m] signalCurrent;
1097 equation
1098 connect(signalCurrent.p, plug_p.pin);
1099 connect(signalCurrent.n, plug_n.pin);
1100 connect(i, signalCurrent.i);
1101 end SignalCurrent;
1102 end Sources;
1103
1104 package Interfaces
1105 connector Plug
1106 parameter Integer m(final min = 1) = 3;
1107 Modelica.Electrical.Analog.Interfaces.Pin[m] pin;
1108 end Plug;
1109
1110 connector PositivePlug
1111 extends Plug;
1112 end PositivePlug;
1113
1114 connector NegativePlug
1115 extends Plug;
1116 end NegativePlug;
1117
1118 partial model ConditionalHeatPort
1119 parameter Integer mh(min = 1) = 3;
1120 parameter Boolean useHeatPort = false;
1121 parameter Modelica.SIunits.Temperature[mh] T = fill(293.15, mh);
1122 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a[mh] heatPort if useHeatPort;
1123 end ConditionalHeatPort;
1124
1125 partial model TwoPlug
1126 parameter Integer m(min = 1) = 3;
1127 Modelica.SIunits.Voltage[m] v;
1128 Modelica.SIunits.Current[m] i;
1129 PositivePlug plug_p(final m = m);
1130 NegativePlug plug_n(final m = m);
1131 equation
1132 v = plug_p.pin.v - plug_n.pin.v;
1133 i = plug_p.pin.i;
1134 end TwoPlug;
1135
1136 partial model OnePort
1137 extends TwoPlug;
1138 equation
1139 plug_p.pin.i + plug_n.pin.i = zeros(m);
1140 end OnePort;
1141 end Interfaces;
1142 end MultiPhase;
1143 end Electrical;
1144
1145 package Mechanics
1146 package Rotational
1147 package Components
1148 model Fixed
1149 parameter .Modelica.SIunits.Angle phi0 = 0;
1150 Interfaces.Flange_b flange;
1151 equation
1152 flange.phi = phi0;
1153 end Fixed;
1154
1155 model Inertia
1156 Rotational.Interfaces.Flange_a flange_a;
1157 Rotational.Interfaces.Flange_b flange_b;
1158 parameter .Modelica.SIunits.Inertia J(min = 0, start = 1);
1159 parameter StateSelect stateSelect = StateSelect.default;
1160 .Modelica.SIunits.Angle phi(stateSelect = stateSelect);
1161 .Modelica.SIunits.AngularVelocity w(stateSelect = stateSelect);
1162 .Modelica.SIunits.AngularAcceleration a;
1163 equation
1164 phi = flange_a.phi;
1165 phi = flange_b.phi;
1166 w = der(phi);
1167 a = der(w);
1168 J * a = flange_a.tau + flange_b.tau;
1169 end Inertia;
1170
1171 model ElastoBacklash
1172 parameter .Modelica.SIunits.RotationalSpringConstant c(final min = Modelica.Constants.small, start = 1.0e5);
1173 parameter .Modelica.SIunits.RotationalDampingConstant d(final min = 0, start = 0);
1174 parameter .Modelica.SIunits.Angle b(final min = 0) = 0;
1175 parameter .Modelica.SIunits.Angle phi_rel0 = 0;
1176 extends Modelica.Mechanics.Rotational.Interfaces.PartialCompliantWithRelativeStates;
1177 extends Modelica.Thermal.HeatTransfer.Interfaces.PartialElementaryConditionalHeatPortWithoutT;
1178 protected
1179 final parameter .Modelica.SIunits.Angle bMax = b / 2;
1180 final parameter .Modelica.SIunits.Angle bMin = -bMax;
1181 .Modelica.SIunits.Torque tau_c;
1182 .Modelica.SIunits.Torque tau_d;
1183 .Modelica.SIunits.Angle phi_diff = phi_rel - phi_rel0;
1184 constant .Modelica.SIunits.Angle bEps = 1e-10;
1185 equation
1186 if initial() then
1187 tau_c = if phi_diff > 1.5 * bMax then c * (phi_diff - bMax) else if phi_diff < 1.5 * bMin then c * (phi_diff - bMin) else c / 3 * phi_diff;
1188 tau_d = d * w_rel;
1189 tau = tau_c + tau_d;
1190 lossPower = tau_d * w_rel;
1191 else
1192 tau_c = if abs(b) <= bEps then c * phi_diff else if phi_diff > bMax then c * (phi_diff - bMax) else if phi_diff < bMin then c * (phi_diff - bMin) else 0;
1193 tau_d = d * w_rel;
1194 tau = if abs(b) <= bEps then tau_c + tau_d else if phi_diff > bMax then smooth(0, noEvent(if tau_c + tau_d <= 0 then 0 else tau_c + min(tau_c, tau_d))) else if phi_diff < bMin then smooth(0, noEvent(if tau_c + tau_d >= 0 then 0 else tau_c + max(tau_c, tau_d))) else 0;
1195 lossPower = if abs(b) <= bEps then tau_d * w_rel else if phi_diff > bMax then smooth(0, noEvent(if tau_c + tau_d <= 0 then 0 else min(tau_c, tau_d) * w_rel)) else if phi_diff < bMin then smooth(0, noEvent(if tau_c + tau_d >= 0 then 0 else max(tau_c, tau_d) * w_rel)) else 0;
1196 end if;
1197 end ElastoBacklash;
1198
1199 model LossyGear
1200 extends Modelica.Mechanics.Rotational.Interfaces.PartialElementaryTwoFlangesAndSupport2;
1201 parameter Real ratio(start = 1);
1202 parameter Real[:, 5] lossTable = [0, 1, 1, 0, 0];
1203 extends Modelica.Thermal.HeatTransfer.Interfaces.PartialElementaryConditionalHeatPortWithoutT;
1204 Modelica.SIunits.Angle phi_a;
1205 Modelica.SIunits.Angle phi_b;
1206 Real sa(final unit = "1");
1207 .Modelica.SIunits.AngularVelocity w_a;
1208 .Modelica.SIunits.AngularAcceleration a_a;
1209 Real[1, size(lossTable, 2) - 1] interpolation_result;
1210 Real eta_mf1;
1211 Real eta_mf2;
1212 Real tau_bf_a;
1213 Real tau_eta;
1214 Real tau_bf1;
1215 Real tau_bf2;
1216 Real quadrant1;
1217 Real quadrant2;
1218 Real quadrant3;
1219 Real quadrant4;
1220 Real quadrant1_p;
1221 Real quadrant2_p;
1222 Real quadrant3_m;
1223 Real quadrant4_m;
1224 .Modelica.SIunits.Torque tauLoss;
1225 .Modelica.SIunits.Torque tauLossMax;
1226 .Modelica.SIunits.Torque tauLossMin;
1227 .Modelica.SIunits.Torque tauLossMax_p;
1228 .Modelica.SIunits.Torque tauLossMin_m;
1229 Boolean tau_aPos(start = true);
1230 Boolean tau_etaPos(start = true);
1231 Boolean startForward(start = false);
1232 Boolean startBackward(start = false);
1233 Boolean locked(start = false);
1234 Boolean ideal;
1235 constant Integer Unknown = 3;
1236 constant Integer Free = 2;
1237 constant Integer Forward = 1;
1238 constant Integer Stuck = 0;
1239 constant Integer Backward = -1;
1240 Integer mode(final min = Backward, final max = Unknown, start = Free, fixed = true);
1241 .Modelica.SIunits.Torque tau_eta_p;
1242 .Modelica.SIunits.Torque tau_eta_m;
1243 protected
1244 constant .Modelica.SIunits.AngularAcceleration unitAngularAcceleration = 1;
1245 constant .Modelica.SIunits.Torque unitTorque = 1;
1246 parameter Real[1, size(lossTable, 2) - 1] interpolation_result_0 = Modelica.Math.tempInterpol2(0, lossTable, {2, 3, 4, 5});
1247 parameter Real eta_mf1_0 = interpolation_result_0[1, 1];
1248 parameter Real eta_mf2_0 = interpolation_result_0[1, 2];
1249 parameter Real tau_bf1_0 = abs(interpolation_result_0[1, 3]);
1250 parameter Real tau_bf2_0 = abs(interpolation_result_0[1, 4]);
1251 parameter Real tau_bf_a_0 = if Modelica.Math.isEqual(eta_mf1_0, 1.0, Modelica.Constants.eps) and Modelica.Math.isEqual(eta_mf2_0, 1.0, Modelica.Constants.eps) then tau_bf1_0 / 2 else (tau_bf1_0 - tau_bf2_0) / (eta_mf1_0 - 1.0 / eta_mf2_0);
1252 equation
1253 assert(abs(ratio) > 0, "Error in initialization of LossyGear: ratio may not be zero");
1254 ideal = Modelica.Math.Matrices.isEqual(lossTable, [0, 1, 1, 0, 0], Modelica.Constants.eps);
1255 interpolation_result = if ideal then [1, 1, 0, 0] else Modelica.Math.tempInterpol2(noEvent(abs(w_a)), lossTable, {2, 3, 4, 5});
1256 eta_mf1 = interpolation_result[1, 1];
1257 eta_mf2 = interpolation_result[1, 2];
1258 tau_bf1 = noEvent(abs(interpolation_result[1, 3]));
1259 tau_bf2 = noEvent(abs(interpolation_result[1, 4]));
1260 if Modelica.Math.isEqual(eta_mf1, 1.0, Modelica.Constants.eps) and Modelica.Math.isEqual(eta_mf2, 1.0, Modelica.Constants.eps) then
1261 tau_bf_a = tau_bf1 / 2;
1262 else
1263 tau_bf_a = (tau_bf1 - tau_bf2) / (eta_mf1 - 1.0 / eta_mf2);
1264 end if;
1265 phi_a = flange_a.phi - phi_support;
1266 phi_b = flange_b.phi - phi_support;
1267 phi_a = ratio * phi_b;
1268 0 = flange_b.tau + ratio * (flange_a.tau - tauLoss);
1269 w_a = der(phi_a);
1270 a_a = der(w_a);
1271 tau_eta_p = flange_a.tau - tau_bf_a_0;
1272 tau_eta_m = flange_a.tau + tau_bf_a_0;
1273 quadrant1_p = (1 - eta_mf1_0) * flange_a.tau + tau_bf1_0;
1274 quadrant2_p = (1 - 1 / eta_mf2_0) * flange_a.tau + tau_bf2_0;
1275 tauLossMax_p = if noEvent(tau_eta_p > 0) then quadrant1_p else quadrant2_p;
1276 quadrant4_m = (1 - 1 / eta_mf2_0) * flange_a.tau - tau_bf2_0;
1277 quadrant3_m = (1 - eta_mf1_0) * flange_a.tau - tau_bf1_0;
1278 tauLossMin_m = if noEvent(tau_eta_m > 0) then quadrant4_m else quadrant3_m;
1279 quadrant1 = (1 - eta_mf1) * flange_a.tau + tau_bf1;
1280 quadrant2 = (1 - 1 / eta_mf2) * flange_a.tau + tau_bf2;
1281 quadrant4 = (1 - 1 / eta_mf2) * flange_a.tau - tau_bf2;
1282 quadrant3 = (1 - eta_mf1) * flange_a.tau - tau_bf1;
1283 tau_eta = if ideal then flange_a.tau else if locked then flange_a.tau else if startForward or pre(mode) == Forward then flange_a.tau - tau_bf_a else flange_a.tau + tau_bf_a;
1284 tau_etaPos = tau_eta >= 0;
1285 tau_aPos = tau_etaPos;
1286 tauLossMax = if tau_etaPos then quadrant1 else quadrant2;
1287 tauLossMin = if tau_etaPos then quadrant4 else quadrant3;
1288 startForward = pre(mode) == Stuck and sa > tauLossMax_p / unitTorque or initial() and w_a > 0;
1289 startBackward = pre(mode) == Stuck and sa < tauLossMin_m / unitTorque or initial() and w_a < 0;
1290 locked = not (ideal or pre(mode) == Forward or startForward or pre(mode) == Backward or startBackward);
1291 tauLoss = if ideal then 0 else if locked then sa * unitTorque else if startForward or pre(mode) == Forward then tauLossMax else tauLossMin;
1292 a_a = unitAngularAcceleration * (if locked then 0 else sa - tauLoss / unitTorque);
1293 mode = if ideal then Free else if (pre(mode) == Forward or startForward) and w_a > 0 then Forward else if (pre(mode) == Backward or startBackward) and w_a < 0 then Backward else Stuck;
1294 lossPower = tauLoss * w_a;
1295 end LossyGear;
1296
1297 model Gearbox
1298 extends Modelica.Mechanics.Rotational.Interfaces.PartialTwoFlangesAndSupport;
1299 parameter Real ratio(start = 1);
1300 parameter Real[:, 5] lossTable = [0, 1, 1, 0, 0];
1301 parameter .Modelica.SIunits.RotationalSpringConstant c(final min = Modelica.Constants.small, start = 1.0e5);
1302 parameter .Modelica.SIunits.RotationalDampingConstant d(final min = 0, start = 0);
1303 parameter .Modelica.SIunits.Angle b(final min = 0) = 0;
1304 parameter StateSelect stateSelect = StateSelect.prefer;
1305 extends Modelica.Thermal.HeatTransfer.Interfaces.PartialConditionalHeatPort(final T = 293.15);
1306 Modelica.SIunits.Angle phi_rel(start = 0, stateSelect = stateSelect, nominal = 1e-4) = flange_b.phi - lossyGear.flange_b.phi;
1307 Modelica.SIunits.AngularVelocity w_rel(start = 0, stateSelect = stateSelect) = der(phi_rel);
1308 Modelica.SIunits.AngularAcceleration a_rel(start = 0) = der(w_rel);
1309 Rotational.Components.LossyGear lossyGear(final ratio = ratio, final lossTable = lossTable, final useSupport = true, final useHeatPort = true);
1310 Rotational.Components.ElastoBacklash elastoBacklash(final b = b, final c = c, final phi_rel0 = 0, final d = d, final useHeatPort = true);
1311 equation
1312 connect(flange_a, lossyGear.flange_a);
1313 connect(lossyGear.flange_b, elastoBacklash.flange_a);
1314 connect(elastoBacklash.flange_b, flange_b);
1315 connect(elastoBacklash.heatPort, internalHeatPort);
1316 connect(lossyGear.heatPort, internalHeatPort);
1317 connect(lossyGear.support, internalSupport);
1318 end Gearbox;
1319
1320 model IdealGearR2T
1321 extends Rotational.Interfaces.PartialElementaryRotationalToTranslational;
1322 parameter Real ratio(final unit = "rad/m", start = 1);
1323 equation
1324 flangeR.phi - internalSupportR.phi = ratio * (flangeT.s - internalSupportT.s);
1325 0 = ratio * flangeR.tau + flangeT.f;
1326 end IdealGearR2T;
1327 end Components;
1328
1329 package Sensors
1330
1331 model AngleSensor
1332 extends Rotational.Interfaces.PartialAbsoluteSensor;
1333 Modelica.Blocks.Interfaces.RealOutput phi(unit = "rad", displayUnit = "deg");
1334 equation
1335 phi = flange.phi;
1336 end AngleSensor;
1337
1338 model SpeedSensor
1339 extends Rotational.Interfaces.PartialAbsoluteSensor;
1340 Modelica.Blocks.Interfaces.RealOutput w(unit = "rad/s");
1341 equation
1342 w = der(flange.phi);
1343 end SpeedSensor;
1344
1345 model RelAngleSensor
1346 extends Rotational.Interfaces.PartialRelativeSensor;
1347 Modelica.Blocks.Interfaces.RealOutput phi_rel(unit = "rad", displayUnit = "deg");
1348 equation
1349 phi_rel = flange_b.phi - flange_a.phi;
1350 0 = flange_a.tau;
1351 end RelAngleSensor;
1352
1353 model TorqueSensor
1354 extends Rotational.Interfaces.PartialRelativeSensor;
1355 Modelica.Blocks.Interfaces.RealOutput tau(unit = "N.m");
1356 equation
1357 flange_a.phi = flange_b.phi;
1358 flange_a.tau = tau;
1359 end TorqueSensor;
1360 end Sensors;
1361
1362 package Interfaces
1363 connector Flange_a
1364 .Modelica.SIunits.Angle phi;
1365 flow .Modelica.SIunits.Torque tau;
1366 end Flange_a;
1367
1368 connector Flange_b
1369 .Modelica.SIunits.Angle phi;
1370 flow .Modelica.SIunits.Torque tau;
1371 end Flange_b;
1372
1373 connector Support
1374 .Modelica.SIunits.Angle phi;
1375 flow .Modelica.SIunits.Torque tau;
1376 end Support;
1377
1378 model InternalSupport
1379 input Modelica.SIunits.Torque tau;
1380 Modelica.SIunits.Angle phi;
1381 Flange_a flange;
1382 equation
1383 flange.tau = tau;
1384 flange.phi = phi;
1385 end InternalSupport;
1386
1387 partial model PartialTwoFlangesAndSupport
1388 parameter Boolean useSupport = false;
1389 Flange_a flange_a;
1390 Flange_b flange_b;
1391 Support support if useSupport;
1392 protected
1393 Support internalSupport;
1394 Components.Fixed fixed if not useSupport;
1395 equation
1396 connect(support, internalSupport);
1397 connect(internalSupport, fixed.flange);
1398 end PartialTwoFlangesAndSupport;
1399
1400 partial model PartialCompliantWithRelativeStates
1401 Modelica.SIunits.Angle phi_rel(start = 0, stateSelect = stateSelect, nominal = if phi_nominal >= Modelica.Constants.eps then phi_nominal else 1);
1402 Modelica.SIunits.AngularVelocity w_rel(start = 0, stateSelect = stateSelect);
1403 Modelica.SIunits.AngularAcceleration a_rel(start = 0);
1404 Modelica.SIunits.Torque tau;
1405 Flange_a flange_a;
1406 Flange_b flange_b;
1407 parameter .Modelica.SIunits.Angle phi_nominal(displayUnit = "rad", min = 0.0) = 1e-4;
1408 parameter StateSelect stateSelect = StateSelect.prefer;
1409 equation
1410 phi_rel = flange_b.phi - flange_a.phi;
1411 w_rel = der(phi_rel);
1412 a_rel = der(w_rel);
1413 flange_b.tau = tau;
1414 flange_a.tau = -tau;
1415 end PartialCompliantWithRelativeStates;
1416
1417 partial model PartialElementaryTwoFlangesAndSupport2
1418 parameter Boolean useSupport = false;
1419 Flange_a flange_a;
1420 Flange_b flange_b;
1421 Support support(phi = phi_support, tau = (-flange_a.tau) - flange_b.tau) if useSupport;
1422 protected
1423 Modelica.SIunits.Angle phi_support;
1424 equation
1425 if not useSupport then
1426 phi_support = 0;
1427 end if;
1428 end PartialElementaryTwoFlangesAndSupport2;
1429
1430 partial model PartialElementaryRotationalToTranslational
1431 parameter Boolean useSupportR = false;
1432 parameter Boolean useSupportT = false;
1433 Rotational.Interfaces.Flange_a flangeR;
1434 Modelica.Mechanics.Translational.Interfaces.Flange_b flangeT;
1435 Rotational.Interfaces.Support supportR if useSupportR;
1436 Translational.Interfaces.Support supportT if useSupportT;
1437 protected
1438 Rotational.Interfaces.InternalSupport internalSupportR(tau = -flangeR.tau);
1439 Translational.Interfaces.InternalSupport internalSupportT(f = -flangeT.f);
1440 Rotational.Components.Fixed fixedR if not useSupportR;
1441 Translational.Components.Fixed fixedT if not useSupportT;
1442 equation
1443 connect(internalSupportR.flange, supportR);
1444 connect(internalSupportR.flange, fixedR.flange);
1445 connect(fixedT.flange, internalSupportT.flange);
1446 connect(internalSupportT.flange, supportT);
1447 end PartialElementaryRotationalToTranslational;
1448
1449 partial model PartialAbsoluteSensor
1450 Flange_a flange;
1451 equation
1452 0 = flange.tau;
1453 end PartialAbsoluteSensor;
1454
1455 partial model PartialRelativeSensor
1456 Flange_a flange_a;
1457 Flange_b flange_b;
1458 equation
1459 0 = flange_a.tau + flange_b.tau;
1460 end PartialRelativeSensor;
1461 end Interfaces;
1462
1463 end Rotational;
1464
1465 package Translational
1466 package Components
1467 model Fixed
1468 parameter .Modelica.SIunits.Position s0 = 0;
1469 Interfaces.Flange_b flange;
1470 equation
1471 flange.s = s0;
1472 end Fixed;
1473
1474 model Mass
1475 parameter .Modelica.SIunits.Mass m(min = 0, start = 1);
1476 parameter StateSelect stateSelect = StateSelect.default;
1477 extends Translational.Interfaces.PartialRigid(L = 0, s(start = 0, stateSelect = stateSelect));
1478 .Modelica.SIunits.Velocity v(start = 0, stateSelect = stateSelect);
1479 .Modelica.SIunits.Acceleration a(start = 0);
1480 equation
1481 v = der(s);
1482 a = der(v);
1483 m * a = flange_a.f + flange_b.f;
1484 end Mass;
1485
1486 model SpringDamper
1487 extends Translational.Interfaces.PartialCompliantWithRelativeStates;
1488 parameter .Modelica.SIunits.TranslationalSpringConstant c(final min = 0, start = 1);
1489 parameter .Modelica.SIunits.TranslationalDampingConstant d(final min = 0, start = 1);
1490 parameter .Modelica.SIunits.Position s_rel0 = 0;
1491 extends Modelica.Thermal.HeatTransfer.Interfaces.PartialElementaryConditionalHeatPortWithoutT;
1492 protected
1493 Modelica.SIunits.Force f_c;
1494 Modelica.SIunits.Force f_d;
1495 equation
1496 f_c = c * (s_rel - s_rel0);
1497 f_d = d * v_rel;
1498 f = f_c + f_d;
1499 lossPower = f_d * v_rel;
1500 end SpringDamper;
1501
1502 model IdealGearR2T
1503 extends Modelica.Mechanics.Rotational.Components.IdealGearR2T;
1504 end IdealGearR2T;
1505 end Components;
1506
1507 package Sources
1508 model ConstantForce
1509 extends Modelica.Mechanics.Translational.Interfaces.PartialForce;
1510 parameter Modelica.SIunits.Force f_constant;
1511 equation
1512 f = -f_constant;
1513 end ConstantForce;
1514 end Sources;
1515
1516 package Interfaces
1517 connector Flange_a
1518 .Modelica.SIunits.Position s;
1519 flow .Modelica.SIunits.Force f;
1520 end Flange_a;
1521
1522 connector Flange_b
1523 .Modelica.SIunits.Position s;
1524 flow .Modelica.SIunits.Force f;
1525 end Flange_b;
1526
1527 connector Support
1528 .Modelica.SIunits.Position s;
1529 flow .Modelica.SIunits.Force f;
1530 end Support;
1531
1532 model InternalSupport
1533 input .Modelica.SIunits.Force f;
1534 .Modelica.SIunits.Position s;
1535 Flange_a flange;
1536 equation
1537 flange.f = f;
1538 flange.s = s;
1539 end InternalSupport;
1540
1541 partial model PartialRigid
1542 .Modelica.SIunits.Position s;
1543 parameter .Modelica.SIunits.Length L(start = 0);
1544 Flange_a flange_a;
1545 Flange_b flange_b;
1546 equation
1547 flange_a.s = s - L / 2;
1548 flange_b.s = s + L / 2;
1549 end PartialRigid;
1550
1551 partial model PartialCompliantWithRelativeStates
1552 parameter StateSelect stateSelect = StateSelect.prefer;
1553 parameter .Modelica.SIunits.Distance s_nominal = 1e-4;
1554 .Modelica.SIunits.Position s_rel(start = 0, stateSelect = stateSelect, nominal = s_nominal);
1555 .Modelica.SIunits.Velocity v_rel(start = 0, stateSelect = stateSelect);
1556 .Modelica.SIunits.Force f;
1557 Translational.Interfaces.Flange_a flange_a;
1558 Translational.Interfaces.Flange_b flange_b;
1559 equation
1560 s_rel = flange_b.s - flange_a.s;
1561 v_rel = der(s_rel);
1562 flange_b.f = f;
1563 flange_a.f = -f;
1564 end PartialCompliantWithRelativeStates;
1565
1566 partial model PartialElementaryOneFlangeAndSupport2
1567 parameter Boolean useSupport = false;
1568 Modelica.SIunits.Length s;
1569 Flange_b flange;
1570 Support support(s = s_support, f = -flange.f) if useSupport;
1571 protected
1572 Modelica.SIunits.Length s_support;
1573 equation
1574 s = flange.s - s_support;
1575 if not useSupport then
1576 s_support = 0;
1577 end if;
1578 end PartialElementaryOneFlangeAndSupport2;
1579
1580 partial model PartialForce
1581 extends PartialElementaryOneFlangeAndSupport2;
1582 Modelica.SIunits.Force f;
1583 equation
1584 f = flange.f;
1585 end PartialForce;
1586 end Interfaces;
1587 end Translational;
1588 end Mechanics;
1589
1590 package Thermal
1591 package HeatTransfer
1592 package Components
1593 model ThermalCollector
1594 parameter Integer m(min = 1) = 3;
1595 Interfaces.HeatPort_a[m] port_a;
1596 Interfaces.HeatPort_b port_b;
1597 equation
1598 port_b.Q_flow + sum(port_a.Q_flow) = 0;
1599 port_a.T = fill(port_b.T, m);
1600 end ThermalCollector;
1601 end Components;
1602
1603 package Sources
1604 model FixedTemperature
1605 parameter Modelica.SIunits.Temperature T;
1606 Interfaces.HeatPort_b port;
1607 equation
1608 port.T = T;
1609 end FixedTemperature;
1610
1611 model PrescribedTemperature
1612 Interfaces.HeatPort_b port;
1613 Modelica.Blocks.Interfaces.RealInput T(unit = "K");
1614 equation
1615 port.T = T;
1616 end PrescribedTemperature;
1617 end Sources;
1618
1619 package Interfaces
1620 partial connector HeatPort
1621 Modelica.SIunits.Temperature T;
1622 flow Modelica.SIunits.HeatFlowRate Q_flow;
1623 end HeatPort;
1624
1625 connector HeatPort_a
1626 extends HeatPort;
1627 end HeatPort_a;
1628
1629 connector HeatPort_b
1630 extends HeatPort;
1631 end HeatPort_b;
1632
1633 partial model PartialElementaryConditionalHeatPortWithoutT
1634 parameter Boolean useHeatPort = false;
1635 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPort(final Q_flow = -lossPower) if useHeatPort;
1636 Modelica.SIunits.Power lossPower;
1637 end PartialElementaryConditionalHeatPortWithoutT;
1638
1639 partial model PartialConditionalHeatPort
1640 parameter Boolean useHeatPort = false;
1641 parameter Modelica.SIunits.Temperature T = 293.15;
1642 Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a heatPort if useHeatPort;
1643 Modelica.Thermal.HeatTransfer.Sources.FixedTemperature fixedTemperature(final T = T) if not useHeatPort;
1644 protected
1645 HeatPort_a internalHeatPort;
1646 equation
1647 connect(heatPort, internalHeatPort);
1648 connect(fixedTemperature.port, internalHeatPort);
1649 end PartialConditionalHeatPort;
1650 end Interfaces;
1651 end HeatTransfer;
1652 end Thermal;
1653
1654 package Math
1655 package Matrices
1656 function isEqual
1657 input Real[:, :] M1;
1658 input Real[:, :] M2;
1659 input Real eps(min = 0) = 0;
1660 output Boolean result;
1661 protected
1662 Integer nrow = size(M1, 1);
1663 Integer ncol = size(M1, 2);
1664 Integer i = 1;
1665 Integer j;
1666 algorithm
1667 result := false;
1668 if size(M2, 1) == nrow and size(M2, 2) == ncol then
1669 result := true;
1670 while i <= nrow loop
1671 j := 1;
1672 while j <= ncol loop
1673 if abs(M1[i, j] - M2[i, j]) > eps then
1674 result := false;
1675 i := nrow;
1676 j := ncol;
1677 else
1678 end if;
1679 j := j + 1;
1680 end while;
1681 i := i + 1;
1682 end while;
1683 else
1684 end if;
1685 end isEqual;
1686 end Matrices;
1687
1688 function isEqual
1689 input Real s1;
1690 input Real s2;
1691 input Real eps(min = 0) = 0;
1692 output Boolean result;
1693 algorithm
1694 result := abs(s1 - s2) <= eps;
1695 end isEqual;
1696
1697 function asin
1698 input Real u;
1699 output .Modelica.SIunits.Angle y;
1700 external "builtin" y = asin(u);
1701 end asin;
1702
1703 function atan2
1704 input Real u1;
1705 input Real u2;
1706 output .Modelica.SIunits.Angle y;
1707 external "builtin" y = atan2(u1, u2);
1708 end atan2;
1709
1710 function exp
1711 input Real u;
1712 output Real y;
1713 external "builtin" y = exp(u);
1714 end exp;
1715
1716 function tempInterpol2
1717 input Real u;
1718 input Real[:, :] table;
1719 input Integer[:] icol;
1720 output Real[1, size(icol, 1)] y;
1721 protected
1722 Integer i;
1723 Integer n;
1724 Real u1;
1725 Real u2;
1726 Real[1, size(icol, 1)] y1;
1727 Real[1, size(icol, 1)] y2;
1728 algorithm
1729 n := size(table, 1);
1730 if n <= 1 then
1731 y := transpose([table[1, icol]]);
1732 else
1733 if u <= table[1, 1] then
1734 i := 1;
1735 else
1736 i := 2;
1737 while i < n and u >= table[i, 1] loop
1738 i := i + 1;
1739 end while;
1740 i := i - 1;
1741 end if;
1742 u1 := table[i, 1];
1743 u2 := table[i + 1, 1];
1744 y1 := transpose([table[i, icol]]);
1745 y2 := transpose([table[i + 1, icol]]);
1746 assert(u2 > u1, "Table index must be increasing");
1747 y := y1 + (y2 - y1) * (u - u1) / (u2 - u1);
1748 end if;
1749 end tempInterpol2;
1750
1751 function tempInterpol2_der
1752 input Real u;
1753 input Real[:, :] table;
1754 input Integer[:] icol;
1755 input Real du;
1756 output Real[1, size(icol, 1)] dy;
1757 protected
1758 Integer i;
1759 Integer n;
1760 Real u1;
1761 Real u2;
1762 Real[1, size(icol, 1)] y1;
1763 Real[1, size(icol, 1)] y2;
1764 algorithm
1765 n := size(table, 1);
1766 if n <= 1 then
1767 dy := zeros(1, size(icol, 1));
1768 else
1769 if u <= table[1, 1] then
1770 i := 1;
1771 else
1772 i := 2;
1773 while i < n and u >= table[i, 1] loop
1774 i := i + 1;
1775 end while;
1776 i := i - 1;
1777 end if;
1778 u1 := table[i, 1];
1779 u2 := table[i + 1, 1];
1780 y1 := transpose([table[i, icol]]);
1781 y2 := transpose([table[i + 1, icol]]);
1782 assert(u2 > u1, "Table index must be increasing");
1783 dy := (y2 - y1) / (u2 - u1);
1784 end if;
1785 end tempInterpol2_der;
1786 end Math;
1787
1788 package Utilities
1789 package Streams
1790 function print
1791 input String string = "";
1792 input String fileName = "";
1793 external "C" ModelicaInternal_print(string, fileName);
1794 end print;
1795
1796 function error
1797 input String string;
1798 external "C" ModelicaError(string);
1799 end error;
1800 end Streams;
1801 end Utilities;
1802
1803 package Constants
1804 final constant Real pi = 2 * Math.asin(1.0);
1805 final constant Real eps = ModelicaServices.Machine.eps;
1806 final constant Real small = ModelicaServices.Machine.small;
1807 final constant .Modelica.SIunits.Velocity c = 299792458;
1808 final constant Real mue_0(final unit = "N/A2") = 4 * pi * 1.e-7;
1809 end Constants;
1810
1811 package SIunits
1812 package Conversions
1813 package NonSIunits
1814 type Temperature_degC = Real(final quantity = "ThermodynamicTemperature", final unit = "degC");
1815 end NonSIunits;
1816 end Conversions;
1817
1818 type Angle = Real(final quantity = "Angle", final unit = "rad", displayUnit = "deg");
1819 type Length = Real(final quantity = "Length", final unit = "m");
1820 type Position = Length;
1821 type Distance = Length(min = 0);
1822 type Time = Real(final quantity = "Time", final unit = "s");
1823 type AngularVelocity = Real(final quantity = "AngularVelocity", final unit = "rad/s");
1824 type AngularAcceleration = Real(final quantity = "AngularAcceleration", final unit = "rad/s2");
1825 type Velocity = Real(final quantity = "Velocity", final unit = "m/s");
1826 type Acceleration = Real(final quantity = "Acceleration", final unit = "m/s2");
1827 type Frequency = Real(final quantity = "Frequency", final unit = "Hz");
1828 type DampingCoefficient = Real(final quantity = "DampingCoefficient", final unit = "s-1");
1829 type Mass = Real(quantity = "Mass", final unit = "kg", min = 0);
1830 type MomentOfInertia = Real(final quantity = "MomentOfInertia", final unit = "kg.m2");
1831 type Inertia = MomentOfInertia;
1832 type Force = Real(final quantity = "Force", final unit = "N");
1833 type TranslationalSpringConstant = Real(final quantity = "TranslationalSpringConstant", final unit = "N/m");
1834 type TranslationalDampingConstant = Real(final quantity = "TranslationalDampingConstant", final unit = "N.s/m");
1835 type Torque = Real(final quantity = "Torque", final unit = "N.m");
1836 type RotationalSpringConstant = Real(final quantity = "RotationalSpringConstant", final unit = "N.m/rad");
1837 type RotationalDampingConstant = Real(final quantity = "RotationalDampingConstant", final unit = "N.m.s/rad");
1838 type Power = Real(final quantity = "Power", final unit = "W");
1839 type ThermodynamicTemperature = Real(final quantity = "ThermodynamicTemperature", final unit = "K", min = 0.0, start = 288.15, nominal = 300, displayUnit = "degC");
1840 type Temperature = ThermodynamicTemperature;
1841 type LinearTemperatureCoefficient = Real(final quantity = "LinearTemperatureCoefficient", final unit = "1/K");
1842 type HeatFlowRate = Real(final quantity = "Power", final unit = "W");
1843 type ElectricCurrent = Real(final quantity = "ElectricCurrent", final unit = "A");
1844 type Current = ElectricCurrent;
1845 type ElectricPotential = Real(final quantity = "ElectricPotential", final unit = "V");
1846 type Voltage = ElectricPotential;
1847 type MagneticFlux = Real(final quantity = "MagneticFlux", final unit = "Wb");
1848 type Inductance = Real(final quantity = "Inductance", final unit = "H");
1849 type Resistance = Real(final quantity = "Resistance", final unit = "Ohm");
1850 type Conductance = Real(final quantity = "Conductance", final unit = "S");
1851 type FaradayConstant = Real(final quantity = "FaradayConstant", final unit = "C/mol");
1852 end SIunits;
1853end Modelica;
1854
1855package Noise
1856 package Examples
1857 package Actuator
1858 model Actuator
1859 Parts.MotorWithCurrentControl Motor;
1860 Parts.Controller controller;
1861 Modelica.Blocks.Sources.Step Speed(startTime = 0.5, height = 50);
1862 Modelica.Mechanics.Rotational.Components.Gearbox gearbox(lossTable = [0, 0.85, 0.8, 0.1, 0.1], c = 1e6, d = 1e4, ratio = 10, b = 0.0017453292519943);
1863 Modelica.Mechanics.Translational.Components.IdealGearR2T idealGearR2T(ratio = 300);
1864 Modelica.Mechanics.Translational.Components.Mass mass(m = 100);
1865 Modelica.Mechanics.Translational.Sources.ConstantForce constantForce(f_constant = 10000);
1866 Modelica.Blocks.Nonlinear.SlewRateLimiter slewRateLimiter(Rising = 50);
1867 Modelica.Mechanics.Translational.Components.Mass rodMass(m = 3);
1868 Modelica.Mechanics.Translational.Components.SpringDamper elastoGap(c = 1e8, d = 1e5);
1869 equation
1870 connect(controller.y1, Motor.iq_rms1);
1871 connect(Motor.phi, controller.positionMeasured);
1872 connect(Motor.flange, gearbox.flange_a);
1873 connect(gearbox.flange_b, idealGearR2T.flangeR);
1874 connect(constantForce.flange, mass.flange_b);
1875 connect(Speed.y, slewRateLimiter.u);
1876 connect(slewRateLimiter.y, controller.positionReference);
1877 connect(rodMass.flange_a, idealGearR2T.flangeT);
1878 connect(rodMass.flange_b, elastoGap.flange_a);
1879 connect(elastoGap.flange_b, mass.flange_a);
1880 end Actuator;
1881
1882 model ActuatorLinearSystemsNoise
1883 extends Actuator(controller(redeclare Noise.Examples.Actuator.Parts.LinearSystemsNoise noiseModel));
1884 end ActuatorLinearSystemsNoise;
1885
1886 package Parts
1887 model MotorWithCurrentControl
1888 constant Integer m = 3;
1889 parameter Modelica.SIunits.Voltage VNominal = 100;
1890 parameter Modelica.SIunits.Frequency fNominal = 50;
1891 parameter Modelica.SIunits.Frequency f = 50;
1892 parameter Modelica.SIunits.Time tRamp = 1;
1893 parameter Modelica.SIunits.Torque TLoad = 181.4;
1894 parameter Modelica.SIunits.Time tStep = 1.2;
1895 parameter Modelica.SIunits.Inertia JLoad = 0.29;
1896 Modelica.SIunits.Angle phi_motor;
1897 Modelica.SIunits.AngularVelocity w;
1898 Modelica.Electrical.Machines.BasicMachines.SynchronousInductionMachines.SM_PermanentMagnet smpm(p = smpmData.p, fsNominal = smpmData.fsNominal, TsOperational = 293.15, Rs = smpmData.Rs, TsRef = smpmData.TsRef, alpha20s = smpmData.alpha20s, Lszero = smpmData.Lszero, Lssigma = smpmData.Lssigma, Jr = smpmData.Jr, Js = smpmData.Js, frictionParameters = smpmData.frictionParameters, phiMechanical(fixed = true), wMechanical(fixed = true), statorCoreParameters = smpmData.statorCoreParameters, strayLoadParameters = smpmData.strayLoadParameters, TrOperational = 293.15, VsOpenCircuit = smpmData.VsOpenCircuit, Lmd = smpmData.Lmd, Lmq = smpmData.Lmq, useDamperCage = smpmData.useDamperCage, Lrsigmad = smpmData.Lrsigmad, Lrsigmaq = smpmData.Lrsigmaq, Rrd = smpmData.Rrd, Rrq = smpmData.Rrq, TrRef = smpmData.TrRef, alpha20r = smpmData.alpha20r, permanentMagnetLossParameters = smpmData.permanentMagnetLossParameters);
1899 Modelica.Electrical.MultiPhase.Sources.SignalCurrent signalCurrent(final m = m);
1900 Modelica.Electrical.MultiPhase.Basic.Star star(final m = m);
1901 Modelica.Electrical.Analog.Basic.Ground ground;
1902 Modelica.Electrical.Machines.Utilities.CurrentController currentController(p = smpm.p);
1903 Modelica.Electrical.Machines.Sensors.VoltageQuasiRMSSensor voltageQuasiRMSSensor;
1904 Modelica.Electrical.MultiPhase.Basic.Star starM(final m = m);
1905 Modelica.Electrical.Analog.Basic.Ground groundM;
1906 Modelica.Electrical.Machines.Utilities.TerminalBox terminalBox(terminalConnection = "Y");
1907 Modelica.Electrical.Machines.Sensors.RotorDisplacementAngle rotorDisplacementAngle(p = smpm.p);
1908 Modelica.Mechanics.Rotational.Sensors.AngleSensor angleSensor;
1909 Modelica.Mechanics.Rotational.Sensors.TorqueSensor torqueSensor;
1910 Modelica.Mechanics.Rotational.Sensors.SpeedSensor speedSensor;
1911 Modelica.Mechanics.Rotational.Components.Inertia inertiaLoad(J = 0.29);
1912 parameter Modelica.Electrical.Machines.Utilities.ParameterRecords.SM_PermanentMagnetData smpmData(useDamperCage = false);
1913 Modelica.Electrical.Machines.Sensors.CurrentQuasiRMSSensor currentQuasiRMSSensor;
1914 Modelica.Blocks.Sources.Constant id(k = 0);
1915 Modelica.Blocks.Interfaces.RealInput iq_rms1;
1916 Modelica.Mechanics.Rotational.Interfaces.Flange_b flange;
1917 Modelica.Blocks.Interfaces.RealOutput phi;
1918 equation
1919 w = speedSensor.w;
1920 phi_motor = angleSensor.phi;
1921 connect(star.pin_n, ground.p);
1922 connect(rotorDisplacementAngle.plug_n, smpm.plug_sn);
1923 connect(rotorDisplacementAngle.plug_p, smpm.plug_sp);
1924 connect(terminalBox.plug_sn, smpm.plug_sn);
1925 connect(terminalBox.plug_sp, smpm.plug_sp);
1926 connect(smpm.flange, rotorDisplacementAngle.flange);
1927 connect(signalCurrent.plug_p, star.plug_p);
1928 connect(angleSensor.flange, rotorDisplacementAngle.flange);
1929 connect(angleSensor.phi, currentController.phi);
1930 connect(groundM.p, terminalBox.starpoint);
1931 connect(smpm.flange, torqueSensor.flange_a);
1932 connect(voltageQuasiRMSSensor.plug_p, terminalBox.plugSupply);
1933 connect(starM.plug_p, voltageQuasiRMSSensor.plug_n);
1934 connect(starM.pin_n, groundM.p);
1935 connect(currentController.y, signalCurrent.i);
1936 connect(speedSensor.flange, smpm.flange);
1937 connect(torqueSensor.flange_b, inertiaLoad.flange_a);
1938 connect(signalCurrent.plug_n, currentQuasiRMSSensor.plug_p);
1939 connect(currentQuasiRMSSensor.plug_n, voltageQuasiRMSSensor.plug_p);
1940 connect(id.y, currentController.id_rms);
1941 connect(currentController.iq_rms, iq_rms1);
1942 connect(inertiaLoad.flange_b, flange);
1943 connect(angleSensor.phi, phi);
1944 end MotorWithCurrentControl;
1945
1946 model Controller
1947 Modelica.Blocks.Continuous.PI speed_PI(k = 10, T = 5e-2);
1948 Modelica.Blocks.Math.Feedback speedFeedback;
1949 Modelica.Blocks.Continuous.Derivative positionToSpeed(T = 0.005);
1950 Modelica.Blocks.Interfaces.RealInput positionMeasured;
1951 Modelica.Blocks.Interfaces.RealInput positionReference;
1952 Modelica.Blocks.Interfaces.RealOutput y1;
1953 Modelica.Blocks.Continuous.PI position_PI(T = 5e-1, k = 3);
1954 Modelica.Blocks.Math.Feedback positionFeedback;
1955 Modelica.Blocks.Math.Add addNoise;
1956 replaceable .Noise.Examples.Actuator.Parts.NoNoise noiseModel constrainedby Noise.Examples.Actuator.Parts.NoiseModel;
1957 Modelica.Blocks.Continuous.FirstOrder busdelay(T = 1e-3);
1958 equation
1959 connect(positionToSpeed.y, speedFeedback.u2);
1960 connect(speedFeedback.y, speed_PI.u);
1961 connect(positionFeedback.u2, positionToSpeed.u);
1962 connect(positionReference, positionFeedback.u1);
1963 connect(positionFeedback.y, position_PI.u);
1964 connect(position_PI.y, speedFeedback.u1);
1965 connect(positionMeasured, addNoise.u2);
1966 connect(addNoise.y, positionToSpeed.u);
1967 connect(noiseModel.y, addNoise.u1);
1968 connect(speed_PI.y, busdelay.u);
1969 connect(y1, busdelay.y);
1970 end Controller;
1971
1972 model NoNoise
1973 extends NoiseModel;
1974 Modelica.Blocks.Sources.Constant noise(k = 0);
1975 equation
1976 connect(noise.y, y);
1977 end NoNoise;
1978
1979 model LinearSystemsNoise
1980 extends NoiseModel;
1981 .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Noise noise(y_max = 0.01, blockType = .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.BlockTypeWithGlobalDefault.Discrete, y_min = -0.01);
1982 inner .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.SampleClock sampleClock(blockType = .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.BlockType.Discrete, sampleTime = 1 / 2000);
1983 .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.FilterFIR filter1(blockType = .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.BlockTypeWithGlobalDefault.Discrete, L = 10);
1984 equation
1985 connect(noise.y, filter1.u);
1986 connect(filter1.y, y);
1987 end LinearSystemsNoise;
1988
1989 partial model NoiseModel
1990 extends Modelica.Blocks.Interfaces.SO;
1991 end NoiseModel;
1992 end Parts;
1993 end Actuator;
1994
1995 package Parts
1996 package Modelica_LinearSystems2
1997
1998 package Controller
1999
2000 block SampleClock
2001 parameter Types.BlockType blockType = Types.BlockType.Continuous;
2002 parameter .Noise.Examples.Parts.Modelica_LinearSystems2.Types.Method methodType = .Noise.Examples.Parts.Modelica_LinearSystems2.Types.Method.Trapezoidal;
2003 parameter Modelica.SIunits.Time sampleTime = 1;
2004 parameter Types.Init initType = Types.Init.SteadyState;
2005 output Boolean sampleTrigger;
2006 equation
2007 if blockType == Types.BlockType.Continuous then
2008 sampleTrigger = false;
2009 else
2010 sampleTrigger = sample(sampleTime, sampleTime);
2011 end if;
2012 end SampleClock;
2013
2014 block Noise
2015 parameter Real y_min;
2016 parameter Real y_max;
2017 parameter Integer[3] firstSeed(each min = 0, each max = 255) = {23, 87, 187};
2018 parameter Types.BlockTypeWithGlobalDefault blockType = Types.BlockTypeWithGlobalDefault.UseSampleClockOption;
2019 final parameter Boolean continuous = blockType == Types.BlockTypeWithGlobalDefault.Continuous or blockType == Types.BlockTypeWithGlobalDefault.UseSampleClockOption and sampleClock.blockType == Types.BlockType.Continuous;
2020 parameter Integer sampleFactor(min = 1) = 1;
2021 Modelica.Blocks.Interfaces.RealOutput y;
2022 protected
2023 outer SampleClock sampleClock;
2024 Internal.DiscreteNoise discretePart(y_min = y_min, y_max = y_max, firstSeed = firstSeed, sampleFactor = sampleFactor) if not continuous;
2025 equation
2026 if continuous then
2027 y = 0.0;
2028 end if;
2029 connect(y, discretePart.y);
2030 end Noise;
2031
2032 package Types
2033 type BlockType = enumeration(Continuous, Discrete);
2034 type BlockTypeWithGlobalDefault = enumeration(Continuous, Discrete, UseSampleClockOption);
2035 type Init = enumeration(NoInit, SteadyState, InitialState, InitialOutput);
2036 type FIRspec = enumeration(MeanValue, Window, Coefficients);
2037 type Window = enumeration(Rectangle, Bartlett, Hann, Hamming, Blackman, Kaiser);
2038 end Types;
2039
2040 package Internal
2041 block DiscreteNoise
2042 parameter Real y_min;
2043 parameter Real y_max;
2044 parameter Integer[3] firstSeed(each min = 0, each max = 255) = {23, 87, 187};
2045 parameter Integer sampleFactor(min = 1) = 1;
2046 final parameter Modelica.SIunits.Time Ts = sampleClock.sampleTime * sampleFactor;
2047 Modelica.Blocks.Interfaces.RealOutput y;
2048 protected
2049 outer SampleClock sampleClock;
2050 Integer ticks;
2051 Integer[3] seedState;
2052 Boolean sampleTrigger;
2053 discrete Real noise;
2054 discrete Real y_sampled;
2055 initial equation
2056 pre(ticks) = 0;
2057 pre(seedState) = firstSeed;
2058 equation
2059 if sampleClock.blockType == Types.BlockType.Continuous then
2060 sampleTrigger = sample(Ts, Ts);
2061 ticks = 0;
2062 else
2063 when sampleClock.sampleTrigger then
2064 ticks = if pre(ticks) < sampleFactor then pre(ticks) + 1 else 1;
2065 end when;
2066 sampleTrigger = sampleClock.sampleTrigger and ticks >= sampleFactor;
2067 end if;
2068 when {initial(), sampleTrigger} then
2069 (noise, seedState) = random(pre(seedState));
2070 y_sampled = y_min + (y_max - y_min) * noise;
2071 end when;
2072 y = y_sampled;
2073 end DiscreteNoise;
2074
2075 function random
2076 input Integer[3] seedIn;
2077 output Real x;
2078 output Integer[3] seedOut;
2079 algorithm
2080 seedOut[1] := rem(171 * seedIn[1], 30269);
2081 seedOut[2] := rem(172 * seedIn[2], 30307);
2082 seedOut[3] := rem(170 * seedIn[3], 30323);
2083 for i in 1:3 loop
2084 if seedOut[i] == 0 then
2085 seedOut[i] := 1;
2086 else
2087 end if;
2088 end for;
2089 x := rem(seedOut[1] / 30269.0 + seedOut[2] / 30307.0 + seedOut[3] / 30323.0, 1.0);
2090 end random;
2091
2092 function bessel0
2093 input Real x;
2094 output Real y;
2095 protected
2096 Real ax;
2097 Real a;
2098 algorithm
2099 ax := abs(x);
2100 if ax < 3.75 then
2101 a := (x / 3.75) ^ 2;
2102 y := 1 + a * (3.5156229 + a * (3.0899424 + a * (1.2067492 + a * (0.2659732 + a * (0.0360768 + a * 0.0045813)))));
2103 else
2104 a := 3.75 / ax;
2105 y := exp(ax) / sqrt(ax) * (0.39894228 + a * (0.01328592 + a * (0.00225319 + a * ((-0.00157565) + a * (0.00916281 + a * ((-0.02057706) + a * (0.02635537 + a * ((-0.01647633) + a * 0.00392377))))))));
2106 end if;
2107 end bessel0;
2108
2109 block DiscreteFIR
2110 extends Interfaces.PartialDiscreteSISO_equality;
2111 parameter Real[:] a = {1, 1};
2112 protected
2113 parameter Integer n = size(a, 1) - 1;
2114 discrete Real[n] x;
2115 discrete Real[n] sum;
2116 discrete Real y_sampled;
2117 initial equation
2118 x = pre(x);
2119 equation
2120 when {initial(), sampleTrigger} then
2121 u_sampled = u;
2122 x[1] = pre(u);
2123 sum[1] = a[2] * x[1];
2124 x[2:n] = pre(x[1:n - 1]);
2125 sum[2:n] = a[3:n + 1] * diagonal(x[2:n]) + sum[1:n - 1];
2126 y_sampled = a[1] * u + sum[n];
2127 end when;
2128 y = y_sampled;
2129 end DiscreteFIR;
2130
2131 function FIR_coefficients
2132 input .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.FIRspec specType = Modelica_LinearSystems2.Controller.Types.FIRspec.MeanValue;
2133 input Integer L(min = 2) = 2;
2134 input .Noise.Examples.Parts.Modelica_LinearSystems2.Types.FilterType filterType = Modelica_LinearSystems2.Types.FilterType.LowPass;
2135 input Integer order(min = 1) = 2;
2136 input Modelica.SIunits.Frequency f_cut = 1;
2137 input Modelica.SIunits.Time Ts(min = 0);
2138 input Types.Window window = Modelica_LinearSystems2.Controller.Types.Window.Rectangle;
2139 input Real beta = 2.12;
2140 input Real[:] a_desired = {1, 1};
2141 output Real[if specType == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.FIRspec.MeanValue then L else if specType == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.FIRspec.Window then if mod(order, 2) > 0 and filterType == .Noise.Examples.Parts.Modelica_LinearSystems2.Types.FilterType.HighPass then order + 2 else order + 1 else size(a_desired, 1)] a;
2142 protected
2143 constant Real pi = Modelica.Constants.pi;
2144 Boolean isEven = mod(order, 2) == 0;
2145 Integer order2 = if not isEven and filterType == .Noise.Examples.Parts.Modelica_LinearSystems2.Types.FilterType.HighPass then order + 1 else order;
2146 Real Wc = 2 * pi * f_cut * Ts;
2147 Integer i;
2148 Real[order2 + 1] w;
2149 Real k;
2150 algorithm
2151 assert(f_cut <= 1 / (2 * Ts), "The cut-off frequency f_cut may not be greater than half the sample frequency (Nyquist frequency), i.e. f_cut <= " + String(1 / (2 * Ts)) + " but is " + String(f_cut));
2152 if specType == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.FIRspec.MeanValue then
2153 a := fill(1 / L, L);
2154 elseif specType == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.FIRspec.Window then
2155 w := Internal.FIR_window(order2 + 1, window, beta);
2156 for i in 1:order2 + 1 loop
2157 k := i - 1 - order2 / 2;
2158 if i - 1 == order2 / 2 then
2159 a[i] := if filterType == .Noise.Examples.Parts.Modelica_LinearSystems2.Types.FilterType.LowPass then Wc * w[i] / pi else w[i] - Wc * w[i] / pi;
2160 else
2161 a[i] := if filterType == .Noise.Examples.Parts.Modelica_LinearSystems2.Types.FilterType.LowPass then sin(k * Wc) * w[i] / (k * pi) else w[i] * (sin(k * pi) - sin(k * Wc)) / (k * pi);
2162 end if;
2163 end for;
2164 else
2165 a := a_desired;
2166 end if;
2167 if not isEven and filterType == .Noise.Examples.Parts.Modelica_LinearSystems2.Types.FilterType.HighPass then
2168 Modelica.Utilities.Streams.print("The requested order of the FIR filter in FIR_coefficients is odd and has been increased by one to get an even order filter\n");
2169 else
2170 end if;
2171 end FIR_coefficients;
2172
2173 function FIR_window
2174 input Integer L;
2175 input .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.Window window;
2176 input Real beta = 2.12;
2177 output Real[L] a;
2178 protected
2179 Integer i = 0;
2180 constant Real pi = Modelica.Constants.pi;
2181 Real k;
2182 algorithm
2183 if window <> .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.Window.Rectangle then
2184 for i in 1:L loop
2185 k := i - 1 - (L - 1) / 2;
2186 if window == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.Window.Bartlett then
2187 a[i] := 1 - 2 * abs(k) / (L - 1);
2188 elseif window == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.Window.Hann then
2189 a[i] := 0.5 + 0.5 * cos(2 * pi * k / (L - 1));
2190 elseif window == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.Window.Hamming then
2191 a[i] := 0.54 + 0.46 * cos(2 * pi * k / (L - 1));
2192 elseif window == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.Window.Blackman then
2193 a[i] := 0.42 + 0.5 * cos(2 * pi * k / (L - 1)) + 0.08 * cos(4 * pi * k / (L - 1));
2194 elseif window == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.Window.Kaiser then
2195 k := 2 * beta * sqrt((i - 1) * (L - i)) / (L - 1);
2196 a[i] := Internal.bessel0(k) / Internal.bessel0(beta);
2197 else
2198 Modelica.Utilities.Streams.error("window = " + String(window) + " not known");
2199 end if;
2200 end for;
2201 else
2202 a := ones(L);
2203 end if;
2204 end FIR_window;
2205 end Internal;
2206
2207 block FilterFIR
2208 extends Interfaces.PartialSISO_equality;
2209 parameter Types.FIRspec specType = Modelica_LinearSystems2.Controller.Types.FIRspec.MeanValue;
2210 parameter Integer L(min = 2) = 2;
2211 parameter .Noise.Examples.Parts.Modelica_LinearSystems2.Types.FilterType filterType = Modelica_LinearSystems2.Types.FilterType.LowPass;
2212 parameter Integer order(min = 1) = 2;
2213 parameter Modelica.SIunits.Frequency f_cut = 1;
2214 parameter Types.Window window = Modelica_LinearSystems2.Controller.Types.Window.Rectangle;
2215 parameter Real beta = 2.12;
2216 parameter Real[:] a = {1, 1};
2217 protected
2218 parameter Real[:] a2 = Internal.FIR_coefficients(specType, L, filterType, order, f_cut, sampleClock.sampleTime * sampleFactor, window, beta, a) if not continuous;
2219 Internal.DiscreteFIR discretePart(sampleFactor = sampleFactor, a = a2) if not continuous;
2220 equation
2221 if continuous then
2222 y = u;
2223 end if;
2224 connect(u, discretePart.u);
2225 connect(y, discretePart.y);
2226 end FilterFIR;
2227
2228 package Interfaces
2229 partial block PartialDiscreteSISO_equality
2230 parameter Integer sampleFactor(min = 1) = 1;
2231 final parameter Modelica.SIunits.Time Ts = sampleClock.sampleTime * sampleFactor;
2232 Modelica.Blocks.Interfaces.RealInput u;
2233 Modelica.Blocks.Interfaces.RealOutput y;
2234 protected
2235 outer SampleClock sampleClock;
2236 discrete Real u_sampled;
2237 Integer ticks;
2238 Boolean sampleTrigger;
2239 initial equation
2240 pre(ticks) = 0;
2241 equation
2242 if sampleClock.blockType == Types.BlockType.Continuous then
2243 sampleTrigger = sample(Ts, Ts);
2244 ticks = 0;
2245 else
2246 when sampleClock.sampleTrigger then
2247 ticks = if pre(ticks) < sampleFactor then pre(ticks) + 1 else 1;
2248 end when;
2249 sampleTrigger = sampleClock.sampleTrigger and ticks >= sampleFactor;
2250 end if;
2251 end PartialDiscreteSISO_equality;
2252
2253 partial block PartialSISO_equality
2254 parameter .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.BlockTypeWithGlobalDefault blockType = Modelica_LinearSystems2.Controller.Types.BlockTypeWithGlobalDefault.UseSampleClockOption;
2255 final parameter Boolean continuous = blockType == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.BlockTypeWithGlobalDefault.Continuous or blockType == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.BlockTypeWithGlobalDefault.UseSampleClockOption and sampleClock.blockType == .Noise.Examples.Parts.Modelica_LinearSystems2.Controller.Types.BlockType.Continuous;
2256 parameter Integer sampleFactor(min = 1) = 1;
2257 Modelica.Blocks.Interfaces.RealInput u;
2258 Modelica.Blocks.Interfaces.RealOutput y;
2259 protected
2260 outer SampleClock sampleClock;
2261 end PartialSISO_equality;
2262 end Interfaces;
2263 end Controller;
2264
2265 package Types
2266 type Method = enumeration(ExplicitEuler, ImplicitEuler, Trapezoidal, ImpulseExact, StepExact, RampExact);
2267 type FilterType = enumeration(LowPass, HighPass, BandPass, BandStop);
2268 end Types;
2269 end Modelica_LinearSystems2;
2270 end Parts;
2271 end Examples;
2272end Noise;
2273
2274model ActuatorLinearSystemsNoise
2275 extends Noise.Examples.Actuator.ActuatorLinearSystemsNoise;
2276end ActuatorLinearSystemsNoise;