Scripting ideas

223 posts Page 4 of 15 First unread post
XxXAtlanXxX
Deuced Up
Posts: 557
Joined: Sun Dec 16, 2012 12:26 am


Blue_Cookie Green_Cookie
:O Izzi u racist
thepolm3
Scripter
Scripter
Posts: 424
Joined: Sat Feb 16, 2013 10:49 pm


lol I never thought THAT would happen :)
thepolm3
Scripter
Scripter
Posts: 424
Joined: Sat Feb 16, 2013 10:49 pm


danhezee wrote:
Tested it out, and it works but I have one more feature request.

Make it so before the timer starts it is impossible to pick up the intel.
Code: Select all
"""
Match script, useful for public matches. Features verbose announcements
on IRC and a custom timer.

Maintainer: mat^2

edited by thepolm3
"""
from commands import add, admin, name, get_team
from twisted.internet import reactor
from twisted.internet.task import LoopingCall

import json
import commands

COMMAND_POS=None

@admin
@name('timer')
def start_timer(connection, end):
    return connection.protocol.start_timer(int(end)*60)

@admin
@name('stoptimer')
def stop_timer(connection):
    return connection.protocol.stop_timer()

@admin
@name('startrecord')
def start_record(connection):
    connection.protocol.start_record()
    return 'Recording started.'

@admin
@name('stoprecord')
def stop_record(connection):
    connection.protocol.stop_record()
    return 'Recording stopped.'

@admin
@name('saverecord')
def save_record(connection, value):
    if not connection.protocol.save_record(value):
        return 'No record file available.'
    return 'Record saved.'

add(start_timer)
add(stop_timer)
add(start_record)
add(stop_record)
add(save_record)

