billy is a small game engine lib meant as a boilerplate for our js13k 2018 entry.


0.0.143 years ago3 years agoMinified + gzip package size for @darkapuch/billy in KB


billy 🐱

billy is a small game engine lib meant as a boilerplate for our js13k 2018 entry.


npm i @darkapuch/billy



billy implements a basic Entity-Component-Systems (ECS) pattern that allows you to create game logic in a lightweight and modular way.

To use it, first create an EntityManager :

import { EntityManager } from "@darkapuch/billy";

const em = new EntityManager();

In an ECS, Entities are simply a collection of components, and components are just data structures.

To create our first component type, we just need to declare a constructor :

function Mortal(maxHealth) {
    this.health = maxHealth;
    this.maxHealth = maxHealth;

We could use the class syntax but since we're not going to add any method, a function is less characters than a class with a constructor inside.

(We want to keep character count as low as possible for js13k. We could use a transpiler to convert the class to a function but they usually add a lot of logic to ensure the correct es6 class behaviour.)

Once your component type is ready, you can use it in your entities.

To create an entity, use em.spawn :

// Create a new entity with 100 health points
em.spawn([new Mortal(100)]);

em.spawn takes in an array of components. Be careful though, only one component of each type can be used. If you add severl components of the same type, only the last one will be taken into account.

Now we can create some logic. Enter systems :

setInterval( () => {
    em.query([Mortal])                      // Query from the EM to get only entities with a Mortal component
      .forEach( entity => {                 // Iterate over them
        const m = entity.get(Mortal);       // Extract the Mortal component
        m.health--;                         // Decrement its health
        if (m.health <= 0) {
            console.log("Entity died :(");  // oh no ...
            entity.delete();                // We can delete you now ...

In this example, every second, we tell the EM to run a function on every entity that has a Mortal component.

If you find any bugs or have a feature request, please open an issue on github!

The npm package download data comes from npm's download counts api and package details come from npms.io.