check move

This commit is contained in:
Ian Jauslin 2021-09-29 03:24:23 -04:00
parent a5caeec29a
commit 159ac83e86

View File

@ -14,7 +14,6 @@ class Cross():
self.pos=Point(x,y)
self.color=kwargs.get("color",(0,0,1))
self.selected=False
self.stuckto=None
# set position
def setpos(self,x,y):
@ -46,7 +45,19 @@ class Cross():
# check whether a cross at pos interacts with cross
def check_interaction(self,pos):
return (pos-self.pos).int()**2>=5
# allow for error
return int(pos.x-self.pos.x+sgn(pos.x-self.pos.x)*1e-11)**2+int(pos.y-self.pos.y+sgn(pos.y-self.pos.y)*1e-11)**2>=5
# check whether a cross at position pos is touching self
def check_touch(self,pos):
rel=pos-self.pos
for i in [-3,-2,-1,1,2,3]:
# allow for error
if abs(rel.x-i)<1e-11 and abs(rel.y)<=4-abs(i)+1e-11 and abs(rel.y)>=3-abs(i)-1e-11:
return True
if abs(rel.y-i)<1e-11 and abs(rel.x)<=4-abs(i)+1e-11 and abs(rel.x)>=3-abs(i)-1e-11:
return True
return False
# find position along a line that comes in contact with the line going through pos in direction v
def move_on_line_to_stick(self,pos,v):
@ -92,7 +103,7 @@ class Cross():
closest=self.move_on_line_to_stick_relative(Point(-x.x,x.y),Point(-v.x,v.y))
return Point(-closest.x,closest.y)
# move along edge of cross while remaining stuck
# move along edge of cross
def move_along(self,newpos,pos):
rel=pos-self.pos
# check if the particle is stuck in the x direction
@ -220,7 +231,7 @@ class Cross_painter(Widget):
def on_touch_down(self,touch):
# create new cross
if touch.button=="right":
if self.check_add(Point(touch.x/Cross.size,touch.y/Cross.size)):
if self.check_interaction_any(Point(touch.x/Cross.size,touch.y/Cross.size),None):
new=Cross(touch.x/Cross.size,touch.y/Cross.size)
with self.canvas:
new.draw()
@ -258,30 +269,37 @@ class Cross_painter(Widget):
# none found
return None
# check whether a position intersects with any of the crosses
def check_interaction_any(self,pos,exception):
for other in self.crosses:
if other!=exception:
if other.check_interaction(pos)==False:
return False
return True
# check that a cross can move to new position
def check_move(self,newpos,cross):
# whether newpos is acceptable
accept_newpos=True
for other in self.crosses:
# do not compare a cross to itself
if other!=cross:
# move would make cross overlap with other
if other.check_interaction(newpos)==False:
# check if cross is stuck to other
if cross.stuckto==other:
accept_newpos=False
# check if cross touches other
if other.check_touch(cross.pos):
# move along other while remaining stuck
return other.move_along(newpos,cross.pos)
candidate=other.move_along(newpos,cross.pos)
else:
# stick to the cross
cross.stuckto=other
return other.move_on_line_to_stick(cross.pos,newpos-cross.pos)
# reset stuckto if move is allowed
cross.stuckto=None
candidate=other.move_on_line_to_stick(cross.pos,newpos-cross.pos)
if self.check_interaction_any(candidate,cross):
return candidate
if accept_newpos:
return newpos
# check that a cross can be added at position
def check_add(self,pos):
for cross in self.crosses:
if cross.check_interaction(pos)==False:
return False
return True
else:
# cannot move cross at all, try again
return self.check_move(candidate,cross)