from otree.api import ( models, widgets, BaseConstants, BaseSubsession, BaseGroup, BasePlayer, Currency as c, currency_range ) doc = 'This is a 20-period game with 4 players in a group. The first 10 periods is a public goods game. The last 10 periods is a public bads game. MPCR are diverse across players in a group.\n' class Constants(BaseConstants): name_in_url = 'diverse_noinfo' players_per_group = 4 num_rounds = 4 endowment = c(20) beta1 = 0.3 beta2 = 0.4 beta3 = 0.5 beta4 = 1.2 part1_rounds = 2 multiplier = 0 inx_pb_template = 'diverse_noinfo/inx_pb.html' inx_pg_template = 'diverse_noinfo/inx_pg.html' class Subsession(BaseSubsession): def vars_for_admin_report(self): contributions = [ p.contribution for p in self.get_players() if p.contribution != None ] if contributions: return dict( avg_contribution=sum(contributions) / len(contributions), min_contribution=min(contributions), max_contribution=max(contributions), ) else: return dict( avg_contribution='(no data)', min_contribution='(no data)', max_contribution='(no data)', ) class Group(BaseGroup): total_contribution = models.CurrencyField() individual_share = models.CurrencyField() def set_payoffs(self): p1 = self.get_player_by_id(1) p2 = self.get_player_by_id(2) p3 = self.get_player_by_id(3) p4 = self.get_player_by_id(4) self.total_contribution = sum([p.contribution for p in self.get_players()]) individual_share1 = self.total_contribution * Constants.beta1 individual_share2 = self.total_contribution * Constants.beta2 individual_share3 = self.total_contribution * Constants.beta3 individual_share4 = self.total_contribution * Constants.beta4 if self.round_number<=Constants.part1_rounds: p1.payoff = (Constants.endowment - p1.contribution) + individual_share1 else: p1.payoff = (Constants.endowment + p1.contribution) - individual_share1 if self.round_number<=Constants.part1_rounds: p2.payoff = (Constants.endowment - p2.contribution) + individual_share2 else: p2.payoff = (Constants.endowment + p2.contribution) - individual_share2 if self.round_number<=Constants.part1_rounds: p3.payoff = (Constants.endowment - p3.contribution) + individual_share3 else: p3.payoff = (Constants.endowment + p3.contribution) - individual_share3 if self.round_number<=Constants.part1_rounds: p4.payoff = (Constants.endowment - p4.contribution) + individual_share4 else: p4.payoff = (Constants.endowment + p4.contribution) - individual_share4 class Player(BasePlayer): contribution = models.CurrencyField(doc='The amount contributed by the player', max=Constants.endowment, min=0) Q1groupmembers = models.StringField(choices=[['Yes', 'Yes'], ['No', 'No']], label='1. Will you know who the other members of your group are?', widget=widgets.RadioSelect) Q2nosingroup = models.StringField(choices=[['1', '1'], ['2', '2'], ['3', '3'], ['4', '4'], ['5', '5']], label='2. Including yourself, how many people are in your group?', widget=widgets.RadioSelect) Q4pointsgiven = models.StringField(choices=[['1', '1'], ['5', '5'], ['10', '10'], ['15', '15'], ['20', '20']], label='4. How many points are you given at the start of each period?', widget=widgets.RadioSelect) Q5carryover = models.StringField(choices=[['Yes', 'Yes'], ['No', 'No']], label='5. Will your uncontributed points carry over from one period to the next?', widget=widgets.RadioSelect) Q6newgroup = models.StringField(choices=[['Yes', 'Yes'], ['No', 'No']], label='1. Will you now be in a new group of people?', widget=widgets.RadioSelect) Q7addperiods = models.StringField(blank=True, choices=[['1', '1'], ['5', '5'], ['10', '10'], ['15', '15'], ['20', '20']], label='2. How many additional periods will there be?', widget=widgets.RadioSelect) Q8beta = models.StringField(choices=[['Yes', 'Yes'], ['No', 'No']], label='3. Will your β for this part be any different from your β in the previous part?', widget=widgets.RadioSelect) Q3periods = models.StringField(choices=[['1', '1'], ['5', '5'], ['10', '10'], ['15', '15'], ['20', '20']], label='3. How many periods will there be?', widget=widgets.RadioSelect) Q9indcon = models.StringField(choices=[['Added', 'Added'], ['Subtracted', 'Subtracted']], label='4. Will your contribution to the POOL will be added or subtracted from your earnings?', widget=widgets.RadioSelect) Q10groupcon = models.StringField(blank=True, choices=[['Added', 'Added'], ['Subtracted', 'Subtracted']], label='5. Will the total GROUP contribution to the POOL be added or subtracted from your earnings?', widget=widgets.RadioSelect) def role(self): if self.id_in_group == 1: return 'Person A (β = 0.30)' if self.id_in_group == 2: return 'Person B (β = 0.40)' if self.id_in_group == 3: return 'Person C (β = 0.50)' if self.id_in_group == 4: return 'Person D (β = 1.20)'