Ejemplo n.º 1
0
 def _attack(self,a,b):
     #Расчёт того, насколько глубоко проник удар I.3
     OO = Vector(b.pos[0].x-a.pos[0].x, b.pos[0].y-a.pos[0].y, isPolar = False) # Вектор, соединяющий центры ботов
     at = Vector(a.radius + a._attack * a._attack_range * a.get_strong() * a.radius, a.pos[1], isPolar = True) #вектор атаки
     if abs(abs_angl(at.phi - OO.phi)) < pi / 2:
         ah = Vector(cos(at.phi - OO.phi)*OO.r, at.phi, isPolar = True) # вектор до высоты, опущенной из центра b
         f_at = at.r-ah.r # первая часть проникновения
         OH = (ah - OO).r # длинна высота из центра b
         if OH < b.radius:
             BH = sqrt(b.radius*b.radius - OH*OH)
             f_at += BH
             if f_at > 0:
                 write_inf("Attack: %d --> %d, by Str %.3f" %(a._id,b._id,f_at))
                 if b.status != 0:
                     f_at *= a._attack * a.get_strong() / a.radius #вычисляем силу атаки
                     if BH > 0.001: # вычисляем угловое ускорение
                         omega = f_at * sin(atan(OH/BH)) # учитываем энергию a и силу удара
                     else:
                         omega = 0
                     b.energy (- f_at)
                     b._add_accel((OO.one() * f_at, omega)) #отталкиваем и крутим противника
                     return f_at
     return 0
Ejemplo n.º 2
0
 def subtractspeed(self):
     self.hook.vel = Vector(0, -1)
Ejemplo n.º 3
0
 def addspeed(self):
     self.hook.vel = Vector(0, 1)
Ejemplo n.º 4
0
 def within(self, pos):
     return (Vector.fTuple(pos) - self.pos).mag() <= self.r
Ejemplo n.º 5
0
def mouse(position):
    global ball
    if ball.within(position):
        ball = Ball(True)
    else:
        ball = Ball(True, Vector.fTuple(position))
Ejemplo n.º 6
0
    def within(self, pos):
        return (Vector.fTuple(pos) - self.pos).mag() <= self.r

    def collides(self, rect: Rect):
        dx = min(abs(self.pos.x - rect.min.x), abs(self.pos.x - rect.max.x))
        dy = min(abs(self.pos.y - rect.min.y), abs(self.pos.y - rect.max.y))
        mid = (rect.max - rect.min) / 2 + rect.min - self.pos
        return not (dx * dx + dy * dy < self.r * self.r or
                    (dx < self.r or dy < self.r) or
                    (abs(mid.x) < rect.width / 2
                     and abs(mid.y) < rect.height / 2))


#stage = Rect(Vector(10,10),WIDTH-20,HEIGHT-20)
stage = Rect(Vector(0, 0), WIDTH, HEIGHT)
ball = Ball(True)


def draw(canvas):
    ball.update(1 / 60)
    ball.draw(canvas)


def mouse(position):
    global ball
    if ball.within(position):
        ball = Ball(True)
    else:
        ball = Ball(True, Vector.fTuple(position))
Ejemplo n.º 7
0
 def __init__(self, pos: Vector, width, height):
     self.min = pos
     self.max = pos + Vector(width, height)
     self.width = width
     self.height = height
Ejemplo n.º 8
0
        # next time step!
        t = t + dt

    print("Simulation ran for {} seconds".format(time.time()-start))

    return time_list, altitude_list, drag_list, velocity_list, phi_list, thrust_list, mass_list



recalculate = True
earth = Earth()

if recalculate:
    
    # 8000kg to LEO please.
    rocket = AtlasV401(8.0e3, Vector([0.0, earth.radius, 0.0]) )
    rocket.velocity = earth.surface_speed(rocket.position)

    time_list, altitude_list, drag_list, velocity_list, phi_list, thrust_list, mass_list = run_simulation(earth, rocket, 150e3)
    np.savetxt('launch.txt', np.c_[time_list, altitude_list, drag_list, velocity_list, phi_list, thrust_list, mass_list], header='time, alt, drag, velocity, phi, thrust, mass_list', delimiter=',')
    altitude_list = np.array(altitude_list)
    phi_list = np.array(phi_list)
