Advertisement
Guest User

Untitled

a guest
Mar 10th, 2020
93
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 16.65 KB | None | 0 0
  1. import plus
  2. import Arenas
  3. import math
  4.  
  5. ## CAMERA IDEAS ##
  6. #Follows bot that is recieving the most damage or is about to die
  7. #Overhead cam (like orbit but above instead of behind)
  8. #Follows soccer ball and stops short of goalie's net to gve a more horizontal view (but still angled)
  9. #Rounded Rectnagle (look below)
  10. #incorporate plus.getScreenSize() to make FOV more accurate
  11. #make efficienct cam
  12.  
  13. class ActionCamera(object):
  14.     """ Keeps a perpendicular angle to the fighting and avoids visual obstructions whenever possible """
  15.     def __init__(self, name="Action Cam", fieldOfView=75, defeatedDelay=2):
  16.         self.name = name
  17.        
  18.         self.defeatedDelay = defeatedDelay
  19.         degrad = 0.01745
  20.         self.prevCam = [[0,0,0], [0,0], fieldOfView*degrad]
  21.         self.nextCam = [[0,0,0], [0,0], fieldOfView*degrad]
  22.        
  23.         self.players = None
  24.         self.playerCount = 0
  25.         self.expiration = {}
  26.        
  27.     def apply(self):
  28.         self.updatePlayers()
  29.        
  30.     def updatePlayers(self):
  31.         if self.players == None: #we had to update after the __init__ of the arena
  32.             self.players = list(plus.getPlayers())
  33.             self.playerCount = len(self.players)
  34.            
  35.         for p in self.players:
  36.             if plus.isEliminated(p) or plus.isDefeated(p):
  37.                 if p in self.expiration:
  38.                     if self.expiration[p]  <= plus.getTimeElapsed():
  39.                         self.players.remove(p)
  40.                         self.playerCount -= 1
  41.                 else:
  42.                     self.expiration[p] = plus.getTimeElapsed() + self.defeatedDelay
  43.        
  44.     def Tick(self):
  45.         a = Arenas.currentArena #have to keep it local otherwise the arena doesn't close properly
  46.         duration = a.__getattr__tickInterval__()
  47.        
  48.         self.updatePlayers()
  49.         locs = [plus.getLocation(b) for b in self.players]
  50.         highest = max([l[1] for l in locs])
  51.        
  52.         midpointBtwnBots = [0,0,0]
  53.         distanceBtwnBots = 0
  54.         outermost = None
  55.         for i,loc1 in zip(xrange(self.playerCount), locs):
  56.             midpointBtwnBots[0] += loc1[0]
  57.             midpointBtwnBots[1] += loc1[1] #not really necessary but here for completeness
  58.             midpointBtwnBots[2] += loc1[2]
  59.             for loc2 in locs[i+1:]:
  60.                 dist = ((loc1[0]-loc2[0])**2 + (loc1[1]-loc2[1])**2 + (loc1[2]-loc2[2])**2)**0.5
  61.                 if dist > distanceBtwnBots:
  62.                     distanceBtwnBots = dist
  63.                     outermost = (loc1, loc2)
  64.        
  65.         midpointBtwnBots = map(lambda x: x/self.playerCount,  midpointBtwnBots)
  66.        
  67.         distanceToCam = max(distanceBtwnBots, 10) * 0.6
  68.         heightOfCam = max(distanceBtwnBots, 10) * 0.4
  69.        
  70.         # Use perpendicular of furthest bots to determine horizontal angle or spin around bot if there aren't any active bots
  71.         if outermost != None: #more than one bot available
  72.             self.nextCam[1][1] = -math.atan2(outermost[1][2]-outermost[0][2], outermost[1][0]-outermost[0][0])
  73.         else: #only one bot available
  74.             self.nextCam[1][1] = self.prevCam[1][1] + 0.6*math.pi*duration #less radians per tick means slower but also smoother circling
  75.        
  76.         # Avoid walls between bots and try to go shorter distance
  77.         angle1 = -self.nextCam[1][1] - math.pi/2 #orbit angle from midpoint
  78.         angle2 = -self.nextCam[1][1] + math.pi/2 #orbit angle from midpoint
  79.         side1 = [midpointBtwnBots[0] + math.cos(angle1) * distanceToCam,
  80.                  highest + heightOfCam,
  81.                  midpointBtwnBots[2] + math.sin(angle1) * distanceToCam]
  82.         side2 = [midpointBtwnBots[0] + math.cos(angle2) * distanceToCam,
  83.                  highest + heightOfCam,
  84.                  midpointBtwnBots[2] + math.sin(angle2) * distanceToCam]
  85.         visible1 = self.playerCount
  86.         visible2 = self.playerCount
  87.         for loc in locs:
  88.             if a.RayTest(tuple(side1),loc)[0]: visible1 -= 1
  89.             if a.RayTest(tuple(side2),loc)[0]: visible2 -= 1
  90.         if visible1 == visible2 or self.playerCount < 2:
  91.             dist1 = ((self.prevCam[0][0]-side1[0])**2 + (self.prevCam[0][1]-side1[1])**2 + (self.prevCam[0][2]-side1[2])**2)**0.5
  92.             dist2 = ((self.prevCam[0][0]-side2[0])**2 + (self.prevCam[0][1]-side2[1])**2 + (self.prevCam[0][2]-side2[2])**2)**0.5
  93.             if dist1 < dist2:
  94.                 self.nextCam[0] = side1
  95.             else:
  96.                 self.nextCam[1][1] += math.pi
  97.                 self.nextCam[0] = side2
  98.         elif visible1 > visible2:
  99.             self.nextCam[0] = side1
  100.         elif visible1 < visible2:
  101.             self.nextCam[1][1] += math.pi
  102.             self.nextCam[0] = side2
  103.        
  104.         # No extra horizontal rotations (by keeping difference always less than math.pi even if we aren't within -math.pi to math.pi)
  105.         diff = self.nextCam[1][1]-self.prevCam[1][1]
  106.         if diff > math.pi:
  107.             self.nextCam[1][1] -= math.pi*2
  108.         elif diff < -math.pi:
  109.             self.nextCam[1][1] += math.pi*2
  110.        
  111.         # Vertical angle of camera
  112.         self.nextCam[1][0] = math.pi/2 - math.atan(distanceToCam/heightOfCam) #vertical
  113.        
  114.         # Move camera
  115.         #plus.animateCamera(XYZ-StartingLocation, (V-DirectionOfView, H-DirectionOfView), Starting Zoom, XYZ-EndingLocation, (V-Swing, H-Swing), End Zoom, self.delay, self.duration)
  116.         plus.animateCamera(tuple(self.prevCam[0]), tuple(self.prevCam[1]), self.prevCam[2],
  117.                            tuple(self.nextCam[0]), tuple(self.nextCam[1]), self.nextCam[2],
  118.                            0, duration)
  119.        
  120.         # Prepare for next time
  121.         if self.nextCam[1][1] > math.pi: self.nextCam[1][1] -= math.pi*2
  122.         elif self.nextCam[1][1] <= -math.pi: self.nextCam[1][1] += math.pi*2
  123.         self.prevCam = [self.nextCam[0][:], self.nextCam[1][:], self.nextCam[2]]
  124.  
  125. ##################################################################################################################################
  126.  
  127. class ActionCamDynamic(object):
  128.     """ Keeps a perpendicular angle to the fighting and avoids visual obstructions whenever possible """
  129.     def __init__(self, name="Action Cam 2", fieldOfView=75, defeatedDelay=2):
  130.         self.name = name
  131.        
  132.         self.defeatedDelay = defeatedDelay
  133.         degrad = 0.01745
  134.         self.prevCam = [[0,0,0], [0,0], fieldOfView*degrad]
  135.         self.nextCam = [[0,0,0], [0,0], fieldOfView*degrad]
  136.        
  137.         self.players = None
  138.         self.playerCount = 0
  139.         self.expiration = {}
  140.        
  141.     def apply(self):
  142.         self.updatePlayers()
  143.        
  144.     def updatePlayers(self):
  145.         if self.players == None: #we had to update after the __init__ of the arena
  146.             self.players = list(plus.getPlayers())
  147.             self.playerCount = len(self.players)
  148.            
  149.         for p in self.players:
  150.             if plus.isEliminated(p) or plus.isDefeated(p):
  151.                 if p in self.expiration:
  152.                     if self.expiration[p]  <= plus.getTimeElapsed():
  153.                         self.players.remove(p)
  154.                         self.playerCount -= 1
  155.                 else:
  156.                     self.expiration[p] = plus.getTimeElapsed() + self.defeatedDelay
  157.    
  158.     def optimalDistance(self):
  159.         threshold = 0.1745 #10 degrees
  160.         ready = 0
  161.         #while ready != 1:
  162.         #    get midpoint+angle to all points and set highest absolute to angle (between pi/2 and -pi/2)
  163.         #    if (angle > FOV/2) or (angle+theshold < FOV/2):
  164.         #        moveOut = angle < FOV/2
  165.         #        ready = -1
  166.         #        A = (moveOut * math.pi) + ((not moveOut)*2*angle - angle)
  167.         #        C = ((not moveOut) * math.pi) + (moveOut*FOV - FOV/2)
  168.         #        B = math.pi/2 - A - C
  169.         #        c = distance to bot in this 2D
  170.         #        b = c/sin(C) * sin(B)
  171.         #        move back by b amount
  172.         #    else: ready += 1
  173.    
  174.     def Tick(self):
  175.         a = Arenas.currentArena #have to keep it local otherwise the arena doesn't close properly
  176.         duration = a.__getattr__tickInterval__()
  177.        
  178.         self.updatePlayers()
  179.         locs = [plus.getLocation(b) for b in self.players]
  180.         highest = max([l[1] for l in locs])
  181.        
  182.         midpointBtwnBots = [0,0,0]
  183.         distanceBtwnBots = 0
  184.         outermost = None
  185.         for i,loc1 in zip(xrange(self.playerCount), locs):
  186.             midpointBtwnBots[0] += loc1[0]
  187.             midpointBtwnBots[1] += loc1[1] #not really necessary but here for completeness
  188.             midpointBtwnBots[2] += loc1[2]
  189.             for loc2 in locs[i+1:]:
  190.                 dist = ((loc1[0]-loc2[0])**2 + (loc1[1]-loc2[1])**2 + (loc1[2]-loc2[2])**2)**0.5
  191.                 if dist > distanceBtwnBots:
  192.                     distanceBtwnBots = dist
  193.                     outermost = (loc1, loc2)
  194.        
  195.         midpointBtwnBots = map(lambda x: x/self.playerCount,  midpointBtwnBots)
  196.        
  197.         distanceToCam = max(distanceBtwnBots, 10) * 0.6
  198.         heightOfCam = max(distanceBtwnBots, 10) * 0.4
  199.        
  200.         # Use perpendicular of furthest bots to determine horizontal angle or spin around bot if there aren't any active bots
  201.         if outermost != None: #more than one bot available
  202.             self.nextCam[1][1] = -math.atan2(outermost[1][2]-outermost[0][2], outermost[1][0]-outermost[0][0])
  203.         else: #only one bot available
  204.             self.nextCam[1][1] = self.prevCam[1][1] + 0.6*math.pi*duration #less radians per tick means slower but also smoother circling
  205.        
  206.         # Avoid walls between bots and try to go shorter distance
  207.         angle1 = -self.nextCam[1][1] - math.pi/2 #orbit angle from midpoint
  208.         angle2 = -self.nextCam[1][1] + math.pi/2 #orbit angle from midpoint
  209.         side1 = [midpointBtwnBots[0] + math.cos(angle1) * distanceToCam,
  210.                  highest + heightOfCam,
  211.                  midpointBtwnBots[2] + math.sin(angle1) * distanceToCam]
  212.         side2 = [midpointBtwnBots[0] + math.cos(angle2) * distanceToCam,
  213.                  highest + heightOfCam,
  214.                  midpointBtwnBots[2] + math.sin(angle2) * distanceToCam]
  215.         visible1 = self.playerCount
  216.         visible2 = self.playerCount
  217.         for loc in locs:
  218.             if a.RayTest(tuple(side1),loc)[0]: visible1 -= 1
  219.             if a.RayTest(tuple(side2),loc)[0]: visible2 -= 1
  220.         if visible1 == visible2 or self.playerCount < 2:
  221.             dist1 = ((self.prevCam[0][0]-side1[0])**2 + (self.prevCam[0][1]-side1[1])**2 + (self.prevCam[0][2]-side1[2])**2)**0.5
  222.             dist2 = ((self.prevCam[0][0]-side2[0])**2 + (self.prevCam[0][1]-side2[1])**2 + (self.prevCam[0][2]-side2[2])**2)**0.5
  223.             if dist1 < dist2:
  224.                 self.nextCam[0] = side1
  225.             else:
  226.                 self.nextCam[1][1] += math.pi
  227.                 self.nextCam[0] = side2
  228.         elif visible1 > visible2:
  229.             self.nextCam[0] = side1
  230.         elif visible1 < visible2:
  231.             self.nextCam[1][1] += math.pi
  232.             self.nextCam[0] = side2
  233.        
  234.         # No extra horizontal rotations (by keeping difference always less than math.pi even if we aren't within -math.pi to math.pi)
  235.         diff = self.nextCam[1][1]-self.prevCam[1][1]
  236.         if diff > math.pi:
  237.             self.nextCam[1][1] -= math.pi*2
  238.         elif diff < -math.pi:
  239.             self.nextCam[1][1] += math.pi*2
  240.        
  241.         # Vertical angle of camera
  242.         self.nextCam[1][0] = math.pi/2 - math.atan(distanceToCam/heightOfCam) #vertical
  243.        
  244.         # Move camera
  245.         #plus.animateCamera(XYZ-StartingLocation, (V-DirectionOfView, H-DirectionOfView), Starting Zoom, XYZ-EndingLocation, (V-Swing, H-Swing), End Zoom, self.delay, self.duration)
  246.         plus.animateCamera(tuple(self.prevCam[0]), tuple(self.prevCam[1]), self.prevCam[2],
  247.                            tuple(self.nextCam[0]), tuple(self.nextCam[1]), self.nextCam[2],
  248.                            0, duration)
  249.        
  250.         # Prepare for next time
  251.         if self.nextCam[1][1] > math.pi: self.nextCam[1][1] -= math.pi*2
  252.         elif self.nextCam[1][1] <= -math.pi: self.nextCam[1][1] += math.pi*2
  253.         self.prevCam = [self.nextCam[0][:], self.nextCam[1][:], self.nextCam[2]]
  254.  
  255.  
  256. class CircularCamera(object):
  257.     """ Rounds the corners as it circles each bot """
  258.     def __init__(self, name="Circular Cam", fieldOfView=75, defeatedDelay=2):
  259.         self.name = name
  260.        
  261.         self.defeatedDelay = defeatedDelay
  262.         degrad = 0.01745
  263.         self.prevCam = [[0,0,0], [0,0], fieldOfView*degrad]
  264.         self.nextCam = [[0,0,0], [0,0], fieldOfView*degrad]
  265.        
  266.         self.players = None
  267.         self.playerCount = 0
  268.         self.expiration = {}
  269.        
  270.     def apply(self):
  271.         self.updateArena()
  272.         self.updatePlayers()
  273.         self.targetOfView = None
  274.         self.updateTarget(self.playerCount) #keeps rotating until we are certain
  275.        
  276.     def updatePlayers(self):
  277.         if self.players == None: #we had to update after the __init__ of the arena
  278.             self.players = list(plus.getPlayers())
  279.             self.playerCount = len(self.players)
  280.            
  281.         for p in self.players:
  282.             if plus.isEliminated(p) or plus.isDefeated(p):
  283.                 if p in self.expiration:
  284.                     if self.expiration[p]  <= plus.getTimeElapsed():
  285.                         self.players.remove(p)
  286.                         self.playerCount -= 1
  287.                 else:
  288.                     self.expiration[p] = plus.getTimeElapsed() + self.defeatedDelay
  289.    
  290.     def updateTarget(self, times=1):
  291.         # Get midpoint and locs
  292.         midpointBtwnBots = [0,0,0]
  293.         locs = []
  294.         for b in self.players:
  295.             loc = plus.getLocation(b)
  296.             midpointBtwnBots[0] += loc[0]
  297.             midpointBtwnBots[1] += loc[1]
  298.             midpointBtwnBots[2] += loc[2]
  299.             locs.append(loc)
  300.         midpointBtwnBots = map(lambda x: x/self.playerCount,  midpointBtwnBots)
  301.        
  302.         # Get angles
  303.         angles = [math.atan2(loc[2]-midpointBtwnBots[2], loc[0]-midpointBtwnBots[0]) for loc in locs]
  304.        
  305.         # Sort by angles
  306.         temp = zip(angles, locs, self.players)
  307.         sort(temp)
  308.         angles, locs, self.players = zip(*temp)
  309.        
  310.         if self.targetOfView == None:
  311.             i1 = 0
  312.             while angles[i1] < self.nextCam[1][1]:
  313.                 if i1 == self.playerCount:
  314.                     i1 = 0
  315.                     break
  316.                 i1 += 1
  317.             self.targetOfView = self.players[i1]
  318.         else:
  319.             i1 = self.players.index(self.targetOfView)
  320.        
  321.             # Get index for next on rotation
  322.             i2 = (i1+1) % self.playerCount #results in a counter clockwise rotation
  323.            
  324.             # Get switching angle
  325.             switchingAngle = math.atan2(locs[i2][2]-locs[i1][2], locs[i2][0]-locs[i1][0])
  326.            
  327.             # Fix angular references so that we can compare angles
  328.             if (self.nextCam[1][1] - switchingAngle) > math.pi: #since we're going counter clockwise
  329.                 switchingAngle += math.pi*2
  330.                
  331.             # Check to see if we've reached switching point
  332.             if switchingAngle <= self.nextCam[1][1]:
  333.                 self.targetOfView = self.players[i2]
  334.    
  335.     def Tick(self):
  336.         a = Arenas.currentArena
  337.         duration = a.__getattr__tickInterval__()
  338.        
  339.         self.updatePlayers()
  340.        
  341.         self.nextCam[1][1] = (self.getTimeElapsed() * math.pi * 0.25)
  342.         self.updateTarget()
  343.        
  344.         # No extra horizontal rotations (by keeping difference always less than math.pi even if we aren't within -math.pi to math.pi)
  345.         diff = self.nextCam[1][1]-self.prevCam[1][1]
  346.         if diff > math.pi:
  347.             self.nextCam[1][1] -= math.pi*2
  348.         elif diff < -math.pi:
  349.             self.nextCam[1][1] += math.pi*2
  350.        
  351.         # Vertical angle of camera
  352.         self.nextCam[1][0] = math.pi/4  #vertical
  353.        
  354.         # Move camera
  355.         #plus.animateCamera(XYZ-StartingLocation, (V-DirectionOfView, H-DirectionOfView), Starting Zoom, XYZ-EndingLocation, (V-Swing, H-Swing), End Zoom, self.delay, self.duration)
  356.         plus.animateCamera(tuple(self.prevCam[0]), tuple(self.prevCam[1]), self.prevCam[2],
  357.                            tuple(self.nextCam[0]), tuple(self.nextCam[1]), self.nextCam[2],
  358.                            0, duration)
  359.        
  360.         # Prepare for next time
  361.         if self.nextCam[1][1] > math.pi: self.nextCam[1][1] -= math.pi*2
  362.         elif self.nextCam[1][1] <= -math.pi: self.nextCam[1][1] += math.pi*2
  363.         self.prevCam = [self.nextCam[0][:], self.nextCam[1][:], self.nextCam[2]]
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement