from otree.api import ( models, widgets, BaseConstants, BaseSubsession, BaseGroup, BasePlayer, Currency as c, currency_range ) import csv import xlrd # for reading XLS-files author = 'Dr. Jana Freundt & Leander Kopp' doc = """ This app reads 2 lotteries from a CSV-file and exports the decision. A prototype_Part2 app that reads its questions from a spreadsheet (see lotteries.csv in this directory). There is 1 decision per page; the number of pages in the game is determined by the number of decisions in the CSV. """ class Constants(BaseConstants): name_in_url = 'Part2_WTP_DOSE' players_per_group = None ############ LANGUAGE SETTINGS # 1: english, 2:german, 3:french..... language_code=1 ############ DEFINE CURRENCY, XRs AND LOTTERYSCALING ### # define displayed currency currency='points' #currency='CHF' currency_real='£' # define exchange rate 1 ECU = xxx $ = xxx CHF XR = 1200 # define scaling of lottery scale = 1 FixedPointsType1 = 2000 payoff_part3 = 1500 ######################################################## ############ DEFINE SHOWUPFEE showup_fee =2 #read & store all prices #with open('Part2_WTP_DOSE/prices.csv') as questions_file: # questions = list(csv.DictReader(questions_file)) #with open('Part2_WTP_DOSE/prices_dez2020.csv') as questions_file: # questions = list(csv.DictReader(questions_file)) with open('Part2_WTP_DOSE/prices.csv') as decisiontree_file: questions = list(csv.DictReader(decisiontree_file)) #with open('Part2_WTP_DOSE/prices_800.csv') as decisiontree_file: # questions = list(csv.DictReader(decisiontree_file)) #tree = ("Part2_WTP_DOSE/decisiontree_WTP.xlsx") #tree = ("Part2_WTP_DOSE/decisiontree_WTP_spicy_prolific3.xlsx") #tree = ("Part2_WTP_DOSE/decisiontree_WTP_dez2020.xlsx") #tree = ("Part2_WTP_DOSE/decisiontree_WTP_feb2021.xlsx") #tree = ("Part2_WTP_DOSE/decisiontree_WTP_10rounds_1-15mu_5random_600points.xlsx") tree = ("Part2_WTP_DOSE/WTP_tree.xlsx") #tree = ("Part2_WTP_DOSE/decisiontree_WTP_nov21.xlsx") # To open Workbook wb = xlrd.open_workbook(tree) sheet = wb.sheet_by_index(0) # Get for every stage all optimal prices (row,column) #num_rounds = len(questions) #num_rounds = 10 # 10 rounds for DOSE #num_rounds = 8 # 8 rounds for DOSE #num_rounds = 9 # 9 rounds for DOSE (prolific) num_rounds = 10 # 10 rounds for DOSE (prolific) num_pages_survey=5 # prepare numbers for going along the binary decision tree ### EXPLANATIONS: The horizontal decision tree is a 1024x10 matrix. ### The first stage is located at row 512 in column 1 ### The price information for the 2nd stage are located at row 512+256 and 512-256 and column 2 and so on. (see shift-numbers) #shift=[256,128,64,32,16,8,4,2,1] #shift=[64,32,16,8,4,2,1] # for prolific: 9 rounds #shift=[128,64,32,16,8,4,2,1] shift=[256,128,64,32,16,8,4,2,1] class Subsession(BaseSubsession): def creating_session(self): if self.round_number == 1: self.session.vars['questions'] = Constants.questions.copy() class Group(BaseGroup): pass class Player(BasePlayer): current_page = models.IntegerField(initial=0) # Define B-Option variables optionB_high = models.FloatField() optionB_low = models.FloatField() round_to_nearest_optionB_low=models.FloatField() # Define A-Option variables optionA_high = models.FloatField() optionA_low = models.FloatField() ######################################### #### Willingness-to-pay for a decision right --> Our primary variable of interest WTP = models.FloatField() #### Choice consistency for WTP DOSE choice_consistency = models.FloatField() #### payoff variable payoff_part2 = models.FloatField() #### selected round for payoff payoffrelevant_round_part2 = models.IntegerField() Payoff_Participant_3_selected_round = models.FloatField() Payoff_Participant_4_selected_round = models.FloatField() #### selected round for payoff (including high and low payoffs of this lottery) payoffrelevant_round_part1 = models.IntegerField() #### Variables for moving in the decision tree optimal_price_index = models.IntegerField() tree_row = models.IntegerField(initial=512) # set the initial row of the optimal price from the binary tree #tree_row = models.IntegerField(initial=128) # set the initial row of the optimal price from the binary tree #tree_row = models.IntegerField(initial=256) # set the initial row of the optimal price from the binary tree #tree_row = models.IntegerField(initial=512) # set the initial row of the optimal price from the binary tree #### price variable for current round current_price = models.FloatField() ######################################### # Define Choice variable: This variable stores whether current_price was chosen to be paid or not (in each round) # (1=autonomy or 0=delegation) pricechoice = models.IntegerField() # Define Choice variable: This variable stores the lottery choice in case of autonomy optionchoice_auto = models.IntegerField() ########## DEFINE CONTROL QUESTION VARIABLES ### ControlQuestion1 = models.IntegerField() ControlQuestion2 = models.IntegerField() ControlQuestion3 = models.IntegerField() ControlQuestion4 = models.IntegerField() # counter for control questions counterWrong = models.IntegerField(initial=0) ################################################ #### Variables from Part 1 (other than lottery information) FixedPointsType1 = models.FloatField() optionchoice_part1 = models.IntegerField() Payoff_Participant_1_selected_round = models.FloatField() Payoff_Participant_2_selected_round = models.FloatField() #### Other payoff-variables final_payoff = models.FloatField() final_payoff_converted = models.FloatField() payoff_part1_converted = models.FloatField() payoff_part2_converted = models.FloatField() payoff_plus_participation_fee=models.FloatField() ### delegation variable --> shows whether delegation or autonomy has been implemented by RLIM delegation = models.BooleanField() #################################################################################################################### ########################## PROLIFIC ONLY (REDUCED SURVEY + FEEDBACK) ############################################### ##### GSES GSE1 = models.FloatField() # 0: not at all, 1: very true GSE2 = models.FloatField() # 0: not at all, 1: very true GSE3 = models.FloatField() # 0: not at all, 1: very true GSE4 = models.FloatField() # 0: not at all, 1: very true GSE5 = models.FloatField() # 0: not at all, 1: very true GSE6 = models.FloatField() # 0: not at all, 1: very true GSE7 = models.FloatField() # 0: not at all, 1: very true GSE8 = models.FloatField() # 0: not at all, 1: very true GSE9 = models.FloatField() # 0: not at all, 1: very true GSE10 = models.FloatField() # 0: not at all, 1: very true ########## ##### IAF bigfive1 = models.FloatField() bigfive2 = models.FloatField() bigfive3 = models.FloatField() bigfive4 = models.FloatField() bigfive5 = models.FloatField() ###### WORK politics1 = models.FloatField() politics2 = models.FloatField() politics3 = models.FloatField() politics4 = models.FloatField() politics5 = models.FloatField() politics6 = models.FloatField() politics7 = models.FloatField() politics8 = models.FloatField() politics9 = models.FloatField() politics10 = models.FloatField() SocialDominance1 = models.FloatField() SocialDominance2 = models.FloatField() SocialDominance3 = models.FloatField() SocialDominance4 = models.FloatField() SocialDominance5 = models.FloatField() SocialDominance6 = models.FloatField() SocialDominance7 = models.FloatField() SocialDominance8 = models.FloatField() trust = models.FloatField() luck = models.FloatField() ##################### Attentionchecks ############################################################################## attentioncheck1 = models.FloatField() attentioncheck2 = models.FloatField() attentioncheck3 = models.FloatField() #################################################################################################################### CultureOrientation1= models.FloatField() CultureOrientation2= models.FloatField() CultureOrientation3= models.FloatField() CultureOrientation4= models.FloatField() CultureOrientation5= models.FloatField() CultureOrientation6= models.FloatField() CultureOrientation7= models.FloatField() CultureOrientation8= models.FloatField() CultureOrientation9= models.FloatField() CultureOrientation10= models.FloatField() CultureOrientation11= models.FloatField() CultureOrientation12= models.FloatField() CultureOrientation13= models.FloatField() CultureOrientation14= models.FloatField() CultureOrientation15= models.FloatField() CultureOrientation16= models.FloatField() Control1 = models.FloatField() Control2 = models.FloatField() Control3 = models.FloatField() Control4 = models.FloatField() Control5 = models.FloatField() Control6 = models.FloatField() Control7 = models.FloatField() Control8 = models.FloatField() Control9 = models.FloatField() Control10 = models.FloatField() Control11 = models.FloatField() Control12 = models.FloatField() Control13 = models.FloatField() Control14 = models.FloatField() Control15 = models.FloatField() Control16 = models.FloatField() Control17 = models.FloatField() Control18 = models.FloatField() ##################### Exclusion #################################################################################### exclusion = models.IntegerField() ######################### END OF PROLIFIC ONLY ##################################################################### #################################################################################################################### # tab switches & focus-/unfocus-time tab_intro_title_part2 = models.IntegerField() tab_general_part2 = models.IntegerField() tab_desc_options_part2 = models.IntegerField() tab_desc_choice_part2 = models.IntegerField() tab_desc_rlim_part2 = models.IntegerField() tab_pre_question_part2 = models.IntegerField() tab_pre_decision_part2 = models.IntegerField() tab_question_part2 = models.IntegerField() tab_self_part2 = models.IntegerField() tab_delegation_part2 = models.IntegerField() tab_payoff_part2 = models.IntegerField() # tab switches & focus-/unfocus-time focus_intro_title_part2 = models.FloatField() focus_general_part2 = models.FloatField() focus_desc_options_part2 = models.FloatField() focus_desc_choice_part2 = models.FloatField() focus_desc_rlim_part2 = models.FloatField() focus_pre_question_part2 = models.FloatField() focus_pre_decision_part2 = models.FloatField() focus_question_part2 = models.FloatField() focus_self_part2 = models.FloatField() focus_delegation_part2 = models.FloatField() focus_payoff_part2 = models.FloatField() # tab switches & focus-/unfocus-time totaltime_intro_title_part2 = models.FloatField() totaltime_general_part2 = models.FloatField() totaltime_desc_options_part2 = models.FloatField() totaltime_desc_choice_part2 = models.FloatField() totaltime_desc_rlim_part2 = models.FloatField() totaltime_pre_question_part2 = models.FloatField() totaltime_pre_decision_part2 = models.FloatField() totaltime_question_part2 = models.FloatField() totaltime_self_part2 = models.FloatField() totaltime_delegation_part2 = models.FloatField() totaltime_payoff_part2 = models.FloatField() age = models.IntegerField(choices=range(18,99), verbose_name="") gender = models.IntegerField(choices=[[1, 'Female'], [2, 'Male'], [3, 'Other'], [4, 'Prefer not to say']], verbose_name="", widget=widgets.RadioSelect) income = models.IntegerField(choices=[[1, 'Less than £10000'], [2, '£10000-£20000'], [3, '£20000-£30000'],[4, '£40000-£50000'],[5, '£50000-£60000'],[6, '£60000-£70000'], [7, '£70000-£80000'], [8, '£80000-£90000'], [9, '£90000-£100000'], [10, '£100000-£110000'], [11, '£110000-£120000'], [12, '£120000-£130000'], [13, '£130000-£140000'], [14, '£140000-£150000'], [15, 'More than £150000']], verbose_name="") maritalstatus = models.IntegerField(choices=[[4, 'Divorced'],[1, 'Married'], [2, 'Single'], [3, 'Widowed']], verbose_name="", widget=widgets.RadioSelect) employmentstatus = models.IntegerField(choices=[[1, 'Employed'],[6, 'Retired'],[2, 'Self-employed'],[5, 'Stay-at-home mother/father'],[4, 'Student'],[3, 'Unemployed']],verbose_name='') education = models.IntegerField(choices=[[1, 'Less than High School'], [2, 'High School Diploma'], [3, 'Some college or associate degree'], [4, '4-year college degree'], [5, 'More than 4-year college degree']], verbose_name="") religious = models.IntegerField(choices=[[1, 'Yes'],[0, 'No'],[2, 'Prefer not to answer']], verbose_name="", widget=widgets.RadioSelect)