else:
    C = np.loadtxt('launch.txt', delimiter=',')
    time_list = C[:,0]
    altitude_list = C[:,1]
    drag_list = C[:,2]
    velocity_list = C[:,3]    
    phi_list = C[:,4]
    thrust_list = C[:,5]
    mass_list = C[:,6]
Ejemplo n.º 9
0
def run_simulation(body, rocket, target_orbit):
   
    # Time
    t = 0.0

    # Our step size
    dt = 0.1


    time_list = []
    altitude_list = []
    phi_list = []
    drag_list = []
    thrust_list = []
    velocity_list = []
    mass_list = []

    start = time.time()
    
    rocket.throttle = 1.0

    # Let's run our simulation
    for i in range(75000):
        
        # gravity depends on altitude!
        A_gravity = body.accelleration(rocket.position)

        # Valid up to 2500,000 meters
        P0, density = body.air_pressure_and_density(rocket.position)

        # AUTO PILOT
        # really crude pitch control. Once above target_orbit. start pushing along the surface of the earth        

        # First find orientation of the rocket. We assume this is always
        # along the surface of the earth, which is the tangent of the 
        # position vector.
        orientation = Vector([-rocket.position[1], rocket.position[0],0])
        
        # In order to rotate the force vector 'upwards' a certain degree
        # we need to find the rotation axis. This is the vector orthogonal
        # to the position and the orientation.
        rotation_axis = rocket.position.cross( orientation ).normalize()

        # High tech auto pilot
        # Straight up first, then abruptly point force vector along the
        # surface of the earth at 200km up. Then when orbital velocity is
        # acchieved power down.
        delta = 1.0
        if rocket.position.magnitude > body.radius + 1e3:
            delta = 0.5
        if rocket.position.magnitude > body.radius + 200e3:
             delta = 0.1

        # should really test for velocity parallel with Earth.
        if rocket.velocity.magnitude > 8672.0:
            rocket.throttle = 0.0

        # Negative rotation means point the force vector out from earth
        # along the surface.
        orientation.rotate(  - delta * math.pi/2.0, rotation_axis )
        rocket.set_orientation(orientation.normalize())

        # Force from rocket thurst depends on altitude    
        F_rocket = rocket.thrust(P0)
        
        # Force from drag due to atmosphere
        F_drag = rocket.drag(density)

        # Force from Gravity
        F_gravity = A_gravity * rocket.mass()
        
        # Make sure our airframe can handle!
        F_rocket_mag = F_rocket.magnitude
        F_drag_mag = F_drag.magnitude
        F_gravity_mag = F_gravity.magnitude
        force_mag_list = [F_rocket_mag, F_drag_mag, F_gravity_mag]

        # if the drag magnitude becomes too big, the airframe will break.    
        maxForce = sum( force_mag_list )
        if ( maxForce > rocket.max_forces ):
            print("R.U.D. Rapid Unscheduled Dissambly, too much forces, your rocket broke up in mid flight, iteration {}".format(i))
            print("velocity={} altitude={}, max_force={}, force_list={} delta={}".format(rocket.velocity, rocket.position.magnitude, maxForce, force_mag_list, delta))
            break

        # Sum Forces: Weight, Rocket Thrust and Drag in 3 dimensions.
        Fs = F_rocket + F_drag + F_gravity
        dv = Fs * (dt / rocket.mass())
        
        # Time step!
        rocket.velocity += dv
        rocket.position += rocket.velocity * dt

        # did we make it back to terra firma?
        # hope we are going slow.
        if rocket.position.magnitude < body.radius - 1:
            print("Current Forces = {}".format(force_mag_list))
            if rocket.velocity.magnitude > 5:
                print("R.U.D. Rapid Unscheduled Dissambly, welcome home!")
            else:
                print("Level: Musk, Mars is next")
            break

        # debug print
        if i%5000==0:
            print("velocity={} pos={}, drag={} delta={}".format(rocket.velocity, rocket.position.magnitude, F_drag, delta))

        # step the rocket time ahead, this burns the fuel and potentially does stage sep.
        rocket.time_step(dt, t)
        
        # keep a list of maxForce and position so we can plot.
        time_list.append(t)    
        drag_list.append( ( F_drag_mag  ) / 1000.0 )
        thrust_list.append( (F_rocket_mag ) / 1000.0 )
        altitude_list.append((rocket.position.magnitude - body.radius ) / 1000.0)
        phi_list.append( 180.0 * rocket.position.phi / math.pi )
        velocity_list.append( rocket.velocity.magnitude )
        mass_list.append(rocket.mass())
        # next time step!
        t = t + dt

    print("Simulation ran for {} seconds".format(time.time()-start))

    return time_list, altitude_list, drag_list, velocity_list, phi_list, thrust_list, mass_list
