def step(self,times):
     for i in range(0,times):
         if not self.on_ground:
             w=self.get_corr_w(self.o_tens,self.ang_mom)
             w_hat=vf.unit(w)
             rad=vf.mag(w)*self.dt
             step_com_node=self.get_translate(self.com_node,self.dt)
             step_corners=self.get_rotate_corners(self.centered_corners,w_hat,rad)
             self.collision_check(step_com_node,step_corners,w_hat,rad)
         else:
             w=self.get_corr_w(self.o_tens,self.ang_mom)
             rad=vf.mag(w)*self.dt
             if rad!=0:
                 w_hat=vf.unit(w)
                 self.centered_corners=self.get_rotate_corners(self.centered_corners,w_hat,rad)
                 self.o_tens=self.get_rot_o_tens2(self.o_tens,w_hat,rad)
                 self.ang_mom=self.ang_mom-self.fric*self.ang_mom*self.dt
         self.t+=self.dt
 def do_collide_after(self,step_com_node,step_corners,corners,step_o_tens,o_tens,ang_mom,com_node):
     #does collision at step in which corner is below floor, but applies those values to block at step before collision
     nodes_below=self.get_nodes_below2(step_com_node,step_corners)
     r=ar([0,0,0])
     count=0
     for n in nodes_below:
         r=r+n.p
         count+=1
     r=r/count
     (delt_v,delt_L)=self.get_delt_v_L(r=r,o_tens=step_o_tens,ang_mom=ang_mom,com_node=step_com_node)
     com_node.v=com_node.v+delt_v
     ang_mom=ang_mom+delt_L
     w=self.get_corr_w(o_tens,ang_mom)
     w_hat=vf.unit(w)
     rad=vf.mag(w)*self.dt_col
     step_com_node=self.get_translate(com_node,self.dt_col)
     step_corners=self.get_rotate_corners(corners,w_hat,rad)
     return step_com_node,step_corners,ang_mom,com_node,w_hat,rad
 def do_collide_before(self,step_com_node,step_corners,corners,o_tens,ang_mom,com_node):
     #does collision as if happening at step before corner goes below floor
     nodes_below=self.get_nodes_below(step_com_node,step_corners,corners)
     r=ar([0,0,0])
     count=0
     for n in nodes_below:
         r=r+n.p
         count+=1
     r=r/count
     (delt_v,delt_L)=self.get_delt_v_L(r=r,o_tens=o_tens,ang_mom=ang_mom,com_node=com_node)
     com_node.v=com_node.v+delt_v
     ang_mom=ang_mom+delt_L
     w=self.get_corr_w(o_tens,ang_mom)
     w_hat=vf.unit(w)
     rad=vf.mag(w)*self.dt_col
     step_com_node=self.get_translate(com_node,self.dt_col)
     step_corners=self.get_rotate_corners(corners,w_hat,rad)
     return step_com_node,step_corners,ang_mom,com_node,w_hat,rad
 def collide(self):
     self.dt_col=self.dt/self.col_N
     com_node=self.com_node
     corners=self.centered_corners
     o_tens=self.o_tens
     ang_mom=self.ang_mom
     print('collide initiated')
     for i in range(0,self.col_N):
         w=self.get_corr_w(o_tens,ang_mom)
         w_hat=vf.unit(w)
         rad=vf.mag(w)*self.dt_col
         step_com_node=self.get_translate(com_node,self.dt_col)
         step_corners=self.get_rotate_corners(corners,w_hat,rad)
         if not self.on_ground:
             if not self.nodes_below(step_com_node,step_corners):
                 com_node=step_com_node
                 corners=step_corners
                 o_tens=self.get_rot_o_tens2(o_tens,w_hat,rad)
             else:
                 (step_com_node,step_corners,ang_mom,com_node,w_hat,rad)=self.do_collide_before(step_com_node,step_corners,corners,o_tens,ang_mom,com_node)
                 if not self.nodes_below(step_com_node,step_corners):
                     print('all good')
                     com_node=step_com_node
                     corners=step_corners
                     o_tens=self.get_rot_o_tens2(o_tens,w_hat,rad)
                 else:
                     if self.get_trans_KE(com_node)+self.get_alt_rot_KE(o_tens,ang_mom)<=self.ground_E_tol:
                         print('on ground, energy less than ground tol')
                         com_node.v=ar([0,0,0])
                         com_node.a=ar([0,0,0])
                         ang_mom=ar([0,0,ang_mom[2]])
                         self.on_ground=True
                     else:
                         step_o_tens=self.get_rot_o_tens2(o_tens,w_hat,rad)
                         (step_com_node,step_corners,ang_mom,com_node,w_hat,rad)=self.do_collide_after(step_com_node,step_corners,corners,step_o_tens,o_tens,ang_mom,com_node)
                         if not self.nodes_below(step_com_node,step_corners):
                             print('all good 2')
                             com_node=step_com_node
                             corners=step_corners
                             o_tens=self.get_rot_o_tens2(step_o_tens,w_hat,rad)
                         else:
                             step_o_tens=self.get_rot_o_tens2(o_tens,w_hat,rad)
                             (step_com_node,step_corners,ang_mom,com_node,w_hat,rad)=self.do_collide_after(step_com_node,step_corners,corners,step_o_tens,o_tens,ang_mom,com_node)
                             if not self.nodes_below(step_com_node,step_corners):
                                 print('all good 3')
                                 com_node=step_com_node
                                 corners=step_corners
                                 o_tens=self.get_rot_o_tens2(step_o_tens,w_hat,rad)
                             else:
                                 step_o_tens=self.get_rot_o_tens2(o_tens,w_hat,rad)
                                 (step_com_node,step_corners,ang_mom,com_node,w_hat,rad)=self.do_collide_after(step_com_node,step_corners,corners,step_o_tens,o_tens,ang_mom,com_node)
                                 if not self.nodes_below(step_com_node,step_corners):
                                     print('all good 4')
                                     com_node=step_com_node
                                     corners=step_corners
                                     o_tens=self.get_rot_o_tens2(step_o_tens,w_hat,rad)
                                 else:
                                     step_o_tens=self.get_rot_o_tens2(o_tens,w_hat,rad)
                                     (step_com_node,step_corners,ang_mom,com_node,w_hat,rad)=self.do_collide_after(step_com_node,step_corners,corners,step_o_tens,o_tens,ang_mom,com_node)
                                     if not self.nodes_below(step_com_node,step_corners):
                                         print('all good 5')
                                         com_node=step_com_node
                                         corners=step_corners
                                         o_tens=self.get_rot_o_tens2(step_o_tens,w_hat,rad)
                                     else:
                                         print('fail, on ground')
                                         com_node.v=ar([0,0,0])
                                         com_node.a=ar([0,0,0])
                                         ang_mom=ar([0,0,ang_mom[2]])
                                         self.on_ground=True
         else:
             w=self.get_corr_w(self.o_tens,self.ang_mom)
             rad=vf.mag(w)*self.dt
             if rad!=0:
                 w_hat=vf.unit(w)
                 corners=self.get_rotate_corners(self.centered_corners,w_hat,rad)
                 o_tens=self.get_rot_o_tens2(self.o_tens,w_hat,rad)
                 ang_mom=self.ang_mom-self.fric*self.ang_mom*self.dt
             else:
                 print('done spinning')
                 break
     print('collide complete')
     return com_node,o_tens,corners,ang_mom
 def get_rot_o_tens2(self,o_tens,w_hat,rad):
     return ar([vf.unit(rotate.point(point=ax,w_hat=w_hat,rad=rad)) for ax in o_tens])
 def get_rot_o_tens(self,o_tens,w):
     return ar([vf.unit(rotate.point(point=ax,w_hat=vf.unit(w),rad=vf.mag(w*self.dt))) for ax in o_tens])