Sending multiple commands through serial ports using arduino and visual c#

I am trying to make a code where you control the direction of a turret then fire it when you are ready with a click of a mouse. The code for firing and the code for aiming work great by themselves but when I put them together I think that the commands go straight to the servos not the motors. I originally tried to use numbers for on and off for motors but then went on to use letters thinking a different datatype would work. I have attached the code for Arduino and C# in visual studio. Any input would be gratefully appreciated, thank you.

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Diagnostics;

namespace firing_retry_retry
{
public partial class Form1 : Form
{
public Stopwatch watch { get; set; }

public Form1()
{
InitializeComponent();
}

private void Form1_Load(object sender, EventArgs e)
{
watch = Stopwatch.StartNew();
Port.Open();
}

private void Form1_MouseMove_2(object sender, MouseEventArgs e)
{
writeToPort(new Point(e.X, e.Y));
}

public void writeToPort(Point coordinates)
{
if (watch.ElapsedMilliseconds > 15)
{
watch = Stopwatch.StartNew();
Port.Write(String.Format(“X{0}Y{1}”,
(coordinates.X / (Size.Width / 180)),
(coordinates.Y / (Size.Height / 180))));
}
}

private void Form1_MouseDown(object sender, MouseEventArgs e)
{
Port.Write(“A”);
}

private void Form1_MouseUp(object sender, MouseEventArgs e)
{
Port.Write(“B”);
}
}
}

arduino_control_code.ino (1.03 KB)

Read the how to use this forum-please read sticky to see how to properly post code and some advice on how to ask an effective question. Remove useless white space and format the code with the IDE autoformat tool (crtl-t or Tools, Auto Format) before posting code.

I suggest that you read the above provided link first and post your code correctly.

And next Robin’s updated serial input basics thread for ideas how to handle serialcommunication reliably.

Further you receive one character and compare it with an array of characters.

       if(receiveVal == "A")

Comparing a single character would be.

       if(receiveVal == 'A')

// Edit
I suggest that you write the Arduino code first and test it with serial monitor (mouse click can be something like the text ). After that you can write the PC side of things.

groundFungus: Read the how to use this forum-please read sticky to see how to properly post code and some advice on how to ask an effective question. Remove useless white space and format the code with the IDE autoformat tool (crtl-t or Tools, Auto Format) before posting code.

Right, thank you you for giving me this, wasn't sure quite how to do this, this is my first post if you haven't already noticed. Thank you, will do this properly next.

groundFungus:
Read the how to use this forum-please read sticky to see how to properly post code and some advice on how to ask an effective question. Remove useless white space and format the code with the IDE autoformat tool (crtl-t or Tools, Auto Format) before posting code.

Right, thank you you for giving me this, wasn’t sure quite how to do this, this is my first post if you haven’t already noticed. Thank you, will do this properly next.

sterretje:
I suggest that you read the above provided link first and post your code correctly.

And next Robin’s updated serial input basics thread for ideas how to handle serialcommunication reliably.

Further you receive one character and compare it with an array of characters.

       if(receiveVal == "A")

Comparing a single character would be.

       if(receiveVal == 'A')

// Edit
I suggest that you write the Arduino code first and test it with serial monitor (mouse click can be something like the text ). After that you can write the PC side of things.

Great, thank you for the feedback, I will post the code properly after this. Thank you for this too. I’m fairly new to Arduino so I am thankful for all the help I can get.

The code I stupidly didn’t format right.

C#

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Diagnostics;

namespace firing_retry_retry
{
    public partial class Form1 : Form
    {
        public Stopwatch watch { get; set; }

        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            watch = Stopwatch.StartNew();
            Port.Open();
        }

        private void Form1_MouseMove_2(object sender, MouseEventArgs e)
        {
            writeToPort(new Point(e.X, e.Y));
        }

        public void writeToPort(Point coordinates)
        {
            if (watch.ElapsedMilliseconds > 15)
            {
                watch = Stopwatch.StartNew();
                Port.Write(String.Format("X{0}Y{1}",
                    (coordinates.X / (Size.Width / 180)),
                    (coordinates.Y / (Size.Height / 180))));
            }
        }

        private void Form1_MouseDown(object sender, MouseEventArgs e)
        {
            Port.Write("A");
        }

        private void Form1_MouseUp(object sender, MouseEventArgs e)
        {
            Port.Write("B");
        }
    }
}

Arduino Code

#include<Servo.h>
const int LedPin = 9;
int ledState = 0;

Servo serX;
Servo serY;

String serialData;


void setup() {
  // put your setup code here, to run once:
serX.attach(10);
serY.attach(11);
pinMode(LedPin, OUTPUT);
Serial.begin(9600);
Serial.setTimeout(10);
}

void loop() {
  // put your main code here, to run repeatedly:
  char receiveVal;   
   
    if(Serial.available() > 0)
    {        
        receiveVal = Serial.read();
        
       if(receiveVal == "A")    
          ledState = 1;   
       else
          ledState = 0;     
    }   
      
    digitalWrite(LedPin, ledState); 
      
    delay(50);    
}

void serialEvent(){
  serialData = Serial.readString();

  serX.write(parseDataX(serialData));
  serY.write(parseDataY(serialData));
  
}

int parseDataX(String data){
  data.remove(data.indexOf("Y"));
  data.remove(data.indexOf("X"), 1);

  return data.toInt();
  
  
}

int parseDataY(String data){
  data.remove(0, data.indexOf("Y") + 1);

  return data.toInt();
}

