From 38e1c77c5cd9061d16d445b15308e9972f61b50d Mon Sep 17 00:00:00 2001 From: Daniel Xie Date: Tue, 27 Jun 2017 23:11:27 -0500 Subject: [PATCH] Rebalancing for favor, Increase reputation cost, Fix bugs with purchasing multiple augmentations, balanced company positions. New netscript functions --- css/menupages.css | 71 +++++--------------------- index.html | 45 ++++++++++++----- src/Augmentations.js | 2 +- src/Company.js | 81 +++++++++++++++-------------- src/Constants.js | 87 ++++++++++++++++---------------- src/NetscriptEvaluator.js | 38 ++++++++++++++ src/SaveObject.js | 5 +- src/Script.js | 2 + utils/PurchaseAugmentationBox.js | 11 ++-- utils/PurchaseRamForHomeBox.js | 2 +- 10 files changed, 183 insertions(+), 161 deletions(-) diff --git a/css/menupages.css b/css/menupages.css index ae5ff9b14..756dca2de 100644 --- a/css/menupages.css +++ b/css/menupages.css @@ -1,18 +1,21 @@ /* CSS for different main menu pages, such as character info, script editor, etc (but excluding terminal which has its own page) */ -/* Character Info */ -#character-container { - position: fixed; +.generic-menupage-container { height: 100%; - padding-top: 10px; padding-left: 10px; margin-left: 10%; width: 99%; - overflow: auto; overflow-y: scroll; } +/* Character Info */ +#character-container { + padding-top: 10px; + position: fixed; +} + + /* Script Editor */ /* This temp element is used for auto adjusting filename field */ .tmp-element { @@ -20,16 +23,13 @@ white-space: pre; } + #script-editor-container { position: fixed; padding-top: 10px; - height: 100%; - margin-left: 10%; - width: 99%; - color: var(--my-font-color); - overflow-y: scroll; } + #script-editor-buttons-wrapper { width: 100%; padding-right: 0xp; @@ -131,11 +131,6 @@ background-color: #555; #active-scripts-container { position: fixed; padding-top: 10px; - padding-left: 10px; - height: 100%; - margin-left: 10%; - width: 99%; - overflow-y: scroll; } #active-scripts-text, @@ -277,12 +272,9 @@ background-color: #555; #hacknet-nodes-container { position: fixed; padding: 10px; - height: 100%; - margin-left: 10%; - width: 99%; - overflow-y: scroll; } + #hacknet-nodes-container li{ padding: 6px; margin: 6px; @@ -337,12 +329,9 @@ background-color: #555; #world-container { position: fixed; padding-top: 10px; - padding-left: 10px; - height: 100%; - margin-left: 10%; - width: 99%; } + #world-city-name, #world-city-desc { padding: 4px; @@ -353,10 +342,6 @@ background-color: #555; #create-program-container { position: fixed; padding-top: 10px; - padding-left: 10px; - height: 100%; - margin-left: 10%; - width: 99%; } #create-program-page-text { @@ -393,23 +378,11 @@ background-color: #555; #factions-container { position: fixed; padding-top: 10px; - padding-left: 10px; - height: 100%; - margin-left: 10%; - width: 99%; - color: var(--my-font-color); - overflow-y: auto; } #faction-container { position: fixed; padding-top: 10px; - padding-left: 10px; - height: 100%; - margin-left: 10%; - width: 99%; - overflow: auto; - overflow-y: auto; } #factions-list li { @@ -472,12 +445,6 @@ div.faction-clear { #faction-augmentations-container{ position: fixed; padding-top: 10px; - padding-left: 10px; - height: 100%; - margin-left: 10%; - width: 99%; - color: var(--my-font-color); - overflow-y: auto; } #faction-augmentations-container p, @@ -503,14 +470,9 @@ div.faction-clear { #augmentations-container { position: fixed; padding-top: 10px; - padding-left: 10px; - height: 100%; - margin-left: 10%; - width: 99%; - color: var(--my-font-color); - overflow-y: scroll; } + #augmentations-list li, #queued-augmentations-list li { width: 70%; @@ -536,13 +498,7 @@ div.faction-clear { /* Tutorial */ #tutorial-container { position: fixed; - height: 100%; padding-top: 10px; - padding-left: 10px; - margin-left: 10%; - width: 99%; - overflow: auto; - overflow-y: scroll; } #tutorial-text { @@ -577,4 +533,3 @@ div.faction-clear { #location-job-reputation, #location-company-favor { display: inline; } - diff --git a/index.html b/index.html index d6369e6e2..f9cd95be5 100644 --- a/index.html +++ b/index.html @@ -142,14 +142,14 @@ -
+

-
+

Script name:

@@ -165,7 +165,7 @@
-
+

This page displays a list of all of your scripts that are currently running across every machine. It also provides information about each script's production. The scripts are categorized by the hostname of the servers on which they are running.

@@ -175,7 +175,7 @@
-
+

Hacknet Nodes

The Hacknet is a global, decentralized network of machines. It is used by hackers all around @@ -205,7 +205,7 @@

-
+

    @@ -402,7 +402,7 @@
-
+

This page displays any programs that you are able to create. Writing the code for a program takes time, which can vary based on how complex the program is. If you are working on creating on a program you can cancel @@ -455,14 +455,14 @@