Ejemplo n.º 10
0
    def draw(self, canvas):
        self.update()
        for ball in self.balls:
            ball.draw(canvas)
        for wall in self.walls:
            wall.draw(canvas)


# The canvas dimensions
CANVAS_WIDTH = 600
CANVAS_HEIGHT = 400

# Creating the objects84

ba = Ball(Vector(200, 200), Vector(0, 0), 20, 10, 'blue', True)
bb = Ball(Vector(220, 200), Vector(-1, -1), 20, 10, 'green')
bc = Ball(Vector(100, 100), Vector(2, 3), 50, 10, 'purple')
bd = Ball(Vector(300, 200), Vector(0, 0), 20, 10, 'blue', True)
be = Ball(Vector(400, 100), Vector(0, 0), 50, 10, 'blue', True)
bf = Ball(Vector(500, 200), Vector(0, 0), 30, 10, 'blue', True)
bg = Ball(Vector(1500, 100), Vector(2, 3), 20, 10, 'orange')

wt = Wall(10, 5, 'red', "t")
wb = Wall(CANVAS_HEIGHT - 10, 5, 'red', "b")
wl = Wall(10, 5, "red", "l")
wr = Wall(CANVAS_WIDTH - 10, 5, "red", "r")
i = Interaction([wt, wb, wl, wr], [ba, bb, bc, bd, be, bf, bg])

# Create a frame and assign callbacks to event handlers
frame = simplegui.create_frame("ball-wall", CANVAS_WIDTH, CANVAS_HEIGHT)
Ejemplo n.º 11
0
def mouse(position):
	global ball
	if ball.within(position):
		ball.vel = (Vector.fTuple(position)-ball.pos)*50
	else:
		ball = Ball(True,Vector.fTuple(position))
