mirror of
https://github.com/bitburner-official/bitburner-src.git
synced 2026-04-16 14:28:36 +02:00
Compare commits
59 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
52a80ad236 | ||
|
|
b2aafea656 | ||
|
|
135df8703c | ||
|
|
4743801e86 | ||
|
|
4e5ebcfe6f | ||
|
|
80b703639e | ||
|
|
0afdba8f38 | ||
|
|
925e96345d | ||
|
|
db2bf79e3b | ||
|
|
6f330efc44 | ||
|
|
708c73fa0f | ||
|
|
c7febd5551 | ||
|
|
ddbdf66d00 | ||
|
|
e572c6dad8 | ||
|
|
ff097db1e2 | ||
|
|
ad12f0e551 | ||
|
|
93f8785ec6 | ||
|
|
69124e7146 | ||
|
|
8a42f6e49c | ||
|
|
2ac4cd41bb | ||
|
|
28584c8461 | ||
|
|
1eddddd14f | ||
|
|
42e9a368b4 | ||
|
|
40713a4112 | ||
|
|
8e79658e67 | ||
|
|
6efc3ec75e | ||
|
|
9840e1f4eb | ||
|
|
7cdca5e813 | ||
|
|
d170693da4 | ||
|
|
31a9c041b4 | ||
|
|
ce7c2c309c | ||
|
|
29abffd464 | ||
|
|
ae4b8228f7 | ||
|
|
04bc2bebdd | ||
|
|
8f30e60d08 | ||
|
|
e8aa1851c5 | ||
|
|
7232a786ed | ||
|
|
2507899762 | ||
|
|
26149d5a01 | ||
|
|
670394ca2f | ||
|
|
e0745d7757 | ||
|
|
dc79f7a940 | ||
|
|
bf4d841f88 | ||
|
|
4c30f107e3 | ||
|
|
c9fe8d9b65 | ||
|
|
29ea1281e0 | ||
|
|
3ec54bcdd8 | ||
|
|
4892f0bd79 | ||
|
|
62c571ef3a | ||
|
|
6c57d548ec | ||
|
|
6c0b5b3ed9 | ||
|
|
f288d982db | ||
|
|
101834fcaf | ||
|
|
642c7a107a | ||
|
|
63da8d709a | ||
|
|
753a1f1193 | ||
|
|
726c36f276 | ||
|
|
640795dbe9 | ||
|
|
802f28082d |
257
.eslintrc.js
257
.eslintrc.js
@@ -2,91 +2,104 @@ module.exports = {
|
||||
"env": {
|
||||
"browser": true,
|
||||
"commonjs": true,
|
||||
"es6": false
|
||||
"es6": false,
|
||||
},
|
||||
"extends": "eslint:recommended",
|
||||
"extends": [
|
||||
"eslint:recommended",
|
||||
"plugin:@typescript-eslint/recommended",
|
||||
],
|
||||
"parser": "@typescript-eslint/parser",
|
||||
"parserOptions": {
|
||||
"ecmaVersion": 8,
|
||||
"sourceType": "module",
|
||||
"ecmaFeatures": {
|
||||
"experimentalObjectRestSpread": true
|
||||
}
|
||||
"experimentalObjectRestSpread": true,
|
||||
},
|
||||
},
|
||||
"plugins": [
|
||||
'@typescript-eslint',
|
||||
],
|
||||
"rules": {
|
||||
"accessor-pairs": [
|
||||
"error",
|
||||
{
|
||||
"setWithoutGet": true,
|
||||
"getWithoutSet": false
|
||||
}
|
||||
"getWithoutSet": false,
|
||||
},
|
||||
],
|
||||
"array-bracket-newline": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"array-bracket-spacing": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"array-callback-return": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"array-element-newline": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"arrow-body-style": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"arrow-parens": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"arrow-spacing": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"block-scoped-var": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"block-spacing": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"brace-style": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"callback-return": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"camelcase": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"capitalized-comments": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"class-methods-use-this": [
|
||||
"error"
|
||||
"off",
|
||||
],
|
||||
"comma-dangle": [
|
||||
"off"
|
||||
"error", {
|
||||
"arrays": "always-multiline",
|
||||
"objects": "always-multiline",
|
||||
"imports": "always-multiline",
|
||||
"exports": "always-multiline",
|
||||
"functions": "always-multiline",
|
||||
}
|
||||
],
|
||||
"comma-spacing": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"comma-style": [
|
||||
"error",
|
||||
"last"
|
||||
"last",
|
||||
],
|
||||
"complexity": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"computed-property-spacing": [
|
||||
"off",
|
||||
"never"
|
||||
"never",
|
||||
],
|
||||
"consistent-return": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"consistent-this": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"constructor-super": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"curly": [
|
||||
"off"
|
||||
@@ -99,203 +112,202 @@ module.exports = {
|
||||
"property"
|
||||
],
|
||||
"dot-notation": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"eol-last": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"eqeqeq": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"for-direction": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"func-call-spacing": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"func-name-matching": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"func-names": [
|
||||
"off",
|
||||
"never"
|
||||
"never",
|
||||
],
|
||||
"func-style": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"function-paren-newline": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"generator-star-spacing": [
|
||||
"error",
|
||||
"before"
|
||||
"before",
|
||||
],
|
||||
"getter-return": [
|
||||
"error",
|
||||
{
|
||||
"allowImplicit": false
|
||||
}
|
||||
"allowImplicit": false,
|
||||
},
|
||||
],
|
||||
"global-require": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"guard-for-in": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"handle-callback-err": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"id-blacklist": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"id-length": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"id-match": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"implicit-arrow-linebreak": [
|
||||
"error",
|
||||
"beside"
|
||||
"beside",
|
||||
],
|
||||
"indent": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"indent-legacy": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"init-declarations": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"jsx-quotes": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"key-spacing": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"keyword-spacing": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"line-comment-position": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"linebreak-style": [
|
||||
"error",
|
||||
"windows"
|
||||
"off", // Line endings automatically converted to LF on git commit so probably shouldn't care about it here
|
||||
],
|
||||
"lines-around-comment": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"lines-around-directive": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"lines-between-class-members": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"max-depth": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"max-len": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"max-lines": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"max-nested-callbacks": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"max-params": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"max-statements": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"max-statements-per-line": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"multiline-comment-style": [
|
||||
"off",
|
||||
"starred-block"
|
||||
"starred-block",
|
||||
],
|
||||
"multiline-ternary": [
|
||||
"off",
|
||||
"never"
|
||||
"never",
|
||||
],
|
||||
"new-cap": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"new-parens": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"newline-after-var": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"newline-before-return": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"newline-per-chained-call": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"no-alert": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-array-constructor": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-await-in-loop": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-bitwise": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"no-buffer-constructor": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-caller": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-case-declarations": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-catch-shadow": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-class-assign": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-compare-neg-zero": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-cond-assign": [
|
||||
"off",
|
||||
"except-parens"
|
||||
"except-parens",
|
||||
],
|
||||
"no-confusing-arrow": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-console": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"no-const-assign": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-constant-condition": [
|
||||
"error",
|
||||
{
|
||||
"checkLoops": false
|
||||
}
|
||||
"checkLoops": false,
|
||||
},
|
||||
],
|
||||
"no-continue": [
|
||||
"off"
|
||||
"off",
|
||||
],
|
||||
"no-control-regex": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-debugger": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-delete-var": [
|
||||
"error"
|
||||
"error",
|
||||
],
|
||||
"no-div-regex": [
|
||||
"error"
|
||||
@@ -346,11 +358,7 @@ module.exports = {
|
||||
"error"
|
||||
],
|
||||
"no-extra-parens": [
|
||||
"error",
|
||||
"all",
|
||||
{
|
||||
"conditionalAssign": false
|
||||
}
|
||||
"off"
|
||||
],
|
||||
"no-extra-semi": [
|
||||
"off"
|
||||
@@ -367,9 +375,6 @@ module.exports = {
|
||||
"no-extra-label": [
|
||||
"error"
|
||||
],
|
||||
"no-extra-parens": [
|
||||
"off"
|
||||
],
|
||||
"no-fallthrough": [
|
||||
"off"
|
||||
],
|
||||
@@ -853,5 +858,53 @@ module.exports = {
|
||||
"error",
|
||||
"never"
|
||||
]
|
||||
}
|
||||
},
|
||||
"overrides": [
|
||||
{
|
||||
// TypeScript configuration
|
||||
"files": [ "**/*.ts", "**/*.tsx" ],
|
||||
"parser": "@typescript-eslint/parser",
|
||||
"plugins": [ "@typescript-eslint" ],
|
||||
"extends": [
|
||||
"plugin:@typescript-eslint/recommended",
|
||||
],
|
||||
"rules": {
|
||||
"lines-between-class-members": "off",
|
||||
"no-empty-pattern": "off",
|
||||
"no-useless-constructor": [
|
||||
"off", // Valid for typescript due to property ctor shorthand
|
||||
],
|
||||
"@typescript-eslint/ban-ts-comment": "off",
|
||||
"@typescript-eslint/ban-ts-ignore": "off",
|
||||
"@typescript-eslint/camelcase": "off",
|
||||
"@typescript-eslint/explicit-function-return-type": ["error", {
|
||||
"allowExpressions": true,
|
||||
}],
|
||||
"@typescript-eslint/member-delimiter-style": ["error", {
|
||||
"multiline": {
|
||||
"delimiter": "semi",
|
||||
"requireLast": true,
|
||||
},
|
||||
"singleline": {
|
||||
"delimiter": "semi",
|
||||
"requireLast": false,
|
||||
}
|
||||
}],
|
||||
"@typescript-eslint/member-ordering": ["error", {
|
||||
"default": [
|
||||
"signature",
|
||||
"static-field",
|
||||
"instance-field",
|
||||
"abstract-field",
|
||||
"constructor",
|
||||
"instance-method",
|
||||
"abstract-method",
|
||||
"static-method",
|
||||
]
|
||||
}],
|
||||
"@typescript-eslint/no-explicit-any": "off",
|
||||
"@typescript-eslint/no-use-before-define": "off",
|
||||
}
|
||||
}
|
||||
]
|
||||
};
|
||||
23
README_contribution.md
Normal file
23
README_contribution.md
Normal file
@@ -0,0 +1,23 @@
|
||||
Deploying a new version
|
||||
-----------------------
|
||||
|
||||
Update the following
|
||||
- `src/Constants.ts` `Version` and `LatestUpdate`
|
||||
- `package.json` `version`
|
||||
- `doc/source/conf.py` `version` and `release`
|
||||
- `doc/source/changelog.rst`
|
||||
- post to discord
|
||||
- post to reddit.com/r/Bitburner
|
||||
|
||||
Deploying `dev` to the Beta Branch
|
||||
----------------------------------
|
||||
|
||||
TODO
|
||||
|
||||
Development Workflow Best Practices
|
||||
-----------------------------------
|
||||
|
||||
- Work in a new branch forked from the `dev` branch to isolate your new code
|
||||
- Keep code-changes on a branch as small as possible. This makes it easier for code review. Each branch should be its own independent feature.
|
||||
- Regularly rebase your branch against `dev` to make sure you have the latest updates pulled.
|
||||
- When merging, always merge your branch into `dev`. When releasing a new update, then merge `dev` into `master`
|
||||
24
css/casino.scss
Normal file
24
css/casino.scss
Normal file
@@ -0,0 +1,24 @@
|
||||
.casino-card {
|
||||
padding: 10px;
|
||||
border: solid 1px #808080;
|
||||
background-color: white;
|
||||
display: inline-block;
|
||||
border-radius: 10px;
|
||||
font-size: 14pt;
|
||||
text-align: center;
|
||||
margin: 3px;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.casino-card .value {
|
||||
font-size:15pt;
|
||||
font-family: sans-serif;
|
||||
}
|
||||
|
||||
.casino-card.red {
|
||||
color: red;
|
||||
}
|
||||
|
||||
.casino-card.black {
|
||||
color: black;
|
||||
}
|
||||
@@ -184,5 +184,4 @@
|
||||
|
||||
#infiltration-buttons .a-link-button {
|
||||
display: inline;
|
||||
width: 25%;
|
||||
}
|
||||
|
||||
5
css/milestones.scss
Normal file
5
css/milestones.scss
Normal file
@@ -0,0 +1,5 @@
|
||||
#milestones-container {
|
||||
position: fixed;
|
||||
padding: 6px;
|
||||
width: 60%;
|
||||
}
|
||||
@@ -228,14 +228,15 @@ a:visited {
|
||||
}
|
||||
|
||||
.status-text {
|
||||
display: inline-block;
|
||||
position: fixed;
|
||||
z-index: 2;
|
||||
-webkit-animation: status-text 3s 1;
|
||||
}
|
||||
|
||||
#status-text-container {
|
||||
background-color: transparent;
|
||||
position:absolute;
|
||||
top:0;
|
||||
left:50%;
|
||||
}
|
||||
|
||||
#status-text {
|
||||
@@ -356,10 +357,27 @@ a:visited {
|
||||
color: $my-stat-cha-color;
|
||||
}
|
||||
|
||||
.reputation {
|
||||
color: $light-yellow;
|
||||
}
|
||||
|
||||
.smallfont {
|
||||
font-size: $defaultFontSize * 0.8125;
|
||||
}
|
||||
|
||||
.samefont {
|
||||
font-size: inherit;
|
||||
}
|
||||
|
||||
.noscrollbar {
|
||||
-ms-overflow-style: none; /* IE and Edge */
|
||||
scrollbar-width: none; /* Firefox */
|
||||
}
|
||||
|
||||
.noscrollbar::-webkit-scrollbar {
|
||||
display: none;
|
||||
}
|
||||
|
||||
input[type=checkbox] {
|
||||
filter: invert(1) sepia(1) hue-rotate(41deg) brightness(100%) saturate(10);
|
||||
}
|
||||
@@ -395,4 +413,12 @@ input[type=checkbox] {
|
||||
height: 10px;
|
||||
background: var(--my-font-color);
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.noselect {
|
||||
-moz-user-select: -moz-none;
|
||||
-khtml-user-select: none;
|
||||
-webkit-user-select: none;
|
||||
-ms-user-select: none;
|
||||
user-select: none;
|
||||
}
|
||||
@@ -85,3 +85,45 @@
|
||||
.tooltip:hover .tooltiptextlow {
|
||||
visibility: visible;
|
||||
}
|
||||
|
||||
.copy_tooltip {
|
||||
position: relative;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.copy_tooltip_copied {
|
||||
color: #fff;
|
||||
transition: color 0.3s;
|
||||
}
|
||||
|
||||
.copy_tooltip .copy_tooltip_text {
|
||||
visibility: hidden;
|
||||
font-size: 15px;
|
||||
padding: 5px;
|
||||
background-color: var(--my-background-color);
|
||||
color: #fff;
|
||||
text-align: center;
|
||||
position: absolute;
|
||||
z-index: 1;
|
||||
top: 120%;
|
||||
left: 5%;
|
||||
opacity: 0;
|
||||
border: 2px solid var(--my-highlight-color);
|
||||
}
|
||||
|
||||
.copy_tooltip .copy_tooltip_text::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 50%;
|
||||
margin-left: -6px;
|
||||
border-width: 8px;
|
||||
border-style: solid;
|
||||
border-color: transparent transparent white transparent;
|
||||
}
|
||||
|
||||
.copy_tooltip .copy_tooltip_text_visible {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
transition: opacity 0.3s;
|
||||
}
|
||||
4
dist/engine.bundle.js
vendored
4
dist/engine.bundle.js
vendored
File diff suppressed because one or more lines are too long
2
dist/engineStyle.bundle.js
vendored
2
dist/engineStyle.bundle.js
vendored
@@ -1,2 +1,2 @@
|
||||
!function(n){function t(t){for(var e,i,f=t[0],c=t[1],l=t[2],p=0,s=[];p<f.length;p++)i=f[p],u[i]&&s.push(u[i][0]),u[i]=0;for(e in c)Object.prototype.hasOwnProperty.call(c,e)&&(n[e]=c[e]);for(a&&a(t);s.length;)s.shift()();return r.push.apply(r,l||[]),o()}function o(){for(var n,t=0;t<r.length;t++){for(var o=r[t],e=!0,f=1;f<o.length;f++){var c=o[f];0!==u[c]&&(e=!1)}e&&(r.splice(t--,1),n=i(i.s=o[0]))}return n}var e={},u={1:0},r=[];function i(t){if(e[t])return e[t].exports;var o=e[t]={i:t,l:!1,exports:{}};return n[t].call(o.exports,o,o.exports,i),o.l=!0,o.exports}i.m=n,i.c=e,i.d=function(n,t,o){i.o(n,t)||Object.defineProperty(n,t,{enumerable:!0,get:o})},i.r=function(n){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(n,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(n,"__esModule",{value:!0})},i.t=function(n,t){if(1&t&&(n=i(n)),8&t)return n;if(4&t&&"object"==typeof n&&n&&n.__esModule)return n;var o=Object.create(null);if(i.r(o),Object.defineProperty(o,"default",{enumerable:!0,value:n}),2&t&&"string"!=typeof n)for(var e in n)i.d(o,e,function(t){return n[t]}.bind(null,e));return o},i.n=function(n){var t=n&&n.__esModule?function(){return n.default}:function(){return n};return i.d(t,"a",t),t},i.o=function(n,t){return Object.prototype.hasOwnProperty.call(n,t)},i.p="";var f=window.webpackJsonp=window.webpackJsonp||[],c=f.push.bind(f);f.push=t,f=f.slice();for(var l=0;l<f.length;l++)t(f[l]);var a=c;r.push([377,0]),o()}({320:function(n,t,o){},322:function(n,t,o){},324:function(n,t,o){},326:function(n,t,o){},328:function(n,t,o){},330:function(n,t,o){},332:function(n,t,o){},334:function(n,t,o){},336:function(n,t,o){},338:function(n,t,o){},340:function(n,t,o){},342:function(n,t,o){},344:function(n,t,o){},346:function(n,t,o){},348:function(n,t,o){},350:function(n,t,o){},352:function(n,t,o){},354:function(n,t,o){},356:function(n,t,o){},358:function(n,t,o){},360:function(n,t,o){},362:function(n,t,o){},364:function(n,t,o){},366:function(n,t,o){},368:function(n,t,o){},370:function(n,t,o){},372:function(n,t,o){},374:function(n,t,o){},377:function(n,t,o){"use strict";o.r(t);o(376),o(374),o(372),o(370),o(368),o(366),o(364),o(362),o(360),o(358),o(356),o(354),o(352),o(350),o(348),o(346),o(344),o(342),o(340),o(338),o(336),o(334),o(332),o(330),o(328),o(326),o(324),o(322),o(320)}});
|
||||
!function(n){function t(t){for(var e,i,f=t[0],c=t[1],l=t[2],p=0,s=[];p<f.length;p++)i=f[p],u[i]&&s.push(u[i][0]),u[i]=0;for(e in c)Object.prototype.hasOwnProperty.call(c,e)&&(n[e]=c[e]);for(a&&a(t);s.length;)s.shift()();return r.push.apply(r,l||[]),o()}function o(){for(var n,t=0;t<r.length;t++){for(var o=r[t],e=!0,f=1;f<o.length;f++){var c=o[f];0!==u[c]&&(e=!1)}e&&(r.splice(t--,1),n=i(i.s=o[0]))}return n}var e={},u={1:0},r=[];function i(t){if(e[t])return e[t].exports;var o=e[t]={i:t,l:!1,exports:{}};return n[t].call(o.exports,o,o.exports,i),o.l=!0,o.exports}i.m=n,i.c=e,i.d=function(n,t,o){i.o(n,t)||Object.defineProperty(n,t,{enumerable:!0,get:o})},i.r=function(n){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(n,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(n,"__esModule",{value:!0})},i.t=function(n,t){if(1&t&&(n=i(n)),8&t)return n;if(4&t&&"object"==typeof n&&n&&n.__esModule)return n;var o=Object.create(null);if(i.r(o),Object.defineProperty(o,"default",{enumerable:!0,value:n}),2&t&&"string"!=typeof n)for(var e in n)i.d(o,e,function(t){return n[t]}.bind(null,e));return o},i.n=function(n){var t=n&&n.__esModule?function(){return n.default}:function(){return n};return i.d(t,"a",t),t},i.o=function(n,t){return Object.prototype.hasOwnProperty.call(n,t)},i.p="";var f=window.webpackJsonp=window.webpackJsonp||[],c=f.push.bind(f);f.push=t,f=f.slice();for(var l=0;l<f.length;l++)t(f[l]);var a=c;r.push([842,0]),o()}({781:function(n,t,o){},783:function(n,t,o){},785:function(n,t,o){},787:function(n,t,o){},789:function(n,t,o){},791:function(n,t,o){},793:function(n,t,o){},795:function(n,t,o){},797:function(n,t,o){},799:function(n,t,o){},801:function(n,t,o){},803:function(n,t,o){},805:function(n,t,o){},807:function(n,t,o){},809:function(n,t,o){},811:function(n,t,o){},813:function(n,t,o){},815:function(n,t,o){},817:function(n,t,o){},819:function(n,t,o){},821:function(n,t,o){},823:function(n,t,o){},825:function(n,t,o){},827:function(n,t,o){},829:function(n,t,o){},831:function(n,t,o){},833:function(n,t,o){},835:function(n,t,o){},837:function(n,t,o){},839:function(n,t,o){},842:function(n,t,o){"use strict";o.r(t);o(841),o(839),o(837),o(835),o(833),o(831),o(829),o(827),o(825),o(823),o(821),o(819),o(817),o(815),o(813),o(811),o(809),o(807),o(805),o(803),o(801),o(799),o(797),o(795),o(793),o(791),o(789),o(787),o(785),o(783),o(781)}});
|
||||
//# sourceMappingURL=engineStyle.bundle.js.map
|
||||
95
dist/engineStyle.css
vendored
95
dist/engineStyle.css
vendored
@@ -250,13 +250,14 @@ a:visited {
|
||||
opacity: 0; } }
|
||||
|
||||
.status-text {
|
||||
display: inline-block;
|
||||
position: fixed;
|
||||
z-index: 2;
|
||||
-webkit-animation: status-text 3s 1; }
|
||||
|
||||
#status-text-container {
|
||||
background-color: transparent; }
|
||||
background-color: transparent;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 50%; }
|
||||
|
||||
#status-text {
|
||||
background-color: transparent;
|
||||
@@ -353,9 +354,24 @@ a:visited {
|
||||
.charisma-purple {
|
||||
color: #a671d1; }
|
||||
|
||||
.reputation {
|
||||
color: #faffdf; }
|
||||
|
||||
.smallfont {
|
||||
font-size: 13px; }
|
||||
|
||||
.samefont {
|
||||
font-size: inherit; }
|
||||
|
||||
.noscrollbar {
|
||||
-ms-overflow-style: none;
|
||||
/* IE and Edge */
|
||||
scrollbar-width: none;
|
||||
/* Firefox */ }
|
||||
|
||||
.noscrollbar::-webkit-scrollbar {
|
||||
display: none; }
|
||||
|
||||
input[type=checkbox] {
|
||||
filter: invert(1) sepia(1) hue-rotate(41deg) brightness(100%) saturate(10); }
|
||||
|
||||
@@ -387,6 +403,13 @@ input[type=checkbox] {
|
||||
background: var(--my-font-color);
|
||||
cursor: pointer; }
|
||||
|
||||
.noselect {
|
||||
-moz-user-select: -moz-none;
|
||||
-khtml-user-select: none;
|
||||
-webkit-user-select: none;
|
||||
-ms-user-select: none;
|
||||
user-select: none; }
|
||||
|
||||
/* COLORS */
|
||||
/* Attributes */
|
||||
/* Styling for tooltip-style elements */
|
||||
@@ -460,6 +483,43 @@ input[type=checkbox] {
|
||||
.tooltip:hover .tooltiptextlow {
|
||||
visibility: visible; }
|
||||
|
||||
.copy_tooltip {
|
||||
position: relative;
|
||||
display: inline-block; }
|
||||
|
||||
.copy_tooltip_copied {
|
||||
color: #fff;
|
||||
transition: color 0.3s; }
|
||||
|
||||
.copy_tooltip .copy_tooltip_text {
|
||||
visibility: hidden;
|
||||
font-size: 15px;
|
||||
padding: 5px;
|
||||
background-color: var(--my-background-color);
|
||||
color: #fff;
|
||||
text-align: center;
|
||||
position: absolute;
|
||||
z-index: 1;
|
||||
top: 120%;
|
||||
left: 5%;
|
||||
opacity: 0;
|
||||
border: 2px solid var(--my-highlight-color); }
|
||||
|
||||
.copy_tooltip .copy_tooltip_text::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
bottom: 100%;
|
||||
left: 50%;
|
||||
margin-left: -6px;
|
||||
border-width: 8px;
|
||||
border-style: solid;
|
||||
border-color: transparent transparent white transparent; }
|
||||
|
||||
.copy_tooltip .copy_tooltip_text_visible {
|
||||
visibility: visible;
|
||||
opacity: 1;
|
||||
transition: opacity 0.3s; }
|
||||
|
||||
/* COLORS */
|
||||
/* Attributes */
|
||||
/**
|
||||
@@ -1315,8 +1375,7 @@ button {
|
||||
margin-top: 20px; }
|
||||
|
||||
#infiltration-buttons .a-link-button {
|
||||
display: inline;
|
||||
width: 25%; }
|
||||
display: inline; }
|
||||
|
||||
/**
|
||||
* Styling for the Augmentations UI. This is the page that displays all of the
|
||||
@@ -4948,5 +5007,31 @@ html {
|
||||
margin-left: 0px;
|
||||
margin-right: 0px; }
|
||||
|
||||
.casino-card {
|
||||
padding: 10px;
|
||||
border: solid 1px #808080;
|
||||
background-color: white;
|
||||
display: inline-block;
|
||||
border-radius: 10px;
|
||||
font-size: 14pt;
|
||||
text-align: center;
|
||||
margin: 3px;
|
||||
font-weight: bold; }
|
||||
|
||||
.casino-card .value {
|
||||
font-size: 15pt;
|
||||
font-family: sans-serif; }
|
||||
|
||||
.casino-card.red {
|
||||
color: red; }
|
||||
|
||||
.casino-card.black {
|
||||
color: black; }
|
||||
|
||||
#milestones-container {
|
||||
position: fixed;
|
||||
padding: 6px;
|
||||
width: 60%; }
|
||||
|
||||
|
||||
/*# sourceMappingURL=engineStyle.css.map*/
|
||||
84
dist/vendor.bundle.js
vendored
84
dist/vendor.bundle.js
vendored
File diff suppressed because one or more lines are too long
@@ -35,7 +35,7 @@ List of Factions and their Requirements
|
||||
| Early Game | Faction Name | Requirements | Joining this Faction prevents |
|
||||
| Factions | | | you from joining: |
|
||||
+ +----------------+-----------------------------------------+-------------------------------+
|
||||
| | CyberSec | * Hack CSEC Manually | |
|
||||
| | CyberSec | * Install a backdoor on the CSEC server | |
|
||||
+ +----------------+-----------------------------------------+-------------------------------+
|
||||
| | Tian Di Hui | * $1m | |
|
||||
| | | * Hacking Level 50 | |
|
||||
@@ -74,13 +74,16 @@ List of Factions and their Requirements
|
||||
| | | | * New Tokyo |
|
||||
| | | | * Ishima |
|
||||
+---------------------+----------------+-----------------------------------------+-------------------------------+
|
||||
| Hacking | NiteSec | * Hack avmnite-02h manually | |
|
||||
| Groups | | * Home Computer RAM of at least 32GB | |
|
||||
| Hacking | NiteSec | * Install a backdoor on the avmnite-02h | |
|
||||
| Groups | | server | |
|
||||
| | | * Home Computer RAM of at least 32GB | |
|
||||
+ +----------------+-----------------------------------------+-------------------------------+
|
||||
| | The Black Hand | * Hack I.I.I.I manually | |
|
||||
| | The Black Hand | * Install a backdoor on the I.I.I.I | |
|
||||
| | | server | |
|
||||
| | | * Home Computer RAM of at least 64GB | |
|
||||
+ +----------------+-----------------------------------------+-------------------------------+
|
||||
| | Bitrunners | * Hack run4theh111z manually | |
|
||||
| | Bitrunners | * Install a backdoor on the run4theh111z| |
|
||||
| | | server | |
|
||||
| | | * Home Computer RAM of at least 128GB | |
|
||||
+---------------------+----------------+-----------------------------------------+-------------------------------+
|
||||
| Megacorporations | ECorp | * Have 200k reputation with | |
|
||||
@@ -112,7 +115,8 @@ List of Factions and their Requirements
|
||||
+ +----------------+-----------------------------------------+-------------------------------+
|
||||
| | Fulcrum Secret | * Have 250k reputation with | |
|
||||
| | Technologies | the Corporation | |
|
||||
| | | * Hack fulcrumassets manually | |
|
||||
| | | * Install a backdoor on the | |
|
||||
| | | fulcrumassets server | |
|
||||
+---------------------+----------------+-----------------------------------------+-------------------------------+
|
||||
| Criminal | Slum Snakes | * All Combat Stats of 30 | |
|
||||
| Organizations | | * -9 Karma | |
|
||||
|
||||
@@ -148,6 +148,14 @@ has root access, what ports are opened/closed, and also hacking-related informat
|
||||
such as an estimated chance to successfully hack, an estimate of how much money is
|
||||
available on the server, etc.
|
||||
|
||||
backdoor
|
||||
^^^^^^^^
|
||||
|
||||
Installs a backdoor on the current server. Root access is required to do this.
|
||||
|
||||
Servers will give different bonuses when you install a backdoor.
|
||||
This can pass faction tests or give bonsues such as discounts from companies.
|
||||
|
||||
buy
|
||||
^^^
|
||||
|
||||
|
||||
@@ -4,38 +4,320 @@ Changelog
|
||||
=========
|
||||
|
||||
|
||||
v0.49.2 - 2021-03-13 (hydroflame)
|
||||
v0.51.6 - 2021-04-28 Backdoor! (Community)
|
||||
-------
|
||||
|
||||
BN8
|
||||
**Backdoor**
|
||||
|
||||
* a new terminal command, backdoor, has been added to help differentiate
|
||||
between the terminal hack command and the netscript hack function. (@dewint)
|
||||
|
||||
**Milestones**
|
||||
|
||||
* A new tab under the Help menu has been added to guide players through the
|
||||
game.
|
||||
|
||||
**Casino**
|
||||
|
||||
* Blackjack has been added (@BigD)
|
||||
|
||||
**Netscript**
|
||||
|
||||
* 'prompt' now converts input to JSON.
|
||||
* 'getRunningScript' is a new netscript function that returns a bunch of
|
||||
data related to a running script.
|
||||
|
||||
**Coding contracts**
|
||||
|
||||
* trivial puzzles should no longer appear.
|
||||
|
||||
**Infiltration**
|
||||
|
||||
* All numbers are formatted like the rest of the game.
|
||||
|
||||
**Misc.**
|
||||
|
||||
* Server security is capped at 100.
|
||||
* Added option to quit a job.
|
||||
* 'cd' no longer works on unexistent folders.
|
||||
* cd with no arguments brings you back to top level folder (@Andreas)
|
||||
* 'softReset' documentation udpated.
|
||||
* Money tracker now accounts for going to the hospital manually.
|
||||
* codemirror is now the default editor (for new save files)
|
||||
* fix typo in dark web help text (@Rodeth)
|
||||
* so many documentation and typos fixes (@Pimgd)
|
||||
* A corruption visual effect has been added to location with servers that
|
||||
have backdoor installed. (@dewint)
|
||||
|
||||
|
||||
v0.51.5 - 2021-04-20 Flags! (hydroflame)
|
||||
----------------------------------------
|
||||
|
||||
**Netscript**
|
||||
|
||||
* 'flags' is a new function that helps script handle flags.
|
||||
This is subject to change if it doesn't meet the need of the players.
|
||||
* 'ps' now returns the pid.
|
||||
* 'tail' now works with pid as first argument.
|
||||
* 'tail' hostname defaults to current server. (like the documentation says)
|
||||
* 'isRunning' hostname defaults to current server.
|
||||
* 'isRunning' now works with pid as first argument.
|
||||
|
||||
**Gang**
|
||||
|
||||
* Nerfed ascension mechanic once again :(
|
||||
|
||||
**Misc.**
|
||||
|
||||
* Souce-File typo fix
|
||||
* Fix 'while you were away' screen.
|
||||
* Bladeburner team size can no longer be set to negative amounts.
|
||||
|
||||
v0.51.4 - 2021-04-19 Manual hacking is fun (hydroflame)
|
||||
-------------------------------------------------------
|
||||
|
||||
**Manual hacking**
|
||||
|
||||
* These bonus require an install or a soft reset to take effect.
|
||||
* Manual hacking gyms and university gives you a 10% discount.
|
||||
* Manual hacking a corporation server decreases the penalty for leaving work
|
||||
early.
|
||||
|
||||
**BladeBurner**
|
||||
|
||||
* nerfed int exp gained.
|
||||
|
||||
**Documentation**
|
||||
|
||||
* purchaseServer specifies what happens on failure.
|
||||
* Fixed typo in recommended bitnode page.
|
||||
* Removed misleading ram requirements for hacking factions.
|
||||
|
||||
**Netscript**
|
||||
|
||||
* growthAnalyze handles Infinity correctly.
|
||||
|
||||
**Misc.**
|
||||
|
||||
* Faction Augmentation will list how much reputation is required even after
|
||||
that goal has been reached.
|
||||
* Removed dollar sign in travel agency confirmation dialog box.
|
||||
* Fixed typo in alpha-omega.lit
|
||||
* the 'Game saved!' text no longer blocks the save game/options button.
|
||||
* The text editor now remembers the location of your cursor and restores it.
|
||||
* skills are recalculated instantly.
|
||||
* Fix typo in Operation Zero description.
|
||||
|
||||
v0.51.3 - 2021-04-16 Y'all broke it on the first day (hydroflame)
|
||||
-----------------------------------------------------------------
|
||||
|
||||
**Passive faction reputation**
|
||||
|
||||
* Reworked, from 1 rep / 2 minute. Now is a complicated percentage of the
|
||||
reputation you'd gain working for them. It's not op but it feels a bit
|
||||
more useful.
|
||||
|
||||
**Netscript**
|
||||
|
||||
* print/tprint now take any number of arguments.
|
||||
* print/tprint will now print object as json.
|
||||
* print/tprint now handle passing in an undefined argument properly.
|
||||
|
||||
**Casino**
|
||||
|
||||
* Cannot bet negative money anymore.
|
||||
* Roulette max bet is a bit higher.
|
||||
* Coin Flip has a small cooldown.
|
||||
* All buttons reject unstrusted mouse events.
|
||||
|
||||
**Documentation**
|
||||
|
||||
* Changed a message that said nsjs only works on Chrome.
|
||||
|
||||
**Bugfix**
|
||||
|
||||
* hacknet.maxNumNodes now works for both nodes and servers.
|
||||
* Fixed a bug where the popup boxes would contain data from previous popup boxes.
|
||||
* .js files will also have the 'export async function' boilerplate.
|
||||
|
||||
**Misc.**
|
||||
|
||||
* turned off web form autocomplete for the terminal text input.
|
||||
* Fixed an issue on Windows+Firefox where pressing up on the terminal would
|
||||
bring the cursor to the begining of the line. (Issue #836)
|
||||
* Hacknet node names is easier to handle for screen readers.
|
||||
* Money spent on classes is now tracked independently of work money.
|
||||
* running coding contract from the terminal will display its name.
|
||||
|
||||
v0.51.2 - 2021-04-09 Vegas, Baby! (hydroflame)
|
||||
----------------------------------------------
|
||||
|
||||
**New location: The Iker Molina Casino**
|
||||
|
||||
* A casino opened in Aevum. However the house is rumored to cheat. If only
|
||||
we could give them a taste of their own medicine.
|
||||
|
||||
**Misc.**
|
||||
|
||||
* Link to discord added under options
|
||||
* 'getMemberInformation' doc updated, oops
|
||||
* tech vendor now handle max ram and cores.
|
||||
|
||||
v0.51.1 - 2021-04-06 Bugfixes because the author of the last patch sucks (it's hydroflame)
|
||||
------------------------------------------------------------------------------------------
|
||||
|
||||
**Netscript**
|
||||
|
||||
* 'getPlayer' returns players faction and tor
|
||||
* 'hospitalization' is a new singularity function.
|
||||
* 'gang.getMemberInformation' now returns more information.
|
||||
* 'hacknet.hashCapacity' is a new hacknet function that returns the maximum hash capacity.
|
||||
|
||||
**Hospitalization**
|
||||
|
||||
* Now only cost at most 10% of your money.
|
||||
|
||||
**Bugfix**
|
||||
|
||||
* confirmation dialog box no longer use previous text
|
||||
|
||||
**Accessibility**
|
||||
|
||||
* The game is a little easier to handle for screen readers (yes, there's an
|
||||
absolute legend playing this game with a screen reader)
|
||||
* Infiltration use buttons instead of a-links
|
||||
* New option to disable ASCII art. This will make the metro map and world
|
||||
map display as a list of buttons.
|
||||
|
||||
**Misc.**
|
||||
|
||||
* 'fl1ght.exe' will no longer suggest the combat path. Related faction
|
||||
requirements unchanged.
|
||||
|
||||
v0.51.0 - 2021-03-31 Formulas (hydroflame)
|
||||
------------------------------------------
|
||||
|
||||
**Formulas API**
|
||||
|
||||
* A new API is introduced, this gives players access to various formulas used in the game.
|
||||
It'll help you make more informed decisions.
|
||||
|
||||
**Netscript**
|
||||
|
||||
* 'getServer' is a new function meant to be used with the formulas API.
|
||||
* 'getPlayer' is a new function meant to be used with the formulas API.
|
||||
* 'getStats' and 'getCharacterInformation' are deprecated in favor of 'getPlayer'
|
||||
* 'getCurrentServer' is a new function that returns the server the player is currently connected.
|
||||
|
||||
**Display**
|
||||
|
||||
* All money should now consistently be orange.
|
||||
* All rep should now consistently be light-yellow.
|
||||
* Most numbers should display consistently now (aka all money is formatted the same).
|
||||
|
||||
**Click to copy**
|
||||
|
||||
* Certain UI elements are now 'click-to-copy'
|
||||
|
||||
v0.50.2 - 2021-03-25 Everyone asked for this one. (hydroflame)
|
||||
--------------------------------------------------------------
|
||||
|
||||
**BitNodeMultipliers**
|
||||
|
||||
* 'GangKarmaRequirements': a new multipler that influences how much karma is required to make a gang different bitnodes.
|
||||
|
||||
**Netscript**
|
||||
|
||||
* 'connect': a new singularity function that connects you to a server. (like the terminal command)
|
||||
* 'manualHack': a new singularity function that performs a manual hack on the players current server.
|
||||
* ns2 stack trace works on Firefox now.
|
||||
|
||||
**Misc.**
|
||||
|
||||
* New shortcut, Alt + b, brings you to bladeburner
|
||||
* New shortcut, Alt + g, brings you to gang
|
||||
|
||||
v0.50.1 - 2021-03-22 (hydroflame)
|
||||
---------------------------------
|
||||
**Netscript**
|
||||
|
||||
* getTaskStats works
|
||||
|
||||
**Source-File -1**
|
||||
|
||||
* Added a new Exploit
|
||||
|
||||
**Factions**
|
||||
|
||||
* Augmentations offered by a Faction but already bought are in a separate list at the bottom of the page.
|
||||
|
||||
**Bug fixed**
|
||||
|
||||
* Fixed a bug where completing a maxed non-repeatable BitNode would make its color on the BitVerse like level 1.
|
||||
|
||||
**Misc.**
|
||||
|
||||
* Minor spacing in stats tables.
|
||||
|
||||
v0.50.0 - 2021-03-20 Intelligence (hydroflame)
|
||||
----------------------------------------------
|
||||
|
||||
**Intelligence**
|
||||
|
||||
* int exp gain and effect has been reworked. It is now much more easy to
|
||||
acquire and far more powerful. The goal here is to feel like players have
|
||||
another tool in their arsenal.
|
||||
|
||||
**Factions**
|
||||
|
||||
* Hacking factions no longer have hacking level requirements since their associated servers do.
|
||||
|
||||
**Misc.**
|
||||
|
||||
* Sleeve styling.
|
||||
* number formatting
|
||||
* remove wiki button in Hacking Missions.
|
||||
* Fix NaN displayed when very very large numbers are reached.
|
||||
|
||||
v0.49.2 - 2021-03-13 (hydroflame)
|
||||
---------------------------------
|
||||
|
||||
**BN8**
|
||||
|
||||
* A new bitnode multipler has been added, it lets you reduce money from a
|
||||
server without gaining actually any money. This is important for BN8 where
|
||||
hack/grow can influence the stock market. No money can be gained from
|
||||
hacking but server money can still be reduced.
|
||||
|
||||
Documentation
|
||||
**Documentation**
|
||||
|
||||
* readthedocs should now be more consistent and many examples were added.
|
||||
|
||||
Netscript
|
||||
**Netscript**
|
||||
|
||||
* Ace editor will now correctly highlight all functions.
|
||||
* 'tFormat' is a new netscript function that returns a human readable
|
||||
representation of milliseconds. eg. "2 hours 15 minute 43 seconds"
|
||||
|
||||
Gang
|
||||
**Gang**
|
||||
|
||||
* style improvements
|
||||
|
||||
Bladeburner
|
||||
**Bladeburner**
|
||||
|
||||
* style improvements
|
||||
* fix bug where 'skill list SKILL' would crash if skill is level 0.
|
||||
|
||||
Sleeve
|
||||
**Sleeve**
|
||||
|
||||
* karma gain now scales with sync.
|
||||
|
||||
Misc.
|
||||
Fix issue where the effective stats under Character>Stats were being calculated.
|
||||
**Misc.**
|
||||
|
||||
* Fix issue where the effective stats under Character>Stats were being calculated.
|
||||
|
||||
v0.49.0 - 2021-03-11 Source-File -1 (hydroflame)
|
||||
-------
|
||||
------------------------------------------------
|
||||
|
||||
**Source-File -1**
|
||||
|
||||
@@ -63,7 +345,7 @@ v0.49.0 - 2021-03-11 Source-File -1 (hydroflame)
|
||||
|
||||
|
||||
v0.48.0 - ASCII - 2021-03-07 (hydroflame)
|
||||
-------
|
||||
-----------------------------------------
|
||||
|
||||
**ASCII**
|
||||
|
||||
@@ -135,7 +417,7 @@ v0.47.2 - 7/15/2019
|
||||
* Added 'Solarized Dark' theme to CodeMirror editor
|
||||
* After Infiltration, you will now return to the company page rather than the city page
|
||||
* Bug fix: Stock Market UI should no longer crash for certain locale settings
|
||||
* Bug fix: You can now properly remove unfinished programs (the *.exe-N%-INC files)
|
||||
* Bug fix: You can now properly remove unfinished programs (the `*.exe-N%-INC` files)
|
||||
* Bug fix: Fixed an issue that allowed you to increase money on servers with a 'maxMoney' of 0 (like CSEC)
|
||||
* Bug fix: Scripts no longer persist if they were started with syntax/import errors
|
||||
* Bug fix: 'hack' and 'analyze' Terminal commands are now blocking
|
||||
|
||||
@@ -64,9 +64,9 @@ documentation_title = '{0} Documentation'.format(project)
|
||||
# built documents.
|
||||
#
|
||||
# The short X.Y version.
|
||||
version = '0.47'
|
||||
version = '0.51'
|
||||
# The full version, including alpha/beta/rc tags.
|
||||
release = '0.47.0'
|
||||
release = '0.51.5'
|
||||
|
||||
# The language for content autogenerated by Sphinx. Refer to documentation
|
||||
# for a list of supported languages.
|
||||
|
||||
@@ -634,7 +634,7 @@ This tells me that I can reach :code:`CSEC` by going through :code:`iron-gym`::
|
||||
Make sure you notice the required hacking skill for the :code:`CSEC` server.
|
||||
This is a random value between 51 and 60. Although you receive the message
|
||||
from CSEC once you hit 50 hacking, you cannot actually pass their test
|
||||
until your hacking is high enough to hack their server.
|
||||
until your hacking is high enough to install a backdoor on their server.
|
||||
|
||||
After you are connected to the :code:`CSEC` server, you can hack it. Note that this
|
||||
server requires one open port in order to gain root access. We can open the SSH port
|
||||
@@ -642,10 +642,10 @@ using the :code:`BruteSSH.exe` program we created earlier. In |Terminal|::
|
||||
|
||||
$ run BruteSSH.exe
|
||||
$ run NUKE.exe
|
||||
$ hack
|
||||
$ backdoor
|
||||
|
||||
Keep hacking the server until you are successful. After you successfully hack it, you should
|
||||
receive a faction invitation from |CyberSec| shortly afterwards. Accept it. If you accidentally
|
||||
After you successfully install the backdoor, you should receive a faction
|
||||
invitation from |CyberSec| shortly afterwards. Accept it. If you accidentally
|
||||
reject the invitation, that's okay. Just go to the :code:`Factions` tab
|
||||
(|Keyboard shortcut| Alt + f) and you should see an option that lets you
|
||||
accept the invitation.
|
||||
@@ -860,7 +860,7 @@ Random Tips
|
||||
.. Substitution definitions
|
||||
.. |Alpha Enterprises| replace:: :code:`Alpha Enterprises`
|
||||
.. |Augmentations tab| replace:: :code:`Augmentations` tab
|
||||
.. |AutoLink| replace:: :code:`NUKE.exe`
|
||||
.. |AutoLink| replace:: :code:`AutoLink.exe`
|
||||
.. |BruteSSH| replace:: :code:`BruteSSH.exe`
|
||||
.. |City tab| replace:: :code:`City` tab
|
||||
.. |CyberSec| replace:: :code:`CyberSec`
|
||||
|
||||
@@ -278,6 +278,7 @@ Description
|
||||
hashes, which can be spent on a variety of different upgrades.
|
||||
|
||||
In this BitNode:
|
||||
|
||||
* Your stats are significantly decreased
|
||||
* You cannnot purchase additional servers
|
||||
* Hacking is significantly less profitable
|
||||
@@ -292,7 +293,7 @@ Source-File
|
||||
* Level 3: Grants a highly-upgraded Hacknet Server when entering a new BitNode
|
||||
|
||||
(Note that the Level 3 effect of this Source-File only applies when entering a new BitNode, NOT
|
||||
when installing Augmentation
|
||||
when installing Augmentations.)
|
||||
|
||||
Difficulty
|
||||
Hard
|
||||
@@ -312,6 +313,7 @@ Description
|
||||
2. Duplicate Sleeves: Duplicate your consciousness into Synthoids, allowing you to perform different tasks synchronously
|
||||
|
||||
In this BitNode:
|
||||
|
||||
* Your stats are significantly decreased
|
||||
* All methods of gaining money are half as profitable (except Stock Market)
|
||||
* Purchased servers are more expensive, have less max RAM, and a lower maximum limit
|
||||
|
||||
@@ -30,4 +30,5 @@ to reach out to the developer!
|
||||
Gang API <netscript/netscriptgangapi>
|
||||
Coding Contract API <netscript/netscriptcodingcontractapi>
|
||||
Sleeve API <netscript/netscriptsleeveapi>
|
||||
Formulas API <netscript/netscriptformulasapi>
|
||||
Miscellaneous <netscript/netscriptmisc>
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
getHackTime(), getGrowTime(), & getWeakenTime()
|
||||
===============================================
|
||||
|
||||
The :js:func:`getHackTime`, :js:func:`getGrowTime`, and :js:func:`getWeakenTime`
|
||||
all take an additional third optional parameter for specifying a specific intelligence
|
||||
level to see how that would affect the hack/grow/weaken times. This parameter
|
||||
defaults to your current intelligence level.
|
||||
|
||||
(Intelligence is unlocked after obtaining Source-File 5).
|
||||
|
||||
The function signatures are then::
|
||||
|
||||
getHackTime(hostname/ip[, hackLvl=current level, intLvl=current level])
|
||||
getGrowTime(hostname/ip[, hackLvl=current level, intLvl=current level])
|
||||
getWeakenTime(hostname/ip[, hackLvl=current level, intLvl=current level])
|
||||
39
doc/source/netscript/advancedfunctions/getServer.rst
Normal file
39
doc/source/netscript/advancedfunctions/getServer.rst
Normal file
@@ -0,0 +1,39 @@
|
||||
getServer() Netscript Function
|
||||
==========================================
|
||||
|
||||
.. js:function:: getServer()
|
||||
|
||||
:RAM cost: 4 GB
|
||||
|
||||
If you are not in BitNode-5, then you must have Source-File 5-1 in order to run this function.
|
||||
|
||||
This function is meant to be used in conjunction with the :doc:`formulas API<../netscriptformulasapi>`.
|
||||
|
||||
Returns an object with the Server's stats. The object has the following properties::
|
||||
|
||||
{
|
||||
cpuCores
|
||||
ftpPortOpen
|
||||
hasAdminRights
|
||||
hostname
|
||||
httpPortOpen
|
||||
ip
|
||||
isConnectedTo
|
||||
maxRam
|
||||
organizationName
|
||||
ramUsed
|
||||
smtpPortOpen
|
||||
sqlPortOpen
|
||||
sshPortOpen
|
||||
baseDifficulty
|
||||
hackDifficulty
|
||||
backdoorInstalled
|
||||
minDifficulty
|
||||
moneyAvailable
|
||||
moneyMax
|
||||
numOpenPortsRequired
|
||||
openPortCount
|
||||
purchasedByPlayer
|
||||
requiredHackingSkill
|
||||
serverGrowth
|
||||
}
|
||||
40
doc/source/netscript/basicfunctions/flags.rst
Normal file
40
doc/source/netscript/basicfunctions/flags.rst
Normal file
@@ -0,0 +1,40 @@
|
||||
flags() Netscript Function
|
||||
============================
|
||||
|
||||
.. js:function:: flags(data)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param data array of pairs of strings: Flags definition.
|
||||
:returns: Object containing all the flags that were parsed or default.
|
||||
|
||||
The flag definition is an array of pairs of values, the first value is the
|
||||
name of the flag, the 2nd value is the default value for that flag.
|
||||
|
||||
The return object is a map containing flag names to the value. It also
|
||||
contains the special field '_' which contains all arguments that were not flags.
|
||||
|
||||
Example:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
/* example.script
|
||||
var data = flags([
|
||||
['delay', 0], // a default number means this flag is a number
|
||||
['server', 'foodnstuff'], // a default string means this flag is a string
|
||||
['exclude', []], // a default array means this flag is a default array of string
|
||||
['help', false], // a default boolean means this flag is a boolean
|
||||
]);
|
||||
tprint(data);
|
||||
*/
|
||||
[home ~/]> run example.script
|
||||
{"_":[],"delay":0,"server":"foodnstuff"}
|
||||
[home ~/]> run example.script --delay 3000
|
||||
{"_":[],"server":"foodnstuff","delay":3000}
|
||||
[home ~/]> run example.script --delay 3000 --server harakiri-sushi
|
||||
{"_":[],"delay":3000,"server":"harakiri-sushi"}
|
||||
[home ~/]> run example.script --delay 3000 --server harakiri-sushi hello world
|
||||
{"_":["hello","world"],"delay":3000,"server":"harakiri-sushi"}
|
||||
[home ~/]> run example.script --delay 3000 --server harakiri-sushi hello world --exclude a --exclude b
|
||||
{"_":["hello","world"],"delay":3000,"server":"harakiri-sushi","exclude":["a","b"]}
|
||||
[home ~/]> run example.script --help
|
||||
{"_":[],"delay":0,"server":"foodnstuff","exclude":[],"help":true}
|
||||
88
doc/source/netscript/basicfunctions/getRunningScript.rst
Normal file
88
doc/source/netscript/basicfunctions/getRunningScript.rst
Normal file
@@ -0,0 +1,88 @@
|
||||
getRunningScript() Netscript Function
|
||||
=====================================
|
||||
|
||||
.. js:function:: getRunningScript()
|
||||
|
||||
:RAM cost: 0.3 GB
|
||||
:returns: Script object or null if not found
|
||||
|
||||
The object has the following properties:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
{
|
||||
// Script arguments
|
||||
args
|
||||
|
||||
// Script filename
|
||||
filename
|
||||
|
||||
// This script's logs. An array of log entries
|
||||
logs
|
||||
|
||||
// Flag indicating whether the logs have been updated since
|
||||
// the last time the UI was updated
|
||||
logUpd
|
||||
|
||||
// Total amount of hacking experience earned from this script when offline
|
||||
offlineExpGained
|
||||
|
||||
// Total amount of money made by this script when offline
|
||||
offlineMoneyMade
|
||||
|
||||
// Number of seconds that the script has been running offline
|
||||
offlineRunningTime
|
||||
|
||||
// Total amount of hacking experience earned from this script when online
|
||||
onlineExpGained
|
||||
|
||||
// Total amount of money made by this script when online
|
||||
onlineMoneyMade
|
||||
|
||||
// Number of seconds that this script has been running online
|
||||
onlineRunningTime
|
||||
|
||||
// Process ID.
|
||||
pid
|
||||
|
||||
// How much RAM this script uses for ONE thread
|
||||
ramUsage
|
||||
|
||||
// IP of the server on which this script is running
|
||||
server
|
||||
|
||||
// Number of threads that this script is running with
|
||||
threads
|
||||
}
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
getRunningScript(); // get the current script.
|
||||
|
||||
.. js:function:: getRunningScript(pid)
|
||||
|
||||
:RAM cost: 0.3 GB
|
||||
:param number pid: PID of the script
|
||||
:returns: Script object or null if not found
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
getRunningScript(42); // get the script with pid 42.
|
||||
|
||||
.. js:function:: getRunningScript(fn, hostname[, args])
|
||||
|
||||
:RAM cost: 0.3 GB
|
||||
:param number fn: filename of the target script
|
||||
:param number hostname: hostname of the server running the script
|
||||
:param number args: arguments to the script.
|
||||
:returns: Script object or null if not found
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
getRunningScript("example.script", "home", "foodnstuff"); // get the script called "example.script" on "home" with argument "foodnstuff"
|
||||
@@ -1,11 +1,11 @@
|
||||
isRunning() Netscript Function
|
||||
==============================
|
||||
|
||||
.. js:function:: isRunning(filename, hostname, [args...])
|
||||
.. js:function:: isRunning(filename[, hostname=current hostname[, args...]])
|
||||
|
||||
:RAM cost: 0.1 GB
|
||||
:param string filename: Filename of script to check. case-sensitive.
|
||||
:param string hostname: Hostname of target server.
|
||||
:param string hostname: Hostname of target server. Defaults to current server
|
||||
:param args...: Arguments to specify/identify which scripts to search for
|
||||
:returns: ``true`` if that script with those args is running on that server.
|
||||
|
||||
@@ -38,3 +38,17 @@ isRunning() Netscript Function
|
||||
.. code-block:: javascript
|
||||
|
||||
isRunning("foo.script", "joesguns", 1, 5, "test");
|
||||
|
||||
|
||||
.. js:function:: isRunning(scriptPid)
|
||||
|
||||
:RAM cost: 0.1 GB
|
||||
:param number scriptPid: PID of the script to check.
|
||||
|
||||
Same as the above version but with pid.
|
||||
|
||||
Example:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
isRunning(39);
|
||||
|
||||
@@ -1,15 +1,16 @@
|
||||
print() Netscript Function
|
||||
===========================
|
||||
|
||||
.. js:function:: print(x)
|
||||
.. js:function:: print(args...)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param x: Value to be printed.
|
||||
:param args: Values to be printed.
|
||||
|
||||
Prints a value or a variable to the script's logs.
|
||||
Prints any number of values to the script's logs.
|
||||
|
||||
Example:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
print("Hello world!"); // Prints "Hello world!" in the logs.
|
||||
print("Hello world!"); // Prints "Hello world!" in the logs.
|
||||
print({a:5}); // Prints '{"a":5}' in the logs.
|
||||
@@ -7,7 +7,7 @@ purchaseServer() Netscript Function
|
||||
:param string hostname: Hostname of the purchased server.
|
||||
:param number ram: Amount of RAM of the purchased server. Must be a power of
|
||||
2. Maximum value of :doc:`getPurchasedServerMaxRam<getPurchasedServerMaxRam>`
|
||||
:returns: The hostname of the newly purchased server.
|
||||
:returns: The hostname of the newly purchased server. Empty string on failure.
|
||||
|
||||
Purchased a server with the specified hostname and amount of RAM.
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
tail() Netscript Function
|
||||
==================================
|
||||
|
||||
.. js:function:: tail([fn[, hostname=current hostname[, [...args]]])
|
||||
.. js:function:: tail([fn[, hostname=current hostname[, ...args]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param string fn: Optional. Filename of script to get logs from.
|
||||
@@ -29,3 +29,33 @@ tail() Netscript Function
|
||||
|
||||
// Open logs from foo.script on the foodnstuff server that was run with the arguments [1, "test"]
|
||||
tail("foo.script", "foodnstuff", 1, "test");
|
||||
|
||||
.. js:function:: tail(scriptPid)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number scriptPid: PID of the script to tail.
|
||||
|
||||
Opens a script's logs by pid
|
||||
|
||||
Example:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
// Open logs from process with id 42
|
||||
tail(42);
|
||||
|
||||
// Open logs from process with id 42 on the foodnstuff server
|
||||
tail(42, "foodnstuff");
|
||||
|
||||
.. js:function:: tail()
|
||||
|
||||
:RAM cost: 0 GB
|
||||
|
||||
Opens the current script logs.
|
||||
|
||||
Example:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
// Open the current script logs.
|
||||
tail();
|
||||
|
||||
@@ -1,15 +1,16 @@
|
||||
tprint() Netscript Function
|
||||
===========================
|
||||
|
||||
.. js:function:: tprint(x)
|
||||
.. js:function:: tprint(args...)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param x: Value to be printed
|
||||
:param args: Values to be printed
|
||||
|
||||
Prints a value or a variable to the Terminal.
|
||||
Prints any number of values to the Terminal.
|
||||
|
||||
Example:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
tprint("Hello world!"); // Prints "Hello world!" to the terminal.
|
||||
tprint("Hello world!"); // Prints "Hello world!" to the terminal.
|
||||
tprint({a:5}); // Prints '{"a":5}' to the terminal.
|
||||
22
doc/source/netscript/formulasapi/basic/calculateExp.rst
Normal file
22
doc/source/netscript/formulasapi/basic/calculateExp.rst
Normal file
@@ -0,0 +1,22 @@
|
||||
calculateExp() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: calculateExp(skillLevel[, mult])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number skillLevel: ``skillLevel`` to convert to exp.
|
||||
:param number mult: Assume a specific skill multipler (not exp multiplier).
|
||||
:returns: number of exp required to reach given ``skillLevel`` with that multiplier.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
This function calculates the amount of experience needed to reach level the given ``skillLevel``.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
nextHacking = getStats().hacking+1;
|
||||
nextExp = formulas.basic.calculateExp(nextHacking);
|
||||
missingExp = nextExp - getCharacterInformation().hackingExp;
|
||||
tprint("Missing " + missingExp + " to reach next hacking level");
|
||||
20
doc/source/netscript/formulasapi/basic/calculateSkill.rst
Normal file
20
doc/source/netscript/formulasapi/basic/calculateSkill.rst
Normal file
@@ -0,0 +1,20 @@
|
||||
calculateSkill() Netscript Function
|
||||
===================================
|
||||
|
||||
.. js:function:: calculateSkill(exp[, mult])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number exp: ``exp`` to convert to skillLevel.
|
||||
:param number mult: Assume a specific skill multipler (not exp multiplier).
|
||||
:returns: skillLevel that ``exp`` would reach with that multiplier.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
This function calculates the skillLevel that the given amount of ``exp`` would reach.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
skillLevel = formulas.basic.calculateSkill(1000);
|
||||
tprint("1000 exp would reach level " + skillLevel);
|
||||
23
doc/source/netscript/formulasapi/basic/growPercent.rst
Normal file
23
doc/source/netscript/formulasapi/basic/growPercent.rst
Normal file
@@ -0,0 +1,23 @@
|
||||
growPercent() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: growPercent(server, threads, player)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param server server: The server that receives the growth.
|
||||
:param number threads: The number of thread that would be used.
|
||||
:param player player: The player.
|
||||
:returns: The percentage growth this server would receive with these parameters.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
Server can be acquired with the :doc:`getServer<../../advancedfunctions/getServer>` function.
|
||||
Player can be acquired with the :doc:`getPlayer<../../singularityfunctions/getPlayer>` function.
|
||||
|
||||
This function calculates percentage of growth a server would receive with these parameters.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
tprint(growPercent(getServer(), 50, getPlayer()))
|
||||
24
doc/source/netscript/formulasapi/basic/growTime.rst
Normal file
24
doc/source/netscript/formulasapi/basic/growTime.rst
Normal file
@@ -0,0 +1,24 @@
|
||||
growTime() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: growTime(server, player)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param server server: The server to grow.
|
||||
:param player player: The player.
|
||||
:returns: The time it takes to grow this server. In seconds.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
Server can be acquired with the :doc:`getServer<../../advancedfunctions/getServer>` function.
|
||||
Player can be acquired with the :doc:`getPlayer<../../singularityfunctions/getPlayer>` function.
|
||||
|
||||
This function calculates the amount of time it takes to grow a server.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
server = getServer();
|
||||
server.hackDifficulty = server.minDifficulty;
|
||||
tprint(growTime(server, getPlayer()));
|
||||
24
doc/source/netscript/formulasapi/basic/hackChance.rst
Normal file
24
doc/source/netscript/formulasapi/basic/hackChance.rst
Normal file
@@ -0,0 +1,24 @@
|
||||
hackChance() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: hackChance(server, player)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param server server: The server to hack.
|
||||
:param player player: The player.
|
||||
:returns: The change to hack that server. between 0 and 1.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
Server can be acquired with the :doc:`getServer<../../advancedfunctions/getServer>` function.
|
||||
Player can be acquired with the :doc:`getPlayer<../../singularityfunctions/getPlayer>` function.
|
||||
|
||||
This function calculates percentage chance to hack a server.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
server = getServer();
|
||||
server.hackDifficulty = server.minDifficulty;
|
||||
tprint(hackChance(server, getPlayer()));
|
||||
24
doc/source/netscript/formulasapi/basic/hackExp.rst
Normal file
24
doc/source/netscript/formulasapi/basic/hackExp.rst
Normal file
@@ -0,0 +1,24 @@
|
||||
hackExp() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: hackExp(server, player)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param server server: The server to hack.
|
||||
:param player player: The player.
|
||||
:returns: The amount of exp that would be acquired if this server were to be hacked.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
Server can be acquired with the :doc:`getServer<../../advancedfunctions/getServer>` function.
|
||||
Player can be acquired with the :doc:`getPlayer<../../singularityfunctions/getPlayer>` function.
|
||||
|
||||
This function calculates the amount of exp obtained by hacking a server.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
server = getServer();
|
||||
server.hackDifficulty = 99.9;
|
||||
tprint(hackExp(server, getPlayer()));
|
||||
25
doc/source/netscript/formulasapi/basic/hackPercent.rst
Normal file
25
doc/source/netscript/formulasapi/basic/hackPercent.rst
Normal file
@@ -0,0 +1,25 @@
|
||||
hackPercent() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: hackPercent(server, player)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param server server: The server to hack.
|
||||
:param player player: The player.
|
||||
:returns: The percentage of money hacked from a servers maximum money.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
Server can be acquired with the :doc:`getServer<../../advancedfunctions/getServer>` function.
|
||||
Player can be acquired with the :doc:`getPlayer<../../singularityfunctions/getPlayer>` function.
|
||||
|
||||
This function calculates the percentage of maximum money hacked from a server.
|
||||
Multiply this by thread count to know calculate the percentage for more than 1 thread.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
server = getServer();
|
||||
server.hackDifficulty = server.minDifficulty;
|
||||
tprint(hackPercent(server, getPlayer()));
|
||||
24
doc/source/netscript/formulasapi/basic/hackTime.rst
Normal file
24
doc/source/netscript/formulasapi/basic/hackTime.rst
Normal file
@@ -0,0 +1,24 @@
|
||||
hackTime() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: hackTime(server, player)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param server server: The server to hack.
|
||||
:param player player: The player.
|
||||
:returns: The time it takes to hack this server. In seconds.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
Server can be acquired with the :doc:`getServer<../../advancedfunctions/getServer>` function.
|
||||
Player can be acquired with the :doc:`getPlayer<../../singularityfunctions/getPlayer>` function.
|
||||
|
||||
This function calculates the amount of time it takes to hack a server.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
server = getServer();
|
||||
server.hackDifficulty = server.minDifficulty;
|
||||
tprint(hackTime(server, getPlayer()));
|
||||
24
doc/source/netscript/formulasapi/basic/weakenTime.rst
Normal file
24
doc/source/netscript/formulasapi/basic/weakenTime.rst
Normal file
@@ -0,0 +1,24 @@
|
||||
weakenTime() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: weakenTime(server, player)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param server server: The server to weaken.
|
||||
:param player player: The player.
|
||||
:returns: The time it takes to weaken this server. In seconds.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
Server can be acquired with the :doc:`getServer<../../advancedfunctions/getServer>` function.
|
||||
Player can be acquired with the :doc:`getPlayer<../../singularityfunctions/getPlayer>` function.
|
||||
|
||||
This function calculates the amount of time it takes to weaken a server.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
server = getServer();
|
||||
server.hackDifficulty = server.minDifficulty;
|
||||
tprint(weakenTime(server, getPlayer()));
|
||||
26
doc/source/netscript/formulasapi/hacknetNodes/constants.rst
Normal file
26
doc/source/netscript/formulasapi/hacknetNodes/constants.rst
Normal file
@@ -0,0 +1,26 @@
|
||||
constants() Netscript Function
|
||||
==============================
|
||||
|
||||
.. js:function:: constants()
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:returns: A structure with various constants related to hacknet nodes.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
{
|
||||
MoneyGainPerLevel
|
||||
BaseCost
|
||||
LevelBaseCost
|
||||
RamBaseCost
|
||||
CoreBaseCost
|
||||
PurchaseNextMult
|
||||
UpgradeLevelMult
|
||||
UpgradeRamMult
|
||||
UpgradeCoreMult
|
||||
MaxLevel
|
||||
MaxRam
|
||||
MaxCores
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
coreUpgradeCost() Netscript Function
|
||||
=============================================
|
||||
|
||||
.. js:function:: coreUpgradeCost(startingCores[, extraCores[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number startingCores: Number of core at the start the calculation.
|
||||
:param number extraCores: Extra number of cores you want to buy. Default to ``1``.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to go from ``startingCores`` to ``startingCores+extraCores``.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
This function calculates the cost of upgrading cores from any level to any level.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetNodes.coreUpgradeCost(1, 5); // returns: 6355000
|
||||
@@ -0,0 +1,19 @@
|
||||
hacknetNodeCost() Netscript Function
|
||||
=============================================
|
||||
|
||||
.. js:function:: hacknetNodeCost(nodeN[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number nodeN: Number of the new node.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to buy your ``nodeN`` th node.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
This function calculates the cost purchasing a hacknet node.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetNodes.hacknetNodeCost(2); // returns: 1800
|
||||
@@ -0,0 +1,20 @@
|
||||
levelUpgradeCost() Netscript Function
|
||||
==============================================
|
||||
|
||||
.. js:function:: levelUpgradeCost(startingLevel[, extraLevels[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number startingLevel: Number of level at the start the calculation.
|
||||
:param number extraLevels: Extra number of levels you want to buy. Default to ``1``.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to go from ``startingLevel`` to ``startingLevel+extraLevels``.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
This function calculates the cost of upgrading levels from any level to any level.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetNodes.levelUpgradeCost(1, 5); // returns: 2816
|
||||
@@ -0,0 +1,24 @@
|
||||
moneyGainRate() Netscript Function
|
||||
===========================================
|
||||
|
||||
.. js:function:: moneyGainRate(level, ram, core[, mult])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number level: level of the node.
|
||||
:param number ram: ram of the node.
|
||||
:param number core: cores of the node.
|
||||
:returns: Money per second that a node with those stats would gain per second.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
This function calculates the money rate of a node with the given stats.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
node = hacknet.getNodeStats(1);
|
||||
currentRate = formulas.hacknetNodes.moneyGainRate(node.level, node.ram, node.cores);
|
||||
levelRate = formulas.hacknetNodes.moneyGainRate(node.level+1, node.ram, node.cores);
|
||||
ramRate = formulas.hacknetNodes.moneyGainRate(node.level, node.ram*2, node.cores);
|
||||
coresRate = formulas.hacknetNodes.moneyGainRate(node.level, node.ram, node.cores+1);
|
||||
@@ -0,0 +1,22 @@
|
||||
ramUpgradeCost() Netscript Function
|
||||
============================================
|
||||
|
||||
.. js:function:: ramUpgradeCost(startingRam[, extraRamLevels[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number startingRam: Amount of RAM at the start the calculation.
|
||||
:param number extraRamLevels: Extra number of levels you want to buy. Default to ``1``.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to go from ``startingRam`` to ``startingRam+extraRamLevels``.
|
||||
|
||||
..note:: ``startingRam`` is the actual amount of ram, not the amount of levels of ram.
|
||||
|
||||
You must have Source-File 5-1 in order to use this function.
|
||||
|
||||
This function calculates the cost of upgrading levels from any level to any level.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetNodes.ramUpgradeCost(1, 5); // returns: 2095000
|
||||
@@ -0,0 +1,20 @@
|
||||
cacheUpgradeCost() Netscript Function
|
||||
==============================================
|
||||
|
||||
.. js:function:: cacheUpgradeCost(startingCache[, extraCacheLevels[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number startingCache: Cache level at the start the calculation.
|
||||
:param number extraCacheLevels: Extra number of cache level you want to buy. Default to ``1``.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to go from ``startingLevel`` to ``startingLevel+extraLevels``.
|
||||
|
||||
You must have Source-File 5-1 and Source-File 9-1 in order to use this function.
|
||||
|
||||
This function calculates the cost of upgrading cache from any level to any level.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetServers.cacheUpgradeCost(1, 5); // returns: 243170000
|
||||
@@ -0,0 +1,29 @@
|
||||
constants() Netscript Function
|
||||
=============================================
|
||||
|
||||
.. js:function:: constants()
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:returns: A structure with various constants related to hacknet servers.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
{
|
||||
HashesPerLevel
|
||||
BaseCost
|
||||
RamBaseCost
|
||||
CoreBaseCost
|
||||
CacheBaseCost
|
||||
PurchaseMult
|
||||
UpgradeLevelMult
|
||||
UpgradeRamMult
|
||||
UpgradeCoreMult
|
||||
UpgradeCacheMult
|
||||
MaxServers
|
||||
MaxLevel
|
||||
MaxRam
|
||||
MaxCores
|
||||
MaxCache
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
coreUpgradeCost() Netscript Function
|
||||
=============================================
|
||||
|
||||
.. js:function:: coreUpgradeCost(startingCores[, extraCores[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number startingCores: Number of core at the start the calculation.
|
||||
:param number extraCores: Extra number of cores you want to buy. Default to ``1``.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to go from ``startingCores`` to ``startingCores+extraCores``.
|
||||
|
||||
You must have Source-File 5-1 and Source-File 9-1 in order to use this function.
|
||||
|
||||
This function calculates the cost of upgrading cores from any level to any level.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetServers.coreUpgradeCost(1, 5); // returns: 12015000
|
||||
@@ -0,0 +1,19 @@
|
||||
hacknetServerCost() Netscript Function
|
||||
===============================================
|
||||
|
||||
.. js:function:: hacknetServerCost(serverN[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number serverN: Number of the new node.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to buy your ``serverN`` th node.
|
||||
|
||||
You must have Source-File 5-1 and Source-File 9-1 in order to use this function.
|
||||
|
||||
This function calculates the cost purchasing a hacknet node.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetNodes.hacknetServerCost(2); // returns: 1800000
|
||||
@@ -0,0 +1,24 @@
|
||||
hashGainRate() Netscript Function
|
||||
==========================================
|
||||
|
||||
.. js:function:: hashGainRate(level, ram, core[, mult])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number level: level of the server.
|
||||
:param number ram: ram of the server.
|
||||
:param number core: cores of the server.
|
||||
:returns: Money per second that a server with those stats would gain per second.
|
||||
|
||||
You must have Source-File 5-1 and Source-File 9-1 in order to use this function.
|
||||
|
||||
This function calculates the hash rate of a server with the given stats.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
server = hacknet.getNodeStats(1);
|
||||
currentRate = formulas.hacknetNodes.hashGainRate(server.level, server.ram, server.cores);
|
||||
levelRate = formulas.hacknetNodes.hashGainRate(server.level+1, server.ram, server.cores);
|
||||
ramRate = formulas.hacknetNodes.hashGainRate(server.level, server.ram*2, server.cores);
|
||||
coresRate = formulas.hacknetNodes.hashGainRate(server.level, server.ram, server.cores+1);
|
||||
@@ -0,0 +1,19 @@
|
||||
hashUpgradeCost() Netscript Function
|
||||
=============================================
|
||||
|
||||
.. js:function:: hashUpgradeCost(upgName, level)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param string upgName: Name of the Hash upgrade.
|
||||
:param number level: Level of the upgrade.
|
||||
:returns: Amount of Hash.
|
||||
|
||||
You must have Source-File 5-1 and Source-File 9-1 in order to use this function.
|
||||
|
||||
This function calculates amount of Hash require to buy level ``level`` of upgrade ``upgName``.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetServers.hashUpgradeCost("Increase Maximum Money", 5); // returns: 250
|
||||
@@ -0,0 +1,20 @@
|
||||
levelUpgradeCost() Netscript Function
|
||||
=============================================
|
||||
|
||||
.. js:function:: levelUpgradeCost(startingLevel[, extraLevels[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number startingLevel: Number of level at the start the calculation.
|
||||
:param number extraLevels: Extra number of levels you want to buy. Default to ``1``.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to go from ``startingLevel`` to ``startingLevel+extraLevels``.
|
||||
|
||||
You must have Source-File 5-1 and Source-File 9-1 in order to use this function.
|
||||
|
||||
This function calculates the cost of upgrading levels from any level to any level.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetServers.levelUpgradeCost(1, 5); // returns: 2792000
|
||||
@@ -0,0 +1,22 @@
|
||||
ramUpgradeCost() Netscript Function
|
||||
=============================================
|
||||
|
||||
.. js:function:: ramUpgradeCost(startingRam[, extraRamLevels[, costMult]])
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param number startingRam: Amount of RAM at the start the calculation.
|
||||
:param number extraRamLevels: Extra number of levels you want to buy. Default to ``1``.
|
||||
:param number costMult: Aug multiplier that reduces cost. Defaults to ``1``.
|
||||
:returns: Money required to go from ``startingRam`` to ``startingRam+extraRamLevels``.
|
||||
|
||||
..note:: ``startingRam`` is the actual amount of ram, not the amount of levels of ram.
|
||||
|
||||
You must have Source-File 5-1 and Source-File 9-1 in order to use this function.
|
||||
|
||||
This function calculates the cost of upgrading levels from any level to any level.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
formulas.hacknetServers.ramUpgradeCost(1, 5); // returns: 15810000
|
||||
@@ -10,27 +10,35 @@ getMemberInformation() Netscript Function
|
||||
The object has the following structure::
|
||||
|
||||
{
|
||||
agility: Agility stat
|
||||
agilityEquipMult: Agility multiplier from equipment. Decimal form
|
||||
agilityAscensionMult: Agility multiplier from ascension. Decimal form
|
||||
augmentations: Array of names of all owned Augmentations
|
||||
charisma: Charisma stat
|
||||
charismaEquipMult: Charisma multiplier from equipment. Decimal form
|
||||
charismaAscensionMult: Charisma multiplier from ascension. Decimal form
|
||||
defense: Defense stat
|
||||
defenseEquipMult: Defense multiplier from equipment. Decimal form
|
||||
defenseAscensionMult: Defense multiplier from ascension. Decimal form
|
||||
dexterity: Dexterity stat
|
||||
dexterityEquipMult: Dexterity multiplier from equipment. Decimal form
|
||||
dexterityAscensionMult: Dexterity multiplier from ascension. Decimal form
|
||||
equipment: Array of names of all owned Non-Augmentation Equipment
|
||||
hacking: Hacking stat
|
||||
hackingEquipMult: Hacking multiplier from equipment. Decimal form
|
||||
hackingAscensionMult: Hacking multiplier from ascension. Decimal form
|
||||
strength: Strength stat
|
||||
strengthEquipMult: Strength multiplier from equipment. Decimal form
|
||||
strengthAscensionMult: Strength multiplier from ascension. Decimal form
|
||||
task: Name of currently assigned task
|
||||
name: Name of this member.
|
||||
task: Name of currently assigned task.
|
||||
earnedRespect: Total amount of respect earned by this member.
|
||||
hack: Hacking stat
|
||||
str: Strength stat
|
||||
def: Defense stat
|
||||
dex: Dexterity stat
|
||||
agi: Agility stat
|
||||
cha: Charisma stat
|
||||
hack_exp: Hacking experience
|
||||
str_exp: Strength experience
|
||||
def_exp: Defense experience
|
||||
dex_exp: Dexterity experience
|
||||
agi_exp: Agility experience
|
||||
cha_exp: Charisma experience
|
||||
hack_mult: Hacking multiplier from equipment. Decimal form
|
||||
str_mult: Strength multiplier from equipment. Decimal form
|
||||
def_mult: Defense multiplier from equipment. Decimal form
|
||||
dex_mult: Dexterity multiplier from equipment. Decimal form
|
||||
agi_mult: Agility multiplier from equipment. Decimal form
|
||||
cha_mult: Charisma multiplier from equipment. Decimal form
|
||||
hack_asc_mult: Hacking multiplier from ascension. Decimal form
|
||||
str_asc_mult: Strength multiplier from ascension. Decimal form
|
||||
def_asc_mult: Defense multiplier from ascension. Decimal form
|
||||
dex_asc_mult: Dexterity multiplier from ascension. Decimal form
|
||||
agi_asc_mult: Agility multiplier from ascension. Decimal form
|
||||
cha_asc_mult: Charisma multiplier from ascension. Decimal form
|
||||
upgrades: Array of names of all owned Non-Augmentation Equipment
|
||||
augmentations: Array of names of all owned Augmentations
|
||||
}
|
||||
|
||||
Get stat and equipment-related information about a Gang Member
|
||||
18
doc/source/netscript/hacknetnodeapi/getHashUpgradeLevel.rst
Normal file
18
doc/source/netscript/hacknetnodeapi/getHashUpgradeLevel.rst
Normal file
@@ -0,0 +1,18 @@
|
||||
getHashUpgradeLevel() Netscript Function
|
||||
========================================
|
||||
|
||||
.. js:function:: getHashUpgradeLevel(upgName)
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:param string upgName: Name of upgrade to spend hashes on. Must be an exact match.
|
||||
:returns: level of the upgrade.
|
||||
|
||||
.. note:: This function is only applicable for Hacknet Servers (the upgraded version
|
||||
of a Hacknet Node).
|
||||
|
||||
Example:
|
||||
|
||||
.. code:: javascript
|
||||
|
||||
hacknet.getHashUpgradeLevel("Sell for Money"); // returns: 5
|
||||
// "Sell for Money" was bought 5 times.
|
||||
13
doc/source/netscript/hacknetnodeapi/getStudyMult.rst
Normal file
13
doc/source/netscript/hacknetnodeapi/getStudyMult.rst
Normal file
@@ -0,0 +1,13 @@
|
||||
getStudyMult() Netscript Function
|
||||
=================================
|
||||
|
||||
.. js:function:: getStudyMult()
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:returns: The multiplier to studying that hash upgrades provide to the player.
|
||||
|
||||
Example:
|
||||
|
||||
.. code:: javascript
|
||||
|
||||
hacknet.getStudyMult(); // return: 1.4
|
||||
13
doc/source/netscript/hacknetnodeapi/getTrainingMult.rst
Normal file
13
doc/source/netscript/hacknetnodeapi/getTrainingMult.rst
Normal file
@@ -0,0 +1,13 @@
|
||||
getTrainingMul() Netscript Function
|
||||
===================================
|
||||
|
||||
.. js:function:: getTrainingMul()
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:returns: The multiplier to training that hash upgrades provide to the player.
|
||||
|
||||
Example:
|
||||
|
||||
.. code:: javascript
|
||||
|
||||
hacknet.getTrainingMult(); // return: 1.4
|
||||
12
doc/source/netscript/hacknetnodeapi/hashCapacity.rst
Normal file
12
doc/source/netscript/hacknetnodeapi/hashCapacity.rst
Normal file
@@ -0,0 +1,12 @@
|
||||
hashCapacity() Netscript Function
|
||||
=================================
|
||||
|
||||
.. warning:: This page contains spoilers for the game
|
||||
|
||||
.. js:function:: hashCapacity()
|
||||
|
||||
:RAM cost: 0 GB
|
||||
:returns: The players maximum hash capacity.
|
||||
|
||||
.. note:: This function is only applicable for Hacknet Servers (the upgraded version of
|
||||
a Hacknet Node).
|
||||
@@ -9,4 +9,4 @@ they contain spoilers for the game.
|
||||
.. toctree::
|
||||
|
||||
getBitNodeMultipliers() <advancedfunctions/getBitNodeMultipliers>
|
||||
getHackTime(), getGrowTime(), & getWeakenTime() <advancedfunctions/getHackGrowWeakenTimes>
|
||||
getServer() <advancedfunctions/getServer>
|
||||
|
||||
61
doc/source/netscript/netscriptformulasapi.rst
Normal file
61
doc/source/netscript/netscriptformulasapi.rst
Normal file
@@ -0,0 +1,61 @@
|
||||
.. _netscriptformulas:
|
||||
|
||||
Netscript Formulas Functions
|
||||
============================
|
||||
|
||||
.. warning:: This page contains spoilers for the game.
|
||||
|
||||
The formulas API allow you to gain insight into the inner workings of the game.
|
||||
These functions will allow you to make more informed decision.
|
||||
|
||||
All of these function cost 0 GB of ram to use. All these function require
|
||||
Source-File 5-1 but some additionally need another source file level 1 to use.
|
||||
|
||||
|
||||
basic formulas
|
||||
--------------
|
||||
|
||||
These functions are under the ``formulas.basic.`` name space and available as
|
||||
soon as you acquire Source-File 5-1
|
||||
|
||||
.. toctree::
|
||||
calculateSkill() <formulasapi/basic/calculateSkill>
|
||||
calculateExp() <formulasapi/basic/calculateExp>
|
||||
growTime() <formulasapi/basic/growTime>
|
||||
hackTime() <formulasapi/basic/hackTime>
|
||||
weakenTime() <formulasapi/basic/weakenTime>
|
||||
growPercent() <formulasapi/basic/growPercent>
|
||||
hackPercent() <formulasapi/basic/hackPercent>
|
||||
hackChance() <formulasapi/basic/hackChance>
|
||||
hackExp() <formulasapi/basic/hackExp>
|
||||
|
||||
|
||||
hacknetNodes formulas
|
||||
---------------------
|
||||
|
||||
These functions are under the ``formulas.hacknetNodes.`` namespace and available as
|
||||
soon as you acquire Source-File 5-1.
|
||||
|
||||
.. toctree::
|
||||
hacknetNodeCost() <formulasapi/hacknetNodes/hacknetNodeCost>
|
||||
moneyGainRate() <formulasapi/hacknetNodes/moneyGainRate>
|
||||
levelUpgradeCost() <formulasapi/hacknetNodes/levelUpgradeCost>
|
||||
ramUpgradeCost() <formulasapi/hacknetNodes/ramUpgradeCost>
|
||||
coreUpgradeCost() <formulasapi/hacknetNodes/coreUpgradeCost>
|
||||
constants() <formulasapi/hacknetNodes/constants>
|
||||
|
||||
hacknetServers formulas
|
||||
-----------------------
|
||||
|
||||
These functions are under the ``formulas.hacknetServers.`` namespace.
|
||||
These functions require Source-File 5-1 and Source-File 9-1 to be invoked.
|
||||
|
||||
.. toctree::
|
||||
hacknetServerCost() <formulasapi/hacknetServers/hacknetServerCost>
|
||||
hashGainRate() <formulasapi/hacknetServers/hashGainRate>
|
||||
levelUpgradeCost() <formulasapi/hacknetServers/levelUpgradeCost>
|
||||
ramUpgradeCost() <formulasapi/hacknetServers/ramUpgradeCost>
|
||||
coreUpgradeCost() <formulasapi/hacknetServers/coreUpgradeCost>
|
||||
cacheUpgradeCost() <formulasapi/hacknetServers/cacheUpgradeCost>
|
||||
hashUpgradeCost() <formulasapi/hacknetServers/hashUpgradeCost>
|
||||
constants() <formulasapi/hacknetServers/constants>
|
||||
@@ -75,6 +75,7 @@ This includes information such as function signatures, what they do, and their r
|
||||
scriptKill() <basicfunctions/scriptKill>
|
||||
getScriptName() <basicfunctions/getScriptName>
|
||||
getScriptRam() <basicfunctions/getScriptRam>
|
||||
getRunningScript() <basicfunctions/getRunningScript>
|
||||
getHackTime() <basicfunctions/getHackTime>
|
||||
getGrowTime() <basicfunctions/getGrowTime>
|
||||
getWeakenTime() <basicfunctions/getWeakenTime>
|
||||
@@ -84,6 +85,8 @@ This includes information such as function signatures, what they do, and their r
|
||||
sprintf() <basicfunctions/sprintf>
|
||||
vsprintf() <basicfunctions/vsprintf>
|
||||
nFormat() <basicfunctions/nFormat>
|
||||
tFormat() <basicfunctions/tFormat>
|
||||
prompt() <basicfunctions/prompt>
|
||||
wget() <basicfunctions/wget>
|
||||
getFavorToDonate() <basicfunctions/getFavorToDonate>
|
||||
flags() <basicfunctions/flags>
|
||||
|
||||
@@ -26,7 +26,7 @@ In :ref:`netscriptjs`::
|
||||
ns.hacknet.getNodeStats(3).level;
|
||||
|
||||
.. toctree::
|
||||
:caption: API Functions:
|
||||
:caption: Hacknet Nodes API Functions:
|
||||
|
||||
numNodes() <hacknetnodeapi/numNodes>
|
||||
maxNumNodes() <hacknetnodeapi/maxNumNodes>
|
||||
@@ -36,14 +36,22 @@ In :ref:`netscriptjs`::
|
||||
upgradeLevel() <hacknetnodeapi/upgradeLevel>
|
||||
upgradeRam() <hacknetnodeapi/upgradeRam>
|
||||
upgradeCore() <hacknetnodeapi/upgradeCore>
|
||||
upgradeCache() <hacknetnodeapi/upgradeCache>
|
||||
getLevelUpgradeCost() <hacknetnodeapi/getLevelUpgradeCost>
|
||||
getRamUpgradeCost() <hacknetnodeapi/getRamUpgradeCost>
|
||||
getCoreUpgradeCost() <hacknetnodeapi/getCoreUpgradeCost>
|
||||
|
||||
.. toctree::
|
||||
:caption: Hacknet Servers API Functions:
|
||||
|
||||
upgradeCache() <hacknetnodeapi/upgradeCache>
|
||||
getCacheUpgradeCost() <hacknetnodeapi/getCacheUpgradeCost>
|
||||
numHashes() <hacknetnodeapi/numHashes>
|
||||
hashCapacity() <hacknetnodeapi/hashCapacity>
|
||||
hashCost() <hacknetnodeapi/hashCost>
|
||||
spendHashes() <hacknetnodeapi/spendHashes>
|
||||
getHashUpgradeLevel() <hacknetnodeapi/getHashUpgradeLevel>
|
||||
getTrainingMult() <hacknetnodeapi/getTrainingMult>
|
||||
getStudyMult() <hacknetnodeapi/getStudyMult>
|
||||
|
||||
.. _netscript_hacknetnodeapi_referencingahacknetnode:
|
||||
|
||||
|
||||
@@ -65,6 +65,6 @@ Here is a short summary of the differences between Netscript 1.0 and Netscript 2
|
||||
|
||||
* Supports (almost) all features of modern JavaScript
|
||||
* Extremely fast - code is executed as an Async Function
|
||||
* Currently only works with Google Chrome browser
|
||||
* Works on most modern browsers.
|
||||
* Each script becomes a module and therefore all instances of that script can easily
|
||||
share data between each other (essentially global/static variables)
|
||||
|
||||
@@ -24,8 +24,11 @@ level 3, then you will be able to access all of the Singularity Functions.
|
||||
travelToCity() <singularityfunctions/travelToCity>
|
||||
purchaseTor() <singularityfunctions/purchaseTor>
|
||||
purchaseProgram() <singularityfunctions/purchaseProgram>
|
||||
getStats() <singularityfunctions/getStats>
|
||||
getCharacterInformation() <singularityfunctions/getCharacterInformation>
|
||||
getCurrentServer() <singularityfunctions/getCurrentServer>
|
||||
connect() <singularityfunctions/connect>
|
||||
manualHack() <singularityfunctions/manualHack>
|
||||
getPlayer() <singularityfunctions/getPlayer>
|
||||
hospitalize() <singularityfunctions/hospitalize>
|
||||
isBusy() <singularityfunctions/isBusy>
|
||||
stopAction() <singularityfunctions/stopAction>
|
||||
upgradeHomeRam() <singularityfunctions/upgradeHomeRam>
|
||||
@@ -55,3 +58,10 @@ level 3, then you will be able to access all of the Singularity Functions.
|
||||
purchaseAugmentation() <singularityfunctions/purchaseAugmentation>
|
||||
installAugmentations() <singularityfunctions/installAugmentations>
|
||||
softReset() <singularityfunctions/softReset>
|
||||
|
||||
|
||||
.. toctree::
|
||||
:caption: Deprecated:
|
||||
|
||||
getStats() <singularityfunctions/getStats>
|
||||
getCharacterInformation() <singularityfunctions/getCharacterInformation>
|
||||
20
doc/source/netscript/singularityfunctions/connect.rst
Normal file
20
doc/source/netscript/singularityfunctions/connect.rst
Normal file
@@ -0,0 +1,20 @@
|
||||
connect() Netscript Function
|
||||
============================
|
||||
|
||||
.. js:function:: connect(hostname)
|
||||
|
||||
:RAM cost: 2 GB
|
||||
:param string hostname: hostname of the server to connect.
|
||||
:returns: ``true`` if the connection was a success.
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 1 of Source-File 4 in order to use this function.
|
||||
|
||||
This function will connect you to the specified server if it's directly connected to the current server.
|
||||
You can also pass in 'home' to return to your home server from anywhere.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
connect("joesguns");
|
||||
connect("CSEC");
|
||||
@@ -9,8 +9,12 @@ getAugmentationStats() Netscript Function
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 3 of Source-File 4 in order to use this function.
|
||||
|
||||
ns.getAugmentationStats("Synfibril Muscle")
|
||||
{
|
||||
strength_mult: 1.3,
|
||||
defense_mult: 1.3,
|
||||
}
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
ns.getAugmentationStats("Synfibril Muscle")
|
||||
{
|
||||
strength_mult: 1.3,
|
||||
defense_mult: 1.3,
|
||||
}
|
||||
|
||||
@@ -3,6 +3,8 @@ getCharacterInformation() Netscript Function
|
||||
|
||||
.. js:function:: getCharacterInformation()
|
||||
|
||||
.. warning:: This function is deprecated.
|
||||
|
||||
:RAM cost: 0.5 GB
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 1 of Source-File 4 in order to run this function.
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
getCurrentServer() Netscript Function
|
||||
=====================================
|
||||
|
||||
.. js:function:: getCurrentServer()
|
||||
|
||||
:RAM cost: 2 GB
|
||||
:returns: The hostname of the server the player is currently connected to.
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 3 of Source-File 4 in order to use this function.
|
||||
|
||||
103
doc/source/netscript/singularityfunctions/getPlayer.rst
Normal file
103
doc/source/netscript/singularityfunctions/getPlayer.rst
Normal file
@@ -0,0 +1,103 @@
|
||||
getPlayer() Netscript Function
|
||||
==============================
|
||||
|
||||
.. js:function:: getPlayer()
|
||||
|
||||
:RAM cost: 0.5 GB
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 1 of Source-File 4 in order to run this function.
|
||||
|
||||
The result of this function can be passed to the :doc:`formulas API<../netscriptformulasapi>`.
|
||||
|
||||
Returns an object with the Player's stats. The object has the following properties::
|
||||
|
||||
{
|
||||
hacking_skill
|
||||
hp
|
||||
max_hp
|
||||
strength
|
||||
defense
|
||||
dexterity
|
||||
agility
|
||||
charisma
|
||||
intelligence
|
||||
hacking_chance_mult
|
||||
hacking_speed_mult
|
||||
hacking_money_mult
|
||||
hacking_grow_mult
|
||||
hacking_exp
|
||||
strength_exp
|
||||
defense_exp
|
||||
dexterity_exp
|
||||
agility_exp
|
||||
charisma_exp
|
||||
hacking_mult
|
||||
strength_mult
|
||||
defense_mult
|
||||
dexterity_mult
|
||||
agility_mult
|
||||
charisma_mult
|
||||
hacking_exp_mult
|
||||
strength_exp_mult
|
||||
defense_exp_mult
|
||||
dexterity_exp_mult
|
||||
agility_exp_mult
|
||||
charisma_exp_mult
|
||||
company_rep_mult
|
||||
faction_rep_mult
|
||||
money
|
||||
city
|
||||
location
|
||||
crime_money_mult
|
||||
crime_success_mult
|
||||
isWorking
|
||||
workType
|
||||
currentWorkFactionName
|
||||
currentWorkFactionDescription
|
||||
workHackExpGainRate
|
||||
workStrExpGainRate
|
||||
workDefExpGainRate
|
||||
workDexExpGainRate
|
||||
workAgiExpGainRate
|
||||
workChaExpGainRate
|
||||
workRepGainRate
|
||||
workMoneyGainRate
|
||||
workMoneyLossRate
|
||||
workHackExpGained
|
||||
workStrExpGained
|
||||
workDefExpGained
|
||||
workDexExpGained
|
||||
workAgiExpGained
|
||||
workChaExpGained
|
||||
workRepGained
|
||||
workMoneyGained
|
||||
createProgramName
|
||||
createProgramReqLvl
|
||||
className
|
||||
crimeType
|
||||
work_money_mult
|
||||
hacknet_node_money_mult
|
||||
hacknet_node_purchase_cost_mult
|
||||
hacknet_node_ram_cost_mult
|
||||
hacknet_node_core_cost_mult
|
||||
hacknet_node_level_cost_mult
|
||||
hasWseAccount
|
||||
hasTixApiAccess
|
||||
has4SData
|
||||
has4SDataTixApi
|
||||
bladeburner_max_stamina_mult
|
||||
bladeburner_stamina_gain_mult
|
||||
bladeburner_success_chance_mult
|
||||
bitNodeN
|
||||
totalPlaytime
|
||||
playtimeSinceLastAug
|
||||
playtimeSinceLastBitnode
|
||||
jobs
|
||||
factions
|
||||
tor
|
||||
}
|
||||
|
||||
Example::
|
||||
|
||||
player = getPlayer();
|
||||
print('My charisma level is: ' + player.charisma);
|
||||
@@ -3,6 +3,8 @@ getStats() Netscript Function
|
||||
|
||||
.. js:function:: getStats()
|
||||
|
||||
.. warning:: This function is deprecated.
|
||||
|
||||
:RAM cost: 0.5 GB
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 1 of Source-File 4 in order to run this function.
|
||||
|
||||
11
doc/source/netscript/singularityfunctions/hospitalize.rst
Normal file
11
doc/source/netscript/singularityfunctions/hospitalize.rst
Normal file
@@ -0,0 +1,11 @@
|
||||
hospitalize() Netscript Function
|
||||
===================================
|
||||
|
||||
.. js:function:: hospitalize()
|
||||
|
||||
:RAM cost: 1 GB
|
||||
:returns: The cost of your visit to the hospital.
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 1 of Source-File 4 in order to use this function.
|
||||
|
||||
Hospitalize yourself. Recovering all lost hp.
|
||||
23
doc/source/netscript/singularityfunctions/manualHack.rst
Normal file
23
doc/source/netscript/singularityfunctions/manualHack.rst
Normal file
@@ -0,0 +1,23 @@
|
||||
manualHack() Netscript Function
|
||||
===============================
|
||||
|
||||
.. js:function:: manualHack()
|
||||
|
||||
:RAM cost: 2 GB
|
||||
:returns: The amount of money stolen if the hack is successful, and zero otherwise
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 1 of Source-File 4 in order to use this function.
|
||||
|
||||
This function will perform a manual hack on the server you are currently connected to.
|
||||
|
||||
Examples:
|
||||
|
||||
.. code-block:: javascript
|
||||
|
||||
connect("foodnstuff");
|
||||
manualHack();
|
||||
|
||||
.. warning::
|
||||
For NS2 users:
|
||||
|
||||
This function is async.
|
||||
@@ -1,7 +1,13 @@
|
||||
softReset() Netscript Function
|
||||
===================================
|
||||
|
||||
.. js:function:: softReset()
|
||||
.. js:function:: softReset([callbackScript])
|
||||
|
||||
:RAM cost: 5 GB
|
||||
:param string cbScript:
|
||||
Optional callback script. This is a script that will automatically be
|
||||
run after the soft reset. This script will be run with no arguments and
|
||||
1 thread. It must be located on your home computer.
|
||||
|
||||
If you are not in BitNode-4, then you must have Level 3 of Source-File 4 in order to use this function.
|
||||
|
||||
|
||||
@@ -31,6 +31,8 @@ Alt + f Switch to 'Factions' page
|
||||
Alt + a Switch to 'Augmentations' page
|
||||
Alt + u Switch to 'Tutorial' page
|
||||
Alt + o Switch to 'Options' page
|
||||
Alt + g Switch to 'Gang' page
|
||||
Alt + b Switch to 'Bladeburner' page
|
||||
========== ===========================================================================
|
||||
|
||||
Script Editor
|
||||
|
||||
64
index.html
64
index.html
@@ -30,7 +30,7 @@
|
||||
<div id="entire-game-container" style="visibility:hidden;">
|
||||
<div id="mainmenu-container">
|
||||
<!-- Main menu -->
|
||||
<ul id="mainmenu" class="mainmenu">
|
||||
<ul id="mainmenu" class="mainmenu noscrollbar">
|
||||
<!-- Hacking dropdown -->
|
||||
<li id="hacking-menu-header-li">
|
||||
<button id="hacking-menu-header" class="mainmenu-accordion-header"> Hacking </button>
|
||||
@@ -100,9 +100,12 @@
|
||||
<li id="help-menu-header-li">
|
||||
<button id="help-menu-header" class="mainmenu-accordion-header"> Help </button>
|
||||
</li>
|
||||
<li id="tutorial-tab" class="mainmenu-accordion-panel">
|
||||
<button id="tutorial-menu-link"> Tutorial </button>
|
||||
</li>
|
||||
<li id="milestones-tab" class="mainmenu-accordion-panel">
|
||||
<button id="milestones-menu-link"> Milestones </button>
|
||||
</li>
|
||||
<li id="tutorial-tab" class="mainmenu-accordion-panel">
|
||||
<button id="tutorial-menu-link"> Tutorial </button>
|
||||
</li>
|
||||
<li id="options-tab" class="mainmenu-accordion-panel">
|
||||
<button id="options-menu-link"> Options </button>
|
||||
</li>
|
||||
@@ -177,7 +180,7 @@
|
||||
<table id="terminal">
|
||||
<tr id="terminal-input">
|
||||
<td id="terminal-input-td" tabindex="2">$
|
||||
<input type="text" id="terminal-input-text-box" class="terminal-input" tabindex="1" onfocus="this.value = this.value;"/>
|
||||
<input type="text" id="terminal-input-text-box" class="terminal-input" tabindex="1" onfocus="this.value = this.value;" autocomplete="off"/>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
@@ -226,6 +229,10 @@
|
||||
<!-- Augmentations -->
|
||||
<div id="augmentations-container" class="generic-menupage-container"></div>
|
||||
|
||||
<!-- Milestones content -->
|
||||
<div id="milestones-container" class="generic-menupage-container">
|
||||
</div>
|
||||
|
||||
<!-- Tutorial content -->
|
||||
<div id="tutorial-container" class="generic-menupage-container">
|
||||
<h1> Tutorial (AKA Links to Documentation) </h1>
|
||||
@@ -261,16 +268,16 @@
|
||||
<div id="infiltration-left-panel">
|
||||
<p id="infiltration-level-text"> </p>
|
||||
<div id="infiltration-buttons">
|
||||
<a class="a-link-button tooltip" id="infiltration-kill"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-knockout"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-stealthknockout"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-assassinate"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-hacksecurity"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-destroysecurity"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-sneak"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-pickdoor"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-bribe"> </a>
|
||||
<a class="a-link-button tooltip" id="infiltration-escape"> </a>
|
||||
<button class="a-link-button tooltip" id="infiltration-kill"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-knockout"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-stealthknockout"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-assassinate"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-hacksecurity"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-destroysecurity"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-sneak"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-pickdoor"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-bribe"> </button>
|
||||
<button class="a-link-button tooltip" id="infiltration-escape"> </button>
|
||||
</div>
|
||||
</div>
|
||||
<div id="infiltration-right-panel">
|
||||
@@ -381,13 +388,13 @@
|
||||
|
||||
<!-- Status text -->
|
||||
<div id="status-text-container">
|
||||
<p id="status-text"> </p>
|
||||
<p id="status-text"></p>
|
||||
</div>
|
||||
|
||||
<!-- Game Options -->
|
||||
<div id="game-options-container" class="popup-box-container">
|
||||
<div id="game-options-content" class="game-options-box">
|
||||
<button id="game-options-close-button">×</button>
|
||||
<button id="game-options-close-button" aria-label="close options dialog">×</button>
|
||||
<h1> Game Options </h1>
|
||||
<br/>
|
||||
<div id="game-options-left-panel">
|
||||
@@ -511,6 +518,26 @@
|
||||
<input class="optionCheckbox" type="checkbox" name="settingsDisableHotkeys" id="settingsDisableHotkeys">
|
||||
</fieldset>
|
||||
|
||||
<!-- View city as list of buttons instead of ASCII art. -->
|
||||
<fieldset>
|
||||
<label for="settingsDisableASCIIArt" class="tooltip">Disable ASCII art:
|
||||
<span class="tooltiptexthigh">
|
||||
If this is set all ASCII art will be disabled.
|
||||
</span>
|
||||
</label>
|
||||
<input class="optionCheckbox" type="checkbox" name="settingsDisableASCIIArt" id="settingsDisableASCIIArt">
|
||||
</fieldset>
|
||||
|
||||
<!-- Disable text effects such as corruption. -->
|
||||
<fieldset>
|
||||
<label for="settingsDisableTextEffects" class="tooltip">Disable Text Effects:
|
||||
<span class="tooltiptexthigh">
|
||||
If this is set, text effects will not be displayed. This can help if text is difficult to read in certain areas.
|
||||
</span>
|
||||
</label>
|
||||
<input class="optionCheckbox" type="checkbox" name="settingsDisableTextEffects" id="settingsDisableTextEffects">
|
||||
</fieldset>
|
||||
|
||||
<!-- Locale for displaying numbers -->
|
||||
<fieldset>
|
||||
<label for="settingsLocale" class="tooltip">Locale:
|
||||
@@ -549,6 +576,7 @@
|
||||
<div id="game-options-right-panel">
|
||||
<a class="a-link-button" href="https://bitburner.readthedocs.io/en/latest/changelog.html" target="_blank"> Changelog </a>
|
||||
<a class="a-link-button" href="https://bitburner.readthedocs.io/en/latest/index.html" target="_blank">Documentation</a>
|
||||
<a class="a-link-button" href="https://discord.gg/TFc3hKD" target="_blank">Discord</a>
|
||||
<a class="a-link-button" href="https://www.reddit.com/r/bitburner" target="_blank">Subreddit</a>
|
||||
<button id="save-game-link" class="a-link-button"> Save Game </button>
|
||||
<button id="delete-game-link" class="a-link-button"> Delete Game </button>
|
||||
@@ -590,6 +618,8 @@
|
||||
<p>If the game fails to load, consider <a href="?noScripts">killing all scripts</a></p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div id="unclickable" style="display: none">Click on this to upgrade your Source-File -1!</div>
|
||||
<script type="text/javascript" src="dist/vendor.bundle.js"></script><script type="text/javascript" src="dist/engine.bundle.js"></script><script type="text/javascript" src="dist/engineStyle.bundle.js"></script></body>
|
||||
|
||||
<!-- Misc Scripts -->
|
||||
|
||||
13822
package-lock.json
generated
13822
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
20
package.json
20
package.json
@@ -6,6 +6,7 @@
|
||||
"url": "https://github.com/danielyxie/bitburner/issues"
|
||||
},
|
||||
"dependencies": {
|
||||
"@material-ui/core": "^4.11.3",
|
||||
"@types/numeral": "0.0.25",
|
||||
"@types/react": "^16.8.6",
|
||||
"@types/react-dom": "^16.8.2",
|
||||
@@ -13,6 +14,7 @@
|
||||
"acorn-walk": "^6.2.0",
|
||||
"ajv": "^5.1.5",
|
||||
"ajv-keywords": "^2.0.0",
|
||||
"arg": "^5.0.0",
|
||||
"async": "^2.6.1",
|
||||
"autosize": "^4.0.2",
|
||||
"brace": "^0.11.1",
|
||||
@@ -35,6 +37,7 @@
|
||||
"numeral": "2.0.6",
|
||||
"react": "^16.8.3",
|
||||
"react-dom": "^16.8.3",
|
||||
"react-modal": "^3.12.1",
|
||||
"sprintf-js": "^1.1.1",
|
||||
"tapable": "^1.0.0",
|
||||
"uuid": "^3.2.1",
|
||||
@@ -45,7 +48,10 @@
|
||||
"@babel/core": "^7.3.4",
|
||||
"@babel/preset-react": "^7.0.0",
|
||||
"@types/chai": "^4.1.7",
|
||||
"@types/lodash": "^4.14.168",
|
||||
"@types/mocha": "^5.2.7",
|
||||
"@typescript-eslint/eslint-plugin": "^4.22.0",
|
||||
"@typescript-eslint/parser": "^4.22.0",
|
||||
"babel-loader": "^8.0.5",
|
||||
"beautify-lint": "^1.0.3",
|
||||
"benchmark": "^2.1.1",
|
||||
@@ -53,8 +59,8 @@
|
||||
"chai": "^4.2.0",
|
||||
"css-loader": "^0.28.11",
|
||||
"es6-promise-polyfill": "^1.1.1",
|
||||
"eslint": "^4.19.1",
|
||||
"eslint-plugin-node": "^6.0.1",
|
||||
"eslint": "^7.24.0",
|
||||
"eslint-plugin-node": "^11.1.0",
|
||||
"file-loader": "^1.1.11",
|
||||
"html-webpack-plugin": "^3.2.0",
|
||||
"i18n-webpack-plugin": "^1.0.0",
|
||||
@@ -84,8 +90,7 @@
|
||||
"stylelint-declaration-use-variable": "^1.6.1",
|
||||
"stylelint-order": "^0.8.1",
|
||||
"ts-loader": "^4.5.0",
|
||||
"tslint": "^5.10.0",
|
||||
"typescript": "^2.9.2",
|
||||
"typescript": "^4.2.4",
|
||||
"uglify-es": "^3.3.9",
|
||||
"uglifyjs-webpack-plugin": "^1.3.0",
|
||||
"url-loader": "^1.0.1",
|
||||
@@ -111,14 +116,13 @@
|
||||
"build": "webpack --mode production",
|
||||
"build:dev": "webpack --mode development",
|
||||
"build:test": "webpack --config webpack.config-test.js",
|
||||
"lint": "npm run lint:typescript & npm run lint:javascript & npm run lint:style",
|
||||
"lint:javascript": "eslint *.js ./src/**/*.js ./tests/**/*.js ./utils/**/*.js",
|
||||
"lint": "npm run lint:jsts & npm run lint:style",
|
||||
"lint:jsts": "eslint '*.{js,jsx,ts,tsx}' './src/**/*.{js,jsx,ts,tsx}' './test/**/*.{js,jsx,ts,tsx}' './utils/**/*.{js,jsx,ts,tsx}'",
|
||||
"lint:style": "stylelint ./css/*",
|
||||
"lint:typescript": "tslint --project . --exclude **/*.d.ts --format stylish src/**/*.ts utils/**/*.ts",
|
||||
"preinstall": "node ./scripts/engines-check.js",
|
||||
"test": "mochapack --webpack-config webpack.config-test.js -r jsdom-global/register ./test/index.js",
|
||||
"watch": "webpack --watch --mode production",
|
||||
"watch:dev": "webpack --watch --mode development"
|
||||
},
|
||||
"version": "0.49.2"
|
||||
"version": "0.51.5"
|
||||
}
|
||||
|
||||
@@ -35,7 +35,7 @@ export function printAliases(): void {
|
||||
}
|
||||
|
||||
// Returns true if successful, false otherwise
|
||||
export function parseAliasDeclaration(dec: string, global: boolean=false) {
|
||||
export function parseAliasDeclaration(dec: string, global = false): boolean {
|
||||
var re = /^([_|\w|!|%|,|@]+)="(.+)"$/;
|
||||
var matches = dec.match(re);
|
||||
if (matches == null || matches.length != 3) {return false;}
|
||||
|
||||
@@ -31,6 +31,7 @@ import { clearObject } from "../../utils/helpers/clearObject";
|
||||
import { createElement } from "../../utils/uiHelpers/createElement";
|
||||
import { isString } from "../../utils/helpers/isString";
|
||||
import { removeChildrenFromElement } from "../../utils/uiHelpers/removeChildrenFromElement";
|
||||
import { Money } from "../ui/React/Money";
|
||||
|
||||
import React from "react";
|
||||
import ReactDOM from "react-dom";
|
||||
@@ -177,7 +178,7 @@ function initAugmentations() {
|
||||
const CombatRib3 = new Augmentation({
|
||||
name:AugmentationNames.CombatRib3, repCost:14e3, moneyCost:24e6,
|
||||
info:"This is an upgrade to the Combat Rib II augmentation, and is capable of releasing even more potent combat-enhancing " +
|
||||
"drugs into the bloodstream<br><br>." +
|
||||
"drugs into the bloodstream.<br><br>" +
|
||||
"This augmentation increases the player's strength and defense by 18%.",
|
||||
prereqs:[AugmentationNames.CombatRib2],
|
||||
strength_mult: 1.18,
|
||||
@@ -880,9 +881,7 @@ function initAugmentations() {
|
||||
info:"The body is genetically re-engineered so that it produces the ADR-V1 pheromone, " +
|
||||
"an artificial pheromone discovered by scientists. The ADR-V1 pheromone, when excreted, " +
|
||||
"triggers feelings of admiration and approval in other people.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the amount of reputation the player gains when working for a company by 10% <br>" +
|
||||
"Increases the amount of reputation the player gains for a faction by 10%.",
|
||||
"This augmentation increases the amount of reputation the player gains when working for a faction or company by 10%.",
|
||||
company_rep_mult: 1.1,
|
||||
faction_rep_mult: 1.1,
|
||||
});
|
||||
@@ -897,8 +896,7 @@ function initAugmentations() {
|
||||
info:"The body is genetically re-engineered so that it produces the ADR-V2 pheromone, " +
|
||||
"which is similar to but more potent than ADR-V1. This pheromone, when excreted, " +
|
||||
"triggers feelings of admiration, approval, and respect in others.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the amount of reputation the player gains for a faction and company by 20%.",
|
||||
"This augmentation increases the amount of reputation the player gains when working for a faction or company by 20%.",
|
||||
company_rep_mult: 1.2,
|
||||
faction_rep_mult: 1.2,
|
||||
});
|
||||
@@ -915,8 +913,7 @@ function initAugmentations() {
|
||||
"criminal organizations and allows the user to project and control holographic " +
|
||||
"simulacrums within a large radius. These simulacrums are commonly used for " +
|
||||
"espionage and surveillance work.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the amount of reputation the player gains when working for a faction or company by 15%.",
|
||||
"This augmentation increases the amount of reputation the player gains when working for a faction or company by 15%.",
|
||||
company_rep_mult: 1.15,
|
||||
faction_rep_mult: 1.15,
|
||||
});
|
||||
@@ -1152,7 +1149,7 @@ function initAugmentations() {
|
||||
"cells, when powered, have a negative refractive index. As a result, they bend light " +
|
||||
"around the skin, making the user much harder to see from the naked eye.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the player's agility by 5% <br>" +
|
||||
"Increases the player's agility by 5%.<br>" +
|
||||
"Increases the amount of money the player gains from crimes by 10%.",
|
||||
agility_mult: 1.05,
|
||||
crime_money_mult: 1.1,
|
||||
@@ -1170,8 +1167,8 @@ function initAugmentations() {
|
||||
"cells, when powered, are capable of not only bending light but also of bending heat, " +
|
||||
"making the user more resilient as well as stealthy.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the player's agility by 10% <br>" +
|
||||
"Increases the player's defense by 10% <br>" +
|
||||
"Increases the player's agility by 10%.<br>" +
|
||||
"Increases the player's defense by 10%.<br>" +
|
||||
"Increases the amount of money the player gains from crimes by 25%.",
|
||||
prereqs:[AugmentationNames.LuminCloaking1],
|
||||
agility_mult: 1.1,
|
||||
@@ -1372,7 +1369,7 @@ function initAugmentations() {
|
||||
name:AugmentationNames.Xanipher, repCost:350e3, moneyCost:850e6,
|
||||
info:"A concoction of advanced nanobots that is orally ingested into the " +
|
||||
"body. These nanobots induce physiological change and significantly " +
|
||||
"improve the body's functionining in all aspects.<br><br>" +
|
||||
"improve the body's functioning in all aspects.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases all of the player's stats by 20%.<br>" +
|
||||
"Increases the player's experience gain rate for all stats by 15%.",
|
||||
@@ -1395,6 +1392,23 @@ function initAugmentations() {
|
||||
}
|
||||
AddToAugmentations(Xanipher);
|
||||
|
||||
const HydroflameLeftArm = new Augmentation({
|
||||
name:AugmentationNames.HydroflameLeftArm, repCost:500e3, moneyCost:500e9,
|
||||
info:"The left arm of a legendary BitRunner who ascended beyond this world. " +
|
||||
"It projects a light blue energy shield that protects the exposed inner parts. " +
|
||||
"Even though it contains no weapons, the advance tungsten titanium " +
|
||||
"alloy increases the users strength to unbelievable levels.<br><br>" +
|
||||
"This augmentation increases the player's strength by 300%.",
|
||||
strength_mult: 3,
|
||||
});
|
||||
HydroflameLeftArm.addToFactions(["NWO"]);
|
||||
if (augmentationExists(AugmentationNames.HydroflameLeftArm)) {
|
||||
delete Augmentations[AugmentationNames.HydroflameLeftArm];
|
||||
}
|
||||
AddToAugmentations(HydroflameLeftArm);
|
||||
|
||||
|
||||
|
||||
// ClarkeIncorporated
|
||||
const nextSENS = new Augmentation({
|
||||
name:AugmentationNames.nextSENS, repCost:175e3, moneyCost:385e6,
|
||||
@@ -1537,12 +1551,12 @@ function initAugmentations() {
|
||||
// Sector12
|
||||
const CashRoot = new Augmentation({
|
||||
name:AugmentationNames.CashRoot, repCost:5e3, moneyCost:25e6,
|
||||
info:"A collection of digital assets saved on a small chip. The chip is implanted " +
|
||||
"into your wrist. A small jack in the chip allows you to connect it to a computer " +
|
||||
"and upload the assets.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Lets the player start with $1,000,000 after a reset.<br>" +
|
||||
"Lets the player start with the BruteSSH.exe program after a reset."
|
||||
info:<>A collection of digital assets saved on a small chip. The chip is implanted
|
||||
into your wrist. A small jack in the chip allows you to connect it to a computer
|
||||
and upload the assets.<br /><br />
|
||||
This augmentation:<br />
|
||||
Lets the player start with {Money(1e6)} after a reset.<br />
|
||||
Lets the player start with the BruteSSH.exe program after a reset.</>
|
||||
});
|
||||
CashRoot.addToFactions(["Sector-12"]);
|
||||
if (augmentationExists(AugmentationNames.CashRoot)) {
|
||||
@@ -1557,8 +1571,7 @@ function initAugmentations() {
|
||||
"synthesizes glucose, amino acids, and vitamins and redistributes them " +
|
||||
"across the body. The device is powered by the body's naturally wasted " +
|
||||
"energy in the form of heat.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the player's experience gain rate for all combat stats by 20%.",
|
||||
"This augmentation increases the player's experience gain rate for all combat stats by 20%.",
|
||||
strength_exp_mult: 1.2,
|
||||
defense_exp_mult: 1.2,
|
||||
dexterity_exp_mult: 1.2,
|
||||
@@ -1768,8 +1781,7 @@ function initAugmentations() {
|
||||
"nature of the plasma disrupts the electrical systems of Augmentations. However, " +
|
||||
"it can also be effective against non-augmented enemies due to its high temperature " +
|
||||
"and concussive force.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the player's success chance in Bladeburner contracts/operations by 6%.",
|
||||
"This augmentation increases the player's success chance in Bladeburner contracts/operations by 6%.",
|
||||
bladeburner_success_chance_mult: 1.06,
|
||||
isSpecial: true,
|
||||
});
|
||||
@@ -1782,8 +1794,7 @@ function initAugmentations() {
|
||||
"is more advanced and powerful than the original V1 model. This V2 model is " +
|
||||
"more power-efficiency, more accurate, and can fire plasma bolts at a much " +
|
||||
"higher velocity than the V1 model.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the player's success chance in Bladeburner contracts/operations by 8%.",
|
||||
"This augmentation increases the player's success chance in Bladeburner contracts/operations by 8%.",
|
||||
prereqs:[AugmentationNames.HyperionV1],
|
||||
bladeburner_success_chance_mult: 1.08,
|
||||
isSpecial: true,
|
||||
@@ -1941,8 +1952,7 @@ function initAugmentations() {
|
||||
info:"Upgrades the BLADE-51b Tesla Armor with a concentrated deuterium-fluoride laser " +
|
||||
"weapon. It's precision an accuracy makes it useful for quickly neutralizing " +
|
||||
"threats while keeping casualties to a minimum.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the player's success chance in Bladeburner contracts/operations by 8%.",
|
||||
"This augmentation increases the player's success chance in Bladeburner contracts/operations by 8%.",
|
||||
prereqs:[AugmentationNames.BladeArmor],
|
||||
bladeburner_success_chance_mult: 1.08,
|
||||
isSpecial: true,
|
||||
@@ -1956,8 +1966,7 @@ function initAugmentations() {
|
||||
"multiple-fiber system. The upgraded weapon uses multiple fiber laser " +
|
||||
"modules that combine together to form a single, more powerful beam of up to " +
|
||||
"2000MW.<br><br>" +
|
||||
"This augmentation:<br>" +
|
||||
"Increases the player's success chance in Bladeburner contracts/operations by 10%.",
|
||||
"This augmentation increases the player's success chance in Bladeburner contracts/operations by 10%.",
|
||||
prereqs:[AugmentationNames.BladeArmorUnibeam],
|
||||
bladeburner_success_chance_mult: 1.1,
|
||||
isSpecial: true,
|
||||
|
||||
@@ -89,6 +89,7 @@ export let AugmentationNames: IMap<string> = {
|
||||
BrachiBlades: "BrachiBlades",
|
||||
BionicArms: "Bionic Arms",
|
||||
SNA: "Social Negotiation Assistant (S.N.A)",
|
||||
HydroflameLeftArm: "Hydroflame Left Arm",
|
||||
EsperEyewear: "EsperTech Bladeburner Eyewear",
|
||||
EMS4Recombination: "EMS-4 Recombination",
|
||||
OrionShoulder: "ORION-MKIV Shoulder",
|
||||
|
||||
@@ -26,8 +26,8 @@ export function PlayerMultipliers(): React.ReactElement {
|
||||
let elems: any[] = [];
|
||||
if(r) {
|
||||
elems = [
|
||||
<td key='2'> => </td>,
|
||||
<td key='3'>{numeralWrapper.formatPercentage(r)}</td>
|
||||
<td key="2"> {"=>"} </td>,
|
||||
<td key="3">{numeralWrapper.formatPercentage(r)}</td>
|
||||
];
|
||||
}
|
||||
return elems;
|
||||
@@ -36,8 +36,8 @@ export function PlayerMultipliers(): React.ReactElement {
|
||||
return <table>
|
||||
<tbody>
|
||||
{rows.map((r: any) => <tr key={r[0]}>
|
||||
<td key='0'><span>{r[0]} multiplier: </span></td>
|
||||
<td key='1' style={{textAlign: 'right'}}>{numeralWrapper.formatPercentage(r[1])}</td>
|
||||
<td key="0"><span>{r[0]} multiplier: </span></td>
|
||||
<td key="1" style={{textAlign: 'right'}}>{numeralWrapper.formatPercentage(r[1])}</td>
|
||||
{improvements(r[2])}
|
||||
</tr>)}
|
||||
</tbody>
|
||||
|
||||
@@ -234,7 +234,7 @@ BitNodes["BitNode11"] = new BitNode(11, "The Big Crash", "Okay. Sell it all.",
|
||||
"Level 3: 56%");
|
||||
BitNodes["BitNode12"] = new BitNode(12, "The Recursion", "Repeat.",
|
||||
"To iterate is human, to recurse divine.<br><br>" +
|
||||
"Every time this BitNode is destroyed, it becomes slightly harder. Destroying this BitNode will give you Souce-File 12, or " +
|
||||
"Every time this BitNode is destroyed, it becomes slightly harder. Destroying this BitNode will give you Source-File 12, or " +
|
||||
"if you already have this Source-File it will upgrade its level. There is no maximum level for Source-File 12. Each level " +
|
||||
"of Source-File 12 will increase all of your multipliers by 1%. This effect is multiplicative with itself. " +
|
||||
"In other words, level N of this Source-File will result in a multiplier of 1.01^N (or 0.99^N for multipliers that decrease)");
|
||||
@@ -274,6 +274,7 @@ export function initBitNodeMultipliers(p: IPlayer) {
|
||||
BitNodeMultipliers.InfiltrationMoney = 3;
|
||||
BitNodeMultipliers.FactionWorkRepGain = 0.5;
|
||||
BitNodeMultipliers.FactionPassiveRepGain = 0;
|
||||
BitNodeMultipliers.GangKarmaRequirement = 0;
|
||||
break;
|
||||
case 3: // Corporatocracy
|
||||
BitNodeMultipliers.HackingLevelMultiplier = 0.8;
|
||||
@@ -289,6 +290,7 @@ export function initBitNodeMultipliers(p: IPlayer) {
|
||||
BitNodeMultipliers.HacknetNodeMoney = 0.25;
|
||||
BitNodeMultipliers.HomeComputerRamCost = 1.5;
|
||||
BitNodeMultipliers.PurchasedServerCost = 2;
|
||||
BitNodeMultipliers.GangKarmaRequirement = 3;
|
||||
break;
|
||||
case 4: // The Singularity
|
||||
BitNodeMultipliers.ServerMaxMoney = 0.15;
|
||||
@@ -331,6 +333,7 @@ export function initBitNodeMultipliers(p: IPlayer) {
|
||||
BitNodeMultipliers.FactionPassiveRepGain = 0;
|
||||
BitNodeMultipliers.HackExpGain = 0.25;
|
||||
BitNodeMultipliers.DaedalusAugsRequirement = 1.166; // Results in 35 Augs needed
|
||||
BitNodeMultipliers.GangKarmaRequirement = 5;
|
||||
break;
|
||||
case 7: // Bladeburner 2079
|
||||
BitNodeMultipliers.BladeburnerRank = 0.6;
|
||||
@@ -351,6 +354,7 @@ export function initBitNodeMultipliers(p: IPlayer) {
|
||||
BitNodeMultipliers.FourSigmaMarketDataCost = 2;
|
||||
BitNodeMultipliers.FourSigmaMarketDataApiCost = 2;
|
||||
BitNodeMultipliers.DaedalusAugsRequirement = 1.166; // Results in 35 Augs needed
|
||||
BitNodeMultipliers.GangKarmaRequirement = 5;
|
||||
break;
|
||||
case 8: // Ghost of Wall Street
|
||||
BitNodeMultipliers.ScriptHackMoney = 0.3;
|
||||
@@ -363,6 +367,7 @@ export function initBitNodeMultipliers(p: IPlayer) {
|
||||
BitNodeMultipliers.RepToDonateToFaction = 0;
|
||||
BitNodeMultipliers.CorporationValuation = 0;
|
||||
BitNodeMultipliers.CodingContractMoney = 0;
|
||||
BitNodeMultipliers.GangKarmaRequirement = 10;
|
||||
break;
|
||||
case 9: // Hacktocracy
|
||||
BitNodeMultipliers.HackingLevelMultiplier = 0.4;
|
||||
@@ -384,6 +389,7 @@ export function initBitNodeMultipliers(p: IPlayer) {
|
||||
BitNodeMultipliers.FourSigmaMarketDataApiCost = 4;
|
||||
BitNodeMultipliers.BladeburnerRank = 0.9;
|
||||
BitNodeMultipliers.BladeburnerSkillCost = 1.2;
|
||||
BitNodeMultipliers.GangKarmaRequirement = 3;
|
||||
break;
|
||||
case 10: // Digital Carbon
|
||||
BitNodeMultipliers.HackingLevelMultiplier = 0.2;
|
||||
@@ -407,6 +413,7 @@ export function initBitNodeMultipliers(p: IPlayer) {
|
||||
BitNodeMultipliers.PurchasedServerLimit = 0.6;
|
||||
BitNodeMultipliers.PurchasedServerMaxRam = 0.5;
|
||||
BitNodeMultipliers.BladeburnerRank = 0.8;
|
||||
BitNodeMultipliers.GangKarmaRequirement = 3;
|
||||
break;
|
||||
case 11: //The Big Crash
|
||||
BitNodeMultipliers.HackingLevelMultiplier = 0.5;
|
||||
|
||||
@@ -109,6 +109,11 @@ interface IBitNodeMultipliers {
|
||||
*/
|
||||
FourSigmaMarketDataCost: number;
|
||||
|
||||
/**
|
||||
* Influences how much negative karma is required to create a gang in this bitnode.
|
||||
*/
|
||||
GangKarmaRequirement: number;
|
||||
|
||||
/**
|
||||
* Influences the experienced gained when hacking a server.
|
||||
*/
|
||||
@@ -268,4 +273,5 @@ export const BitNodeMultipliers: IBitNodeMultipliers = {
|
||||
BladeburnerSkillCost: 1,
|
||||
|
||||
DaedalusAugsRequirement: 1,
|
||||
GangKarmaRequirement: 1,
|
||||
};
|
||||
|
||||
@@ -8,6 +8,7 @@ import { Factions, factionExists } from "./Faction/Factions";
|
||||
import { joinFaction, displayFactionContent } from "./Faction/FactionHelpers";
|
||||
import { Player } from "./Player";
|
||||
import { hackWorldDaemon, redPillFlag } from "./RedPill";
|
||||
import { calculateHospitalizationCost } from "./Hospital/Hospital";
|
||||
|
||||
import { Page, routing } from "./ui/navigationTracking";
|
||||
import { numeralWrapper } from "./ui/numeralFormat";
|
||||
@@ -50,6 +51,12 @@ import { createPopup } from "../utils/uiHelpers/createPopup";
|
||||
import { removeElement } from "../utils/uiHelpers/removeElement";
|
||||
import { removeElementById } from "../utils/uiHelpers/removeElementById";
|
||||
|
||||
import { StatsTable } from "./ui/React/StatsTable";
|
||||
import { CopyableText } from "./ui/React/CopyableText";
|
||||
import { Money } from "./ui/React/Money";
|
||||
import React from "react";
|
||||
import ReactDOM from "react-dom";
|
||||
|
||||
const stealthIcon = `<svg xmlns="http://www.w3.org/2000/svg" width="16px" height="16px" viewBox="0 0 166 132" style="fill:#adff2f;"><g><path d="M132.658-0.18l-24.321,24.321c-7.915-2.71-16.342-4.392-25.087-4.392c-45.84,0-83,46-83,46 s14.1,17.44,35.635,30.844L12.32,120.158l12.021,12.021L144.68,11.841L132.658-0.18z M52.033,80.445 c-2.104-4.458-3.283-9.438-3.283-14.695c0-19.054,15.446-34.5,34.5-34.5c5.258,0,10.237,1.179,14.695,3.284L52.033,80.445z"/><path d="M134.865,37.656l-18.482,18.482c0.884,3.052,1.367,6.275,1.367,9.612c0,19.055-15.446,34.5-34.5,34.5 c-3.337,0-6.56-0.483-9.611-1.367l-10.124,10.124c6.326,1.725,12.934,2.743,19.735,2.743c45.84,0,83-46,83-46 S153.987,50.575,134.865,37.656z"/></g></svg> `
|
||||
const killIcon = `<svg xmlns="http://www.w3.org/2000/svg" width="16px" height="16px" viewBox="-22 0 511 511.99561" style="fill:#adff2f;"><path d="m.496094 466.242188 39.902344-39.902344 45.753906 45.753906-39.898438 39.902344zm0 0"/><path d="m468.421875 89.832031-1.675781-89.832031-300.265625 300.265625 45.753906 45.753906zm0 0"/><path d="m95.210938 316.785156 16.84375 16.847656h.003906l83.65625 83.65625 22.753906-22.753906-100.503906-100.503906zm0 0"/><path d="m101.445312 365.300781-39.902343 39.902344 45.753906 45.753906 39.902344-39.902343-39.90625-39.902344zm0 0"/></svg>`
|
||||
|
||||
@@ -706,7 +713,7 @@ Bladeburner.prototype.completeAction = function() {
|
||||
if (isOperation && this.logging.ops) {
|
||||
this.log(action.name + " successfully completed! Gained " + formatNumber(gain, 3) + " rank");
|
||||
} else if (!isOperation && this.logging.contracts) {
|
||||
this.log(action.name + " contract successfully completed! Gained " + formatNumber(gain, 3) + " rank and " + numeralWrapper.format(moneyGain, "$0.000a"));
|
||||
this.log(action.name + " contract successfully completed! Gained " + formatNumber(gain, 3) + " rank and " + numeralWrapper.formatMoney(moneyGain));
|
||||
}
|
||||
}
|
||||
isOperation ? this.completeOperation(true) : this.completeContract(true);
|
||||
@@ -722,9 +729,10 @@ Bladeburner.prototype.completeAction = function() {
|
||||
damage = action.hpLoss * difficultyMultiplier;
|
||||
damage = Math.ceil(addOffset(damage, 10));
|
||||
this.hpLost += damage;
|
||||
const cost = calculateHospitalizationCost(Player, damage);
|
||||
if (Player.takeDamage(damage)) {
|
||||
++this.numHosp;
|
||||
this.moneyLost += (CONSTANTS.HospitalCostPerHp * Player.max_hp);
|
||||
this.moneyLost += cost;
|
||||
}
|
||||
}
|
||||
var logLossText = "";
|
||||
@@ -794,9 +802,10 @@ Bladeburner.prototype.completeAction = function() {
|
||||
if (action.hpLoss) {
|
||||
damage = action.hpLoss * difficultyMultiplier;
|
||||
damage = Math.ceil(addOffset(damage, 10));
|
||||
const cost = calculateHospitalizationCost(Player, damage);
|
||||
if (Player.takeDamage(damage)) {
|
||||
++this.numHosp;
|
||||
this.moneyLost += (CONSTANTS.HospitalCostPerHp * Player.max_hp);
|
||||
this.moneyLost += cost;
|
||||
}
|
||||
}
|
||||
teamLossMax = Math.floor(teamCount);
|
||||
@@ -899,7 +908,7 @@ Bladeburner.prototype.completeAction = function() {
|
||||
this.stamina = Math.min(this.maxStamina, this.stamina + staminaGain);
|
||||
this.startAction(this.action);
|
||||
if (this.logging.general) {
|
||||
this.log(`Rested in Hyperbolic Regeneration Chamber. Restored ${BladeburnerConstants.HrcHpGain} HP and gained ${numeralWrapper.format(staminaGain, "0.0")} stamina`);
|
||||
this.log(`Rested in Hyperbolic Regeneration Chamber. Restored ${BladeburnerConstants.HrcHpGain} HP and gained ${numeralWrapper.formatStamina(staminaGain)} stamina`);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -1060,7 +1069,11 @@ Bladeburner.prototype.gainActionStats = function(action, success) {
|
||||
Player.gainDexterityExp(unweightedGain * action.weights.dex * Player.dexterity_exp_mult * skillMult);
|
||||
Player.gainAgilityExp(unweightedGain * action.weights.agi * Player.agility_exp_mult * skillMult);
|
||||
Player.gainCharismaExp(unweightedGain * action.weights.cha * Player.charisma_exp_mult * skillMult);
|
||||
Player.gainIntelligenceExp(unweightedIntGain * action.weights.int * skillMult);
|
||||
let intExp = unweightedIntGain * action.weights.int * skillMult;
|
||||
if (intExp > 1) {
|
||||
intExp = Math.pow(intExp, 0.8);
|
||||
}
|
||||
Player.gainIntelligenceExp(intExp);
|
||||
}
|
||||
|
||||
Bladeburner.prototype.randomEvent = function() {
|
||||
@@ -1211,10 +1224,7 @@ Bladeburner.prototype.initializeDomElementRefs = function() {
|
||||
overviewChaos: null,
|
||||
overviewSkillPoints: null,
|
||||
overviewBonusTime: null,
|
||||
overviewAugSuccessMult: null,
|
||||
overviewAugMaxStaminaMult: null,
|
||||
overviewAugStaminaGainMult: null,
|
||||
overviewAugAnalysisMult: null,
|
||||
overviewAugMults: null,
|
||||
|
||||
// Actions and Skills Content
|
||||
actionsAndSkillsDesc: null,
|
||||
@@ -1256,7 +1266,7 @@ Bladeburner.prototype.createContent = function() {
|
||||
// Console
|
||||
DomElems.consoleDiv = createElement("div", {
|
||||
class:"bladeburner-console-div",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
if (DomElems.consoleInput instanceof Element) {
|
||||
DomElems.consoleInput.focus();
|
||||
}
|
||||
@@ -1264,12 +1274,12 @@ Bladeburner.prototype.createContent = function() {
|
||||
}
|
||||
});
|
||||
DomElems.consoleTable = createElement("table", {class:"bladeburner-console-table"});
|
||||
DomElems.consoleInputRow = createElement("tr", {class:"bladeburner-console-input-row", id:"bladeubrner-console-input-row"});
|
||||
DomElems.consoleInputRow = createElement("tr", {class:"bladeburner-console-input-row", id:"bladeburner-console-input-row"});
|
||||
DomElems.consoleInputCell = createElement("td", {class:"bladeburner-console-input-cell"});
|
||||
DomElems.consoleInputHeader = createElement("pre", {innerText:"> "});
|
||||
DomElems.consoleInput = createElement("input", {
|
||||
type:"text", class:"bladeburner-console-input", tabIndex:1,
|
||||
onfocus:()=>{DomElems.consoleInput.value = DomElems.consoleInput.value}
|
||||
onfocus:() => {DomElems.consoleInput.value = DomElems.consoleInput.value}
|
||||
});
|
||||
|
||||
DomElems.consoleInputCell.appendChild(DomElems.consoleInputHeader);
|
||||
@@ -1330,7 +1340,7 @@ Bladeburner.prototype.createOverviewContent = function() {
|
||||
DomElems.overviewStaminaHelpTip = createElement("div", {
|
||||
class:"help-tip",
|
||||
innerText:"?",
|
||||
clickListener: ()=> {
|
||||
clickListener: () => {
|
||||
dialogBoxCreate("Performing actions will use up your stamina.<br><br>" +
|
||||
"Your max stamina is determined primarily by your agility stat.<br><br>" +
|
||||
"Your stamina gain rate is determined by both your agility and your " +
|
||||
@@ -1358,7 +1368,7 @@ Bladeburner.prototype.createOverviewContent = function() {
|
||||
|
||||
DomElems.overviewEstPopHelpTip = createElement("div", {
|
||||
innerText:"?", class:"help-tip",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
dialogBoxCreate("The success rate of your contracts/operations depends on " +
|
||||
"the population of Synthoids in your current city. " +
|
||||
"The success rate that is shown to you is only an estimate, " +
|
||||
@@ -1397,10 +1407,7 @@ Bladeburner.prototype.createOverviewContent = function() {
|
||||
DomElems.overviewSkillPoints = createElement("p", {display:"block"});
|
||||
|
||||
|
||||
DomElems.overviewAugSuccessMult = createElement("p", {display:"block"});
|
||||
DomElems.overviewAugMaxStaminaMult = createElement("p", {display:"block"});
|
||||
DomElems.overviewAugStaminaGainMult = createElement("p", {display:"block"});
|
||||
DomElems.overviewAugAnalysisMult = createElement("p", {display:"block"});
|
||||
DomElems.overviewAugMults = createElement("div", {display:"block"});
|
||||
|
||||
|
||||
DomElems.overviewDiv.appendChild(DomElems.overviewRank);
|
||||
@@ -1418,21 +1425,18 @@ Bladeburner.prototype.createOverviewContent = function() {
|
||||
DomElems.overviewDiv.appendChild(DomElems.overviewBonusTime);
|
||||
DomElems.overviewDiv.appendChild(DomElems.overviewSkillPoints);
|
||||
appendLineBreaks(DomElems.overviewDiv, 1);
|
||||
DomElems.overviewDiv.appendChild(DomElems.overviewAugSuccessMult);
|
||||
DomElems.overviewDiv.appendChild(DomElems.overviewAugMaxStaminaMult);
|
||||
DomElems.overviewDiv.appendChild(DomElems.overviewAugStaminaGainMult);
|
||||
DomElems.overviewDiv.appendChild(DomElems.overviewAugAnalysisMult);
|
||||
DomElems.overviewDiv.appendChild(DomElems.overviewAugMults);
|
||||
|
||||
// Travel to new city button
|
||||
appendLineBreaks(DomElems.overviewDiv, 1);
|
||||
DomElems.overviewDiv.appendChild(createElement("a", {
|
||||
innerHTML:"Travel", class:"a-link-button", display:"inline-block",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
var popupId = "bladeburner-travel-popup-cancel-btn";
|
||||
var popupArguments = [];
|
||||
popupArguments.push(createElement("a", { // Cancel Button
|
||||
innerText:"Cancel", class:"a-link-button",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
removeElementById(popupId); return false;
|
||||
}
|
||||
}))
|
||||
@@ -1451,7 +1455,7 @@ Bladeburner.prototype.createOverviewContent = function() {
|
||||
*/
|
||||
class:"cmpy-mgmt-find-employee-option",
|
||||
innerText:BladeburnerConstants.CityNames[i],
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
inst.city = BladeburnerConstants.CityNames[i];
|
||||
removeElementById(popupId);
|
||||
inst.updateOverviewContent();
|
||||
@@ -1474,7 +1478,7 @@ Bladeburner.prototype.createOverviewContent = function() {
|
||||
DomElems.overviewDiv.appendChild(createElement("a", {
|
||||
innerText:"Faction", class:"a-link-button", display:"inline-block",
|
||||
tooltip:"Apply to the Bladeburner Faction, or go to the faction page if you are already a member",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
if (bladeburnerFac.isMember) {
|
||||
Engine.loadFactionContent();
|
||||
displayFactionContent(bladeburnersFactionName);
|
||||
@@ -1518,7 +1522,7 @@ Bladeburner.prototype.createActionAndSkillsContent = function() {
|
||||
DomElems.actionAndSkillsDiv.appendChild(createElement("a", {
|
||||
innerText:buttons[i],
|
||||
class:currTab === buttons[i].toLowerCase() ? "bladeburner-nav-button-inactive" : "bladeburner-nav-button",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
DomElems.currentTab = buttons[i].toLowerCase();
|
||||
inst.createActionAndSkillsContent();
|
||||
return false;
|
||||
@@ -1770,23 +1774,26 @@ Bladeburner.prototype.updateOverviewContent = function() {
|
||||
if (!routing.isOn(Page.Bladeburner)) {return;}
|
||||
DomElems.overviewRank.childNodes[0].nodeValue = "Rank: " + formatNumber(this.rank, 2);
|
||||
DomElems.overviewStamina.innerText = "Stamina: " + formatNumber(this.stamina, 3) + " / " + formatNumber(this.maxStamina, 3);
|
||||
DomElems.overviewGen1.innerHTML =
|
||||
"Stamina Penalty: " + formatNumber((1-this.calculateStaminaPenalty())*100, 1) + "%<br><br>" +
|
||||
"Team Size: " + formatNumber(this.teamSize, 0) + "<br>" +
|
||||
"Team Members Lost: " + formatNumber(this.teamLost, 0) + "<br><br>" +
|
||||
"Num Times Hospitalized: " + this.numHosp + "<br>" +
|
||||
"Money Lost From Hospitalizations: " + numeralWrapper.format(this.moneyLost, "$0.000a") + "<br><br>" +
|
||||
"Current City: " + this.city + "<br>";
|
||||
ReactDOM.render(<>
|
||||
Stamina Penalty: {formatNumber((1-this.calculateStaminaPenalty())*100, 1)}%<br /><br />
|
||||
Team Size: {formatNumber(this.teamSize, 0)}<br />
|
||||
Team Members Lost: {formatNumber(this.teamLost, 0)}<br /><br />
|
||||
Num Times Hospitalized: {this.numHosp}<br />
|
||||
Money Lost From Hospitalizations: {Money(this.moneyLost)}<br /><br />
|
||||
Current City: {this.city}<br />
|
||||
</>, DomElems.overviewGen1);
|
||||
|
||||
DomElems.overviewEstPop.childNodes[0].nodeValue = "Est. Synthoid Population: " + numeralWrapper.format(this.getCurrentCity().popEst, "0.000a");
|
||||
DomElems.overviewEstPop.childNodes[0].nodeValue = "Est. Synthoid Population: " + numeralWrapper.formatPopulation(this.getCurrentCity().popEst);
|
||||
DomElems.overviewEstComms.childNodes[0].nodeValue = "Est. Synthoid Communities: " + formatNumber(this.getCurrentCity().comms, 0);
|
||||
DomElems.overviewChaos.childNodes[0].nodeValue = "City Chaos: " + formatNumber(this.getCurrentCity().chaos);
|
||||
DomElems.overviewSkillPoints.innerText = "Skill Points: " + formatNumber(this.skillPoints, 0);
|
||||
DomElems.overviewBonusTime.childNodes[0].nodeValue = "Bonus time: " + convertTimeMsToTimeElapsedString(this.storedCycles/BladeburnerConstants.CyclesPerSecond*1000);
|
||||
DomElems.overviewAugSuccessMult.innerText = "Aug. Success Chance Mult: " + formatNumber(Player.bladeburner_success_chance_mult*100, 1) + "%";
|
||||
DomElems.overviewAugMaxStaminaMult.innerText = "Aug. Max Stamina Mult: " + formatNumber(Player.bladeburner_max_stamina_mult*100, 1) + "%";
|
||||
DomElems.overviewAugStaminaGainMult.innerText = "Aug. Stamina Gain Mult: " + formatNumber(Player.bladeburner_stamina_gain_mult*100, 1) + "%";
|
||||
DomElems.overviewAugAnalysisMult.innerText = "Aug. Field Analysis Mult: " + formatNumber(Player.bladeburner_analysis_mult*100, 1) + "%";
|
||||
ReactDOM.render(StatsTable([
|
||||
["Aug. Success Chance mult: ", formatNumber(Player.bladeburner_success_chance_mult*100, 1) + "%"],
|
||||
["Aug. Max Stamina mult: ", formatNumber(Player.bladeburner_max_stamina_mult*100, 1) + "%"],
|
||||
["Aug. Stamina Gain mult: ", formatNumber(Player.bladeburner_stamina_gain_mult*100, 1) + "%"],
|
||||
["Aug. Field Analysis mult: ", formatNumber(Player.bladeburner_analysis_mult*100, 1) + "%"],
|
||||
]), DomElems.overviewAugMults);
|
||||
}
|
||||
|
||||
Bladeburner.prototype.updateActionAndSkillsContent = function() {
|
||||
@@ -1902,7 +1909,7 @@ Bladeburner.prototype.updateGeneralActionsUIElement = function(el, action) {
|
||||
el.appendChild(createElement("a", {
|
||||
innerText:"Start", class: "a-link-button",
|
||||
margin:"3px", padding:"3px",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
this.action.type = ActionTypes[action.name];
|
||||
this.action.name = action.name;
|
||||
this.startAction(this.action);
|
||||
@@ -1943,7 +1950,7 @@ Bladeburner.prototype.updateContractsUIElement = function(el, action) {
|
||||
el.appendChild(createElement("a", {
|
||||
innerText:"Start", class: "a-link-button",
|
||||
padding:"3px", margin:"3px",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
this.action.type = ActionTypes.Contract;
|
||||
this.action.name = action.name;
|
||||
this.startAction(this.action);
|
||||
@@ -1967,7 +1974,7 @@ Bladeburner.prototype.updateContractsUIElement = function(el, action) {
|
||||
padding:"2px", margin:"2px",
|
||||
tooltip: isActive ? "WARNING: changing the level will restart the contract" : "",
|
||||
display:"inline",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
++action.level;
|
||||
if (isActive) {this.startAction(this.action);} // Restart Action
|
||||
this.updateContractsUIElement(el, action);
|
||||
@@ -1979,7 +1986,7 @@ Bladeburner.prototype.updateContractsUIElement = function(el, action) {
|
||||
padding:"2px", margin:"2px",
|
||||
tooltip: isActive ? "WARNING: changing the level will restart the contract" : "",
|
||||
display:"inline",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
--action.level;
|
||||
if (isActive) {this.startAction(this.action);} // Restart Action
|
||||
this.updateContractsUIElement(el, action);
|
||||
@@ -1993,8 +2000,7 @@ Bladeburner.prototype.updateContractsUIElement = function(el, action) {
|
||||
display:"inline-block",
|
||||
innerHTML:action.desc + "\n\n" +
|
||||
`Estimated success chance: ${formatNumber(estimatedSuccessChance*100, 1)}% ${action.isStealth?stealthIcon:''}${action.isKill?killIcon:''}\n` +
|
||||
|
||||
"Time Required (s): " + formatNumber(actionTime, 0) + "\n" +
|
||||
"Time Required: " + convertTimeMsToTimeElapsedString(actionTime*1000) + "\n" +
|
||||
"Contracts remaining: " + Math.floor(action.count) + "\n" +
|
||||
"Successes: " + action.successes + "\n" +
|
||||
"Failures: " + action.failures,
|
||||
@@ -2042,7 +2048,7 @@ Bladeburner.prototype.updateOperationsUIElement = function(el, action) {
|
||||
el.appendChild(createElement("a", {
|
||||
innerText:"Start", class: "a-link-button",
|
||||
margin:"3px", padding:"3px",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
this.action.type = ActionTypes.Operation;
|
||||
this.action.name = action.name;
|
||||
this.startAction(this.action);
|
||||
@@ -2053,7 +2059,7 @@ Bladeburner.prototype.updateOperationsUIElement = function(el, action) {
|
||||
el.appendChild(createElement("a", {
|
||||
innerText:"Set Team Size (Curr Size: " + formatNumber(action.teamCount, 0) + ")", class:"a-link-button",
|
||||
margin:"3px", padding:"3px",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
var popupId = "bladeburner-operation-set-team-size-popup";
|
||||
var txt = createElement("p", {
|
||||
innerText:"Enter the amount of team members you would like to take on these " +
|
||||
@@ -2067,10 +2073,10 @@ Bladeburner.prototype.updateOperationsUIElement = function(el, action) {
|
||||
});
|
||||
var setBtn = createElement("a", {
|
||||
innerText:"Confirm", class:"a-link-button",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
var num = Math.round(parseFloat(input.value));
|
||||
if (isNaN(num)) {
|
||||
dialogBoxCreate("Invalid value entered for number of Team Members (must be numeric)")
|
||||
if (isNaN(num) || num < 0) {
|
||||
dialogBoxCreate("Invalid value entered for number of Team Members (must be numeric, positive)")
|
||||
} else {
|
||||
action.teamCount = num;
|
||||
this.updateOperationsUIElement(el, action);
|
||||
@@ -2081,7 +2087,7 @@ Bladeburner.prototype.updateOperationsUIElement = function(el, action) {
|
||||
});
|
||||
var cancelBtn = createElement("a", {
|
||||
innerText:"Cancel", class:"a-link-button",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
removeElementById(popupId);
|
||||
return false;
|
||||
}
|
||||
@@ -2105,7 +2111,7 @@ Bladeburner.prototype.updateOperationsUIElement = function(el, action) {
|
||||
padding:"2px", margin:"2px",
|
||||
tooltip: isActive ? "WARNING: changing the level will restart the Operation" : "",
|
||||
display:"inline",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
++action.level;
|
||||
if (isActive) {this.startAction(this.action);} // Restart Action
|
||||
this.updateOperationsUIElement(el, action);
|
||||
@@ -2117,7 +2123,7 @@ Bladeburner.prototype.updateOperationsUIElement = function(el, action) {
|
||||
padding:"2px", margin:"2px",
|
||||
tooltip: isActive ? "WARNING: changing the level will restart the Operation" : "",
|
||||
display:"inline",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
--action.level;
|
||||
if (isActive) {this.startAction(this.action);} // Restart Action
|
||||
this.updateOperationsUIElement(el, action);
|
||||
@@ -2133,7 +2139,7 @@ Bladeburner.prototype.updateOperationsUIElement = function(el, action) {
|
||||
display:"inline-block",
|
||||
innerHTML:action.desc + "\n\n" +
|
||||
`Estimated success chance: ${formatNumber(estimatedSuccessChance*100, 1)}% ${action.isStealth?stealthIcon:''}${action.isKill?killIcon:''}\n` +
|
||||
"Time Required(s): " + formatNumber(actionTime, 0) + "\n" +
|
||||
"Time Required: " + convertTimeMsToTimeElapsedString(actionTime*1000) + "\n" +
|
||||
"Operations remaining: " + Math.floor(action.count) + "\n" +
|
||||
"Successes: " + action.successes + "\n" +
|
||||
"Failures: " + action.failures,
|
||||
@@ -2194,7 +2200,7 @@ Bladeburner.prototype.updateBlackOpsUIElement = function(el, action) {
|
||||
el.appendChild(createElement("a", { // Start button
|
||||
innerText:"Start", margin:"3px", padding:"3px",
|
||||
class:hasReqdRank ? "a-link-button" : "a-link-button-inactive",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
this.action.type = ActionTypes.BlackOperation;
|
||||
this.action.name = action.name;
|
||||
this.startAction(this.action);
|
||||
@@ -2205,7 +2211,7 @@ Bladeburner.prototype.updateBlackOpsUIElement = function(el, action) {
|
||||
el.appendChild(createElement("a", { // Set Team Size Button
|
||||
innerText:"Set Team Size (Curr Size: " + formatNumber(action.teamCount, 0) + ")", class:"a-link-button",
|
||||
margin:"3px", padding:"3px",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
var popupId = "bladeburner-operation-set-team-size-popup";
|
||||
var txt = createElement("p", {
|
||||
innerText:"Enter the amount of team members you would like to take on this " +
|
||||
@@ -2219,10 +2225,10 @@ Bladeburner.prototype.updateBlackOpsUIElement = function(el, action) {
|
||||
});
|
||||
var setBtn = createElement("a", {
|
||||
innerText:"Confirm", class:"a-link-button",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
var num = Math.round(parseFloat(input.value));
|
||||
if (isNaN(num)) {
|
||||
dialogBoxCreate("Invalid value entered for number of Team Members (must be numeric)")
|
||||
if (isNaN(num) || num < 0) {
|
||||
dialogBoxCreate("Invalid value entered for number of Team Members (must be numeric, positive)")
|
||||
} else {
|
||||
action.teamCount = num;
|
||||
this.updateBlackOpsUIElement(el, action);
|
||||
@@ -2233,7 +2239,7 @@ Bladeburner.prototype.updateBlackOpsUIElement = function(el, action) {
|
||||
});
|
||||
var cancelBtn = createElement("a", {
|
||||
innerText:"Cancel", class:"a-link-button",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
removeElementById(popupId);
|
||||
return false;
|
||||
}
|
||||
@@ -2256,7 +2262,7 @@ Bladeburner.prototype.updateBlackOpsUIElement = function(el, action) {
|
||||
el.appendChild(createElement("p", {
|
||||
display:"inline-block",
|
||||
innerHTML:`Estimated Success Chance: ${formatNumber(estimatedSuccessChance*100, 1)}% ${action.isStealth?stealthIcon:''}${action.isKill?killIcon:''}\n` +
|
||||
"Time Required(s): " + formatNumber(actionTime, 0),
|
||||
"Time Required: " + convertTimeMsToTimeElapsedString(actionTime*1000),
|
||||
}))
|
||||
}
|
||||
|
||||
@@ -2269,9 +2275,15 @@ Bladeburner.prototype.updateSkillsUIElement = function(el, skill) {
|
||||
}
|
||||
var pointCost = skill.calculateCost(currentLevel);
|
||||
|
||||
el.appendChild(createElement("h2", { // Header
|
||||
innerText:skill.name + " (Lvl " + currentLevel + ")", display:"inline-block"
|
||||
}));
|
||||
const nameDiv = createElement("div");
|
||||
ReactDOM.render(React.createElement(CopyableText, {value: skill.name}, null), nameDiv);
|
||||
el.appendChild(nameDiv)
|
||||
|
||||
const h2 = createElement("h2", { // Header
|
||||
display:"inline-block",
|
||||
});
|
||||
h2.appendChild(nameDiv);
|
||||
el.appendChild(h2);
|
||||
|
||||
var canLevel = this.skillPoints >= pointCost;
|
||||
var maxLvl = skill.maxLvl ? currentLevel >= skill.maxLvl : false;
|
||||
@@ -2279,7 +2291,7 @@ Bladeburner.prototype.updateSkillsUIElement = function(el, skill) {
|
||||
innerText:"Level", display:"inline-block",
|
||||
class: canLevel && !maxLvl ? "a-link-button" : "a-link-button-inactive",
|
||||
margin:"3px", padding:"3px",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
if (this.skillPoints < pointCost) {return;}
|
||||
this.skillPoints -= pointCost;
|
||||
this.upgradeSkill(skill);
|
||||
@@ -2288,6 +2300,10 @@ Bladeburner.prototype.updateSkillsUIElement = function(el, skill) {
|
||||
}
|
||||
}));
|
||||
appendLineBreaks(el, 2);
|
||||
el.appendChild(createElement("p", {
|
||||
display:"block",
|
||||
innerText:`Level: ${currentLevel}`,
|
||||
}));
|
||||
if (maxLvl) {
|
||||
el.appendChild(createElement("p", {
|
||||
color:"red", display:"block",
|
||||
@@ -2315,7 +2331,7 @@ Bladeburner.prototype.postToConsole = function(input, saveToLogs=true) {
|
||||
}
|
||||
|
||||
if (input == null || DomElems.consoleDiv == null) {return;}
|
||||
$("#bladeubrner-console-input-row").before('<tr><td class="bladeburner-console-line" style="color: var(--my-font-color); white-space:pre-wrap;">' + input + '</td></tr>');
|
||||
$("#bladeburner-console-input-row").before('<tr><td class="bladeburner-console-line" style="color: var(--my-font-color); white-space:pre-wrap;">' + input + '</td></tr>');
|
||||
|
||||
if (DomElems.consoleTable.childNodes.length > MaxConsoleEntries) {
|
||||
DomElems.consoleTable.removeChild(DomElems.consoleTable.firstChild);
|
||||
@@ -3195,7 +3211,7 @@ Bladeburner.prototype.setTeamSizeNetscriptFn = function(type, name, size, worker
|
||||
}
|
||||
|
||||
const sanitizedSize = Math.round(size);
|
||||
if (isNaN(sanitizedSize)) {
|
||||
if (isNaN(sanitizedSize) || sanitizedSize < 0) {
|
||||
workerScript.log("bladeburner.setTeamSize", `Invalid size: ${size}`);
|
||||
return -1;
|
||||
}
|
||||
@@ -214,6 +214,7 @@ export class Action {
|
||||
competence += (this.weights[stat] * Math.pow(effMultiplier*playerStatLvl, this.decays[stat]));
|
||||
}
|
||||
}
|
||||
competence *= Player.getIntelligenceBonus(0.75);
|
||||
competence *= inst.calculateStaminaPenalty();
|
||||
|
||||
competence *= this.getTeamSuccessBonus(inst);
|
||||
|
||||
@@ -21,7 +21,7 @@ export const BlackOperations: IMap<BlackOperation> = {};
|
||||
BlackOperations["Operation Zero"] = new BlackOperation({
|
||||
name:"Operation Zero",
|
||||
desc:"AeroCorp is one of the world's largest defense contractors. " +
|
||||
"It's leader, Steve Watataki, is thought to be a supporter of " +
|
||||
"Its leader, Steve Watataki, is thought to be a supporter of " +
|
||||
"Synthoid rights. He must be removed.<br><br>" +
|
||||
"The goal of Operation Zero is to covertly infiltrate AeroCorp and " +
|
||||
"uncover any incriminating evidence or " +
|
||||
|
||||
@@ -60,7 +60,7 @@ export const BladeburnerConstants: {
|
||||
ChaosThreshold: 50, // City chaos level after which it starts making tasks harder
|
||||
|
||||
BaseStatGain: 1, // Base stat gain per second
|
||||
BaseIntGain: 0.001, // Base intelligence stat gain
|
||||
BaseIntGain: 0.003, // Base intelligence stat gain
|
||||
|
||||
ActionCountGrowthPeriod: 480, // Time (s) it takes for action count to grow by its specified value
|
||||
|
||||
|
||||
424
src/Casino/Blackjack.tsx
Normal file
424
src/Casino/Blackjack.tsx
Normal file
@@ -0,0 +1,424 @@
|
||||
import * as React from "react";
|
||||
|
||||
import { IPlayer } from "../PersonObjects/IPlayer";
|
||||
import { Money } from "../ui/React/Money";
|
||||
import { Game } from "./Game";
|
||||
import { Deck } from "./CardDeck/Deck";
|
||||
import { Hand } from "./CardDeck/Hand";
|
||||
import { InputAdornment } from "@material-ui/core";
|
||||
import { ReactCard } from "./CardDeck/ReactCard";
|
||||
import { MuiTextField } from "../ui/React/MuiTextField";
|
||||
import { MuiButton } from "../ui/React/MuiButton";
|
||||
import { MuiPaper } from "../ui/React/MuiPaper";
|
||||
|
||||
const MAX_BET = 100e6;
|
||||
|
||||
enum Result {
|
||||
Pending = "",
|
||||
PlayerWon = "You won!",
|
||||
PlayerWonByBlackjack = "You Won! Blackjack!",
|
||||
DealerWon = "You lost!",
|
||||
Tie = "Push! (Tie)",
|
||||
}
|
||||
|
||||
type Props = {
|
||||
p: IPlayer;
|
||||
}
|
||||
|
||||
type State ={
|
||||
playerHand: Hand;
|
||||
dealerHand: Hand;
|
||||
bet: number;
|
||||
betInput: string;
|
||||
gameInProgress: boolean;
|
||||
result: Result;
|
||||
gains: number; // Track gains only for this session
|
||||
wagerInvalid: boolean;
|
||||
wagerInvalidHelperText: string;
|
||||
}
|
||||
|
||||
export class Blackjack extends Game<Props, State> {
|
||||
|
||||
deck: Deck;
|
||||
|
||||
constructor(props: Props) {
|
||||
super(props);
|
||||
|
||||
this.deck = new Deck(5); // 5-deck multideck
|
||||
|
||||
const initialBet = 1e6;
|
||||
|
||||
this.state = {
|
||||
playerHand: new Hand([]),
|
||||
dealerHand: new Hand([]),
|
||||
bet: initialBet,
|
||||
betInput: String(initialBet),
|
||||
gameInProgress: false,
|
||||
result: Result.Pending,
|
||||
gains: 0,
|
||||
wagerInvalid: false,
|
||||
wagerInvalidHelperText: "",
|
||||
}
|
||||
}
|
||||
|
||||
canStartGame = (): boolean => {
|
||||
const { p } = this.props;
|
||||
const { bet } = this.state;
|
||||
|
||||
return p.canAfford(bet);
|
||||
}
|
||||
|
||||
startGame = (): void => {
|
||||
if (!this.canStartGame()) { return; }
|
||||
|
||||
// Take money from player right away so that player's dont just "leave" to avoid the loss (I mean they could
|
||||
// always reload without saving but w.e)
|
||||
this.props.p.loseMoney(this.state.bet);
|
||||
|
||||
const playerHand = new Hand([ this.deck.safeDrawCard(), this.deck.safeDrawCard() ]);
|
||||
const dealerHand = new Hand([ this.deck.safeDrawCard(), this.deck.safeDrawCard() ]);
|
||||
|
||||
this.setState({
|
||||
playerHand,
|
||||
dealerHand,
|
||||
gameInProgress: true,
|
||||
result: Result.Pending,
|
||||
});
|
||||
|
||||
// If the player is dealt a blackjack and the dealer is not, then the player
|
||||
// immediately wins
|
||||
if (this.getTrueHandValue(playerHand) === 21) {
|
||||
if (this.getTrueHandValue(dealerHand) === 21) {
|
||||
this.finishGame(Result.Tie);
|
||||
} else {
|
||||
this.finishGame(Result.PlayerWonByBlackjack);
|
||||
}
|
||||
} else if (this.getTrueHandValue(dealerHand) === 21) {
|
||||
// Check if dealer won by blackjack. We know at this point that the player does not also have blackjack.
|
||||
this.finishGame(Result.DealerWon);
|
||||
}
|
||||
}
|
||||
|
||||
// Returns an array of numbers representing all possible values of the given Hand. The reason it needs to be
|
||||
// an array is because an Ace can count as both 1 and 11.
|
||||
getHandValue = (hand: Hand): number[] => {
|
||||
let result: number[] = [ 0 ];
|
||||
|
||||
for (let i = 0 ; i < hand.cards.length; ++i) {
|
||||
const value = hand.cards[i].value;
|
||||
if (value >= 10) {
|
||||
result = result.map((x) => x + 10);
|
||||
} else if (value === 1) {
|
||||
result = result.flatMap((x) => [ x + 1, x + 11 ]);
|
||||
} else {
|
||||
result = result.map((x) => x + value);
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
// Returns the single hand value used for determine things like victory and whether or not
|
||||
// the dealer has to hit. Essentially this uses the biggest value that's 21 or under. If no such value exists,
|
||||
// then it means the hand is busted and we can just return whatever
|
||||
getTrueHandValue = (hand: Hand): number => {
|
||||
const handValues = this.getHandValue(hand);
|
||||
const valuesUnder21 = handValues.filter((x) => (x <= 21));
|
||||
|
||||
if (valuesUnder21.length > 0) {
|
||||
valuesUnder21.sort((a, b) => a - b);
|
||||
return valuesUnder21[valuesUnder21.length - 1];
|
||||
} else {
|
||||
// Just return the first value. It doesnt really matter anyways since hand is buted
|
||||
return handValues[0];
|
||||
}
|
||||
}
|
||||
|
||||
// Returns all hand values that are 21 or under. If no values are 21 or under, then the first value is returned.
|
||||
getHandDisplayValues = (hand: Hand): number[] => {
|
||||
const handValues = this.getHandValue(hand);
|
||||
if (this.isHandBusted(hand)) {
|
||||
// Hand is busted so just return the 1st value, doesn't really matter
|
||||
return [ ...new Set([ handValues[0] ]) ];
|
||||
} else {
|
||||
return [ ...new Set(handValues.filter((x) => x <= 21)) ];
|
||||
}
|
||||
}
|
||||
|
||||
isHandBusted = (hand: Hand): boolean => {
|
||||
return this.getTrueHandValue(hand) > 21;
|
||||
}
|
||||
|
||||
playerHit = (event: React.MouseEvent): void => {
|
||||
if (!event.isTrusted) { return; }
|
||||
|
||||
const newHand = this.state.playerHand.addCards(this.deck.safeDrawCard());
|
||||
|
||||
this.setState({
|
||||
playerHand: newHand,
|
||||
});
|
||||
|
||||
// Check if player busted, and finish the game if so
|
||||
if (this.isHandBusted(newHand)) {
|
||||
this.finishGame(Result.DealerWon);
|
||||
}
|
||||
}
|
||||
|
||||
playerStay = (event: React.MouseEvent): void => {
|
||||
if (!event.isTrusted) { return; }
|
||||
|
||||
// Determine if Dealer needs to hit. A dealer must hit if they have 16 or lower.
|
||||
// If the dealer has a Soft 17 (Ace + 6), then they stay.
|
||||
let newDealerHand = this.state.dealerHand;
|
||||
while (true) {
|
||||
// The dealer's "true" hand value is the 2nd one if its 21 or less (the 2nd value is always guaranteed
|
||||
// to be equal or larger). Otherwise its the 1st.
|
||||
const dealerHandValue = this.getTrueHandValue(newDealerHand);
|
||||
|
||||
if (dealerHandValue <= 16) {
|
||||
newDealerHand = newDealerHand.addCards(this.deck.safeDrawCard());
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
this.setState({
|
||||
dealerHand: newDealerHand,
|
||||
})
|
||||
|
||||
// If dealer has busted, then player wins
|
||||
if (this.isHandBusted(newDealerHand)) {
|
||||
this.finishGame(Result.PlayerWon);
|
||||
} else {
|
||||
const dealerHandValue = this.getTrueHandValue(newDealerHand);
|
||||
const playerHandValue = this.getTrueHandValue(this.state.playerHand);
|
||||
|
||||
console.log(`dealerHandValue: ${dealerHandValue}`);
|
||||
console.log(`playerHandValue: ${playerHandValue}`);
|
||||
|
||||
// We expect nobody to have busted. If someone busted, there is an error
|
||||
// in our game logic
|
||||
if (dealerHandValue > 21 || playerHandValue > 21) {
|
||||
throw new Error("Someone busted when not expected to");
|
||||
}
|
||||
|
||||
if (playerHandValue > dealerHandValue) {
|
||||
this.finishGame(Result.PlayerWon);
|
||||
} else if (playerHandValue < dealerHandValue) {
|
||||
this.finishGame(Result.DealerWon);
|
||||
} else {
|
||||
this.finishGame(Result.Tie);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
finishGame = (result: Result): void => {
|
||||
let gains = 0;
|
||||
if (this.isPlayerWinResult(result)) {
|
||||
gains = this.state.bet;
|
||||
|
||||
// We 2x the gains because we took away money at the start, so we need to give the original bet back.
|
||||
this.win(this.props.p, 2 * gains);
|
||||
} else if (result === Result.DealerWon) {
|
||||
gains = -1 * this.state.bet;
|
||||
// Dont need to take money here since we already did it at the start
|
||||
} else if (result === Result.Tie) {
|
||||
this.win(this.props.p, this.state.bet); // Get the original bet back
|
||||
}
|
||||
|
||||
this.setState({
|
||||
gameInProgress: false,
|
||||
result,
|
||||
gains: this.state.gains + gains,
|
||||
});
|
||||
}
|
||||
|
||||
isPlayerWinResult = (result: Result): boolean => {
|
||||
return (result === Result.PlayerWon || result === Result.PlayerWonByBlackjack);
|
||||
}
|
||||
|
||||
wagerOnChange = (event: React.ChangeEvent<HTMLInputElement>): void => {
|
||||
const { p } = this.props;
|
||||
const betInput = event.target.value;
|
||||
const wager = Math.round(parseFloat(betInput));
|
||||
if (isNaN(wager)) {
|
||||
this.setState({
|
||||
bet: 0,
|
||||
betInput,
|
||||
wagerInvalid: true,
|
||||
wagerInvalidHelperText: "Not a valid number",
|
||||
});
|
||||
} else if (wager <= 0) {
|
||||
this.setState({
|
||||
bet: 0,
|
||||
betInput,
|
||||
wagerInvalid: true,
|
||||
wagerInvalidHelperText: "Must bet a postive amount",
|
||||
});
|
||||
} else if (wager > MAX_BET) {
|
||||
this.setState({
|
||||
bet: 0,
|
||||
betInput,
|
||||
wagerInvalid: true,
|
||||
wagerInvalidHelperText: "Exceeds max bet",
|
||||
});
|
||||
} else if (!p.canAfford(wager)) {
|
||||
this.setState({
|
||||
bet: 0,
|
||||
betInput,
|
||||
wagerInvalid: true,
|
||||
wagerInvalidHelperText: "Not enough money",
|
||||
});
|
||||
} else {
|
||||
// Valid wager
|
||||
this.setState({
|
||||
bet: wager,
|
||||
betInput,
|
||||
wagerInvalid: false,
|
||||
wagerInvalidHelperText: "",
|
||||
result: Result.Pending, // Reset previous game status to clear the win/lose text UI
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
// Start game button
|
||||
startOnClick = (event: React.MouseEvent): void => {
|
||||
// Protect against scripting...although maybe this would be fun to automate
|
||||
if (!event.isTrusted) { return; }
|
||||
|
||||
if (!this.state.wagerInvalid) {
|
||||
this.startGame();
|
||||
}
|
||||
}
|
||||
|
||||
render(): React.ReactNode {
|
||||
const {
|
||||
betInput,
|
||||
playerHand,
|
||||
dealerHand,
|
||||
gameInProgress,
|
||||
result,
|
||||
wagerInvalid,
|
||||
wagerInvalidHelperText,
|
||||
gains,
|
||||
} = this.state;
|
||||
|
||||
// Get the player totals to display.
|
||||
const playerHandValues = this.getHandDisplayValues(playerHand);
|
||||
const dealerHandValues = this.getHandDisplayValues(dealerHand);
|
||||
|
||||
return (
|
||||
<div>
|
||||
{/* Wager input */}
|
||||
<div>
|
||||
<MuiTextField
|
||||
value={betInput}
|
||||
label={
|
||||
<>
|
||||
{"Wager (Max: "}
|
||||
{Money(MAX_BET)}
|
||||
{")"}
|
||||
</>
|
||||
}
|
||||
disabled={gameInProgress}
|
||||
onChange={this.wagerOnChange}
|
||||
error={wagerInvalid}
|
||||
helperText={wagerInvalid ? wagerInvalidHelperText : ""}
|
||||
type="number"
|
||||
variant="filled"
|
||||
style={{
|
||||
width: "200px",
|
||||
}}
|
||||
InputProps={{
|
||||
startAdornment: <InputAdornment position="start" >$</InputAdornment>,
|
||||
}} />
|
||||
|
||||
<p>
|
||||
{"Total earnings this session: "}
|
||||
{Money(gains)}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
|
||||
{/* Buttons */}
|
||||
{!gameInProgress ? (
|
||||
<div>
|
||||
<MuiButton
|
||||
color="primary"
|
||||
onClick={this.startOnClick}
|
||||
disabled={wagerInvalid || !this.canStartGame()}>
|
||||
|
||||
Start
|
||||
</MuiButton>
|
||||
</div>
|
||||
) : (
|
||||
<div>
|
||||
<MuiButton color="primary" onClick={this.playerHit} >
|
||||
Hit
|
||||
</MuiButton>
|
||||
<MuiButton color="secondary" onClick={this.playerStay} >
|
||||
Stay
|
||||
</MuiButton>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Main game part. Displays both if the game is in progress OR if there's a result so you can see
|
||||
* the cards that led to that result. */}
|
||||
{(gameInProgress || result !== Result.Pending) && (
|
||||
<div>
|
||||
<MuiPaper variant="outlined" elevation={2}>
|
||||
<pre>Player</pre>
|
||||
{playerHand.cards.map((card, i) => (
|
||||
<ReactCard card={card} key={i} />
|
||||
))}
|
||||
|
||||
<pre>Value(s): </pre>
|
||||
{playerHandValues.map((value, i) => (
|
||||
<pre key={i}>{value}</pre>
|
||||
))}
|
||||
</MuiPaper>
|
||||
|
||||
<br />
|
||||
|
||||
<MuiPaper variant="outlined" elevation={2}>
|
||||
<pre>Dealer</pre>
|
||||
{dealerHand.cards.map((card, i) => (
|
||||
// Hide every card except the first while game is in progress
|
||||
<ReactCard card={card} hidden={gameInProgress && i !== 0} key={i} />
|
||||
))}
|
||||
|
||||
{!gameInProgress && (
|
||||
<>
|
||||
<pre>Value(s): </pre>
|
||||
{dealerHandValues.map((value, i) => (
|
||||
<pre key={i}>{value}</pre>
|
||||
))}
|
||||
</>
|
||||
)}
|
||||
</MuiPaper>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Results from previous round */}
|
||||
{result !== Result.Pending && (
|
||||
<p>
|
||||
{result}
|
||||
{this.isPlayerWinResult(result) && (
|
||||
<>
|
||||
{" You gained "}
|
||||
{Money(this.state.bet)}
|
||||
</>
|
||||
)}
|
||||
{result === Result.DealerWon && (
|
||||
<>
|
||||
{" You lost "}
|
||||
{Money(this.state.bet)}
|
||||
</>
|
||||
)}
|
||||
</p>
|
||||
)}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
42
src/Casino/CardDeck/Card.ts
Normal file
42
src/Casino/CardDeck/Card.ts
Normal file
@@ -0,0 +1,42 @@
|
||||
// Enum values are lowercased to match css classes
|
||||
export enum Suit {
|
||||
Clubs = "clubs",
|
||||
Diamonds = "diamonds",
|
||||
Hearts = "hearts",
|
||||
Spades = "spades",
|
||||
}
|
||||
|
||||
export class Card {
|
||||
|
||||
constructor(readonly value: number, readonly suit: Suit) {
|
||||
if (value < 1 || value > 13) {
|
||||
throw new Error(`Card instantiated with improper value: ${value}`);
|
||||
}
|
||||
}
|
||||
|
||||
formatValue(): string {
|
||||
switch (this.value) {
|
||||
case 1:
|
||||
return "A";
|
||||
case 11:
|
||||
return "J";
|
||||
case 12:
|
||||
return "Q";
|
||||
case 13:
|
||||
return "K";
|
||||
default:
|
||||
return `${this.value}`;
|
||||
}
|
||||
}
|
||||
|
||||
isRedSuit(): boolean {
|
||||
return this.suit === Suit.Hearts || this.suit === Suit.Diamonds;
|
||||
}
|
||||
|
||||
getStringRepresentation(): string {
|
||||
const value = this.formatValue();
|
||||
|
||||
return `${value} of ${this.suit}`;
|
||||
}
|
||||
|
||||
}
|
||||
58
src/Casino/CardDeck/Deck.ts
Normal file
58
src/Casino/CardDeck/Deck.ts
Normal file
@@ -0,0 +1,58 @@
|
||||
import { Card, Suit } from "./Card";
|
||||
import { shuffle } from "lodash";
|
||||
|
||||
export class Deck {
|
||||
|
||||
private cards: Card[] = [];
|
||||
|
||||
// Support multiple decks
|
||||
constructor(private numDecks = 1) {
|
||||
this.reset();
|
||||
}
|
||||
|
||||
shuffle(): void {
|
||||
this.cards = shuffle(this.cards); // Just use lodash
|
||||
}
|
||||
|
||||
drawCard(): Card {
|
||||
if (this.cards.length == 0) {
|
||||
throw new Error("Tried to draw card from empty deck");
|
||||
}
|
||||
|
||||
return this.cards.shift() as Card; // Guaranteed to return a Card since we throw an Error if array is empty
|
||||
}
|
||||
|
||||
// Draws a card, resetting the deck beforehands if the Deck is empty
|
||||
safeDrawCard(): Card {
|
||||
if (this.cards.length === 0) {
|
||||
this.reset();
|
||||
}
|
||||
|
||||
return this.drawCard();
|
||||
}
|
||||
|
||||
// Reset the deck back to the original 52 cards and shuffle it
|
||||
reset(): void {
|
||||
this.cards = [];
|
||||
|
||||
for (let i = 1; i <= 13; ++i) {
|
||||
for (let j = 0; j < this.numDecks; ++j) {
|
||||
this.cards.push(new Card(i, Suit.Clubs));
|
||||
this.cards.push(new Card(i, Suit.Diamonds));
|
||||
this.cards.push(new Card(i, Suit.Hearts));
|
||||
this.cards.push(new Card(i, Suit.Spades));
|
||||
}
|
||||
}
|
||||
|
||||
this.shuffle();
|
||||
}
|
||||
|
||||
size(): number {
|
||||
return this.cards.length;
|
||||
}
|
||||
|
||||
isEmpty(): boolean {
|
||||
return this.cards.length === 0;
|
||||
}
|
||||
|
||||
}
|
||||
25
src/Casino/CardDeck/Hand.ts
Normal file
25
src/Casino/CardDeck/Hand.ts
Normal file
@@ -0,0 +1,25 @@
|
||||
/**
|
||||
* Represents a Hand of cards.
|
||||
*
|
||||
* This class is IMMUTABLE
|
||||
*/
|
||||
|
||||
import { Card } from "./Card";
|
||||
|
||||
export class Hand {
|
||||
|
||||
constructor(readonly cards: readonly Card[]) {}
|
||||
|
||||
addCards(...cards: Card[]): Hand {
|
||||
return new Hand([ ...this.cards, ...cards ]);
|
||||
}
|
||||
|
||||
removeByIndex(i: number): Hand {
|
||||
if (i >= this.cards.length) {
|
||||
throw new Error(`Tried to remove invalid card from Hand by index: ${i}`);
|
||||
}
|
||||
|
||||
return new Hand([ ...this.cards.slice().splice(i, 1) ])
|
||||
}
|
||||
|
||||
}
|
||||
40
src/Casino/CardDeck/ReactCard.tsx
Normal file
40
src/Casino/CardDeck/ReactCard.tsx
Normal file
@@ -0,0 +1,40 @@
|
||||
import React, { FC } from "react";
|
||||
import { Card, Suit } from "./Card";
|
||||
|
||||
type Props = {
|
||||
card: Card;
|
||||
hidden?: boolean;
|
||||
}
|
||||
|
||||
export const ReactCard: FC<Props> = ({ card, hidden }) => {
|
||||
let suit : React.ReactNode;
|
||||
switch (card.suit) {
|
||||
case Suit.Clubs:
|
||||
suit = <span>♣</span>;
|
||||
break;
|
||||
case Suit.Diamonds:
|
||||
suit = <span>♦</span>;
|
||||
break;
|
||||
case Suit.Hearts:
|
||||
suit = <span>♥</span>;
|
||||
break;
|
||||
case Suit.Spades:
|
||||
suit = <span>♠</span>;
|
||||
break;
|
||||
default:
|
||||
throw new Error(`MissingCaseException: ${card.suit}`);
|
||||
|
||||
}
|
||||
return (
|
||||
<div className={`casino-card ${card.isRedSuit() ? "red" : "black"}`}>
|
||||
<>
|
||||
<div className="value">
|
||||
{hidden ? " - " : card.formatValue()}
|
||||
</div>
|
||||
<div className={`suit`}>
|
||||
{hidden ? " - " : suit}
|
||||
</div>
|
||||
</>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
98
src/Casino/CoinFlip.tsx
Normal file
98
src/Casino/CoinFlip.tsx
Normal file
@@ -0,0 +1,98 @@
|
||||
/**
|
||||
* React Subcomponent for displaying a location's UI, when that location is a gym
|
||||
*
|
||||
* This subcomponent renders all of the buttons for training at the gym
|
||||
*/
|
||||
import * as React from "react";
|
||||
|
||||
import { IPlayer } from "../PersonObjects/IPlayer";
|
||||
import { StdButton } from "../ui/React/StdButton";
|
||||
import { BadRNG } from "./RNG";
|
||||
import { Game } from "./Game";
|
||||
import { trusted } from "./utils";
|
||||
|
||||
type IProps = {
|
||||
p: IPlayer;
|
||||
}
|
||||
|
||||
type IState = {
|
||||
investment: number;
|
||||
result: any;
|
||||
status: string;
|
||||
playLock: boolean;
|
||||
}
|
||||
|
||||
const minPlay = 0;
|
||||
const maxPlay = 10e3;
|
||||
|
||||
export class CoinFlip extends Game<IProps, IState> {
|
||||
|
||||
constructor(props: IProps) {
|
||||
super(props);
|
||||
|
||||
this.state = {
|
||||
investment: 1000,
|
||||
result: <span> </span>,
|
||||
status: '',
|
||||
playLock: false,
|
||||
};
|
||||
|
||||
this.play = this.play.bind(this);
|
||||
this.updateInvestment = this.updateInvestment.bind(this);
|
||||
}
|
||||
|
||||
updateInvestment(e: React.FormEvent<HTMLInputElement>) {
|
||||
let investment: number = parseInt(e.currentTarget.value);
|
||||
if (isNaN(investment)) {
|
||||
investment = minPlay;
|
||||
}
|
||||
if (investment > maxPlay) {
|
||||
investment = maxPlay;
|
||||
}
|
||||
if (investment < minPlay) {
|
||||
investment = minPlay;
|
||||
}
|
||||
this.setState({investment: investment});
|
||||
}
|
||||
|
||||
play(guess: string) {
|
||||
if(this.reachedLimit(this.props.p)) return;
|
||||
const v = BadRNG.random();
|
||||
let letter: string;
|
||||
if (v < 0.5) {
|
||||
letter = 'H';
|
||||
} else {
|
||||
letter = 'T';
|
||||
}
|
||||
const correct: boolean = guess===letter;
|
||||
this.setState({
|
||||
result: <span className={correct ? "text" : "failure"}>{letter}</span>,
|
||||
status: correct ? " win!" : "lose!",
|
||||
playLock: true,
|
||||
});
|
||||
setTimeout(()=>this.setState({playLock: false}), 250);
|
||||
if (correct) {
|
||||
this.win(this.props.p, this.state.investment);
|
||||
} else {
|
||||
this.win(this.props.p, -this.state.investment);
|
||||
}
|
||||
if(this.reachedLimit(this.props.p)) return;
|
||||
}
|
||||
|
||||
|
||||
render() {
|
||||
return <>
|
||||
<pre>
|
||||
+———————+<br />
|
||||
| | | |<br />
|
||||
| | {this.state.result} | |<br />
|
||||
| | | |<br />
|
||||
+———————+<br />
|
||||
</pre>
|
||||
<span className="text">Play for: </span><input type="number" className='text-input' onChange={this.updateInvestment} value={this.state.investment} /><br />
|
||||
<StdButton onClick={trusted(() => this.play('H'))} text={"Head!"} disabled={this.state.playLock} />
|
||||
<StdButton onClick={trusted(() => this.play('T'))} text={"Tail!"} disabled={this.state.playLock} />
|
||||
<h1>{this.state.status}</h1>
|
||||
</>
|
||||
}
|
||||
}
|
||||
20
src/Casino/Game.tsx
Normal file
20
src/Casino/Game.tsx
Normal file
@@ -0,0 +1,20 @@
|
||||
import * as React from "react";
|
||||
import { IPlayer } from "../PersonObjects/IPlayer";
|
||||
import { dialogBoxCreate } from "../../utils/DialogBox";
|
||||
|
||||
const gainLimit = 10e9;
|
||||
|
||||
export class Game<T,U> extends React.Component<T, U> {
|
||||
win(p: IPlayer, n: number): void{
|
||||
p.gainMoney(n);
|
||||
p.recordMoneySource(n, "casino");
|
||||
}
|
||||
|
||||
reachedLimit(p: IPlayer): boolean {
|
||||
const reached = p.getCasinoWinnings() > gainLimit;
|
||||
if(reached) {
|
||||
dialogBoxCreate(<>Alright cheater get out of here. You're not allowed here anymore.</>);
|
||||
}
|
||||
return reached;
|
||||
}
|
||||
}
|
||||
64
src/Casino/RNG.ts
Normal file
64
src/Casino/RNG.ts
Normal file
@@ -0,0 +1,64 @@
|
||||
|
||||
export interface RNG {
|
||||
random(): number
|
||||
}
|
||||
|
||||
/*
|
||||
* very bad RNG, meant to be used as introduction to RNG manipulation. It has a
|
||||
* period of 1024.
|
||||
*/
|
||||
class RNG0 implements RNG {
|
||||
x: number;
|
||||
m: number = 1024;
|
||||
a: number = 341;
|
||||
c: number = 1;
|
||||
|
||||
constructor() {
|
||||
this.x = 0;
|
||||
this.reset();
|
||||
}
|
||||
|
||||
step() {
|
||||
this.x = (this.a*this.x+this.c) % this.m;
|
||||
}
|
||||
|
||||
random(): number {
|
||||
this.step();
|
||||
return this.x/this.m;
|
||||
}
|
||||
|
||||
reset() {
|
||||
this.x = (new Date()).getTime() % this.m;
|
||||
}
|
||||
}
|
||||
|
||||
export const BadRNG: RNG0 = new RNG0();
|
||||
|
||||
/*
|
||||
* Wichmann–Hill PRNG
|
||||
* The period is 6e12.
|
||||
*/
|
||||
export class WHRNG implements RNG {
|
||||
s1: number = 0;
|
||||
s2: number = 0;
|
||||
s3: number = 0;
|
||||
|
||||
constructor(totalPlaytime: number) {
|
||||
// This one is seeded by the players total play time.
|
||||
const v: number = (totalPlaytime/1000)%30000;
|
||||
this.s1 = v;
|
||||
this.s2 = v;
|
||||
this.s3 = v;
|
||||
}
|
||||
|
||||
step() {
|
||||
this.s1 = (171 * this.s1) % 30269;
|
||||
this.s2 = (172 * this.s2) % 30307;
|
||||
this.s3 = (170 * this.s3) % 30323;
|
||||
}
|
||||
|
||||
random(): number {
|
||||
this.step();
|
||||
return (this.s1/30269.0 + this.s2/30307.0 + this.s3/30323.0)%1.0;
|
||||
}
|
||||
}
|
||||
295
src/Casino/Roulette.tsx
Normal file
295
src/Casino/Roulette.tsx
Normal file
@@ -0,0 +1,295 @@
|
||||
import * as React from "react";
|
||||
|
||||
import { IPlayer } from "../PersonObjects/IPlayer";
|
||||
import { StdButton } from "../ui/React/StdButton";
|
||||
import { Money } from "../ui/React/Money";
|
||||
import { Game } from "./Game";
|
||||
import { WHRNG } from "./RNG";
|
||||
import { trusted } from "./utils";
|
||||
|
||||
type IProps = {
|
||||
p: IPlayer;
|
||||
}
|
||||
|
||||
type IState = {
|
||||
investment: number;
|
||||
canPlay: boolean;
|
||||
status: string | JSX.Element;
|
||||
n: number;
|
||||
lock: boolean;
|
||||
strategy: Strategy;
|
||||
}
|
||||
|
||||
const minPlay = 0;
|
||||
const maxPlay = 1e7;
|
||||
|
||||
function isRed(n: number): boolean {
|
||||
return [1, 3, 5, 7, 9, 12, 14, 16, 18, 19,
|
||||
21, 23, 25, 27, 30, 32, 34, 36].includes(n);
|
||||
}
|
||||
|
||||
function isBlack(n: number): boolean {
|
||||
return !isRed(n);
|
||||
}
|
||||
|
||||
type Strategy = {
|
||||
match: (n: number) => boolean;
|
||||
payout: number;
|
||||
}
|
||||
|
||||
const redNumbers: number[] = [1, 3, 5, 7, 9, 12, 14, 16, 18, 19,
|
||||
21, 23, 25, 27, 30, 32, 34, 36];
|
||||
|
||||
const strategies: {
|
||||
Red: Strategy;
|
||||
Black: Strategy;
|
||||
Odd: Strategy;
|
||||
Even: Strategy;
|
||||
High: Strategy;
|
||||
Low: Strategy;
|
||||
Third1: Strategy;
|
||||
Third2: Strategy;
|
||||
Third3: Strategy;
|
||||
} = {
|
||||
Red: {
|
||||
match: (n: number): boolean => {
|
||||
if (n === 0) return false;
|
||||
return redNumbers.includes(n);
|
||||
},
|
||||
payout: 1,
|
||||
},
|
||||
Black: {
|
||||
match: (n: number): boolean => {
|
||||
return !redNumbers.includes(n);
|
||||
},
|
||||
payout: 1,
|
||||
},
|
||||
Odd: {
|
||||
match: (n: number): boolean => {
|
||||
if (n === 0) return false;
|
||||
return n%2 === 1;
|
||||
},
|
||||
payout: 1,
|
||||
},
|
||||
Even: {
|
||||
match: (n: number): boolean => {
|
||||
if (n === 0) return false;
|
||||
return n%2 === 0;
|
||||
},
|
||||
payout: 1,
|
||||
},
|
||||
High: {
|
||||
match: (n: number): boolean => {
|
||||
if (n === 0) return false;
|
||||
return n>18
|
||||
},
|
||||
payout: 1,
|
||||
},
|
||||
Low: {
|
||||
match: (n: number): boolean => {
|
||||
if (n === 0) return false;
|
||||
return n<19;
|
||||
},
|
||||
payout: 1,
|
||||
},
|
||||
Third1: {
|
||||
match: (n: number): boolean => {
|
||||
if (n === 0) return false;
|
||||
return n <= 12;
|
||||
},
|
||||
payout: 2,
|
||||
},
|
||||
Third2: {
|
||||
match: (n: number): boolean => {
|
||||
if (n === 0) return false;
|
||||
return 13 <= n && n <= 24;
|
||||
},
|
||||
payout: 2,
|
||||
},
|
||||
Third3: {
|
||||
match: (n: number): boolean => {
|
||||
if (n === 0) return false;
|
||||
return 25 <= n;
|
||||
},
|
||||
payout: 2,
|
||||
},
|
||||
}
|
||||
|
||||
function Single(s: number): Strategy {
|
||||
return {
|
||||
match: (n: number): boolean => {
|
||||
return s === n;
|
||||
},
|
||||
payout: 36,
|
||||
}
|
||||
}
|
||||
|
||||
export class Roulette extends Game<IProps, IState> {
|
||||
interval: number = -1;
|
||||
rng: WHRNG;
|
||||
|
||||
constructor(props: IProps) {
|
||||
super(props);
|
||||
|
||||
this.rng = new WHRNG((new Date()).getTime());
|
||||
this.state = {
|
||||
investment: 1000,
|
||||
canPlay: true,
|
||||
status: 'waiting',
|
||||
n: 0,
|
||||
lock: true,
|
||||
strategy: {
|
||||
payout: 0,
|
||||
match: (n: number): boolean => { return false },
|
||||
},
|
||||
}
|
||||
|
||||
this.step = this.step.bind(this);
|
||||
this.currentNumber = this.currentNumber.bind(this);
|
||||
this.updateInvestment = this.updateInvestment.bind(this);
|
||||
}
|
||||
|
||||
|
||||
componentDidMount() {
|
||||
this.interval = setInterval(this.step, 50);
|
||||
}
|
||||
|
||||
step() {
|
||||
if (!this.state.lock) {
|
||||
this.setState({n: Math.floor(Math.random()*37)});
|
||||
}
|
||||
}
|
||||
|
||||
componentWillUnmount() {
|
||||
clearInterval(this.interval);
|
||||
}
|
||||
|
||||
updateInvestment(e: React.FormEvent<HTMLInputElement>) {
|
||||
let investment: number = parseInt(e.currentTarget.value);
|
||||
if (isNaN(investment)) {
|
||||
investment = minPlay;
|
||||
}
|
||||
if (investment > maxPlay) {
|
||||
investment = maxPlay;
|
||||
}
|
||||
if (investment < minPlay) {
|
||||
investment = minPlay;
|
||||
}
|
||||
this.setState({investment: investment});
|
||||
}
|
||||
|
||||
currentNumber() {
|
||||
if (this.state.n === 0) return '0';
|
||||
const color = isRed(this.state.n) ? 'R' : 'B';
|
||||
return `${this.state.n}${color}`;
|
||||
}
|
||||
|
||||
play(s: Strategy) {
|
||||
if(this.reachedLimit(this.props.p)) return;
|
||||
this.setState({
|
||||
canPlay: false,
|
||||
lock: false,
|
||||
status: 'playing',
|
||||
strategy: s,
|
||||
})
|
||||
setTimeout(() => {
|
||||
let n = Math.floor(this.rng.random()*37);
|
||||
let status = <></>;
|
||||
let gain = 0;
|
||||
let playerWin = this.state.strategy.match(n)
|
||||
// oh yeah, the house straight up cheats. Try finding the seed now!
|
||||
if(playerWin && Math.random() > 0.9) {
|
||||
playerWin = false;
|
||||
while(this.state.strategy.match(n)) {
|
||||
n++;
|
||||
}
|
||||
}
|
||||
if(playerWin) {
|
||||
gain = this.state.investment*this.state.strategy.payout;
|
||||
status = <>won {Money(gain)}</>;
|
||||
} else {
|
||||
gain = -this.state.investment;
|
||||
status = <>lost {Money(-gain)}</>;
|
||||
}
|
||||
this.win(this.props.p, gain);
|
||||
this.setState({
|
||||
canPlay: true,
|
||||
lock: true,
|
||||
status: status,
|
||||
n: n,
|
||||
});
|
||||
this.reachedLimit(this.props.p);
|
||||
}, 1600);
|
||||
}
|
||||
|
||||
|
||||
render() {
|
||||
return <>
|
||||
<h1>{this.currentNumber()}</h1>
|
||||
<input type="number" className='text-input' onChange={this.updateInvestment} placeholder={"Amount to play"} value={this.state.investment} disabled={!this.state.canPlay} />
|
||||
<h1>{this.state.status}</h1>
|
||||
<table>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td><StdButton text={"3"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(3)))} /></td>
|
||||
<td><StdButton text={"6"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(6)))} /></td>
|
||||
<td><StdButton text={"9"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(9)))} /></td>
|
||||
<td><StdButton text={"12"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(12)))} /></td>
|
||||
<td><StdButton text={"15"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(15)))} /></td>
|
||||
<td><StdButton text={"18"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(18)))} /></td>
|
||||
<td><StdButton text={"21"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(21)))} /></td>
|
||||
<td><StdButton text={"24"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(24)))} /></td>
|
||||
<td><StdButton text={"27"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(27)))} /></td>
|
||||
<td><StdButton text={"30"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(30)))} /></td>
|
||||
<td><StdButton text={"33"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(33)))} /></td>
|
||||
<td><StdButton text={"36"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(36)))} /></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><StdButton text={"2"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(2)))} /></td>
|
||||
<td><StdButton text={"5"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(5)))} /></td>
|
||||
<td><StdButton text={"8"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(8)))} /></td>
|
||||
<td><StdButton text={"11"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(11)))} /></td>
|
||||
<td><StdButton text={"14"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(14)))} /></td>
|
||||
<td><StdButton text={"17"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(17)))} /></td>
|
||||
<td><StdButton text={"20"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(20)))} /></td>
|
||||
<td><StdButton text={"23"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(23)))} /></td>
|
||||
<td><StdButton text={"26"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(26)))} /></td>
|
||||
<td><StdButton text={"29"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(29)))} /></td>
|
||||
<td><StdButton text={"32"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(32)))} /></td>
|
||||
<td><StdButton text={"35"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(35)))} /></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><StdButton text={"1"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(1)))} /></td>
|
||||
<td><StdButton text={"4"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(4)))} /></td>
|
||||
<td><StdButton text={"7"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(7)))} /></td>
|
||||
<td><StdButton text={"10"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(10)))} /></td>
|
||||
<td><StdButton text={"13"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(13)))} /></td>
|
||||
<td><StdButton text={"16"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(16)))} /></td>
|
||||
<td><StdButton text={"19"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(19)))} /></td>
|
||||
<td><StdButton text={"22"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(22)))} /></td>
|
||||
<td><StdButton text={"25"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(25)))} /></td>
|
||||
<td><StdButton text={"28"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(28)))} /></td>
|
||||
<td><StdButton text={"31"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(31)))} /></td>
|
||||
<td><StdButton text={"34"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(34)))} /></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td colSpan={4}><StdButton text={"1 to 12"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.Third1))} /></td>
|
||||
<td colSpan={4}><StdButton text={"13 to 24"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.Third2))} /></td>
|
||||
<td colSpan={4}><StdButton text={"25 to 36"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.Third3))} /></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td colSpan={2}><StdButton text={"Red"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.Red))} /></td>
|
||||
<td colSpan={2}><StdButton text={"Black"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.Black))} /></td>
|
||||
<td colSpan={2}><StdButton text={"Odd"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.Odd))} /></td>
|
||||
<td colSpan={2}><StdButton text={"Even"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.Even))} /></td>
|
||||
<td colSpan={2}><StdButton text={"High"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.High))} /></td>
|
||||
<td colSpan={2}><StdButton text={"Low"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(strategies.Low))} /></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><StdButton text={"0"} disabled={!this.state.canPlay} onClick={trusted(()=>this.play(Single(0)))} /></td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</>
|
||||
}
|
||||
}
|
||||
239
src/Casino/SlotMachine.tsx
Normal file
239
src/Casino/SlotMachine.tsx
Normal file
@@ -0,0 +1,239 @@
|
||||
import * as React from "react";
|
||||
|
||||
import { IPlayer } from "../PersonObjects/IPlayer";
|
||||
import { StdButton } from "../ui/React/StdButton";
|
||||
import { Money } from "../ui/React/Money";
|
||||
import { WHRNG } from "./RNG";
|
||||
import { Game } from "./Game";
|
||||
import { trusted } from "./utils";
|
||||
|
||||
type IProps = {
|
||||
p: IPlayer;
|
||||
}
|
||||
|
||||
type IState = {
|
||||
index: number[];
|
||||
locks: number[];
|
||||
investment: number;
|
||||
canPlay: boolean;
|
||||
status: string | JSX.Element;
|
||||
}
|
||||
|
||||
// statically shuffled array of symbols.
|
||||
let symbols = ["D", "C", "$", "?", "♥", "A", "C", "B", "C", "E", "B", "E", "C",
|
||||
"*", "D", "♥", "B", "A", "A", "A", "C", "A", "D", "B", "E", "?", "D", "*",
|
||||
"@", "♥", "B", "E", "?"];
|
||||
|
||||
function getPayout(s: string, n: number): number {
|
||||
switch (s) {
|
||||
case "$":
|
||||
return [20, 200, 1000][n];
|
||||
case "@":
|
||||
return [8, 80, 400][n];
|
||||
case "♥":
|
||||
case "?":
|
||||
return [6, 20, 150][n];
|
||||
case "D":
|
||||
case "E":
|
||||
return [1, 8, 30][n];
|
||||
default:
|
||||
return [1, 5, 20][n];
|
||||
}
|
||||
}
|
||||
|
||||
const payLines = [
|
||||
// lines
|
||||
[[0, 0], [0, 1], [0, 2], [0, 3], [0, 4]],
|
||||
[[1, 0], [1, 1], [1, 2], [1, 3], [1, 4]],
|
||||
[[2, 0], [2, 1], [2, 2], [2, 3], [2, 4]],
|
||||
|
||||
// Vs
|
||||
[[2, 0], [1, 1], [0, 2], [1, 3], [2, 4]],
|
||||
[[0, 0], [1, 1], [2, 2], [1, 3], [0, 4]],
|
||||
|
||||
// rest
|
||||
[[0, 0], [1, 1], [1, 2], [1, 3], [0, 4]],
|
||||
[[2, 0], [1, 1], [1, 2], [1, 3], [2, 4]],
|
||||
[[1, 0], [0, 1], [0, 2], [0, 3], [1, 4]],
|
||||
[[1, 0], [2, 1], [2, 2], [2, 3], [1, 4]],
|
||||
];
|
||||
|
||||
const minPlay = 0;
|
||||
const maxPlay = 1e6;
|
||||
|
||||
export class SlotMachine extends Game<IProps, IState> {
|
||||
rng: WHRNG;
|
||||
interval: number = -1;
|
||||
|
||||
constructor(props: IProps) {
|
||||
super(props);
|
||||
this.rng = new WHRNG(this.props.p.totalPlaytime);
|
||||
|
||||
this.state = {
|
||||
index: [0, 0, 0, 0, 0],
|
||||
investment: 1000,
|
||||
locks: [0, 0, 0, 0, 0],
|
||||
canPlay: true,
|
||||
status: 'waiting',
|
||||
};
|
||||
|
||||
this.play = this.play.bind(this);
|
||||
this.lock = this.lock.bind(this);
|
||||
this.unlock = this.unlock.bind(this);
|
||||
this.step = this.step.bind(this);
|
||||
this.checkWinnings = this.checkWinnings.bind(this);
|
||||
this.getTable = this.getTable.bind(this);
|
||||
this.updateInvestment = this.updateInvestment.bind(this);
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
this.interval = setInterval(this.step, 50);
|
||||
}
|
||||
|
||||
step() {
|
||||
let stoppedOne = false;
|
||||
const index = this.state.index.slice();
|
||||
for(const i in index) {
|
||||
if (index[i] === this.state.locks[i] && !stoppedOne) continue;
|
||||
index[i] = (index[i] + 1) % symbols.length;
|
||||
stoppedOne = true;
|
||||
}
|
||||
|
||||
this.setState({index: index});
|
||||
|
||||
if(stoppedOne && index.every((e, i) => e === this.state.locks[i])) {
|
||||
this.checkWinnings();
|
||||
}
|
||||
}
|
||||
|
||||
componentWillUnmount() {
|
||||
clearInterval(this.interval);
|
||||
}
|
||||
|
||||
getTable(): string[][] {
|
||||
return [
|
||||
[symbols[(this.state.index[0]+symbols.length-1)%symbols.length], symbols[(this.state.index[1]+symbols.length-1)%symbols.length], symbols[(this.state.index[2]+symbols.length-1)%symbols.length], symbols[(this.state.index[3]+symbols.length-1)%symbols.length], symbols[(this.state.index[4]+symbols.length-1)%symbols.length]],
|
||||
[symbols[this.state.index[0]], symbols[this.state.index[1]], symbols[this.state.index[2]], symbols[this.state.index[3]], symbols[this.state.index[4]]],
|
||||
[symbols[(this.state.index[0]+1)%symbols.length], symbols[(this.state.index[1]+1)%symbols.length], symbols[(this.state.index[2]+1)%symbols.length], symbols[(this.state.index[3]+1)%symbols.length], symbols[(this.state.index[4]+1)%symbols.length]],
|
||||
];
|
||||
}
|
||||
|
||||
play() {
|
||||
if(this.reachedLimit(this.props.p)) return;
|
||||
this.setState({status: 'playing'});
|
||||
this.win(this.props.p, -this.state.investment);
|
||||
if(!this.state.canPlay) return;
|
||||
this.unlock();
|
||||
setTimeout(this.lock, this.rng.random()*2000+1000);
|
||||
}
|
||||
|
||||
lock() {
|
||||
this.setState({
|
||||
locks: [
|
||||
Math.floor(this.rng.random()*symbols.length),
|
||||
Math.floor(this.rng.random()*symbols.length),
|
||||
Math.floor(this.rng.random()*symbols.length),
|
||||
Math.floor(this.rng.random()*symbols.length),
|
||||
Math.floor(this.rng.random()*symbols.length),
|
||||
],
|
||||
})
|
||||
}
|
||||
|
||||
checkWinnings() {
|
||||
const t = this.getTable();
|
||||
const getPaylineData = function(payline: number[][]): string[] {
|
||||
let data = [];
|
||||
for(const point of payline) {
|
||||
data.push(t[point[0]][point[1]]);
|
||||
}
|
||||
return data;
|
||||
}
|
||||
|
||||
const countSequence = function(data: string[]): number {
|
||||
let count = 1;
|
||||
for(let i = 1; i < data.length; i++) {
|
||||
if (data[i]!==data[i-1]) break;
|
||||
count++;
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
let gains = -this.state.investment;
|
||||
for (const payline of payLines) {
|
||||
const data = getPaylineData(payline);
|
||||
const count = countSequence(data);
|
||||
if (count < 3) continue;
|
||||
const payout = getPayout(data[0], count-3);
|
||||
gains += this.state.investment*payout;
|
||||
this.win(this.props.p, this.state.investment*payout);
|
||||
}
|
||||
|
||||
this.setState({
|
||||
status: <>{gains>0?"gained":"lost"} {Money(Math.abs(gains))}</>,
|
||||
canPlay: true,
|
||||
})
|
||||
if(this.reachedLimit(this.props.p)) return;
|
||||
}
|
||||
|
||||
unlock() {
|
||||
this.setState({
|
||||
locks: [-1, -1, -1, -1, -1],
|
||||
canPlay: false,
|
||||
})
|
||||
}
|
||||
|
||||
updateInvestment(e: React.FormEvent<HTMLInputElement>) {
|
||||
let investment: number = parseInt(e.currentTarget.value);
|
||||
if (isNaN(investment)) {
|
||||
investment = minPlay;
|
||||
}
|
||||
if (investment > maxPlay) {
|
||||
investment = maxPlay;
|
||||
}
|
||||
if (investment < minPlay) {
|
||||
investment = minPlay;
|
||||
}
|
||||
this.setState({investment: investment});
|
||||
}
|
||||
|
||||
render() {
|
||||
const t = this.getTable();
|
||||
return <>
|
||||
<pre>
|
||||
+———————————————————————+<br />
|
||||
| | {t[0][0]} | {t[0][1]} | {t[0][2]} | {t[0][3]} | {t[0][4]} | |<br />
|
||||
| | | | | | | |<br />
|
||||
| | {symbols[this.state.index[0]]} | {symbols[this.state.index[1]]} | {symbols[this.state.index[2]]} | {symbols[this.state.index[3]]} | {symbols[this.state.index[4]]} | |<br />
|
||||
| | | | | | | |<br />
|
||||
| | {symbols[(this.state.index[0]+1)%symbols.length]} | {symbols[(this.state.index[1]+1)%symbols.length]} | {symbols[(this.state.index[2]+1)%symbols.length]} | {symbols[(this.state.index[3]+1)%symbols.length]} | {symbols[(this.state.index[4]+1)%symbols.length]} | |<br />
|
||||
+———————————————————————+<br />
|
||||
</pre>
|
||||
<input type="number" className='text-input' onChange={this.updateInvestment} placeholder={"Amount to play"} value={this.state.investment} disabled={!this.state.canPlay} />
|
||||
<StdButton onClick={trusted(this.play)} text={"Spin!"} disabled={!this.state.canPlay} />
|
||||
<h1>{this.state.status}</h1>
|
||||
<h2>Pay lines</h2>
|
||||
<pre>
|
||||
----- ····· ····· <br />
|
||||
····· ----- ····· <br />
|
||||
····· ····· ----- <br />
|
||||
</pre>
|
||||
<br />
|
||||
|
||||
<pre>
|
||||
··^·· \···/ \···/<br />
|
||||
·/·\· ·\·/· ·---·<br />
|
||||
/···\ ··v·· ·····<br />
|
||||
</pre>
|
||||
<br />
|
||||
|
||||
<pre>
|
||||
····· ·---· ·····<br />
|
||||
·---· /···\ \···/<br />
|
||||
/···\ ····· ·---·<br />
|
||||
</pre>
|
||||
</>
|
||||
}
|
||||
}
|
||||
|
||||
// https://felgo.com/doc/how-to-make-a-slot-game-tutorial/
|
||||
8
src/Casino/utils.ts
Normal file
8
src/Casino/utils.ts
Normal file
@@ -0,0 +1,8 @@
|
||||
import * as React from "react";
|
||||
|
||||
export function trusted(f: () => void): (event: React.MouseEvent<HTMLElement, MouseEvent>) => any {
|
||||
return function(event: React.MouseEvent<HTMLElement, MouseEvent>): any {
|
||||
if(!event.isTrusted) return;
|
||||
f();
|
||||
};
|
||||
}
|
||||
@@ -1,20 +1,23 @@
|
||||
import {
|
||||
CodingContract,
|
||||
CodingContractRewardType,
|
||||
CodingContractTypes
|
||||
CodingContractTypes,
|
||||
ICodingContractReward
|
||||
} from "./CodingContracts";
|
||||
import { Factions } from "./Faction/Factions";
|
||||
import { Player } from "./Player";
|
||||
import { AllServers } from "./Server/AllServers";
|
||||
import { GetServerByHostname } from "./Server/ServerHelpers";
|
||||
import { SpecialServerNames } from "./Server/SpecialServerIps";
|
||||
import { Server } from "./Server/Server";
|
||||
import { HacknetServer } from "./Hacknet/HacknetServer";
|
||||
|
||||
import { getRandomInt } from "../utils/helpers/getRandomInt";
|
||||
|
||||
|
||||
export function generateRandomContract() {
|
||||
// First select a random problem type
|
||||
let problemType = getRandomProblemType();
|
||||
const problemType = getRandomProblemType();
|
||||
|
||||
// Then select a random reward type. 'Money' will always be the last reward type
|
||||
const reward = getRandomReward();
|
||||
@@ -22,15 +25,15 @@ export function generateRandomContract() {
|
||||
// Choose random server
|
||||
const randServer = getRandomServer();
|
||||
|
||||
let contractFn = getRandomFilename(randServer, reward);
|
||||
let contract = new CodingContract(contractFn, problemType, reward);
|
||||
const contractFn = getRandomFilename(randServer, reward);
|
||||
const contract = new CodingContract(contractFn, problemType, reward);
|
||||
|
||||
randServer.addContract(contract);
|
||||
}
|
||||
|
||||
export function generateRandomContractOnHome() {
|
||||
// First select a random problem type
|
||||
let problemType = getRandomProblemType();
|
||||
const problemType = getRandomProblemType();
|
||||
|
||||
// Then select a random reward type. 'Money' will always be the last reward type
|
||||
const reward = getRandomReward();
|
||||
@@ -38,13 +41,19 @@ export function generateRandomContractOnHome() {
|
||||
// Choose random server
|
||||
const serv = Player.getHomeComputer();
|
||||
|
||||
let contractFn = getRandomFilename(serv, reward);
|
||||
let contract = new CodingContract(contractFn, problemType, reward);
|
||||
const contractFn = getRandomFilename(serv, reward);
|
||||
const contract = new CodingContract(contractFn, problemType, reward);
|
||||
|
||||
serv.addContract(contract);
|
||||
}
|
||||
|
||||
export function generateContract(params) {
|
||||
export interface IGenerateContractParams {
|
||||
problemType?: string;
|
||||
server?: string;
|
||||
fn?: string;
|
||||
}
|
||||
|
||||
export function generateContract(params: IGenerateContractParams) {
|
||||
// Problem Type
|
||||
let problemType;
|
||||
const problemTypes = Object.keys(CodingContractTypes);
|
||||
@@ -62,7 +71,7 @@ export function generateContract(params) {
|
||||
if (params.server != null) {
|
||||
server = GetServerByHostname(params.server);
|
||||
if (server == null) {
|
||||
server = AllServers[param.server];
|
||||
server = AllServers[params.server];
|
||||
}
|
||||
if (server == null) {
|
||||
server = getRandomServer();
|
||||
@@ -84,7 +93,7 @@ export function generateContract(params) {
|
||||
}
|
||||
|
||||
// Ensures that a contract's reward type is valid
|
||||
function sanitizeRewardType(rewardType) {
|
||||
function sanitizeRewardType(rewardType: CodingContractRewardType): CodingContractRewardType {
|
||||
let type = rewardType; // Create copy
|
||||
|
||||
const factionsThatAllowHacking = Player.factions.filter((fac) => {
|
||||
@@ -115,9 +124,11 @@ function getRandomProblemType() {
|
||||
return problemTypes[randIndex];
|
||||
}
|
||||
|
||||
function getRandomReward() {
|
||||
let reward = {};
|
||||
reward.type = getRandomInt(0, CodingContractRewardType.Money);
|
||||
function getRandomReward(): ICodingContractReward {
|
||||
let reward: ICodingContractReward = {
|
||||
name: "",
|
||||
type: getRandomInt(0, CodingContractRewardType.Money),
|
||||
};
|
||||
reward.type = sanitizeRewardType(reward.type);
|
||||
|
||||
// Add additional information based on the reward type
|
||||
@@ -155,7 +166,7 @@ function getRandomReward() {
|
||||
return reward;
|
||||
}
|
||||
|
||||
function getRandomServer() {
|
||||
function getRandomServer(): Server | HacknetServer {
|
||||
const servers = Object.keys(AllServers);
|
||||
let randIndex = getRandomInt(0, servers.length - 1);
|
||||
let randServer = AllServers[servers[randIndex]];
|
||||
@@ -163,7 +174,7 @@ function getRandomServer() {
|
||||
// An infinite loop shouldn't ever happen, but to be safe we'll use
|
||||
// a for loop with a limited number of tries
|
||||
for (let i = 0; i < 200; ++i) {
|
||||
if (!randServer.purchasedByPlayer && randServer.hostname !== SpecialServerNames.WorldDaemon) {
|
||||
if (randServer instanceof Server && !randServer.purchasedByPlayer && randServer.hostname !== SpecialServerNames.WorldDaemon) {
|
||||
break;
|
||||
}
|
||||
randIndex = getRandomInt(0, servers.length - 1);
|
||||
@@ -173,11 +184,11 @@ function getRandomServer() {
|
||||
return randServer;
|
||||
}
|
||||
|
||||
function getRandomFilename(server, reward) {
|
||||
function getRandomFilename(server: Server | HacknetServer, reward: ICodingContractReward): string {
|
||||
let contractFn = `contract-${getRandomInt(0, 1e6)}`;
|
||||
|
||||
for (let i = 0; i < 1000; ++i) {
|
||||
if (server.contracts.filter((c) => {return c.fn === contractFn}).length <= 0) { break; }
|
||||
if (server.contracts.filter((c: CodingContract) => {return c.fn === contractFn}).length <= 0) { break; }
|
||||
contractFn = `contract-${getRandomInt(0, 1e6)}`;
|
||||
}
|
||||
|
||||
@@ -181,6 +181,9 @@ export class CodingContract {
|
||||
return new Promise<CodingContractResult>((resolve: Function, reject: Function) => {
|
||||
const contractType: CodingContractType = CodingContractTypes[this.type];
|
||||
const popupId: string = `coding-contract-prompt-popup-${this.fn}`;
|
||||
const title: HTMLElement = createElement("h1", {
|
||||
innerHTML: this.type,
|
||||
});
|
||||
const txt: HTMLElement = createElement("p", {
|
||||
innerHTML: ["You are attempting to solve a Coding Contract. You have",
|
||||
`${this.getMaxNumTries() - this.tries} tries remaining,`,
|
||||
@@ -225,7 +228,7 @@ export class CodingContract {
|
||||
innerText: "Cancel",
|
||||
});
|
||||
const lineBreak: HTMLElement = createElement("br");
|
||||
createPopup(popupId, [txt, lineBreak, lineBreak, answerInput, solveBtn, cancelBtn]);
|
||||
createPopup(popupId, [title, lineBreak, txt, lineBreak, lineBreak, answerInput, solveBtn, cancelBtn]);
|
||||
answerInput.focus();
|
||||
});
|
||||
}
|
||||
|
||||
@@ -6,13 +6,13 @@
|
||||
import { IMap } from "./types";
|
||||
|
||||
export let CONSTANTS: IMap<any> = {
|
||||
Version: "0.49.0",
|
||||
Version: "0.51.6",
|
||||
|
||||
/** Max level for any skill, assuming no multipliers. Determined by max numerical value in javascript for experience
|
||||
/** 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
|
||||
* the player will have this level assuming no multipliers. Multipliers can cause skills to go above this.
|
||||
*/
|
||||
MaxSkillLevel: 975,
|
||||
MaxSkillLevel: 975,
|
||||
|
||||
// Milliseconds per game cycle
|
||||
MilliPerCycle: 200,
|
||||
@@ -75,14 +75,14 @@ export let CONSTANTS: IMap<any> = {
|
||||
HospitalCostPerHp: 100e3,
|
||||
|
||||
// Intelligence-related constants
|
||||
IntelligenceCrimeWeight: 0.05, // Weight for how much int affects crime success rates
|
||||
IntelligenceCrimeWeight: 0.025, // Weight for how much int affects crime success rates
|
||||
IntelligenceInfiltrationWeight: 0.1, // Weight for how much int affects infiltration success rates
|
||||
IntelligenceCrimeBaseExpGain: 0.001,
|
||||
IntelligenceProgramBaseExpGain: 500, // Program required hack level divided by this to determine int exp gain
|
||||
IntelligenceCrimeBaseExpGain: 0.05,
|
||||
IntelligenceProgramBaseExpGain: 2.5, // Program required hack level divided by this to determine int exp gain
|
||||
IntelligenceTerminalHackBaseExpGain: 200, // Hacking exp divided by this to determine int exp gain
|
||||
IntelligenceSingFnBaseExpGain: 0.002,
|
||||
IntelligenceClassBaseExpGain: 0.000001,
|
||||
IntelligenceHackingMissionBaseExpGain: 0.03, // Hacking Mission difficulty multiplied by this to get exp gain
|
||||
IntelligenceSingFnBaseExpGain: 1.5,
|
||||
IntelligenceClassBaseExpGain: 0.01,
|
||||
IntelligenceHackingMissionBaseExpGain: 3, // Hacking Mission difficulty multiplied by this to get exp gain
|
||||
|
||||
// Hacking Missions
|
||||
// TODO Move this into Hacking Mission implementation
|
||||
@@ -218,7 +218,7 @@ export let CONSTANTS: IMap<any> = {
|
||||
CrimeHeist: "pull off the ultimate heist",
|
||||
|
||||
// Coding Contract
|
||||
// TODO Move this into Coding contract impelmentation?
|
||||
// TODO: Move this into Coding contract implementation?
|
||||
CodingContractBaseFactionRepGain: 2500,
|
||||
CodingContractBaseCompanyRepGain: 4000,
|
||||
CodingContractBaseMoneyGain: 75e6,
|
||||
@@ -228,34 +228,42 @@ export let CONSTANTS: IMap<any> = {
|
||||
|
||||
LatestUpdate:
|
||||
`
|
||||
v0.49.2 - 2021-03-13
|
||||
v0.51.6 - 2021-04-28 Backdoor! (Community)
|
||||
-------
|
||||
|
||||
BN8
|
||||
* A new bitnode multipler has been added, it lets you reduce money from a
|
||||
server without gaining actually any money. This is important for BN8 where
|
||||
hack/grow can influence the stock market. No money can be gained from
|
||||
hacking but server money can still be reduced.
|
||||
Backdoor
|
||||
* a new terminal command, backdoor, has been added to help differentiate
|
||||
between the terminal hack command and the netscript hack function. (@dewint)
|
||||
|
||||
Documentation
|
||||
* readthedocs should now be more consistent and many examples were added.
|
||||
Milestones
|
||||
* A new tab under the Help menu has been added to guide players through the
|
||||
game.
|
||||
|
||||
Casino
|
||||
* Blackjack has been added (@BigD)
|
||||
|
||||
Netscript
|
||||
* Ace editor will now correctly highlight all functions.
|
||||
* 'tFormat' is a new netscript function that returns a human readable
|
||||
representation of milliseconds. eg. "2 hours 15 minute 43 seconds"
|
||||
* 'prompt' now converts input to JSON.
|
||||
* 'getRunningScript' is a new netscript function that returns a bunch of
|
||||
data related to a running script.
|
||||
|
||||
Gang
|
||||
* style improvements
|
||||
Coding contracts
|
||||
* trivial puzzles should no longer appear.
|
||||
|
||||
Bladeburner
|
||||
* style improvements
|
||||
* fix bug where 'skill list SKILL' would crash if skill is level 0.
|
||||
|
||||
Sleeve
|
||||
* karma gain now scales with sync.
|
||||
Infiltration
|
||||
* All numbers are formatted like the rest of the game.
|
||||
|
||||
Misc.
|
||||
Fix issue where the effective stats under Character>Stats were being calculated.
|
||||
* Server security is capped at 100.
|
||||
* Added option to quit a job.
|
||||
* 'cd' no longer works on unexistent folders.
|
||||
* cd with no arguments brings you back to top level folder (@Andreas)
|
||||
* 'softReset' documentation udpated.
|
||||
* Money tracker now accounts for going to the hospital manually.
|
||||
* codemirror is now the default editor (for new save files)
|
||||
* fix typo in dark web help text (@Rodeth)
|
||||
* so many documentation and typos fixes (@Pimgd)
|
||||
* A corruption visual effect has been added to location with servers that
|
||||
have backdoor installed. (@dewint)
|
||||
`
|
||||
}
|
||||
}
|
||||
@@ -17,7 +17,8 @@ import { Warehouse } from "./Warehouse";
|
||||
import { BitNodeMultipliers } from "../BitNode/BitNodeMultipliers";
|
||||
import { CONSTANTS } from "../Constants";
|
||||
import { Factions } from "../Faction/Factions";
|
||||
import { showLiterature } from "../Literature";
|
||||
import { showLiterature } from "../Literature/LiteratureHelpers";
|
||||
import { LiteratureNames } from "../Literature/data/LiteratureNames";
|
||||
import { createCityMap } from "../Locations/Cities";
|
||||
import { CityName } from "../Locations/data/CityNames";
|
||||
import { Player } from "../Player";
|
||||
@@ -1795,7 +1796,7 @@ OfficeSpace.prototype.findEmployees = function(parentRefs) {
|
||||
"Creativity: " + formatNumber(employee.cre, 1) + "<br>" +
|
||||
"Efficiency: " + formatNumber(employee.eff, 1) + "<br>" +
|
||||
"Salary: " + numeralWrapper.format(employee.sal, '$0.000a') + " \ s<br>",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
office.hireEmployee(employee, parentRefs);
|
||||
removeElementById("cmpy-mgmt-hire-employee-popup");
|
||||
return false;
|
||||
@@ -1808,7 +1809,7 @@ OfficeSpace.prototype.findEmployees = function(parentRefs) {
|
||||
class:"a-link-button",
|
||||
innerText:"Cancel",
|
||||
float:"right",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
removeElementById("cmpy-mgmt-hire-employee-popup");
|
||||
return false;
|
||||
}
|
||||
@@ -1842,7 +1843,7 @@ OfficeSpace.prototype.hireEmployee = function(employee, parentRefs) {
|
||||
company.rerender();
|
||||
return yesNoTxtInpBoxClose();
|
||||
});
|
||||
noBtn.addEventListener("click", ()=>{
|
||||
noBtn.addEventListener("click", () => {
|
||||
return yesNoTxtInpBoxClose();
|
||||
});
|
||||
yesNoTxtInpBoxCreate("Give your employee a nickname!");
|
||||
@@ -2075,14 +2076,14 @@ Corporation.prototype.getInvestment = function() {
|
||||
noBtn = yesNoBoxGetNoButton();
|
||||
yesBtn.innerHTML = "Accept";
|
||||
noBtn.innerHML = "Reject";
|
||||
yesBtn.addEventListener("click", ()=>{
|
||||
yesBtn.addEventListener("click", () => {
|
||||
++this.fundingRound;
|
||||
this.funds = this.funds.plus(funding);
|
||||
this.numShares -= investShares;
|
||||
this.rerender();
|
||||
return yesNoBoxClose();
|
||||
});
|
||||
noBtn.addEventListener("click", ()=>{
|
||||
noBtn.addEventListener("click", () => {
|
||||
return yesNoBoxClose();
|
||||
});
|
||||
yesNoBoxCreate("An investment firm has offered you " + numeralWrapper.format(funding, '$0.000a') +
|
||||
@@ -2107,7 +2108,7 @@ Corporation.prototype.goPublic = function() {
|
||||
var input = createElement("input", {
|
||||
type:"number",
|
||||
placeholder: "Shares to issue",
|
||||
onkeyup:(e)=>{
|
||||
onkeyup:(e) => {
|
||||
e.preventDefault();
|
||||
if (e.keyCode === KEY.ENTER) {yesBtn.click();}
|
||||
}
|
||||
@@ -2116,7 +2117,7 @@ Corporation.prototype.goPublic = function() {
|
||||
yesBtn = createElement("a", {
|
||||
class:"a-link-button",
|
||||
innerText:"Go Public",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
var numShares = Math.round(input.value);
|
||||
var initialSharePrice = this.determineValuation() / (this.totalShares);
|
||||
if (isNaN(numShares)) {
|
||||
@@ -2142,7 +2143,7 @@ Corporation.prototype.goPublic = function() {
|
||||
var noBtn = createElement("a", {
|
||||
class:"a-link-button",
|
||||
innerText:"Cancel",
|
||||
clickListener:()=>{
|
||||
clickListener:() => {
|
||||
removeElementById(goPublicPopupId);
|
||||
return false;
|
||||
}
|
||||
@@ -2330,7 +2331,7 @@ Corporation.prototype.getStarterGuide = function() {
|
||||
// Check if player already has Corporation Handbook
|
||||
let homeComp = Player.getHomeComputer(),
|
||||
hasHandbook = false,
|
||||
handbookFn = "corporation-management-handbook.lit";
|
||||
handbookFn = LiteratureNames.CorporationManagementHandbook;
|
||||
for (let i = 0; i < homeComp.messages.length; ++i) {
|
||||
if (isString(homeComp.messages[i]) && homeComp.messages[i] === handbookFn) {
|
||||
hasHandbook = true;
|
||||
|
||||
@@ -210,9 +210,13 @@ export class Product {
|
||||
}
|
||||
|
||||
//Delete unneeded variables
|
||||
// @ts-ignore
|
||||
delete this.prog;
|
||||
// @ts-ignore
|
||||
delete this.createCity;
|
||||
// @ts-ignore
|
||||
delete this.designCost;
|
||||
// @ts-ignore
|
||||
delete this.advCost;
|
||||
}
|
||||
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user