本帖最后由 taotie 于 2021-5-13 14:20 編輯
程序:
rem Main.bas file generated by New Project wizard
rem
rem Created: 周日 5月 9 2021
rem Processor: ATmega8
rem Compiler: BASCOM-AVR
rem Write your code here
'------------------------------------------------------------------------------
'name : PID速度控制
'copyright : (c) 2009 by Türk Mario
'purpose : 直流電動機的速度控制
'
'micro : Mega8
'------------------------------------------------------------------------------
$regfile = "m8def.dat"
$crystal = 8000000
$hwstack = 32
$swstack = 8
$framesize = 24
$baud = 9600
Config Pinb.0 = Output 'LED
Config Pinb.3 = Output 'PWM
Config Pinc.0 = Output '方向
Config Pinc.1 = Output '方向
Config Pind.2 = Input
Portd.2 = 1 '激活上拉
Config Portd.0 = Input '串口輸入
Portd.0 = 1
Dim E As Single
Dim Esum As Single
Dim Ealt As Single
Dim Kp As Single
Dim Ki As Single
Dim Kd As Single
Dim Ta As Single
Dim Proportionalteil As Single '比例部分為單精度
Dim Integralteil As Single '積分 部分為單精度'
Dim Differentialteil As Single '微分部分為單精度
Dim Cv As Single
Dim Gv As Single
Dim Flanken As Integer '計入側翼
Dim Flankenperturn As Integer '每圈側翼數
Dim Umdrehungen As Single
Dim Solldrehzahl As Single '目標速度
Dim Maxdrehzahl As Single '最大速度
Dim Befehl As String * 9 '指令
Dim Bcount As Integer '計數
Dim Ar(5) As String * 5
Kp = 60
Ki = 8
Kd = 0.2
Ta = 0.04
Solldrehzahl = 10 '目標速度
Maxdrehzahl = 50 '最大速度
Flankenperturn = 30 '每圈側翼數
E = 0
Esum = 0
Ealt = 0
Config Int0 = Falling '下降沿觸發中斷
Enable Interrupts
Enable Int0
On Int0 Encoder_zaehlen '發生中斷時觸發編碼器計數
Config Timer1 = Timer , Prescale = 256 'Timer1每40ms執行一次調節
On Timer1 Regler
Timer1 = 64285 ' 65535 - (8000000/256/Ta) Ta = 25
Enable Timer1
Start Timer1
'定時器2負責電機PWM
Config Timer2 = Pwm , Compare Pwm = Clear Up , Pwm = On , Prescale = 64
Ocr2 = 30
'指定方向:
Portc.0 = 1
Portc.1 = 0
'啟動PWM電機
Enable Timer2
Start Timer2
'$sim
Do '主程序
Input "" , Befehl
Bcount = Split(befehl , Ar(1) , ": ") '將字符串拆分為多個數組元素。計數=拆分(源、數組(idx)、搜索)
If Ar(1) = "Kp" Then '設置和信息選項
Kp = Val(ar(2))
End If
If Ar(1) = "Ki" Then
Ki = Val(ar(2))
End If
If Ar(1) = "Kd" Then
Kd = Val(ar(2) )
End If
If Ar(1) = "soll" Then
Solldrehzahl = Val(ar(2))
End If
If Ar(1) = "max" Then
Maxdrehzahl = Val(ar(2))
End If
If Ar(1) = "rps" Then
Print Umdrehungen
End If
If Ar(1) = "pid" Then
Print "Kp=" ; Kp
Print "Ki=" ; Ki
Print "Kd=" ; Kd
End If
If Ar(1) = "pwm" Then
Print Ocr2
End If
Loop
Encoder_zaehlen: '所有邊緣都在這里計算
Incr Flanken
Return
Regler: 'PID控制器算法
Timer1 = 64285
Umdrehungen = Flanken / Ta '確定每秒的轉數
Umdrehungen = Umdrehungen / Flankenperturn
Flanken = 0 '將邊緣計數器設置為零
E = Solldrehzahl - Umdrehungen '計算控制偏差
Esum = Esum + E '加總錯誤
Proportionalteil = Kp * E '計算比例項
Integralteil = Ki * Ta '計算積分項
Integralteil = Integralteil * Esum
Differentialteil = E - Ealt '計算微分項
Differentialteil = Differentialteil / Ta
Differentialteil = Differentialteil * Kd
Cv = Proportionalteil + Integralteil '匯總所有鏈接
Cv = Cv + Differentialteil
Gv = Maxdrehzahl / 255 '轉移到PWM占空比
Gv = Gv * Cv
If Gv < 0 Then Gv = 0
If Gv > 255 Then Gv = 255
Ocr2 = Gv '電機PWM進行了相應的調整
Ealt = E '注意下一次運行的規則錯誤
Return
工程文件:用8.9版打開
新建文件夾 (3).zip
(205.6 KB, 下載次數: 14)
2021-5-13 13:41 上傳
點擊文件名下載附件
|