Split time lord (#320)

Split time lord into src/roles/timelord.py
This commit is contained in:
Ammon Smith 2018-04-25 16:44:24 -07:00 committed by Em Barry
parent b86e52de25
commit 6d0d6f7169
3 changed files with 78 additions and 59 deletions

71
src/roles/timelord.py Normal file
View File

@ -0,0 +1,71 @@
import re
import random
import itertools
import math
import time
from collections import defaultdict
import botconfig
from src.utilities import *
from src import channels, users, debuglog, errlog, plog
from src.functions import get_players, get_all_players, get_main_role, get_reveal_role, get_target
from src.decorators import command, event_listener
from src.containers import UserList, UserSet, UserDict, DefaultUserDict
from src.messages import messages
from src.events import Event
TIME_ATTRIBUTES = (
("DAY_TIME_LIMIT", "TIME_LORD_DAY_LIMIT"),
("DAY_TIME_WARN", "TIME_LORD_DAY_WARN"),
("SHORT_DAY_LIMIT", "TIME_LORD_DAY_LIMIT"),
("SHORT_DAY_WARN", "TIME_LORD_DAY_WARN"),
("NIGHT_TIME_LIMIT", "TIME_LORD_NIGHT_LIMIT"),
("NIGHT_TIME_WARN", "TIME_LORD_NIGHT_WARN"),
)
@event_listener("del_player")
def on_del_player(evt, var, user, mainrole, allroles, death_triggers):
if not death_triggers or "time lord" not in allroles:
return
for attr, new_attr in TIME_ATTRIBUTES:
if attr not in var.ORIGINAL_SETTINGS:
var.ORIGINAL_SETTINGS[attr] = getattr(var, attr)
setattr(var, attr, getattr(var, new_attr))
channels.Main.send(messages["time_lord_dead"].format(var.TIME_LORD_DAY_LIMIT, var.TIME_LORD_NIGHT_LIMIT))
if var.GAMEPHASE == "day":
time_limit = var.DAY_TIME_LIMIT
time_warn = var.DAY_TIME_WARN
phase_id = "DAY_ID"
timer_name = "day_warn"
elif var.GAMEPHASE == "night":
time_limit = var.NIGHT_TIME_LIMIT
time_warn = var.NIGHT_TIME_WARN
phase_id = "NIGHT_ID"
timer_name = "night_warn"
if var.GAMEPHASE in var.TIMERS:
time_left = int((var.TIMERS[var.GAMEPHASE][1] + var.TIMERS[var.GAMEPHASE][2]) - time.time())
if time_left > time_limit > 0:
t = threading.Timer(time_limit, hurry_up, [phase_id, True])
var.TIMERS[var.GAMEPHASE] = (t, time.time(), time_limit)
t.daemon = True
t.start()
# Don't duplicate warnings, i.e. only set the warning timer if a warning was not already given
if timer_name in var.TIMERS:
timer = var.TIMERS[timer_name][0]
if timer.isAlive():
timer.cancel()
t = threading.Timer(time_warn, hurry_up, [phase_id, False])
var.TIMERS[timer_name] = (t, time.time(), time_warn)
t.daemon = True
t.start()
debuglog("{0} (time lord) TRIGGER".format(user))
# vim: set sw=4 expandtab:

View File

@ -355,7 +355,7 @@ def complete_match(string, matches):
return sorted(possible_matches)
def complete_one_match(string, matches):
matches = complete_match(string,matches)
matches = complete_match(string,matches)
if len(matches) == 1:
return matches.pop()
return None

View File

@ -2472,56 +2472,6 @@ def del_player(player, *, devoice=True, end_game=True, death_triggers=True, kill
debuglog("{0} ({1}) LOVE SUICIDE: {2} ({3})".format(lover, get_main_role(lover), player, mainrole))
del_player(lover, end_game=False, killer_role=killer_role, deadlist=deadlist, original=original, ismain=False)
pl = refresh_pl(pl)
if mainrole == "time lord":
if "DAY_TIME_LIMIT" not in var.ORIGINAL_SETTINGS:
var.ORIGINAL_SETTINGS["DAY_TIME_LIMIT"] = var.DAY_TIME_LIMIT
if "DAY_TIME_WARN" not in var.ORIGINAL_SETTINGS:
var.ORIGINAL_SETTINGS["DAY_TIME_WARN"] = var.DAY_TIME_WARN
if "SHORT_DAY_LIMIT" not in var.ORIGINAL_SETTINGS:
var.ORIGINAL_SETTINGS["SHORT_DAY_LIMIT"] = var.SHORT_DAY_LIMIT
if "SHORT_DAY_WARN" not in var.ORIGINAL_SETTINGS:
var.ORIGINAL_SETTINGS["SHORT_DAY_WARN"] = var.SHORT_DAY_WARN
if "NIGHT_TIME_LIMIT" not in var.ORIGINAL_SETTINGS:
var.ORIGINAL_SETTINGS["NIGHT_TIME_LIMIT"] = var.NIGHT_TIME_LIMIT
if "NIGHT_TIME_WARN" not in var.ORIGINAL_SETTINGS:
var.ORIGINAL_SETTINGS["NIGHT_TIME_WARN"] = var.NIGHT_TIME_WARN
var.DAY_TIME_LIMIT = var.TIME_LORD_DAY_LIMIT
var.DAY_TIME_WARN = var.TIME_LORD_DAY_WARN
var.SHORT_DAY_LIMIT = var.TIME_LORD_DAY_LIMIT
var.SHORT_DAY_WARN = var.TIME_LORD_DAY_WARN
var.NIGHT_TIME_LIMIT = var.TIME_LORD_NIGHT_LIMIT
var.NIGHT_TIME_WARN = var.TIME_LORD_NIGHT_WARN
channels.Main.send(messages["time_lord_dead"].format(var.TIME_LORD_DAY_LIMIT, var.TIME_LORD_NIGHT_LIMIT))
if var.GAMEPHASE == "day" and timeleft_internal("day") > var.DAY_TIME_LIMIT and var.DAY_TIME_LIMIT > 0:
if "day" in var.TIMERS:
var.TIMERS["day"][0].cancel()
t = threading.Timer(var.DAY_TIME_LIMIT, hurry_up, [var.DAY_ID, True])
var.TIMERS["day"] = (t, time.time(), var.DAY_TIME_LIMIT)
t.daemon = True
t.start()
# Don't duplicate warnings, i.e. only set the warn timer if a warning was not already given
if "day_warn" in var.TIMERS and var.TIMERS["day_warn"][0].isAlive():
var.TIMERS["day_warn"][0].cancel()
t = threading.Timer(var.DAY_TIME_WARN, hurry_up, [var.DAY_ID, False])
var.TIMERS["day_warn"] = (t, time.time(), var.DAY_TIME_WARN)
t.daemon = True
t.start()
elif var.GAMEPHASE == "night" and timeleft_internal("night") > var.NIGHT_TIME_LIMIT and var.NIGHT_TIME_LIMIT > 0:
if "night" in var.TIMERS:
var.TIMERS["night"][0].cancel()
t = threading.Timer(var.NIGHT_TIME_LIMIT, hurry_up, [var.NIGHT_ID, True])
var.TIMERS["night"] = (t, time.time(), var.NIGHT_TIME_LIMIT)
t.daemon = True
t.start()
# Don't duplicate warnings, e.g. only set the warn timer if a warning was not already given
if "night_warn" in var.TIMERS and var.TIMERS["night_warn"][0].isAlive():
var.TIMERS["night_warn"][0].cancel()
t = threading.Timer(var.NIGHT_TIME_WARN, hurry_up, [var.NIGHT_ID, False])
var.TIMERS["night_warn"] = (t, time.time(), var.NIGHT_TIME_WARN)
t.daemon = True
t.start()
debuglog(player.nick, "(time lord) TRIGGER")
pl = refresh_pl(pl)
# i herd u liek parameters
@ -3020,7 +2970,7 @@ def nick_change(evt, var, user, old_rawnick):
# perhaps mark them as back
return_to_village(var, user, show_message=True)
@event_listener("cleanup_user")
@event_listener("cleanup_user")
def cleanup_user(evt, var, user):
var.LAST_GOAT.pop(user, None)
@ -5960,22 +5910,20 @@ def timeleft(cli, nick, chan, rest):
reply(cli, nick, chan, msg)
if var.PHASE in var.TIMERS:
remaining = timeleft_internal(var.PHASE)
if var.PHASE == "day":
what = "sunset"
elif var.PHASE == "night":
what = "sunrise"
elif var.PHASE == "join":
what = "the game is canceled if it's not started"
remaining = int((var.TIMERS[var.PHASE][1] + var.TIMERS[var.PHASE][2]) - time.time())
msg = "There is \u0002{0[0]:0>2}:{0[1]:0>2}\u0002 remaining until {1}.".format(divmod(remaining, 60), what)
else:
msg = messages["timers_disabled"].format(var.PHASE.capitalize())
reply(cli, nick, chan, msg)
def timeleft_internal(phase):
return int((var.TIMERS[phase][1] + var.TIMERS[phase][2]) - time.time()) if phase in var.TIMERS else -1
@cmd("roles", pm=True)
def listroles(cli, nick, chan, rest):
"""Displays which roles are enabled at a certain number of players."""
@ -6216,7 +6164,7 @@ def game_stats(cli, nick, chan, rest):
if gamemode != "all" and gamemode not in var.GAME_MODES.keys():
matches = complete_match(gamemode, var.GAME_MODES.keys())
if len(matches) == 1:
gamemode = matches[0]
gamemode = matches[0]
if not matches:
cli.notice(nick, messages["invalid_mode"].format(rest[0]))
return
@ -6301,7 +6249,7 @@ def player_stats(cli, nick, chan, rest):
reply(cli, nick, chan, messages["no_such_role"].format(role))
return
if len(matches) > 1:
reply(cli, nick, chan, messages["ambiguous_role"].format(", ".join(matches)))
reply(cli, nick, chan, messages["ambiguous_role"].format(", ".join(matches)))
return
role = matches[0]
# Attempt to find the player's stats
@ -6332,7 +6280,7 @@ def vote_gamemode(var, wrapper, gamemode, doreply):
return
if len(matches) == 1:
gamemode = matches[0]
if gamemode != "roles" and gamemode != "villagergame" and gamemode not in var.DISABLED_GAMEMODES:
if var.GAMEMODE_VOTES.get(wrapper.source.nick) == gamemode:
wrapper.pm(messages["already_voted_game"].format(gamemode))