Add 'Jeopardy/' from commit '0fc85014d136671257180831029710c82b778307'
git-subtree-dir: Jeopardy git-subtree-mainline:d26ffc2e84
git-subtree-split:0fc85014d1
This commit is contained in:
commit
d75fec8cce
|
@ -0,0 +1 @@
|
|||
Insert a description of your plugin here, with any notes, etc. about using it.
|
|
@ -0,0 +1,71 @@
|
|||
###
|
||||
# Copyright (c) 2010, quantumlemur
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
#
|
||||
# * Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions, and the following disclaimer.
|
||||
# * Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions, and the following disclaimer in the
|
||||
# documentation and/or other materials provided with the distribution.
|
||||
# * Neither the name of the author of this software nor the name of
|
||||
# contributors to this software may be used to endorse or promote products
|
||||
# derived from this software without specific prior written consent.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
# POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
###
|
||||
|
||||
"""
|
||||
Add a description of the plugin (to be presented to the user inside the wizard)
|
||||
here. This should describe *what* the plugin does.
|
||||
"""
|
||||
|
||||
import supybot
|
||||
import supybot.world as world
|
||||
|
||||
# Use this for the version of this plugin. You may wish to put a CVS keyword
|
||||
# in here if you're keeping the plugin in CVS or some similar system.
|
||||
__version__ = "1.0"
|
||||
|
||||
# XXX Replace this with an appropriate author or supybot.Author instance.
|
||||
__author__ = supybot.Author('quantumlemur', 'quantumlemur',
|
||||
'quantumlemur@users.sourceforge.net')
|
||||
|
||||
# This is a dictionary mapping supybot.Author instances to lists of
|
||||
# contributions.
|
||||
if not hasattr(supybot.authors, 'progval'):
|
||||
supybot.authors.progval = supybot.Author('Valentin Lorentz', 'ProgVal',
|
||||
'progval@gmail.com')
|
||||
__contributors__ = {supybot.authors.progval: ['code enhancement']}
|
||||
|
||||
# This is a url where the most recent plugin package can be downloaded.
|
||||
__url__ = '' # 'http://supybot.com/Members/yourname/Trivia/download'
|
||||
|
||||
from . import config
|
||||
from . import plugin
|
||||
from imp import reload
|
||||
reload(plugin) # In case we're being reloaded.
|
||||
# Add more reloads here if you add third-party modules and want them to be
|
||||
# reloaded when this plugin is reloaded. Don't forget to import them as well!
|
||||
|
||||
if world.testing:
|
||||
from . import test
|
||||
|
||||
Class = plugin.Class
|
||||
configure = config.configure
|
||||
|
||||
|
||||
# vim:set shiftwidth=4 tabstop=4 expandtab textwidth=79:
|
|
@ -0,0 +1,98 @@
|
|||
###
|
||||
# Copyright (c) 2010, quantumlemur
|
||||
# Copyright (c) 2011, Valentin Lorentz
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
#
|
||||
# * Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions, and the following disclaimer.
|
||||
# * Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions, and the following disclaimer in the
|
||||
# documentation and/or other materials provided with the distribution.
|
||||
# * Neither the name of the author of this software nor the name of
|
||||
# contributors to this software may be used to endorse or promote products
|
||||
# derived from this software without specific prior written consent.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
# POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
###
|
||||
|
||||
import supybot.conf as conf
|
||||
import supybot.registry as registry
|
||||
from supybot.i18n import PluginInternationalization, internationalizeDocstring
|
||||
_ = PluginInternationalization('Trivia')
|
||||
def configure(advanced):
|
||||
# This will be called by supybot to configure this module. advanced is
|
||||
# a bool that specifies whether the user identified himself as an advanced
|
||||
# user or not. You should effect your configuration by manipulating the
|
||||
# registry as appropriate.
|
||||
from supybot.questions import expect, anything, something, yn
|
||||
conf.registerPlugin('Trivia', True)
|
||||
|
||||
|
||||
Trivia = conf.registerPlugin('Trivia')
|
||||
# This is where your configuration variables (if any) should go. For example:
|
||||
# conf.registerGlobalValue(Trivia, 'someConfigVariableName',
|
||||
# registry.Boolean(False, """Help for someConfigVariableName."""))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'blankChar',
|
||||
registry.String('*', _("""The character used for a blank when
|
||||
displaying hints""")))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'numHints',
|
||||
registry.PositiveInteger(3, _("""The number of hints to be given for
|
||||
each question""")))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'timeout',
|
||||
registry.PositiveInteger(90, _("""The number of seconds to allow for
|
||||
each question""")))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'hintPercentage',
|
||||
registry.Probability(0.25, _("""The fraction of the answer that
|
||||
should be revealed with each hint""")))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'flexibility',
|
||||
registry.PositiveInteger(8, _("""The flexibility of the trivia answer
|
||||
checker. One typo will be allowed for every __ characters.""")))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'color',
|
||||
registry.PositiveInteger(10, _("""The mIRC color to use for trivia
|
||||
questions""")))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'inactiveShutoff',
|
||||
registry.Integer(6, _("""The number of questions that can go
|
||||
unanswered before the trivia stops automatically.""")))
|
||||
|
||||
conf.registerGlobalValue(Trivia, 'scoreFile',
|
||||
registry.String('scores.txt', _("""The path to the scores file.
|
||||
If it doesn't exist, it will be created.""")))
|
||||
|
||||
conf.registerGlobalValue(Trivia, 'questionFile',
|
||||
registry.String('questions.txt', _("""The path to the questions file.
|
||||
If it doesn't exist, it will be created.""")))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'defaultRoundLength',
|
||||
registry.PositiveInteger(10, _("""The default number of questions to
|
||||
be asked in a round of trivia.""")))
|
||||
|
||||
conf.registerGlobalValue(Trivia, 'questionFileSeparator',
|
||||
registry.String('*', _("""The separator used between the questions
|
||||
and answers in your trivia file.""")))
|
||||
|
||||
conf.registerChannelValue(Trivia, 'randomize',
|
||||
registry.Boolean('True', _("""This will determine whether or not the
|
||||
bot will randomize the trivia questions.""")))
|
||||
|
||||
# vim:set shiftwidth=4 tabstop=4 expandtab textwidth=79:
|
|
@ -0,0 +1 @@
|
|||
# Stub so local is a module, used for third-party modules
|
|
@ -0,0 +1,162 @@
|
|||
# SOME DESCRIPTIVE TITLE.
|
||||
# Copyright (C) YEAR ORGANIZATION
|
||||
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
|
||||
#
|
||||
msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: Supybot\n"
|
||||
"POT-Creation-Date: 2011-11-01 19:21+CET\n"
|
||||
"PO-Revision-Date: 2011-11-01 19:37+0100\n"
|
||||
"Last-Translator: Florian Besser <fbesser@gmail.com>\n"
|
||||
"Language-Team: German <fbesser@gmail.com>\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
"Generated-By: pygettext.py 1.5\n"
|
||||
|
||||
#: config.py:51
|
||||
msgid ""
|
||||
"The character used for a blank when\n"
|
||||
" displaying hints"
|
||||
msgstr "Das Zeichen das als blankes Zeichen bei Tipps benutzt wird."
|
||||
|
||||
#: config.py:55
|
||||
msgid ""
|
||||
"The number of hints to be given for\n"
|
||||
" each question"
|
||||
msgstr "Die Nummer der Tipps die pro Frage gegeben werden."
|
||||
|
||||
#: config.py:59
|
||||
msgid ""
|
||||
"The number of seconds to allow for\n"
|
||||
" each question"
|
||||
msgstr "Die Anzahl der Sekunden für jede Frage."
|
||||
|
||||
#: config.py:63
|
||||
msgid ""
|
||||
"The fraction of the answer that\n"
|
||||
" should be revealed with each hint"
|
||||
msgstr "Der Anteil der Frage die mit jedem Tipp preisgegeben wird."
|
||||
|
||||
#: config.py:67
|
||||
msgid ""
|
||||
"The flexibility of the trivia answer\n"
|
||||
" checker. One typo will be allowed for every __ characters."
|
||||
msgstr "Die Flexibilität des Fragencheckers. Ein Fehler wird alle __ Zeichen erlaubt."
|
||||
|
||||
#: config.py:71
|
||||
msgid ""
|
||||
"The mIRC color to use for trivia\n"
|
||||
" questions"
|
||||
msgstr "Die mIRC Frage für Quizfragen."
|
||||
|
||||
#: config.py:75
|
||||
msgid ""
|
||||
"The number of questions that can go\n"
|
||||
" unanswered before the trivia stops automatically."
|
||||
msgstr "Die Anzahl der Fragen die unbeantwortet bleiben können, bevor das Quiz automatisch stoppt."
|
||||
|
||||
#: config.py:79
|
||||
msgid ""
|
||||
"The path to the scores file.\n"
|
||||
" If it doesn't exist, it will be created."
|
||||
msgstr "Der Pfad zur Punktedatei. Falls diese nicht existiert wird sie erstellt."
|
||||
|
||||
#: config.py:83
|
||||
msgid ""
|
||||
"The path to the questions file.\n"
|
||||
" If it doesn't exist, it will be created."
|
||||
msgstr "Der Pfad zur Fragendatei. Falls diese nicht existiert wird sie erstellt."
|
||||
|
||||
#: config.py:87
|
||||
msgid ""
|
||||
"The default number of questions to\n"
|
||||
" be asked in a round of trivia."
|
||||
msgstr "Die Standardanzahl an Fragen die in einer Quizrunde gestellt werden."
|
||||
|
||||
#: config.py:91
|
||||
msgid ""
|
||||
"The separator used between the questions\n"
|
||||
" and answers in your trivia file."
|
||||
msgstr "Der Seperator zwischen Fragen und Antworten in deiner Triviadatei."
|
||||
|
||||
#: plugin.py:50
|
||||
msgid ""
|
||||
"Add the help for \"@plugin help Trivia\" here\n"
|
||||
" This should describe *how* to use this plugin."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:130
|
||||
msgid "Seems like no one's playing any more."
|
||||
msgstr "Ich glaube es spielt niemand mehr."
|
||||
|
||||
#: plugin.py:133
|
||||
msgid "Oops! I ran out of questions!"
|
||||
msgstr "Ups! Ich habe keine Fragen mehr!"
|
||||
|
||||
#: plugin.py:147
|
||||
msgid "%s#%d of %d: %s"
|
||||
msgstr "%s#%d aus %d: %s"
|
||||
|
||||
#: plugin.py:159
|
||||
msgid "Trivia stopping."
|
||||
msgstr "Quiz wird gestoppt."
|
||||
|
||||
#: plugin.py:177
|
||||
msgid "Top finishers: "
|
||||
msgstr "Top Spieler: "
|
||||
|
||||
#: plugin.py:183
|
||||
msgid "%s %s %s."
|
||||
msgstr "%s %s %s."
|
||||
|
||||
#: plugin.py:190
|
||||
msgid "No one got the answer! It was: %s"
|
||||
msgstr "Niemand hatte die Antwort! Die Antwort war: %s"
|
||||
|
||||
#: plugin.py:208
|
||||
msgid "HINT: %s%s"
|
||||
msgstr "Tipp: %s%s"
|
||||
|
||||
#: plugin.py:235
|
||||
msgid "%s got it! The full answer was: %s. Points: %d"
|
||||
msgstr "%s hat es richtig! Die volle Antwort war: %s. Punkte: %d"
|
||||
|
||||
#: plugin.py:276
|
||||
msgid ""
|
||||
"[<channel>] [<number of questions>]\n"
|
||||
"\n"
|
||||
" Starts a game of trivia. <channel> is only necessary if the message\n"
|
||||
" isn't sent in the channel itself."
|
||||
msgstr ""
|
||||
"[<Kanal>] [<Anzahl der Fragen>]\n"
|
||||
"\n"
|
||||
"Startet ein neues Quiz. <Kanal> wird nur benötigt falls der Befehl nicht im Kanal gegeben wird."
|
||||
|
||||
#: plugin.py:294
|
||||
msgid "Orphaned trivia game found and removed."
|
||||
msgstr "Verwaistes Quiz gefunden und entfernt."
|
||||
|
||||
#: plugin.py:298
|
||||
msgid "%d questions added to active game!"
|
||||
msgstr "%d Fragen zum aktiven Spiel hinzugefügt!"
|
||||
|
||||
#: plugin.py:306
|
||||
msgid ""
|
||||
"[<channel>]\n"
|
||||
"\n"
|
||||
" Stops a running game of trivia. <channel> is only necessary if the\n"
|
||||
" message isn't sent in the channel itself."
|
||||
msgstr ""
|
||||
"[<Kanal>]\n"
|
||||
"\n"
|
||||
"Stoppt das laufende Quiz. <Kanal> wird nur benötigt falls der Befehl nicht im Kanal gegeben wird."
|
||||
|
||||
#: plugin.py:314
|
||||
msgid "No trivia started"
|
||||
msgstr "Es läuft kein Quiz."
|
||||
|
||||
#: plugin.py:320
|
||||
msgid "Trivia stopped"
|
||||
msgstr "Quiz gestoppt"
|
||||
|
|
@ -0,0 +1,164 @@
|
|||
msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: Supybot-fr\n"
|
||||
"POT-Creation-Date: 2011-11-01 19:21+CET\n"
|
||||
"PO-Revision-Date: 2011-11-07 14:45+0100\n"
|
||||
"Last-Translator: skizzhg <skizzhg@gmx.com>\n"
|
||||
"Language-Team: Italian <skizzhg@gmx.com>\n"
|
||||
"Language: it\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
|
||||
|
||||
#: config.py:51
|
||||
msgid ""
|
||||
"The character used for a blank when\n"
|
||||
" displaying hints"
|
||||
msgstr "Il carattere usato per lo spazio vuoto quando vengono visualizzati i suggerimenti."
|
||||
|
||||
#: config.py:55
|
||||
msgid ""
|
||||
"The number of hints to be given for\n"
|
||||
" each question"
|
||||
msgstr "Il numero di suggerimenti da fornire per ogni domanda."
|
||||
|
||||
#: config.py:59
|
||||
msgid ""
|
||||
"The number of seconds to allow for\n"
|
||||
" each question"
|
||||
msgstr "Il numero di secondi permessi per ogni domanda."
|
||||
|
||||
#: config.py:63
|
||||
msgid ""
|
||||
"The fraction of the answer that\n"
|
||||
" should be revealed with each hint"
|
||||
msgstr "La porzione della risposta rivelata da ogni suggerimento."
|
||||
|
||||
#: config.py:67
|
||||
msgid ""
|
||||
"The flexibility of the trivia answer\n"
|
||||
" checker. One typo will be allowed for every __ characters."
|
||||
msgstr "La flessibilità del controllore delle risposte, sarà consentito un errore di battitura ogni __ caratteri."
|
||||
|
||||
#: config.py:71
|
||||
msgid ""
|
||||
"The mIRC color to use for trivia\n"
|
||||
" questions"
|
||||
msgstr "Il colore mIRC da utilizzare per le domande del trivia."
|
||||
|
||||
#: config.py:75
|
||||
msgid ""
|
||||
"The number of questions that can go\n"
|
||||
" unanswered before the trivia stops automatically."
|
||||
msgstr "Il numero di domande che possono rimanere senza risposta prima che il trivia si fermi automaticamente."
|
||||
|
||||
#: config.py:79
|
||||
msgid ""
|
||||
"The path to the scores file.\n"
|
||||
" If it doesn't exist, it will be created."
|
||||
msgstr "Il percorso del file dei punteggi, se non esiste verrà creato."
|
||||
|
||||
#: config.py:83
|
||||
msgid ""
|
||||
"The path to the questions file.\n"
|
||||
" If it doesn't exist, it will be created."
|
||||
msgstr "Il percorso del file delle domande, se non esiste verrà creato."
|
||||
|
||||
#: config.py:87
|
||||
msgid ""
|
||||
"The default number of questions to\n"
|
||||
" be asked in a round of trivia."
|
||||
msgstr "Il numero predefinito di domande da porre in una partita di trivia."
|
||||
|
||||
#: config.py:91
|
||||
msgid ""
|
||||
"The separator used between the questions\n"
|
||||
" and answers in your trivia file."
|
||||
msgstr "Il separatore usato tra le domande e le risposte nel file del trivia."
|
||||
|
||||
#: plugin.py:50
|
||||
#, docstring
|
||||
msgid ""
|
||||
"Add the help for \"@plugin help Trivia\" here\n"
|
||||
" This should describe *how* to use this plugin."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:130
|
||||
msgid "Seems like no one's playing any more."
|
||||
msgstr "Sembra che nessuno stia più giocando."
|
||||
|
||||
#: plugin.py:133
|
||||
msgid "Oops! I ran out of questions!"
|
||||
msgstr "Oops! Ho finito le domande!"
|
||||
|
||||
#: plugin.py:147
|
||||
msgid "\003%s#%d of %d: %s"
|
||||
msgstr "\003%s#%d di %d: %s"
|
||||
|
||||
#: plugin.py:159
|
||||
msgid "Trivia stopping."
|
||||
msgstr "Trivia fermato."
|
||||
|
||||
#: plugin.py:177
|
||||
msgid "Top finishers: "
|
||||
msgstr "Primi classificati: "
|
||||
|
||||
#: plugin.py:183
|
||||
msgid "%s %s %s."
|
||||
msgstr "%s %s %s."
|
||||
|
||||
#: plugin.py:190
|
||||
msgid "No one got the answer! It was: %s"
|
||||
msgstr "Nessuno ha la risposta! Era: %s"
|
||||
|
||||
#: plugin.py:208
|
||||
msgid "HINT: %s%s"
|
||||
msgstr "Suggerimento: %s%s"
|
||||
|
||||
#: plugin.py:235
|
||||
msgid "%s got it! The full answer was: %s. Points: %d"
|
||||
msgstr "%s ha indovinato! La risposta intera era: %s. Punti: %d"
|
||||
|
||||
#: plugin.py:276
|
||||
#, docstring
|
||||
msgid ""
|
||||
"[<channel>] [<number of questions>]\n"
|
||||
"\n"
|
||||
" Starts a game of trivia. <channel> is only necessary if the message\n"
|
||||
" isn't sent in the channel itself."
|
||||
msgstr ""
|
||||
"[<canale>] [<numero di domande>]\n"
|
||||
"\n"
|
||||
" Inizia una partita di trivia. <canale> è necessario solo se il messaggio\n"
|
||||
" non viene inviato nel canale stesso."
|
||||
|
||||
#: plugin.py:294
|
||||
msgid "Orphaned trivia game found and removed."
|
||||
msgstr "Trovata e rimossa una partita di trivia abbandonata."
|
||||
|
||||
#: plugin.py:298
|
||||
msgid "%d questions added to active game!"
|
||||
msgstr "%d domande aggiunte al gioco in corso!"
|
||||
|
||||
#: plugin.py:306
|
||||
#, docstring
|
||||
msgid ""
|
||||
"[<channel>]\n"
|
||||
"\n"
|
||||
" Stops a running game of trivia. <channel> is only necessary if the\n"
|
||||
" message isn't sent in the channel itself."
|
||||
msgstr ""
|
||||
"[<canale>]\n"
|
||||
"\n"
|
||||
" Interrompe una partita di trivia in corso. <canale> è necessario solo se\n"
|
||||
" il messaggio non viene inviato nel canale stesso."
|
||||
|
||||
#: plugin.py:314
|
||||
msgid "No trivia started"
|
||||
msgstr "Nessun trivia avviato."
|
||||
|
||||
#: plugin.py:320
|
||||
msgid "Trivia stopped"
|
||||
msgstr "Trivia fermato."
|
||||
|
|
@ -0,0 +1,160 @@
|
|||
# SOME DESCRIPTIVE TITLE.
|
||||
# Copyright (C) YEAR ORGANIZATION
|
||||
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
|
||||
#
|
||||
msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: PACKAGE VERSION\n"
|
||||
"POT-Creation-Date: 2011-11-01 19:21+CET\n"
|
||||
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
||||
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
|
||||
"Language-Team: LANGUAGE <LL@li.org>\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=CHARSET\n"
|
||||
"Content-Transfer-Encoding: ENCODING\n"
|
||||
"Generated-By: pygettext.py 1.5\n"
|
||||
|
||||
|
||||
#: config.py:51
|
||||
msgid ""
|
||||
"The character used for a blank when\n"
|
||||
" displaying hints"
|
||||
msgstr ""
|
||||
|
||||
#: config.py:55
|
||||
msgid ""
|
||||
"The number of hints to be given for\n"
|
||||
" each question"
|
||||
msgstr ""
|
||||
|
||||
#: config.py:59
|
||||
msgid ""
|
||||
"The number of seconds to allow for\n"
|
||||
" each question"
|
||||
msgstr ""
|
||||
|
||||
#: config.py:63
|
||||
msgid ""
|
||||
"The fraction of the answer that\n"
|
||||
" should be revealed with each hint"
|
||||
msgstr ""
|
||||
|
||||
#: config.py:67
|
||||
msgid ""
|
||||
"The flexibility of the trivia answer\n"
|
||||
" checker. One typo will be allowed for every __ characters."
|
||||
msgstr ""
|
||||
|
||||
#: config.py:71
|
||||
msgid ""
|
||||
"The mIRC color to use for trivia\n"
|
||||
" questions"
|
||||
msgstr ""
|
||||
|
||||
#: config.py:75
|
||||
msgid ""
|
||||
"The number of questions that can go\n"
|
||||
" unanswered before the trivia stops automatically."
|
||||
msgstr ""
|
||||
|
||||
#: config.py:79
|
||||
msgid ""
|
||||
"The path to the scores file.\n"
|
||||
" If it doesn't exist, it will be created."
|
||||
msgstr ""
|
||||
|
||||
#: config.py:83
|
||||
msgid ""
|
||||
"The path to the questions file.\n"
|
||||
" If it doesn't exist, it will be created."
|
||||
msgstr ""
|
||||
|
||||
#: config.py:87
|
||||
msgid ""
|
||||
"The default number of questions to\n"
|
||||
" be asked in a round of trivia."
|
||||
msgstr ""
|
||||
|
||||
#: config.py:91
|
||||
msgid ""
|
||||
"The separator used between the questions\n"
|
||||
" and answers in your trivia file."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:50
|
||||
#, docstring
|
||||
msgid ""
|
||||
"Add the help for \"@plugin help Trivia\" here\n"
|
||||
" This should describe *how* to use this plugin."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:130
|
||||
msgid "Seems like no one's playing any more."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:133
|
||||
msgid "Oops! I ran out of questions!"
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:147
|
||||
msgid "\003%s#%d of %d: %s"
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:159
|
||||
msgid "Trivia stopping."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:177
|
||||
msgid "Top finishers: "
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:183
|
||||
msgid "%s %s %s."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:190
|
||||
msgid "No one got the answer! It was: %s"
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:208
|
||||
msgid "HINT: %s%s"
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:235
|
||||
msgid "%s got it! The full answer was: %s. Points: %d"
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:276
|
||||
#, docstring
|
||||
msgid ""
|
||||
"[<channel>] [<number of questions>]\n"
|
||||
"\n"
|
||||
" Starts a game of trivia. <channel> is only necessary if the message\n"
|
||||
" isn't sent in the channel itself."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:294
|
||||
msgid "Orphaned trivia game found and removed."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:298
|
||||
msgid "%d questions added to active game!"
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:306
|
||||
#, docstring
|
||||
msgid ""
|
||||
"[<channel>]\n"
|
||||
"\n"
|
||||
" Stops a running game of trivia. <channel> is only necessary if the\n"
|
||||
" message isn't sent in the channel itself."
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:314
|
||||
msgid "No trivia started"
|
||||
msgstr ""
|
||||
|
||||
#: plugin.py:320
|
||||
msgid "Trivia stopped"
|
||||
msgstr ""
|
||||
|
|
@ -0,0 +1,329 @@
|
|||
###
|
||||
# Copyright (c) 2010, quantumlemur
|
||||
# Copyright (c) 2011, Valentin Lorentz
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
#
|
||||
# * Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions, and the following disclaimer.
|
||||
# * Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions, and the following disclaimer in the
|
||||
# documentation and/or other materials provided with the distribution.
|
||||
# * Neither the name of the author of this software nor the name of
|
||||
# contributors to this software may be used to endorse or promote products
|
||||
# derived from this software without specific prior written consent.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
# POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
###
|
||||
|
||||
import re
|
||||
import os
|
||||
import time
|
||||
import math
|
||||
import string
|
||||
import random
|
||||
import supybot.utils as utils
|
||||
import supybot.ircdb as ircdb
|
||||
from supybot.commands import *
|
||||
import supybot.plugins as plugins
|
||||
import supybot.ircmsgs as ircmsgs
|
||||
import supybot.ircutils as ircutils
|
||||
import supybot.schedule as schedule
|
||||
import supybot.callbacks as callbacks
|
||||
from supybot.i18n import PluginInternationalization, internationalizeDocstring
|
||||
_ = PluginInternationalization('Trivia')
|
||||
|
||||
class Trivia(callbacks.Plugin):
|
||||
"""Add the help for "@plugin help Trivia" here
|
||||
This should describe *how* to use this plugin."""
|
||||
threaded = True
|
||||
|
||||
|
||||
def __init__(self, irc):
|
||||
self.__parent = super(Trivia, self)
|
||||
self.__parent.__init__(irc)
|
||||
self.games = {}
|
||||
self.scores = {}
|
||||
questionfile = self.registryValue('questionFile')
|
||||
if not os.path.exists(questionfile):
|
||||
f = open(questionfile, 'w')
|
||||
f.write(('If you\'re seeing this question, it means that the '
|
||||
'questions file that you specified wasn\'t found, and '
|
||||
'a new one has been created. Go get some questions!%s'
|
||||
'No questions found') %
|
||||
self.registryValue('questionFileSeparator'))
|
||||
f.close()
|
||||
self.scorefile = self.registryValue('scoreFile')
|
||||
if not os.path.exists(self.scorefile):
|
||||
f = open(self.scorefile, 'w')
|
||||
f.close()
|
||||
f = open(self.scorefile, 'r')
|
||||
line = f.readline()
|
||||
while line:
|
||||
(name, score) = line.split(' ')
|
||||
self.scores[name] = int(score.strip('\r\n'))
|
||||
line = f.readline()
|
||||
f.close()
|
||||
|
||||
|
||||
def doPrivmsg(self, irc, msg):
|
||||
channel = ircutils.toLower(msg.args[0])
|
||||
if not irc.isChannel(channel):
|
||||
return
|
||||
if callbacks.addressed(irc.nick, msg):
|
||||
return
|
||||
if channel in self.games:
|
||||
self.games[channel].answer(msg)
|
||||
|
||||
|
||||
class Game:
|
||||
def __init__(self, irc, channel, num, plugin):
|
||||
self.rng = random.Random()
|
||||
self.rng.seed()
|
||||
self.registryValue = plugin.registryValue
|
||||
self.irc = irc
|
||||
self.channel = channel
|
||||
self.num = num
|
||||
self.numAsked = 0
|
||||
self.hints = 0
|
||||
self.games = plugin.games
|
||||
self.scores = plugin.scores
|
||||
self.scorefile = plugin.scorefile
|
||||
self.questionfile = self.registryValue('questionFile')
|
||||
self.total = num
|
||||
self.active = True
|
||||
self.questions = []
|
||||
self.roundscores = {}
|
||||
self.unanswered = 0
|
||||
f = open(self.questionfile, 'r')
|
||||
line = f.readline()
|
||||
while line:
|
||||
self.questions.append(line.strip('\n\r'))
|
||||
line = f.readline()
|
||||
f.close()
|
||||
if self.registryValue('randomize', channel): random.shuffle(self.questions)
|
||||
try:
|
||||
schedule.removeEvent('next_%s' % self.channel)
|
||||
except KeyError:
|
||||
pass
|
||||
self.newquestion()
|
||||
|
||||
|
||||
def newquestion(self):
|
||||
inactiveShutoff = self.registryValue('inactiveShutoff',
|
||||
self.channel)
|
||||
if self.num == 0:
|
||||
self.active = False
|
||||
elif self.unanswered > inactiveShutoff and inactiveShutoff >= 0:
|
||||
self.reply(_('Seems like no one\'s playing any more.'))
|
||||
self.active = False
|
||||
elif len(self.questions) == 0:
|
||||
self.reply(_('Oops! I ran out of questions!'))
|
||||
self.active = False
|
||||
if not self.active:
|
||||
self.stop()
|
||||
return
|
||||
self.hints = 0
|
||||
self.num -= 1
|
||||
self.numAsked += 1
|
||||
q = self.questions.pop(len(self.questions)-1)
|
||||
sep = self.registryValue('questionFileSeparator')
|
||||
self.q = q[:q.find(sep)]
|
||||
self.a = q[q.find(sep)+len(sep):].split(sep)
|
||||
color = self.registryValue('color', self.channel)
|
||||
self.reply(_('\x03%s#%d of %d: %s') % (color, self.numAsked,
|
||||
self.total, self.q))
|
||||
def event():
|
||||
self.timedEvent()
|
||||
timeout = self.registryValue('timeout', self.channel)
|
||||
numHints = self.registryValue('numHints', self.channel)
|
||||
eventTime = time.time() + timeout / (numHints + 1)
|
||||
if self.active:
|
||||
schedule.addEvent(event, eventTime, 'next_%s' % self.channel)
|
||||
|
||||
|
||||
def stop(self):
|
||||
self.reply(_('Trivia stopping.'))
|
||||
self.active = False
|
||||
try:
|
||||
schedule.removeEvent('next_%s' % self.channel)
|
||||
except KeyError:
|
||||
pass
|
||||
scores = iter(self.roundscores.items())
|
||||
sorted = []
|
||||
for i in range(0, len(self.roundscores)):
|
||||
item = next(scores)
|
||||
sorted.append(item)
|
||||
def cmp(a, b):
|
||||
return b[1] - a[1]
|
||||
sorted.sort(key=lambda item: item[1], reverse=True)
|
||||
max = 3
|
||||
if len(sorted) < max:
|
||||
max = len(sorted)
|
||||
#self.reply('max: %d. len: %d' % (max, len(sorted)))
|
||||
s = _('Top finishers: ')
|
||||
if max > 0:
|
||||
recipients = []
|
||||
maxp = sorted[0][1]
|
||||
for i in range(0, max):
|
||||
item = sorted[i]
|
||||
s = _('%s %s %s.') % (s, item[0], item[1])
|
||||
self.reply(s)
|
||||
del self.games[self.channel]
|
||||
|
||||
|
||||
def timedEvent(self):
|
||||
if self.hints >= self.registryValue('numHints', self.channel):
|
||||
self.reply(_('No one got the answer! It was: %s') % self.a[0])
|
||||
self.unanswered += 1
|
||||
self.newquestion()
|
||||
else:
|
||||
self.hint()
|
||||
|
||||
|
||||
def hint(self):
|
||||
self.hints += 1
|
||||
ans = self.a[0]
|
||||
hintPercentage = self.registryValue('hintPercentage', self.channel)
|
||||
divider = int(math.ceil(len(ans) * hintPercentage * self.hints ))
|
||||
if divider == len(ans):
|
||||
divider -= 1
|
||||
show = ans[ : divider]
|
||||
blank = ans[divider : ]
|
||||
blankChar = self.registryValue('blankChar', self.channel)
|
||||
blank = re.sub('\w', blankChar, blank)
|
||||
self.reply(_('HINT: %s%s') % (show, blank))
|
||||
def event():
|
||||
self.timedEvent()
|
||||
timeout = self.registryValue('timeout', self.channel)
|
||||
numHints = self.registryValue('numHints', self.channel)
|
||||
eventTime = time.time() + timeout / (numHints + 1)
|
||||
if self.active:
|
||||
schedule.addEvent(event, eventTime, 'next_%s' % self.channel)
|
||||
|
||||
|
||||
def answer(self, msg):
|
||||
correct = False
|
||||
for ans in self.a:
|
||||
dist = self.DL(str.lower(msg.args[1]), str.lower(ans))
|
||||
flexibility = self.registryValue('flexibility', self.channel)
|
||||
if dist <= len(ans) / flexibility:
|
||||
correct = True
|
||||
#if self.registryValue('debug'):
|
||||
# self.reply('Distance: %d' % dist)
|
||||
if correct:
|
||||
if not msg.nick in self.scores:
|
||||
self.scores[msg.nick] = 0
|
||||
self.scores[msg.nick] += 1
|
||||
if not msg.nick in self.roundscores:
|
||||
self.roundscores[msg.nick] = 0
|
||||
self.roundscores[msg.nick] += 1
|
||||
self.unanswered = 0
|
||||
self.reply(_('%s got it! The full answer was: %s. Points: %d') %
|
||||
(msg.nick, self.a[0], self.scores[msg.nick]))
|
||||
schedule.removeEvent('next_%s' % self.channel)
|
||||
self.writeScores()
|
||||
self.newquestion()
|
||||
|
||||
|
||||
def reply(self, s):
|
||||
self.irc.queueMsg(ircmsgs.privmsg(self.channel, s))
|
||||
|
||||
|
||||
def writeScores(self):
|
||||
f = open(self.scorefile, 'w')
|
||||
scores = iter(self.scores.items())
|
||||
for i in range(0, len(self.scores)):
|
||||
score = next(scores)
|
||||
f.write('%s %s\n' % (score[0], score[1]))
|
||||
f.close()
|
||||
|
||||
|
||||
def DL(self, seq1, seq2):
|
||||
oneago = None
|
||||
thisrow = list(range(1, len(seq2) + 1)) + [0]
|
||||
for x in range(len(seq1)):
|
||||
# Python lists wrap around for negative indices, so put the
|
||||
# leftmost column at the *end* of the list. This matches with
|
||||
# the zero-indexed strings and saves extra calculation.
|
||||
twoago, oneago, thisrow = oneago, thisrow, [0]*len(seq2)+[x+1]
|
||||
for y in range(len(seq2)):
|
||||
delcost = oneago[y] + 1
|
||||
addcost = thisrow[y - 1] + 1
|
||||
subcost = oneago[y - 1] + (seq1[x] != seq2[y])
|
||||
thisrow[y] = min(delcost, addcost, subcost)
|
||||
# This block deals with transpositions
|
||||
if x > 0 and y > 0 and seq1[x] == seq2[y - 1] and \
|
||||
seq1[x-1] == seq2[y] and seq1[x] != seq2[y]:
|
||||
thisrow[y] = min(thisrow[y], twoago[y - 2] + 1)
|
||||
return thisrow[len(seq2) - 1]
|
||||
|
||||
@internationalizeDocstring
|
||||
def start(self, irc, msg, args, channel, num):
|
||||
"""[<channel>] [<number of questions>]
|
||||
|
||||
Starts a game of trivia. <channel> is only necessary if the message
|
||||
isn't sent in the channel itself."""
|
||||
if num == None:
|
||||
num = self.registryValue('defaultRoundLength', channel)
|
||||
#elif num > 100:
|
||||
# irc.reply('sorry, for now, you can\'t start games with more '
|
||||
# 'than 100 questions :(')
|
||||
# num = 100
|
||||
channel = ircutils.toLower(channel)
|
||||
if channel in self.games:
|
||||
if not self.games[channel].active:
|
||||
del self.games[channel]
|
||||
try:
|
||||
schedule.removeEvent('next_%s' % channel)
|
||||
except KeyError:
|
||||
pass
|
||||
irc.reply(_('Orphaned trivia game found and removed.'))
|
||||
else:
|
||||
self.games[channel].num += num
|
||||
self.games[channel].total += num
|
||||
irc.reply(_('%d questions added to active game!') % num)
|
||||
else:
|
||||
self.games[channel] = self.Game(irc, channel, num, self)
|
||||
irc.noReply()
|
||||
start = wrap(start, ['channel', optional('positiveInt')])
|
||||
|
||||
@internationalizeDocstring
|
||||
def stop(self, irc, msg, args, channel):
|
||||
"""[<channel>]
|
||||
|
||||
Stops a running game of trivia. <channel> is only necessary if the
|
||||
message isn't sent in the channel itself."""
|
||||
channel = ircutils.toLower(channel)
|
||||
try:
|
||||
schedule.removeEvent('next_%s' % channel)
|
||||
except KeyError:
|
||||
irc.error(_('No trivia started'))
|
||||
if channel in self.games:
|
||||
if self.games[channel].active:
|
||||
self.games[channel].stop()
|
||||
else:
|
||||
del self.games[channel]
|
||||
irc.reply(_('Trivia stopped'))
|
||||
else:
|
||||
irc.noReply()
|
||||
stop = wrap(stop, ['channel'])
|
||||
|
||||
|
||||
Class = Trivia
|
||||
|
||||
|
||||
# vim:set shiftwidth=4 softtabstop=4 expandtab textwidth=79:
|
|
@ -0,0 +1,42 @@
|
|||
###
|
||||
# Copyright (c) 2011, Valentin Lorentz
|
||||
# All rights reserved.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions are met:
|
||||
#
|
||||
# * Redistributions of source code must retain the above copyright notice,
|
||||
# this list of conditions, and the following disclaimer.
|
||||
# * Redistributions in binary form must reproduce the above copyright notice,
|
||||
# this list of conditions, and the following disclaimer in the
|
||||
# documentation and/or other materials provided with the distribution.
|
||||
# * Neither the name of the author of this software nor the name of
|
||||
# contributors to this software may be used to endorse or promote products
|
||||
# derived from this software without specific prior written consent.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
# ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
# LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
# POSSIBILITY OF SUCH DAMAGE.
|
||||
|
||||
###
|
||||
|
||||
from supybot.test import *
|
||||
|
||||
class TriviaTestCase(ChannelPluginTestCase):
|
||||
plugins = ('Trivia',)
|
||||
|
||||
def testStartStop(self):
|
||||
self.assertRegexp('start', '...#1 of 10:.*')
|
||||
self.assertResponse('stop', 'Trivia stopping.')
|
||||
self.assertError('stop')
|
||||
|
||||
|
||||
# vim:set shiftwidth=4 tabstop=4 expandtab textwidth=79:
|
Loading…
Reference in New Issue