TimerFcn loop for arduino

hi
I want to read some data from arduino with timer object and I want to read these data each 0.01 second as input datas and calculate datas and give output datas
the code that I want to use is:
t=timer('Period',0.01,'ExecutionMode','fixedRate');
t.TimerFcn=@(function1);
start(t)
function [T]=function1(x)
x=readCount(encoder);
k=5*x;
T=k+3;
end
is it correct?

1 Comment

actually my question is about writting the TimerFcn to do the loop function

Sign in to comment.

Answers (1)

john - is the above code nested within another function so that the function1 has access to the encoder variable which (presumably) has been initialized in that other/parent function? Note that there is no output parameter for a timer function callback, and the default parameters (of which there are generally two) correspond to the handle of the timer object and some event data (if it exists). So the above might not work as you intend. An example might be
function timerTest
k = 1;
T = [];
t=timer('Period',0.01,'ExecutionMode','fixedRate');
t.TimerFcn=@function1;
start(t)
function function1(~,~)
T(k) = randi(256,1,1);
k = k + 1;
end
end
Note how we must define the nested variables that the function1 callback will access before we assign the timer callback. And instead of returning an output parameter from the callback - which you cannot do - we store the result in an array (or you could do something with that value (i.e. update a plot) from within the callback.

19 Comments

thanks for your answer, actually encoder variable is read from arduino port like this:
a=arduino('com3','uno','Libraries','RotaryEncoder');
encoder=rotaryEncoder(a,'D2','D3');
and I want to read the value of the encoder each 0.01 seconds and put this value in K formula and then calculate the T as the output and do this in a loop until the result be what I want
do this in a loop...do what in a loop? until the result be what I want...what is the condition then for stopping then?
john white
john white on 10 Apr 2019
Edited: john white on 10 Apr 2019
the loop is reading encoder pulse value an gives it to the K formula and gets the T as output (each 0.01 seconds) and the stop condition is control method when the value of the encoder be a special value
so by loop you just mean the timer firing every 0.01 seconds. So to stop you just compare T against the special value to end the timer?
function function1(~, ~)
x=readCount(encoder);
k=5*x;
T=k+3;
if T == specialValue
stop(t);
end
end
actually as you know the encoder is used to read the position of the dc motor and I want to control a dc motor with, so I have a method for controlling and the input signals of the control method is (or are) the position of the dc motor ( which reads by encoder and defined as x) and the output signal of the control method is the torque(T) , to stop the loop when dc motor reach to the special position the output signal would be zero and the dc motor would be turned off
Geoff Hayes - could you help me on this? I couldn't define the loop to do my purpose please help me and as I wrote I want to control a dc motor which needs to read the value of encoder and gives this value to the control formula as a input signal and gets the torque as output signal and repeat this loop each 0.01 seconds until the postion of the dc motor reaches at a special value and then the dc motor would be off
John - if you have a timer, then you won't need a loop since the timer will fire every 0.01 seconds (or whatever you choose) which behaves much like a loop.
you mean that I just need to define the function to the TimerFcn and StopFcn like this?
t=timer('Period',0.01,'ExecutionMode','fixedRate');
t.TimerFcn=@(function1);
t.TasksToExecute = 1000;
start(t)
function [T]=function1(x)
x=readCount(encoder);
k=5*x;
T=k+3;
end
and it repeats the solving the code 1000 times each 0.01 seconds(totally 10 seconds) ?
and is TimerFcn defined correctly?
Yes, the timer will execute 1000 times and then will stop (you haven't defined a StopFcn. But your TimerFcn is still incorrectly defined (unless something has changed in a later version of MATLAB). You cannot return an output parameter and there are generally two inputs to your timer function - see Timer Callback Functions for details. Your function needs to look more like
function function1(~,~)
x=readCount(encoder);
k=5*x;
T=k+3;
end
where T has already been defined in the parent function (assuming that you are using nested functions like I showed above). Your StopFcn, which executes when the timer stops, could then use T to do "something".
I have a problem yet!
when I use this code :
a1=arduino('com3','uno','Libraries','RotaryEncoder');
encoder1=rotaryEncoder(a1,'D2','D3',4000);
t=timer('Period',0.01,'ExecutionMode','fixedRate');
t.TimerFcn=@function1;
t.TasksToExecute=3000;
start(t)
function function1(~,~)
x=readCount(encoder1);
k=5*x;
T=k+3
end
the Matlab showed this error:
Error while evaluating TimerFcn for timer 'timer-1'
Undefined function or variable 'encoder1'.
_______
and when I defined the encoder and arduino board in the function1 as :
t=timer('Period',0.01,'ExecutionMode','fixedRate');
t.TimerFcn=@ function1;
t.TasksToExecute=3000;
start(t)
function function1(~,~)
a1=arduino('com3','uno','Libraries','RotaryEncoder');
encoder1=rotaryEncoder(a1,'D2','D3',4000);
x=readCount(encoder1);
k=5*x;
T=k+3;
end
it showed this error:
Error while evaluating TimerFcn for timer 'timer-2'
The value of the "a" property must be a numeric array without any Inf's or NaN's.
john - for your first set of code, are you nesting the callback within the parent function? You need to do something like
function parentFunction
a1=arduino('com3','uno','Libraries','RotaryEncoder');
encoder1=rotaryEncoder(a1,'D2','D3',4000);
t=timer('Period',0.01,'ExecutionMode','fixedRate');
t.TimerFcn=@function1;
t.TasksToExecute=3000;
start(t)
function function1(~,~)
x=readCount(encoder1);
k=5*x;
T=k+3
end
end
where the above code is saved to a parentFunction.m file. Your error message is suggesting that you aren't doing this and so the callback cannot find the encoder1 variable.
As for your second set of code, I don't think that you want to be opening a connection to the arduino device every 0.01 seconds. The error message references a variable named a but I don't see that in your code....
for the first set I didn't write the parentFunction and for the 2nd one I have no idea about the "a" ! what I write as error was the error which Matlab showed
try writing with the parent function.
I wrote the parentFunction but this is the error!!
88.png
john - i feel that you are not showing all of your code because nowhere in your timer callback do i see any of the three encoders being used. please attach your code rather than showing a partial screenshot.
actually my code is controlling 3 dc motors so I defined 3 encoders on 3 arduino boards and but the problem is here if i only define 1 encoder and 1 arduino board in parentFunction it showed the same error!!!
and I never use "a" variable in my code!!!!!!
and this is my full code:
function parentFunction
a1=arduino('com5','uno','Libraries','RotaryEncoder');
a2=arduino('com6','uno');
a3=arduino('com3','Due','Libraries','RotaryEncoder');
encoder1=rotaryEncoder(a3,'D2','D3',4000);
encoder2=rotaryEncoder(a3,'D4','D5',4000);
encoder3=rotaryEncoder(a1,'D2','D3',48);
t=timer('Period',0.01,'ExecutionMode','fixedRate');
t.TimerFcn=@function1;
t.TasksToExecute=3000;
start(t)
function function1(~,~)
R=5*diag([1/2 1/2 1/2]);
Q = zeros(9,9); q = 500;
Q(1) = q; Q(7) = -q; Q(55) = -q; Q(61) = q;
Q(11) = q; Q(17) = -q; Q(65) = -q; Q(71) = q;
Q(21) = q; Q(27) = -q; Q(75) = -q; Q(81) = q;
count1=readCount(encoder1);
degree1=(count1/(5*4000))*360;
theta1=degree1*pi/180;
speed1=readSpeed(encoder1);
rpm1=speed1/5;
theta_dot1=rpm1*2*pi/60;
count2=readCount(encoder2);
degree2=(count2/(5*4000))*360;
theta2=degree2*pi/180;
speed2=readSpeed(encoder2);
rpm2=speed2/5;
theta_dot2=rpm2*2*pi/60;
count3=readCount(encoder3);
degree3=(count3/(5*48))*360;
theta3=degree3*pi/180;
speed3=readSpeed(encoder3);
rpm3=speed3/5;
theta_dot3=rpm3*2*pi/60;
T1 = u(1,1);T2 = u(1,2);T3 = u(1,3);
if T1>2
T1=2;
end
if T1<-2
T1=-2;
end
if T2>2
T2=2;
end
if T2<-2
T2=-2;
end
if T3>2
T3=2;
end
if T3<-2
T3=-2;
end
Res=1.003;
kt=0.6835;
kto=Res/kt^2;
vol1=kt.*theta_dot1+kto.*T1;
vol2=kt.*theta_dot2+kto.*T2;
vol3=kt.*theta_dot3+kto.*T3;
pwdc1=vol1/12;
pwdc2=vol2/12;
pwdc3=vol3/12;
p1=abs(pwdc1);
p2=abs(pwdc2);
p3=abs(pwdc3);
if p1>1
p1=1;
end
if p2>1
p2=1;
end
if p3>1
p3=1;
end
writePWMDutyCycle(a1,'D5',p1);
writePWMDutyCycle(a1,'D6',p2);
writePWMDutyCycle(a2,'D5',p3);
if sign(pwdc1)==1
writeDigitalPin(a1,'D7',1);
writeDigitalPin(a1,'D8',0);
else if sign(pwdc1)==-1
writeDigitalPin(a1,'D7',0);
writeDigitalPin(a1,'D8',1);
else if sign(pwdc1)==0
writeDigitalPin(a1,'D7',0);
writeDigitalPin(a1,'D8',0);
end
end
end
if sign(pwdc2)==1
writeDigitalPin(a1,'D4',1);
writeDigitalPin(a1,'D9',0);
else if sign(pwdc2)==-1
writeDigitalPin(a1,'D4',0);
writeDigitalPin(a1,'D9',1);
else if sign(pwdc2)==0
writeDigitalPin(a1,'D4',0);
writeDigitalPin(a1,'D9',0);
end
end
end
if sign(pwdc3)==1
writeDigitalPin(a2,'D7',1);
writeDigitalPin(a2,'D8',0);
else if sign(pwdc3)==-1
writeDigitalPin(a2,'D7',0);
writeDigitalPin(a2,'D8',1);
else if sign(pwdc3)==0
writeDigitalPin(a2,'D7',0);
writeDigitalPin(a2,'D8',0);
end
end
end
end
end
John - so looking closer at the error message
The value of the "a" property must be a numeric array without any Inf's or NaN's.
it isn't actually referring to a variable (in your code) named a. It is more likely referring to a parameter that is being passed into a function whose input parameter name (as defined in the function signature) is named a. The problem is that I don't know which of the functions might be the problem. It could be lqr since I've seen other posts (that have this same error message) with other functions from the Control System Toolbox. You may need to reduce your code to the smallest working example that generates this error so that you can pinpoint which function call is responsible for it.

Sign in to comment.

Categories

Find more on MATLAB Support Package for Arduino Hardware in Help Center and File Exchange

Asked:

on 9 Apr 2019

Edited:

on 10 May 2019

Community Treasure Hunt

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

Start Hunting!