Refresh device manager with options bridge status and propagate to popup

This commit is contained in:
hensm
2022-09-04 07:32:42 +01:00
parent 25bd72f0fe
commit 75f334f4ae
8 changed files with 75 additions and 37 deletions

View File

@@ -149,11 +149,15 @@ export default class ReceiverSelector extends TypedEventTarget<ReceiverSelectorE
}
/** Updates receiver devices displayed in the receiver selector. */
public update(devices: ReceiverDevice[], connectedSessionIds: string[]) {
public update(
devices: ReceiverDevice[],
isBridgeCompatible: boolean,
connectedSessionIds: string[]
) {
this.devices = devices;
this.messagePort?.postMessage({
subject: "popup:update",
data: { devices, connectedSessionIds }
data: { devices, isBridgeCompatible, connectedSessionIds }
});
}
@@ -205,8 +209,7 @@ export default class ReceiverSelector extends TypedEventTarget<ReceiverSelectorE
subject: "popup:init",
data: {
appInfo: this.appInfo,
pageInfo: this.pageInfo,
isBridgeCompatible: this.isBridgeCompatible
pageInfo: this.pageInfo
}
});
@@ -214,6 +217,7 @@ export default class ReceiverSelector extends TypedEventTarget<ReceiverSelectorE
subject: "popup:update",
data: {
devices: this.devices,
isBridgeCompatible: this.isBridgeCompatible,
defaultMediaType: this.defaultMediaType,
availableMediaTypes: this.availableMediaTypes
}

View File

