sfs.py

Created by stimorol

Created on September 03, 2023

6.23 KB

Recréation simplifiée du super jeu space flight simulator. Il est possible de modifier de poussée de la fusée (en N), son poids ou son carburant. L’utilisateur peut la piloter et lire des information relatives a sa position (vitesse, angle de vol). Une version sera peut être crée pour créer sa propre fusée et ajouter des planètes.


from math import *
from kandinsky import fill_rect as rect, draw_string as txt, fill_polygon as poly, set_pixel, fill_circle as fcircle, draw_line as line
from time import *
from random import *
from ion import keydown as key

# MADE BY ARMAND JAMET, started 04.12.22 ended 08.12.22
# HOPE U LIKE IT ! <3

ground,gray,Upsilon=(0,175,0),'gray',(120,160,200)
deg=pi/180
rad=lambda θ:radians(θ)
ab=lambda x,y:int(sqrt(x**2+y**2))
t=lambda s:monotonic()-s
def toPol(list):return [(ab(i[0],i[1]),2*atan(i[1]/(i[0]+ab(i[0],i[1])+1))-pi/2) for i in list]
def toCart(list,x,y,θ):return [(x+int(r[0]*cos(θ+r[1])),y-int(r[0]*sin(θ+r[1]))) for r in list]
class Graphics():
  def __init__(g,dim=1,col=[(0,0,50),(200,)*3,(125,)*3,(255,119,0)],x=161,y=111,w=15,h=35):
    g.col,g.x,g.y,g.h=col,x//dim,y//dim,h//dim
    g.rkt=toPol([(-w//4,h),(w//4,h),(w,h-10),(w,-h),(-w,-h),(-w,h-10)])
    h-=1
    g.pCol={'Earth':'blue','Moon':'gray'}
    g.motor=toPol([(w-3,-h),(3*w//4-3,-h-7),(w//2-3,-h-7),(w-5,-h-20),(5-w,-h-20),(3-w//2,-h-7),(3-3*w//4,-h-7),(3-w,-h)])
    g.rktMap=toPol([(8,-5),(0,10),(-8,-4)])
    g.fs=(30,w-5,-h-20)
    g.r={'Earth':6_378,'Moon':3_474}
    g.newFlames(0)
    g.size=1
    g.bgCol(0);g.draw(pi/2);rect(0,y+h+20,320,h+25,ground)
  def bgCol(g,y):g.col[0]=(0,0,150-(y//1000))
  def draw(g,θ):
    rect(0,15,320,217,g.col[0])
    g.drawRkt(θ)
  def drawRkt(g,θ):
    poly(toCart(g.rkt,g.x,g.y,θ),g.col[1])
    poly(toCart(g.motor,g.x,g.y,θ),g.col[2])
    poly(toCart(g.flames,g.x,g.y,θ),g.col[3])
  def newFlames(g,th):g.flames=toPol([(-g.fs[1],g.fs[2]),(g.fs[1],g.fs[2]),(0,g.fs[2]-int(g.fs[0]*th))])
  def map(g,t,tf,θ,x,y,pnt):
    rect(0,15,320,207,(0,)*3)
    fcircle(g.x-int(x(t))//g.r[pnt],g.y+int(y(t)//g.r[pnt]+83//g.size),int(83//g.size),g.pCol[pnt])
    poly(toCart(g.rktMap,g.x,g.y,θ),g.col[1])
#    for t in range(tf):
 #     set_pixel(int(x(t))//6378+161,int(y(t))//6378+111,gray)
class Physics():
  def __init__(phy,m,T,fuel):
    phy.m,phy.T,phy.fuel,phy.g,phy.ng,phy.x,phy.y,phy.vx,phy.vy,phy.ax,phy.ay=m,T,fuel,9.81,3.983324e14,0,0,0,0,0,0
    phy.v0,phy.p0=(0,0),(0,0)
    phy.skip=1
    phy.moonPos,phy.planet=(0,384_400_000),'Earth'
    phy.r={'Earth':6378e3,'Moon':3474600}
    phy.tf=lambda:(phy.y()-phy.p0[1])/(1/2*phy.vy())
  def start(phy):
    phy.s=monotonic()
    phy.t=lambda: phy.skip*(monotonic()-phy.s)
    phy.vx=lambda:phy.ax*phy.t()+phy.v0[0]
    phy.vy=lambda:phy.ay*phy.t()+phy.v0[1]
    phy.nx=lambda t:.5*phy.ax*(t**2)+phy.v0[0]*t+phy.p0[0]
    phy.ny=lambda t:.5*phy.ay*(t**2)+phy.v0[1]*t+phy.p0[1]
    phy.x=lambda:.5*phy.ax*(phy.t()**2)+phy.v0[0]*phy.t()+phy.p0[0]
    phy.y=lambda:.5*phy.ay*(phy.t()**2)+phy.v0[1]*phy.t()+phy.p0[1]
  def refresh(phy):
    phy.g=round(phy.ng/((phy.y()+phy.r[phy.planet])**2),3)
    phy.fuel-=phy.th*phy.skip*.1
  def new(phy,θ,th):
    phy.v0=(phy.vx(),phy.vy())
    #if phy.planet!='Moon' and phy.moonPos[0]-10_000<phy.x()<phy.moonPos[0]+10_000 and phy.moonPos[1]-10_000<phy.y()<phy.moonPos[1]+10_000:
    #  sfs.phy.planet,sfs.phy.ng='Moon',4.897114e12
    phy.p0=(phy.x(),phy.y())
    phy.th=th
    phy.s=monotonic()
    phy.ax=(phy.T*th/phy.m)*cos(θ)
    phy.ay=(phy.T*th/phy.m)*sin(θ)-phy.g
class SFS():
  def __init__(sfs,m=1,T=18,fuel=500,mode='None'):
    print('Duh')
    sfs.col=[(120,160,200),(125,)*3,(10,)*3,(0,0,50)] # THEME, PRINT, BG, BG GAME
    sfs.phy=Physics(m,T,fuel)
    if mode=='To Earth':
      sfs.phy.p0=(randint(100_000,250_000),randint(2_500,15_000))
      sfs.phy.v0=(randint(-750,750),randint(-750,0))
    sfs.g=Graphics()
    sfs.fuel=fuel
    sfs.map=lambda θ:sfs.g.map(sfs.phy.t(),sfs.phy.tf(),θ,sfs.phy.nx,sfs.phy.ny,sfs.phy.planet)
    sfs.pol=lambda x,y: 2*atan(y/(x+ab(x,y)+1))-pi/2
    rect(0,0,320,15,sfs.col[0])
    txt('PRESS UP TO LAUNCH !',2,17,'white',sfs.g.col[0],1)
    sfs.play()
  def stats(sfs,θ,th):
    rect(38,205,100,10,sfs.g.col[0])
    rect(38,205,int(th*100),10,'white')
    txt(str(int(th*100))+'%',7,206,'white',sfs.g.col[0],1)
    txt('FUEL'+str(int(100*sfs.phy.fuel/sfs.fuel))+'% ALT.: '+str(int(sfs.phy.y()))+'m Vx: '+str(int(sfs.phy.vx()))+'ms Vy: '+str(int(sfs.phy.vy()))+'ms θ: '+str(int(degrees(θ)))+'deg',7,0,'white',Upsilon,1)
#    txt(str(sfs.phy.g),7,15,'white',Upsilon,1)
  def refresh(sfs,θ,th):
    sfs.phy.refresh()
    if not sfs.nav:
      a=sfs.pol(sfs.phy.vy(),sfs.phy.vx())
      line(161+int(75*cos(a)),111+int(75*sin(a)),161+int(79*cos(a)),111+int(79*sin(a)),'white')
    sfs.stats(θ,th)
  def play(sfs):
    θ,th,sfs.nav=pi/2,1,False
    while not key(1):sleep(.1)
    sfs.phy.start()
    sfs.phy.new(θ,th)
    ti=int(monotonic())
    while 1:
      if key(4):
        sfs.nav=not sfs.nav
        if not sfs.nav:sfs.g.draw(θ)
        sfs.refresh(θ,th)
      for k in [0,3]:
        if key(k):
          θ=(θ+[5*deg,-5*deg][k!=0])%(2*pi)      
          sfs.phy.new(θ,th)
          if sfs.nav:sfs.map(θ)
          else:sfs.g.draw(θ)
          sfs.refresh(θ,th)
      for k in [33,34]:
        if key(k):
          iVal=((sfs.phy.x(),sfs.phy.y()),(sfs.phy.vx(),sfs.phy.vy()))
          sfs.phy.skip=max(1,sfs.phy.skip+[-5,5][k-33])
          txt('TIME:'+str(sfs.phy.skip)+'x',7,0,(0,)*3,Upsilon,1)
          sleep(1)
          sfs.phy.new(θ,th)
          sfs.phy.p0,sfs.phy.v0=iVal[0],iVal[1]
      for k in [1,2]:
        if key(k):
          th=min(1,max(0,th+[.05,-.05][k-1]))
          sfs.phy.new(θ,th)
          if not sfs.nav:sfs.g.newFlames(th);sfs.g.draw(θ)
      if sfs.nav:
        for k in [45,46]:
          if key(k):
            sfs.g.size=max(.25,sfs.g.size+[-.25,.25][k-45])
        sfs.map(θ)
      else:
        sfs.g.bgCol(sfs.phy.y())
        if sfs.phy.y()<75:sfs.g.draw(θ);rect(0,int(sfs.phy.y())+166,320,111,ground)
      if sfs.phy.y()<0:
        if ab(sfs.phy.vx(),sfs.phy.vy())<25:
          sfs.stats(θ,th)
          sfs.phy=Physics(sfs.phy.m,sfs.phy.T,sfs.phy.fuel)
          txt('Landed on Earth !',7,25,'white',sfs.g.col[0],1)
          sfs.play()
        else:break
      elif sfs.phy.fuel<=0:sfs.phy.T=sfs.phy.th=0;sfs.phy.new(pi/2,0)#txt('!!! OUT OF FUEL !!!',7,15,'red',sfs.g.col[0],)
      sfs.refresh(θ,th)
      sleep(0.1)
    txt('U CRASHED :(',130,25,'red',sfs.g.col[0])
    txt('FLIGHT TIME: '+str(int(monotonic()-ti))+'s',130,50,'white',sfs.g.col[0],1)
    print('   ---   FINAL STATS ---\n','Vx',sfs.phy.vx(),'  Vy',sfs.phy.vy())
              
SFS(1,23,750)

During your visit to our site, NumWorks needs to install "cookies" or use other technologies to collect data about you in order to:

With the exception of Cookies essential to the operation of the site, NumWorks leaves you the choice: you can accept Cookies for audience measurement by clicking on the "Accept and continue" button, or refuse these Cookies by clicking on the "Continue without accepting" button or by continuing your browsing. You can update your choice at any time by clicking on the link "Manage my cookies" at the bottom of the page. For more information, please consult our cookies policy.