Ich habe dafür einen extra arduino pro mini 3.3V, 8MHz genommen. Das ist der Code glaube ich....:
Code:
'===CHIP SETTINGS===
$regfile = "m328pdef.dat"
$framesize = 128
$swstack = 128
$hwstack = 128
$crystal = 8000000
$baud = 38400
Config Pind.2 = Input 'eoc
Config Pinb.5 = Output 'green led
Dim Ac1 As Single
Dim Ac2 As Single
Dim Ac3 As Single
Dim Ac4 As Long
Dim Ac5 As Long
Dim Ac6 As Long
Dim B1 As Single
Dim B2 As Single
Dim B3 As Long
Dim B4 As Long
Dim B4a As Single
Dim B5 As Single
Dim B6 As Single
Dim B7 As Long
Dim B7a As Long
Dim Mb As Single
Dim Mc As Single
Dim Md As Single
Dim Ut As Long
Dim Up As Long
Dim X1 As Single
Dim X2 As Single
Dim X3 As Single
Dim Zwr1 As Single
Dim Zwr2 As Single
Dim Zwr3 As Single
Dim Zwr4 As Single
Dim T As Single
Dim P As Single
Dim Po As Single
Dim A As Single
Dim Height_filt As Single
Dim A2(6) As Integer 'Word
Dim Height As Integer 'Word
Dim Averaging As Byte
Dim I As Byte
Dim Startup As Word
Dim Okay As Bit
Dim Heightzero As Single
Dim Adres As Byte
Dim Value As Byte
Dim Result As Integer
Dim Hi As Long
Dim P_set_height As Single
Dim P_set_height_old As Single
Dim I_set_height As Single
Dim D_set_height As Single
Dim P_set_height_out As Single
Dim I_set_height_out As Single
Dim D_set_height_out As Single
Dim Setpoint_height As Single
Dim Outputpid As Byte
Dim Outputpid_height_integer As Single
'output:
Dim Command(2) As Byte
'compass
' I2C-Slave-Address of the HMC6352 Digital Compass Module and Configuration values
Const Compass_address = &H42
Dim Compass_w_array(3) As Byte
Compass_w_array(1) = &H47 ' "G"-Command: write to RAM
Compass_w_array(2) = &H74 ' RAM Address H74: Operational Mode
'Compass_w_array(3) = &B01110000 ' 20Hz, Set/Reset=yes, Standby mode
Compass_w_array(3) = &B01110010 ' 20Hz, Set/Reset=yes, Standby mode
' Compass value read variables
Dim Compass_r_array(2) As Byte ' Byte array for the two bytes of heading value
Dim Compass_value As Word At Compass_r_array(1) Overlay ' WORD variable for the heading value
Dim Compass_value2(6) As Integer
Dim Heading As Integer
Dim Setpoint_heading As Integer
Dim P_set_heading As Integer
Dim P_set_heading_raw As Integer
Dim P_set_heading_raw_abs As Word
Dim P_set_heading_v1 As Integer
Dim P_set_heading_v1_abs As Word
Dim P_set_heading_out As Integer
Dim I_set_heading_out As Integer
Dim I_set_heading As Single
Dim Outputpid_heading_integer As Integer
'===READ RX SETTINGS===
Config Timer0 = Timer , Prescale = 256
On Timer0 Detectrxpause 'timer overflow = pause in receiver's signal
Config Int1 = Rising
On Int1 Getreceiver
$lib "i2c_twi.lbx" ' we do not use software emulated I2C but the TWI
Config Scl = Portc.5 ' we need to provide the SCL pin name
Config Sda = Portc.4 ' we need to provide the SDA pin name
I2cinit
Declare Sub Write_bmp(byval Adres As Byte , Byval Value As Byte)
Declare Sub Read_bmp(byval Adres As Byte , Value As Byte)
Declare Sub Read_reg
Const Addressw = &B11101110 'slave write address
Const Addressr = &B11101111 'slave read address
'--Read Receiver (Rx)--
Dim Empf(6) As Word 'data from getreceiver interrupt
Dim Sempf(6) As Integer 'rescaled data
Dim Channel As Byte 'current channel to be read out
Dim Rc_on_counter As Word 'counter that counts the amount of correct rx signals
Dim Poslock As Bit
Dim Poslock_old As Bit
Config Twi = 100000
Enable Timer0
Enable Int1
Enable Interrupts
Config Serialout = Buffered , Size = 254
Clear Serialout
Waitms 100
'hole Kalibrierungsdaten
'-------------------------------------------------------------------------------
Adres = &HAA 'Startadresse calibration data
Call Read_reg
Ac1 = Result
Call Read_reg
Ac2 = Result
Call Read_reg
Ac3 = Result
Call Read_reg
Ac4 = Result
Call Read_reg
Ac5 = Result
Call Read_reg
Ac6 = Result
Call Read_reg
B1 = Result
Call Read_reg
B2 = Result
Call Read_reg
Mb = Result
Call Read_reg
Mc = Result
Call Read_reg
Md = Result
Averaging = 1
'compass config
I2csend Compass_address , Compass_w_array(1) , 3 ' set Compass Configuration
Waitms 100
Do
If Empf(5) > 185 And Empf(6) > 170 Then
Poslock = 1
Else
Poslock = 0
End If
'lese kompass:
I2creceive Compass_address , Compass_r_array(1) , 0 , 2 ' receive the two heading bytes MSB first
Swap Compass_r_array(1) , Compass_r_array(2) ' swap MSB and LSB bytes to be read as WORD variable
Compass_value = Compass_value / 10
'Print Compass_value 'in degrees
'hole Rohdaten Temperatur
'-------------------------------------------------------------------------------
If Averaging = 1 Then 'datasheet: would be enough to get temp every second
If Okay = 1 Then
Toggle Portb.5
End If
Call Write_bmp(&Hf4 , &H2E)
While Pind.2 < 1 'wait until EOC is 1 ca. 5ms
Waitus 100
Wend
Call Read_bmp(&Hf6 , Value) 'read it back
Hi = Value * 256
Call Read_bmp(&Hf7 , Value) 'read it back
Ut = Hi + Value
End If
'hole Rohdaten Luftdruck
'-------------------------------------------------------------------------------
'Call Write_bmp(&Hf4 , &HF4) 'ultra-high precision mode
'Call Write_bmp(&Hf4 , &H34) 'normal mode
Call Write_bmp(&Hf4 , &HB4) 'high precision mode
While Pind.2 < 1 ''wait until EOC is 1 ca. 26 ms in ultra high precision mode
Waitus 100
Wend
Call Read_bmp(&Hf6 , Value) 'read it back
Hi = Value * 256
Call Read_bmp(&Hf7 , Value) 'read it back
Up = Hi + Value
'kalkuliere tatsaechliche Temperatur
'-------------------------------------------------------------------------------
Zwr1 = Ut - Ac6 : Zwr2 = 2 ^ 15 : Zwr2 = Ac5 / Zwr2 : X1 = Zwr1 * Zwr2
Zwr1 = 2 ^ 11 : Zwr2 = Mc * Zwr1 : Zwr3 = X1 + Md : X2 = Zwr2 / Zwr3 : B5 = X1 + X2
T = B5 + 8 : Zwr3 = 2 ^ 4 : T = T / Zwr3 : T = T / 10
'kalkuliere tatsaechlichen Luftdruck
'-------------------------------------------------------------------------------
B6 = B5 - 4000 : Zwr1 = 2 ^ 11 : Zwr2 = 2 ^ 12 : Zwr3 = B6 / Zwr2 : Zwr3 = B6 * Zwr3 : Zwr4 = B2 * Zwr3 : X1 = Zwr4 / Zwr1
Zwr1 = 2 ^ 11 : Zwr2 = B6 / Zwr1 : X2 = Ac2 * Zwr2 : X3 = X1 + X2
Zwr1 = Ac1 * 4 : Zwr1 = Zwr1 + X3 : Zwr1 = Zwr1 + 2 : B3 = Zwr1 / 4
Zwr1 = 2 ^ 13 : Zwr2 = B6 / Zwr1 : X1 = Ac3 * Zwr2
Zwr1 = 2 ^ 12 : Zwr2 = 2 ^ 16 : Zwr3 = B6 / Zwr1 : Zwr3 = B6 * Zwr3 : Zwr4 = B1 * Zwr3 : X2 = Zwr4 / Zwr2
X3 = X1 + X2 : X3 = X3 + 2 : X3 = X3 / 4
Zwr1 = X3 + 32768 : Zwr2 = 2 ^ 15 : Zwr3 = Zwr1 / Zwr2 : B4a = Ac4 * Zwr3 : B4 = Abs(b4a)
B7 = Up - B3 : B7a = B7 * 50000 : Zwr1 = B7a * 2 : Zwr1 = Zwr1 / B4 : Zwr2 = B7a / B4 : Zwr2 = Zwr2 * 2
If B7a < &H8000000 Then P = Zwr1 Else P = Zwr2
Zwr1 = 2 ^ 8 : Zwr2 = P / Zwr1 : X1 = Zwr2 * Zwr2
Zwr1 = 2 ^ 16 : X1 = X1 * 3028 : X1 = X1 / Zwr1 : X1 = Abs(x1)
Zwr1 = -7357 * P : Zwr2 = 2 ^ 16 : X2 = Zwr1 / Zwr2
Zwr1 = X1 + X2 : Zwr1 = Zwr1 + 3791 : Zwr2 = 2 ^ 4 : Zwr1 = Zwr1 / Zwr2 : P = P + Zwr1 : P = P / 100
'kalkuliere Hoehenwerte
'-------------------------------------------------------------------------------
Po = 1013.25 'Pressure auf Seepegel
Zwr1 = 1 / 5.255 : Zwr2 = P / Po : Zwr3 = Zwr2 ^ Zwr1 : Zwr4 = 1 - Zwr3 : A = 44330 * Zwr4
If Okay = 0 Then
If Startup < 200 Then
Startup = Startup + 1
If Startup > 150 Then
Heightzero = Heightzero + A
End If
Else
Okay = 1
Heightzero = Heightzero / 50
End If
End If
A = A - Heightzero
A = A * 100 'höhe in zentimetern
If Okay = 0 Then
Height_filt = A
For I = 1 To 6
A2(i) = A
Next
End If
Height_filt = Height_filt * 0.965 '0.96
A = A * 0.035 '0.04
Height_filt = Height_filt + A
Height_filt = Height_filt
If Averaging <= 6 Then
A2(averaging) = Int(height_filt)
Averaging = Averaging + 1
End If
If Averaging = 7 Then 'reduced output rate
Height = 0
For I = 1 To 6
Height = Height + A2(i)
Next
Height = Height / 6
Heading = Compass_value
If Poslock_old <> Poslock Then 'switched
If Poslock = 1 Then
Setpoint_height = Height
Setpoint_heading = Heading
P_set_height = 0
P_set_heading = 0
I_set_height = 0
I_set_heading = 0
D_set_height = 0
End If
If Poslock = 0 Then 'switch off
Command(1) = 128
Command(2) = 128
Printbin Command(1)
End If
Poslock_old = Poslock
End If
If Okay = 1 And Poslock = 1 Then
P_set_height = Setpoint_height - Height
P_set_height_out = P_set_height * 0.03 '10cm --> 1.5 direkt auf motoren
I_set_height = I_set_height + P_set_height
If I_set_height > 500000 Then
I_set_height = 500000
End If
If I_set_height < -500000 Then
I_set_height = -500000
End If
I_set_height_out = I_set_height * 0.00008 '0.00005
D_set_height = P_set_height - P_set_height_old
D_set_height_out = D_set_height * 0.16 '0.1
P_set_height_old = P_set_height
'Print Height ; " " ; P_set_height_out ; " " ; i_set_height_out ; " " ; d_set_height_out
'Print "height: " ; Height
Outputpid_height_integer = 128 + P_set_height_out
Outputpid_height_integer = Outputpid_height_integer + I_set_height_out
Outputpid_height_integer = Outputpid_height_integer + D_set_height_out
If Outputpid_height_integer > 254 Then
Outputpid_height_integer = 254
End If
If Outputpid_height_integer < 0 Then
Outputpid_height_integer = 0
End If
'heading
P_set_heading_raw = Setpoint_heading - Heading
''(
If P_set_heading_raw > 0 Then
P_set_heading_v1 = P_set_heading_raw - 359
P_set_heading_v1_abs = Abs(p_set_heading_v1)
P_set_heading_raw_abs = Abs(p_set_heading_raw)
If P_set_heading_v1_abs > P_set_heading_raw_abs Then
P_set_heading = P_set_heading_raw
Else
P_set_heading = P_set_heading_v1
End If
Elseif P_set_heading_raw < 0 Then
P_set_heading_v1 = P_set_heading_raw + 359
P_set_heading_v1_abs = Abs(p_set_heading_v1)
P_set_heading_raw_abs = Abs(p_set_heading_raw)
If P_set_heading_v1_abs > P_set_heading_raw_abs Then
P_set_heading = P_set_heading_raw
Else
P_set_heading = P_set_heading_v1
End If
End If
'')
'P_set_heading = P_set_heading_raw
'print p_set_heading
P_set_heading_out = P_set_heading / 2
I_set_heading = I_set_heading + P_set_heading
If I_set_heading > 960 Then
I_set_heading = 960
End If
If I_set_heading < -960 Then
I_set_heading = -960
End If
I_set_heading_out = I_set_heading / 16 ' *0.1 geht nich...
I_set_heading_out = 0
Outputpid_heading_integer = 128 + P_set_heading_out
Outputpid_heading_integer = Outputpid_heading_integer + I_set_heading_out
'Print Heading ; " " ; P_set_heading_out ; " " ; I_set_heading_out ; " " ; Outputpid_heading_integer
If Outputpid_heading_integer > 254 Then
Outputpid_heading_integer = 254
End If
If Outputpid_heading_integer < 0 Then
Outputpid_heading_integer = 0
End If
Command(1) = Outputpid_height_integer
Command(2) = Outputpid_heading_integer
'Printbin Command(1)
Print Height ; " " ; Heading
End If
Averaging = 1
End If
Loop
End
'------------------------------------------------------------
Sub Read_reg
Call Read_bmp(adres , Value)
Hi = Value * 256
Adres = Adres + 1
Call Read_bmp(adres , Value)
Result = Hi + Value
Adres = Adres + 1
End Sub
'----------------------------------------------------------
Sub Write_bmp(byval Adres As Byte , Byval Value As Byte)
I2cstart 'start condition
I2cwbyte Addressw 'slave address
I2cwbyte Adres 'address of register
I2cwbyte Value 'value to write
I2cstop 'stop condition
End Sub
'----------------------------------------------------------
Sub Read_bmp(byval Adres As Byte , Value As Byte)
I2cstart 'generate start
I2cwbyte Addressw 'slave address
I2cwbyte Adres 'address of register
I2cstart 'repeated start
I2cwbyte Addressr 'slave address (read)
I2crbyte Value , Nack 'read byte
I2cstop 'generate stop
End Sub
'===READ RX=====================================================================
Getreceiver: 'falling edge detection
If Channel > 0 And Channel < 7 Then 'fill empf(1-5)
Empf(channel) = Timer0
End If
Timer0 = 131 'preload for 4.096 ms
Incr Channel 'if no falling edge was detected for a longer period, channel will increase above 11
Return 'that means that there are problems with the receiver
Detectrxpause:
Channel = 0
Timer0 = 131 'preload for 4.096 ms
Return
Lesezeichen