As said, in your Arduino code, check for 'A', not "A"; same for 'B', not "B".

And see my edit in reply #2. It's difficult to work on both sides at the same time. Test with Serial Monitor till the Arduino code does what it is supposed to do and next concentrate on the C# part.

You are working on both sides at the same time, which will be really difficult to debug. So, you should first test your Arduino Code in Serial Monitor so that you are sure Arduino is sending all the commands correctly.

After that you should create a Virtual COM Port on your computer. You can use Eltima Virtual Software and then test your C# code.

@jackthomson42 There is already a comport when the Arduino is connected. What is the advantage of creating one?

sterretje: As said, in your Arduino code, check for 'A', not "A"; same for 'B', not "B".

And see my edit in reply #2. It's difficult to work on both sides at the same time. Test with Serial Monitor till the Arduino code does what it is supposed to do and next concentrate on the C# part.

So I made the changes you suggested and I am still getting the same problem. I used the serial monitor to input coordinates and it worked. However, when I put in A it moves the servos instead of turning on my test LED.

Thank you for your responses.

When you make changes to your code, please post the latest version so we can keep up.

Looked at your Arduino code again. I should have picked up that you use serialEvent as well as serial reading in loop().

That doesn't work. Either use the one or the other.

This would be a quick fix (not tested)

void loop()
{
    delay(50);    
}

void serialEvent(){
  serialData = Serial.readString();
  
  if(data[0] == 'A')
  {
    digitalWrite(LedPin, HIGH);
  }
  else if(data[0] == 'B')
  {
    digitalWrite(LedPin, LOW);
  }
  else
  {
    serX.write(parseDataX(serialData));
    serY.write(parseDataY(serialData));
  }  
}

int parseDataX(String data){
  data.remove(data.indexOf("Y"));
  data.remove(data.indexOf("X"), 1);

  return data.toInt();
}

int parseDataY(String data){
  data.remove(0, data.indexOf("Y") + 1);

  return data.toInt();
}

I posted a link in reply #2 to Robin's updated Serial Input Basics thread; it will give you some (better) ideas for more reliable communication.

sterretje:
Looked at your Arduino code again. I should have picked up that you use serialEvent as well as serial reading in loop().

That doesn’t work. Either use the one or the other.

This would be a quick fix (not tested)

void loop()

{
   delay(50);    
}

void serialEvent(){
 serialData = Serial.readString();
 
 if(data[0] == ‘A’)
 {
   digitalWrite(LedPin, HIGH);
 }
 else if(data[0] == ‘B’)
 {
   digitalWrite(LedPin, LOW);
 }
 else
 {
   serX.write(parseDataX(serialData));
   serY.write(parseDataY(serialData));
 }  
}

int parseDataX(String data){
 data.remove(data.indexOf(“Y”));
 data.remove(data.indexOf(“X”), 1);

return data.toInt();
}

int parseDataY(String data){
 data.remove(0, data.indexOf(“Y”) + 1);

return data.toInt();
}




I posted a link in reply #2 to Robin's updated [Serial Input Basics](https://forum.arduino.cc/index.php?topic=396450.0) thread; it will give you some (better) ideas for more reliable communication.

Thank you so much for this, it now works!!! I had thought that having the two at the same time could’ve possibly done something to the code but I wasn’t extremely sure. The C# Visual Code works brilliantly with it now. I will finish this off by giving you my final code:

Final C# Visual Code:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Diagnostics;

namespace firing_retry_retry
{
    public partial class Form1 : Form
    {
        public Stopwatch watch { get; set; }

        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            watch = Stopwatch.StartNew();
            Port.Open();
        }

        private void Form1_MouseMove_2(object sender, MouseEventArgs e)
        {
            writeToPort(new Point(e.X, e.Y));
        }

        public void writeToPort(Point coordinates)
        {
            if (watch.ElapsedMilliseconds > 15)
            {
                watch = Stopwatch.StartNew();
                Port.Write(String.Format("X{0}Y{1}",
                    (coordinates.X / (Size.Width / 180)),
                    (coordinates.Y / (Size.Height / 180))));
            }
        }

        private void Form1_MouseDown(object sender, MouseEventArgs e)
        {
            Port.Write("A");
        }

        private void Form1_MouseUp(object sender, MouseEventArgs e)
        {
            Port.Write("B");
        }
    }
}

Final Arduino Code:

#include<Servo.h>
const int LedPin = 9;
int ledState = 0;

Servo serX;
Servo serY;

String serialData;


void setup() {
  // put your setup code here, to run once:
serX.attach(10);
serY.attach(11);
pinMode(LedPin, OUTPUT);
Serial.begin(9600);
Serial.setTimeout(10);
}

void loop()
{
    delay(50);    
}

void serialEvent(){
  serialData = Serial.readString();
  
  if(serialData[0] == 'A')
  {
    digitalWrite(LedPin, HIGH);
  }
  else if(serialData[0] == 'B')
  {
    digitalWrite(LedPin, LOW);
  }
  else
  {
    serX.write(parseDataX(serialData));
    serY.write(parseDataY(serialData));
  }  
}

int parseDataX(String data){
  data.remove(data.indexOf("Y"));
  data.remove(data.indexOf("X"), 1);

  return data.toInt();
}

int parseDataY(String data){
  data.remove(0, data.indexOf("Y") + 1);

  return data.toInt();
}

Thank you all for your input and not just helping with this code but also helping me with learning how to post better questions in the future.