Last active
February 21, 2016 20:13
-
-
Save dubslow/afcb08a9d3e11baa77d2 to your computer and use it in GitHub Desktop.
A simple JS script to make purchasing decisions easier in CookieClicker
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* This is a small addon script for CookieClicker to display building purchase efficiencies, in a | |
manner similar to FrozenCookie (though several orders of magnitude more primitive). No decisions | |
or playing is done on behalf of the player, this is merely some extra passive calculations. */ | |
// first a small helper | |
function guardedSave(obj, funcname) | |
{ // if obj.oldfuncname exists, do nothing | |
// else: save the funcname to oldfuncname, so that funcname may be overwritten | |
// this protects against crashing after accidentally running this js twice | |
var oldfuncname = 'old' + funcname; | |
if (typeof obj[oldfuncname] === "undefined") | |
{ | |
obj[oldfuncname] = obj[funcname]; | |
} | |
} | |
var inverselog10 = 1/Math.log(10); | |
Game.RecalcEfficiencies = function(recalcScale) | |
{ | |
var recalcGains = Game.recalculateGains; | |
var curCps = Game.cookiesPs; | |
var effLogSum = 0; | |
for (var i in Game.Objects) | |
{ | |
var me = Game.Objects[i]; | |
// get the new hypothetical cps if this object is purchased | |
me.amount++; | |
// below, we replace CalculateGains with a version that also calls RefreshStore, which we specifically | |
// don't want to do in this case | |
Game.oldCalculateGains(); | |
var newCps = Game.cookiesPs; | |
me.amount--; | |
me.efficiency = (newCps - curCps) / me.getPrice(); | |
//console.log(me.name, me.efficiency) | |
effLogSum += -Math.log(me.efficiency) * inverselog10; | |
//console.log(me.name, effLogSum) | |
} | |
Game.oldCalculateGains(); | |
// reset back to actual cps rather than hypothetical | |
Game.recalculateGains = recalcGains; | |
if (recalcScale) // do not change scale for frenzies (passed as an arg) | |
{ | |
var effLogAvg = effLogSum / Game.ObjectsN; | |
var effLog = Math.ceil(effLogAvg + 2.1); // we want things to be 3 digit efficiencies on average | |
// (and slightly biased to 4 digits instead of 2) | |
Game.EffScale = Math.pow(10, effLog); | |
} | |
//console.log(effLogAvg, effLog, Game.EffScale); | |
for (var i in Game.Objects) | |
{ | |
var me = Game.Objects[i]; | |
me.scaledEfficiency = me.efficiency * Game.EffScale; | |
} | |
} | |
for (var i in Game.Objects) | |
{ | |
var me = Game.Objects[i]; | |
/* | |
me.ChocEggRecovAmnt = function() | |
{ // it will take time for the newly bought building to pay for itself relative to using the price towards the chocolate egg bonus | |
// figure that out here. total recovery amount = price*5%*1/2 (since you sell all the buildings before popping) | |
// use that to get an ETA, but then figure out what your total cookie count would be at the ETA, and if | |
// that amount is more than you plan to reset with, then you shouldn't buy the building. | |
var recovAmount = this.getPrice() * 0.5 * 0.05; | |
var eta = recovAmount/this.getAddedCPS(); | |
var togo = Game.cookiesPs*eta; | |
return togo + Game.cookiesEarned+Game.cookiesReset; // if this amount is higher than your reset target, don't buy, just save. | |
} | |
*/ | |
// ^^^ I don't think this is actually useful because it doesn't account for future cps mult upgrades | |
guardedSave(me, 'rebuild'); | |
me.rebuild = function() | |
{ | |
this.oldrebuild(); | |
l('productPrice'+this.id).innerHTML += '<br/> (Eff ' + Beautify(this.scaledEfficiency, 0) + ')'; | |
/*+ ', CERA ' + Beautify(this.ChocEggRecovAmnt()+Game.cookiesReset) */ | |
} | |
} | |
// call Game.RefreshStore whenver we recalc efficiencies, which is whenever cps is changed | |
guardedSave(Game, 'CalculateGains'); | |
Game.CalculateGains = function() | |
{ | |
Game.oldCalculateGains(); | |
Game.RecalcEfficiencies(!(Game.frenzy>0)); // arg is whether or not to recalc scale, which we don't during frenzies | |
Game.RefreshStore(); | |
} | |
// and away we go! | |
Game.RecalcEfficiencies(1); // always recalc scale when initializing | |
Game.RefreshStore(); | |
/* | |
//////////////////////////////////////////////////////////////////////////////// | |
// add dumb ETA to 1k yottacookies | |
// this is presented in the stats menu, whose html is unfortunately not id'd, so | |
// search for the proper divs by hand | |
// http://stackoverflow.com/a/26595625/1497645 | |
function findElemByContent(content, cls) | |
{ | |
var textProp = 'textContent' in document ? 'textContent' : 'innerText'; | |
var elems = [].slice.call(document.querySelectorAll('div'), 0); | |
var found = elems.filter(function(e){return e.className == cls && e[textProp].indexOf(content) > -1;}); | |
return found.length ? found : false; | |
} | |
Game.CountWrinklers = function() | |
{ | |
var n = 0; | |
for (var i in Game.wrinklers) | |
{ | |
if (Game.wrinklers[i].phase==2) | |
n++; | |
} | |
return n; | |
} | |
Game.WrinklerMult = function(n) | |
{ | |
// http://cookieclicker.wikia.com/wiki/Wrinkler#CPS_multiplier | |
if (Game.Has('Wrinklerspawn')) | |
return 1 - 0.05*n + 0.05775*n*n; | |
else | |
return 1 - 0.05*n + 0.055*n*n; | |
} | |
Game.EffectiveRate = function() | |
{ | |
var rate = Game.cookiesPs; | |
if (Game.elderWrath > 0) | |
rate *= Game.WrinklerMult(10) * 0.9; // assume that maximum wrinkler efficiency is unobtainable | |
return rate; | |
} | |
Game.LinearETA = function() | |
{ | |
// now uses wrinkler count! | |
var current = Game.cookiesEarned + Game.cookiesReset; | |
var remaining = 1E27 - current; // 1 octillion cookies is the goal | |
return remaining/Game.EffectiveRate(); | |
} | |
Game.CurrentQuadraticETA = function() | |
{ | |
// slightly less dumb ETA. heavenly chips, i.e. cookie rate, go as square root of cookies, | |
// so cookie increase is approximately quadratic | |
var currentTime = (new Date().getTime() - Game.fullDate); | |
var totalCookies = Game.cookiesEarned + Game.cookiesReset; | |
// y = k t^2 => k = y/t^2 | |
// 1E27 = k t^2 => t = sqrt(1E27/k) = sqrt(1E27*t^2/y) | |
// sqrt(1E27) = 10^13*sqrt(10) | |
var finalTime = Math.sqrt(currentTime*(currentTime/totalCookies)) * 1E13 * 3.1622776601683795; | |
return (finalTime - currentTime)/1000; | |
} | |
Game.insertBefore = function(content, cls, newnode) | |
{ | |
// find the div containing the given content, then insert the new node before it | |
var elems = findElemByContent(content, cls); | |
if (elems != false) | |
{ | |
var elem = elems[0]; | |
var rent = elem.parentNode; | |
rent.insertBefore(newnode, elem); | |
} | |
} | |
guardedSave(Game, 'UpdateMenu'); | |
Game.UpdateMenu = function() | |
{ | |
Game.oldUpdateMenu(); | |
var eta1 = Game.sayTime(Game.LinearETA()*Game.fps); | |
var eta2 = Game.sayTime(Game.CurrentQuadraticETA()*Game.fps); | |
// I don't know why Game.sayTime requires a factor of Game.fps | |
var newdiv = document.createElement("div"); | |
newdiv.className = "listing"; | |
newdiv.innerHTML = '<b>1kYcookies ETAs :</b> linear: ' + eta1 + ', quadratic: ' + eta2; | |
// SI prefixes end at septillion | |
Game.insertBefore('Session started :', 'listing', newdiv); | |
newdiv = document.createElement("div"); | |
newdiv.className = "listing"; | |
newdiv.innerHTML = '<b>Price to 400 cursors :</b> <div class="price plain">'+Game.tinyCookie()+Beautify(Game.FourHundredCursors())+'</div>'; | |
Game.insertBefore('Legacy started :', 'listing', newdiv); | |
} | |
Game.UpdateMenu(); | |
*/ |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
javascript:function guardedSave(e,a){var i="old"+a;"undefined"==typeof e[i]&&(e[i]=e[a])}var inverselog10=1/Math.log(10);Game.RecalcEfficiencies=function(e){var a=Game.recalculateGains,i=Game.cookiesPs,c=0;for(var f in Game.Objects){var l=Game.Objects[f];l.amount++,Game.oldCalculateGains();var n=Game.cookiesPs;l.amount--,l.efficiency=(n-i)/l.getPrice(),c+=-Math.log(l.efficiency)*inverselog10}if(Game.oldCalculateGains(),Game.recalculateGains=a,e){var r=c/Game.ObjectsN,t=Math.ceil(r+2.1);Game.EffScale=Math.pow(10,t)}for(var f in Game.Objects){var l=Game.Objects[f];l.scaledEfficiency=l.efficiency*Game.EffScale}};for(var i in Game.Objects){var me=Game.Objects[i];guardedSave(me,"rebuild"),me.rebuild=function(){this.oldrebuild(),l("productPrice"+this.id).innerHTML+="<br/> (Eff "+Beautify(this.scaledEfficiency,0)+")"}}guardedSave(Game,"CalculateGains"),Game.CalculateGains=function(){Game.oldCalculateGains(),Game.RecalcEfficiencies(!(Game.frenzy>0)),Game.RefreshStore()},Game.RecalcEfficiencies(1),Game.RefreshStore(); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment