Skip to content

Commit 62bed5a

Browse files
committed
add loopshapingPD
1 parent 8f2f89b commit 62bed5a

File tree

1 file changed

+40
-0
lines changed

1 file changed

+40
-0
lines changed

lib/ControlSystemsBase/src/pid_design.jl

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -519,6 +519,46 @@ function loopshapingPI(P0, ωp; ϕl=0, rl=0, phasemargin=0, form::Symbol=:standa
519519
(; C, kp, ki, fig, CF)
520520
end
521521

522+
function loopshapingPD(P0, ωp; ϕl=0, rl=0, phasemargin=0, form::Symbol=:standard, doplot=false, Tf = nothing, F=nothing)
523+
issiso(P0) || throw(ArgumentError("P must be SISO"))
524+
if F === nothing && Tf !== nothing
525+
F = tf(1, [Tf^2, 2*Tf/sqrt(2), 1])
526+
end
527+
if F !== nothing
528+
P = P0*F
529+
else
530+
P = P0
531+
end
532+
Pw = freqresp(P, ωp)[]
533+
ϕp = angle(Pw)
534+
rp = abs.(Pw)
535+
536+
if phasemargin > 0
537+
ϕl == 0 || @warn "Both phasemargin and ϕl provided, the provided value for ϕl will be ignored."
538+
ϕl = deg2rad(-180+phasemargin)
539+
else
540+
ϕl = ϕl == 0 ? ϕp : ϕl
541+
end
542+
rl = rl == 0 ? rp : rl
543+
544+
kp = rl/rp*cos(ϕp-ϕl)
545+
kd = rl/(rp*ωp)*sin(ϕl-ϕp)
546+
C = pid(kp, 0, kd, form=:parallel)
547+
CF = F === nothing ? C : C*F
548+
549+
fig = if doplot
550+
w = exp10.(LinRange(log10(ωp)-2, log10(ωp)+2, 500))
551+
f1 = gangoffourplot(P0,CF, w)
552+
f2 = nyquistplot([P0 * CF, P0], w, ylims=(-4,2), xlims=(-4,1.2), unit_circle=true, show=false, lab=["PC" "P"])
553+
RecipesBase.plot!([rl*cos(ϕl)], [rl*sin(ϕl)], lab="Specification point", seriestype=:scatter)
554+
RecipesBase.plot(f1, f2)
555+
else
556+
nothing
557+
end
558+
kp, _, kd = convert_pidparams_from_parallel(kp, 0, kd, form)
559+
(; C, kp, kd, fig, CF)
560+
end
561+
522562

523563
"""
524564
C, kp, ki = placePI(P, ω₀, ζ; form=:standard)

0 commit comments

Comments
 (0)