diff --git a/src/features/conversion.ts b/src/features/conversion.ts index 55b1547..785a6d1 100644 --- a/src/features/conversion.ts +++ b/src/features/conversion.ts @@ -1,8 +1,8 @@ import { GenericLayer } from "game/layers"; +import { Modifier } from "game/modifiers"; import Decimal, { DecimalSource } from "util/bignum"; import { Computable, - convertComputable, GetComputableTypeWithDefault, processComputable, ProcessedComputable @@ -23,7 +23,7 @@ export interface ConversionOptions { buyMax?: Computable; roundUpCost?: Computable; convert?: VoidFunction; - gainModifier?: GainModifier; + gainModifier?: Modifier; } export interface BaseConversion { @@ -54,11 +54,6 @@ export type GenericConversion = Replace< } >; -export interface GainModifier { - apply: (gain: DecimalSource) => DecimalSource; - revert: (gain: DecimalSource) => DecimalSource; -} - export function createConversion( optionsFunc: OptionsFunc, BaseConversion> ): Conversion { @@ -307,34 +302,3 @@ export function addHardcap( currentGain: conversion => Decimal.min(scaling.currentGain(conversion), unref(cap)) }; } - -export function createAdditiveModifier(addend: Computable): GainModifier { - const processedAddend = convertComputable(addend); - return { - apply: gain => Decimal.add(gain, unref(processedAddend)), - revert: gain => Decimal.sub(gain, unref(processedAddend)) - }; -} - -export function createMultiplicativeModifier(multiplier: Computable): GainModifier { - const processedMultiplier = convertComputable(multiplier); - return { - apply: gain => Decimal.times(gain, unref(processedMultiplier)), - revert: gain => Decimal.div(gain, unref(processedMultiplier)) - }; -} - -export function createExponentialModifier(exponent: Computable): GainModifier { - const processedExponent = convertComputable(exponent); - return { - apply: gain => Decimal.pow(gain, unref(processedExponent)), - revert: gain => Decimal.root(gain, unref(processedExponent)) - }; -} - -export function createSequentialModifier(...modifiers: GainModifier[]): GainModifier { - return { - apply: gain => modifiers.reduce((gain, modifier) => modifier.apply(gain), gain), - revert: gain => modifiers.reduceRight((gain, modifier) => modifier.revert(gain), gain) - }; -} diff --git a/src/game/modifiers.ts b/src/game/modifiers.ts new file mode 100644 index 0000000..1584c7b --- /dev/null +++ b/src/game/modifiers.ts @@ -0,0 +1,76 @@ +import Decimal, { DecimalSource, format } from "util/bignum"; +import { Computable, convertComputable, ProcessedComputable } from "util/computed"; +import { computed, unref } from "vue"; + +export interface Modifier { + apply: (gain: DecimalSource) => DecimalSource; + revert: (gain: DecimalSource) => DecimalSource; + enabled: ProcessedComputable; + description?: ProcessedComputable; +} + +export function createAdditiveModifier( + addend: Computable, + description?: string, + enabled?: Computable +): Modifier { + const processedAddend = convertComputable(addend); + const processedEnabled = convertComputable(enabled == null ? true : enabled); + return { + apply: gain => Decimal.add(gain, unref(processedAddend)), + revert: gain => Decimal.sub(gain, unref(processedAddend)), + enabled: processedEnabled, + description: computed(() => `+${format(unref(processedAddend))} ${description}`) + }; +} + +export function createMultiplicativeModifier( + multiplier: Computable, + description?: string, + enabled?: Computable +): Modifier { + const processedMultiplier = convertComputable(multiplier); + const processedEnabled = convertComputable(enabled == null ? true : enabled); + return { + apply: gain => Decimal.times(gain, unref(processedMultiplier)), + revert: gain => Decimal.div(gain, unref(processedMultiplier)), + enabled: processedEnabled, + description: computed(() => `x${format(unref(processedMultiplier))} ${description}`) + }; +} + +export function createExponentialModifier( + exponent: Computable, + description?: string, + enabled?: Computable +): Modifier { + const processedExponent = convertComputable(exponent); + const processedEnabled = convertComputable(enabled == null ? true : enabled); + return { + apply: gain => Decimal.pow(gain, unref(processedExponent)), + revert: gain => Decimal.root(gain, unref(processedExponent)), + enabled: processedEnabled, + description: computed(() => `^${format(unref(processedExponent))} ${description}`) + }; +} + +export function createSequentialModifier(...modifiers: Modifier[]): Modifier { + return { + apply: gain => + modifiers + .filter(m => unref(m.enabled)) + .reduce((gain, modifier) => modifier.apply(gain), gain), + revert: gain => + modifiers + .filter(m => unref(m.enabled)) + .reduceRight((gain, modifier) => modifier.revert(gain), gain), + enabled: computed(() => modifiers.filter(m => unref(m.enabled)).length > 0), + description: computed(() => { + return modifiers + .filter(m => unref(m.enabled)) + .map(m => unref(m.description)) + .filter(d => d) + .join("\n"); + }) + }; +}