Commit ee53cfbf authored by Mahmoud Aglan's avatar Mahmoud Aglan

fix: reduce capture frequency and add time-decay for fairer Ludo

- Halved near-capture dice boost (0.3 → 0.15) and reduced per-die
  capture bonus (0.15 → 0.08)
- Capture bias decays to zero as game approaches 15 min (captureMul
  factor), making late-game rolls essentially fair/random
- Removed the multi-capture boost that added +0.2 to all dice 1-5
- Increased six-boost after 8 min (scales up to +0.8 by 15 min) to
  accelerate finishing and keep games under ~15 minutes
Co-Authored-By: 's avatarClaude Opus 4.6 <noreply@anthropic.com>
parent a2876e3e
...@@ -100,6 +100,9 @@ function detectNearCapture(game, playerIdx) { ...@@ -100,6 +100,9 @@ function detectNearCapture(game, playerIdx) {
function computeDiceWeights(ctx) { function computeDiceWeights(ctx) {
const w = [1, 1, 1, 1, 1, 1]; const w = [1, 1, 1, 1, 1, 1];
// Time factor: 0 at start, 1 at 15 min — used to decay capture bias and boost finishing
const timeFactor = Math.min(1, ctx.elapsed / 15);
if (ctx.piecesHome === 4) { if (ctx.piecesHome === 4) {
w[5] += 0.8; w[5] += 0.8;
} else if (ctx.piecesHome >= 3) { } else if (ctx.piecesHome >= 3) {
...@@ -111,25 +114,23 @@ function computeDiceWeights(ctx) { ...@@ -111,25 +114,23 @@ function computeDiceWeights(ctx) {
w[5] += Math.min(0.8, deficit / 40); w[5] += Math.min(0.8, deficit / 40);
} }
if (ctx.killValues >= 2 && ctx.progress < ctx.avgOthersProgress) {
w[1] += 0.2; w[2] += 0.2; w[3] += 0.2; w[4] += 0.2;
}
if (ctx.progress - ctx.avgOthersProgress > 20 && ctx.piecesHome === 0) { if (ctx.progress - ctx.avgOthersProgress > 20 && ctx.piecesHome === 0) {
w[5] = Math.max(0.5, w[5] - 0.5); w[5] = Math.max(0.5, w[5] - 0.5);
} }
if (ctx.elapsed > 12) { // As game progresses, boost sixes more aggressively to ensure finish within 15 min
w[5] += 0.3; if (ctx.elapsed > 8) {
w[5] += 0.3 + timeFactor * 0.5;
} }
// "Lucky roll" — subtle boost toward capture dice (should feel lucky, not guaranteed) // Capture bias decays with time — early game has mild luck, late game is fair/random
const captureMul = Math.max(0, 1 - timeFactor * 1.2);
if (ctx.nearCapture > 0) { if (ctx.nearCapture > 0) {
const idx = ctx.nearCapture - 1; const idx = ctx.nearCapture - 1;
w[idx] += 0.3; w[idx] += 0.15 * captureMul;
} }
for (let i = 0; i < 6; i++) { for (let i = 0; i < 6; i++) {
if (ctx.capturePerDie[i]) w[i] += 0.15; if (ctx.capturePerDie[i]) w[i] += 0.08 * captureMul;
} }
return w; return w;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment