Fixes for infection game (#2003)
* Fixes for infection game * Updated infection game to use message class * fixed whitespace * Changes to Message class
This commit is contained in:
parent
61aae94d8b
commit
24c42cc3e8
@ -69,8 +69,6 @@ As a result, it will not convert back to blocks.
|
|||||||
|
|
||||||
### ~
|
### ~
|
||||||
|
|
||||||
https://makecode.microbit.org/_gymCJCWPbiDu
|
|
||||||
|
|
||||||
## JavaScript code
|
## JavaScript code
|
||||||
|
|
||||||
```typescript
|
```typescript
|
||||||
@ -128,6 +126,16 @@ enum HealthState {
|
|||||||
Dead
|
Dead
|
||||||
}
|
}
|
||||||
|
|
||||||
|
enum MessageKind {
|
||||||
|
PairRequest,
|
||||||
|
PairConfirmation,
|
||||||
|
HealthSet,
|
||||||
|
HealthValue,
|
||||||
|
InitialInfect,
|
||||||
|
TransmitVirus,
|
||||||
|
GameState
|
||||||
|
}
|
||||||
|
|
||||||
const GameIcons = {
|
const GameIcons = {
|
||||||
Pairing: IconNames.Ghost,
|
Pairing: IconNames.Ghost,
|
||||||
Paired: IconNames.Happy,
|
Paired: IconNames.Happy,
|
||||||
@ -137,6 +145,52 @@ const GameIcons = {
|
|||||||
Healthy: IconNames.Happy
|
Healthy: IconNames.Happy
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class Message {
|
||||||
|
|
||||||
|
private _data: Buffer;
|
||||||
|
|
||||||
|
constructor(input?: Buffer) {
|
||||||
|
this._data = input || control.createBuffer(13);
|
||||||
|
}
|
||||||
|
|
||||||
|
get kind(): number {
|
||||||
|
return this._data.getNumber(NumberFormat.Int8LE, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
set kind(x: number) {
|
||||||
|
this._data.setNumber(NumberFormat.Int8LE, 0, x);
|
||||||
|
}
|
||||||
|
|
||||||
|
get fromSerialNumber(): number {
|
||||||
|
return this._data.getNumber(NumberFormat.Int32LE, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
set fromSerialNumber(x: number) {
|
||||||
|
this._data.setNumber(NumberFormat.Int32LE, 1, x);
|
||||||
|
}
|
||||||
|
|
||||||
|
get value(): number {
|
||||||
|
return this._data.getNumber(NumberFormat.Int32LE, 5);
|
||||||
|
}
|
||||||
|
|
||||||
|
set value(x: number) {
|
||||||
|
this._data.setNumber(NumberFormat.Int32LE, 5, x);
|
||||||
|
}
|
||||||
|
|
||||||
|
get toSerialNumber(): number {
|
||||||
|
return this._data.getNumber(NumberFormat.Int32LE, 9);
|
||||||
|
}
|
||||||
|
|
||||||
|
set toSerialNumber(x: number) {
|
||||||
|
this._data.setNumber(NumberFormat.Int32LE, 9, x);
|
||||||
|
}
|
||||||
|
|
||||||
|
send() {
|
||||||
|
radio.sendBuffer(this._data);
|
||||||
|
basic.pause(250);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const playerIcons = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
const playerIcons = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
||||||
class Player {
|
class Player {
|
||||||
id: number;
|
id: number;
|
||||||
@ -280,70 +334,76 @@ input.onButtonPressed(Button.AB, () => {
|
|||||||
})
|
})
|
||||||
|
|
||||||
radio.setGroup(42);
|
radio.setGroup(42);
|
||||||
radio.setTransmitSerialNumber(true)
|
radio.onReceivedBuffer(function (receivedBuffer: Buffer) {
|
||||||
radio.onDataPacketReceived(({ time, receivedNumber, receivedString, signal, serial: id }) => {
|
const incomingMessage = new Message(receivedBuffer);
|
||||||
|
const signal = radio.receivedPacket(RadioPacketProperty.SignalStrength);
|
||||||
if (master) {
|
if (master) {
|
||||||
if (receivedString == "pair") {
|
switch (incomingMessage.kind) {
|
||||||
// register player
|
case MessageKind.PairRequest:
|
||||||
let n = players.length;
|
// register player
|
||||||
let p = player(id);
|
let n = players.length;
|
||||||
// show player number if changed
|
player(incomingMessage.fromSerialNumber);
|
||||||
if (n != players.length) {
|
// show player number if changed
|
||||||
led.stopAnimation();
|
if (n != players.length) {
|
||||||
basic.showNumber(players.length);
|
basic.showNumber(players.length);
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (receivedString == "health") {
|
|
||||||
let p = player(id);
|
|
||||||
p.health = receivedNumber;
|
|
||||||
// check if all infected
|
|
||||||
if (allDead())
|
|
||||||
gameOver();
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (receivedString == "state") {
|
|
||||||
// update game state
|
|
||||||
state = receivedNumber as GameState;
|
|
||||||
} else if (infectedBy < 0 &&
|
|
||||||
receivedString == "infect"
|
|
||||||
&& receivedNumber == control.deviceSerialNumber()) {
|
|
||||||
// infected by master
|
|
||||||
infectedBy = 0; // infected my master
|
|
||||||
infectedTime = input.runningTime();
|
|
||||||
health = HealthState.Incubating;
|
|
||||||
serial.writeLine(`infected ${control.deviceSerialNumber()}`);
|
|
||||||
}
|
|
||||||
if (receivedString == "h" + control.deviceSerialNumber().toString() &&
|
|
||||||
health < receivedNumber) {
|
|
||||||
health = receivedNumber;
|
|
||||||
}
|
|
||||||
switch (state) {
|
|
||||||
case GameState.Pairing:
|
|
||||||
// medium range in pairing mode
|
|
||||||
if (!paired &&
|
|
||||||
receivedString == "paired"
|
|
||||||
&& receivedNumber == control.deviceSerialNumber()) {
|
|
||||||
// paired!
|
|
||||||
serial.writeLine(`player paired ==> ${control.deviceSerialNumber()}`)
|
|
||||||
paired = true;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
else if (paired && receivedString == "i" + control.deviceSerialNumber().toString()) {
|
|
||||||
playerIcon = receivedNumber;
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case GameState.Running:
|
case MessageKind.HealthValue:
|
||||||
// broadcast infection status
|
let p = player(incomingMessage.fromSerialNumber);
|
||||||
if (health == HealthState.Healthy && receivedString == "transmit") {
|
p.health = incomingMessage.value;
|
||||||
serial.writeLine(`signal: ${signal}`);
|
// check if all infected
|
||||||
if (signal > RSSI &&
|
if (allDead())
|
||||||
Math.randomRange(0, 100) > TRANSMISSIONPROB) {
|
gameOver();
|
||||||
infectedBy = receivedNumber;
|
break;
|
||||||
infectedTime = input.runningTime();
|
}
|
||||||
health = HealthState.Incubating;
|
} else {
|
||||||
|
switch (incomingMessage.kind) {
|
||||||
|
case MessageKind.GameState:
|
||||||
|
// update game state
|
||||||
|
state = incomingMessage.value as GameState;
|
||||||
|
break;
|
||||||
|
case MessageKind.InitialInfect:
|
||||||
|
if (infectedBy < 0 &&
|
||||||
|
incomingMessage.toSerialNumber == control.deviceSerialNumber()) {
|
||||||
|
// infected by master
|
||||||
|
infectedBy = 0; // infected my master
|
||||||
|
infectedTime = input.runningTime();
|
||||||
|
health = HealthState.Incubating;
|
||||||
|
serial.writeLine(`infected ${control.deviceSerialNumber()}`);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case MessageKind.HealthSet:
|
||||||
|
if (incomingMessage.toSerialNumber == control.deviceSerialNumber()) {
|
||||||
|
const newHealth = incomingMessage.value;
|
||||||
|
if (health < newHealth) {
|
||||||
|
health = newHealth;
|
||||||
}
|
}
|
||||||
} else if (health != HealthState.Dead
|
}
|
||||||
&& receivedString == "health" && signal > RSSI) {
|
break;
|
||||||
|
case MessageKind.PairConfirmation:
|
||||||
|
if (!paired && state == GameState.Pairing &&
|
||||||
|
incomingMessage.toSerialNumber == control.deviceSerialNumber()) {
|
||||||
|
// paired!
|
||||||
|
serial.writeLine(`player paired ==> ${control.deviceSerialNumber()}`)
|
||||||
|
playerIcon = incomingMessage.value;
|
||||||
|
paired = true;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case MessageKind.TransmitVirus:
|
||||||
|
if (state == GameState.Running) {
|
||||||
|
if (health == HealthState.Healthy) {
|
||||||
|
serial.writeLine(`signal: ${signal}`);
|
||||||
|
if (signal > RSSI &&
|
||||||
|
Math.randomRange(0, 100) > TRANSMISSIONPROB) {
|
||||||
|
infectedBy = incomingMessage.value;
|
||||||
|
infectedTime = input.runningTime();
|
||||||
|
health = HealthState.Incubating;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case MessageKind.HealthValue:
|
||||||
|
if (health != HealthState.Dead && signal > RSSI) {
|
||||||
game.addScore(1);
|
game.addScore(1);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@ -353,20 +413,27 @@ radio.onDataPacketReceived(({ time, receivedNumber, receivedString, signal, seri
|
|||||||
|
|
||||||
// main game loop
|
// main game loop
|
||||||
basic.forever(() => {
|
basic.forever(() => {
|
||||||
|
let message: Message;
|
||||||
if (master) {
|
if (master) {
|
||||||
switch (state) {
|
switch (state) {
|
||||||
case GameState.Pairing:
|
case GameState.Pairing:
|
||||||
// tell each player they are registered
|
// tell each player they are registered
|
||||||
for (const p of players) {
|
for (const p of players) {
|
||||||
radio.sendValue("paired", p.id);
|
message = new Message();
|
||||||
radio.sendValue("i" + p.id, p.icon);
|
message.kind = MessageKind.PairConfirmation;
|
||||||
|
message.value = p.icon;
|
||||||
|
message.toSerialNumber = p.id;
|
||||||
|
message.send();
|
||||||
}
|
}
|
||||||
serial.writeLine(`pairing ${players.length} players`);
|
serial.writeLine(`pairing ${players.length} players`);
|
||||||
basic.pause(500);
|
basic.pause(500);
|
||||||
break;
|
break;
|
||||||
case GameState.Infecting:
|
case GameState.Infecting:
|
||||||
if (patientZero.health == HealthState.Healthy) {
|
if (patientZero.health == HealthState.Healthy) {
|
||||||
radio.sendValue("infect", patientZero.id);
|
message = new Message();
|
||||||
|
message.kind = MessageKind.InitialInfect;
|
||||||
|
message.toSerialNumber = patientZero.id;
|
||||||
|
message.send();
|
||||||
basic.pause(100);
|
basic.pause(100);
|
||||||
} else {
|
} else {
|
||||||
serial.writeLine(`patient ${patientZero.id} infected`);
|
serial.writeLine(`patient ${patientZero.id} infected`);
|
||||||
@ -377,7 +444,11 @@ basic.forever(() => {
|
|||||||
break;
|
break;
|
||||||
case GameState.Running:
|
case GameState.Running:
|
||||||
for (const p of players) {
|
for (const p of players) {
|
||||||
radio.sendValue("h" + p.id, p.health);
|
message = new Message();
|
||||||
|
message.kind = MessageKind.HealthSet;
|
||||||
|
message.value = p.health;
|
||||||
|
message.toSerialNumber = p.id;
|
||||||
|
message.send();
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case GameState.Over:
|
case GameState.Over:
|
||||||
@ -385,18 +456,33 @@ basic.forever(() => {
|
|||||||
patientZero.show();
|
patientZero.show();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
radio.sendValue("state", state); // keep broadcasting the game state
|
message = new Message()
|
||||||
|
message.kind = MessageKind.GameState;
|
||||||
|
message.value = state;
|
||||||
|
message.send();
|
||||||
} else { // player loop
|
} else { // player loop
|
||||||
switch (state) {
|
switch (state) {
|
||||||
case GameState.Pairing:
|
case GameState.Pairing:
|
||||||
// broadcast player id
|
// broadcast player id
|
||||||
if (playerIcon < 0)
|
if (playerIcon < 0) {
|
||||||
radio.sendValue("pair", control.deviceSerialNumber());
|
message = new Message();
|
||||||
else if (infectedBy > -1)
|
message.kind = MessageKind.PairRequest;
|
||||||
radio.sendValue("health", health);
|
message.fromSerialNumber = control.deviceSerialNumber();
|
||||||
|
message.send();
|
||||||
|
} else if (infectedBy > -1) {
|
||||||
|
message = new Message();
|
||||||
|
message.kind = MessageKind.HealthValue;
|
||||||
|
message.fromSerialNumber = control.deviceSerialNumber();
|
||||||
|
message.value = health;
|
||||||
|
message.send();
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case GameState.Infecting:
|
case GameState.Infecting:
|
||||||
radio.sendValue("health", health);
|
message = new Message();
|
||||||
|
message.kind = MessageKind.HealthValue;
|
||||||
|
message.fromSerialNumber = control.deviceSerialNumber();
|
||||||
|
message.value = health;
|
||||||
|
message.send();
|
||||||
break;
|
break;
|
||||||
case GameState.Running:
|
case GameState.Running:
|
||||||
// update health status
|
// update health status
|
||||||
@ -405,9 +491,18 @@ basic.forever(() => {
|
|||||||
else if (health != HealthState.Healthy && input.runningTime() - infectedTime > INCUBATION)
|
else if (health != HealthState.Healthy && input.runningTime() - infectedTime > INCUBATION)
|
||||||
health = HealthState.Sick;
|
health = HealthState.Sick;
|
||||||
// transmit disease
|
// transmit disease
|
||||||
if (health == HealthState.Incubating || health == HealthState.Sick)
|
if (health == HealthState.Incubating || health == HealthState.Sick) {
|
||||||
radio.sendValue("transmit", playerIcon);
|
message = new Message();
|
||||||
radio.sendValue("health", health);
|
message.kind = MessageKind.TransmitVirus;
|
||||||
|
message.fromSerialNumber = control.deviceSerialNumber();
|
||||||
|
message.value = playerIcon;
|
||||||
|
message.send();
|
||||||
|
}
|
||||||
|
message = new Message();
|
||||||
|
message.kind = MessageKind.HealthValue;
|
||||||
|
message.fromSerialNumber = control.deviceSerialNumber();
|
||||||
|
message.value = health;
|
||||||
|
message.send();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
// show current animation
|
// show current animation
|
||||||
|
Loading…
Reference in New Issue
Block a user