Ejemplo n.º 12
0
class Rocket:

    """
    Rocket Constructor
    takes a list of stages
    
    Rocket currently is simulated as a point mass. Real geometry will be later.

    Only simple stacked stages for now. Side boosters in next iteration.

    max_force = maximum force the airframe can handle.
    position = cartesian coordinates ( body center is 0,0 )
    velocity = orientation, please face rocket pointing up!
    """
    def __init__(self, stages, max_force, position, orientation = None):

        self.__stages = stages
        self.__current_stage = 0
        self.__max_force = max_force
        self.__position = position
        

        if orientation == None:
            # pick orientation orthogonal to surface.
            self.__orientation = self.__position.deepcopy().normalize()            
        else:
            self.__orientation = orientation

        self.__velocity = Vector()
        self.__drag = Vector()
        self.__thrust = Vector()
        self.__throttle = 0.0
        

    @property
    def max_forces(self):
        return self.__max_force

    @property
    def position(self):
        return self.__position

    @position.setter
    def position(self, value):
        self.__position = value

    @property
    def velocity(self):
        return self.__velocity

    @velocity.setter
    def velocity(self, value):
        self.__velocity = value
    

    def drag_coefficient(self):
        # really this is dependent on velocity and vehicle configuration 
        # see https://space.stackexchange.com/questions/12649
        return 0.30


    def drag(self, atmosphere_mass_density):

        # find the wides part of the rocket and
        # use that for drag calculations
        max_drag_surface = 0.0
        for stage in self.__stages:
            if not stage.jettisoned and stage.drag_surface >= max_drag_surface:
                max_drag_surface = stage.drag_surface

        # Get velocity
        velocity = self.__velocity.magnitude

        # No speed, no drag!
        if ( velocity == 0.0 ):
            self.__drag.zero()
            return self.__drag
        
        # Calculate drag depends on atmosphere of course
        f = -0.5 * atmosphere_mass_density * velocity * velocity * self.drag_coefficient() * max_drag_surface
        
        # Force is directed against the velocity vector.
        return self.__drag.assign(self.velocity).mult(f / velocity)
        

    def mass(self):

        mass = 0.0
        for stage in self.__stages:
            if not stage.jettisoned:
                mass += stage.mass

        return mass


    def thrust(self, p_external):

        # Only the lowest stage can be active at any time for now.
        # Once we get multiple stages running at the same time 
        # this will change a bit.
        stage = self.__stages[self.__current_stage] 
        
        if stage.propellant_mass <= 0.0:
            self.__thrust.zero()
            return self.__thrust

        
        F = stage.thrust(p_external)        
        return self.__thrust.assign(self.__orientation).mult(F)        

    def time_step(self, dt, t):
        
        stage = self.__stages[self.__current_stage]
        
        propellant_left = stage.burn(dt)
        if propellant_left <= 0.0 and stage.jettison_after_use and self.__current_stage < len(self.__stages) - 1:
            print("Staging! {} jettisoning {}, next stage = {}".format(t, self.__stages[self.__current_stage].name, self.__stages[self.__current_stage+1].name))
            self.__current_stage = self.__current_stage + 1
            stage.jettisoned = True
            self.__stages[self.__current_stage].throttle = self.__throttle
            print("Force from stage {} = {}".format(self.__stages[self.__current_stage].name, self.__stages[self.__current_stage].thrust(0.0)))
            

    @property
    def throttle(self):
        return self.__throttle

    @throttle.setter
    def throttle(self, value):
        self.__throttle = value
        stage = self.__stages[self.__current_stage]
        stage.throttle = value

    # Once we go away from point source we can calculate 
    # orientation based on forces. For now fake it!
    def set_orientation(self, orientation):
        self.__orientation = orientation
Ejemplo n.º 13
0
 def __init__(self, pos):
     self.pos = pos
     self.url = "https://raw.githubusercontent.com/CougarTasker/twenty-four/master/proto/images/Fishing%20hook.jpeg"
     self.img = simplegui.load_image(self.url)
     self.ratio = 1 / 46
     self.vel = Vector()
Ejemplo n.º 14
0
 def drawheart(self, canvas, img, i):
     canvas.draw_image(img, self.cen, self.dim,
                       (self.pos + Vector(self.pading, self.pading) +
                        self.offset * i).get_p(), self.draw_dim)
Ejemplo n.º 15
0
    def draw(self, canvas):
        self.update()
        for ball in self.balls:
            ball.draw(canvas)
        for wall in self.walls:
            wall.draw(canvas)


# The canvas dimensions
CANVAS_WIDTH = 600
CANVAS_HEIGHT = 400

# Creating the objects84

ba = Ball(Vector(200, 200), Vector(2, -1), 20, 50, 'blue', True)
bb = Ball(Vector(200.1, 200), Vector(-1, -1), 20, 50, 'green')
#bc = Ball(Vector(100,100), Vector(2,3), 20, 50, 'purple')
bd = Ball(Vector(300, 200), Vector(2, -1), 20, 50, 'blue', True)
be = Ball(Vector(400, 200), Vector(2, -1), 20, 10, 'blue', True)
bf = Ball(Vector(500, 200), Vector(2, -1), 30, 50, 'blue', True)

wt = Wall(10, 5, 'red', "t")
wb = Wall(CANVAS_HEIGHT - 10, 5, 'red', "b")
wl = Wall(10, 5, "red", "l")
wr = Wall(CANVAS_WIDTH - 10, 5, "red", "r")
i = Interaction([wt, wb, wl, wr], [ba, bb, bd, be, bf])

# Create a frame and assign callbacks to event handlers
frame = simplegui.create_frame("ball-wall", CANVAS_WIDTH, CANVAS_HEIGHT)
frame.set_draw_handler(i.draw)
Ejemplo n.º 16
0
 def fromstring(string):
     vals = string[1:len(string) - 1].rsplit(",")
     return Line(Vector.fromstring(vals[0]), Vector.fromstring(vals[1]))