fix(rules): apply the power attack penalty to melee touch attacks

PF1e (CRB Power Attack): "take a -1 penalty on all melee attack rolls ...
The bonus damage does not apply to touch attacks." A melee touch (kind
"touch", no range increment) is a melee attack, so _power_attack_amt now
rides its attack and confirmation rolls; the +2X/+3X damage bonus stays
gated on kind == "melee". Ranged attacks and rays are unaffected. The
test that pinned the old melee-weapon-only simplification was rewritten to
lock the corrected behavior; README and abilities.py updated.

Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
This commit is contained in:
2026-09-11 23:35:07 +02:00
parent 8a8b813889
commit a2825e73cc
4 changed files with 30 additions and 11 deletions
+9 -4
View File
@@ -6,7 +6,9 @@ B8 Flanking: the flanking ally must actually THREATEN the target (a reach
weapon's 5-ft dead zone does not threaten) and must not be unable to act.
B9 Melee touch (kind "touch", no range increment) is a melee attack: it gains
flanking, high ground, the vs-helpless +4 and can sneak attack; Power
Attack stays melee-only.
Attack's -X penalty rides its attack rolls while the bonus damage never
applies to touch (A6 refinement — the original "melee-only feat" reading
was itself a deviation).
B10 Blinded: NO flat -2 on attack rolls (the modeled 50% total-concealment
miss is the RAW penalty); the -4 Dex-skill penalty rides the dex_skills
target (B22).
@@ -233,7 +235,7 @@ def test_melee_touch_can_sneak_attack() -> None:
assert any("sneak attack" in line for line in eng._transcript)
def test_power_attack_still_excludes_melee_touch() -> None:
def test_power_attack_penalizes_melee_touch_attack_roll() -> None:
atk = _combatant(
"atk", bab=5, attacks=(_touch("atk"),), features=("Power Attack",)
)
@@ -242,8 +244,11 @@ def test_power_attack_still_excludes_melee_touch() -> None:
a = eng._states[0]
a.power_attack = True
result = eng.resolve_attack(a, eng._states[1], _touch("atk"))
# Power Attack is melee-weapon-only: the touch swing keeps its full bonus.
assert result.total == 10 + 10
# PF1e (CRB Power Attack): the -X penalty rides ALL melee attack rolls and
# a melee touch IS a melee attack (X = 5//4 + 1 = 2); the bonus damage
# never applies to touch attacks — 1d6 = 2, no +2X.
assert result.total == 10 + 10 - 2
assert result.damage == 2
# ── B10: blinded has no flat attack penalty ──────────────────────────────────