Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add event management class with event handling methods #5

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
119 changes: 85 additions & 34 deletions index.ts
Original file line number Diff line number Diff line change
@@ -1,65 +1,105 @@

export interface IEventHandlers {
[key: string]: Map<Function, boolean>;
[ key: string ]: Map<Function, boolean>;
}

export default class EventManagment {
export default class EventManagement {
private eventHandlersMap: IEventHandlers = {
'*': new Map(),
};
private isDebug: boolean = false;

private addEventHandler(eventName: string, callback: Function, isOnce: boolean = false) {
if (!this.eventHandlersMap[eventName]) {
this.eventHandlersMap[eventName] = new Map();
// Private methods

/**
* Add an event handler.
*
* @private
* @param {string} eventName - Name of the event.
* @param {Function} callback - Callback function for the event.
* @param {boolean} [isOnce=false] - Whether the callback is fired only once.
*/
private addEventHandler(eventName: string, callback: Function, isOnce: boolean = false): void {
if (!this.eventHandlersMap[ eventName ]) {
this.eventHandlersMap[ eventName ] = new Map();
}

if (callback && !this.eventHandlersMap[eventName].has(callback)) {
this.eventHandlersMap[eventName].set(callback, isOnce);
if (!this.eventHandlersMap[ eventName ].has(callback)) {
this.eventHandlersMap[ eventName ].set(callback, isOnce);
}
}

private callHandlers(eventName: string, payload: any, realEventName?: string) {
if (this.eventHandlersMap[eventName]) {
this.eventHandlersMap[eventName].forEach((isOnce: boolean, handler: Function) => {
handler && handler(payload, { eventName: realEventName || eventName, isOnce });
if (isOnce) {
this.off(eventName, handler);
}
});
}
/**
* Call registered handlers for a specific event.
*
* @private
* @param {string} eventName - Name of the event.
* @param {any} payload - Data payload for the event.
* @param {string} [realEventName] - Real event name.
*/
private callHandlers(eventName: string, payload: any, realEventName?: string): void {
this.eventHandlersMap[ eventName ]?.forEach((isOnce: boolean, handler: Function) => {
handler(payload, { eventName: realEventName || eventName, isOnce });
if (isOnce) {
this.off(eventName, handler);
}
});
}

public setDebug(isDebug: boolean) {
this.isDebug = isDebug;
// Public methods

/**
* Set debug mode for the event management.
*
* @param {boolean} isDebug - Whether to activate debug mode.
* @returns {EventManagement} - Returns the instance of EventManagement.
*/
public setDebug(isDebug: boolean): this {
this.isDebug = isDebug;
return this;
}

public on(eventName: string, callback: Function): EventManagment {
/**
* Register an event listener.
*
* @param {string} eventName - Name of the event.
* @param {Function} callback - Callback function for the event.
* @returns {EventManagement} - Returns the instance of EventManagement.
*/
public on(eventName: string, callback: Function): this {
this.addEventHandler(eventName, callback);

return this;
}

public once(eventName: string, callback: Function): EventManagment {
/**
* Register an event listener that listens only once.
*
* @param {string} eventName - Name of the event.
* @param {Function} callback - Callback function for the event.
* @returns {EventManagement} - Returns the instance of EventManagement.
*/
public once(eventName: string, callback: Function): this {
this.addEventHandler(eventName, callback, true);

return this;
}

public off(eventName: string, callback: Function): EventManagment {
if (!this.eventHandlersMap[eventName]) {
return this;
}

if (callback && this.eventHandlersMap[eventName].has(callback)) {
this.eventHandlersMap[eventName].delete(callback);
}

/**
* Remove an event listener.
*
* @param {string} eventName - Name of the event.
* @param {Function} callback - Callback function for the event.
* @returns {EventManagement} - Returns the instance of EventManagement.
*/
public off(eventName: string, callback: Function): this {
this.eventHandlersMap[ eventName ]?.delete(callback);
return this;
}

/**
* Emit/fire an event.
*
* @param {string} eventName - Name of the event.
* @param {any} [payload] - Data payload for the event.
*/
public emit(eventName: string, payload?: any): void {
if (this.isDebug) {
console.info(`[${this.constructor.name}]: Fires ${eventName}`);
Expand All @@ -69,13 +109,24 @@ export default class EventManagment {
this.callHandlers(eventName, payload);
}

/// Aliases:
// Aliases

/** Alias for emit method. */
public fire = this.emit;

/** Alias for on method. */
public listen = this.on;

/** Alias for on method. */
public subscribe = this.on;

/** Alias for off method. */
public remove = this.off;

/** Alias for off method. */
public unsubscribe = this.off;
///
}

const eventManager = new EventManagement();

export { eventManager };