@@ -1,14 +1,16 @@
import defaultOptions from "../defaultOptions";
import logger from "../lib/logger";
import options from "../lib/options";
import bridge, { BridgeInfo } from "../lib/bridge";
import { baseConfigStorage, fetchBaseConfig } from "../lib/chromecastConfigApi";
import defaultOptions from "../defaultOptions";
import messaging from "../messaging";
import castManager from "./castManager";
import deviceManager from "./deviceManager";
import { initMenus } from "./menus";
import { initWhitelist } from "./whitelist";
import { baseConfigStorage, fetchBaseConfig } from "../lib/chromecastConfigApi";
const _ = browser.i18n.getMessage;
@@ -130,6 +132,14 @@ async function init() {
await initMenus();
await initWhitelist();
messaging.onMessage.addListener(message => {
switch (message.subject) {
case "main:refreshDeviceManager":
deviceManager.refresh();
break;
}
});
browser.browserAction.onClicked.addListener(async tab => {
if (tab.id === undefined) {
logger.error("Tab ID not found in browser action handler.");

View File

@@ -761,7 +761,11 @@ function createSelector() {
}
}
selector.update(deviceManager.getDevices(), connectedSessionIds);
selector.update(
deviceManager.getDevices(),
deviceManager.getBridgeInfo()?.isVersionCompatible ?? false,
connectedSessionIds
);
};
deviceManager.addEventListener("deviceUp", onDeviceChange);

View File

@@ -47,7 +47,6 @@ export default new (class extends TypedEventTarget<EventMap> {
*/
async refresh() {
this.bridgePort?.disconnect();
this.receiverDevices.clear();
try {
this.bridgeInfo = await bridge.getInfo();
@@ -218,20 +217,28 @@ export default new (class extends TypedEventTarget<EventMap> {
};
private onBridgeDisconnect = () => {
const deviceIds = [...this.receiverDevices.keys()];
delete this.bridgeInfo;
this.receiverDevices.clear();
// Notify listeners of device availablility
for (const [, receiverDevice] of this.receiverDevices) {
for (const deviceId of deviceIds) {
const event = new CustomEvent("deviceDown", {
detail: { deviceId: receiverDevice.id }
detail: { deviceId }
});
this.dispatchEvent(event);
}
this.receiverDevices.clear();
// Re-initialize after 10 seconds
/**
* Reconnect 10 seconds after disconnect if not already
* reconnected (like immediately after a refresh).
*/
window.setTimeout(() => {
this.refresh();
if (!this.bridgeInfo) {
this.refresh();
}
}, 10000);
};
})();

View File

@@ -46,11 +46,11 @@ type ExtMessageDefinitions = {
"popup:init": {
appInfo?: ReceiverSelectorAppInfo;
pageInfo?: ReceiverSelectorPageInfo;
isBridgeCompatible: boolean;
};
/** Updates selector popup with new data. */
"popup:update": {
devices: ReceiverDevice[];
isBridgeCompatible: boolean;
connectedSessionIds?: string[];
defaultMediaType?: ReceiverSelectorMediaType;
availableMediaTypes?: ReceiverSelectorMediaType;
@@ -102,6 +102,12 @@ type ExtMessageDefinitions = {
"main:sendReceiverMessage": ReceiverSelectorReceiverMessage;
/** Allows the selector popup to send cast NS_MEDIA messages. */
"main:sendMediaMessage": ReceiverSelectorMediaMessage;
/**
* Tells the device manager to clear its device list and re-connect
* to the bridge.
*/
"main:refreshDeviceManager": void;
};
/**
@@ -319,21 +325,23 @@ export default new (class Messenger {
return browser.tabs.connect(tabId, connectInfo) as Port;
}
onConnect = {
addListener(cb: (port: Port) => void) {
browser.runtime.onConnect.addListener(
cb as (port: browser.runtime.Port) => void
);
},
removeListener(cb: (port: Port) => void) {
browser.runtime.onConnect.removeListener(
cb as (port: browser.runtime.Port) => void
);
},
hasListener(cb: (port: Port) => void) {
return browser.runtime.onConnect.hasListener(
cb as (port: browser.runtime.Port) => void
);
}
};
sendMessage(
message: Message,
options?: browser.runtime._SendMessageOptions
): Promise<any>;
sendMessage(
extensionId: string,
options?: browser.runtime._SendMessageOptions
): Promise<any>;
sendMessage(
messageOrExtensionId: string | Message,
options?: browser.runtime._SendMessageOptions
) {
return browser.runtime.sendMessage(messageOrExtensionId, options);
}
onConnect = browser.runtime.onConnect as WebExtEvent<(port: Port) => void>;
onMessage = browser.runtime.onMessage as WebExtEvent<
(message: Message, sender: browser.runtime.MessageSender) => void
>;
})();

View File

@@ -10,9 +10,10 @@
BridgeAuthenticationError
} from "../../lib/bridge";
import logger from "../../lib/logger";
import type { Options } from "../../lib/options";
import messaging from "../../messaging";
const _ = browser.i18n.getMessage;
export let opts: Options;
@@ -26,13 +27,15 @@
let statusTitle: string;
let statusText: Nullable<string> = null;
async function checkBridgeStatus() {
async function refreshBridgeStatus() {
// Reset state
bridgeInfo = null;
bridgeInfoError = null;
isLoadingInfo = true;
statusText = null;
messaging.sendMessage({ subject: "main:refreshDeviceManager" });
try {
bridgeInfo = await bridge.getInfo();
} catch (err) {
@@ -78,7 +81,7 @@
}
onMount(() => {
checkBridgeStatus();
refreshBridgeStatus();
});
// Updates
@@ -197,7 +200,7 @@
type="button"
class="ghost bridge__refresh"
title={_("optionsBridgeRefresh")}
on:click={checkBridgeStatus}
on:click={refreshBridgeStatus}
/>
</div>

View File

@@ -174,10 +174,11 @@
case "popup:init":
appInfo = message.data.appInfo;
pageInfo = message.data.pageInfo;
isBridgeCompatible = message.data.isBridgeCompatible;
break;
case "popup:update": {
isBridgeCompatible = message.data.isBridgeCompatible;
updateKnownApp();
if (

View File

@@ -92,6 +92,7 @@ body {
.receiver-list__not-found {
align-items: center;
color: var(--secondary-color);
display: flex;
height: 50px;
justify-content: center;