@name Voar.io
@inputs CS:wirelink
@persist [Planet Moon]:entity [Astrd Ships Models CSM]:array Astrd_Cnt Spn_Astrd G Joined CanJoin
@persist [Msg_1 Msg_2 Msg_3 Msg_4 Msg_5]:array Leader:entity ColorBuf:array
interval(100)
 
if(first()){    
    runOnChat(1)
   
    function number array:findPlyIndex(E:entity){
        if(!E:isValid()){
            return 0
        }
       
        local Index = 0
       
        foreach(I, Ship:entity = This){
            if(E == Ship["ply", entity]){
                Index = I
                break
            }
        }
       
        return Index
    }
    
    function void array:addToBuf(S:string, Clr:vector)
    {
        This:unshiftString(S)
        ColorBuf:unshiftVector(Clr)
        
        This:remove(18)
        ColorBuf:remove(18)
    }

    function void wirelink:drawStuff(Buf:array)
    {
        This:writeString("                             ", 0, 0) # clear line
        This:writeString("Leader: " + Leader:name() + " with " + Leader["max_score", number] + " pts", 0, 0)
        This:writeString("                             ", 0, 1, 0, 999) # white line
        
        for(I = 0, 15)
        {
            #clear, then write
            This:writeString("                              ", 0, 17 - I) # i think this is 30 lmao
            This:writeString(Buf[I + 1, string], 0, 17 - I, ColorBuf[I + 1, vector]) #write at the bottom lmao
        }
    }


    

 
    G = 20000
   
    CanJoin = 0
   
    Models = array("models/props_debris/concrete_chunk01a.mdl", "models/props_debris/concrete_chunk01b.mdl", "models/props_debris/concrete_chunk01c.mdl", "models/props_debris/concrete_chunk02b.mdl")
   
    Msg_1 = array("'s pathetic.", " is terrible at this.", ", kys lmao", ", u suck lol", " fucking failed.", "<- what a loser lol", " should consider suicide.", " already died.", ", learn how to fly.",
    " no pode voar.", " never had a chance.", "'s pathetic attempt to fly utterly failed.", " will never amount to anything.", " can't even reach orbit.", " is a failure.", " thought that they were a missile instead of a pilot.")
    Msg_2 = array(" has gone to meet his maker.", " decided to end it all.", " didn't fly so good.", " done it this time.", " committed suicide!", " ceased to exist!", " = North Korean Space Program",
    " is teaching angels to orbit...", " failed miserably...", " just crashed!", " died!", " fuckinf died lmoa", " went rip", " ended their miserable life.",
    " did a die", " is a terrible pilot.", " was put to sleep.", " ended their misery.", " exploded.", " was destroyed.", " flew to their death.", " forgot how to fly.", " was obliterated.",
    " was scattered across the cosmos.", " was wiped out.", " was erased from existance.", " was deleted from the universe.")
    Msg_3 = array(" needed to die anyway.", " finally died.", " was finally stopped.", " was finally destroyed.", "'s venture through space was finally put to an end.", " died a hero.",
    ", this is Ground Control to Major Tom. You've really made the grade.")
    Msg_4 = array(" dreamed of the moon.", " crashed into the moon.", " was obliterated by the moon.", " got mooned.", " left a small crater on the moon.", " flew to the moon.")
    Msg_5 = array(" makes a better ICBM than a pilot.", " is North Korea's attempt to launch a missile: a failure.", " just crashed into the earth.", " made a splash", " went splat.",
    " left a small crater on earth.")
   
    Planet = propSpawn("models/hunter/misc/sphere375x375.mdl", entity():pos() + vec(0, 0, 2), 1)
  
    #entity():setAlpha(0)
   
    holoCreate(-1, Planet:pos(), vec(13.8, 13.8, 0), ang(0), vec(0, 80, 255))
    holoModel(-1, "hq_sphere")
    holoDisableShading(-1, 1)
   
    holoCreate(-2, Planet:pos() + vec(0, 0, 2), vec(12, 12, -4), ang(0), vec(255, 0, 0))
    holoModel(-2, "models/hunter/tubes/circle4x4.mdl")
    holoMaterial(-2, "models/debug/debugwhite")
    holoDisableShading(-2, 1)
   
    holoCreate(-3, entity():pos(), vec(6, 6, 1), ang(0), vec(192))
    holoModel(-3, "models/hunter/plates/plate8x8.mdl")
    holoMaterial(-3, "models/debug/debugwhite")
    holoDisableShading(-3, 1)
   
    
 
   
    Astrd_Cnt = 30
   
    timer("afterspawn", 100)
    timer("antispam", 2000)
    timer("create_moon", 1000)
}
if(clk("afterspawn")){
    entity():setPos(Planet:pos() + vec(0, 0, 100))
}
if(clk("create_moon")){
    Moon = propSpawn("models/sprops/geometry/sphere_96.mdl", 1)
   
    local Apogee = vec(1500, 0, 0)
    Moon["pos", vector] = Planet:pos() + Apogee
   
    local PerpAng = atan(Apogee:y(), Apogee:x()) + 90
    local PerpVec = vec(cos(PerpAng), sin(PerpAng), 0)
   
    Moon["vel", vector] = PerpVec * sqrt((G * 0.4) / Moon["pos", vector]:distance(Planet:pos()))
   
    Planet:setAlpha(0)
    Moon:setAlpha(0)
    
    #moon holo
    holoCreate(-4, Moon:pos(), vec(7.5, 7.5, 0), ang(0), vec(255))
    holoModel(-4, "hq_sphere")
    holoDisableShading(-4, 1)
    holoParent(-4, Moon)
    holoMaterial(-4, "models/pi_window/plaster")
}
holoAng(-4, holoEntity(-4):toWorld(ang(0, 5, 0)))
 
