Code does not work on real microbits (#1723)

Radio packets are not received when while() loop in button callback waits for health status of first infected. That results in master waiting in while loop forever.
Added "Infecting" state. Master sends infect messages in forever loop in non-blocking way.
Another bug is in call to Math.randomRange while selecting patientZero. randomRange returns number incusive with boundaries. This results in accessing players array beyond end.
This commit is contained in:
Michal 2018-12-11 16:08:05 +01:00 committed by Peli de Halleux
parent 3413ecb935
commit a0313dad34

View File

@ -107,6 +107,7 @@ const TRANSMISSIONPROB = 40; // % probability to transfer disease
enum GameState {
Stopped,
Pairing,
Infecting,
Running,
Over
}
@ -191,6 +192,7 @@ function gameFace() {
else
basic.showIcon(paired ? GameIcons.Paired : GameIcons.Pairing, 1);
break;
case GameState.Infecting:
case GameState.Running:
switch (health) {
case HealthState.Dead:
@ -257,18 +259,11 @@ input.onButtonPressed(Button.AB, () => {
// launch game
if (state == GameState.Pairing) {
// pick 1 player and infect him
patientZero = players[Math.randomRange(0, players.length)];
while (patientZero.health == HealthState.Healthy) {
radio.sendValue("infect", patientZero.id);
basic.pause(100);
}
// all ready
state = GameState.Running;
patientZero = players[Math.randomRange(0, players.length - 1)];
// infecting message needs to be confirmed by
// the player
state = GameState.Infecting;
serial.writeLine(`game started ${players.length} players`);
// show startup
basic.showIcon(GameIcons.Dead);
} // end game
else if (state == GameState.Running) {
gameOver();
@ -360,6 +355,17 @@ basic.forever(() => {
serial.writeLine(`pairing ${players.length} players`);
basic.pause(500);
break;
case GameState.Infecting:
if (patientZero.health == HealthState.Healthy) {
radio.sendValue("infect", patientZero.id);
basic.pause(100);
} else {
serial.writeLine(`patient ${patientZero.id} infected`);
// show startup
basic.showIcon(GameIcons.Dead);
state = GameState.Running;
}
break;
case GameState.Running:
for (const p of players) {
radio.sendValue("h" + p.id, p.health);
@ -380,6 +386,9 @@ basic.forever(() => {
else if (infectedBy > -1)
radio.sendValue("health", health);
break;
case GameState.Infecting:
radio.sendValue("health", health);
break;
case GameState.Running:
// update health status
if (health != HealthState.Healthy && input.runningTime() - infectedTime > DEATH)
@ -402,4 +411,4 @@ basic.showIcon(GameIcons.Pairing)
```package
radio
```
```