Aetheria/Assets/Scripts/ServerShared/Behaviors/Thermotoggle.cs
Meta Vens 74d2cf8fc4 Power bus: a consumer its thermostat has closed is not billed
The bus billed every active IPowerConsumer, but a behaviour group stops at its
Thermotoggle: a heater above its target never runs its EnergyDraw, yet its
full draw (1000-2500/s) was charged every tick. On an idle station that kept
the reactor in permanent deficit, overloading at overload efficiency. The bus
now skips a consumer whose group has a closed thermostat ahead of it, the same
rule it already applies to inactive items; Thermotoggle.Open is the one
statement of when a thermostat is open, and Execute returns it.

Tests (Soul's F2; S17 survived before): from a hull at one uniform temperature,
one tick below the heater's target raises its cells and one above does not, so
the heater's own contribution is measured with no reactor heat in it; and the
bus bills the heater's draw below its target and not above.

This does not keep an idle station warm (Soul's F1, reported separately): the
reactor's throttled idle heat alone still drives it past its plateau.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-30 20:46:30 +02:00

54 lines
No EOL
1.7 KiB
C#

/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at https://mozilla.org/MPL/2.0/. */
using System;
using System.Linq;
using MessagePack;
using Newtonsoft.Json;
[Inspectable, MessagePackObject, JsonObject(MemberSerialization.OptIn)]
public class ThermotoggleData : BehaviorData
{
[InspectableTemperature, JsonProperty("targetTemp"), Key(1)]
public float TargetTemperature;
[Inspectable, JsonProperty("highPass"), Key(2)]
public bool HighPass;
[Inspectable, JsonProperty("adjustable"), Key(3)]
public bool Adjustable;
public override Behavior CreateInstance(EquippedItem item)
{
return new Thermotoggle(this, item);
}
public override Behavior CreateInstance(ConsumableItemEffect item)
{
return new Thermotoggle(this, item);
}
}
public class Thermotoggle : Behavior
{
public float TargetTemperature;
private ThermotoggleData _data;
public ThermotoggleData ThermotoggleData => _data;
public Thermotoggle(ThermotoggleData data, EquippedItem item) : base(data, item)
{
_data = data;
TargetTemperature = data.TargetTemperature;
}
public Thermotoggle(ThermotoggleData data, ConsumableItemEffect item) : base(data, item)
{
_data = data;
TargetTemperature = data.TargetTemperature;
}
// Whether the rest of this behaviour's group runs this tick: below the target, or above it for a high-pass one.
public bool Open => Temperature < TargetTemperature ^ _data.HighPass;
public override bool Execute(float dt) => Open;
}