mirror of
https://github.com/bitburner-official/bitburner-src.git
synced 2026-04-16 06:18:42 +02:00
Compare commits
3 Commits
c5536d252b
...
dev
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
45bce6e45e | ||
|
|
c21d1f44b2 | ||
|
|
956e00f789 |
@@ -4,19 +4,10 @@ import { AchievementList } from "./AchievementList";
|
||||
import { achievements } from "./Achievements";
|
||||
import { Box, Typography } from "@mui/material";
|
||||
import { Player } from "@player";
|
||||
import { makeStyles } from "tss-react/mui";
|
||||
|
||||
const useStyles = makeStyles()({
|
||||
root: {
|
||||
width: 50,
|
||||
userSelect: "none",
|
||||
},
|
||||
});
|
||||
|
||||
export function AchievementsRoot(): JSX.Element {
|
||||
const { classes } = useStyles();
|
||||
return (
|
||||
<div className={classes.root} style={{ width: "100%" }}>
|
||||
<div style={{ width: "100%" }}>
|
||||
<Typography variant="h4">Achievements</Typography>
|
||||
<Box mx={2}>
|
||||
<Typography>
|
||||
|
||||
@@ -7,7 +7,7 @@ export const CONSTANTS = {
|
||||
VersionString: "3.0.0dev",
|
||||
isDevBranch: true,
|
||||
isInTestEnvironment: globalThis.process?.env?.JEST_WORKER_ID !== undefined,
|
||||
VersionNumber: 48,
|
||||
VersionNumber: 49,
|
||||
|
||||
/** 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
|
||||
|
||||
@@ -9,6 +9,10 @@ import Tabs from "@mui/material/Tabs";
|
||||
import Tab from "@mui/material/Tab";
|
||||
|
||||
import { useCycleRerender } from "../../ui/React/hooks";
|
||||
import Button from "@mui/material/Button";
|
||||
import { Router } from "../../ui/GameRoot";
|
||||
import { Page } from "../../ui/Router";
|
||||
import { Factions } from "../../Faction/Factions";
|
||||
|
||||
/** React Component for all the gang stuff. */
|
||||
export function GangRoot(): React.ReactElement {
|
||||
@@ -18,7 +22,7 @@ export function GangRoot(): React.ReactElement {
|
||||
})();
|
||||
const [value, setValue] = React.useState(0);
|
||||
|
||||
function handleChange(event: React.SyntheticEvent, tab: number): void {
|
||||
function handleChange(__event: React.SyntheticEvent, tab: number): void {
|
||||
setValue(tab);
|
||||
}
|
||||
|
||||
@@ -26,11 +30,26 @@ export function GangRoot(): React.ReactElement {
|
||||
|
||||
return (
|
||||
<Context.Gang.Provider value={gang}>
|
||||
<Tabs variant="fullWidth" value={value} onChange={handleChange} sx={{ minWidth: "fit-content", maxWidth: "45%" }}>
|
||||
<Tab label="Management" />
|
||||
<Tab label="Equipment" />
|
||||
<Tab label="Territory" />
|
||||
</Tabs>
|
||||
<div style={{ display: "flex" }}>
|
||||
<Tabs
|
||||
variant="fullWidth"
|
||||
value={value}
|
||||
onChange={handleChange}
|
||||
sx={{ minWidth: "fit-content", maxWidth: "45%" }}
|
||||
>
|
||||
<Tab label="Management" />
|
||||
<Tab label="Equipment" />
|
||||
<Tab label="Territory" />
|
||||
</Tabs>
|
||||
<Button
|
||||
style={{ marginLeft: "20px" }}
|
||||
onClick={() => {
|
||||
Router.toPage(Page.Faction, { faction: Factions[gang.facName] });
|
||||
}}
|
||||
>
|
||||
Faction
|
||||
</Button>
|
||||
</div>
|
||||
{value === 0 && <ManagementSubpage />}
|
||||
{value === 1 && <EquipmentsSubpage />}
|
||||
{value === 2 && <TerritorySubpage />}
|
||||
|
||||
@@ -147,6 +147,10 @@ export abstract class Person implements IPerson {
|
||||
}
|
||||
|
||||
overrideIntelligence(): void {
|
||||
// Do not set anything if the player has not unlocked Intelligence.
|
||||
if (Player.sourceFileLvl(5) === 0 && Player.bitNodeN !== 5) {
|
||||
return;
|
||||
}
|
||||
const persistentIntelligenceSkill = this.calculateSkill(this.persistentIntelligenceData.exp, 1);
|
||||
// Reset exp and skill to the persistent values if there is no limit (intelligenceOverride) or the limit is greater
|
||||
// than or equal to the persistent skill.
|
||||
@@ -172,7 +176,7 @@ export abstract class Person implements IPerson {
|
||||
* Don't change sourceFileLvl to activeSourceFileLvl. When the player has int level, the ability to gain more int is
|
||||
* a permanent benefit.
|
||||
*/
|
||||
if (Player.sourceFileLvl(5) > 0 || this.skills.intelligence > 0 || Player.bitNodeN === 5) {
|
||||
if (Player.sourceFileLvl(5) > 0 || Player.bitNodeN === 5) {
|
||||
this.exp.intelligence += exp;
|
||||
this.skills.intelligence = Math.floor(this.calculateSkill(this.exp.intelligence, 1));
|
||||
this.persistentIntelligenceData.exp += exp;
|
||||
|
||||
@@ -157,7 +157,7 @@ const Engine = {
|
||||
messages: 150,
|
||||
mechanicProcess: 5, // Process Bladeburner
|
||||
contractGeneration: 3000, // Generate Coding Contracts
|
||||
achievementsCounter: 60, // Check if we have new achievements
|
||||
achievementsCounter: 5, // Check if we have new achievements
|
||||
},
|
||||
|
||||
decrementAllCounters: function (numCycles = 1) {
|
||||
@@ -215,7 +215,7 @@ const Engine = {
|
||||
|
||||
if (Engine.Counters.achievementsCounter <= 0) {
|
||||
calculateAchievements();
|
||||
Engine.Counters.achievementsCounter = 300;
|
||||
Engine.Counters.achievementsCounter = 5;
|
||||
}
|
||||
|
||||
// This **MUST** remain the last block in the function!
|
||||
|
||||
@@ -637,4 +637,11 @@ Error: ${e}`,
|
||||
if (ver < 48) {
|
||||
showAPIBreaks("3.0.0", breakingChanges300);
|
||||
}
|
||||
if (ver < 49 && Player.sourceFileLvl(5) === 0 && Player.bitNodeN !== 5) {
|
||||
for (const person of [Player, ...Player.sleeves]) {
|
||||
person.persistentIntelligenceData.exp = 0;
|
||||
person.exp.intelligence = 0;
|
||||
person.skills.intelligence = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -105,4 +105,31 @@ describe("v3", () => {
|
||||
`bitburnerSave_backup_2.8.1_${Math.round(lastUpdate / 1000)}.json.gz`,
|
||||
);
|
||||
});
|
||||
|
||||
describe("Intelligence migration bug", () => {
|
||||
test("No change in exp and skill level", async () => {
|
||||
const saveData = new Uint8Array(fs.readFileSync("test/jest/Migration/save-files/v2.8.1_SF1.1_SF10.3.gz"));
|
||||
const mockedDownload = await loadGameFromSaveData(saveData);
|
||||
|
||||
for (const person of [Player, ...Player.sleeves]) {
|
||||
expect(person.persistentIntelligenceData.exp).toStrictEqual(0);
|
||||
expect(person.exp.intelligence).toStrictEqual(0);
|
||||
expect(person.skills.intelligence).toStrictEqual(0);
|
||||
}
|
||||
|
||||
expect(mockedDownload).toHaveBeenCalledWith(saveData, "bitburnerSave_backup_2.8.1_1776173824.json.gz");
|
||||
});
|
||||
test("Reset wrong exp and skill level", async () => {
|
||||
const saveData = new Uint8Array(fs.readFileSync("test/jest/Migration/save-files/v3.0.0_int_migration_bug.gz"));
|
||||
const mockedDownload = await loadGameFromSaveData(saveData);
|
||||
|
||||
for (const person of [Player, ...Player.sleeves]) {
|
||||
expect(person.persistentIntelligenceData.exp).toStrictEqual(0);
|
||||
expect(person.exp.intelligence).toStrictEqual(0);
|
||||
expect(person.skills.intelligence).toStrictEqual(0);
|
||||
}
|
||||
|
||||
expect(mockedDownload).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
BIN
test/jest/Migration/save-files/v2.8.1_SF1.1_SF10.3.gz
Normal file
BIN
test/jest/Migration/save-files/v2.8.1_SF1.1_SF10.3.gz
Normal file
Binary file not shown.
BIN
test/jest/Migration/save-files/v3.0.0_int_migration_bug.gz
Normal file
BIN
test/jest/Migration/save-files/v3.0.0_int_migration_bug.gz
Normal file
Binary file not shown.
@@ -55,8 +55,12 @@ function testIntelligenceOverride(
|
||||
setUpBeforePrestige = () => {},
|
||||
): void {
|
||||
Player.sourceFiles.set(5, 1);
|
||||
// The intelligence skill level starts at 0.
|
||||
expect(Player.skills.intelligence).toStrictEqual(0);
|
||||
prestigeSourceFile(true);
|
||||
// Start without exp.
|
||||
expect(Player.exp.intelligence).toStrictEqual(0);
|
||||
// When having SF5 and the skill level is 0, it's set to 1.
|
||||
expect(Player.skills.intelligence).toStrictEqual(1);
|
||||
expect(Player.persistentIntelligenceData.exp).toStrictEqual(0);
|
||||
// Gain 1e6 exp (skill = 242).
|
||||
|
||||
Reference in New Issue
Block a user