-
+

Factions

Lists all factions you have joined

    -
    +

    ---------------

    @@ -539,7 +539,7 @@



    -
    +
    Back

    Faction Augmentations

    Lists all augmentations that are available to purchase from

    @@ -549,7 +549,7 @@
    -
    +

    Purchased Augmentations

    Below is a list of all Augmentations you have purchased but not yet installed. Click the button below to install them. @@ -576,7 +576,7 @@

    -
    + -
    + + +
    +
    +

    +
    + + + + + + + + + + +
    +
    +
    +

    +
    +
    diff --git a/src/Augmentations.js b/src/Augmentations.js index ba1fde4a4..c6b811983 100644 --- a/src/Augmentations.js +++ b/src/Augmentations.js @@ -1373,7 +1373,7 @@ initAugmentations = function() { AddToAugmentations(SNA); //Update costs based on how many have been purchased - var mult = Math.pow(1.5, Player.queuedAugmentations.length); + var mult = Math.pow(CONSTANTS.MultipleAugMultiplier, Player.queuedAugmentations.length); for (var name in Augmentations) { if (Augmentations.hasOwnProperty(name)) { Augmentations[name].baseCost *= mult; diff --git a/src/Company.js b/src/Company.js index 8d9b8ca56..b6bd27dd0 100644 --- a/src/Company.js +++ b/src/Company.js @@ -82,7 +82,7 @@ function CompanyPosition(name, reqHack, reqStr, reqDef, reqDex, reqAgi, reqCha, // //NOTE: These parameters should total to 100, such that each parameter represents a "weighting" of how // important that stat/skill is for the job -CompanyPosition.prototype.setPerformanceParameters = function(hackEff, strEff, defEff, dexEff, agiEff, chaEff) { +CompanyPosition.prototype.setPerformanceParameters = function(hackEff, strEff, defEff, dexEff, agiEff, chaEff, posMult=1) { if (hackEff + strEff + defEff + dexEff + agiEff + chaEff != 100) { console.log("CompanyPosition.setPerformanceParameters() arguments do not total to 100"); return; @@ -93,6 +93,7 @@ CompanyPosition.prototype.setPerformanceParameters = function(hackEff, strEff, d this.dexterityEffectiveness = dexEff; this.agilityEffectiveness = agiEff; this.charismaEffectiveness = chaEff; + this.positionMultiplier = posMult; //Reputation multiplier for this position } //Set the stat/skill experience a Player should gain for working at a CompanyPosition. The experience is per game loop (200 ms) @@ -115,7 +116,13 @@ CompanyPosition.prototype.calculateJobPerformance = function(hacking, str, def, var dexRatio = this.dexterityEffectiveness * dex / CONSTANTS.MaxSkillLevel; var agiRatio = this.agilityEffectiveness * agi / CONSTANTS.MaxSkillLevel; var chaRatio = this.charismaEffectiveness * cha / CONSTANTS.MaxSkillLevel; - return (hackRatio + strRatio + defRatio + dexRatio + agiRatio + chaRatio) / 100; + + var reputationGain = this.positionMultiplier * (hackRatio + strRatio + defRatio + dexRatio + agiRatio + chaRatio) / 100; + if (isNaN(reputationGain)) { + console.log("ERROR: Code should not reach here"); + reputationGain = (hackRatio + strRatio + defRatio + dexRatio + agiRatio + chaRatio) / 100; + } + return reputationGain; } CompanyPosition.prototype.isSoftwareJob = function() { @@ -278,63 +285,63 @@ CompanyPositions = { init: function() { //Argument order: hack, str, def, dex, agi, cha //Software - CompanyPositions.SoftwareIntern.setPerformanceParameters(90, 0, 0, 0, 0, 10); + CompanyPositions.SoftwareIntern.setPerformanceParameters(90, 0, 0, 0, 0, 10, 1); CompanyPositions.SoftwareIntern.setExperienceGains(.1, 0, 0, 0, 0, .02); - CompanyPositions.JuniorDev.setPerformanceParameters(85, 0, 0, 0, 0, 15); + CompanyPositions.JuniorDev.setPerformanceParameters(85, 0, 0, 0, 0, 15, 1.1); CompanyPositions.JuniorDev.setExperienceGains(.2, 0, 0, 0, 0, .04); - CompanyPositions.SeniorDev.setPerformanceParameters(75, 0, 0, 0, 0, 25); + CompanyPositions.SeniorDev.setPerformanceParameters(75, 0, 0, 0, 0, 25, 1.2); CompanyPositions.SeniorDev.setExperienceGains(.4, 0, 0, 0, 0, .08); - CompanyPositions.LeadDev.setPerformanceParameters(70, 0, 0, 0, 0, 30); + CompanyPositions.LeadDev.setPerformanceParameters(70, 0, 0, 0, 0, 30, 1.3); CompanyPositions.LeadDev.setExperienceGains(.5, 0, 0, 0, 0, .1); - CompanyPositions.SoftwareConsultant.setPerformanceParameters(80, 0, 0, 0, 0, 20); + CompanyPositions.SoftwareConsultant.setPerformanceParameters(80, 0, 0, 0, 0, 20, 1); CompanyPositions.SoftwareConsultant.setExperienceGains(.175, 0, 0, 0, 0, .03); - CompanyPositions.SeniorSoftwareConsultant.setPerformanceParameters(75, 0, 0, 0, 0, 25); + CompanyPositions.SeniorSoftwareConsultant.setPerformanceParameters(75, 0, 0, 0, 0, 25, 1.15); CompanyPositions.SeniorSoftwareConsultant.setExperienceGains(.35, 0, 0, 0, 0, .06); //Security - CompanyPositions.ITIntern.setPerformanceParameters(90, 0, 0, 0, 0, 10); + CompanyPositions.ITIntern.setPerformanceParameters(90, 0, 0, 0, 0, 10, 1); CompanyPositions.ITIntern.setExperienceGains(.05, 0, 0, 0, 0, .01); - CompanyPositions.ITAnalyst.setPerformanceParameters(85, 0, 0, 0, 0, 15); + CompanyPositions.ITAnalyst.setPerformanceParameters(85, 0, 0, 0, 0, 15, 1.1); CompanyPositions.ITAnalyst.setExperienceGains(.15, 0, 0, 0, 0, .02); - CompanyPositions.ITManager.setPerformanceParameters(75, 0, 0, 0, 0, 25); + CompanyPositions.ITManager.setPerformanceParameters(75, 0, 0, 0, 0, 25, 1.2); CompanyPositions.ITManager.setExperienceGains(.4, 0, 0, 0, 0, .1); - CompanyPositions.SysAdmin.setPerformanceParameters(80, 0, 0, 0, 0, 20); + CompanyPositions.SysAdmin.setPerformanceParameters(80, 0, 0, 0, 0, 20, 1.2); CompanyPositions.SysAdmin.setExperienceGains(.5, 0, 0, 0, 0, .05); - CompanyPositions.SecurityEngineer.setPerformanceParameters(85, 0, 0, 0, 0, 15); + CompanyPositions.SecurityEngineer.setPerformanceParameters(85, 0, 0, 0, 0, 15, 1.15); CompanyPositions.SecurityEngineer.setExperienceGains(0.4, 0, 0, 0, 0, .05); - CompanyPositions.NetworkEngineer.setPerformanceParameters(85, 0, 0, 0, 0, 15); + CompanyPositions.NetworkEngineer.setPerformanceParameters(85, 0, 0, 0, 0, 15, 1.15); CompanyPositions.NetworkEngineer.setExperienceGains(0.4, 0, 0, 0, 0, .05); - CompanyPositions.NetworkAdministrator.setPerformanceParameters(75, 0, 0, 0, 0, 25); + CompanyPositions.NetworkAdministrator.setPerformanceParameters(75, 0, 0, 0, 0, 25, 1.25); CompanyPositions.NetworkAdministrator.setExperienceGains(0.5, 0, 0, 0, 0, .1); //Technology management - CompanyPositions.HeadOfSoftware.setPerformanceParameters(65, 0, 0, 0, 0, 35); + CompanyPositions.HeadOfSoftware.setPerformanceParameters(65, 0, 0, 0, 0, 35, 1.4); CompanyPositions.HeadOfSoftware.setExperienceGains(1, 0, 0, 0, 0, .5); - CompanyPositions.HeadOfEngineering.setPerformanceParameters(60, 0, 0, 0, 0, 40); + CompanyPositions.HeadOfEngineering.setPerformanceParameters(60, 0, 0, 0, 0, 40, 1.4); CompanyPositions.HeadOfEngineering.setExperienceGains(1.1, 0, 0, 0, 0, .5); - CompanyPositions.VicePresident.setPerformanceParameters(60, 0, 0, 0, 0, 40); + CompanyPositions.VicePresident.setPerformanceParameters(60, 0, 0, 0, 0, 40, 1.5); CompanyPositions.VicePresident.setExperienceGains(1.2, 0, 0, 0, 0, .6); - CompanyPositions.CTO.setPerformanceParameters(50, 0, 0, 0, 0, 50); + CompanyPositions.CTO.setPerformanceParameters(50, 0, 0, 0, 0, 50, 1.5); CompanyPositions.CTO.setExperienceGains(1.5, 0, 0, 0, 1); //Business - CompanyPositions.BusinessIntern.setPerformanceParameters(10, 0, 0, 0, 0, 90); + CompanyPositions.BusinessIntern.setPerformanceParameters(10, 0, 0, 0, 0, 90, 1); CompanyPositions.BusinessIntern.setExperienceGains(.01, 0, 0, 0, 0, .1); - CompanyPositions.BusinessAnalyst.setPerformanceParameters(20, 0, 0, 0, 0, 80); + CompanyPositions.BusinessAnalyst.setPerformanceParameters(20, 0, 0, 0, 0, 80, 1.1); CompanyPositions.BusinessAnalyst.setExperienceGains(.02, 0, 0, 0, 0, .2); - CompanyPositions.BusinessManager.setPerformanceParameters(15, 0, 0, 0, 0, 85); + CompanyPositions.BusinessManager.setPerformanceParameters(15, 0, 0, 0, 0, 85, 1.2); CompanyPositions.BusinessManager.setExperienceGains(.02, 0, 0, 0, 0, .4); - CompanyPositions.OperationsManager.setPerformanceParameters(15, 0, 0, 0, 0, 85); + CompanyPositions.OperationsManager.setPerformanceParameters(15, 0, 0, 0, 0, 85, 1.2); CompanyPositions.OperationsManager.setExperienceGains(.02, 0, 0, 0, 0, .4); - CompanyPositions.CFO.setPerformanceParameters(10, 0, 0, 0, 0, 90); + CompanyPositions.CFO.setPerformanceParameters(10, 0, 0, 0, 0, 90, 1.3); CompanyPositions.CFO.setExperienceGains(.05, 0, 0, 0, 0, 1); - CompanyPositions.CEO.setPerformanceParameters(10, 0, 0, 0, 0, 90); + CompanyPositions.CEO.setPerformanceParameters(10, 0, 0, 0, 0, 90, 1.5); CompanyPositions.CEO.setExperienceGains(.1, 0, 0, 0, 0, 1.5); - CompanyPositions.BusinessConsultant.setPerformanceParameters(20, 0, 0, 0, 0, 80); + CompanyPositions.BusinessConsultant.setPerformanceParameters(20, 0, 0, 0, 0, 80, 1); CompanyPositions.BusinessConsultant.setExperienceGains(.015, 0, 0, 0, 0, .15); - CompanyPositions.SeniorBusinessConsultant.setPerformanceParameters(15, 0, 0, 0, 0, 85); + CompanyPositions.SeniorBusinessConsultant.setPerformanceParameters(15, 0, 0, 0, 0, 85, 1.15); CompanyPositions.SeniorBusinessConsultant.setExperienceGains(.015, 0, 0, 0, 0, .3); //Non-tech/management jobs @@ -347,23 +354,23 @@ CompanyPositions = { CompanyPositions.Waiter.setExperienceGains(0, .01, .01, .01, .01, .05); CompanyPositions.Employee.setPerformanceParameters(0, 10, 0, 10, 10, 70); CompanyPositions.Employee.setExperienceGains(0, .01, .01, .01, .01, .04); - CompanyPositions.SecurityGuard.setPerformanceParameters(5, 20, 20, 20, 20, 15); + CompanyPositions.SecurityGuard.setPerformanceParameters(5, 20, 20, 20, 20, 15, 1); CompanyPositions.SecurityGuard.setExperienceGains(.01, .02, .02, .02, .02, .01); - CompanyPositions.PoliceOfficer.setPerformanceParameters(5, 20, 20, 20, 20, 15); + CompanyPositions.PoliceOfficer.setPerformanceParameters(5, 20, 20, 20, 20, 15, 1); CompanyPositions.PoliceOfficer.setExperienceGains(.01, .04, .04, .04, .04, .02); - CompanyPositions.PoliceChief.setPerformanceParameters(5, 20, 20, 20, 20, 15); + CompanyPositions.PoliceChief.setPerformanceParameters(5, 20, 20, 20, 20, 15, 1.25); CompanyPositions.PoliceChief.setExperienceGains(.02, .06, .06, .06, .06, .05); - CompanyPositions.SecurityOfficer.setPerformanceParameters(10, 20, 20, 20, 20, 10); + CompanyPositions.SecurityOfficer.setPerformanceParameters(10, 20, 20, 20, 20, 10, 1.1); CompanyPositions.SecurityOfficer.setExperienceGains(.02, .06, .06, .06, .06, .04); - CompanyPositions.SecuritySupervisor.setPerformanceParameters(10, 15, 15, 15, 15, 30); + CompanyPositions.SecuritySupervisor.setPerformanceParameters(10, 15, 15, 15, 15, 30, 1.25); CompanyPositions.SecuritySupervisor.setExperienceGains(.02, .06, .06, .06, .06, .08); - CompanyPositions.HeadOfSecurity.setPerformanceParameters(10, 15, 15, 15, 15, 30); + CompanyPositions.HeadOfSecurity.setPerformanceParameters(10, 15, 15, 15, 15, 30, 1.4); CompanyPositions.HeadOfSecurity.setExperienceGains(.05, .1, .1, .1, .1, .1); - CompanyPositions.FieldAgent.setPerformanceParameters(10, 15, 15, 20, 20, 20); + CompanyPositions.FieldAgent.setPerformanceParameters(10, 15, 15, 20, 20, 20, 1); CompanyPositions.FieldAgent.setExperienceGains(.04, .06, .06, .06, .06, .04); - CompanyPositions.SecretAgent.setPerformanceParameters(15, 15, 15, 20, 20, 15); + CompanyPositions.SecretAgent.setPerformanceParameters(15, 15, 15, 20, 20, 15, 1.25); CompanyPositions.SecretAgent.setExperienceGains(.08, .1, .1, .1, .1, .08); - CompanyPositions.SpecialOperative.setPerformanceParameters(15, 15, 15, 20, 20, 15); + CompanyPositions.SpecialOperative.setPerformanceParameters(15, 15, 15, 20, 20, 15, 1.5); CompanyPositions.SpecialOperative.setExperienceGains(.12, .15, .15, .15, .15, .12); } } @@ -381,7 +388,7 @@ getNextCompanyPosition = function(currPos) { if (currPos.positionName == CompanyPositions.SeniorDev.positionName) { return CompanyPositions.LeadDev; } - if (currPos.positionName == CompanyPositions.LeadDev.positionname) { + if (currPos.positionName == CompanyPositions.LeadDev.positionName) { return CompanyPositions.HeadOfSoftware; } diff --git a/src/Constants.js b/src/Constants.js index 767bf28b5..1ca6a45c9 100644 --- a/src/Constants.js +++ b/src/Constants.js @@ -1,5 +1,5 @@ CONSTANTS = { - Version: "0.23.0.BETA", + Version: "0.23.0", //Max level for any skill, assuming no multipliers. Determined by max numerical value in javascript for experience //and the skill level formula in Player.js. Note that all this means it that when experience hits MAX_INT, then @@ -29,8 +29,8 @@ CONSTANTS = { HacknetNodeMaxCores: 16, /* Faction and Company favor */ - FactionReputationToFavor: 6000, - CompanyReputationToFavor: 4500, + FactionReputationToFavor: 6500, + CompanyReputationToFavor: 6000, /* Augmentation */ //NeuroFlux Governor cost multiplier as you level up @@ -47,6 +47,7 @@ CONSTANTS = { ScriptHackRamCost: 0.1, ScriptGrowRamCost: 0.15, ScriptWeakenRamCost: 0.15, + ScriptScanRamCost: 0.2, ScriptNukeRamCost: 0.05, ScriptBrutesshRamCost: 0.05, ScriptFtpcrackRamCost: 0.05, @@ -71,7 +72,7 @@ CONSTANTS = { ScriptHNUpgRamRamCost: 0.6, ScriptHNUpgCoreRamCost: 0.8, - MultithreadingRAMCost: 1.002, + MultithreadingRAMCost: 1, //Server constants ServerBaseGrowthRate: 1.03, //Unadjusted Growth rate @@ -81,7 +82,8 @@ CONSTANTS = { //Augmentation Constants AugmentationCostMultiplier: 5, //Used for balancing costs without having to readjust every Augmentation cost - AugmentationRepMultiplier: 1.5, //Used for balancing rep cost without having to readjust every value + AugmentationRepMultiplier: 1.75, //Used for balancing rep cost without having to readjust every value + MultipleAugMultiplier: 1.75, //Maximum number of log entries for a script MaxLogCapacity: 50, @@ -193,7 +195,7 @@ CONSTANTS = { "and you can purchase additional servers as you progress through the game. Connecting to other servers " + "and hacking them can be a major source of income and experience. Servers can also be used to run " + "scripts which can automatically hack servers for you.

    " + - "In order to navigate between machines, use the 'scan' command to see all servers " + + "In order to navigate between machines, use the 'scan' or 'scan-analyze' Terminal command to see all servers " + "that are reachable from your current server. Then, you can use the 'connect [hostname/ip]' " + "command to connect to one of the available machines.

    " + "The 'hostname' and 'ifconfig' commands can be used to display the hostname/IP of the " + @@ -286,16 +288,15 @@ CONSTANTS = { "every call to the hack(), grow(), and weaken() Netscript functions will have its effect multiplied by the number of scripts. " + "For example, if a normal single-threaded script is able to hack $10,000, then running the same script with 5 threads would " + "yield $50,000.

    " + - "Each additional thread to a script will slightly increase the RAM usage for that thread. The total cost of running a script with " + - "n threads can be calculated with:
    " + - "base cost * n * (1.005 ^ n)
    " + - "where the base cost is the amount of RAM required to run the script with a single thread. In the terminal, you can run the " + + "When multithreading a script, the total RAM cost can be calculated by simply multiplying the base RAM cost of the script " + + "with the number of threads, where the base cost refers to the amount of RAM required to run the script single-threaded. " + + "In the terminal, you can run the " + "'mem [scriptname] -t n' command to see how much RAM a script requires with n threads.

    " + "Every method for running a script has an option for making it multihreaded. To run a script with " + "n threads from a Terminal:
    " + "run [scriptname] -t n

    " + "Using Netscript commands:
    " + - "run('scriptname.script', m);
    " + + "run('scriptname.script', n);
    " + "exec('scriptname.script, 'targetServer', n);

    " + "

    Notes about how scripts work offline


    " + " The scripts that you write and execute are interpreted in Javascript. For this " + @@ -404,7 +405,7 @@ CONSTANTS = { "is determined by the server's growth rate and varies between servers. Generally, higher-level servers have higher growth rates.

    " + "Like hack(), grow() can be called on any server, regardless of where the script is running. " + "The grow() command requires root access to the target server, but there is no required hacking level to run the command. " + - "It grants 0.5 hacking exp when it completes. It also raises the security level of the target server by 0.004. " + + "It also raises the security level of the target server by 0.004. " + "Returns the number by which the money on the server was multiplied for the growth. " + "Works offline at a slower rate.
    Example: grow('foodnstuff');

    " + "weaken(hostname/ip)
    Use your hacking skills to attack a server's security, lowering the server's security level. The argument passed " + @@ -412,11 +413,13 @@ CONSTANTS = { "hacking level and the target server's security level. This function lowers the security level of the target server by " + "0.1.

    Like hack() and grow(), weaken() can be called on " + "any server, regardless of where the script is running. This command requires root access to the target server, but " + - "there is no required hacking level to run the command. Grants 3 hacking exp when it completes. Returns " + + "there is no required hacking level to run the command. Returns " + "0.1. Works offline at a slower rate
    Example: weaken('foodnstuff');

    " + - "print(x)
    Prints a value or a variable to the scripts logs (which can be viewed with the 'tail [script]' terminal command ).
    " + + "print(x)
    Prints a value or a variable to the scripts logs (which can be viewed with the 'tail [script]' terminal command ).
    " + "WARNING: Do NOT call print() on an array. The script will crash. You can, however, call print on single elements of an array. For example, if " + "the variable 'a' is an array, then do NOT call print(a), but it is okay to call print(a[0]).

    " + + "scan()
    Returns an array containing the hostnames of all servers that are one node away from the current server. The " + + "current server is the server on which the script that calls this function is running. The hostnames are strings.

    " + "nuke(hostname/ip)
    Run NUKE.exe on the target server. NUKE.exe must exist on your home computer. Does NOT work while offline
    Example: nuke('foodnstuff');

    " + "brutessh(hostname/ip)
    Run BruteSSH.exe on the target server. BruteSSH.exe must exist on your home computer. Does NOT work while offline
    Example: brutessh('foodnstuff');

    " + "ftpcrack(hostname/ip)
    Run FTPCrack.exe on the target server. FTPCrack.exe must exist on your home computer. Does NOT work while offline
    Example: ftpcrack('foodnstuff');

    " + @@ -476,6 +479,8 @@ CONSTANTS = { "getHackingLevel()
    Returns the Player's current hacking level. Does NOT work while offline

    " + "getServerMoneyAvailable(hostname/ip)
    Returns the amount of money available on a server. The argument passed in must be a string with either the " + "hostname or IP of the target server. Does NOT work while offline
    Example: getServerMoneyAvailable('foodnstuff');

    " + + "getServerMaxMoney(hostname/ip)
    Returns the maximum amount of money that can be available on a server. The argument passed in must be a string with " + + "the hostname or IP of the target server. Does NOT work while offline
    Example: getServerMaxMoney('foodnstuff');

    " + "getServerSecurityLevel(hostname/ip)
    Returns the security level of a server. The argument passed in must be a string with either the " + "hostname or IP of the target server. A server's security is denoted by a number between 1 and 100. Does NOT work while offline.

    " + "getServerBaseSecurityLevel(hostname/ip)
    Returns the base security level of a server. This is the security level that the server starts out with. " + @@ -485,6 +490,8 @@ CONSTANTS = { "Does NOT work while offline.

    " + "getServerRequiredHackingLevel(hostname/ip)
    Returns the required hacking level of a server. The argument passed in must be a string with either the " + "hostname or IP or the target server. Does NOT work while offline

    " + + "getServerNumPortsRequired(hostname/ip)
    Returns the number of open ports required to successfully run NUKE.exe on a server. The argument " + + "passed in must be a string with either the hostname or IP of the target server. Does NOT work while offline

    " + "fileExists(filename, [hostname/ip])
    Returns a boolean (true or false) indicating whether the specified file exists on a server. " + "The first argument must be a string with the name of the file. A file can either be a script or a program. A script name is case-sensitive, but a " + "program is not. For example, fileExists('brutessh.exe') will work fine, even though the actual program is named BruteSSH.exe.

    " + @@ -657,11 +664,17 @@ CONSTANTS = { Changelog: "v0.23.0
    " + "-You can now purchase multiple Augmentations in a run. When you purchase an Augmentation you will lose money equal to the price " + - "and then the cost of purchasing another Augmentation during this run will be increased by 50%. You do not gain the benefits " + + "and then the cost of purchasing another Augmentation during this run will be increased by 75%. You do not gain the benefits " + "of your purchased Augmentations until you install them. This installation can be done through the 'Augmentation' tab. When " + "you install your Augmentations, your game will reset like before.
    " + - "-Reputation needed to gain a favor from faction decreased from 7500 to 6000
    " + - "-Reputation needed to gain a favor from company decreased from 5000 to 4500
    " + + "-Reputation needed to gain a favor from faction decreased from 7500 to 6500
    " + + "-Reputation needed to gain a favor from company increased from 5000 to 6000
    " + + "-Reputation cost of all Augmentations increased by 16%
    " + + "-Higher positions at companies now grant slightly more reputation for working
    " + + "-Added getServerMaxMoney() Netscript function
    " + + "-Added scan() Netscript function
    " + + "-Added getServerNumPortsRequired() Netscript function
    " + + "-There is now no additional RAM cost incurred when multithreading a script

    " + "v0.22.1
    " + "-You no longer lose progress on creating programs when cancelling your work. Your progress will be saved and you will pick up " + "where you left off when you start working on it again
    " + @@ -841,31 +854,17 @@ CONSTANTS = { "-You can now see what an Augmentation does and its price even while its locked

    ", LatestUpdate: - "v0.22.1
    " + - "-You no longer lose progress on creating programs when cancelling your work. Your progress will be saved and you will pick up " + - "where you left off when you start working on it again
    " + - "-Added two new programs: AutoLink.exe and ServerProfiler.exe
    " + - "-Fixed bug with Faction Field work reputation gain

    " + - "v0.22.0 - Major rebalancing, optimization, and favor system
    " + - "-Significantly nerfed most augmentations
    " + - "-Almost every server with a required hacking level of 200 or more now has slightly randomized server parameters. This means that after every Augmentation " + - "purchase, the required hacking level, base security level, and growth factor of these servers will all be slightly different
    " + - "-The hacking speed multiplier now increases rather than decreases. The hacking time is now divided by your hacking speed " + - "multiplier rather than multiplied. In other words, a higher hacking speed multiplier is better
    " + - "-Servers now have a minimum server security, which is approximately one third of their starting ('base') server security
    " + - "-If you do not steal any money from a server, then you gain hacking experience equal to the amount you would have gained " + - "had you failed the hack
    " + - "-The effects of grow() were increased by 50%
    " + - "-grow() and weaken() now give hacking experience based on the server's base security level, rather than a flat exp amount
    " + - "-Slightly reduced amount of exp gained from hack(), weaken(), and grow()
    " + - "-Rebalanced formulas that determine crime success
    " + - "-Reduced RAM cost for multithreading a script. The RAM multiplier for each thread was reduced from 1.02 to 1.005
    " + - "-Optimized Script objects so they take less space in the save file
    " + - "-Added getServerBaseSecurityLevel() Netscript function
    " + - "-New favor system for companies and factions. Earning reputation at a company/faction will give you favor for that entity when you " + - "reset after installing an Augmentation. This favor persists through the rest of the game. The more favor you have, the faster you will earn " + - "reputation with that faction/company
    " + - "-You can no longer donate to a faction for reputation until you have 150 favor with that faction
    " + - "-Added unalias Terminal command
    " + - "-Changed requirements for endgame Factions
    ", + "v0.23.0
    " + + "-You can now purchase multiple Augmentations in a run. When you purchase an Augmentation you will lose money equal to the price " + + "and then the cost of purchasing another Augmentation during this run will be increased by 75%. You do not gain the benefits " + + "of your purchased Augmentations until you install them. This installation can be done through the 'Augmentation' tab. When " + + "you install your Augmentations, your game will reset like before.
    " + + "-Reputation needed to gain a favor from faction decreased from 7500 to 6500
    " + + "-Reputation needed to gain a favor from company increased from 5000 to 6000
    " + + "-Reputation cost of all Augmentations increased by 16%
    " + + "-Higher positions at companies now grant slightly more reputation for working
    " + + "-Added getServerMaxMoney() Netscript function
    " + + "-Added scan() Netscript function
    " + + "-Added getServerNumPortsRequired() Netscript function
    " + + "-There is now no additional RAM cost incurred when multithreading a script

    ", } diff --git a/src/NetscriptEvaluator.js b/src/NetscriptEvaluator.js index 3c9453de9..a939af495 100644 --- a/src/NetscriptEvaluator.js +++ b/src/NetscriptEvaluator.js @@ -202,6 +202,22 @@ function evaluate(exp, workerScript) { }, function(e) { reject(e); }); + + } else if (exp.func.value == "scan") { + if (exp.args.length != 0) { + return reject(makeRuntimeRejectMsg(workerScript, "scan() call has incorrect number of arguments. Takes 0 arguments")); + } + var currServ = getServer(workerScript.serverIp); + if (currServ == null) { + return reject(makeRuntimeRejectMsg(workerScript, "Could not find server ip for this script. This is a bug please contact game developer")); + } + var res = []; + for (var i = 0; i < currServ.serversOnNetwork.length; ++i) { + var thisServ = getServer(currServ.serversOnNetwork[i]); + if (thisServ == null) {continue;} + res.push({type:"str", value: thisServ.hostname}); + } + resolve(res); } else if (exp.func.value == "nuke") { var p = netscriptRunProgram(exp, workerScript, Programs.NukeProgram); p.then(function(res) { @@ -546,6 +562,22 @@ function evaluate(exp, workerScript) { }, function(e) { reject(e); }); + } else if (exp.func.value == "getServerNumPortsRequired") { + if (exp.args.length != 1) { + return reject(makeRuntimeRejectMsg(workerScript, "getServerNumPortsRequired() call has incorrect number of arguments. Takes 1 argument")); + } + var ipPromise = evaluate(exp.args[0], workerScript); + ipPromise.then(function(ip) { + var server = getServer(ip); + if (server == null) { + workerScript.scriptRef.log("getServerNumPortsRequired() failed. Invalid IP or hostname passed in: " + ip); + return reject(makeRuntimeRejectMsg(workerScript, "Invalid IP or hostname passed into getServerNumPortsRequired() command")); + } + workerScript.scriptRef.log("getServerNumPortsRequired() returned " + formatNumber(server.numOpenPortsRequired, 0) + " for " + server.hostname); + resolve(server.numOpenPortsRequired); + }, function(e) { + reject(e); + }); } else if (exp.func.value == "fileExists") { if (exp.args.length != 1 && exp.args.length != 2) { return reject(makeRuntimeRejectMsg(workerScript, "fileExists() call has incorrect number of arguments. Takes 1 or 2 arguments")); @@ -640,6 +672,12 @@ function evaluate(exp, workerScript) { if (exp.args.length != 1) { return reject(makeRuntimeRejectMsg(workerScript, "val() call has incorrect number of arguments. Takes 1 arguments")); } + var valPromise = evaluate(exp.args[0], workerScript); + valPromise.then(function(val) { + resolve(val); + }, function(e) { + reject(e); + }); } else { reject(makeRuntimeRejectMsg(workerScript, "Invalid function: " + exp.func.value)); } diff --git a/src/SaveObject.js b/src/SaveObject.js index c04847369..6d4e5aaf1 100644 --- a/src/SaveObject.js +++ b/src/SaveObject.js @@ -34,7 +34,6 @@ BitburnerSaveObject.prototype.saveGame = function() { this.CompaniesSave = JSON.stringify(Companies); this.FactionsSave = JSON.stringify(Factions); this.SpecialServerIpsSave = JSON.stringify(SpecialServerIps); - //this.AugmentationsSave = JSON.stringify(Augmentations); this.AliasesSave = JSON.stringify(Aliases); this.MessagesSave = JSON.stringify(Messages); this.VersionSave = JSON.stringify(CONSTANTS.Version); @@ -95,7 +94,7 @@ loadGame = function(saveObj) { } } } - if (CONSTANTS.Version == "0.23.0.BETA") { + if (CONSTANTS.Version == "0.23.0") { Augmentations = JSON.parse(saveObj.AugmentationsSave, Reviver); } createNewUpdateText(); @@ -168,7 +167,7 @@ loadImportedGame = function(saveObj, saveString) { } } } - if (CONSTANTS.Version == "0.23.0.BETA") { + if (CONSTANTS.Version == "0.23.0") { Augmentations = JSON.parse(saveObj.AugmentationsSave, Reviver); } createNewUpdateText(); diff --git a/src/Script.js b/src/Script.js index 9ac11c611..211e9bd4d 100644 --- a/src/Script.js +++ b/src/Script.js @@ -136,6 +136,7 @@ Script.prototype.updateRamUsage = function() { var hackCount = numOccurrences(codeCopy, "hack("); var growCount = numOccurrences(codeCopy, "grow("); var weakenCount = numOccurrences(codeCopy, "weaken("); + var scanCount = numOccurrences(codeCopy, "scan("); var nukeCount = numOccurrences(codeCopy, "nuke("); var brutesshCount = numOccurrences(codeCopy, "brutessh("); var ftpcrackCount = numOccurrences(codeCopy, "ftpcrack("); @@ -168,6 +169,7 @@ Script.prototype.updateRamUsage = function() { (hackCount * CONSTANTS.ScriptHackRamCost) + (growCount * CONSTANTS.ScriptGrowRamCost) + (weakenCount * CONSTANTS.ScriptWeakenRamCost) + + (scanCount * CONSTANTS.ScriptScanRamCost) + (nukeCount * CONSTANTS.ScriptNukeRamCost) + (brutesshCount * CONSTANTS.ScriptBrutesshRamCost) + (ftpcrackCount * CONSTANTS.ScriptFtpcrackRamCost) + diff --git a/utils/PurchaseAugmentationBox.js b/utils/PurchaseAugmentationBox.js index 412ce413d..81186eacc 100644 --- a/utils/PurchaseAugmentationBox.js +++ b/utils/PurchaseAugmentationBox.js @@ -98,17 +98,18 @@ purchaseAugmentationBoxCreate = function(aug, fac) { var mult = Math.pow(CONSTANTS.NeuroFluxGovernorLevelMult, nextLevel); aug.setRequirements(500 * mult, 750000 * mult); - for (var i = 0; i < Player.queuedAugmentations.length; ++i) { - aug.baseCost *= 1.5; + for (var i = 0; i < Player.queuedAugmentations.length-1; ++i) { + aug.baseCost *= CONSTANTS.MultipleAugMultiplier; } } - for (var name in Augmentations) { - if (Augmentations.hasOwnProperty(name) && name != AugmentationNames.NeuroFluxGovernor) { - Augmentations[name].baseCost *= 1.5; + if (Augmentations.hasOwnProperty(name)) { + Augmentations[name].baseCost *= CONSTANTS.MultipleAugMultiplier; } } + + displayFactionAugmentations(fac.name); } else { dialogBoxCreate("You don't have enough money to purchase this Augmentation!"); } diff --git a/utils/PurchaseRamForHomeBox.js b/utils/PurchaseRamForHomeBox.js index a59ed0bf9..c6d0e0798 100644 --- a/utils/PurchaseRamForHomeBox.js +++ b/utils/PurchaseRamForHomeBox.js @@ -36,7 +36,7 @@ purchaseRamForHomeBoxCreate = function() { //Calculate cost //Have cost increase by some percentage each time RAM has been upgraded var cost = currentRam * CONSTANTS.BaseCostFor1GBOfRamHome; - var mult = Math.pow(1.45, numUpgrades); + var mult = Math.pow(1.44, numUpgrades); cost = cost * mult; purchaseRamForHomeBoxSetText("Would you like to purchase additional RAM for your home computer?

    " +