这是一个用刀模拟裁布的过程,因为刀尖是受刀的控制点控制,为了达到尽量精确,只能把刀尖点转换为控制点,然后插补过去。
% 计算线段的角度
function theta = get_line_angle(point1, point2)
v_x = point2(1) - point1(1);
v_y = point2(2) - point1(2);
L = sqrt(v_x^2 + v_y^2);
%防止线段长度为零的情况
if L < 1e-4
theta = 0;
return
end
theta = acos(v_x / L)*180/pi;
if v_y < 0
theta = 360 - theta;
end
% 计算线段之间的夹角在-180-180度之间
function theta = get_inter_angle(v1_x, v1_y, v2_x, v2_y)
new_x = (v1_x * v2_x + v1_y * v2_y);
new_y = (v1_x * v2_y - v2_x * v1_y);
theta = acos(new_x / sqrt(new_x^2 + new_y^2))*180/pi;
if new_y < 0
theta = -theta ;
end
%得到刀的控制点中心
function new_points = get_control_points(L, points)
new_points = [];
n = size(points,1);
v_inter_step = 0;
for i = 1:n
pre_i = max(1,i-1);
next_i = min(n,i+1);
point1 = points(pre_i,:);
point2 = points(i,:);
point3 = points(next_i,:);
if norm(point3 - point1)<eps || v_inter_step == 1
v_inter_step = v_inter_step + 1;
else
v_inter_step = 0;
end
if i == 1
line_angle = get_line_angle(point2,point3);
inter_angle = 0;
elseif i==n
line_angle = new_points(end,3);
inter_angle = 0;
else
v1_x = point2(1) - point1(1);
v1_y = point2(2) - point1(2);
v2_x = point3(1) - point2(1);
v2_y = point3(2) - point2(2);
line_angle = new_points(end,3);
if v_inter_step == 2
inter_angle = get_inter_angle(-v1_x,-v1_y,v2_x,v2_y);
else
inter_angle = get_inter_angle(v1_x,v1_y,v2_x,v2_y);
end
end
arc_angle = (line_angle + inter_angle)*pi/180;
knife_vect = L*[cos(arc_angle),sin(arc_angle)];
max_inter_angle = 10;
if abs(inter_angle)<20
temp_points = [point2 - knife_vect,line_angle + inter_angle,i];
elseif v_inter_step == 1
temp_points = [point2 + knife_vect,line_angle - 180 + inter_angle,i] ;
else
m = floor(abs(inter_angle)/max_inter_angle)+1;
temp_points = zeros(m,4);
for j = 0:m
new_angle = (line_angle + j*inter_angle/m)*pi/180;
new_knife_vect = L*[cos(new_angle),sin(new_angle)];
temp_points(j+1,:) = [point2 - new_knife_vect, line_angle + j*inter_angle/m,i];
end
end
new_points = [new_points;temp_points];
end
%main函数
%模拟刀的跟随裁剪
clc;clear all;
points = [0 0
490 0
500 20
510 0
1000 0
1000 1000
500 1000
500 995
500 1000
0 1000
0 500
5 500
0 500
0 0];
knife_e = 50;
new_points = get_control_points1(knife_e, points);
n = size(new_points,1);
for i = 1: n-1
p1 = new_points(i,:);
p2 = new_points(i+1,:);
L = norm(p2 - p1);
m = floor(L/10) + 1;
for j = 0:m
p = ((m - j)*p1 + j*p2 )/m;
p_start = [p(1),p(2)];
t = p(3)*pi/180;
p_end = p_start + knife_e * [cos(t) sin(t)];
plot(points(:,1),points(:,2),'-s')
hold on
axis equal;
plot(new_points(:,1),new_points(:,2),'-*')
plot([p_start(1),p_end(1)],[p_start(2),p_end(2)],'-*');
text(p_start(1), p_start(2) ,'start')
text(p_end(1), p_end(2) ,'end')
hold off
pause(0.1);
end
pause(0.3);
end