From 5520ae8dcd7d309d172b00fe131707bf3afe1b9b Mon Sep 17 00:00:00 2001 From: Arun Madhavan Date: Thu, 2 Apr 2026 14:32:01 -0400 Subject: [PATCH 1/8] RDKEAPPRT-683: RemoteControl plugin API align with MW APIv3.4.2 --- accelerator-home-ui/settings.json | 2 +- accelerator-home-ui/src/api/RemoteControl.js | 42 +++++++++++++++---- .../FactoryResetConfirmationScreen.js | 2 +- .../src/screens/RcInformationScreen.js | 16 +++---- .../screens/SplashScreens/BluetoothScreen.js | 16 +++---- 5 files changed, 53 insertions(+), 25 deletions(-) diff --git a/accelerator-home-ui/settings.json b/accelerator-home-ui/settings.json index 768f608..624fba0 100644 --- a/accelerator-home-ui/settings.json +++ b/accelerator-home-ui/settings.json @@ -13,6 +13,6 @@ "log": true, "enableAppSuspended": true, "showVersion": false, - "version": "6.0.1" + "version": "6.0.2" } } diff --git a/accelerator-home-ui/src/api/RemoteControl.js b/accelerator-home-ui/src/api/RemoteControl.js index 1caf9f1..158419e 100644 --- a/accelerator-home-ui/src/api/RemoteControl.js +++ b/accelerator-home-ui/src/api/RemoteControl.js @@ -92,10 +92,9 @@ export default class RCApi { }) } - startPairing(timeout = 30, netType ) { + startPairing(timeout = 30) { return new Promise((resolve, reject) => { - //this.INFO("RCApi: startPairing netType " + netType + " timeout " + timeout); - this.thunder.call('org.rdk.RemoteControl', 'startPairing', { netType: netType, timeout: timeout }).then(result => { + this.thunder.call('org.rdk.RemoteControl', 'startPairing', { timeout: timeout, screenBindEnable:false }).then(result => { //this.INFO("RCApi: startPairing result: ", JSON.stringify(result)) resolve(result.success); }).catch(err => { @@ -103,10 +102,23 @@ export default class RCApi { Metrics.error(Metrics.ErrorType.OTHER,"RemoteControlApiError", "Error in Thunder RemoteControl startPairing "+JSON.stringify(err), false, null) reject(err); }); - resolve(true); }) } + stopPairing() { + return new Promise((resolve, reject) => { + this.INFO("RCApi: stopPairing"); + this.thunder.call('org.rdk.RemoteControl', 'stopPairing', {scanDisable: true}).then(result => { + this.INFO("RCApi: stopPairing result: " + JSON.stringify(result)) + resolve(result.success); + }).catch(err => { + this.ERR("RCApi: stopPairing error: " + JSON.stringify(err)); + Metrics.error(Metrics.ErrorType.OTHER, "RemoteControlApiError", "Error in Thunder RemoteControl stopPairing " + JSON.stringify(err), false, null) + reject(err); + }); + }); + } + initializeIRDB() { return new Promise((resolve, reject) => { /*TODO: implement when requirement comes.*/ @@ -186,10 +198,10 @@ export default class RCApi { }) } - findMyRemote(netType = 1, level = "mid") { + findMyRemote(level = "mid") { return new Promise((resolve, reject) => { - this.INFO("RCApi: findMyRemote netType:" + JSON.stringify(netType) + " level:" + JSON.stringify(level)); - this.thunder.call('org.rdk.RemoteControl', 'findMyRemote', { netType: netType, level: level }).then(result => { + this.INFO("RCApi: findMyRemote level:" + JSON.stringify(level)); + this.thunder.call('org.rdk.RemoteControl', 'findMyRemote', { level: level }).then(result => { this.INFO("RCApi: findMyRemote result: " + JSON.stringify(result)) resolve(result.success); }).catch(err => { @@ -200,6 +212,8 @@ export default class RCApi { }) } + // This is to reset the remote control firmware; not to be confused with factory reset of the device. + // This will not erase user data or settings on the device. factoryReset() { return new Promise((resolve, reject) => { this.INFO("RCApi: factoryReset"); @@ -213,4 +227,18 @@ export default class RCApi { }); }) } + + unpair(macAddressList) { + return new Promise((resolve, reject) => { + this.INFO("RCApi: unpair macAddressList:" + JSON.stringify(macAddressList)); + this.thunder.call('org.rdk.RemoteControl', 'unpair', { macAddressList: macAddressList }).then(result => { + this.INFO("RCApi: unpair result: " + JSON.stringify(result)) + resolve(result.success); + }).catch(err => { + this.ERR("RCApi: unpair error: " + JSON.stringify(err)); + Metrics.error(Metrics.ErrorType.OTHER, "RemoteControlApiError", "Error in Thunder RemoteControl unpair " + JSON.stringify(err), false, null) + reject(err); + }); + }); + } } diff --git a/accelerator-home-ui/src/screens/OtherSettingsScreens/FactoryResetConfirmationScreen.js b/accelerator-home-ui/src/screens/OtherSettingsScreens/FactoryResetConfirmationScreen.js index 730d7fb..fa94a09 100644 --- a/accelerator-home-ui/src/screens/OtherSettingsScreens/FactoryResetConfirmationScreen.js +++ b/accelerator-home-ui/src/screens/OtherSettingsScreens/FactoryResetConfirmationScreen.js @@ -211,7 +211,7 @@ export default class RebootConfirmationScreen extends Lightning.Component { try { localStorage.clear(); this.LOG("localStorage cleared successfully"); - } + } catch (err) { this.ERR("Error clearing localStorage: " + JSON.stringify(err)); } diff --git a/accelerator-home-ui/src/screens/RcInformationScreen.js b/accelerator-home-ui/src/screens/RcInformationScreen.js index 03fe522..d382a48 100644 --- a/accelerator-home-ui/src/screens/RcInformationScreen.js +++ b/accelerator-home-ui/src/screens/RcInformationScreen.js @@ -244,16 +244,16 @@ export default class RCInformationScreen extends Lightning.Component { this.tag("SwVersion.Value").text.text = `N/A` this.tag("BatteryPercent.Value").text.text = `N/A` this.tag("RCUName.Value").text.text = `N/A` - //RCApi.get().deactivate().catch(err=> { console.error("RCInformationScreen error:", err)}); } onStatusCB(cbData) { // getStatus response has 'success' property; notification payload does not have that. + // this.LOG("RCInformationScreen onStatusCB cbData:" + JSON.stringify(cbData)); if ((cbData !== undefined) && ("success" in cbData ? cbData.success : true)) { let cbDatastatus if (Array.isArray(cbData.status)) { cbDatastatus = cbData.status[0] || {}; - } + } else if (cbData.status && typeof cbData.status === 'object') { cbDatastatus = cbData.status; } @@ -283,14 +283,14 @@ export default class RCInformationScreen extends Lightning.Component { this.tag("BatteryPercent.Value").text.text = BatteryPercent this.tag("RCUName.Value").text.text = RemoteName } else { - if(cbDatastatus.pairingState != "SEARCHING" && cbDatastatus.pairingState != "PAIRING" ) { - for(let i=0;i { + if (cbDatastatus.pairingState === "IDLE" || cbDatastatus.pairingState === "FAILED") { + // after 2 seconds, initiate pairing flow if status is IDLE, as there is no paired device. + this.scanTrigger && Registry.clearTimeout(this.scanTrigger); + this.scanTrigger = Registry.setTimeout(() => { + RCApi.get().startPairing().catch(err => { this.ERR("RCInformationScreen startPairing error: " + JSON.stringify(err)); }); - } + }, 2000); } } } diff --git a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js index 847e366..afbb7b2 100644 --- a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js +++ b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js @@ -196,13 +196,13 @@ export default class BluetoothScreen extends Lightning.Component { } onStatusCB(cbData) { - //console.log("BluetoothScreen cbData:", JSON.stringify(cbData)); + //console.log("BluetoothScreen cbData:" + JSON.stringify(cbData)); // getStatus response has 'success' property; notification payload does not have that. if ((cbData !== undefined) && (cbData.hasOwnProperty("success") ? cbData.success : true)) { let cbDatastatus if (Array.isArray(cbData.status)) { cbDatastatus = cbData.status[0] || {}; - } + } else if (cbData.status && typeof cbData.status === 'object') { cbDatastatus = cbData.status; } @@ -226,14 +226,14 @@ export default class BluetoothScreen extends Lightning.Component { } }) } else { - if(cbDatastatus.pairingState != "SEARCHING" && cbDatastatus.pairingState != "PAIRING" ) { - for(let i=0;i { + if (cbDatastatus.pairingState === "IDLE" || cbDatastatus.pairingState === "FAILED") { + // after 2 seconds, initiate pairing flow if status is IDLE, as there is no paired device. + this.scanTrigger && Registry.clearTimeout(this.scanTrigger); + this.scanTrigger = Registry.setTimeout(() => { + RCApi.get().startPairing().catch(err => { this.ERR("RCInformationScreen startPairing error: " + JSON.stringify(err)); }); - } + }, 2000); } } } From 47df6367819c67c9bcab0a5ed99fa3007e976d99 Mon Sep 17 00:00:00 2001 From: Arun Madhavan Date: Thu, 2 Apr 2026 15:53:36 -0400 Subject: [PATCH 2/8] RDKEAPPRT-683: Fix the RCU pairing trigger timers --- accelerator-home-ui/src/api/RemoteControl.js | 6 +-- accelerator-home-ui/src/routes/routes.js | 2 +- .../src/screens/RcInformationScreen.js | 23 ++++++++---- .../screens/SplashScreens/BluetoothScreen.js | 37 +++++++++++-------- 4 files changed, 41 insertions(+), 27 deletions(-) diff --git a/accelerator-home-ui/src/api/RemoteControl.js b/accelerator-home-ui/src/api/RemoteControl.js index 158419e..0cb6978 100644 --- a/accelerator-home-ui/src/api/RemoteControl.js +++ b/accelerator-home-ui/src/api/RemoteControl.js @@ -94,8 +94,8 @@ export default class RCApi { startPairing(timeout = 30) { return new Promise((resolve, reject) => { - this.thunder.call('org.rdk.RemoteControl', 'startPairing', { timeout: timeout, screenBindEnable:false }).then(result => { - //this.INFO("RCApi: startPairing result: ", JSON.stringify(result)) + this.thunder.call('org.rdk.RemoteControl', 'startPairing', { timeout: timeout, screenBindEnable: false }).then(result => { + this.INFO("RCApi: startPairing result: " + JSON.stringify(result)) resolve(result.success); }).catch(err => { this.ERR("RCApi: startPairing error: " + JSON.stringify(err)); @@ -231,7 +231,7 @@ export default class RCApi { unpair(macAddressList) { return new Promise((resolve, reject) => { this.INFO("RCApi: unpair macAddressList:" + JSON.stringify(macAddressList)); - this.thunder.call('org.rdk.RemoteControl', 'unpair', { macAddressList: macAddressList }).then(result => { + this.thunder.call('org.rdk.RemoteControl', 'unpair', { macAddressList: macAddressList }).then(result => { this.INFO("RCApi: unpair result: " + JSON.stringify(result)) resolve(result.success); }).catch(err => { diff --git a/accelerator-home-ui/src/routes/routes.js b/accelerator-home-ui/src/routes/routes.js index 7f99815..dd67e76 100644 --- a/accelerator-home-ui/src/routes/routes.js +++ b/accelerator-home-ui/src/routes/routes.js @@ -207,7 +207,7 @@ export default { if ("ResidentApp" !== GLOBALS.selfClientName) { Metrics.page(request.hash) .then(success => { - console.log("successfully routed to page ==>", request.hash) + console.log("successfully routed to page ==>" + JSON.stringify(request.hash)) }) .catch(err => console.log("error in metrics.page", err)) } diff --git a/accelerator-home-ui/src/screens/RcInformationScreen.js b/accelerator-home-ui/src/screens/RcInformationScreen.js index d382a48..5b28250 100644 --- a/accelerator-home-ui/src/screens/RcInformationScreen.js +++ b/accelerator-home-ui/src/screens/RcInformationScreen.js @@ -16,7 +16,7 @@ * See the License for the specific language governing permissions and * limitations under the License. **/ -import { Lightning, Language, Router } from '@lightningjs/sdk' +import { Lightning, Language, Registry, Router } from '@lightningjs/sdk' import { COLORS } from './../colors/Colors' import { CONFIG } from '../Config/Config' import ThunderJS from 'ThunderJS' @@ -228,6 +228,7 @@ export default class RCInformationScreen extends Lightning.Component { } async _active() { + this.scanTrigger = null; await RCApi.get().activate().catch(err => { this.ERR("RCInformationScreen error: " + JSON.stringify(err)) }); await RCApi.get().getNetStatus().then(result => { this.INFO("RCInformationScreen getNetStatus: " + JSON.stringify(result)) @@ -244,6 +245,9 @@ export default class RCInformationScreen extends Lightning.Component { this.tag("SwVersion.Value").text.text = `N/A` this.tag("BatteryPercent.Value").text.text = `N/A` this.tag("RCUName.Value").text.text = `N/A` + if (this.scanTrigger) { + Registry.clearTimeout(this.scanTrigger); + } } onStatusCB(cbData) { @@ -282,15 +286,20 @@ export default class RCInformationScreen extends Lightning.Component { this.tag("SwVersion.Value").text.text = swVersion this.tag("BatteryPercent.Value").text.text = BatteryPercent this.tag("RCUName.Value").text.text = RemoteName + RCApi.get().findMyRemote().catch(err => { + this.ERR("RCInformationScreen findMyRemote error: " + JSON.stringify(err)) + }); } else { if (cbDatastatus.pairingState === "IDLE" || cbDatastatus.pairingState === "FAILED") { // after 2 seconds, initiate pairing flow if status is IDLE, as there is no paired device. - this.scanTrigger && Registry.clearTimeout(this.scanTrigger); - this.scanTrigger = Registry.setTimeout(() => { - RCApi.get().startPairing().catch(err => { - this.ERR("RCInformationScreen startPairing error: " + JSON.stringify(err)); - }); - }, 2000); + if (!this.scanTrigger) { + this.scanTrigger = Registry.setTimeout(() => { + RCApi.get().startPairing().catch(err => { + this.ERR("RCInformationScreen startPairing error: " + JSON.stringify(err)); + }); + this.scanTrigger = null; + }, 2000); + } } } } diff --git a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js index afbb7b2..c85d5b1 100644 --- a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js +++ b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js @@ -169,23 +169,22 @@ export default class BluetoothScreen extends Lightning.Component { Router.navigate('splash/language') } }) - }) - .catch(err => { - this.ERR(`SplashBluetoothScreen cant stopscan device : ${JSON.stringify(err)}`) - }) - }) .catch(err => { - this.ERR("SplashBluetoothScreen cant stopscan device : " + JSON.stringify(err)) + this.ERR(`SplashBluetoothScreen cant stopscan device : ${JSON.stringify(err)}`) }) }) .catch(err => { - this.ERR("SplashBluetoothScreen cant getpaired device : " + JSON.stringify(err)) + this.ERR("SplashBluetoothScreen cant stopscan device : " + JSON.stringify(err)) }) }) .catch(err => { - this.ERR(`SplashBluetoothScreen Can't pair device : ${JSON.stringify(err)}`) + this.ERR("SplashBluetoothScreen cant getpaired device : " + JSON.stringify(err)) }) + }) + .catch(err => { + this.ERR(`SplashBluetoothScreen Can't pair device : ${JSON.stringify(err)}`) + }) }) }) }) @@ -202,10 +201,10 @@ export default class BluetoothScreen extends Lightning.Component { let cbDatastatus if (Array.isArray(cbData.status)) { cbDatastatus = cbData.status[0] || {}; - } + } else if (cbData.status && typeof cbData.status === 'object') { cbDatastatus = cbData.status; - } + } if (cbDatastatus.remoteData.length) { //console.log("BluetoothScreen rcPairingApis RemoteData Length ", cbData.status.remoteData.length) cbDatastatus.remoteData.map(item => { @@ -228,12 +227,14 @@ export default class BluetoothScreen extends Lightning.Component { } else { if (cbDatastatus.pairingState === "IDLE" || cbDatastatus.pairingState === "FAILED") { // after 2 seconds, initiate pairing flow if status is IDLE, as there is no paired device. - this.scanTrigger && Registry.clearTimeout(this.scanTrigger); - this.scanTrigger = Registry.setTimeout(() => { - RCApi.get().startPairing().catch(err => { - this.ERR("RCInformationScreen startPairing error: " + JSON.stringify(err)); - }); - }, 2000); + if (!this.scanTrigger) { + this.scanTrigger = Registry.setTimeout(() => { + RCApi.get().startPairing().catch(err => { + this.ERR("SplashBluetoothScreen startPairing error: " + JSON.stringify(err)); + }); + this.scanTrigger = null; + }, 2000); + } } } } @@ -280,6 +281,7 @@ export default class BluetoothScreen extends Lightning.Component { _active() { this.initTimer() + this.scanTrigger = null; } pageTransition() { @@ -302,6 +304,9 @@ export default class BluetoothScreen extends Lightning.Component { if (this.RCTimeout) { Registry.clearTimeout(this.RCTimeout) } + if (this.scanTrigger) { + Registry.clearTimeout(this.scanTrigger) + } } static _states() { From 34ee6bea00a1aba71dcbc2e969ef5a6d22f2e94c Mon Sep 17 00:00:00 2001 From: Arun Madhavan Date: Thu, 2 Apr 2026 16:12:46 -0400 Subject: [PATCH 3/8] /RDKEAPPRT-683: stop the scan triggers after RCU pairing --- .../src/screens/RcInformationScreen.js | 17 ++++++++++++++--- .../screens/SplashScreens/BluetoothScreen.js | 14 ++++++++------ 2 files changed, 22 insertions(+), 9 deletions(-) diff --git a/accelerator-home-ui/src/screens/RcInformationScreen.js b/accelerator-home-ui/src/screens/RcInformationScreen.js index 5b28250..e1afd8e 100644 --- a/accelerator-home-ui/src/screens/RcInformationScreen.js +++ b/accelerator-home-ui/src/screens/RcInformationScreen.js @@ -235,6 +235,7 @@ export default class RCInformationScreen extends Lightning.Component { onStatusCBhandle = _thunder.on('org.rdk.RemoteControl', 'onStatus', data => { this.onStatusCB(data) }); this.onStatusCB(result); }).catch(err => this.ERR("RCInformationScreen error: " + JSON.stringify(err))); + this.findRemoteTrigger = true; } _inactive() { @@ -247,7 +248,9 @@ export default class RCInformationScreen extends Lightning.Component { this.tag("RCUName.Value").text.text = `N/A` if (this.scanTrigger) { Registry.clearTimeout(this.scanTrigger); + this.scanTrigger = null; } + this.findRemoteTrigger = false; } onStatusCB(cbData) { @@ -286,9 +289,12 @@ export default class RCInformationScreen extends Lightning.Component { this.tag("SwVersion.Value").text.text = swVersion this.tag("BatteryPercent.Value").text.text = BatteryPercent this.tag("RCUName.Value").text.text = RemoteName - RCApi.get().findMyRemote().catch(err => { - this.ERR("RCInformationScreen findMyRemote error: " + JSON.stringify(err)) - }); + if (this.findRemoteTrigger) { + this.findRemoteTrigger = false; + RCApi.get().findMyRemote().catch(err => { + this.ERR("RCInformationScreen findMyRemote error: " + JSON.stringify(err)) + }); + } } else { if (cbDatastatus.pairingState === "IDLE" || cbDatastatus.pairingState === "FAILED") { // after 2 seconds, initiate pairing flow if status is IDLE, as there is no paired device. @@ -300,6 +306,11 @@ export default class RCInformationScreen extends Lightning.Component { this.scanTrigger = null; }, 2000); } + } else if (cbDatastatus.pairingState === "COMPLETE") { + if (this.scanTrigger) { + Registry.clearTimeout(this.scanTrigger); + this.scanTrigger = null; + } } } } diff --git a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js index c85d5b1..79d3021 100644 --- a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js +++ b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js @@ -135,10 +135,6 @@ export default class BluetoothScreen extends Lightning.Component { } } - _active() { - this.timeout = 30; - } - _PairingApis() { //bluetoothApi.btactivate().then(enableResult =>{ // console.log('1') @@ -175,11 +171,11 @@ export default class BluetoothScreen extends Lightning.Component { }) }) .catch(err => { - this.ERR("SplashBluetoothScreen cant stopscan device : " + JSON.stringify(err)) + this.ERR("SplashBluetoothScreen getpairedDevices failed : " + JSON.stringify(err)) }) }) .catch(err => { - this.ERR("SplashBluetoothScreen cant getpaired device : " + JSON.stringify(err)) + this.ERR("SplashBluetoothScreen getConnectedDevices failed : " + JSON.stringify(err)) }) }) .catch(err => { @@ -235,6 +231,11 @@ export default class BluetoothScreen extends Lightning.Component { this.scanTrigger = null; }, 2000); } + } else if (cbDatastatus.pairingState === "COMPLETE") { + if (this.scanTrigger) { + Registry.clearTimeout(this.scanTrigger); + this.scanTrigger = null; + } } } } @@ -280,6 +281,7 @@ export default class BluetoothScreen extends Lightning.Component { } _active() { + this.timeout = 30; this.initTimer() this.scanTrigger = null; } From 2610642a37e0d975cfb59ac9d5d4aa498ae4a115 Mon Sep 17 00:00:00 2001 From: Arun Madhavan Date: Thu, 2 Apr 2026 19:20:30 -0400 Subject: [PATCH 4/8] RDKEAPPRT-683: fix the RCU re scanning logic leak. --- accelerator-home-ui/src/App.js | 8 ++++- .../src/screens/RcInformationScreen.js | 29 ++++++++++++++++--- .../screens/SplashScreens/BluetoothScreen.js | 27 ++++++++++++++--- 3 files changed, 55 insertions(+), 9 deletions(-) diff --git a/accelerator-home-ui/src/App.js b/accelerator-home-ui/src/App.js index 6a10881..c39a543 100644 --- a/accelerator-home-ui/src/App.js +++ b/accelerator-home-ui/src/App.js @@ -276,6 +276,12 @@ export default class App extends Router.App { if(GLOBALS.MiracastNotificationstatus && key.keyCode !== Keymap.Power && key.keyCode !== Keymap.Home ){ return false } else if ((key.keyCode == Keymap.Home || key.keyCode == Keymap.Escape) && !Router.isNavigating()) { + if (Router.getActiveHash().startsWith("splash")) { + if (Router.getActiveHash() !== "splash/language") { + Router.navigate("splash/language"); + } + return true; + } if (GLOBALS.topmostApp.includes("dac.native")) { this.jumpToRoute("apps"); } else if (GLOBALS.Miracastclientdevicedetails.state === "INITIATED" || GLOBALS.Miracastclientdevicedetails.state === "INPROGRESS ") { @@ -2868,4 +2874,4 @@ export default class App extends Router.App { } } } -} \ No newline at end of file +} diff --git a/accelerator-home-ui/src/screens/RcInformationScreen.js b/accelerator-home-ui/src/screens/RcInformationScreen.js index e1afd8e..ef9b666 100644 --- a/accelerator-home-ui/src/screens/RcInformationScreen.js +++ b/accelerator-home-ui/src/screens/RcInformationScreen.js @@ -269,6 +269,11 @@ export default class RCInformationScreen extends Lightning.Component { let RemoteName = []; let connectedStatus = []; let MacAddress = []; let swVersion = []; let BatteryPercent = []; + if (this.scanTrigger) { + Registry.clearTimeout(this.scanTrigger); + this.scanTrigger = null; + } + cbDatastatus.remoteData.map(item => { RemoteName.push(item.name) }) @@ -300,13 +305,29 @@ export default class RCInformationScreen extends Lightning.Component { // after 2 seconds, initiate pairing flow if status is IDLE, as there is no paired device. if (!this.scanTrigger) { this.scanTrigger = Registry.setTimeout(() => { - RCApi.get().startPairing().catch(err => { - this.ERR("RCInformationScreen startPairing error: " + JSON.stringify(err)); - }); this.scanTrigger = null; + RCApi.get().getNetStatus().then(result => { + let latestStatus = {}; + if (Array.isArray(result.status)) { + latestStatus = result.status[0] || {}; + } else if (result.status && typeof result.status === 'object') { + latestStatus = result.status; + } + + const latestHasRemoteData = Array.isArray(latestStatus.remoteData) && latestStatus.remoteData.length; + const latestInRetryState = latestStatus.pairingState === "IDLE" || latestStatus.pairingState === "FAILED"; + + if (!latestHasRemoteData && latestInRetryState) { + RCApi.get().startPairing().catch(err => { + this.ERR("RCInformationScreen startPairing error: " + JSON.stringify(err)); + }); + } + }).catch(err => { + this.ERR("RCInformationScreen getNetStatus before startPairing error: " + JSON.stringify(err)); + }); }, 2000); } - } else if (cbDatastatus.pairingState === "COMPLETE") { + } else { if (this.scanTrigger) { Registry.clearTimeout(this.scanTrigger); this.scanTrigger = null; diff --git a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js index 79d3021..6ae14c5 100644 --- a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js +++ b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js @@ -203,6 +203,10 @@ export default class BluetoothScreen extends Lightning.Component { } if (cbDatastatus.remoteData.length) { //console.log("BluetoothScreen rcPairingApis RemoteData Length ", cbData.status.remoteData.length) + if (this.scanTrigger) { + Registry.clearTimeout(this.scanTrigger); + this.scanTrigger = null; + } cbDatastatus.remoteData.map(item => { this.tag('Info').text.text = `paired with device ${item.name}` // Do not clear this.RCTimeout if need to run this in background to reconnect on loss. @@ -225,13 +229,28 @@ export default class BluetoothScreen extends Lightning.Component { // after 2 seconds, initiate pairing flow if status is IDLE, as there is no paired device. if (!this.scanTrigger) { this.scanTrigger = Registry.setTimeout(() => { - RCApi.get().startPairing().catch(err => { - this.ERR("SplashBluetoothScreen startPairing error: " + JSON.stringify(err)); - }); this.scanTrigger = null; + RCApi.get().getNetStatus().then(result => { + let latestStatus = {}; + if (Array.isArray(result.status)) { + latestStatus = result.status[0] || {}; + } else if (result.status && typeof result.status === 'object') { + latestStatus = result.status; + } + + const latestHasRemoteData = Array.isArray(latestStatus.remoteData) && latestStatus.remoteData.length; + const latestInRetryState = latestStatus.pairingState === "IDLE" || latestStatus.pairingState === "FAILED"; + if (!latestHasRemoteData && latestInRetryState) { + RCApi.get().startPairing().catch(err => { + this.ERR("SplashBluetoothScreen startPairing error: " + JSON.stringify(err)); + }); + } + }).catch(err => { + this.ERR("SplashBluetoothScreen getNetStatus before startPairing error: " + JSON.stringify(err)); + }); }, 2000); } - } else if (cbDatastatus.pairingState === "COMPLETE") { + } else { if (this.scanTrigger) { Registry.clearTimeout(this.scanTrigger); this.scanTrigger = null; From 791331733db5b5f9876c86bd2f2ab324f7254060 Mon Sep 17 00:00:00 2001 From: Arun Madhavan Date: Thu, 2 Apr 2026 19:30:00 -0400 Subject: [PATCH 5/8] RDKEAPPRT-683: fix the alignment issue - this change is introduced to fix the accidental route happening to menu page when RCU key is received from FTU --- accelerator-home-ui/src/App.js | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/accelerator-home-ui/src/App.js b/accelerator-home-ui/src/App.js index c39a543..2bac5cd 100644 --- a/accelerator-home-ui/src/App.js +++ b/accelerator-home-ui/src/App.js @@ -276,12 +276,12 @@ export default class App extends Router.App { if(GLOBALS.MiracastNotificationstatus && key.keyCode !== Keymap.Power && key.keyCode !== Keymap.Home ){ return false } else if ((key.keyCode == Keymap.Home || key.keyCode == Keymap.Escape) && !Router.isNavigating()) { - if (Router.getActiveHash().startsWith("splash")) { - if (Router.getActiveHash() !== "splash/language") { - Router.navigate("splash/language"); - } - return true; - } + if (Router.getActiveHash().startsWith("splash")) { + if (Router.getActiveHash() !== "splash/language") { + Router.navigate("splash/language"); + } + return true; + } if (GLOBALS.topmostApp.includes("dac.native")) { this.jumpToRoute("apps"); } else if (GLOBALS.Miracastclientdevicedetails.state === "INITIATED" || GLOBALS.Miracastclientdevicedetails.state === "INPROGRESS ") { From 8add25c150df64f3f9a749d40fe25bbd37466336 Mon Sep 17 00:00:00 2001 From: Arun Madhavan Date: Thu, 2 Apr 2026 19:35:26 -0400 Subject: [PATCH 6/8] RDKEAPPRT-683: fix typos and cleanup sequence --- accelerator-home-ui/src/screens/RcInformationScreen.js | 2 +- .../src/screens/SplashScreens/BluetoothScreen.js | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/accelerator-home-ui/src/screens/RcInformationScreen.js b/accelerator-home-ui/src/screens/RcInformationScreen.js index ef9b666..565303b 100644 --- a/accelerator-home-ui/src/screens/RcInformationScreen.js +++ b/accelerator-home-ui/src/screens/RcInformationScreen.js @@ -229,13 +229,13 @@ export default class RCInformationScreen extends Lightning.Component { async _active() { this.scanTrigger = null; + this.findRemoteTrigger = true; await RCApi.get().activate().catch(err => { this.ERR("RCInformationScreen error: " + JSON.stringify(err)) }); await RCApi.get().getNetStatus().then(result => { this.INFO("RCInformationScreen getNetStatus: " + JSON.stringify(result)) onStatusCBhandle = _thunder.on('org.rdk.RemoteControl', 'onStatus', data => { this.onStatusCB(data) }); this.onStatusCB(result); }).catch(err => this.ERR("RCInformationScreen error: " + JSON.stringify(err))); - this.findRemoteTrigger = true; } _inactive() { diff --git a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js index 6ae14c5..7f466e9 100644 --- a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js +++ b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js @@ -167,7 +167,7 @@ export default class BluetoothScreen extends Lightning.Component { }) }) .catch(err => { - this.ERR(`SplashBluetoothScreen cant stopscan device : ${JSON.stringify(err)}`) + this.ERR(`SplashBluetoothScreen can't stop scan device : ${JSON.stringify(err)}`) }) }) .catch(err => { @@ -327,6 +327,7 @@ export default class BluetoothScreen extends Lightning.Component { } if (this.scanTrigger) { Registry.clearTimeout(this.scanTrigger) + this.scanTrigger = null; } } From 65ec43f96a03810de3254fe283819d5a692d01b9 Mon Sep 17 00:00:00 2001 From: Arun Madhavan Date: Thu, 2 Apr 2026 19:42:16 -0400 Subject: [PATCH 7/8] RDKEAPPRT-683: initialize the var declared --- .../src/screens/SplashScreens/BluetoothScreen.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js index 7f466e9..1672f6d 100644 --- a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js +++ b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js @@ -194,7 +194,7 @@ export default class BluetoothScreen extends Lightning.Component { //console.log("BluetoothScreen cbData:" + JSON.stringify(cbData)); // getStatus response has 'success' property; notification payload does not have that. if ((cbData !== undefined) && (cbData.hasOwnProperty("success") ? cbData.success : true)) { - let cbDatastatus + let cbDatastatus = {}; if (Array.isArray(cbData.status)) { cbDatastatus = cbData.status[0] || {}; } From 641dae2c82efa4a64bbc7e54ddb61db6d54236c9 Mon Sep 17 00:00:00 2001 From: Arun Madhavan Date: Thu, 2 Apr 2026 20:05:40 -0400 Subject: [PATCH 8/8] fix(bluetooth-splash): prevent scanTrigger timer race across init/active lifecycle --- .../src/screens/SplashScreens/BluetoothScreen.js | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js index 1672f6d..bafc50e 100644 --- a/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js +++ b/accelerator-home-ui/src/screens/SplashScreens/BluetoothScreen.js @@ -35,6 +35,7 @@ export default class BluetoothScreen extends Lightning.Component { this.LOG = console.log; this.ERR = console.error; this.WARN = console.warn; + this.scanTrigger = null; } static _template() { @@ -201,13 +202,14 @@ export default class BluetoothScreen extends Lightning.Component { else if (cbData.status && typeof cbData.status === 'object') { cbDatastatus = cbData.status; } - if (cbDatastatus.remoteData.length) { + const remoteData = Array.isArray(cbDatastatus.remoteData) ? cbDatastatus.remoteData : []; + if (remoteData.length > 0) { //console.log("BluetoothScreen rcPairingApis RemoteData Length ", cbData.status.remoteData.length) if (this.scanTrigger) { Registry.clearTimeout(this.scanTrigger); this.scanTrigger = null; } - cbDatastatus.remoteData.map(item => { + remoteData.map(item => { this.tag('Info').text.text = `paired with device ${item.name}` // Do not clear this.RCTimeout if need to run this in background to reconnect on loss. // if (this.RCTimeout) { @@ -302,7 +304,9 @@ export default class BluetoothScreen extends Lightning.Component { _active() { this.timeout = 30; this.initTimer() - this.scanTrigger = null; + if (typeof this.scanTrigger === 'undefined') { + this.scanTrigger = null; + } } pageTransition() {