
reaper7
Members-
Posts
9 -
Joined
-
Last visited
reaper7's Achievements

Seeker (1/7)
0
Reputation
-
Glad you have it working . Real thanks goes to Martin and his UDF - his helped me to work it out Initially.
-
Hi adolfito, Sure no problem you can use this to get you up and running. I've included code for 2 servos bit its simple to add more to it. Code for Autoit #include 'CommMG.au3' ;Internal for the Serial UDF Global $sportSetError = '' ;COM Vars Global $CMPort = 1 ; Port Global $CmBoBaud = 9600 ; Baud Global $CmboDataBits = 8 ; Data Bits Global $CmBoParity = "none" ; Parity Global $CmBoStop = 1 ; Stop Global $setflow = 2 ; Flow _CommSetPort($CMPort, $sportSetError, $CmBoBaud, $CmboDataBits, $CmBoParity, $CmBoStop, $setflow) _CommSetRTS(0) _CommSetDTR(0) If @error Then ConsoleWrite("Error in Com Port!" & @CR) Exit EndIf while 1 (Your code to create the values to send to servo 1 and 2) _CommSendString(stringformat("A%03d",int($Servo1))) _CommSendString(stringformat("B%03d",int($Servo2))) WEnd This (stringformat("A%03d",int($Servo1))) part is sending the following Axxx (where x is a value between 000 and 999) the value xxx is whats contained in $Servo1. This is then read into the Arduino as follows And Code for Arduino #include <Servo.h> Servo Servo1; // create servo called Servo1 Servo Servo2; // create servo called Servo2 char Address; //Variable to store Incoming Packets ID int val = 0; int data = 0; void setup() { Serial.begin(9600); Servo1.attach(8); // attaches the servo1 on pin 8 to the servo object Servo2.attach(9); // attaches the servo2 on pin 9 to the servo object } void loop() { while (Serial.available() > 0) { Address = Serial.read(); if (Address == 'A') Read_Servo1(); // If ID = A goto Servo1 if (Address == 'B') Read_Servo2(); // If ID = B goto Servo2 } } void Read_Servo1() { delay(2); int data100 = Serial.read()- '0'; // Read in first bit od data delay(2); int data10 = Serial.read()- '0'; // Read in second bit od data delay(2); int data1 = Serial.read()- '0'; // Read in third bit od data data = 100*data100 + 10*data10 + data1; // Left shift each byte, add add together to get our value 000 val = map(data, 0, 200, 10, 180); // Asign our range of 0 - 200 to the servos range of 0 - 180 Servo1.write(val); //Write the value to Serial delay(10); // waits 10ms for the servo to reach the position } void Read_Servo2() { delay(2); int data100 = Serial.read()- '0'; delay(2); int data10 = Serial.read()- '0'; delay(2); int data1 = Serial.read()- '0'; data = 100*data100 + 10*data10 + data1; val = map(data, 0, 250, 10, 180); Servo2.write(val); delay(10); // waits 10ms for the servo to reach the position } You need to change your range to suit the range of values you are sending your servo. Eg I'm sending a range of 0 to 200 to my servo so the above converts 1-200 into the range of travel of my servo 0deg to 180deg. So for you first servo you could have [val = map(data, 0, 20, 0, 90);] This would convert your range of 0-20 into the servo movement of 0deg to 90deg. Also I'm sending and reviving numbers in the range of 1-999 ie: 3 characters long, you could change the above code easily to send in the range of 0-99 2 characters long very easily. Hope that helps.
-
Cheers Martin, Appreciate you taking time out to answer my questions. Got some Arduino Books ordered so hopefully they answer my remaining questions. Thanks for your Serial scripts they have brought my project to life.
- 680 replies
-
- serial port
- virtual port
-
(and 2 more)
Tagged with:
-
Thanks Martin Finally got it working once I got my head around it all. Here's my working code so far AUTOIT: #include <NomadMemory2.au3> #include <GUIConstants.au3> #include <String.au3> #include <Date.au3> #include <array.au3> #Include <Misc.au3> #include 'CommMG.au3' $path = RegRead("HKEY_LOCAL_MACHINE\SOFTWARE\xxxxxxxxx\xxxxxxxxxxxx", "InstalledPath") If StringRight($path, 1) <> "\" Then $path &= "\" If NOT ProcessExists("xxxxxxxx.exe") Then Run($path & "sxxxxxxxxxx.exe") EndIf sleep(10000) Global $ProcessID = WinGetProcess("xxxxxxxxxxx","") sleep(2000) ;Internal for the Serial UDF Global $sportSetError = '' ;COM Vars Global $CMPort = 1 ; Port Global $CmBoBaud = 9600 ; Baud Global $CmboDataBits = 8 ; Data Bits Global $CmBoParity = "none" ; Parity Global $CmBoStop = 1 ; Stop Global $setflow = 2 ; Flow Global $TorpSpeedValue _CommSetPort($CMPort, $sportSetError, $CmBoBaud, $CmboDataBits, $CmBoParity, $CmBoStop, $setflow) _CommSetRTS(0) _CommSetDTR(0) If @error Then ConsoleWrite("Error in Com Port!" & @CR) Exit EndIf while 1 $TorpedoDepth = Read_Torpedo_Depth () $SalvoAngle = Read_Salvo_Angle () _CommSendString(stringformat("A%03d",int($SalvoAngle*10))) Sleep(10) _CommSendString(stringformat("B%03d",int($TorpedoDepth*10))) Sleep(10) WEnd ;################################## ;Function Read Torpedo Depth ;################################## Func Read_Torpedo_Depth () Local $TorpedoDepthValue, $TorpedoDepthPointer_1 Local $TorpedoDepthOffset1 = 0x50 Local $DllInformation = _MemoryOpen($ProcessID) $TorpedoDepthValue = _MemoryRead(0x5543DC, $DllInformation) $TorpedoDepthPointer_1 = '0x' & hex($TorpedoDepthValue + $TorpedoDepthOffset1) $TorpedoDepthValue = _MemoryRead($TorpedoDepthPointer_1, $DllInformation, 'float') _MemoryClose($DllInformation) Return $TorpedoDepthValue EndFunc ;################################## ;Function Read Salvo Angle ;################################## Func Read_Salvo_Angle () Local $SalvoAngleValue, $SalvoAnglePointer_1, $SalvoAngleSend Local $SalvoAngleOffset1 = 0x94 Local $DllInformation = _MemoryOpen($ProcessID) $SalvoAngleValue = _MemoryRead(0x5543DC, $DllInformation) $SalvoAnglePointer_1 = '0x' & hex($SalvoAngleValue + $SalvoAngleOffset1) $SalvoAngleValue = _MemoryRead($SalvoAnglePointer_1, $DllInformation, 'float') $SalvoAngleSend = Round($SalvoAngleValue, 1) _MemoryClose($DllInformation) Return $SalvoAngleSend EndFunc And my Arduino: //****************************** ALPHA SIMULATOR PANEL ****************************** //****************************** JOHN GREANEY V0.01 ****************************** #include <Servo.h> Servo SalvoAngle; // create servo called SalvoAngle Servo TorpedoDepth; // create servo called TorpedoDepth char Address; //Variable to store Incoming Packets ID int val = 0; int data = 0; //****************************** Main Setup ****************************** void setup() { Serial.begin(9600); TorpedoDepth.attach(8); // attaches the servo on pin 8 to the servo object SalvoAngle.attach(9); // attaches the servo on pin 9 to the servo object } //****************************** READ ADDRESS IDENTIFIERS ****************************** void loop() { while (Serial.available() > 0) { Address = Serial.read(); if (Address == 'A') Read_SalvoAngle(); // If ID = A goto SalvoAngle if (Address == 'B') Read_TorpedoDepth(); // If ID = B goto TorpedoDepth } } //****************************** READ DATA IN FROM SERIAL ****************************** //****************************** SALVO ANGLE SERVO ROUTINE ****************************** void Read_SalvoAngle() { delay(2); int data100 = Serial.read()- '0'; // Read in first bit od data delay(2); int data10 = Serial.read()- '0'; // Read in second bit od data delay(2); int data1 = Serial.read()- '0'; // Read in third bit od data data = 100*data100 + 10*data10 + data1; // Left shift each byte, add add together to get our value 000 val = map(data, 0, 200, 10, 180); // Asign our range of 0 - 200 to the servos range of 0 - 180 SalvoAngle.write(val); //Write the value to Serial delay(10); // waits 10ms for the servo to reach the position } //****************************** TORPDEDO DEPTH SERVO ROUTINE ****************************** void Read_TorpedoDepth() { delay(2); int data100 = Serial.read()- '0'; delay(2); int data10 = Serial.read()- '0'; delay(2); int data1 = Serial.read()- '0'; data = 100*data100 + 10*data10 + data1; val = map(data, 0, 250, 10, 180); TorpedoDepth.write(val); delay(10); // waits 10ms for the servo to reach the position } It works perfectly, reads the two values from Sim Memory (Floats) and sends them via serial to the Arduino. The Arduino takes the values and send them to there relevant servo routine. (I've decided not to convert to decimal place and leave my value*10 - ie instead of 20.2 its 202) This value is then mapped to the servos range of 0 to 180. When running - The Servos now rotate in conjunction with the Dials Needles in the Sim So that's a great start - now I need to do all the dials and other values. One question though for now - Im using the startbit from "_CommSendString(stringformat("A%03d",int($SalvoAngle*10))" So 'A' is the ascii value that the serial looks for and jumps to the relevant routine. How could I remake my code to read in two ascii characters to give me more ID addresses as I dont have enough using just one ascii character (I reckon I need at least 100 IDs and not 50) For example in AutoIt sending the following: "_CommSendString(stringformat("ZA%03d",int($SalvoAngle*10)) Had tried the following with no success void loop() { while (Serial.available() > 0) { Address1 = Serial.read(); while (Address1 == 'Z') { Address2 = Serial.read(); if (Address2 == 'A') Read_SalvoAngle(); // If ID = ZA goto SalvoAngle if (Address2 == 'B') Read_TorpedoDepth(); // If ID = ZB goto TorpedoDepth } } } And this void loop() { while (Serial.available() > 0) { Address1 = Serial.read(); Address2 = Serial.read(); if (Address2 == 'Z' && Address2 == 'A') Read_SalvoAngle(); // If ID = ZA goto SalvoAngle if (Address2 == 'Z' && Address2 == 'B') Read_TorpedoDepth(); // If ID = ZB goto TorpedoDepth } }: Any suggestions
- 680 replies
-
- serial port
- virtual port
-
(and 2 more)
Tagged with:
-
Thanks Martin, that gives me a good footing to work with. Using your String example above - can this also be used for negative float values eg -100.5 Regards John G
- 680 replies
-
- serial port
- virtual port
-
(and 2 more)
Tagged with:
-
Hi Martin, thanks for assist but I've being trying to understand all this but getting nowhere fast This is what I have that works so far: Auto it code: #include 'CommMG.au3' ;Internal for the Serial UDF Global $sportSetError = '' ;COM Vars Global $CMPort = 1 ; Port Global $CmBoBaud = 9600 ; Baud Global $CmboDataBits = 8 ; Data Bits Global $CmBoParity = "none" ; Parity Global $CmBoStop = 1 ; Stop Global $setflow = 2 ; Flow _CommSetPort($CMPort, $sportSetError, $CmBoBaud, $CmboDataBits, $CmBoParity, $CmBoStop, $setflow) _CommSetRTS(0) _CommSetDTR(0) If @error Then ConsoleWrite("Error in Com Port!" & @CR) Exit EndIf while 1 // Only showing one of the Functions - There are over 50 of them $TargetRange = Read_Target_Range () // Calls the Function Read_Target_Range ;_CommSendstring($TargetRange) // Send the value for Range Sleep(100) // Delay to stop overuse of comms WEnd //Only showing 1 of the 50 plus memory ;################################## ;Function Read Target Range from Memory ;################################## Func Read_Target_Range () //Function not shown - but works ok //function returns a one decimal placed Float //value is in range from 0 to 160 (Will display the needle position on a dial). Return $TargetRangeValue EndFunc And my arduino code #include <Servo.h> Servo ServoAngleServo; // create servo object to control a servo int ServoAngleValue; // variable to store the servo position void setup() { Serial.begin(9600); ServoAngleServo.attach(9); // attaches the servo on pin 9 to the servo object } void loop() { if (Serial.available()) // wait for serial input { ServoAngleValue = Serial.read(); // read the incoming byte: Serial.write(ServoAngleValue); if(ServoAngleValue >=0 and ServoAngleValue <= 180) { ServoAngleValue = map(ServoAngleValue, 0, 20, 10, 180); // Reads the sent value (Range 0-20) and converts to servo momement (0-180 degrees) ServoAngleServo.write(ServoAngleValue); delay(15); // waits 15ms for the servo to reach the position } } } The above works but values are not received as float but int values eg In Autoit I send a value for $TargetRange of 10.6 it only send the value 10. This is received by the arduino as 10 and the servo responds correctly ( But this resolution is not accurate enough due to stepper only moving in 1 degree steps (Due to decimal place being lost). I have tried using: $sf = Dllstructcreate("float") $psf = dllstructgetptr($sf) $sb = DllStructCreate("byte;byte;byte;byte", $psf);array of bytes but in same memory location as the float $srf = Dllstructcreate("byte;byte;byte;byte");to hold the reversed bytes<br>$psrf = DllStructGetPtr($srf) for $h = 1 to 4 DllStructSetData($srf,$h,dllstructgetdata($sb,5 - $h)) Next _CommSendByteArray($psrf,4,1) But this does not seem to send my value correctly example sending value of 0.6 shows 33?A (33:33:D7:41) in 'Free Serial Port Monitor'. What I hope to do with Autoit Serial comms: I wish to send to the Arduino using serial handshake the following a; start bit, 1byte (0x7E) b: ID, 1byte (eg 0x01) c: float value, 4bytes (eg Float 285.4) e: end bit. 1byte (oxFF) I can use the above to send each value one by one, and with code on the Arduino detect the startbit, read in the ID and assign it to relevant variable, then read in the 4bytes for for the value and convert back to float. When end byte is received wait for new data. Again my knowledge on serial comms is very weak, but I know it should be straight forward enough - but alas it eludes me at this moment in time
- 680 replies
-
- serial port
- virtual port
-
(and 2 more)
Tagged with:
-
Posted twice in error
- 680 replies
-
- serial port
- virtual port
-
(and 2 more)
Tagged with:
-
Hi Martin, new to all this so learning as I go along. I've managed to use your UDF to communicate to an Arduino development board to control a Servo Motor using the _CommSendByte($Value) function. My problem is I need to output to multiple servos, Leds etc (These are almost all of float type), Servos will be used for dials in the 0 to 270 degree range. Hence the need for Float types as I require at least one decimal place resolution. //Read values that need to be sent via serial $Value = Read_Value () $Value1 = Read_Value2 () $Value2 = Read_Value2 () $Value3 = Read_Value3 () $Value4 = Read_Value4 () $Value5 = Read_Value5 () $Value6 = Read_Value6 () $Value7 = Read_Value7 () $Value8 = Read_Value8 () .......... // Upto 50 Values (Mostly Float) //Send values via serial _CommSendByte($Value, $Value1, $Value...... $Value50) <------ What to use here to send multiple float values??? Not sure what to use to send float values via your UDF would _CommSendByteArray work? Thanks Martin
- 680 replies
-
- serial port
- virtual port
-
(and 2 more)
Tagged with:
-
Hi Guys, my first post just started with AutoIt and the Arduino. Just got this working myself today, so will post what worked for me Using the CommMG UDF from Martin. Autoit _CommSendByte($VariableName) // Eg. Sending a value between 0 and 20 Arduino Sketch #include <Servo.h> Servo ServoAngleServo; // create servo object to control a servo int ServoAngleValue; // variable to store the servo position void setup() { Serial.begin(9600); ServoAngleServo.attach(9); // attaches the servo on pin 9 to the servo object } void loop() { if (Serial.available()) // wait for serial input { int ServoAngleValue = Serial.read(); // read the incoming byte: if(ServoAngleValue >=0 and ServoAngleValue <= 180) { ServoAngleValue = map(ServoAngleValue, 0, 20, 0, 180); //Convert my value (0-20) into servo range (0-180) ServoAngleServo.write(ServoAngleValue); delay(15); // waits 15ms for the servo to reach the position } } } Hope that helps.