diff --git a/packages/puter-js/src/modules/UI.js b/packages/puter-js/src/modules/UI.js index 849d4cad..abfd43c2 100644 --- a/packages/puter-js/src/modules/UI.js +++ b/packages/puter-js/src/modules/UI.js @@ -14,7 +14,11 @@ class AppConnection extends EventListener { // Whether the target app is open #isOpen; - constructor(messageTarget, appInstanceID, targetAppInstanceID) { + // Whether the target app uses the Puter SDK, and so accepts messages + // (Closing and close events will still function.) + #usesSDK; + + constructor(messageTarget, appInstanceID, targetAppInstanceID, usesSDK) { super([ 'message', // The target sent us something with postMessage() 'close', // The target app was closed @@ -23,6 +27,7 @@ class AppConnection extends EventListener { this.appInstanceID = appInstanceID; this.targetAppInstanceID = targetAppInstanceID; this.#isOpen = true; + this.#usesSDK = usesSDK; // TODO: Set this.#puterOrigin to the puter origin @@ -54,12 +59,21 @@ class AppConnection extends EventListener { }); } + // Does the target app use the Puter SDK? If not, certain features will be unavailable. + get usesSDK() { return this.#usesSDK; } + + // Send a message to the target app. Requires the target to use the Puter SDK. postMessage(message) { if (!this.#isOpen) { console.warn('Trying to post message on a closed AppConnection'); return; } + if (!this.#usesSDK) { + console.warn('Trying to post message to a non-SDK app'); + return; + } + this.messageTarget.postMessage({ msg: 'messageToApp', appInstanceID: this.appInstanceID, @@ -155,7 +169,7 @@ class UI extends EventListener { } if (this.parentInstanceID) { - this.#parentAppConnection = new AppConnection(this.messageTarget, this.appInstanceID, this.parentInstanceID); + this.#parentAppConnection = new AppConnection(this.messageTarget, this.appInstanceID, this.parentInstanceID, true); } // Tell the host environment that this app is using the Puter SDK and is ready to receive messages, @@ -374,7 +388,7 @@ class UI extends EventListener { } else if (e.data.msg === 'childAppLaunched') { // execute callback with a new AppConnection to the child - const connection = new AppConnection(this.messageTarget, this.appInstanceID, e.data.child_instance_id); + const connection = new AppConnection(this.messageTarget, this.appInstanceID, e.data.child_instance_id, e.data.uses_sdk); this.#callbackFunctions[e.data.original_msg_id](connection); } else{ diff --git a/src/IPC.js b/src/IPC.js index dbe18eb1..6e9b4cc3 100644 --- a/src/IPC.js +++ b/src/IPC.js @@ -90,17 +90,7 @@ window.addEventListener('message', async (event) => { $(target_iframe).attr('data-appUsesSDK', 'true'); // If we were waiting to launch this as a child app, report to the parent that it succeeded. - const child_launch_callback = window.child_launch_callbacks[event.data.appInstanceID]; - if (child_launch_callback) { - const parent_iframe = iframe_for_app_instance(child_launch_callback.parent_instance_id); - // send confirmation to requester window - parent_iframe.contentWindow.postMessage({ - msg: 'childAppLaunched', - original_msg_id: child_launch_callback.launch_msg_id, - child_instance_id: event.data.appInstanceID, - }, '*'); - delete window.child_launch_callbacks[event.data.appInstanceID]; - } + window.report_app_launched(event.data.appInstanceID, { uses_sdk: true }); // Send any saved broadcasts to the new app globalThis.services.get('broadcast').sendSavedBroadcastsTo(event.data.appInstanceID); diff --git a/src/helpers.js b/src/helpers.js index 5c0ff66a..1273bb2b 100644 --- a/src/helpers.js +++ b/src/helpers.js @@ -3523,3 +3523,19 @@ window.window_for_app_instance = (instance_id) => { window.iframe_for_app_instance = (instance_id) => { return $(window_for_app_instance(instance_id)).find('.window-app-iframe').get(0); }; + +// Run any callbacks to say that the app has launched +window.report_app_launched = (instance_id, { uses_sdk = true }) => { + const child_launch_callback = window.child_launch_callbacks[instance_id]; + if (child_launch_callback) { + const parent_iframe = iframe_for_app_instance(child_launch_callback.parent_instance_id); + // send confirmation to requester window + parent_iframe.contentWindow.postMessage({ + msg: 'childAppLaunched', + original_msg_id: child_launch_callback.launch_msg_id, + child_instance_id: instance_id, + uses_sdk: uses_sdk, + }, '*'); + delete window.child_launch_callbacks[instance_id]; + } +}