from otree.api import * doc = """ Your app description """ class C(BaseConstants): NAME_IN_URL = 'PublicGood' PLAYERS_PER_GROUP = 3 NUM_ROUNDS = 1 ENDOWMENT = cu(2) MULTIPLIER = 0.4 # muss noch definiert werden XXXX pg_time = 120 timer_text = "To make sure your group members don't have to wait too long, please press the Next button before the timer runs out:" class Subsession(BaseSubsession): pass def group_by_arrival_time_method(subsession: Subsession, waiting_players): # we now place users into different baskets, according to their group in the previous app. # the dict 'd' will contain all these baskets. d = {} for p in waiting_players: group_id = p.participant.vars['past_group_id'] if group_id not in d: # since 'd' is initially empty, we need to initialize an empty list (basket) # each time we see a new group ID. d[group_id] = [] players_in_my_group = d[group_id] players_in_my_group.append(p) if len(players_in_my_group) == 3: return players_in_my_group # print('d is', d) class Group(BaseGroup): total_contribution = models.CurrencyField() individual_share = models.CurrencyField() class Player(BasePlayer): contribution = models.CurrencyField( min=0, max=C.ENDOWMENT, label="How much do you contribute?" ) contribution_live = models.FloatField(initial = 11) PG_payoff = models.CurrencyField() contribution_timeout = models.BooleanField(initial=False) def set_payoffs(group: Group): player_lists = group.get_players() player_1 = player_lists[0] player_2 = player_lists[1] player_3 = player_lists[2] #print('contribution player 1', player_1.contribution) #print('contribution player 2', player_2.contribution) #print('contribution player 3', player_3.contribution) if player_1.field_maybe_none('contribution') is None: player_1.contribution = 0 player_1.contribution_timeout = True if player_2.field_maybe_none('contribution') is None: player_2.contribution = 0 player_2.contribution_timeout = True if player_3.field_maybe_none('contribution') is None: player_3.contribution = 0 player_3.contribution_timeout = True players = group.get_players() contributions = [p.contribution for p in players] group.total_contribution = sum(contributions) group.individual_share = (group.total_contribution * C.MULTIPLIER) for p in players: p.PG_payoff = C.ENDOWMENT - p.contribution + group.individual_share p.participant.vars["PG_payoff"] = p.PG_payoff p.participant.vars["PG_contribution"] = p.contribution p.participant.vars['individual_share'] = group.individual_share p.participant.vars['PG_keep'] = C.ENDOWMENT - p.contribution # PAGES class Contribute(Page): form_model = 'player' timeout_seconds = C.pg_time timer_text = C.timer_text @staticmethod def before_next_page(player, timeout_happened): if 0 <= player.contribution_live <= C.ENDOWMENT: player.contribution = player.contribution_live if timeout_happened and player.contribution_live == 11.0: player.contribution_timeout = True player.contribution = 0 @staticmethod def live_method(player, input): print(input) if 0<=input['value']<=C.ENDOWMENT: player.contribution_live = input['value'] class ResultsWaitPage(WaitPage): after_all_players_arrive = 'set_payoffs' class GBATWait(WaitPage): group_by_arrival_time = True class Results(Page): pass page_sequence = [ GBATWait, Contribute, ResultsWaitPage, Results, ]