Phase 4: Mana Flow effects
This commit is contained in:
@@ -63,8 +63,13 @@ export function useManaStats() {
|
||||
? Math.floor(maxMana / 100) * 0.1
|
||||
: 0;
|
||||
|
||||
// Mana Waterfall bonus
|
||||
const manaWaterfallBonus = hasSpecial(upgradeEffects, SPECIAL_EFFECTS.MANA_WATERFALL)
|
||||
? Math.floor(maxMana / 100) * 0.25
|
||||
: 0;
|
||||
|
||||
// Final effective regen
|
||||
const effectiveRegen = (effectiveRegenWithSpecials + manaCascadeBonus) * meditationMultiplier;
|
||||
const effectiveRegen = (effectiveRegenWithSpecials + manaCascadeBonus + manaWaterfallBonus) * meditationMultiplier;
|
||||
|
||||
return {
|
||||
upgradeEffects,
|
||||
@@ -75,11 +80,16 @@ export function useManaStats() {
|
||||
incursionStrength,
|
||||
effectiveRegenWithSpecials,
|
||||
manaCascadeBonus,
|
||||
manaWaterfallBonus,
|
||||
effectiveRegen,
|
||||
hasSteadyStream: hasSpecial(upgradeEffects, SPECIAL_EFFECTS.STEADY_STREAM),
|
||||
hasManaTorrent: hasSpecial(upgradeEffects, SPECIAL_EFFECTS.MANA_TORRENT),
|
||||
hasDesperateWells: hasSpecial(upgradeEffects, SPECIAL_EFFECTS.DESPERATE_WELLS),
|
||||
hasManaEcho: hasSpecial(upgradeEffects, SPECIAL_EFFECTS.MANA_ECHO),
|
||||
hasManaWaterfall: hasSpecial(upgradeEffects, SPECIAL_EFFECTS.MANA_WATERFALL),
|
||||
hasFlowSurge: hasSpecial(upgradeEffects, SPECIAL_EFFECTS.FLOW_SURGE),
|
||||
hasManaOverflow: hasSpecial(upgradeEffects, SPECIAL_EFFECTS.MANA_OVERFLOW),
|
||||
hasEternalFlow: hasSpecial(upgradeEffects, SPECIAL_EFFECTS.ETERNAL_FLOW),
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
+28
-3
@@ -720,6 +720,7 @@ function makeInitial(overrides: Partial<GameState> = {}): GameState {
|
||||
|
||||
log: ['✨ The loop begins. You start with a Basic Staff (Mana Bolt) and civilian clothes. Gather your strength, mage.'],
|
||||
loopInsight: 0,
|
||||
flowSurgeEndTime: 0, // Hour timestamp for FLOW_SURGE effect (0 = inactive)
|
||||
};
|
||||
}
|
||||
|
||||
@@ -857,10 +858,24 @@ export const useGameStore = create<GameStore>()(
|
||||
}
|
||||
|
||||
// Calculate effective regen with incursion and meditation
|
||||
const effectiveRegen = baseRegen * (1 - incursionStrength) * meditationMultiplier;
|
||||
let effectiveRegen = baseRegen * (1 - incursionStrength) * meditationMultiplier;
|
||||
|
||||
// Mana regeneration
|
||||
let rawMana = Math.min(state.rawMana + effectiveRegen * HOURS_PER_TICK, maxMana);
|
||||
// FLOW_SURGE: +100% regen for 1 hour after clicking
|
||||
let flowSurgeEndTime = state.flowSurgeEndTime;
|
||||
if (flowSurgeEndTime > 0) {
|
||||
if (state.hour <= flowSurgeEndTime) {
|
||||
// FLOW_SURGE is active - double the regen
|
||||
effectiveRegen *= 2;
|
||||
} else {
|
||||
// FLOW_SURGE has expired
|
||||
flowSurgeEndTime = 0;
|
||||
}
|
||||
}
|
||||
|
||||
// Mana regeneration with MANA_OVERFLOW support
|
||||
const overflowMultiplier = hasSpecial(effects, SPECIAL_EFFECTS.MANA_OVERFLOW) ? 1.2 : 1.0;
|
||||
const maxManaWithOverflow = maxMana * overflowMultiplier;
|
||||
let rawMana = Math.min(state.rawMana + effectiveRegen * HOURS_PER_TICK, maxManaWithOverflow);
|
||||
let totalManaGathered = state.totalManaGathered;
|
||||
|
||||
// Attunement mana conversion - convert raw mana to attunement's primary mana type
|
||||
@@ -1405,6 +1420,7 @@ export const useGameStore = create<GameStore>()(
|
||||
log,
|
||||
castProgress,
|
||||
golemancy,
|
||||
flowSurgeEndTime,
|
||||
...craftingUpdates,
|
||||
});
|
||||
},
|
||||
@@ -1421,9 +1437,18 @@ export const useGameStore = create<GameStore>()(
|
||||
cm = Math.floor(cm * overflowBonus);
|
||||
|
||||
const max = computeMaxMana(state, effects);
|
||||
|
||||
// FLOW_SURGE: Clicks restore 2x regen for 1 hour
|
||||
let flowSurgeEndTime = state.flowSurgeEndTime;
|
||||
if (hasSpecial(effects, SPECIAL_EFFECTS.FLOW_SURGE) && flowSurgeEndTime === 0) {
|
||||
// Activate FLOW_SURGE for 1 hour
|
||||
flowSurgeEndTime = state.hour + 1;
|
||||
}
|
||||
|
||||
set({
|
||||
rawMana: Math.min(state.rawMana + cm, max),
|
||||
totalManaGathered: state.totalManaGathered + cm,
|
||||
flowSurgeEndTime,
|
||||
});
|
||||
},
|
||||
|
||||
|
||||
@@ -105,6 +105,7 @@ export interface GameState {
|
||||
rawMana: number;
|
||||
meditateTicks: number;
|
||||
totalManaGathered: number;
|
||||
flowSurgeEndTime: number; // Hour timestamp for FLOW_SURGE effect (0 = inactive)
|
||||
|
||||
// Attunements (class-like system)
|
||||
attunements: Record<string, AttunementState>; // attunement id -> state
|
||||
|
||||
@@ -336,6 +336,11 @@ export function computeDynamicRegen(
|
||||
regen += Math.floor(maxMana / 100) * 0.1;
|
||||
}
|
||||
|
||||
// Mana Waterfall: +0.25 regen per 100 max mana (upgraded cascade)
|
||||
if (hasSpecial(effects, SPECIAL_EFFECTS.MANA_WATERFALL)) {
|
||||
regen += Math.floor(maxMana / 100) * 0.25;
|
||||
}
|
||||
|
||||
// Mana Torrent: +50% regen when above 75% mana
|
||||
if (hasSpecial(effects, SPECIAL_EFFECTS.MANA_TORRENT) && currentMana > maxMana * 0.75) {
|
||||
regen *= 1.5;
|
||||
@@ -346,6 +351,11 @@ export function computeDynamicRegen(
|
||||
regen *= 1.5;
|
||||
}
|
||||
|
||||
// Eternal Flow: Regen immune to ALL penalties (stronger than Steady Stream)
|
||||
if (hasSpecial(effects, SPECIAL_EFFECTS.ETERNAL_FLOW)) {
|
||||
return regen * effects.regenMultiplier;
|
||||
}
|
||||
|
||||
// Steady Stream: Regen immune to incursion
|
||||
if (hasSpecial(effects, SPECIAL_EFFECTS.STEADY_STREAM)) {
|
||||
return regen * effects.regenMultiplier;
|
||||
|
||||
Reference in New Issue
Block a user