from otree.api import ( models, widgets, BaseConstants, BaseSubsession, BaseGroup, BasePlayer, Currency as c, currency_range, Page, WaitPage ) cu = c doc = "\nEach player decides if to free ride or to volunteer from which all will\nbenefit.\n\nSee: Diekmann, A. (1985). Volunteer's dilemma. Journal of Conflict\nResolution, 605-610.\n" class Constants(BaseConstants): name_in_url = 'volunteer_dilemma' new_match_periods = (8, 9, 5, 10, 2, 1, 22, 4, 16, 2) random_cost_draws = (0, 1, 1, 0, 1, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1) num_rounds = 130 players_per_group = 2 num_other_players = 1 block_size = 10 num_matches = 10 general_benefit = c(10) volunteer_cost = c(2) volunteer_costH = c(6) volunteer_costL = c(4) instructions_fixed_cost_template = 'volunteer_dilemma/instructions_fixed_cost.html' instructions_random_cost_template = 'volunteer_dilemma/instructions_random_cost.html' instructions_symmetric_cost_template = 'volunteer_dilemma/instructions_symmetric_cost.html' def creating_session(subsession): session = subsession.session import math players = subsession.get_players() blocks=[] cum_blocks=[] match_start_rounds=[] match_start_rounds.append(1) for p in range(Constants.num_matches): blocks.append(math.ceil(Constants.new_match_periods[p]/Constants.block_size)) cum_blocks.append(sum(blocks)) for q in range(Constants.num_matches-1): match_start_rounds.append(Constants.block_size*cum_blocks[q]+1) for r in players: r.match=len([x for x in match_start_rounds if x<=subsession.round_number]) r.round=subsession.round_number-match_start_rounds[r.match-1]+1 r.real=r.round<=Constants.new_match_periods[r.match-1] r.last_real_round=Constants.new_match_periods[r.match-1] ##Random Costs ##if Constants.random_cost_draws[subsession.round_number-1] == 1: ## r.cost_role=r.id_in_group ##else: ## r.cost_role=3-r.id_in_group ##Fixed Costs r.cost_role=r.id_in_group ##Symmetric Costs (2 points) # r.cost_role=2 if r.round == 1: subsession.group_randomly(fixed_id_in_group = True) else: subsession.group_like_round(subsession.round_number-1) def set_vals(subsession): session = subsession.session groups=subsession.get_groups() for g in groups: players = g.get_players() for p in players: if p.cost_role==1: p.own_cost=Constants.volunteer_costH p.other_cost=Constants.volunteer_costL else: p.own_cost=Constants.volunteer_costL p.other_cost=Constants.volunteer_costH otherplayer=p.get_others_in_group() for o in otherplayer: if o.volunteer: p.other_volunteer = True else: p.other_volunteer = False if p.volunteer: baseline_amount=Constants.general_benefit elif o.volunteer: baseline_amount=Constants.general_benefit else: baseline_amount=c(0) p.points = baseline_amount p.other_points = baseline_amount if p.volunteer: p.points -= p.own_cost if p.other_volunteer: p.other_points -= p.other_cost if p.round == 1: p.real_points = c(0) p.other_real_points = c(0) else: p.real_points = p.in_round(subsession.round_number - 1).real_points p.other_real_points = p.in_round(subsession.round_number - 1).other_real_points if p.real: p.payoff = p.points p.real_points += p.points p.other_real_points += p.other_points class Subsession(BaseSubsession): creating_session = creating_session set_vals = set_vals class Group(BaseGroup): pass class Player(BasePlayer): match = models.IntegerField() round = models.IntegerField() cost_role = models.IntegerField() volunteer = models.BooleanField(doc='Whether player volunteers', label='Do you choose to invest?') other_volunteer = models.BooleanField() points = models.CurrencyField() other_points = models.CurrencyField() own_cost = models.CurrencyField() other_cost = models.CurrencyField() real = models.BooleanField() last_real_round = models.IntegerField() real_points = models.CurrencyField() other_real_points = models.CurrencyField()