quiz time
This commit is contained in:
146
plugins/quiz.py
Normal file
146
plugins/quiz.py
Normal file
@@ -0,0 +1,146 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
import os
|
||||
import random
|
||||
from functools import lru_cache
|
||||
|
||||
import re
|
||||
|
||||
import time
|
||||
|
||||
|
||||
@lru_cache(10)
|
||||
def get_questions(directory=None):
|
||||
if not directory:
|
||||
directory = 'plugins/quiz_resources/'
|
||||
all_files = sorted(filter(lambda x: x.endswith('.txt'), os.listdir(directory)))
|
||||
all_questions = []
|
||||
for q_file in all_files:
|
||||
with open(directory + q_file) as f:
|
||||
all_questions += f.readlines()[1:]
|
||||
return all_questions
|
||||
|
||||
|
||||
def get_random_question(quizcfg):
|
||||
questions = get_questions()
|
||||
# select a random question
|
||||
used_ids = quizcfg.get('used_ids', [])
|
||||
q_index = None
|
||||
while q_index is None:
|
||||
rand = random.choice(range(0, len(questions)-2, 2))
|
||||
if rand not in used_ids:
|
||||
q_index = rand
|
||||
|
||||
quizcfg['active_id'] = q_index
|
||||
quizcfg['used_ids'] = used_ids + [q_index]
|
||||
return questions[q_index], questions[q_index+1]
|
||||
|
||||
|
||||
def get_current_question(quizcfg):
|
||||
if quizcfg.get('active_id'):
|
||||
return int(quizcfg['active_id'])
|
||||
|
||||
|
||||
def end_question(quizcfg):
|
||||
lines = ['Question time over!']
|
||||
|
||||
score = float(quizcfg.get('current_max_score', 0))
|
||||
winner = quizcfg.get('current_max_user', 'nobody')
|
||||
|
||||
print(winner, score)
|
||||
win_msg = '{} scores with {:.2f}%'.format(winner, score)
|
||||
lose_msg = 'nobody scores.'
|
||||
|
||||
if score > 50.0:
|
||||
lines.append(win_msg)
|
||||
else:
|
||||
lines.append(lose_msg)
|
||||
|
||||
quizcfg['current_max_user'] = 'nobody'
|
||||
quizcfg['current_max_score'] = 0
|
||||
|
||||
quizcfg['active_id'] = None
|
||||
|
||||
start_next = None
|
||||
if not quizcfg.get('stop_bit', False):
|
||||
start_next = {
|
||||
'time': time.time() + 10,
|
||||
'command': (start_random_question, ([quizcfg],))
|
||||
}
|
||||
return {
|
||||
'msg': lines,
|
||||
'event': start_next
|
||||
}
|
||||
|
||||
|
||||
def stop(quizcfg):
|
||||
quizcfg['stop_bit'] = True
|
||||
return end_question(quizcfg)
|
||||
|
||||
|
||||
def rate(quizcfg, response, user):
|
||||
"""
|
||||
rate answer, check threshold, note user score
|
||||
:param quizcfg: configsection plugins/quiz
|
||||
:param response: text given by users
|
||||
:param user: nick to the response
|
||||
:return: actiondict
|
||||
"""
|
||||
questions = get_questions()
|
||||
current_quiz_question = get_current_question(quizcfg)
|
||||
answer = questions[current_quiz_question+1].lower()
|
||||
|
||||
anwer_words = set(re.findall('[a-zA-ZäöüÄÖÜß]+', answer))
|
||||
words = set(response.lower().split())
|
||||
|
||||
# stripping all fill words seems like a tedious task...
|
||||
|
||||
same_words = words.intersection(anwer_words)
|
||||
percentage = len(same_words)/len(anwer_words)*100
|
||||
|
||||
threshold = 50
|
||||
if (
|
||||
percentage > threshold and
|
||||
float(quizcfg.get('current_max_score', 0)) < percentage
|
||||
):
|
||||
quizcfg['current_max_user'] = user
|
||||
quizcfg['current_max_score'] = percentage
|
||||
return {
|
||||
'msg': 'Good answer.'
|
||||
}
|
||||
|
||||
# verbose_response = {
|
||||
# 'msg': 'matching {} words (answer {}), percentage {}'.format(
|
||||
# same_words, anwer_words, percentage
|
||||
# )
|
||||
# }
|
||||
|
||||
|
||||
def start_random_question(quizcfg):
|
||||
stop(quizcfg)
|
||||
qa = get_random_question(quizcfg)
|
||||
|
||||
return {
|
||||
'msg': ['Q: {}'.format(qa[0])],
|
||||
'event': {
|
||||
'command': (end_question, ([quizcfg],)),
|
||||
'time': time.time() + 15
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
def skip(quizcfg):
|
||||
""" skip the current question, omitting the
|
||||
answer and removing it from the used ones """
|
||||
quizcfg['used_ids'].remove(get_current_question(quizcfg))
|
||||
return end_question(quizcfg)
|
||||
|
||||
|
||||
def answer(quizcfg):
|
||||
the_answer = get_questions()[get_current_question(quizcfg)+1]
|
||||
return {
|
||||
'msg': 'Answer to the question: {}'.format(the_answer),
|
||||
'event': {
|
||||
'command': (end_question, ([quizcfg], )),
|
||||
'time': time.time() + 3
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user