721 lines
30 KiB
JavaScript
721 lines
30 KiB
JavaScript
|
// Define humanTime function
|
||
|
function humanTime (time) {
|
||
|
var days = (((Math.abs(time)/1000)/60)/60)/24;
|
||
|
var hours = (days%1)*24;
|
||
|
var minutes = (hours%1)*60;
|
||
|
var seconds = (minutes%1)*60;
|
||
|
return (1 < days ? Math.floor(days)+"D " : "") + (1 < hours ? Math.floor(hours).toString().padStart(2,"0")+":": "") + ( 1 < minutes ? Math.floor(minutes).toString().padStart(2,"0")+":" : "")+ Math.floor(seconds).toString().padStart(2,"0") ;
|
||
|
}
|
||
|
// Define RNA validator function
|
||
|
function validateRna (rna) {
|
||
|
rna = "object" == typeof rna ? rna : {};
|
||
|
rna.healthMax = "number" == typeof rna.healthMax ? rna.healthMax : Math.floor(Math.random()*25)+75;
|
||
|
rna.stomachMax = "number" == typeof rna.stomachMax ? rna.stomachMax : Math.floor(Math.random()*25)+25;
|
||
|
rna.hydrationMax = "number" == typeof rna.hydrationMax ? rna.hydrationMax : Math.floor(Math.random()*90)+10;
|
||
|
rna.nurishmentMax = "number" == typeof rna.nurishmentMax ? rna.nurishmentMax : Math.floor(Math.random()*90)+10;
|
||
|
rna.thirstRate = "number" == typeof rna.thirstRate ? rna.thirstRate : 300000;
|
||
|
rna.hungerRate = "number" == typeof rna.hungerRate ? rna.hungerRate : 300000;
|
||
|
return rna;
|
||
|
}
|
||
|
// Define RNA to DNA function
|
||
|
function rna2dna (motherRna,fatherRna) {
|
||
|
return dna = [validateRna(motherRna),validateRna(fatherRna)];
|
||
|
}
|
||
|
// Define DNA to RNA function
|
||
|
function dna2rna (dna) {
|
||
|
var rna = validateRna({
|
||
|
"healthMax":dna[Math.floor(Math.random())].healthMax,
|
||
|
"stomachMax":dna[Math.floor(Math.random())].stomachMax,
|
||
|
"hydrationMax":dna[Math.floor(Math.random())].hydrationMax,
|
||
|
"nurishmentMax":dna[Math.floor(Math.random())].nurishmentMax,
|
||
|
"thirstRate":dna[Math.floor(Math.random())].thirstRate,
|
||
|
"hungerRate":dna[Math.floor(Math.random())].hungerRate
|
||
|
});
|
||
|
return rna;
|
||
|
}
|
||
|
// Define item class
|
||
|
class item {
|
||
|
constructor (itemDef) {
|
||
|
this.id = -1;
|
||
|
this.name = "Azathoth";
|
||
|
this.desc = "Unknowable";
|
||
|
this.countInc = 1;
|
||
|
this.action = function () { return 0; };
|
||
|
if ("object" == typeof itemDef) {
|
||
|
if ("number" == typeof itemDef.id) { this.id = itemDef.id; }
|
||
|
if ("string" == typeof itemDef.name) { this.name = itemDef.name; }
|
||
|
if ("string" == typeof itemDef.desc) { this.desc = itemDef.desc; }
|
||
|
if ("number" == typeof itemDef.countInc) { this.countInc = itemDef.countInc; }
|
||
|
if ("function" == typeof itemDef.action) { this.action = itemDef.action; }
|
||
|
}
|
||
|
|
||
|
}
|
||
|
};
|
||
|
// Define inventory class
|
||
|
class inventory {
|
||
|
constructor () {
|
||
|
var me = this;
|
||
|
this.update = false;
|
||
|
this.contents = [];
|
||
|
this.addItem = function (itemID,amount,overrides) {
|
||
|
if ("number" != typeof amount) { amount = 1;}
|
||
|
var exsistingItem = me.contents.findIndex( function (item) { return item.id == itemID; });
|
||
|
if (exsistingItem >= 0) {
|
||
|
me.contents[exsistingItem].count += amount;
|
||
|
} else {
|
||
|
me.contents.push(new item(petGame.itemDB[itemID]));
|
||
|
me.contents[me.contents.length-1].count = amount;
|
||
|
if ("object" == typeof overrides) {
|
||
|
if ("string" == typeof overrides.name) { me.contents[me.contents.length-1].name = overrides.name; }
|
||
|
if ("string" == typeof overrides.desc) { me.contents[me.contents.length-1].desc = overrides.desc; }
|
||
|
if ("number" == typeof overrides.countInc) { me.contents[me.contents.length-1].countInc = overrides.countInc; }
|
||
|
if ("function" == typeof overrides.action) { me.contents[me.contents.length-1].action = overrides.action; }
|
||
|
}
|
||
|
}
|
||
|
me.update = true;
|
||
|
};
|
||
|
|
||
|
this.useItem = function (itemIndex,actionBool) {
|
||
|
if (actionBool) { me.contents[itemIndex].action(); }
|
||
|
me.contents[itemIndex].count -= me.contents[itemIndex].countInc;
|
||
|
if (me.contents[itemIndex].count <= 0) {
|
||
|
me.contents.splice(itemIndex,1);
|
||
|
}
|
||
|
me.update = true;
|
||
|
};
|
||
|
|
||
|
this.getBasic = function (info) {
|
||
|
return me.contents.map( function (item) { return item[info]; } );
|
||
|
};
|
||
|
|
||
|
this.getEssentials = function () {
|
||
|
return me.contents.map( function (item) { return {"id":item.id,"count":item.count}; });
|
||
|
};
|
||
|
|
||
|
}
|
||
|
};
|
||
|
// Define Pet class
|
||
|
class pet {
|
||
|
constructor (mother,father) {
|
||
|
var me = this;
|
||
|
this.dna = rna2dna(mother,father);
|
||
|
this.activeRna = dna2rna(this.dna);
|
||
|
this.birth = performance.now();
|
||
|
this.healthMax = this.activeRna.healthMax + (Math.floor(Math.random()*20)-10);
|
||
|
this.stomachMax = this.activeRna.stomachMax + (Math.floor(Math.random()*10)-5);
|
||
|
this.hydrationMax = this.activeRna.hydrationMax + (Math.floor(Math.random()*10)-5);
|
||
|
this.thirstRate = this.activeRna.thirstRate + (Math.floor(Math.random()*120000)-60000);
|
||
|
this.nurishmentMax = this.activeRna.nurishmentMax + (Math.floor(Math.random()*10)-5);
|
||
|
this.hungerRate = this.activeRna.hungerRate + (Math.floor(Math.random()*120000)-60000);
|
||
|
this.health = this.healthMax;
|
||
|
this.stomach = 0;
|
||
|
this.hydration = this.hydrationMax;
|
||
|
this.nurishment = this.nurishmentMax;
|
||
|
this.affection = 0;
|
||
|
this.mood = 0;
|
||
|
this.name = "pet"+Math.floor(this.birth);
|
||
|
this.gender = Math.round(Math.random());
|
||
|
this.ageStart = this.birth.valueOf();
|
||
|
this.age = 0;
|
||
|
this.dirty = 0;
|
||
|
this.lastPoop = this.birth;
|
||
|
this.busyUntil = this.birth;
|
||
|
this.currentAction = null;
|
||
|
this.dead = false;
|
||
|
this.tick = function (deltaT) {
|
||
|
var oldMood = me.mood;
|
||
|
me.mood = 0;
|
||
|
me.hydration -= deltaT/me.thirstRate;
|
||
|
me.nurishment -= deltaT/me.hungerRate;
|
||
|
|
||
|
if (me.hydrationMax / 2 >= me.hydration) { //Attempt to drink
|
||
|
me.takeAction(function () { return me.intake("water"); }, 5000, "drinking",true);
|
||
|
}
|
||
|
if (me.nurishmentMax / 2 >= me.nurishment) { //Attempt to eat
|
||
|
me.takeAction(function () { return me.intake("food"); }, 5000, "eating",true);
|
||
|
}
|
||
|
|
||
|
me.mood += me.hydration < 0 ? me.hydration : 0;
|
||
|
me.health += me.hydration < 0 ? me.hydration : 0;
|
||
|
me.hydration = me.hydration > 0 ? me.hydration : 0;
|
||
|
|
||
|
me.mood += me.nurishment < 0 ? me.nurishment : 0;
|
||
|
me.health += me.nurishment < 0 ? me.nurishment : 0;
|
||
|
me.nurishment = me.nurishment > 0 ? me.nurishment : 0;
|
||
|
|
||
|
var poops = Math.floor(me.stomach / 10);
|
||
|
if (poops) {
|
||
|
var time = Math.floor((performance.now() - me.lastPoop) / 25000);
|
||
|
if (time > poops) {
|
||
|
me.dirty += poops/10;
|
||
|
me.stomach -= 10 * poops;
|
||
|
me.lastPoop = performance.now();
|
||
|
petGame.gui.player.pets.update = true;
|
||
|
} else {
|
||
|
me.dirty += time/10;
|
||
|
me.stomach -= 10 * time;
|
||
|
}
|
||
|
}
|
||
|
if (0 >= me.stomach) { me.stomach = 0; }
|
||
|
|
||
|
me.mood -= me.dirty*(deltaT/30000);
|
||
|
|
||
|
me.affection += ((oldMood + me.mood)/2)*(deltaT/30000);
|
||
|
|
||
|
if (performance.now() >= me.ageStart+(Math.pow(me.age+1,2)*1800000)) {
|
||
|
me.age++;
|
||
|
me.ageStart = performance.now();
|
||
|
petGame.log.messageAdd(me.name+" has grown!",2);
|
||
|
}
|
||
|
|
||
|
if (10 < me.age) { // Death from old age
|
||
|
me.dead = true;
|
||
|
me.tick = function () {return 0;};
|
||
|
petGame.log.messageAdd(me.name+" has died of old age.",2);
|
||
|
}
|
||
|
|
||
|
if (0 >= me.health) { //Death from health loss
|
||
|
me.dead = true;
|
||
|
me.tick = function () { return 0; };
|
||
|
petGame.log.messageAdd(me.name+" has died from health loss", 2);
|
||
|
}
|
||
|
|
||
|
if ((me.busyUntil <= performance.now()) && ("string" == typeof me.currentAction)) {
|
||
|
petGame.log.messageAdd(me.name+" has finished "+me.currentAction);
|
||
|
me.currentAction = null;
|
||
|
petGame.gui.player.pets.update = true;
|
||
|
if (true == me.selected) { petGame.player.actions.update = true; }
|
||
|
}
|
||
|
};
|
||
|
|
||
|
this.intake = function (type) {
|
||
|
if (("string" != typeof type) || ("water" != type && "food" != type)) { console.error("intake: invalid type given to intake: "+type); return 0;}
|
||
|
var max = "water" == type ? "hydrationMax" : "nurishmentMax";
|
||
|
var current = "water" == type ? "hydration" : "nurishment";
|
||
|
|
||
|
var def = me[max] - Math.ceil(me[current]);
|
||
|
var sdef = me.stomachMax - Math.ceil(me.stomach);
|
||
|
var amount = def <= sdef ? def : def - (def - sdef);
|
||
|
if (petGame.player[type] > 0) {
|
||
|
if (petGame.player[type] >= amount) {
|
||
|
petGame.player[type] -= amount;
|
||
|
me[current] += amount;
|
||
|
me.stomach += amount;
|
||
|
return [2, amount];
|
||
|
} else {
|
||
|
me[current] += petGame.player[type];
|
||
|
me.stomach += petGame.player[type];
|
||
|
petGame.player[type] = 0;
|
||
|
return 3;
|
||
|
}
|
||
|
} else {
|
||
|
return 4;
|
||
|
}
|
||
|
};
|
||
|
|
||
|
this.takeAction = function (action, actionTime,actionString,silent) {
|
||
|
if ("function" != typeof action) { console.error("given action is not a function"); return 0; }
|
||
|
if ("number" != typeof actionTime) { actionTime = 10000; }
|
||
|
if ("string" != typeof actionString) { actionString = "something"; }
|
||
|
console.log(performance.now()+"-"+me.busyUntil);
|
||
|
petGame.gui.player.pets.update = true;
|
||
|
if (0 <= performance.now() - me.busyUntil){
|
||
|
var result = action();
|
||
|
if (0 == result) { return 0; }
|
||
|
petGame.log.messageAdd(me.name+" began "+actionString);
|
||
|
me.currentAction = actionString;
|
||
|
me.busyUntil = performance.now()+actionTime;
|
||
|
if (true == me.selected) { petGame.player.actions.update = true; }
|
||
|
return result;
|
||
|
} else {
|
||
|
if (silent) {} else { petGame.log.messageAdd(me.name+" is busy right now."); }
|
||
|
return 1;
|
||
|
}
|
||
|
|
||
|
};
|
||
|
|
||
|
this.feed = function () {
|
||
|
var result = me.takeAction(function () { return me.intake("food"); },10000,"eating");
|
||
|
if ("number" == typeof result) {
|
||
|
if (3 == result) { petGame.log.messageAdd("You fed "+me.name+" your remaining food."); }
|
||
|
if (4 == result) { petGame.log.messageAdd("You have no food to give "+me.name, 1); }
|
||
|
if (0 == result) { return console.error("Something went wrong");}
|
||
|
}
|
||
|
if ("object" == typeof result) {
|
||
|
if (2 == result[0]) { petGame.log.messageAdd("You fed "+me.name+" "+result[1]+" food."); }
|
||
|
}
|
||
|
return result;
|
||
|
};
|
||
|
|
||
|
this.water = function () {
|
||
|
var result = me.takeAction(function () { return me.intake("water"); },10000,"drinking");
|
||
|
if ("number" == typeof result) {
|
||
|
if (3 == result) { petGame.log.messageAdd("You gave "+me.name+" your remaining water."); }
|
||
|
if (4 == result) { petGame.log.messageAdd("You have no water to give "+me.name, 1); }
|
||
|
if (0 == result) { return console.error("Something went wrong");}
|
||
|
}
|
||
|
if ("object" == typeof result) {
|
||
|
if (2 == result[0]) { petGame.log.messageAdd("You gave "+me.name+" "+result[1]+" water."); }
|
||
|
}
|
||
|
return result;
|
||
|
};
|
||
|
|
||
|
this.play = function () {
|
||
|
var result = me.takeAction(function () {
|
||
|
me.mood+=50*(1+(function (a) {return a.length > 0 ? a.reduce(function (a,b) { return a + b;}) : 0})(petGame.player.inventory.contents.filter(function (item) { return (item.id == 4 || item.id == 5)}).map(function (item) { return item.count})));
|
||
|
return 2;
|
||
|
}, 10000, "playing");
|
||
|
return result;
|
||
|
};
|
||
|
|
||
|
this.sleep = function () {
|
||
|
var result = me.takeAction(function () {
|
||
|
var dif = me.healthMax - me.health;
|
||
|
if (20 <= dif) {
|
||
|
me.health += 20;
|
||
|
} else {
|
||
|
me.mood += (me.health+20)-me.healthMax;
|
||
|
me.health = me.healthMax;
|
||
|
}
|
||
|
return 2;
|
||
|
},30000,"sleeping");
|
||
|
return result;
|
||
|
};
|
||
|
|
||
|
this.walk = function () {
|
||
|
var result = me.takeAction(function () {
|
||
|
me.mood+=20;
|
||
|
me.health-=20;
|
||
|
if(25 >= Math.floor(Math.random()*100)) {
|
||
|
petGame.log.messageAdd("While out walking, "+me.name+" found something");
|
||
|
petGame.player.giveItem(5);
|
||
|
}
|
||
|
return 2;
|
||
|
},10000,"walking");
|
||
|
return result;
|
||
|
};
|
||
|
|
||
|
this.clean = function () {
|
||
|
var result = me.takeAction(function () { me.dirty = 0; me.mood+=10; return 2; },10000,"bathing");
|
||
|
return result;
|
||
|
};
|
||
|
|
||
|
this.rename = function () { me.name = window.prompt("What would you like to change "+me.name+"'s name to?",me.name)};
|
||
|
|
||
|
petGame.gui.player.pets.update = true;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// Define main game object and its imidiate children
|
||
|
window.petGame = {};
|
||
|
petGame.start = performance.now();
|
||
|
petGame.current = petGame.start;
|
||
|
petGame.player = {};
|
||
|
petGame.log = {};
|
||
|
petGame.market = {};
|
||
|
petGame.eventDB = [];
|
||
|
petGame.eventCountdown = 300000;
|
||
|
petGame.itemDB = [];
|
||
|
// Define player object and its children
|
||
|
petGame.player.inventory = new inventory();
|
||
|
petGame.player.pets = [];
|
||
|
petGame.player.water = 0;
|
||
|
petGame.player.food = 0;
|
||
|
petGame.player.coins = 0;
|
||
|
petGame.player.actions = {};
|
||
|
petGame.player.give = function (type,amount) {
|
||
|
if ("string" != typeof type) { return console.error("type must be string but was:"+(typeof type)); }
|
||
|
if ("number" != typeof amount) { return console.error("amount must be number but was:"+(typeof amount)); }
|
||
|
petGame.player[type] += amount;
|
||
|
}
|
||
|
petGame.player.giveItem = function (itemID,amount) {
|
||
|
petGame.player.inventory.addItem(itemID,amount);
|
||
|
}
|
||
|
petGame.gui = {};
|
||
|
// Define log object and its children
|
||
|
petGame.log.queue = [];
|
||
|
petGame.log.messageAdd = function (message, priority, life) {
|
||
|
if (petGame.log.queue.length >= 50) { petGame.log.queue.shift(); }
|
||
|
message = "string" == typeof message ? message : "No message proveded?";
|
||
|
priority = "number" == typeof priority ? priority : 0;
|
||
|
life = "number" == typeof life ? life : 600000;
|
||
|
petGame.log.queue.push({"message":message, "priority":priority, "life":performance.now()+life});
|
||
|
petGame.log.update = true;
|
||
|
}
|
||
|
petGame.log.clean = function () {
|
||
|
petGame.log.queue.forEach( function (message, index, queue) {
|
||
|
if (performance.now() > message.life) {
|
||
|
queue.splice(index,1);
|
||
|
petGame.log.update = true;
|
||
|
}
|
||
|
});
|
||
|
}
|
||
|
// Define market object and its children
|
||
|
petGame.market.exchangeRate = 1;
|
||
|
petGame.market.inventory = new inventory();
|
||
|
petGame.market.coins = 0;
|
||
|
petGame.market.addItem = function (itemID,amount,override) {
|
||
|
petGame.market.inventory.addItem(itemID,amount,override);
|
||
|
}
|
||
|
// Build eventDB database
|
||
|
petGame.eventDB = [
|
||
|
{"chance":90,"action":function () {
|
||
|
petGame.log.messageAdd("A stranger gives you some money, weird...");
|
||
|
petGame.player.give("coins",Math.floor(Math.random()*100));
|
||
|
}},
|
||
|
{"chance":3,"action":function () {
|
||
|
petGame.log.messageAdd("A strange new egg appeared in the market.");
|
||
|
petGame.market.addItem(3);;
|
||
|
}},
|
||
|
{"chance":10,"action":function () {
|
||
|
petGame.log.messageAdd("The market has more eggs!");
|
||
|
petGame.market.addItem(0,5);
|
||
|
}},
|
||
|
{"chance":40,"action":function () {
|
||
|
petGame.log.messageAdd("You find a toy on the ground, maybe your pets will have more fun playing now.");
|
||
|
petGame.player.giveItem(4);
|
||
|
}},
|
||
|
{"chance":30,"action":function () {
|
||
|
petGame.log.messageAdd("The market has more food and water!");
|
||
|
petGame.market.addItem(1,5);
|
||
|
petGame.market.addItem(2,5);
|
||
|
}},
|
||
|
{"chance":3,"action":function () {
|
||
|
petGame.log.messageAdd("The market has a Nexus for sale");
|
||
|
petGame.market.addItem(6,1);
|
||
|
}},
|
||
|
];
|
||
|
// Build itemDB database
|
||
|
petGame.itemDB = [
|
||
|
{"id":0,"name":"Egg","cost":300,"countInc":1,"desc":"This is a pet egg, when you use it, it will hatch into a new pet.","action": function () {
|
||
|
return petGame.player.pets.push(new pet());
|
||
|
}},
|
||
|
{"id":1,"name":"Water","cost":50,"countInc":1,"desc":"A package of water, use this to add more water to your supply.","action": function () {
|
||
|
return petGame.player.give("water",100);
|
||
|
}},
|
||
|
{"id":2,"name":"Food","cost":50,"countInc":1,"desc":"A package of food, use this to add more food to your supply.","action": function () {
|
||
|
return petGame.player.give("food",100);
|
||
|
}},
|
||
|
{"id":3,"name":"SEgg","cost":50000,"countInc":1,"desc":"This pet egg seems different than others, it seems stronger.","action": function () {
|
||
|
return petGame.player.pets.push(new pet({
|
||
|
"healthMax":200,
|
||
|
"stomachMax":200,
|
||
|
"nutritionMax":200,
|
||
|
"hydrationMax":200,
|
||
|
"hungerRate":12000000,
|
||
|
"thirstRate":12000000
|
||
|
},{
|
||
|
|
||
|
}));;
|
||
|
}},
|
||
|
{"id":4,"name":"Toy","cost":100,"countInc":0,"desc":"This is a pet toy, the more of them you have for your pets to play with, the more affection you will gain each time you play with your pets.","action": function () {
|
||
|
return petGame.log.messageAdd("It doesnt seem all that fun to you, but your pets sure enjoy it.");
|
||
|
}},
|
||
|
{"id":5,"name":"Treasure","cost":500,"countInc":1,"desc":"A buried treasure, sell it for more coins or keep it for more bonus affection from your pets when you play with them.","action": function () {
|
||
|
petGame.player.give("coins",500);
|
||
|
petGame.market.addItem(5);
|
||
|
return petGame.log.messageAdd("You have sold the treasure");
|
||
|
}},
|
||
|
{"id":6,"name":"Nexus","cost":1000,"countInc":1,"desc":"A nexus allows you to breed two pets of the opposite gender that are at least age 5.","action": function () {
|
||
|
if ((1 <= petGame.player.pets.filter(function (pet) {if ((1 == pet.gender) && (5 <= pet.age)) { return {"name":pet.name,"dna":pet.dna}; } else { return false; }}).length) && (1 <= petGame.player.pets.filter(function (pet) {if ((0 == pet.gender) && (5 <= pet.age)) { return {"name":pet.name,"dna":pet.dna}; } else { return false; }}).length)) {
|
||
|
popupDialog("breed","New Egg cross Unity System (N.E.X.U.S)",false,function (dialogRoot,container,args) {
|
||
|
container.innerHTML = args.content;
|
||
|
var father = elementPlace("#"+container.id, null, "nexus_father", "select");
|
||
|
args.malesOfAge.forEach(function (pet,index) {father.innerHTML += '<option value="'+index+'">'+pet.name+'</option>';});
|
||
|
var mother = elementPlace("#"+container.id,null, "nexus_mother", "select");
|
||
|
args.femalesOfAge.forEach(function (pet,index) {mother.innerHTML += '<option value="'+index+'">'+pet.name+'</option>';});
|
||
|
buttonAdd("#"+container.id,null,"Breed",function () {
|
||
|
if (("number" != typeof parseInt(father.value)) || ("number" != typeof parseInt(mother.value))) {
|
||
|
petGame.player.giveItem(6);
|
||
|
petGame.log.messageAdd("Your Nexus was not provided good information, try again or wait till later");
|
||
|
} else {
|
||
|
petGame.player.pets.push(new pet(dna2rna(args.malesOfAge[parseInt(father.value)].dna),dna2rna(args.femalesOfAge[parseInt(mother.value)].dna)));
|
||
|
}
|
||
|
dialogRoot.parentNode.removeChild(dialogRoot);
|
||
|
},"dialog_button","div");
|
||
|
buttonAdd("#"+container.id,null,"Cancel",function () {
|
||
|
petGame.player.giveItem(6);
|
||
|
dialogRoot.parentNode.removeChild(dialogRoot);
|
||
|
},"dialog_button","div");
|
||
|
},{
|
||
|
"content":"Please select the pets you wish to breed:",
|
||
|
"malesOfAge":petGame.player.pets.filter(function (pet) {if ((1 == pet.gender) && (5 <= pet.age)) { return {"name":pet.name,"dna":pet.dna}; } else { return false; }}),
|
||
|
"femalesOfAge":petGame.player.pets.filter(function (pet) {if ((0 == pet.gender) && (5 <= pet.age)) { return {"name":pet.name,"dna":pet.dna}; } else { return false; }})
|
||
|
});
|
||
|
} else {
|
||
|
petGame.log.messageAdd("You don't have enough pets of the right age or gender to use this...");
|
||
|
petGame.player.giveItem(6);
|
||
|
}
|
||
|
}},
|
||
|
];
|
||
|
// Define petGame.gui init function
|
||
|
petGame.gui.init = function () {
|
||
|
window.document.body.innerHTML = null;
|
||
|
petGame.gui.player = titledContainer("body","player",null,"div",null,"Player:");
|
||
|
petGame.gui.player.stats = titledContainer("#player","playerStats",null,"ul",null,"Stats:");
|
||
|
petGame.gui.player.stats.water = elementPlace("#playerStats",null,"playerStat water","li");
|
||
|
petGame.gui.player.stats.food = elementPlace("#playerStats",null,"playerStat food","li");
|
||
|
petGame.gui.player.stats.coins = elementPlace("#playerStats",null,"playerStat coins","li");
|
||
|
petGame.gui.player.inventory = titledContainer("#player","playerInv","inventory","ul",null,"Inventory:");
|
||
|
petGame.gui.player.actions = titledContainer("#player","playerActions","actions","ul",null,"Actions:");
|
||
|
petGame.gui.player.pets = titledContainer("#player","playerPets",null,"div",null,"Pets:");
|
||
|
petGame.gui.player.pets.update = true;
|
||
|
petGame.gui.info = elementPlace("body","info",null,"div");
|
||
|
petGame.gui.info.log = titledContainer("#info","infoLog",null,"ul",null,"Event Log:");
|
||
|
petGame.gui.info.market = titledContainer("#info","infoMarket","inventory","ul",null,"Market:");
|
||
|
}
|
||
|
// Define gui update function
|
||
|
petGame.gui.update = function () {
|
||
|
petGame.gui.player.stats.water.innerText = "Water: "+numberShorten(petGame.player.water);
|
||
|
petGame.gui.player.stats.food.innerText = "Food: "+numberShorten(petGame.player.food);
|
||
|
petGame.gui.player.stats.coins.innerText = "Coins: "+numberShorten(petGame.player.coins);
|
||
|
if (petGame.player.inventory.update) {
|
||
|
petGame.gui.player.inventory.innerHTML = null;
|
||
|
petGame.player.inventory.contents.forEach(function (item,itemIndex) {
|
||
|
var itemGui = elementPlace("#playerInv",null,"item item"+item.name,"li");
|
||
|
itemGui.innerHTML ='<span class="itemName">'+ item.name+'</span><span class="itemCount">'+numberShorten(item.count)+'</span><span class="itemDesc">'+item.desc+'</span>';
|
||
|
itemGui.onclick = function () { petGame.player.inventory.useItem(itemIndex,true); };
|
||
|
});
|
||
|
petGame.player.inventory.update = false;
|
||
|
}
|
||
|
if (true == petGame.gui.player.pets.update) {
|
||
|
petGame.gui.player.pets.innerHTML = null;
|
||
|
petGame.player.pets.forEach(function (pet,index) {
|
||
|
petGame.gui.player.pets["pet_"+index] = elementPlace("#playerPets","pet_"+pet.name, "pet gender"+pet.gender, "div");
|
||
|
var petGUI = petGame.gui.player.pets["pet_"+index];
|
||
|
petGUI.name = elementPlace("#pet_"+pet.name, null, "petName", "span");
|
||
|
petGUI.name.innerText = pet.name;
|
||
|
if (false == pet.dead) {
|
||
|
petGUI.age = elementPlace("#pet_"+pet.name, null, "petAge", "span");
|
||
|
petGUI.age.innerText = "Age: "+pet.age;
|
||
|
petGUI.affection = elementPlace("#pet_"+pet.name, null, "petAffection", "span");
|
||
|
petGUI.affection.innerText = "Love: "+(Math.sign(pet.affection)*Math.floor(Math.pow(Math.abs(pet.affection),1/7)));
|
||
|
petGUI.health = elementPlace("#pet_"+pet.name, null, "petHealth", "span");
|
||
|
petGUI.health.innerText = "health: "+Math.ceil(pet.health)+"/"+pet.healthMax;
|
||
|
petGUI.hydration = elementPlace("#pet_"+pet.name, null, "petHydration", "span");
|
||
|
petGUI.hydration.innerText = "Hydration: "+Math.ceil(pet.hydration)+"/"+pet.hydrationMax;
|
||
|
petGUI.nurishment = elementPlace("#pet_"+pet.name, null, "petNurishment", "span");
|
||
|
petGUI.nurishment.innerText = "Nurishment: "+Math.ceil(pet.nurishment)+"/"+pet.nurishmentMax;
|
||
|
petGUI.stomach = elementPlace("#pet_"+pet.name, null, "petStomach", "span");
|
||
|
petGUI.stomach.innerText = "Stomach: "+Math.ceil(pet.stomach)+"/"+pet.stomachMax;
|
||
|
if ("string" == typeof pet.currentAction) {
|
||
|
petGUI.action = elementPlace("#pet_"+pet.name, null, "petAction", "span");
|
||
|
petGUI.action.innerText = humanTime(pet.busyUntil - performance.now());
|
||
|
petGUI.action.classList.add(pet.currentAction);
|
||
|
}
|
||
|
if (0 < pet.dirty) {
|
||
|
petGUI.poop = elementPlace("#pet_"+pet.name, null, "petPoop", "span");
|
||
|
petGUI.poop.innerText = "Poop: "+Math.ceil(pet.dirty);
|
||
|
}
|
||
|
if (pet.selected) {
|
||
|
petGUI.classList.add("selected");
|
||
|
} else {
|
||
|
petGUI.onclick = function () {
|
||
|
petGame.player.pets.forEach(function (p) { p.selected = false;});
|
||
|
petGame.player.actions.available = [
|
||
|
{ "name":"Rename", "action":pet.rename, "petPointer": pet },
|
||
|
{ "name":"Feed", "action":pet.feed, "petPointer": pet },
|
||
|
{ "name":"Water", "action":pet.water, "petPointer": pet },
|
||
|
{ "name":"Play", "action":pet.play, "petPointer": pet },
|
||
|
{ "name":"Walk", "action":pet.walk, "petPointer": pet },
|
||
|
{ "name":"Sleep", "action":pet.sleep, "petPointer": pet },
|
||
|
{ "name":"Clean", "action":pet.clean, "petPointer": pet },
|
||
|
];
|
||
|
petGame.player.actions.update = true;
|
||
|
petGame.gui.player.pets.update = true;
|
||
|
pet.selected = true;
|
||
|
};
|
||
|
}
|
||
|
} else {
|
||
|
petGUI.name.innerHTML += '<p class="dead">RIP</p>';
|
||
|
petGUI.classList.add("dead");
|
||
|
}
|
||
|
});
|
||
|
petGame.gui.player.pets.update = false;
|
||
|
} else {
|
||
|
petGame.player.pets.forEach(function (pet,index) {
|
||
|
var petGUI = petGame.gui.player.pets["pet_"+index];
|
||
|
petGUI.name.innerText = pet.name;
|
||
|
if (false == pet.dead) {
|
||
|
petGUI.age.innerText = "Age: "+pet.age;
|
||
|
petGUI.affection.innerText = "Love: "+(Math.sign(pet.affection)*Math.floor(Math.pow(Math.abs(pet.affection),1/7)));
|
||
|
petGUI.health.innerText = "health: "+Math.ceil(pet.health)+"/"+pet.healthMax;
|
||
|
petGUI.hydration.innerText = "Hydration: "+Math.ceil(pet.hydration)+"/"+pet.hydrationMax;
|
||
|
petGUI.nurishment.innerText = "Nurishment: "+Math.ceil(pet.nurishment)+"/"+pet.nurishmentMax;
|
||
|
petGUI.stomach.innerText = "Stomach: "+Math.ceil(pet.stomach)+"/"+pet.stomachMax;
|
||
|
if ("string" == typeof pet.currentAction) {
|
||
|
petGUI.action.innerText = humanTime(pet.busyUntil - performance.now());
|
||
|
petGUI.action.classList.add(pet.currentAction);
|
||
|
}
|
||
|
if (0 < pet.dirty) {
|
||
|
petGUI.poop.innerText = "Poop: "+Math.ceil(pet.dirty);
|
||
|
}
|
||
|
} else {
|
||
|
petGUI.name.innerHTML += '<p class="dead">RIP</p>';
|
||
|
petGUI.classList.add("dead");
|
||
|
}
|
||
|
|
||
|
});
|
||
|
}
|
||
|
if (true == petGame.player.actions.update) {
|
||
|
petGame.gui.player.actions.innerHTML = null;
|
||
|
petGame.player.actions.available.forEach(function (action) {
|
||
|
var enabled = action.petPointer.currentAction ? "disabled" : "enabled";
|
||
|
var thisAction = elementPlace("#playerActions",null,"actionButton "+enabled,"span");
|
||
|
thisAction.innerText = action.name;
|
||
|
thisAction.onclick = action.action;
|
||
|
});
|
||
|
petGame.player.actions.update = false;
|
||
|
}
|
||
|
if (true == petGame.log.update) {
|
||
|
petGame.gui.info.log.innerHTML = null;
|
||
|
petGame.log.queue.forEach(function (message) {
|
||
|
petGame.gui.info.log.innerHTML += '<p class="'+message.priority+'">'+message.message+"</p>";
|
||
|
});
|
||
|
petGame.gui.info.log.scrollTop = petGame.gui.info.log.scrollHeight;
|
||
|
petGame.log.update = false;
|
||
|
}
|
||
|
if(petGame.market.inventory.update) {
|
||
|
petGame.gui.info.market.innerHTML = null;
|
||
|
petGame.market.inventory.contents.forEach(function (item,itemIndex) {
|
||
|
var itemGui = elementPlace("#infoMarket",null,"item item"+item.name,"li");
|
||
|
var cost = petGame.itemDB[item.id].cost;
|
||
|
itemGui.innerHTML ='<span class="itemName">'+ item.name+'</span><span class="itemCost">'+numberShorten(cost)+'</span><span class="itemCount">'+numberShorten(item.count)+'</span><span class="itemDesc">'+item.desc+'</span>';
|
||
|
itemGui.onclick = function () {
|
||
|
if (cost <= petGame.player.coins) {
|
||
|
petGame.market.coins += cost;
|
||
|
petGame.player.coins -= cost;
|
||
|
petGame.player.giveItem(item.id);
|
||
|
petGame.market.inventory.useItem(itemIndex,false);
|
||
|
} else {
|
||
|
petGame.log.messageAdd("You don't have enough coins for "+item.name,2,10000);
|
||
|
}
|
||
|
};
|
||
|
});
|
||
|
petGame.market.inventory.update = false;
|
||
|
}
|
||
|
|
||
|
}
|
||
|
// Define random events function
|
||
|
petGame.randomEvent = function () {
|
||
|
var dice = Math.floor(Math.random()*100);
|
||
|
var potentialEvents = petGame.eventDB.filter(anEvent => anEvent.chance > dice);
|
||
|
if (potentialEvents.length > 0) {
|
||
|
potentialEvents[Math.floor(Math.random()*potentialEvents.length)].action();
|
||
|
}
|
||
|
}
|
||
|
// Define Save function
|
||
|
petGame.save = function () {
|
||
|
var save = {};
|
||
|
save.sessionDate = performance.timeOrigin + performance.now();
|
||
|
save.sessionTime = performance.now();
|
||
|
save.current = petGame.current;
|
||
|
save.eventCountdown = petGame.eventCountdown;
|
||
|
save.market = {"exchangeRate":petGame.market.exchangeRate,"coins":petGame.market.coins,"inventory":petGame.market.inventory.getEssentials()};
|
||
|
save.player = {"water":petGame.player.water,"food":petGame.player.food,"coins":petGame.player.coins,"inventory":petGame.player.inventory.getEssentials(),"pets":[]};
|
||
|
petGame.player.pets.forEach(function (pet,index) {
|
||
|
save.player.pets[index] = {
|
||
|
"affection":pet.affection,
|
||
|
"age":pet.age,
|
||
|
"ageStart":pet.ageStart,
|
||
|
"birth":pet.birth,
|
||
|
"busyUntil":pet.busyUntil,
|
||
|
"currentAction":pet.currentAction,
|
||
|
"dead":pet.dead,
|
||
|
"dirty":pet.dirty,
|
||
|
"dna":pet.dna,
|
||
|
"activeRna":pet.activeRna,
|
||
|
"gender":pet.gender,
|
||
|
"health":pet.health,
|
||
|
"healthMax":pet.healthMax,
|
||
|
"hungerRate":pet.hungerRate,
|
||
|
"hydration":pet.hydration,
|
||
|
"hydrationMax":pet.hydrationMax,
|
||
|
"lastPoop":pet.lastPoop,
|
||
|
"mood":pet.mood,
|
||
|
"name":pet.name,
|
||
|
"nurishment":pet.nurishment,
|
||
|
"nurishmentMax":pet.nurishmentMax,
|
||
|
"stomach":pet.stomach,
|
||
|
"stomachMax":pet.stomachMax,
|
||
|
"thirstRate":pet.thirstRate,
|
||
|
};
|
||
|
});
|
||
|
localStorage.setItem("petGameSave",JSON.stringify(save));
|
||
|
}
|
||
|
// Define Load function
|
||
|
petGame.load = function () {
|
||
|
var load = JSON.parse(localStorage.getItem("petGameSave"));
|
||
|
var sessionStartDif = (load.sessionDate - load.sessionTime) - performance.timeOrigin;
|
||
|
var offlineDeltaT = performance.timeOrigin - load.sessionDate;
|
||
|
console.log("deltaT = "+offlineDeltaT);
|
||
|
console.log("time between last start and this start: "+sessionStartDif);
|
||
|
petGame.current = load.current + sessionStartDif + offlineDeltaT;
|
||
|
petGame.eventCountdown = load.eventCountdown + offlineDeltaT + sessionStartDif;
|
||
|
petGame.market.exchangeRate = load.market.exchangeRate;
|
||
|
petGame.market.coins = load.market.coins;
|
||
|
petGame.market.inventory.contents = [];
|
||
|
load.market.inventory.forEach(function (item) {petGame.market.addItem(item.id,item.count);});
|
||
|
petGame.player.water = load.player.water;
|
||
|
petGame.player.food = load.player.food;
|
||
|
petGame.player.coins = load.player.coins;
|
||
|
petGame.player.inventory.contents = [];
|
||
|
load.player.inventory.forEach(function (item) {petGame.player.giveItem(item.id,item.count);});
|
||
|
load.player.pets.forEach(function (oldPet) {
|
||
|
var index = (petGame.player.pets.push(new pet()) - 1);
|
||
|
petGame.player.pets[index].affection = oldPet.affection;
|
||
|
petGame.player.pets[index].age = oldPet.age,
|
||
|
petGame.player.pets[index].ageStart = oldPet.ageStart + sessionStartDif + offlineDeltaT,
|
||
|
petGame.player.pets[index].birth = oldPet.birth + sessionStartDif + offlineDeltaT,
|
||
|
petGame.player.pets[index].busyUntil = oldPet.busyUntil + sessionStartDif + offlineDeltaT,
|
||
|
petGame.player.pets[index].currentAction = oldPet.currentAction,
|
||
|
petGame.player.pets[index].dead = oldPet.dead,
|
||
|
petGame.player.pets[index].dirty = oldPet.dirty,
|
||
|
petGame.player.pets[index].dna = oldPet.dna,
|
||
|
petGame.player.pets[index].activeRna = oldPet.activeRna,
|
||
|
petGame.player.pets[index].gender = oldPet.gender,
|
||
|
petGame.player.pets[index].health = oldPet.health,
|
||
|
petGame.player.pets[index].healthMax = oldPet.healthMax,
|
||
|
petGame.player.pets[index].hungerRate = oldPet.hungerRate,
|
||
|
petGame.player.pets[index].hydration = oldPet.hydration,
|
||
|
petGame.player.pets[index].hydrationMax = oldPet.hydrationMax,
|
||
|
petGame.player.pets[index].lastPoop = oldPet.lastPoop + offlineDeltaT + sessionStartDif,
|
||
|
petGame.player.pets[index].mood = oldPet.mood,
|
||
|
petGame.player.pets[index].name = oldPet.name,
|
||
|
petGame.player.pets[index].nurishment = oldPet.nurishment,
|
||
|
petGame.player.pets[index].nurishmentMax = oldPet.nurishmentMax,
|
||
|
petGame.player.pets[index].stomach = oldPet.stomach,
|
||
|
petGame.player.pets[index].stomachMax = oldPet.stomachMax,
|
||
|
petGame.player.pets[index].thirstRate = oldPet.thirstRate
|
||
|
});
|
||
|
}
|
||
|
// Define games ticker function
|
||
|
petGame.tickerFunction = function () {
|
||
|
var deltaT = performance.now() - petGame.current;
|
||
|
petGame.current += deltaT;
|
||
|
petGame.eventCountdown -= deltaT;
|
||
|
petGame.player.pets.forEach( function (pet) { pet.tick(deltaT); });
|
||
|
if (petGame.eventCountdown <= 0) {
|
||
|
petGame.eventCountdown += Math.floor(Math.random()*1800000);
|
||
|
petGame.randomEvent();
|
||
|
}
|
||
|
// non time sensitive ticking functions
|
||
|
petGame.save();
|
||
|
petGame.log.clean();
|
||
|
petGame.gui.update();
|
||
|
}
|
||
|
// Define petGame init function
|
||
|
petGame.init = function () {
|
||
|
petGame.gui.init();
|
||
|
petGame.gui.update();
|
||
|
petGame.ticker = setInterval(petGame.tickerFunction, 250);
|
||
|
if (localStorage.getItem("petGameSave")) {
|
||
|
petGame.load();
|
||
|
} else {
|
||
|
petGame.player.give("coins",500);
|
||
|
petGame.market.addItem(0);
|
||
|
petGame.market.addItem(1,10);
|
||
|
petGame.market.addItem(2,10);
|
||
|
}
|
||
|
}
|