Open dwvanstone opened 7 years ago
Yeah, that looks like a real bug. It looks like I'll need to perform the TimeAndSpace check later in the turn sequence now.
@cgolubi1, when you've got a chance, would you be able to generate me a responder test case for this please? I figure it should be possible to test this with a pretty short test case.
Ack, will do.
Just noting that I'm still waiting on a responder test to replicate this bug, and I'd like to have that before attempting a fix, since I fear it's going to be a somewhat involved fix.
@cgolubi1, just bringing this to your attention again, so that you can generate me a responder test and I can fix this bug.
Ack. Putting this on my list for the week.
Here you go, blackshadowshade. As noted by the comments, once the bug is fixed, we should actually check the response to make sure the code does the right thing, and i can help add that when we get to that point. But since the action log response is clearly wrong, i think this gives you enough to work with to fix the bug.
/**
* @depends test_request_savePlayerInfo
* @group fulltest_deps
*
* Regression-testing Dead Guy skill attack behavior
*/
public function test_interface_game_053() {
// responder003 is the POV player, so if you need to fake
// login as a different player e.g. to submit an attack, always
// return to responder003 as soon as you've done so
$this->game_number = 53;
$_SESSION = $this->mock_test_user_login('responder003');
$gameId = $this->verify_api_createGame(
array(1, 1, 1, 1, 1, 1, 1, 1, 1),
'responder003', 'responder004', 'SailorMur', 'Giant', 3
);
$expData = $this->generate_init_expected_data_array($gameId, 'responder003', 'responder004', 3, 'SPECIFY_DICE');
$expData['gameSkillsInfo'] = $this->get_skill_info(array('Giant', 'Poison', 'Shadow', 'Stinger', 'TimeAndSpace', 'Trip', 'Turbo'));
$expData['playerDataArray'][0]['button'] = array('name' => 'SailorMur', 'recipe' => 'g(10) sp(12) t(4) (10/20) ^(X)!', 'originalRecipe' => 'g(10) sp(12) t(4) (10/20) ^(X)!', 'artFilename' => 'BMdefaultRound.png');
$expData['playerDataArray'][1]['button'] = array('name' => 'Giant', 'recipe' => '(20) (20) (20) (20) (20) (20)', 'originalRecipe' => '(20) (20) (20) (20) (20) (20)', 'artFilename' => 'giant.png');
$expData['playerDataArray'][0]['swingRequestArray'] = array('X' => array(4, 20));
$expData['playerDataArray'][0]['optRequestArray'] = array('3' => array(10, 20));
$expData['playerDataArray'][1]['waitingOnAction'] = FALSE;
$expData['playerDataArray'][0]['activeDieArray'] = array(
array('value' => NULL, 'sides' => 10, 'skills' => array('Stinger'), 'properties' => array(), 'recipe' => 'g(10)', 'description' => 'Stinger 10-sided die'),
array('value' => NULL, 'sides' => 12, 'skills' => array('Shadow', 'Poison'), 'properties' => array(), 'recipe' => 'sp(12)', 'description' => 'Shadow Poison 12-sided die'),
array('value' => NULL, 'sides' => 4, 'skills' => array('Trip'), 'properties' => array(), 'recipe' => 't(4)', 'description' => 'Trip 4-sided die'),
array('value' => NULL, 'sides' => NULL, 'skills' => array(), 'properties' => array(), 'recipe' => '(10/20)', 'description' => 'Option Die (with 10 or 20 sides)'),
array('value' => NULL, 'sides' => NULL, 'skills' => array('TimeAndSpace', 'Turbo'), 'properties' => array(), 'recipe' => '^(X)!', 'description' => 'TimeAndSpace Turbo X Swing Die'),
);
$expData['playerDataArray'][1]['activeDieArray'] = array(
array('value' => NULL, 'sides' => 20, 'skills' => array(), 'properties' => array(), 'recipe' => '(20)', 'description' => '20-sided die'),
array('value' => NULL, 'sides' => 20, 'skills' => array(), 'properties' => array(), 'recipe' => '(20)', 'description' => '20-sided die'),
array('value' => NULL, 'sides' => 20, 'skills' => array(), 'properties' => array(), 'recipe' => '(20)', 'description' => '20-sided die'),
array('value' => NULL, 'sides' => 20, 'skills' => array(), 'properties' => array(), 'recipe' => '(20)', 'description' => '20-sided die'),
array('value' => NULL, 'sides' => 20, 'skills' => array(), 'properties' => array(), 'recipe' => '(20)', 'description' => '20-sided die'),
array('value' => NULL, 'sides' => 20, 'skills' => array(), 'properties' => array(), 'recipe' => '(20)', 'description' => '20-sided die'),
);
$retval = $this->verify_api_loadGameData($expData, $gameId, 10);
////////////////////
// Move 01 - responder003 submits die values
$this->verify_api_submitDieValues(
array(1, 1),
$gameId, 1, array('X' => 5), array(3 => 10));
array_unshift($expData['gameActionLog'], array('timestamp' => 'TIMESTAMP', 'player' => 'responder003', 'message' => 'responder003 set swing values: X=5 and option dice: (10/20=10)'));
array_unshift($expData['gameActionLog'], array('timestamp' => 'TIMESTAMP', 'player' => '', 'message' => 'responder003 won initiative for round 1. Initial die values: responder003 rolled [g(10):1, sp(12):1, t(4):1, (10/20=10):1, ^(X=5)!:1], responder004 rolled [(20):1, (20):1, (20):1, (20):1, (20):1, (20):1]. responder004\'s button has the "slow" button special, and cannot win initiative normally.'));
$expData['gameActionLogCount'] = 3;
$expData['gameState'] = 'START_TURN';
$expData['activePlayerIdx'] = 0;
$expData['playerWithInitiativeIdx'] = 0;
$expData['validAttackTypeArray'] = array('Power', 'Skill', 'Shadow', 'Trip');
$expData['playerDataArray'][0]['roundScore'] = 2.5;
$expData['playerDataArray'][0]['sideScore'] = -38.3;
$expData['playerDataArray'][1]['roundScore'] = 60;
$expData['playerDataArray'][1]['sideScore'] = 38.3;
$expData['playerDataArray'][0]['swingRequestArray'] = array();
$expData['playerDataArray'][0]['turboSizeArray'] = array("4" => array(4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20));
$expData['playerDataArray'][0]['activeDieArray'][0]['value'] = 1;
$expData['playerDataArray'][0]['activeDieArray'][1]['value'] = 1;
$expData['playerDataArray'][0]['activeDieArray'][2]['value'] = 1;
$expData['playerDataArray'][0]['activeDieArray'][3]['value'] = 1;
$expData['playerDataArray'][0]['activeDieArray'][3]['sides'] = 10;
$expData['playerDataArray'][0]['activeDieArray'][3]['description'] = 'Option Die (with 10 sides)';
$expData['playerDataArray'][0]['activeDieArray'][4]['value'] = 1;
$expData['playerDataArray'][0]['activeDieArray'][4]['sides'] = 5;
$expData['playerDataArray'][0]['activeDieArray'][4]['description'] = 'TimeAndSpace Turbo X Swing Die (with 5 sides)';
$expData['playerDataArray'][1]['activeDieArray'][0]['value'] = 1;
$expData['playerDataArray'][1]['activeDieArray'][1]['value'] = 1;
$expData['playerDataArray'][1]['activeDieArray'][2]['value'] = 1;
$expData['playerDataArray'][1]['activeDieArray'][3]['value'] = 1;
$expData['playerDataArray'][1]['activeDieArray'][4]['value'] = 1;
$expData['playerDataArray'][1]['activeDieArray'][5]['value'] = 1;
$retval = $this->verify_api_loadGameData($expData, $gameId, 10);
////////////////////
// Move 02 - responder003 Power attack using ^(X)!
// BUG: responder003 should not get another turn
$this->verify_api_submitTurn(
array(2),
'responder003 performed Power attack using [^(X=5)!:1] against [(20):1]; Defender (20) was captured; Attacker ^(X=5)! rerolled from 1. responder003 gets another turn because a Time and Space die rolled odd. Turbo die ^(X=5)! changed size from 5 to 10 sides, recipe changed from ^(X=5)! to ^(X=10)!, rolled 2. ',
$retval, array(array(0, 4), array(1, 0)),
$gameId, 1, 'Power', 0, 1, '', array(4 => 10));
// FIXME: add a check of the response data to this once the bug is fixed and it's easy to get the data
}
@cgolubi1, I've created a branch called 2253_turbo_timespace_interaction. I haven't yet tested it manually, but all the responder tests (including a version of the one you provided above with an altered verify_api_submitTurn) now pass.
You should be able to give me some response data based on this branch.
The same thing appears to be true for Mighty Time&Space dice, or at least for Mighty Time&Space Stinger dice, as seen in http://www.buttonweavers.com/ui/game.html?game=55794
I think it's likely that this TimeAndSpace bug is potentially caused by any skill that requires the attacking die to be replaced before being rolled. As well as Turbo (which has already been fixed), this includes Berserk, Mighty, Weak, Morphing, Mood, Mad.
Looks like I'll need to do some testing with CustomBMs to work out if this is true.
The actual fix should be pretty simple, since the major work was done for Turbo.
The only existing button (apart from RandomBM*) that combines TimeAndSpace with a skill that replaces the attacking die is
Coyote: f(1/4) (4/20) z(10,10) ^(U)? s(X)!
I tried a Coyote vs Coyote match, and after swing setting, I've hit the following error message:
"[22-Nov-2020 04:44:15 UTC] PHP Fatal error: Declaration of BMAttackShadow::validate_attack($game, array $attackers, array $defenders) must be compatible with BMAttackPower::validate_attack($game, array $attackers, array $defenders, array $args = Array) in /Volumes/Development/buttonmen/src/engine/BMAttackShadow.php on line 136"
Apparently, in PHP 7.2 and up (and I'm running either 7.2 or 7.3 at home), they've changed the warning to a fatal error. I'll open a new issue for that and put in a one line fix.
On the upside, though, testing with Coyote vs Coyote gives the expected behaviour for the TimeAndSpace Mood Swing die over 20 times in a row, so I'll exclude Mood/Mad from consideration.
http://buttonweavers.com/ui/game.html?game=27806
The SailorMur button features a ^(X)! die. When playing, we observed that the time & space rule (odd roll goes again) is applied to the value before the reroll instead of after the reroll.
Here is a case where irilyth got an extra turn but shouldn't have:
Here is a case where irilyth did not got an extra turn but should have: