import { HarmonixRegionManager, IRegionManager, HarmonixViewDefinition } from "@uxland/harmonix"; import { PluginInfo } from "../../handle-plugins"; import { IRegion } from "@uxland/regions"; import { shellRegions, clinicalMonitoringRegions, activityHistoryRegions, administrativeManagementRegions } from "./regions"; import { PrimariaBroker } from "../broker/primaria-broker"; import { BROKER_EVENTS } from "../broker/broker-events"; export interface PrimariaRegionManager extends HarmonixRegionManager { regions: { shell: typeof shellRegions; clinicalMonitoring: typeof clinicalMonitoringRegions; activityHistory: typeof activityHistoryRegions; administrativeManagement: typeof administrativeManagementRegions; }; registerQuickAction(view: HarmonixViewDefinition): Promise; registerNavigationMenu(view: HarmonixViewDefinition): Promise; registerMainView(view: HarmonixViewDefinition): Promise; activateMainView(viewId: string): Promise; activatePluginView(regionName: string, pluginId: string, viewId: string): Promise; getCurrentMainViewActive(): string | undefined; _destroy(): void; } class RegionManagerProxy implements PrimariaRegionManager { regions = { shell: shellRegions, clinicalMonitoring: clinicalMonitoringRegions, activityHistory: activityHistoryRegions, administrativeManagement: administrativeManagementRegions, }; constructor( private pluginInfo: PluginInfo, private regionManager: IRegionManager, private broker: PrimariaBroker, ) {} /** * Register a view in a specific region. * * @param {string} regionName - The name of the region to register the view with. * @param {HarmonixViewDefinition} view - The view definition to be registered. * @return {Promise} A promise that resolves when the view is successfully registered. */ async registerView(regionName: string, view: HarmonixViewDefinition): Promise { const key = `${this.pluginInfo.pluginId}::${view.id}`; await this.regionManager.registerViewWithRegion(regionName, key, view); this.activateIfDefault(regionName, key, view); } /** * Removes a view from a specific region. * * @param {string} regionName - The name of the region to remove the view from. * @param {string} viewId - The ID of the view to be removed. * @return {Promise} A promise that resolves when the view is successfully removed. */ async removeView(regionName: string, viewId: string): Promise { await this.regionManager.unregisterViewFromRegion(regionName, `${this.pluginInfo.pluginId}::${viewId}`); } /** * Activates a view in a specific region. * * @param {string} regionName - The name of the region where the view is located. * @param {string} viewId - The ID of the view to be activated. * @return {Promise} A promise that resolves when the view is successfully activated. */ activateView(regionName: string, viewId: string): Promise { this.regionManager.getRegion(regionName).activate(`${this.pluginInfo.pluginId}::${viewId}`); if (regionName === this.regions.shell.main) this._notifyMainViewChanged(viewId); return Promise.resolve(); } /** * Deactivates a view in a specific region. * * @param {string} regionName - The name of the region where the view is located. * @param {string} viewId - The ID of the view to be deactivated. * @return {Promise} A promise that resolves when the view is successfully deactivated. */ deactivateView(regionName: string, viewId: string): Promise { this.regionManager.getRegion(regionName).deactivate(`${this.pluginInfo.pluginId}::${viewId}`); return Promise.resolve(); } /** * Retrieves a region by its name. * * @param {string} regionName - The name of the region to retrieve. * @return {Promise} A promise that resolves to the retrieved region. */ getRegion(regionName: string): Promise { return Promise.resolve(this.regionManager.getRegion(regionName)); } /** * Checks if a view with the given ID exists in a specific region. * * @param {string} regionName - The name of the region to check. * @param {string} viewId - The ID of the view to check for. * @return {Promise} A promise that resolves to true if the view exists, false otherwise. */ containsView(regionName: string, viewId: string) { const region = this.regionManager.getRegion(regionName); return Promise.resolve(region?.containsView(`${this.pluginInfo.pluginId}::${viewId}`)); } /** * Checks if a view with the given ID is active in a specific region. * * @param {string} regionName - The name of the region to check. * @param {string} viewId - The ID of the view to check for. * @return {Promise} A promise that resolves to true if the view is active, false otherwise. */ isViewActive(regionName: string, viewId: string) { const region = this.regionManager.getRegion(regionName); const isViewActive = region.currentActiveViews.some((view) => view.id === viewId); return Promise.resolve(isViewActive); } async registerQuickAction(view: HarmonixViewDefinition): Promise { await this.regionManager.registerViewWithRegion(this.regions.shell.quickActions, `${this.pluginInfo.pluginId}::${view.id}`, view); } async registerNavigationMenu(view: HarmonixViewDefinition): Promise { await this.regionManager.registerViewWithRegion(this.regions.shell.navigationMenu, `${this.pluginInfo.pluginId}::${view.id}`, view); } async registerMainView(view: HarmonixViewDefinition): Promise { await this.regionManager.registerViewWithRegion(this.regions.shell.main, `${this.pluginInfo.pluginId}::${view.id}`, view); } activateMainView(viewId: string): Promise { this.regionManager.getRegion(this.regions.shell.main).activate(`${this.pluginInfo.pluginId}::${viewId}`); this._notifyMainViewChanged(viewId); return Promise.resolve(); } /** * Activates a view that was registered by another plugin. * * Unlike `activateView`, which always prefixes with the calling plugin's id, this method * lets an orchestrator activate views owned by a different plugin by passing the owner's * pluginId explicitly. Use only when crossing plugin boundaries. * * @param {string} regionName - The name of the region where the view is located. * @param {string} pluginId - The id of the plugin that registered the view. * @param {string} viewId - The id of the view to be activated. * @return {Promise} A promise that resolves when the view is successfully activated. */ activatePluginView(regionName: string, pluginId: string, viewId: string): Promise { this.regionManager.getRegion(regionName).activate(`${pluginId}::${viewId}`); if (regionName === this.regions.shell.main) this._notifyMainViewChanged(viewId); return Promise.resolve(); } getCurrentMainViewActive() { const mainView = this.regionManager.getRegion(this.regions.shell.main).currentActiveViews[0] as HarmonixViewDefinition; return mainView?.id; } /** * Activates a view if it is marked as default and the region currently has no active views. * * @param {string} regionName - The name of the region to activate the view in. * @param {string} key - The key of the view to activate. * @param {HarmonixViewDefinition} view - The view to activate. * @return {void} */ activateIfDefault(regionName: string, key: string, view: HarmonixViewDefinition) { if (!(view as any).isDefault) return; const region = this.regionManager.getRegion(regionName); if (!region || typeof (region as any).activate !== "function") return; const hasActiveView = region.currentActiveViews?.length > 0; if (!hasActiveView) { (region as any).activate(key); } } _notifyMainViewChanged(viewId: string) { this.broker.publish(BROKER_EVENTS.shell.mainViewChanged, { viewId }); } _destroy() { this.regionManager.destroy(); } } /** * Creates a proxy for the region manager with the given plugin info and region manager instance. * * @param {PluginInfo} pluginInfo - The plugin information. * @param {IRegionManager} regionManager - The region manager instance. * @return {HarmonixRegionManager} The created region manager proxy. */ export const createRegionManagerProxy = ( pluginInfo: PluginInfo, regionManager: IRegionManager, broker: PrimariaBroker, ): PrimariaRegionManager => new RegionManagerProxy(pluginInfo, regionManager, broker);