def apply_script(protocol, connection, config):
    class MatchConnection(connection):
        def on_flag_take(self):
            if not self.protocol.timer_end:
                return False
            self.add_message("%s took %s's flag!" %
                (self.printable_name, self.team.other.name.lower()))
            return connection.on_flag_take(self)
        
        def on_flag_drop(self):
            self.add_message("%s dropped %s's flag!" %
                (self.printable_name, self.team.other.name.lower()))
            return connection.on_flag_drop(self)
                
        def on_flag_capture(self):
            self.add_message("%s captured %s's flag!" %
                (self.printable_name, self.team.other.name.lower()))
            return connection.on_flag_capture(self)

        def on_line_build_attempt(self, points):
            if self.protocol.timer_end:
                return connection.on_line_build_attempt(self,points)
            return False

        def on_block_build_attempt(self, x, y, z):
            if self.protocol.timer_end:
                return connection.on_block_build_attempt(self,x,y,z)
            return False

        def on_block_destroy(self, x, y, z,value):
            if self.protocol.timer_end:
                return connection.on_block_destroy(self,x,y,z,value)
            return False

        def on_kill(self, killer, type, grenade):
            if not self.protocol.timer_end:
                if killer==self or killer==None:
                    return connection.on_kill(self,killer,type,grenade)
                return False
            if killer is None:
                killer = self
            self.add_message("%s was killed by %s!" %
                (self.printable_name, killer.printable_name))
            self.protocol.add_kill(self, killer)
            return connection.on_kill(self, killer, type, grenade)
        
        def add_message(self, value):
            self.protocol.messages.append(value)
    
    class MatchProtocol(protocol):
        timer_left = None
        timer_call = None
        timer_end = None
        record = None
        blue_command=(0,0,0)
        green_command=(0,0,0)
        def __init__(self, *arg, **kw):
            protocol.__init__(self, *arg, **kw)
            self.messages = []
            self.send_message_loop = LoopingCall(self.display_messages)
            self.send_message_loop.start(3)
            
        def start_timer(self, end):
            if self.timer_end is not None:
                return 'Timer is running already.'
            self.timer_end = reactor.seconds() + end
            if end/60==1:
                unit="minute"
                end/=60
            elif end/60>1:
                unit="minutes"
                end/=60
            else:
                unit="seconds"
            self.send_chat('Timer started, ending in %d %s' % (end,unit),
                irc = True)
            self.display_timer(True)
            for name in self.players:
                player=self.players[name]
                if player.world_object:
                    if player.team==get_team(player,"blue"):
                        player.spawn(self.blue_command)
                    else:
                        player.spawn(self.green_command)
        
        def stop_timer(self):
            if self.timer_call is not None:
                self.timer_call.cancel()
                self.send_chat('Timer stopped.')
                self.timer_call = None
                self.timer_end = None
            else:
                return 'No timer in progress.'
        
        def display_timer(self, silent = False):
            time_left = self.timer_end - reactor.seconds()
            minutes_left = time_left / 60.0
            next_call = 60
            if not silent:
                if time_left <= 0:
                    self.send_chat('Timer ended!', irc = True)
                    self.timer_end = None
                    return
                elif minutes_left <= 1:
                    self.send_chat('%s seconds left' % int(time_left), 
                        irc = True)
                    next_call = max(1, int(time_left / 2.0))
                else:
                    self.send_chat('%s minutes left' % int(minutes_left), 
                        irc = True)
            self.timer_call = reactor.callLater(next_call, self.display_timer)
        
        def display_messages(self):
            if not self.messages:
                return
            message = self.messages.pop(0)
            self.irc_say(message)
        
        # recording
        
        def add_kill(self, player, killing_player):
            if self.record is None:
                return
            self.get_record(player.name)['deaths'] += 1
            self.get_record(killing_player.name)['kills'] += 1
        
        def get_record(self, name):
            try:
                return self.record[name]
            except KeyError:
                record = {'deaths' : 0, 'kills' : 0}
                self.record[name] = record
                return record
        
        def start_record(self):
            self.record = {}
        
        def stop_record(self):
            self.record = None
        
        def save_record(self, value):
            if self.record is None:
                return False
            json.dump(self.record, open(value, 'wb'))
            return True

        def on_base_spawn(self, x, y, z, base, entity_id):
            if entity_id==2:
                self.blue_command=(x,y,z)
            else:
                self.green_command=(x,y,z)
            return protocol.on_base_spawn(self,x,y,z,base,entity_id)

    return MatchProtocol, MatchConnection
Venator
League Participant
League Participant
Posts: 1225
Joined: Wed Nov 07, 2012 8:32 pm


Could you try to rip the Rush gamemode from BF ?
XxXAtlanXxX
Deuced Up
Posts: 557
Joined: Sun Dec 16, 2012 12:26 am


Yes yes Vena, I asked.. I asked...
thepolm3
Scripter
Scripter
Posts: 424
Joined: Sat Feb 16, 2013 10:49 pm


Venator wrote:
Could you try to rip the Rush gamemode from BF ?
Funny, I'm in the middle of that atm :)
Venator
League Participant
League Participant
Posts: 1225
Joined: Wed Nov 07, 2012 8:32 pm


yaaaay :D
thepolm3
Scripter
Scripter
Posts: 424
Joined: Sat Feb 16, 2013 10:49 pm


Sorry, I haven't worked with tc before. I need to start again. Might take a while :)
XxXAtlanXxX
Deuced Up
Posts: 557
Joined: Sun Dec 16, 2012 12:26 am


Ok :)






















Do it fast or i will sacrifice ur family to mighty god kukelekuu
danhezee
Former Admin / Co-founder
Former Admin / Co-founder
Posts: 1710
Joined: Wed Oct 03, 2012 12:09 am


thepolm3 this thread might be a good starting point for understanding tc
http://www.buildandshoot.com/viewtopic.php?f=5&t=1599
KomradeKorakoff
League Champs
League Champs
Posts: 179
Joined: Sat Nov 03, 2012 5:24 pm


