Demo | Versions | MessageBoard
An event library that communicates using MessageChannel.
- Support event communication across workers
- Powerful ts type support, support event names and parameter type hints for on, emit and other functions
- Support static call, new call, inheritance call and binding use
- Support to get whether the configuration triggers the last emit event before on
- Support head, once, headOnce, off, clear methods (subsequent may consider adding logic such as index, order, but may increase the package size)
- Easy to use, does not depend on any third-party library
npm i mc-event
Use MessageChannel for cross-worker communication
In worker (worker.js)
import MCEvent from 'mc-event';
async function workerMain () {
const e = await MCevents.copy();
e.on('test', (v) => {console.log('Worker receive', v);});
e.emit('test', 'worker data');
}
workerMain();
Main thread
import MCEvent from 'mc-event';
const e = new MCEvent();
const worker = new Worker('worker.js'); // Fill in the real worker or use vite import syntax to import the worker
e.into(worker)
e.on('test', (v) => {console.log('Main receive', v);});
e.emit('test', 'main data');
In worker (worker.js)
// id can be agreed upon or passed using worker message
const e = await MCEvent.copy(id);
e.emitTransfer('test', {
data: [{
stream: readableStream, // Transferable to be transferred
}],
transfer: [readableStream]
})
MCEvent Also Support all Usages in this Section
import {Events} from 'mc-event';
Events.on('hello', (v) => {
console.log('Say ' + v);
});
Events.emit('hello', 'Hi');
const e = new Events<{
aa: [string, number, ...any[]],
bb: [{a: string}],
}>();
e.on('aa', (a1, a2, a3) => {
// Here it will be inferred that a1 is string, a2 is number, a3 is any
});
e.on('bb', (v, v2) => {
v.a; // here it will be inferred that v is {a:string}
// v2 will report an error
});
e.on('cc', () => { // error, cc does not exist
});
e.emit('bb', {a: '1', b: 2}); // attribute b will report an error
const e = new Events();
e.on('hello', (v) => {
console.log('Say ' + v);
});
e.emit('hello', 'Hi');
class Test extends Events {
test () {
this.on('hello', () => {console.log('hello');});
this.emit('hello');
}
}
Generics + inheritance
class Test extends Events<{
aa: [string, number, ...any[]],
bb: [{a: string}],
}> {
//...
}
const a = {};
events.bind(a);
a.on('hello', () => {console.log('hello');});
a.emit('hello');
binding + generics
const a: Events<{aa: [string]}> & {
[prop: string]: any;
} = {
};
events.bind(a);
a.on('aa', (v) => {console.log('hello', v);});
a.emit('aa');
const e = new Events();
e.once('hello', (v) => {console.log('once', v);}); // Only trigger once
e.head('hello', (v) => {console.log('head', v);}); // Put the event in the head
e.headOnce('hello', (v) => {console.log('head', v);}); // combine the above two
const handler = (v) => {console.log(v);}
e.on('hello', handler);
e.off('hello', handler); // Remove a single event listener
e.clear('hello'); // Remove all listeners for the entire event
global open
events.usePrevEmit = true;
events.emit('hello', 'hi');
events.on('hello', (v) => {console.log(v);});
turn on or off for an object
const e = new Events();
e.usePrevEmit = false;
e.emit('hello', 'hi');
e.on('hello', (v) => {console.log(v);}); // will not trigger hello
If you only want to trigger on static calls, you can write like this
Events._.usePrevEmit = true;
Events.onWait('xxx').then();
const e = new Events();
e.onWait('xxx').then();