Files
Battle-for-Tismo/client/js/modals/format.js
T
adrien ede258d39f Added warfare depth, focused research and a reworked HUD
- Tile improvements (fortifications, radar towers, coastal cannons), trenches,
  zone of control, support-unit capture and launch transports, with parabolic
  barrage arcs drawn between attacker and target.
- Focused research that pours points straight into the chosen technology, with
  per-technology progress kept when the focus changes, plus repeatable levels.
- Popularity reworked to integer points, war and pillage effects, minority
  policies and month-over-month arrows on the nation summary.
- City progress bars, square improvement buttons, a technology tab of wide
  short cards with progress bars, transport cargo readout and double-click to
  open a city panel.
2026-09-21 01:07:36 +02:00

78 lines
3.0 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
// Shared formatting helpers for the modal panels.
import { groupDigits } from "../../../shared/text_format.js";
import { policyById } from "../../../shared/data.js";
export function formatEffect(effect, level) {
const value = level <= 0 ? 0 : effect.baseValue * Math.pow(level, effect.exponent);
switch (effect.stat) {
case "gdp":
return `${value >= 0 ? "+" : ""}${(value * 100).toFixed(1)}% GDP/capita`;
case "budget_income":
return `${value >= 0 ? "+" : ""}${(value * 100).toFixed(1)}% tax income`;
case "research":
return `${value >= 0 ? "+" : ""}${value.toFixed(2)} research/h`;
case "culture":
return `${value >= 0 ? "+" : ""}${value.toFixed(2)} culture/h`;
case "infantry_attack":
return `${value >= 0 ? "+" : ""}${(value * 100).toFixed(1)}% infantry attack`;
case "infantry_defense":
return `${value >= 0 ? "+" : ""}${(value * 100).toFixed(1)}% infantry defense`;
case "artillery_attack":
return `${value >= 0 ? "+" : ""}${(value * 100).toFixed(1)}% artillery attack`;
case "construction_speed":
return `${value >= 0 ? "+" : ""}${(value * 100).toFixed(1)}% construction speed`;
case "rail_speed":
return `${value >= 0 ? "+" : ""}${(value * 100).toFixed(1)}% railway speed`;
default:
return `${effect.stat} ${value.toFixed(2)}`;
}
}
export function effectsText(effects, level) {
const parts = effects.map((e) => formatEffect(e, level));
return parts.length > 0 ? parts.join(" · ") : "No effect";
}
export const SOURCE_LABELS = { building: "building", government: "government", technology: "research" };
export function signedMoney(value) {
return `${value < 0 ? "−" : "+"}€${groupDigits(Math.round(Math.abs(value)))}/h`;
}
export function percent(value) {
return `${value < 0 ? "−" : "+"}${(Math.abs(value) * 100).toFixed(1)}%`;
}
// Renders one news entry as text, resolving civ indices to names and demonyms.
export function describeNews(entry, civs) {
const name = (index) => (civs[index] ? civs[index].name : `Nation ${index + 1}`);
const people = (index) => {
const civ = civs[index];
return civ && civ.demonym ? `The ${civ.demonym}` : name(index);
};
switch (entry.type) {
case "war":
return `${people(entry.actor)} declared war on ${name(entry.target)}`;
case "capture":
return `${people(entry.to)} captured ${entry.city} from ${name(entry.from)}`;
case "policy": {
const policy = policyById(entry.policy);
const policyName = policy ? policy.name : entry.policy;
const who =
civs[entry.ethnicity] && civs[entry.ethnicity].demonym
? `the ${civs[entry.ethnicity].demonym}`
: name(entry.ethnicity);
return `${name(entry.civ)} enacted ${policyName} for ${who}`;
}
case "technology":
return entry.repeatable
? `${name(entry.civ)} improved ${entry.name}`
: `${name(entry.civ)} discovered ${entry.name}`;
case "join":
return `${entry.player} took control of ${name(entry.civ)}`;
default:
return entry.type;
}
}