CORPORATION: adding prevState and changed state display in the warehouse UI (#861)

This commit is contained in:
Caldwell 2023-10-23 10:48:06 +02:00 committed by GitHub
parent eed2c5d6d4
commit e992cb966a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
11 changed files with 96 additions and 76 deletions

@ -26,11 +26,12 @@ interface CorporationInfo
| [issuedShares](./bitburner.corporationinfo.issuedshares.md) | | number | Amount of shares owned by public traders. Available for CEO buyback. |
| [issueNewSharesCooldown](./bitburner.corporationinfo.issuenewsharescooldown.md) | | number | Cooldown until new shares can be issued |
| [name](./bitburner.corporationinfo.name.md) | | string | Name of the corporation |
| [nextState](./bitburner.corporationinfo.nextstate.md) | | [CorpStateName](./bitburner.corpstatename.md) | <p>The next state to be processed.</p><p>I.e. when the state is PURCHASE, it means purchasing will occur during the next state transition.</p><p>Possible states are START, PURCHASE, PRODUCTION, EXPORT, SALE.</p> |
| [numShares](./bitburner.corporationinfo.numshares.md) | | number | Amount of shares owned by the CEO. |
| [prevState](./bitburner.corporationinfo.prevstate.md) | | [CorpStateName](./bitburner.corpstatename.md) | <p>The last state that got processed.</p><p>I.e. when that state is PURCHASE, it means purchasing just happened.</p><p>Possible states are START, PURCHASE, PRODUCTION, EXPORT, SALE.</p> |
| [public](./bitburner.corporationinfo.public.md) | | boolean | Indicating if the company is public |
| [revenue](./bitburner.corporationinfo.revenue.md) | | number | Revenue per second this cycle |
| [sharePrice](./bitburner.corporationinfo.shareprice.md) | | number | Price of the shares |
| [shareSaleCooldown](./bitburner.corporationinfo.sharesalecooldown.md) | | number | Cooldown until shares can be sold again |
| [state](./bitburner.corporationinfo.state.md) | | string | <p>The next state to be processed.</p><p>I.e. when the state is PURCHASE, it means purchasing will occur during the next state transition.</p><p>Possible states are START, PURCHASE, PRODUCTION, EXPORT, SALE.</p> |
| [totalShares](./bitburner.corporationinfo.totalshares.md) | | number | Total number of shares issued by this corporation. |

@ -1,8 +1,8 @@
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
[Home](./index.md) &gt; [bitburner](./bitburner.md) &gt; [CorporationInfo](./bitburner.corporationinfo.md) &gt; [state](./bitburner.corporationinfo.state.md)
[Home](./index.md) &gt; [bitburner](./bitburner.md) &gt; [CorporationInfo](./bitburner.corporationinfo.md) &gt; [nextState](./bitburner.corporationinfo.nextstate.md)
## CorporationInfo.state property
## CorporationInfo.nextState property
The next state to be processed.
@ -13,5 +13,5 @@ Possible states are START, PURCHASE, PRODUCTION, EXPORT, SALE.
**Signature:**
```typescript
state: string;
nextState: CorpStateName;
```

@ -0,0 +1,17 @@
<!-- Do not edit this file. It is automatically generated by API Documenter. -->
[Home](./index.md) &gt; [bitburner](./bitburner.md) &gt; [CorporationInfo](./bitburner.corporationinfo.md) &gt; [prevState](./bitburner.corporationinfo.prevstate.md)
## CorporationInfo.prevState property
The last state that got processed.
I.e. when that state is PURCHASE, it means purchasing just happened.
Possible states are START, PURCHASE, PRODUCTION, EXPORT, SALE.
**Signature:**
```typescript
prevState: CorpStateName;
```

@ -94,8 +94,8 @@ export class Corporation {
this.funds += amt;
}
getState(): CorpStateName {
return this.state.getState();
getNextState(): CorpStateName {
return this.state.nextName;
}
storeCycles(numCycles: number): void {
@ -106,7 +106,7 @@ export class Corporation {
if (this.storedCycles < 0) this.storedCycles = 0;
if (this.storedCycles >= corpConstants.gameCyclesPerCorpStateCycle) {
const state = this.getState();
const state = this.getNextState();
const marketCycles = 1;
const gameCycles = marketCycles * corpConstants.gameCyclesPerCorpStateCycle;
this.storedCycles -= gameCycles;
@ -171,7 +171,7 @@ export class Corporation {
this.updateSharePrice();
}
this.state.nextState();
this.state.incrementState();
// Handle "nextUpdate" resolvers after this update
for (const resolve of CorporationResolvers.splice(0)) {

@ -9,12 +9,14 @@ export class CorporationState {
// Get the name of the current state
// NOTE: This does NOT return the number stored in the 'state' property,
// which is just an index for the array of all possible Corporation States.
getState(): CorpStateName {
get nextName(): CorpStateName {
return stateNames[this.state];
}
get prevName(): CorpStateName {
return stateNames[(this.state + (stateNames.length - 1)) % stateNames.length];
}
// Transition to the next state
nextState(): void {
incrementState(): void {
this.state = (this.state + 1) % stateNames.length;
}
@ -22,7 +24,6 @@ export class CorporationState {
toJSON(): IReviverValue {
return Generic_toJSON("CorporationState", this);
}
// Initializes a CorporationState object from a JSON save state.
static fromJSON(value: IReviverValue): CorporationState {
return Generic_fromJSON(CorporationState, value.data);

@ -142,7 +142,7 @@ export class Division {
}
process(marketCycles = 1, corporation: Corporation): void {
const state = corporation.state.getState();
const state = corporation.state.nextName;
//At the start of a cycle, store and reset revenue/expenses
//Then calculate salaries and process the markets
if (state === "START") {
@ -264,7 +264,7 @@ export class Division {
//Process production, purchase, and import/export of materials
processMaterials(marketCycles = 1, corporation: Corporation): [number, number] {
const state = corporation.state.getState();
const state = corporation.state.nextName;
let revenue = 0;
let expenses = 0;
this.calculateProductionFactors();
@ -717,7 +717,7 @@ export class Division {
/** Process product development and production/sale */
processProducts(marketCycles = 1, corporation: Corporation): [number, number] {
const state = corporation.state.getState();
const state = corporation.state.nextName;
let revenue = 0;
const expenses = 0;
@ -746,7 +746,7 @@ export class Division {
//Processes FINISHED products
processProduct(marketCycles = 1, product: Product, corporation: Corporation): number {
const state = corporation.state.getState();
const state = corporation.state.nextName;
let totalProfit = 0;
for (const [city, office] of getRecordEntries(this.offices)) {
const warehouse = this.warehouses[city];

@ -10,7 +10,7 @@ import { SmartSupplyModal } from "./modals/SmartSupplyModal";
import { ProductElem } from "./ProductElem";
import { MaterialElem } from "./MaterialElem";
import { MaterialInfo } from "../MaterialInfo";
import { createProgressBarText } from "../../utils/helpers/createProgressBarText";
import { formatBigNumber, formatMaterialSize } from "../../ui/formatNumber";
import { Corporation } from "../Corporation";
@ -20,7 +20,7 @@ import { isRelevantMaterial } from "./Helpers";
import { IndustryProductEquation } from "./IndustryProductEquation";
import { purchaseWarehouse } from "../Actions";
import { useCorporation, useDivision } from "./Context";
import { gameCyclesPerCorpStateCycle } from "../data/Constants";
import { ButtonWithTooltip } from "../../ui/Components/ButtonWithTooltip";
interface WarehouseProps {
@ -57,30 +57,14 @@ function WarehouseRoot(props: WarehouseProps): React.ReactElement {
corp.funds = corp.funds - sizeUpgradeCost;
props.rerender();
}
// Next state which will be processed:
const state = corp.state.getState();
let stateText;
switch (state) {
case "START":
stateText = "Next state: Preparing";
break;
case "PURCHASE":
stateText = "Next state: Purchasing materials";
break;
case "PRODUCTION":
stateText = "Next state: Producing materials and/or products";
break;
case "SALE":
stateText = "Next state: Selling materials and/or products";
break;
case "EXPORT":
stateText = "Next state: Exporting materials and/or products";
break;
default:
console.error(`Invalid state: ${state}`);
break;
}
// -1 because as soon as it hits "full" it processes and resets to 0, *2 to double the size of the bar
const ticks = (gameCyclesPerCorpStateCycle - 1) * 2;
const nextState = corp.state.nextName;
const prevState = corp.state.prevName.padStart(11);
const stateBar = createProgressBarText({
progress: Math.min(corp.storedCycles * 2, ticks) / ticks,
totalTicks: ticks,
});
// Create React components for materials
const mats = [];
@ -160,9 +144,9 @@ function WarehouseRoot(props: WarehouseProps): React.ReactElement {
divisions.
</Typography>
<br />
<Typography className={classes.retainHeight}>{stateText}</Typography>
<Typography style={{ whiteSpace: "pre-wrap" }} className={classes.retainHeight}>
{prevState} {stateBar} {nextState}
</Typography>
{corp.unlocks.has(CorpUnlockName.SmartSupply) && (
<>
<Button onClick={() => setSmartSupplyOpen(true)}>Configure Smart Supply</Button>

@ -103,6 +103,7 @@ import { ContentFilePath } from "./Paths/ContentFile";
import { hasContractExtension } from "./Paths/ContractFilePath";
import { getRamCost } from "./Netscript/RamCostGenerator";
import { getEnumHelper } from "./utils/EnumHelper";
import { setDeprecatedProperties, deprecationWarning } from "./utils/DeprecationHelper";
export const enums: NSEnums = {
CityName,
@ -1807,30 +1808,3 @@ function getFunctionNames(obj: object, prefix: string): string[] {
}
return functionNames;
}
const deprecatedWarningsGiven = new Set();
function setDeprecatedProperties(
obj: object,
properties: Record<string, { identifier: string; message: string; value: any }>,
) {
for (const [name, info] of Object.entries(properties)) {
Object.defineProperty(obj, name, {
get: () => {
deprecationWarning(info.identifier, info.message);
return info.value;
},
set: (value: any) => (info.value = value),
enumerable: true,
});
}
}
function deprecationWarning(identifier: string, message: string) {
if (!deprecatedWarningsGiven.has(identifier)) {
deprecatedWarningsGiven.add(identifier);
Terminal.warn(`Accessed deprecated function or property: ${identifier}`);
Terminal.warn(`This is no longer supported usage and will be removed in a later version.`);
Terminal.warn(message);
Terminal.info(`This message can also appear for object properties when the object's values are iterated.`);
Terminal.info(`This message will only be shown once per game session for each deprecated item accessed.`);
}
}

@ -7,7 +7,7 @@ import { Warehouse } from "../Corporation/Warehouse";
import { Division } from "../Corporation/Division";
import { Corporation, CorporationResolvers } from "../Corporation/Corporation";
import { cloneDeep, omit } from "lodash";
import { setDeprecatedProperties } from "../utils/DeprecationHelper";
import {
Corporation as NSCorporation,
Division as NSDivision,
@ -698,7 +698,7 @@ export function NetscriptCorporation(): InternalAPI<NSCorporation> {
getCorporation: (ctx) => () => {
checkAccess(ctx);
const corporation = getCorporation();
return {
const data = {
name: corporation.name,
funds: corporation.funds,
revenue: corporation.revenue,
@ -714,9 +714,18 @@ export function NetscriptCorporation(): InternalAPI<NSCorporation> {
dividendRate: corporation.dividendRate,
dividendTax: corporation.dividendTax,
dividendEarnings: corporation.getCycleDividends() / corpConstants.secondsPerMarketCycle,
state: corporation.state.getState(),
nextState: corporation.state.nextName,
prevState: corporation.state.prevName,
divisions: [...corporation.divisions.keys()],
};
setDeprecatedProperties(data, {
state: {
identifier: "ns.corporation.getCorporation().state",
message: "Use ns.corporation.getCorporation().nextState instead.",
value: corporation.state.nextName,
},
});
return data;
},
createCorporation:
(ctx) =>

@ -7686,7 +7686,13 @@ interface CorporationInfo {
* I.e. when the state is PURCHASE, it means purchasing will occur during the next state transition.
*
* Possible states are START, PURCHASE, PRODUCTION, EXPORT, SALE. */
state: string;
nextState: CorpStateName;
/** The last state that got processed.
*
* I.e. when that state is PURCHASE, it means purchasing just happened.
*
* Possible states are START, PURCHASE, PRODUCTION, EXPORT, SALE. */
prevState: CorpStateName;
/** Array of all division names */
divisions: string[];
}

@ -0,0 +1,28 @@
import { Terminal } from "../Terminal";
const deprecatedWarningsGiven = new Set();
export function setDeprecatedProperties(
obj: object,
properties: Record<string, { identifier: string; message: string; value: any }>,
) {
for (const [name, info] of Object.entries(properties)) {
Object.defineProperty(obj, name, {
get: () => {
deprecationWarning(info.identifier, info.message);
return info.value;
},
set: (value: any) => (info.value = value),
enumerable: true,
});
}
}
export function deprecationWarning(identifier: string, message: string) {
if (!deprecatedWarningsGiven.has(identifier)) {
deprecatedWarningsGiven.add(identifier);
Terminal.warn(`Accessed deprecated function or property: ${identifier}`);
Terminal.warn(`This is no longer supported usage and will be removed in a later version.`);
Terminal.warn(message);
Terminal.info(`This message can also appear for object properties when the object's values are iterated.`);
Terminal.info(`This message will only be shown once per game session for each deprecated item accessed.`);
}
}