There was once a script with landmines, where a person was able to place 10 red blocks to serve as landmines and shoot them to explode (creation of 5 nades). https://code.google.com/r/plasmicorigin ... 33fc76231b
Perhaps you could check that out.
TB_
Post Demon
Post Demon
Posts: 998
Joined: Tue Nov 20, 2012 6:59 pm


Wow, I didn't know that existed. Thanks korakoff
thepolm3
Scripter
Scripter
Posts: 424
Joined: Sat Feb 16, 2013 10:49 pm


You guys are so great ^^
danhezee
Former Admin / Co-founder
Former Admin / Co-founder
Posts: 1710
Joined: Wed Oct 03, 2012 12:09 am


thepolm3 wrote:
I'm not entirely sure if this works, as I've only been able to test it on my own.
here you go; Tournament.py!
Code: Select all

"""
Tournament mode by thepolm3
Idea by TB_
""" 
from commands import add, admin, get_player, join_arguments, name, alias, get_team
from pyspades.constants import *
from random import randint
from twisted.internet.reactor import callLater

HIDE_COORD = (0, 0, 63)
HIDE_COORD2 = (511, 511, 63)
BUILDING_ENABLED = False
MAX_SPAWN_DISTANCE=5
def apply_script(protocol,connection,config):
    class TournamentConnection(connection):
        tournament_id=None
        myroundended=False
        opponant=None
        
        def on_spawn_location(self, pos):
            if self.protocol.tournament_enabled:
                prot=self.protocol
                if self.tournament_id%2==1:
                    callLater(1,self.match)
                else:
                    self.send_chat("Please wait until an opponant arrives")
                if self.myroundended and prot.round_active:
                    self.opponant=prot.tournament_players[self.tournament_id-1]
                    self.opponant.opponant=self
                    self.send_chat("You have been matched against %s Fight to the death!" %(self.opponant.name))
                    self.opponant.send_chat("You have been matched against %s Fight to the death!" %(self.name))
                    return HIDE_COORD2
                else:
                    if not prot.round_active:
                        self.myroundended=False
                    x,y,z = prot.spawns[self.tournament_id]
                    return(x,y,z)
            return connection.on_spawnlocation(self,pos)
                
                    
        def on_kill(self, killer, type, grenade):
            if self.protocol.tournament_enabled:
                if killer!=None and killer!=self:
                    if self.opponant==killer and self.protocol.round_active and not self.myroundended:
                        killer.send_chat("You won this round!")
                        self.myroundended=True
                        killer.myroundended=True
                        self.send_chat("Sorry, you died. wait until the end of the round to play again")
                        killer.kill()
                        self.protocol.check_end()
                        self.switch_team()
                        a=callLater(0.01,self.switch_team)
                        return connection.on_kill(self,killer,type,grenade)
                    else:
                        if killer.opponant==None:
                            killer.send_chat("Wait for your opponant to arrive!")
                        elif not self.protocol.round_active:
                            killer.send_chat("not yet!")
                        else:
                            killer.send_chat("Shoot %s, not %s!" %(killer.opponant.name,self.name))
                        return False
            return connection.on_kill(self,killer,type,grenade)

        def switch_team(self):
            self.set_team(self.team.other)
            self.spawn()

        def on_position_update(self):
            prot=self.protocol
            if prot.tournament_enabled:
                if self.opponant==None or not prot.round_active:
                    pos = self.world_object.position
                    x,y,z=prot.spawns[self.tournament_id]
                    xd = x - pos.x
                    yd = y - pos.y
                    zd = z - pos.z
                    if (xd ** 2 + yd ** 2 + zd ** 2)**0.5 > MAX_SPAWN_DISTANCE:
                        self.set_location(prot.spawns[self.tournament_id])
                    if self.opponant==None:
                        self.send_chat("Wait for your opponant to arrive!")
            return connection.on_position_update(self)

        def on_connect(self):
            prot=self.protocol
            if prot.tournament_enabled:
                get_team(self, "green").locked = True
                self.tournament_id = len(prot.tournament_players)
                prot.tournament_players.append(self)
            return connection.on_connect(self)

        def on_disconnect(self):
            prot=self.protocol
            if prot.tournament_enabled:
                self.myroundended=False
                del(prot.tournament_players[self.tournament_id])
                self.tournament_id=None
                if self.opponant:
                    self.opponant.send_chat("%s has disconnected and forfeight. Prove yourself next game!"%(self.name))
                self.opponant.opponant=None
                self.opponant=None
            return connection.on_disconnect(self)

    class TournamentProtocol(protocol):
        game_mode=CTF_MODE
        tournament_enabled = False
        spawns=[]
        olds=[]
        tournament_players=[]
        round_active=False
        gamesfinished=0

        def on_map_change(self, map):
            extensions = self.map_info.extensions
            if config.get("game_mode","ctf")=="tournament" or extensions.has_key('tournament'):
                self.tournament_enabled = True
                self.olds = [self.respawn_time,self.building,self.friendly_fire,self.max_players]
                self.respawn_time = 0
                self.building = BUILDING_ENABLED
                self.friendly_fire = True
                if extensions.has_key('tournament'):
                    try:
                        for i in extensions["tournament"]: #setting spawns
                            self.spawns.append(i)
                        self.max_players=len(self.spawns)
                    except Exception:
                        raise "Tournament defined incorrectly in map meta data, use format tournament:[(spawn1),(spawn2),(spawn3)] etc"
                else:
                    raise Exception("No extentions")
                self.send_chat("The round will begin in 10 seconds")
                a=callLater(10,self.begin_round)
            else:
                # Cleanup after a map change
                self.tournament_enabled=False
                if self.olds:
                    self.respawn_time,self.building,self.friendly_fire,self.max_players=self.olds
                self.olds=[]
            return protocol.on_map_change(self,map)

        def check_end(self):
            self.gamesfinished+=1
            if self.gamesfinished>=int(len(self.tournament_players)/2):
                self.end_round()
                self.send_chat("Round finished")
                
        def end_round(self):
            self.gamesfinished=0
            tournament_players=self.tournament_players
            length = len(tournament_players) - 1
            sorted = False
            while not sorted:
                sorted = True
                for i in range(length):
                    if tournament_players[i].kills > tournament_players[i+1].kills:
                        sorted = False
                        tournament_players[i], tournament_players[i+1] = tournament_players[i+1], tournament_players[i]
            for player in tournament_players:
                player.tournament_id=tournament_players.index(player)
                player.kill()
                player.myroundended=False
                player.opponant=None
            self.send_chat("The round will begin in 5 seconds")
            self.round_active=False
            a=callLater(10,self.begin_round)

        def begin_round(self):
            if len(self.tournament_players)>1:
                self.round_active=True
                self.send_chat("Begin killing!")
            else:
                self.send_chat("Not enough players. The round will begin in 10 seconds")
                a=callLater(10,self.begin_round)

        def on_flag_spawn(self, x, y, z, flag, entity_id):
            if not self.tournament_enabled:
                return protocol.on_base_spawn(self, x, y, z, flag, entity_id)
            return HIDE_COORD

        def on_base_spawn(self, x, y, z, base, entity_id):
            if not self.tournament_enabled:
                return protocol.on_base_spawn(self, x, y, z, base, entity_id)
            return HIDE_COORD
        
    return TournamentProtocol, TournamentConnection


to create a map for it, make sure you have the extension "tournament" and set it to a list of spawns. Thats all!
Umm, I would like to test this out but I am not sure how list the spawns in the map extension. Can you give me an example / template to follow?
thepolm3
Scripter
Scripter
Posts: 424
Joined: Sat Feb 16, 2013 10:49 pm


I tried to keep it a simple as possible: just do this in the extensions tournament:[(x,y,z),(x,y,z),(x,y,z)]
This is the script I am Least confident with, so there will almost certainly be bugs
223 posts Page 4 of 15 First unread post
Return to “Ideas / Requests”

Who is online

Users browsing this forum: No registered users and 5 guests