README
π¬ Miski ECS
Miski: Quechuan adjective meaning "sweet".
ECS: Entity-Component-System; A software architecture pattern.
Miski ECS: A sweet ECS architecture written in Typescript.
β οΈ Miski is currently in alpha. Expect breaking changes every version until beta.
Contents
- Purpose
- Features
- Install
- API Reference
- Demos
- Benchmarks
- Building
- To-Do
- Contributing
- Feature Requests
- Acknowledgements
- License
Purpose
Miski's purpose is to provide a stable, user-friendly ECS architecture for modern Javascript projects.
Goals
- To provide good and predictable performance
- To provide a developer-friendly and user-friendly API
- To provide a clean, readable, self-documenting, open-source codebase
Not Goals
Because Miski is designed to be used inside other projects, we'll let those devs configure bundling and tune performance to suit their needs, therefore the following are not goals of this project:
- To be the fastest or smallest ECS on the web
- To provide polyfills, workarounds, or older browser support for modern ECMAScript features
Features
- Simple, human-friendly API
- Modern ES2020 data-oriented Typescript codebase
- No dependencies
- Memory-friendly archetype-based ECS model
- Ability to use more than 32 components in one world using Uint32Array bitfields
- Basic serialization methods (
world.load
&world.save
) - Fast, cache-friendly ArrayBuffer-based component data storage
- Define components and queries once, reuse them across multiple worlds
AND
,OR
,NOT
operators in Queriesworld.getQueryEntered
&world.getQueryExited
methods
Install
The javascript module miski.min.js
is found in the ./dist
folder, along with a sourcemap file and typescript definitions .d.ts
file.
import { createComponent, createQuery, createSystem, createWorld } from './miski.min.js';
See API Reference below for a complete list of named exports.
Various type definitions are also exported - see index.ts for a complete list.
API Reference
This is the complete API:
𧩠Components // Schema = Record<string, TypedArrayConstructor>. E.g., { r: Uint8ClampedArray, g: Uint8ClampedArray, b: Uint8ClampedArray };
createComponent: <T extends Schema<T>>(spec: ComponentSpec<T>) => Component<T>;
π Queries
createQuery: (spec: QuerySpec) => Query;
π Systems // optional but helps with type safety - A system is a function of any arity where the first parameter is the World
createSystem: <T, U>(system: System<T, U>) => (world: World) => (...args: U) => ReturnType<T>;
π World
createWorld: (spec: WorldSpec) => World;
β World info
world.capacity: number; // Maximum number of Entities
world.getVacancyCount: () => number; // Number of available (i.e., unused) Entities
world.version: string; // Miski build version
πΎ World Entity methods // ('Entity' is just a type alias for 'number')
world.createEntity: () => Entity | undefined;
world.destroyEntity: (entity: Entity) => boolean;
world.hasEntity: (entity: Entity) => boolean;
world.getEntityArchetype: (entity: Entity) => Archetype | undefined;
world.entityHasComponent: <T>(entity: Entity, component: Component<T>) => boolean;
𧩠World Component methods
world.addComponentToEntity: <T>(component: Component<T>, entity: Entity, props?: SchemaProps<T>) => boolean;
world.removeComponentFromEntity: <T>(component: Component<T>, entity: Entity) => boolean;
π World Query methods
world.getQueryResult: (query: Query) => [Entity[], ComponentRecord];
world.getQueryEntered: (query: Query) => Entity[];
world.getQueryExited: (query: Query) => Entity[];
πΎ World serialization methods
world.load: (data: MiskiData) => boolean;
world.save: () => Readonly<MiskiData>;
π§ World maintenance methods
world.refresh: () => void;
world.purgeCaches: () => void;
Demos
See ./demo
for demo code or the demo page for live examples.
Benchmarks
Soonβ’οΈ
Building
To build Miski from source, run:
npm run build
To-Do
Before Beta
- Finalise API
- Write comprehensive tests
- Write consistent code documentation throughout
Before 1.0.0
- Optimise performance
- Consistent code style throughout
Future
- Allow for "changed" in queries
- Multithreading support / playing nicely with WebWorkers / SharedArrayBuffers
- Proper Deno support
- Resizable/dynamic component data storage
- Object pooling where necessary
Contributing
Contributions are also welcome and invited. See CONTRIBUTING.md
for details.
Feature Requests
Feature requests are welcome and invited. Please open an issue on Github to make a request.
Acknowledgements
Miski is inspired by ape-ecs, BECSY, bitECS, ECSY, Geotic, HECS, and Wolf ECS.
License
© 2021-2022 P. Hughes. All rights reserved.
Miski ECS is released under the MIT license. See LICENSE
for further details.