ploting in while loop start with uncalled for changes

2 次查看(过去 30 天)
Hello all,
Sorry for this legnthy description.
I am trying to animate a robot (a very simple robot with 3 links).
The code supposed to do the following:
starting with an initial configuration, the mouse cursor shouls be able to move over the figure (the robot) and pick a poit on the robot. a function is caled (IsPointOneLine.m) to see if the point is on the robot's link or not ( located on the 1st link,the 2nd or the 3rd one).
After getting the point on one of the mentioned links, it updates the robot's legnth (for example, if the cursor is on the 2nd link, l = [2;2;1] will become lnew = [2;norm(point-f(:,1)')] where f(:,1) is the coordinated of the 1st joint).
Not to be mentioned that the location check should only takes once (that's why I flagged it by i==0 initially and i==1 as the point on the robot is taken already).
The new jacobian obtains and updates the state of the robot (x) which is the angle between the links of the robot. in this case if the cursor moves the location is updated and function f which is forward kinematic realize and fulfill the robot in the while loop.
here are the problem:
. After being run, the robot in the figur should wait for the mouse event but there you can see it moves already;
. In the while loop, each time robot moves, its new confuiguration is plotted which is not favorable (I only need the very curent robot plot not all those previouse ones).
Is there any way to fix these isues ?
Thanks a lot
function vg_p1
% SS = get(0,'ScreenSize');
% figure('position',[10,10,SS(3)-100,SS(4)-200]); axis off; hold on;
i = 0
T = 5; %Number of datapoints
D = 3; %State space dimension (x1,x2,x3)
l = [2; 2; 1]; %Robot links lengths
fh = [-2; 3]; %Desired target for the end-effector
x = ones(D,1) * pi/D; %Initial robot pose
L = tril(ones(D)); %Transformation matrix
fi = [L * diag(l) * cos(L * x), L * diag(l) * sin(L * x)]'; %Forward kinematics (for all articulations, including end-effector)
f = [L * diag(l) * cos(L * x), L * diag(l) * sin(L * x)]'; %Forward kinematics (for all articulations, including end-effector)
J = [-sin(L * x)' * diag(l) * L; cos(L * x)' * diag(l) * L];
set(gcf,'WindowButtonMotionFcn',{@wbm});
axis([-1,1,-1,1]);
xmo = get(0,'PointerLocation');
xi = [0, 0];
xp=[0,0]
xtemp = [];
disp('Move mouse to draw. Press right mouse button to quit.');
while 1
mb = get(gcf,'SelectionType');
if strcmp(mb,'alt')==1
close all;
return;
end
if double(get(gcf,'CurrentCharacter'))==27
close all;
return;
end
h = plot([0,fi(1,:)], [0,fi(2,:)], 'y-','LineWidth',2); %Plot robot
hold on
xp=xi
cur_point = get(gca,'Currentpoint');
xi(1:2) = cur_point(1,1:2)';
xm = get(0,'PointerLocation');
% x = x + (xm - xmo) * 2E-4;
% xmo = xm;1
% i
if i==0
xtemp = xi(1:2);
R1 = isPointOnLine(fi(:,1)',[0 0] ,xi(1:2)',0.1)
R2 = isPointOnLine(fi(:,2)',fi(:,1)',xi(1:2)',0.1)
R3 = isPointOnLine(fi(:,3)',fi(:,2)',xi(1:2)',0.1)
if R1==1
fprintf("first link is activated!\n");
lnew = [norm(xi(1:2)-zeros(1,2)');zeros(2,1)];
elseif R2==1
fprintf("scond link is activated!\n");
lnew = [l(1);norm(xi(1:2)-f(:,1)');0];
elseif R3==1
fprintf("third link in activated!\n");
lnew = [l(1:2);norm(xi(1:2)-f(:,2)')];
end
i=i+1;
end
% clf();
if i ~=1
f = [L * diag(l) * cos(L * x), L * diag(l) * sin(L * x)]'; %Forward kinematics (for all articulations, including end-effector)
J = [-sin(L * x)' * diag(l) * L; cos(L * x)' * diag(l) * L]; %Jacobian (for end-effector)
x = x + J \ (xi' - xp') ; %Update state
h = plot([0,f(1,:)], [0,f(2,:)], 'B-','LineWidth',2); %Plot robot
axis equal;
% plot(xi(1), xi(2), 'k.','markersize',20);
% drawnow;
end
%clf
drawnow;
end
end
%% Mouse move
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function wbm(h,evd)
end
If
  2 个评论
dpb
dpb 2022-8-12
I didn't really look at the code, but look at animatedline and friends for this kind of animation drawing...
MEHRDAD TAVASSOLI
MEHRDAD TAVASSOLI 2022-8-13
Well It's not really an animation. what it needs to do is basically move the robot acording to the curso's location.
Anyway thank you for suggestion. It is another nice function in Matlab

请先登录,再进行评论。

回答(1 个)

Binaya
Binaya 2023-10-27
Hi Mehrdad,
Based on the provided description, you would like to resolve why the plotting starts without any mouse movement and why the previous plots of mouse movements stay on the plot when a new mouse movement plot occurs. Please find the following suggestions to resolve your issue:
  1. Plotting without mouse cursor movement:
  2. Reason: Command at line number 39 inside the while loop calls the “get” function for curser position. The cursor position is returned even if the cursor has not moved, leading to execution of the following plot commands.
  3. Resolution: You can try to use “get” command with a “SelectionType option that triggers the plotting of mouse cursor movement similar to its use in line number 25 for stopping the code execution.
  4. Previous mouse movement plot persists in the current plot:
  5. Reason: Presence of “hold on” command at line number 36. “hold on” command keeps all the plots on the axes without replacement until “hold off” command is executed.
  6. Resolution: Remove the “hold on” command from line number 36. This will plot only the plot corresponding to current mouse cursor position.
Please refer to the following documentation links for more details:
  1. Hold: https://www.mathworks.com/help/matlab/ref/hold.html
  2. SelectionType: https://www.mathworks.com/help/matlab/ref/matlab.ui.figure-properties.html#buiwuyk-1-SelectionType
  3. CurrentPoint: https://www.mathworks.com/help/matlab/ref/matlab.ui.figure-properties.html#buiwuyk-1-CurrentPoint
I hope this helps.
Regards 
Binaya 

类别

Help CenterFile Exchange 中查找有关 Code Generation 的更多信息

产品


版本

R2022a

Community Treasure Hunt

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

Start Hunting!

Translated by