if(clk("antispam") & propCanCreate() & Spn_Astrd < Astrd_Cnt){
    Spn = propSpawn("models/sprops/geometry/sphere_42.mdl", 1)
    Spn:setAlpha(0)
   
    Astrd:pushEntity(Spn)
 
    local Offset = randvec():setZ(0):normalized() * randint(150, 1130)
    local PerpAng = atan(Offset:y(), Offset:x()) + 90
    local PerpVec = vec(cos(PerpAng), sin(PerpAng), 0)
 
       
    Spn["pos", vector] = Planet:pos() + Offset
    Spn["vel", vector] = PerpVec * sqrt((G + randint(-5000, 1)) / Spn["pos", vector]:distance(Planet:pos()))
   
    holoCreate(Spn_Astrd, Spn:pos(), vec(0.5, 0.5, 0.08), ang(0, randint(0, 360), 0), vec(150, 150, 150))
    holoModel(Spn_Astrd, Models[randint(1, Models:count()), string])
    holoMaterial(Spn_Astrd, "models/pi_window/plaster")
    holoDisableShading(Spn_Astrd, 1)
    holoParent(Spn_Astrd, Spn)
   
    Spn_Astrd++
    
    timer("antispam", 300)
}
if(Spn_Astrd == Astrd_Cnt){
    CanJoin = 1
}
 
 
for(K = 1, Astrd:count()){
    local A = Astrd[K, entity]
    A["accel", vector] = (Planet:pos() - A["pos", vector]):normalized() * (G / A["pos", vector]:distance(Planet:pos())^2)
    A["vel", vector] = A["vel", vector] + A["accel", vector]
    A["pos", vector] = A["pos", vector] + A["vel", vector]
   
    A:setPos(A["pos", vector])
}
 
Moon["accel", vector] = (Planet:pos() - Moon["pos", vector]):normalized() * (G / Moon["pos", vector]:distance(Planet:pos())^2)
Moon["vel", vector] = Moon["vel", vector] + Moon["accel", vector]
Moon["pos", vector] = Moon["pos", vector] + Moon["vel", vector]
   
Moon:setPos(Moon["pos", vector])
   
#Players
 if(chatClk()){
    if(lastSaid() == "!play" & CanJoin){
        local Valid = 1        
        foreach(I, Ship:entity = Ships){
            local Ply = Ship["ply", entity]
            if(Ply == lastSpoke()){
                Valid = 0
                break
            }
        }
       
        if(Valid){
           
            SpnPly = propSpawn("models/sprops/geometry/sphere_30.mdl", Planet:pos() + vec(0, 100, 0), 1)
            SpnPly:setAlpha(0)
           
            Ships:pushEntity(SpnPly)    
       
            local Offset = randvec():setZ(0):normalized() * 90
            local PerpAng = atan(Offset:y(), Offset:x()) + 60
            local PerpVec = vec(cos(PerpAng), sin(PerpAng), 0)
           
            SpnPly["ply", entity] = lastSpoke()
               
            SpnPly["pos", vector] = Planet:pos() + Offset
            SpnPly["vel", vector] = PerpVec * 17.5
            SpnPly["color", vector] = hsv2rgb(randint(0, 255), 1, 1)#randvec(0, 255):normalized() * 255
            SpnPly["lock", number] = 1
           
            SpnPly["holo", entity] = holoCreate(SpnPly["ply", entity]:id() + Astrd_Cnt, SpnPly:pos(), vec(0.2, 0.2, 0), ang(0), SpnPly["color", vector])
            holoModel(holoIndex(SpnPly["holo", entity]), "models/props_combine/headcrabcannister01a.mdl")
            holoDisableShading(holoIndex(SpnPly["holo", entity]), 1)
            holoMaterial(holoIndex(SpnPly["holo", entity]), "models/debug/debugwhite")
            holoParent(holoIndex(SpnPly["holo", entity]), SpnPly)
                           
           
            concmd("say [Voar] " + lastSpoke():name() + " has entered the game. COLOR: " + round(SpnPly["color", vector]))
        }
    }elseif(lastSaid() == "!play" & !CanJoin){
        concmd("say [Voar] Please wait to join...")
    }
   
    if(lastSaid() == "!quit"){
        foreach(K, Ship:entity = Ships){
            local P = lastSpoke()#Ship["ply", entity]
            local Ind = Ships:findPlyIndex(P)
           
            holoDelete(holoIndex(Ships[Ind, entity]["holo", entity]))
            Ships[Ind, entity]:propBreak()
            Ships:remove(Ind)
           
            concmd("say [Voar] " + lastSpoke():name() + " has left the game.")
           
            #fix holos
            foreach(K, Ship:entity = Ships){
                local H = Ship["holo", entity]
               
                holoPos(holoIndex(H), Ship:pos())
                holoParent(holoIndex(H), Ship)
            }
            #fix holos#
               
        }
    }
}
#Players
 
