I am connecting an ultrasonic distance sensor to matlab with the 'serial' command, using the code below. When trying to get the distances as an output with a for loop I get an error in the line where I use the command 'fscanf'. Matlab tells me:
Error using fscanf
Invalid file identifier. Use fopen to generate a valid file identifier.
Error in subsonicsensor (line 12)
y(i)=fscanf('arduino','%cm');
Can anybody tell me how I can adjust my for loop, or rest of the code to get the right distances from the code?
I also tried using fprintf instead of fscanf. This gave me the value 7cm for al 100 measurements. Can anybody explain?
Here is my code:
clear all
clc
arduino=serial('COM3','BaudRate',9600);
x=linspace(1,100);
L = length(x);
for i=1:L
fopen('arduino');
y(i)=fscanf('arduino','%cm');
pause(0.05);
end
fclose(arduino);
disp('making plot..')
plot(x,y);

 Akzeptierte Antwort

Walter Roberson
Walter Roberson am 28 Nov. 2017
Bearbeitet: Walter Roberson am 28 Nov. 2017

0 Stimmen

Move the
fopen('arduino');
to before the loop, and change it to
fopen(arduino);
Change the
y(i)=fscanf('arduino','%cm');
to
y(i)=fscanf(arduino,'%fm');

6 Kommentare

Thank you for answering. Adjusting my code this way gave me a succesfull plot one time. After running the code a second time I got the following error and no plot.
Error using serial/fopen (line 72)
Open failed: Port: COM3 is not available. No ports are available.
Use INSTRFIND to determine if other instrument objects are connected to the requested device.
Error in subsonicsensor (line 8)
fopen(arduino);
Right now the code looks like this:
clear all
clc
arduino=serial('COM3','BaudRate',9600);
x=linspace(1,100);
L = length(x);
fopen(arduino);
for i=1:L
y(i)=fscanf(arduino,'%fm');
pause(0.05);
end
fclose(arduino);
disp('making plot..')
plot(x,y);
After reconnecting the usb I get the following faillure
Warning: Unsuccessful read: Matching failure in format.. Subscripted assignment dimension mismatch.
Error in subsonicsensor (line 12)
y(i)=fscanf(arduino,'%fm');
You are not sending the arduino a command, so we can guess that your arduino is sending a continuous stream of results to MATLAB. At the time you connect to the arduino, it might be in the middle of sending something, so the first character available in the buffer might be 'm', which is not something that can be matched by the '%fm' format.
The quick fix: before the "for" loop, add
fgetl(arduino); %flush out any partial line in the buffer
I think I'm almost there. I fixed the fopen error, which refused to change my port status from closed to open by adding the command delete(instrfindall); to the start of my script. The port status is now open but when running the code I get the message that my dimensions mismatch.
Warning: Unsuccessful read: Matching failure in format..
Subscripted assignment dimension mismatch.
Error in subsonicsensor (line 17)
y(i)=fscanf(arduino,'%fm');
My code looks like this at the moment:
clear all
clc
delete(instrfindall);
arduino=serial('COM3');
set(arduino,'BaudRate',9600);
fopen(arduino);
x=linspace(1,100);
L = length(x);
fgetl(arduino); %flush out any partial line in the buffer
for i=1:L
y(i)=fscanf(arduino,'%fm');
pause(0.05);
end
fclose(arduino);
disp('making plot..')
plot(x,y);
This is the arduino code that I uploaded to the Arduino UNO board by the way:
#define trigPin 12
#define echoPin 13
void setup() {
// put your setup code here, to run once:
Serial.begin(9600);
pinMode(trigPin, OUTPUT);
pinMode(echoPin, INPUT);
}
void loop() {
// put your main code here, to run repeatedly:
long duration, distance;
digitalWrite(trigPin, LOW);
delayMicroseconds(2);
digitalWrite(trigPin, HIGH);
delayMicroseconds(10);
digitalWrite(trigPin, LOW);
duration = pulseIn(echoPin, HIGH);
distance = (duration/2) / 29.1;
if(distance >= 400 || distance <= 2){
Serial.println("Out of Range");
}
else {
Serial.print(distance);
Serial.println("cm");
}
delay(500);
}
Again what I'm trying to achieve is to get a constant output of my ultrasonic distance sensor displayed in Matlab. Thank you for helping
Change
y(i)=fscanf(arduino,'%fm');
to
thisline = fgetl(arduino);
if strcmpi(thisline, 'Out of Range')
fprintf('Out of Range reported at point #%d\n', i)
y(i) = nan;
else
thisdist = sscanf(thisline, '%f');
if isempty(thisdist)
fprintf('Unexpected response at point #%d; line was: "%s"\n', i, thisline);
y(i) = nan;
else
if length(thisdist) > 1
fprintf('Multiple distances reported for point #%d, using first; line was "%s"\n', i, thisline);
end
y(i) = thisdist(1);
end
end
Thanks Walter for helping us out. Matlab after running the code now shows us the step numbers at which the distance sensor gives: 'Out of Range', and a plot of the measured distances that are not out of range. However, what we would like to achieve is a non-stop real-time display of the measured distance values. How do we get matlab to print the measured values in real time without stopping?

Melden Sie sich an, um zu kommentieren.

Weitere Antworten (0)

Kategorien

Mehr zu MATLAB Support Package for Arduino Hardware finden Sie in Hilfe-Center und File Exchange

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by