Reputation: 49
I'm making a program that can control an Arduino board through C#. Here is the steps the program needs to take:
Below is the code i have so far for the connect() method.
public void connect()
{
string[] ports = SerialPort.GetPortNames();
SerialPort[] serialport = new SerialPort[ports.Length];
foreach(string p in ports)
{
int i = Array.IndexOf(ports, p);
serialport[i].PortName = p;
serialport[i].BaudRate = 9600;
serialport[i].Open();
//Scan inputs for "connectAlready"
}
Not much i know, and i keep getting a "System.NullReferenceException" at serialport[i].PortName = p;
How can I make this program work? Thank you for all the help
Upvotes: 1
Views: 3121
Reputation: 30813
Firstly, you need to declare new serial port object for each serial port which you create:
string[] ports = SerialPort.GetPortNames();
SerialPort[] serialport = new SerialPort[ports.Length];
foreach(string p in ports)
{
int i = Array.IndexOf(ports, p);
serialport[i] = new SerialPort(); //note this line, otherwise you have no serial port declared, only array reference which can contains real SerialPort object
serialport[i].PortName = p;
serialport[i].BaudRate = 9600;
serialport[i].Open();
//Scan inputs for "connectAlready"
}
And then, you need at least four things to get and to handle your data:
Event handler for DataReceived
for your serial port
serialport[i].DataReceived += serialPort_DataReceived; //This is to add event handler delegate when data is received by the port
private void serialPort_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e) { //This is to handle the data when it comes
//Do something on data received
}
Get the data from the underlying stream of the port.
private void serialPort_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e) {
SerialPort serialPort1 = sender as SerialPort;
byte[] data = new byte[serialPort1.BytesToRead]; //this is to provide the data buffer
Stream portStream = serialPort1.BaseStream;
portStream.Read(data, 0, data.Length); //You get your data from serial port as byte[]
//Do something on your data
}
Encoding.UTF8.GetString
to convert the input data from byte[]
to ASCII
characters (Edit: consider of changing/skip this step and step 2 if the data received is not byte[]
but ASCII
)
private void serialPort_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e) {
SerialPort serialPort1 = sender as SerialPort;
byte[] data = new byte[serialPort1.BytesToRead]; //this is to provide the data buffer
Stream portStream = serialPort1.BaseStream;
portStream.Read(data, 0, data.Length); //You get your data from serial port as byte[]
string dataString = Encoding.UTF8.GetString(data); //here is your data in string
//Do something on your data
}
Check if the data string
contains the data that you want
bool hasData = dataString.Contains("connectAlready"); //this is to check if your data has this, if it doesn't do something
And as a last note, beware that the data from your serial port doesn't come together (like "conne" and then "ctAlready"). In such case, you need to copy your received data in a global buffer first then have additional checking (use Buffer.BlockCopy
)
byte[] globalBuffer = new byte[4000]; //large buffer, put globally
//In your data received, use Buffer.BlockCopy to copy data to your globalBuffer
//Beware the index
if (globalBuffer.Length >= 14){ //less than this length, then the data is incomplete
//Do the checking if length is at least 14
}
Upvotes: 2
Reputation: 2083
At this Point
SerialPort[] serialport = new SerialPort[ports.Length];
You are initializing the Array here. However at this point in for loop,
serialport[i].PortName = p;
The SerialPort object at that location is not Initialized. Hence the Null Reference Exception
So try adding this in the for loop before assigning anything to Serial port
serialport[i]=new SerialPort()
Using any constructor you need off-course.
Upvotes: 2