foreach(K, Ship:entity = Ships){
   
    local P = Ship["ply", entity]
   
    if(Ship["lock", number] == 0){
        Ship:propNotSolid(0)
       
        Ship["accel", vector] = (Planet:pos() - Ship["pos", vector]):normalized() * (G / Ship["pos", vector]:distance(Planet:pos())^2) + (Moon:pos() - Ship["pos", vector]):normalized() * (G * 0.54 / Ship["pos", vector]:distance(Moon:pos())^2)
        Ship["vel", vector] = Ship["vel", vector] + Ship["accel", vector]
        Ship["pos", vector] = Ship["pos", vector] + Ship["vel", vector]
       
        Ship["score", number] = Ship["score", number] + Ship["vel", vector]:length()
    } else {
        Ship:propNotSolid(1)
    }
   
    Ship:setPos(Ship["pos", vector])
   
    holoAng(holoIndex(Ship["holo", entity]), Ship["vel", vector]:toAngle())
   
 
    if(P:keyAttack2()){
        Ship["vel", vector] = Ship["vel", vector] + Ship["vel", vector]:normalized() * 0.4
       
        if(Ship["lock", number] == 1){
            Ship["lock", number] = 0
            Ship:setTrails(25, 25, 20, "trails/laser", Ship["color", vector], 255)
        }
    }
   
    rangerFilter(Ship)
    if(Ship["lock", number] == 0){
        Hit = rangerOffset(1, Ship:pos(), vec(1))
    }
   
    if(Hit:hit() | Ship["pos", vector]:distance(Planet:pos()) > 1135){
        Boom = propSpawn("models/props_phx/misc/potato_launcher_explosive.mdl", Ship:pos(), 1)
        Boom:propBreak()
       
        local Offset = randvec():setZ(0):normalized() * 90
        local PerpAng = atan(Offset:y(), Offset:x()) + 60
        local PerpVec = vec(cos(PerpAng), sin(PerpAng), 0)
           
        Ship["pos", vector] = Planet:pos() + Offset
        Ship["vel", vector] = PerpVec * 17.5
        Ship["lock", number] = 1
        Ship:removeTrails()
   
        local Score = round(Ship["score", number] / 100)
       
       
        if(Hit:entity() == Moon){
            concmd("say [Voar] " + P:name() + Msg_4[randint(1, Msg_4:count()), string] + " (" + Score + " points)")
        }elseif(round(Ship["score", number] / 100) > 40){
            concmd("say [Voar] " + P:name() + Msg_3[randint(1, Msg_3:count()), string] + " (" + Score + " points)")
        }elseif(Hit:entity() == Planet){
            concmd("say [Voar] " + P:name() + Msg_5[randint(1, Msg_5:count()), string] + " (" + Score + " points)")
        }elseif(round(Ship["score", number] / 100) < 10){
            concmd("say [Voar] " + P:name() + Msg_1[randint(1, Msg_1:count()), string] + " (" + Score + " points)")
        }elseif(round(Ship["score", number] / 100) > 10){
            concmd("say [Voar] " + P:name() + Msg_2[randint(1, Msg_2:count()), string] + " (" + Score + " points)")
        }
       
        if(round(Ship["score", number] / 100) > round(Ship["max_score", number] / 100)){
            Ship["max_score", number] = round(Ship["score", number] / 100)
        }
        if(Ship["max_score", number] > Leader["max_score", number]){
            Leader = P
            Leader["max_score", number] = Ship["max_score", number]
        }
       
        CSM:addToBuf(P:name() + ": " + Score + " pts.", Ship["color", vector])
        CS:drawStuff(CSM)
        
        Ship["score", number] = 0
    }
    
    #remove disconnected players
    if(!P:isValid()){
        holoDelete(holoIndex(Ship["holo", entity]))
        Ship:propBreak()
        Ships:remove(Ships:findPlyIndex(P))
           
        #fix holos
        local H = Ship["holo", entity]               
        holoPos(holoIndex(H), Ship:pos())
        holoParent(holoIndex(H), Ship)
            
        #fix holos#   
    }
}