import { buildCondition, buildExpression, buildInvoke, } from '@avocado/behavior'; import {Latus} from '@latus/core'; import {normalize} from '@latus/socket'; import {expect} from 'chai'; let latus; let Entity; beforeEach(async () => { latus = Latus.mock({ '@avocado/behavior': require('@avocado/behavior'), '@avocado/entity': require('../src'), '@avocado/resource': require('@avocado/resource'), '@avocado/traits': require('@avocado/traits'), '@latus/socket': require('@latus/socket'), }); await Promise.all(latus.invokeFlat('@latus/core/starting')); ({Entity} = latus.get('%resources')); }); describe('Alive', () => { let entity; beforeEach(async () => { entity = await Entity.load({ traits: { Alive: {}, }, }); }); it('exists', async () => { expect(entity.is('Alive')).to.be.true; }); if ('client' !== process.env.SIDE) { it('can die', async () => { let isDying = false; entity.once('startedDying', () => { isDying = true; }); entity.life = 0; entity.tick(0); expect(isDying).to.be.true; }); } it('clamps life', async () => { entity.life = 120; expect(entity.life).to.equal(100); entity.maxLife = 50; expect(entity.life).to.equal(50); }); if ('client' !== process.env.SIDE) { it('can have a custom death condition', async () => { const entity = await Entity.load({ traits: { Alive: { params: { deathCondition: buildCondition('<=', [ buildExpression(['entity', 'life']), 10, ]), }, }, }, }); let isDying = false; entity.on('startedDying', () => { isDying = true; }); entity.tick(0); expect(isDying).to.be.false; entity.life = 10; entity.tick(0); expect(isDying).to.be.true; }); } it('runs actions on death', async () => { let didActions; const entity = await Entity.load({ traits: { Alive: { params: { deathActions: { type: 'expressions', expressions: [ buildInvoke(['entity', 'ded']), ], }, }, }, }, }); entity.ded = () => { didActions = true; }; const handle = setInterval(() => { entity.tick(); }, 16.66); await entity.die(); clearInterval(handle); expect(didActions).to.be.true; }); describe('Packets', () => { let entity2; beforeEach(async () => { entity2 = await Entity.load({ traits: { Alive: {}, }, }); }); it('generates and accepts life packets', async () => { entity.life = 80; entity.maxLife = 90; const packets = entity.trait('Alive').packets(); expect(packets).to.have.lengthOf(1); expect(packets[0][0]).to.equal('TraitUpdateAlive'); expect(packets[0][1]).to.deep.equal({life: 80, maxLife: 90}); entity2.trait('Alive').acceptPacket(normalize(latus, packets[0])); expect(entity2.life).to.equal(80); expect(entity2.maxLife).to.equal(90); }); if ('client' !== process.env.SIDE) { it('generates and accepts death packets', async () => { entity.life = 0; entity.tick(); const packets = entity.trait('Alive').packets(); expect(packets).to.have.lengthOf(2); expect(packets[0][0]).to.equal('Died'); expect(packets[1][0]).to.equal('TraitUpdateAlive'); expect(packets[1][1]).to.deep.equal({life: 0, maxLife: 100}); const promise = new Promise((resolve) => { entity2.once('startedDying', resolve); }); entity2.trait('Alive').acceptPacket(normalize(latus, packets[0])); entity2.trait('Alive').acceptPacket(normalize(latus, packets[1])); expect(entity2.life).to.equal(0); return promise; }); } }); });