I am making an application where I need to send my phone's accelerometer readings to my Arduino via bluetooth. I am able to send strings easily but, I am getting errors when I am altering the function for integers.
Here is the code I used:
private async void BT2Arduino_Sendint(int value)
{
if (BTSock == null)
{
txtBTStatus.Text = "No connection found. Try again!";
return;
}
else
if (BTSock != null)
{
byte[] buffer = new byte[] { Convert.ToByte(value) };
var datab = GetBufferFromByteArray(UTF8Encoding.UTF8.GetBytes(buffer, 0, 4)); await BTSock.OutputStream.WriteAsync(datab);
txtBTStatus.Text = "Connected to the Device";
}
}
private IBuffer GetBufferFromByteArray(byte[] package)
{
using (DataWriter dw = new DataWriter())
{
dw.WriteBytes(package);
return dw.DetachBuffer();
}
}
The error is basically in the line where I am using UTF8 encoding. It says "The best overloaded method match for System.Text.Encoding.GetBytes(char[], int, int) has some invalid arguments"
Please help me resolve this issue as soon as you can. I know I am doing a mistake with the basics, but I don't have much knowledge with Encoding. Thanks for any help you can provide. :)
Apparently the first parameter of System.Text.Encoding.GetBytes needs to be a char array and not a byte array.
To me looks like you can simply use BitConverter class replacing the code:
if (BTSock != null)
{
byte[] buffer = new byte[] { Convert.ToByte(value) };
var datab = GetBufferFromByteArray(UTF8Encoding.UTF8.GetBytes(buffer, 0, 4));
await BTSock.OutputStream.WriteAsync(datab);
txtBTStatus.Text = "Connected to the Device";
}
with:
if (BTSock != null)
{
byte[] datab = BitConverter.GetBytes(value);
await BTSock.OutputStream.WriteAsync(datab);
txtBTStatus.Text = "Connected to the Device";
}
Related
Need some help to write a function located inside "Application A" to pass multiple variable values using byte [] into another function located in a different application "Application B". So far, I am able to send one variable value but I am really struggling to pass multiple variable values. Thanks in advance for the help, happy holidays!
Application A code:
public static void eventVideoData(string appID, int ID)
{
string application_ID = appID;
int idP = ID;
string pubHeader = "/SERVICES/REQUEST/ECG/UDCMGR/";
//Client.Publish(topic, message, MqttMsgBase.QOS_LEVEL_EXACTLY_ONCE, false);
byte[] bytes = Encoding.ASCII.GetBytes(application_ID);
progrm.ADCSOAPub.Publish(pubHeader + "VIDEODATA", bytes);
Console.WriteLine("Message Sent");
}
Application B code:
if (e.Topic == "/SERVICES/REQUEST/ECG/UDCMGR/IMAGEDATA")
{
//Logic for message received?
Console.WriteLine(msg1);
string pubHeader = "/SERVICES/RESPONSE/ECG/UDCMGR/";
Client.Publish(pubHeader + "IMAGEDATA", Encoding.ASCII.GetBytes("1"));
Console.WriteLine("Message Sent to Scripting Engine");
}
you could create a tuple and send as byte array then covert back to tuple retrieve the property values, this may not be elegant but you could achieve what you wanted.
private byte[] ApplicationA()
{
(string topic, string message) obj = (
topic: "topic",
message: "message"
);
var bf = new BinaryFormatter();
using MemoryStream ms = new MemoryStream();
bf.Serialize(ms, obj);
return ms.ToArray();
}
private (string,string) ApplicationB(byte[] input)
{
var bf = new BinaryFormatter();
using var ms = new MemoryStream(input);
var obj = bf.Deserialize(ms);
return ((string, string))obj;
}
[Fact]
public void Test()
{
var byteArray = ApplicationA();
var t = ApplicationB(byteArray);
Console.WriteLine(t.Item1);
Console.WriteLine(t.Item2);
}
I know it sounds simple but I got some trouble with it. I am trying to make a system with a pic Microcontroller (MCU) and an xamarin android app. The sending part from app to the pic MCU is solved but when I want to send data from the MCU to the app it won't go as flaweless. I am using a HC-06 as a bluetooth device for receiving and sending messages.
The code for receiving from the MCU to the app is:
public void beginListenForData()
{
try
{
inStream = btSocket.InputStream;
}
catch (IOException ex)
{
Console.WriteLine(ex.Message);
}
Task.Factory.StartNew(() => {
byte[] buffer = new byte[1024];
int bytes;
while (true)
{
try
{
Array.Reverse(buffer, 0, buffer.Length);
bytes = inStream.Read(buffer, 0, buffer.Length);
if (bytes > 0)
{
string valor = Encoding.ASCII.GetString(buffer);
System.Diagnostics.Debug.WriteLine(buffer);
System.Diagnostics.Debug.WriteLine(bytes);
System.Diagnostics.Debug.WriteLine(valor);
if (valor == "D0O")
{
System.Diagnostics.Debug.WriteLine("Vergelijking gelukt!");
break;
}
//Result.Text = Result.Text + "\n" + valor;
}
}
catch (Java.IO.IOException)
{
//Result.Text = string.Empty;
break;
}
}
});
}
As you perhaps could geuss the message I try to sent from the MCU is D0O (valor) when the comparison worked with the incoming message I want to debug write that is was successful with:
System.Diagnostics.Debug.WriteLine("Vergelijking gelukt!");
The next part is for checking what for data is coming in:
System.Diagnostics.Debug.WriteLine(buffer);
System.Diagnostics.Debug.WriteLine(bytes);
System.Diagnostics.Debug.WriteLine(valor);
What I noticed is the strange output (see image):
As you can see the message is cut into 2 parts every time. Does anyone has any idea why and how to solve it?
I did change the array order with:
Array.Reverse(buffer, 0, buffer.Length);
Because I did notice it entered in the wrong order. This did work to put it in the right order.
Little update:
I changed some line of code and it works more "flaweless"
while ((count = inStream.Read(buffer, 0, buffer.Length)) > 0)
But what is strange that the first bit gets sepparated from the rest of the receiving string. I am not sure what causes this problem if anyone has a idea?
Thanks in advance.
I found a solution for the problem I was facing. So I will share my answer and thought process so perhaps other people can use the same.
So what I thought was there is a receiving buffer that saves the incoming char's. If the buffer is read with streamReader.Read it returns an integer of the readed char's. So I made second buffer of the datatype string[].
If the string[0] is empty I would place in my first Char that was read by the streamReader.Read. If the string[0] is NOT empty it means that the first char is already been read so I put the incoming char into string[1]. This means that the message that was split up is now into string[0] and string[1]. So what if I could combine it and save it into a string variable. This was done by: string eindtekst = string.Join("", buf); and this gives me the string in one piece so I can compare it. It is importent to clear the both array's as you're done with the comparing otherwise there would be new data added. And as you perhaps can tell string[0] == null would never be true. So only string[1] get's overridden al the time and that means you're losing out on data.
public void beginListenForData()
{
try
{
inStream = btSocket.InputStream;
streamReader = new StreamReader(inStream);
}
catch (IOException ex)
{
Console.WriteLine(ex.Message);
}
char[] buffer = new char[256];
string[] buf = new string[2];
int bytes;
while (1)
{
try
{
if ((bytes = streamReader.Read(buffer, 0, buffer.Length)) > 0)
{
string tekst = new string(buffer, 0, bytes);
if(buf[0] == null)
{
buf[0] = tekst;
}
else
{
buf[1] = tekst;
}
string eindtekst = string.Join("", buf);
if (eindtekst == "D0O")
{
System.Diagnostics.Debug.WriteLine("Vergelijking gelukt!");
System.Diagnostics.Debug.WriteLine(eindtekst);
Array.Clear(buffer, 0, buffer.Length);
Array.Clear(buf, 0, buf.Length);
writeData("D2O");
}
streamReader.DiscardBufferedData();
}
}
catch (Java.IO.IOException)
{
break;
}
}
}
Thanks for all the help
Currently I am working on a little project which should work over the network. But I have a problem with a read method, which should read bytes from a network stream. The function reads each single bytes and when it comes to a specific byte(in my case it is ! = 33) it fires an data received event. However when the server sends several messages in a short time the read method misses some messages. Here my code:
public void Read()
{
while (this.isReading == true)
{
try
{
if (!this.stream.DataAvailable)
{
Thread.Sleep(10);
continue;
}
List<byte> receivedBytes = new List<byte>();
byte[] buffer = new byte[1];
while (this.stream.DataAvailable)
{
this.stream.Read(buffer, 0, 1);
// Checks if the current byte is the last byte of a protocol
if (buffer[0] == 33)
{
break;
}
receivedBytes.Add(buffer[0]);
}
this.FireOnDataReceived(receivedBytes.ToArray());
}
catch
{
this.FireOnConnectionLost();
}
}
}
I'm having troubles to make my program work correctly - here I explain :
I have, on one hand a C# WinForms app which launches an instance of IE by using the "Navigate" method : myWebBrowser.Navigate(myUrl, "_blank", intarray, "");, with intarray defined like this : byte[] intarray = BitConverter.GetBytes(id);. On this side, it works.
On the other side, I have an ASP .NET WebForms application which has to retrieve this intarray. I've tried this.
if (HttpContext.Current != null)
{
if (Session["Authenticated"] == null)
{
var current = HttpContext.Current;
byte[] postdata = getpostdata(current);
}
}
private byte[] getpostdata(HttpContext CurrentContext)
{
MemoryStream ms = new MemoryStream();
CurrentContext.Request.InputStream.CopyTo(ms);
byte[] postdata = ms.ToArray();
return postdata;
}
// Convert a byte array to an Object
public int ByteArrayToInt(byte[] arrBytes)
{
if (BitConverter.IsLittleEndian) Array.Reverse(arrBytes);
int i = BitConverter.ToInt32(arrBytes, 0);
return i;
}
The problem seems to be in retrieving the Data in the getpostdata(HttpContext) function... I get a byte array with length = 0 instead of the one which is sent with length = 4...
Does anyone know how to make it work ?
Yann
var current = HttpContext.Current;
var sr = new StreamReader(Request.InputStream, Encoding.Default);
var postdata = sr.ReadToEnd();
above
I want to write messages to a MSMQ queue using C++ and read them using C#.
I send the messages as strings.
It works fine if I both write and read the messages in C++ but if I try to read the message using C#, I get only the first character of the message. (eg: I send "abcd" and I receive only "a").
I also must mention that I am using this code in Windows Mobile.
Here is the c++ code:
HRESULT MSMQManager::WriteMessage(LPWSTR text){
// define the required constants and variables.
const int NUMBEROFPROPERTIES = 5; // number of properties
DWORD cPropId = 0; // property counter
HRESULT hr = MQ_OK; // return code
HANDLE hQueue = NULL; // queue handle
// define an MQMSGPROPS structure.
MQMSGPROPS msgProps;
MSGPROPID aMsgPropId[NUMBEROFPROPERTIES];
MQPROPVARIANT aMsgPropVar[NUMBEROFPROPERTIES];
HRESULT aMsgStatus[NUMBEROFPROPERTIES];
// message label
aMsgPropId[cPropId] = PROPID_M_LABEL;
aMsgPropVar[cPropId].vt = VT_LPWSTR;
aMsgPropVar[cPropId].pwszVal = L"msg";
cPropId++;
// message body
aMsgPropId[cPropId] = PROPID_M_BODY;
aMsgPropVar[cPropId].vt = VT_VECTOR | VT_UI1;
aMsgPropVar[cPropId].caub.pElems = (LPBYTE)text;
aMsgPropVar[cPropId].caub.cElems = wcslen(text)*2;
cPropId++;
// message body type
aMsgPropId[cPropId] = PROPID_M_BODY_TYPE;
aMsgPropVar[cPropId].vt = VT_UI4;
aMsgPropVar[cPropId].ulVal = VT_LPWSTR;
cPropId++;
// initialize the MQMSGPROPS structure.
msgProps.cProp = cPropId;
msgProps.aPropID = aMsgPropId;
msgProps.aPropVar = aMsgPropVar;
msgProps.aStatus = aMsgStatus;
// Call MQSendMessage to send the message to the queue.
hr = MQSendMessage(
this->writeHandle, // Queue handle
&msgProps, // Message property structure
MQ_NO_TRANSACTION // Not in a transaction
);
Here is the c# code:
public string ReadMessageUnformatted()
{
try
{
Message received;
Stream bodyStream = null;
StreamReader sr = null;
char[] buffer = new char[256];
received = this.readMQ.Receive();
bodyStream = received.BodyStream;
sr = new StreamReader(bodyStream);
//this.lastReceived = sr.ReadLine();
sr.Read(buffer, 0, 256);
this.lastReceived = new string(buffer);
return lastReceived;
}
catch (Exception exc)
{
MessageBox.Show(exc.ToString(), "Exception");
return null;
}
}
I am using BodyStream instead of Body for the message because I don't want to use any message formatter.
Thanks
I solved myself the problem. I shall post here the code maybe there is someone else interested.
try
{
Message received;
Stream bodyStream = null;
int bufLength = 512;
byte[] buffer = new byte[bufLength];
received = this.readMQ.Receive();
bodyStream = received.BodyStream;
bodyStream.Read(buffer, 0, bufLength);
this.lastReceived = Encoding.Unicode.GetString(buffer, 0, buffer.Length);
return lastReceived;
}
catch (Exception exc)
{
MessageBox.Show(exc.ToString(), "Exception");
return null;
}
Maybe you can try:
aMsgPropVar[cPropId].ulVal = VT_BSTR;
VT_BSTR is used to indicate a unicode string.
VT_LPWSTR needs to be null-terminated, which I don't think your string is.