File indexing completed on 2024-04-28 15:07:57
0001 /* GCompris - money.js 0002 * 0003 * SPDX-FileCopyrightText: 2014 Bruno Coudoin 0004 * 0005 * Authors: 0006 * Bruno Coudoin <bruno.coudoin@gcompris.net> (GTK+ version) 0007 * Bruno Coudoin <bruno.coudoin@gcompris.net> (Qt Quick port) 0008 * 0009 * SPDX-License-Identifier: GPL-3.0-or-later 0010 */ 0011 .pragma library 0012 .import "qrc:/gcompris/src/core/core.js" as Core 0013 .import GCompris 1.0 as GCompris 0014 .import "moneyConstants.js" as MoneyConstants 0015 0016 var url = "qrc:/gcompris/src/activities/money/resource/" 0017 0018 // We create 3 prices categories to make the game more realistic. 0019 // List of images to use in the game (cheap objects) 0020 0021 var numberOfLevel 0022 var dataset 0023 var items 0024 var centsMode 0025 var backMode 0026 var priceTotal 0027 0028 function start(items_, datasetName) { 0029 items = items_ 0030 dataset = items.levels 0031 switch(datasetName) { 0032 case "WITHOUT_CENTS": 0033 centsMode = false 0034 backMode = false 0035 break 0036 case "WITH_CENTS": 0037 centsMode = true 0038 backMode = false 0039 break 0040 case "BACK_WITHOUT_CENTS": 0041 centsMode = false 0042 backMode = true 0043 break 0044 case "BACK_WITH_CENTS": 0045 centsMode = true 0046 backMode = true 0047 break 0048 } 0049 numberOfLevel = dataset.length 0050 items.currentLevel = Core.getInitialLevel(numberOfLevel) 0051 initLevel() 0052 } 0053 0054 function stop() { 0055 } 0056 0057 function getCoinCount (pocket) { 0058 var count = 0 0059 for(var i = 0; i < pocket.length; i++) { 0060 if(pocket[i].val <= 2) 0061 count++ 0062 } 0063 return count; 0064 } 0065 0066 function initLevel() { 0067 items.answerModel.clear() 0068 items.pocketModel.clear() 0069 0070 var data = dataset[items.currentLevel] 0071 var pocket = Core.shuffle(data.pocket) 0072 var coinCount = getCoinCount(pocket) 0073 items.moneyCount = data.pocket.length 0074 0075 for(var i = 0; i < pocket.length; i++) 0076 items.pocketModel.append(pocket[i]) 0077 0078 var locale = GCompris.ApplicationSettings.locale 0079 if(locale == "system") { 0080 locale = Qt.locale().name == "C" ? "en_US" : Qt.locale().name 0081 } 0082 // fill up the store in a random way 0083 var storeModel = new Array() 0084 // the real minimum price should always be at least the number of items 0085 // in non cents mode, to always have positive prices 0086 // else it could happen to have a price of 1 and 3 items to sell... 0087 var realMinPrice = Math.max(data.minPrice, data.numberOfItem) 0088 priceTotal = Math.floor(realMinPrice + Math.random() * 0089 (data.maxPrice - realMinPrice)) 0090 var priceCounter = 0 0091 for(var i = 0; i < data.numberOfItem; i++) { 0092 var price 0093 if(i < data.numberOfItem - 1) { 0094 var delta = (centsMode ? 0 : 1) 0095 // Calc a random price for each item based on the previous prices 0096 price = Math.floor(delta + 0097 Math.random() * 0098 (2 * (priceTotal - priceCounter) / data.numberOfItem - delta)) 0099 } 0100 else { 0101 // Put the remaining missing price on the last item 0102 price = priceTotal - priceCounter 0103 // If the price is 0, we recompute it to be between 1 and the remaining values 0104 // between the actual total price and the max price possible 0105 if(price == 0) { 0106 price = delta + Math.floor(Math.random() * (data.maxPrice - priceTotal - delta)); 0107 priceTotal += price; 0108 } 0109 } 0110 var cents = 0 0111 if(centsMode) { 0112 if(items.currentLevel === 0) 0113 cents += 0.10 + Math.floor(Math.random() * 9) / 10 0114 else 0115 cents += 0.01 + Math.floor(Math.random() * 99) / 100 0116 0117 // To be sure that the sums of the cents will never go higher than the 0118 // maxPrice, we remove them instead of adding them if the item price 0119 // is above 1 0120 if(price > 1) { 0121 cents = cents - 1 0122 } 0123 priceTotal += cents 0124 price += cents 0125 } 0126 0127 var priceText = Core.convertNumberToLocaleCurrencyString(Number(price), locale) 0128 if(!centsMode) { 0129 // Strip floating part 0130 priceText = priceText.replace((/[,.]00/), "") 0131 } 0132 0133 storeModel.push({img: getRandomObject(price), 0134 price: priceText}) 0135 priceCounter += price 0136 } 0137 items.store.model = storeModel 0138 0139 if(!backMode) { 0140 items.instructions.text = 0141 qsTr("Click on the coins or on the notes at the bottom of the screen to pay." + 0142 " If you want to remove a coin or a note, click on it on the upper screen area.") 0143 } else { 0144 var availableCurrency = pocket.slice() 0145 availableCurrency.sort(function sort(a, b) { return b.val - a.val }); 0146 var amountToBeCovered = data.paid 0147 var tuxMoney = [] 0148 while(amountToBeCovered > 0) { 0149 var maxPossible = 0 0150 for(var i = 0; i < availableCurrency.length; i++) { 0151 if((availableCurrency[i].val <= amountToBeCovered)) { 0152 maxPossible = availableCurrency[i] 0153 break; 0154 } 0155 } 0156 tuxMoney.push(maxPossible) 0157 amountToBeCovered -= maxPossible.val; 0158 } 0159 items.tuxMoney.model = tuxMoney 0160 0161 var tuxTotal = 0 0162 for(var i=0; i < tuxMoney.length; i++) 0163 tuxTotal += tuxMoney[i].val 0164 0165 var priceText = Core.convertNumberToLocaleCurrencyString(Number(tuxTotal), locale) 0166 if(!centsMode) { 0167 // Strip floating part 0168 priceText = priceText.replace((/.00/), "") 0169 } 0170 0171 /* The money sign is inserted based on the current locale */ 0172 items.instructions.text = qsTr("Tux just bought some items in your shop.\n" + 0173 "He gives you %1, please give back his change.") 0174 .arg(priceText) 0175 } 0176 0177 //Keyboard reset 0178 items.itemIndex = -1 0179 items.selectedArea = items.pocket 0180 0181 } 0182 0183 // Given a price return a random object 0184 function getRandomObject(price) { 0185 var objectList 0186 if(price < 5) 0187 objectList = MoneyConstants.cheapObjects 0188 else if(price < 10) 0189 objectList = MoneyConstants.normalObjects 0190 else 0191 objectList = MoneyConstants.expensiveObjects 0192 0193 return objectList[Math.floor(Math.random() * objectList.length)] 0194 } 0195 0196 function checkAnswer() { 0197 var paid = 0 0198 for (var i = 0; i < items.answerModel.count; ++i) 0199 paid += items.answerModel.get(i).val 0200 0201 paid = paid.toFixed(2) 0202 0203 if(!backMode) { 0204 if(paid === priceTotal.toFixed(2)) 0205 items.bonus.good("flower") 0206 } else { 0207 if(paid === (dataset[items.currentLevel].paid - priceTotal).toFixed(2)) 0208 items.bonus.good("flower") 0209 } 0210 } 0211 0212 function pay(index) { 0213 items.audioEffects.play(url + "money1.wav") 0214 // Add it to the anwser 0215 items.answerModel.append(items.pocketModel.get(index)) 0216 0217 // Remove it from the pocket 0218 items.pocketModel.remove(index, 1) 0219 0220 checkAnswer() 0221 } 0222 0223 function unpay(index) { 0224 items.audioEffects.play(url + "money2.wav") 0225 // Add it to the pocket 0226 items.pocketModel.append(items.answerModel.get(index)) 0227 0228 // Remove it from the Answer 0229 items.answerModel.remove(index, 1) 0230 0231 checkAnswer() 0232 } 0233 0234 function nextLevel() { 0235 items.currentLevel = Core.getNextLevel(items.currentLevel, numberOfLevel); 0236 initLevel(); 0237 } 0238 0239 function previousLevel() { 0240 items.currentLevel = Core.getPreviousLevel(items.currentLevel, numberOfLevel); 0241 initLevel(); 0242 }