UI: Consistently calculate BitNode "level" (#2645)

This commit is contained in:
catloversg
2026-04-11 05:45:18 +07:00
committed by GitHub
parent 54287e5f7f
commit 5cb0d559df
5 changed files with 21 additions and 9 deletions

View File

@@ -93,3 +93,12 @@ export function finishBitNode() {
}
wd.backdoorInstalled = true;
}
/**
* BitNode level is not something that is stored, but rather calculated from the current BN and SF level. The concept
* appeared because saying "Enter BN1.2" is shorter than saying "Enter BN1 with SF1.1". This is how we display it in the
* BitVerse UI and other places. This function is used to consistently calculate this "level".
*/
export function getBitNodeLevel(bn = Player.bitNodeN, sfLevel = Player.activeSourceFileLvl(bn)): number {
return Math.min(sfLevel + 1, bn === 12 ? Number.MAX_VALUE : 3);
}

View File

@@ -20,7 +20,7 @@ import { StatsRow } from "../../ui/React/StatsRow";
import { defaultMultipliers, getBitNodeMultipliers } from "../BitNode";
import { BitNodeMultipliers } from "../BitNodeMultipliers";
import { PartialRecord, getRecordEntries } from "../../Types/Record";
import { canAccessBitNodeFeature } from "../BitNodeUtils";
import { canAccessBitNodeFeature, getBitNodeLevel } from "../BitNodeUtils";
interface IProps {
n: number;
@@ -56,8 +56,7 @@ export const BitNodeMultipliersDisplay = ({ n, level, hideMultsIfCannotAccessFea
// If not, then we have to assume that we want the next level up from the
// current node's source file, so we get the min of that, the SF's max level,
// or if it's BN12, ∞
const maxSfLevel = n === 12 ? Number.MAX_VALUE : 3;
const mults = getBitNodeMultipliers(n, level ?? Math.min(Player.activeSourceFileLvl(n) + 1, maxSfLevel));
const mults = getBitNodeMultipliers(n, level ?? getBitNodeLevel(n));
return (
<Box sx={{ columnCount: 2, columnGap: 1, mb: n === 1 ? 0 : -2 }}>

View File

@@ -10,6 +10,7 @@ import Button from "@mui/material/Button";
import { BitNodeMultiplierDescription } from "./BitnodeMultipliersDescription";
import { BitNodeAdvancedOptions } from "./BitNodeAdvancedOptions";
import { JSONMap } from "../../Types/Jsonable";
import { getBitNodeLevel } from "../BitNodeUtils";
interface IProps {
open: boolean;
@@ -37,7 +38,7 @@ export function PortalModal(props: IProps): React.ReactElement {
const bitNode = BitNodes[bitNodeKey];
if (bitNode == null) throw new Error(`Could not find BitNode object for number: ${props.n}`);
const maxSourceFileLevel = props.n === 12 ? "∞" : "3";
const newLevel = Math.min(props.level + 1, props.n === 12 ? Number.MAX_VALUE : 3);
const newLevel = getBitNodeLevel(props.n, props.level);
let currentSourceFiles = new Map(Player.sourceFiles);
if (!props.flume) {

View File

@@ -36,6 +36,7 @@ import { loadInfiltrations } from "./Infiltration/SaveLoadInfiltration";
import { InfiltrationState } from "./Infiltration/formulas/game";
import { hasDarknetAccess } from "./DarkNet/utils/darknetAuthUtils";
import { loadSettings } from "./Settings/SettingsUtils";
import { getBitNodeLevel } from "./BitNode/BitNodeUtils";
/* SaveObject.js
* Defines the object used to save/load games
@@ -270,7 +271,7 @@ class BitburnerSaveObject implements BitburnerSaveObjectType {
* - Base64 format: save file uses .json extension. Save data is the base64-encoded json save string.
*/
const extension = canUseBinaryFormat() ? "json.gz" : "json";
return `bitburnerSave_${epochTime}_BN${bn}x${Player.sourceFileLvl(bn) + 1}.${extension}`;
return `bitburnerSave_${epochTime}_BN${bn}x${getBitNodeLevel()}.${extension}`;
}
async exportGame(): Promise<void> {
@@ -430,7 +431,10 @@ class BitburnerSaveObject implements BitburnerSaveObjectType {
achievements: importedPlayer.achievements?.length ?? 0,
bitNode: importedPlayer.bitNodeN,
bitNodeLevel: importedPlayer.sourceFileLvl(importedPlayer.bitNodeN) + 1,
bitNodeLevel: getBitNodeLevel(
importedPlayer.bitNodeN,
importedPlayer.activeSourceFileLvl(importedPlayer.bitNodeN),
),
sourceFiles: [...importedPlayer.sourceFiles].reduce<number>((total, [__bn, lvl]) => (total += lvl), 0),
exploits: importedPlayer.exploits.length,

View File

@@ -17,7 +17,7 @@ import { StatsRow } from "./React/StatsRow";
import { StatsTable } from "./React/StatsTable";
import { useCycleRerender } from "./React/hooks";
import { getMaxRep } from "../Go/effects/effect";
import { canAccessBitNodeFeature, knowAboutBitverse } from "../BitNode/BitNodeUtils";
import { canAccessBitNodeFeature, getBitNodeLevel, knowAboutBitverse } from "../BitNode/BitNodeUtils";
interface EmployersModalProps {
open: boolean;
@@ -103,11 +103,10 @@ function MultiplierTable(props: MultTableProps): React.ReactElement {
function CurrentBitNode(): React.ReactElement {
if (knowAboutBitverse()) {
const index = "BitNode" + Player.bitNodeN;
const lvl = Math.min(Player.sourceFileLvl(Player.bitNodeN) + 1, Player.bitNodeN === 12 ? Number.MAX_VALUE : 3);
return (
<Paper sx={{ mb: 1, p: 1 }}>
<Typography variant="h5">
BitNode {Player.bitNodeN}: {BitNodes[index].name} (Level {lvl})
BitNode {Player.bitNodeN}: {BitNodes[index].name} (Level {getBitNodeLevel()})
</Typography>
<Typography component="div" sx={{ whiteSpace: "pre-wrap", overflowWrap: "break-word" }}>
{BitNodes[index].info}