Fix unused locals and better receiver selector available media checking

This commit is contained in:
hensm
2019-08-16 12:57:23 +01:00
parent 1c67354e1d
commit e2eca07876
28 changed files with 282 additions and 363 deletions

View File

@@ -25,25 +25,14 @@ export interface UpdateMessageData {
export default class Media { export default class Media {
private sessionId: number;
private mediaSessionId: number;
private referenceId: string;
private session: Session;
private channel: Channel; private channel: Channel;
private sendMessageCallback: SendMessageCallback;
constructor ( constructor (
sessionId: number sessionId: number
, mediaSessionId: number , mediaSessionId: number
, referenceId: string , private referenceId: string
, session: Session , private session: Session
, sendMessageCallback: SendMessageCallback) { , private sendMessageCallback: SendMessageCallback) {
this.sessionId = sessionId;
this.mediaSessionId = mediaSessionId;
this.referenceId = referenceId;
this.session = session;
this.sendMessageCallback = sendMessageCallback;
this.session.createChannel(MEDIA_NAMESPACE); this.session.createChannel(MEDIA_NAMESPACE);
this.channel = this.session.channelMap.get(MEDIA_NAMESPACE)!; this.channel = this.session.channelMap.get(MEDIA_NAMESPACE)!;
@@ -77,11 +66,6 @@ export default class Media {
} }
this.sendMessage("shim:/media/update", messageData); this.sendMessage("shim:/media/update", messageData);
// Update ID
if (status.mediaSessionId) {
this.mediaSessionId = status.mediaSessionId;
}
} }
}); });
} }

View File

@@ -1,7 +1,5 @@
"use strict"; "use strict";
import uuid from "uuid";
import { Channel, Client } from "castv2"; import { Channel, Client } from "castv2";
import { Message import { Message

View File

@@ -17,10 +17,7 @@ export default class StatusListener extends EventEmitter {
private clientReceiver?: Channel; private clientReceiver?: Channel;
private clientHeartbeatIntervalId?: NodeJS.Timeout; private clientHeartbeatIntervalId?: NodeJS.Timeout;
constructor ( constructor (host: string, port: number) {
private host: string
, private port: number) {
super(); super();
this.client = new Client(); this.client = new Client();

View File

@@ -12,11 +12,9 @@ import Session from "./Session";
import StatusListener from "./StatusListener"; import StatusListener from "./StatusListener";
import { DecodeTransform import { DecodeTransform
, EncodeTransform , EncodeTransform } from "../transforms";
, ResponseTransform } from "../transforms";
import { MediaStatus import { ReceiverStatus } from "./castTypes";
, ReceiverStatus } from "./castTypes";
import { Message } from "./types"; import { Message } from "./types";
@@ -146,7 +144,6 @@ async function handleMessage (message: Message) {
switch (message.subject) { switch (message.subject) {
case "bridge:/getInfo": { case "bridge:/getInfo": {
const extensionVersion = message.data;
encodeTransform.write(__applicationVersion); encodeTransform.write(__applicationVersion);
} }

View File

@@ -3,7 +3,6 @@
import { spawn } from "child_process"; import { spawn } from "child_process";
import { Readable } from "stream"; import { Readable } from "stream";
import path from "path";
import WebSocket from "ws"; import WebSocket from "ws";
import { DecodeTransform import { DecodeTransform

View File

@@ -3,6 +3,7 @@
"esModuleInterop": true "esModuleInterop": true
, "module": "commonjs" , "module": "commonjs"
, "noImplicitAny": true , "noImplicitAny": true
, "noUnusedLocals": true
, "removeComments": true , "removeComments": true
, "resolveJsonModule": true , "resolveJsonModule": true
, "target": "es6" , "target": "es6"

View File

@@ -4,9 +4,9 @@ import bridge from "../lib/bridge";
import loadSender from "../lib/loadSender"; import loadSender from "../lib/loadSender";
import options from "../lib/options"; import options from "../lib/options";
import { TypedEventTarget } from "../lib/typedEvents";
import { Message } from "../types"; import { Message } from "../types";
import { getMediaTypesForPageUrl } from "../lib/utils";
import { ReceiverSelectorMediaType } from "./receiverSelector"; import { ReceiverSelectorMediaType } from "./receiverSelector";
import ReceiverSelectorManager import ReceiverSelectorManager
@@ -140,17 +140,15 @@ export default new class ShimManager {
} }
case "main:/selectReceiverBegin": { case "main:/selectReceiverBegin": {
const allMediaTypes = const contentTab = await browser.tabs.get(shim.contentTabId);
ReceiverSelectorMediaType.App const availableMediaTypes = getMediaTypesForPageUrl(
| ReceiverSelectorMediaType.Tab contentTab.url);
| ReceiverSelectorMediaType.Screen
| ReceiverSelectorMediaType.File;
try { try {
const selection = await ReceiverSelectorManager const selection = await ReceiverSelectorManager
.getSelection( .getSelection(
ReceiverSelectorMediaType.App ReceiverSelectorMediaType.App
, allMediaTypes); , availableMediaTypes);
// Handle cancellation // Handle cancellation
if (!selection) { if (!selection) {

View File

@@ -1,7 +1,6 @@
"use strict"; "use strict";
import bridge from "../lib/bridge"; import bridge from "../lib/bridge";
import options from "../lib/options";
import { TypedEventTarget } from "../lib/typedEvents"; import { TypedEventTarget } from "../lib/typedEvents";
import { Message, Receiver, ReceiverStatus } from "../types"; import { Message, Receiver, ReceiverStatus } from "../types";

View File

@@ -2,12 +2,10 @@
import defaultOptions from "../defaultOptions"; import defaultOptions from "../defaultOptions";
import loadSender from "../lib/loadSender"; import loadSender from "../lib/loadSender";
import options, { Options } from "../lib/options"; import options from "../lib/options";
import { getChromeUserAgent } from "../lib/userAgents"; import { getChromeUserAgent } from "../lib/userAgents";
import { stringify } from "../lib/utils"; import { getMediaTypesForPageUrl, stringify } from "../lib/utils";
import { Message } from "../types";
import { CAST_FRAMEWORK_LOADER_SCRIPT_URL import { CAST_FRAMEWORK_LOADER_SCRIPT_URL
, CAST_LOADER_SCRIPT_URL } from "../lib/endpoints"; , CAST_LOADER_SCRIPT_URL } from "../lib/endpoints";
@@ -45,7 +43,6 @@ browser.runtime.onInstalled.addListener(async details => {
}); });
function initBrowserAction () { function initBrowserAction () {
browser.browserAction.disable(); browser.browserAction.disable();
@@ -68,7 +65,10 @@ function initBrowserAction () {
* top-level frame. * top-level frame.
*/ */
browser.browserAction.onClicked.addListener(async tab => { browser.browserAction.onClicked.addListener(async tab => {
const selection = await ReceiverSelectorManager.getSelection(); const selection = await ReceiverSelectorManager.getSelection(
ReceiverSelectorMediaType.Tab
, getMediaTypesForPageUrl(tab.url)
& ~ReceiverSelectorMediaType.App);
if (selection) { if (selection) {
loadSender({ loadSender({
@@ -154,17 +154,14 @@ async function initMenus () {
return; return;
} }
const availableMediaTypes = getMediaTypesForPageUrl(info.pageUrl);
switch (info.menuItemId) { switch (info.menuItemId) {
case menuIdMediaCast: { case menuIdMediaCast: {
const allMediaTypes =
ReceiverSelectorMediaType.App
| ReceiverSelectorMediaType.Tab
| ReceiverSelectorMediaType.Screen
| ReceiverSelectorMediaType.File;
const selection = await ReceiverSelectorManager.getSelection( const selection = await ReceiverSelectorManager.getSelection(
ReceiverSelectorMediaType.App ReceiverSelectorMediaType.App
, allMediaTypes); , availableMediaTypes);
// Selection cancelled // Selection cancelled
if (!selection) { if (!selection) {
@@ -203,7 +200,9 @@ async function initMenus () {
} }
case menuIdMirroringCast: { case menuIdMirroringCast: {
const selection = await ReceiverSelectorManager.getSelection(); const selection = await ReceiverSelectorManager.getSelection(
ReceiverSelectorMediaType.Tab
, availableMediaTypes & ~ReceiverSelectorMediaType.App);
loadSender({ loadSender({
tabId: tab.id tabId: tab.id
@@ -319,11 +318,9 @@ async function initMenus () {
.reverse(); .reverse();
if (pathSegments.length) { if (pathSegments.length) {
let index = 0; for (let i = 0; i < pathSegments.length; i++) {
for (const pathSegment of pathSegments) {
const partialPath = pathSegments const partialPath = pathSegments
.slice(index) .slice(i)
.reverse() .reverse()
.join("/"); .join("/");
@@ -336,8 +333,6 @@ async function initMenus () {
whitelistChildMenuPatterns.set( whitelistChildMenuPatterns.set(
partialPathMenuId, pattern); partialPathMenuId, pattern);
index++;
} }
} }
} }

View File

@@ -16,7 +16,6 @@ export default class PopupReceiverSelector
implements ReceiverSelector { implements ReceiverSelector {
private windowId: number; private windowId: number;
private openerWindowId: number;
private messagePort: browser.runtime.Port; private messagePort: browser.runtime.Port;
private messagePortDisconnected: boolean; private messagePortDisconnected: boolean;
@@ -102,7 +101,6 @@ export default class PopupReceiverSelector
this._isOpen = true; this._isOpen = true;
this.windowId = popup.id; this.windowId = popup.id;
this.openerWindowId = openerWindow.id;
// Size/position not set correctly on creation (bug?) // Size/position not set correctly on creation (bug?)
await browser.windows.update(this.windowId, { await browser.windows.update(this.windowId, {
@@ -168,7 +166,6 @@ export default class PopupReceiverSelector
// Cleanup // Cleanup
this.windowId = null; this.windowId = null;
this.openerWindowId = null;
this.messagePort = null; this.messagePort = null;
this.receivers = null; this.receivers = null;
this.defaultMediaType = null; this.defaultMediaType = null;

View File

@@ -83,6 +83,29 @@ async function getSelection (
}); });
const opts = await options.getAll();
// Remove mirroring media types if mirroring is not enabled.
if (!opts.mirroringEnabled) {
availableMediaTypes &= ~(
ReceiverSelectorMediaType.Tab
| ReceiverSelectorMediaType.Screen);
}
// Remove file media type if local media is not enabled
if (!opts.mediaEnabled || !opts.localMediaEnabled) {
availableMediaTypes &= ~ReceiverSelectorMediaType.File;
}
if (!availableMediaTypes || availableMediaTypes
=== ReceiverSelectorMediaType.File) {
console.error("fx_cast (Debug): No available media types");
resolve(null);
return;
}
// Ensure status manager is initialized // Ensure status manager is initialized
await StatusManager.init(); await StatusManager.init();

View File

@@ -1,8 +1,5 @@
"use strict"; "use strict";
import { Message } from "../types";
const WEBSOCKET_DAEMON_URL = "ws://localhost:9556"; const WEBSOCKET_DAEMON_URL = "ws://localhost:9556";

View File

@@ -3,7 +3,6 @@
import defaultOptions from "../defaultOptions"; import defaultOptions from "../defaultOptions";
import { ReceiverSelectorType } from "../background/receiverSelector"; import { ReceiverSelectorType } from "../background/receiverSelector";
import { Message } from "../types";
import { TypedEventTarget } from "./typedEvents"; import { TypedEventTarget } from "./typedEvents";

View File

@@ -1,5 +1,8 @@
"use strict"; "use strict";
import { ReceiverSelectorMediaType } from "../background/receiverSelector";
export function getNextEllipsis (ellipsis: string): string { export function getNextEllipsis (ellipsis: string): string {
/* tslint:disable:curly */ /* tslint:disable:curly */
if (ellipsis === "") return "."; if (ellipsis === "") return ".";
@@ -29,6 +32,28 @@ export function stringify (
return formattedString; return formattedString;
} }
export function getMediaTypesForPageUrl (
pageUrl: string): ReceiverSelectorMediaType {
let availableMediaTypes =
ReceiverSelectorMediaType.App
| ReceiverSelectorMediaType.Tab
| ReceiverSelectorMediaType.Screen
| ReceiverSelectorMediaType.File;
/**
* Remove "Screen" option when on an insecure origin as
* MediaDevices.getDisplayMedia will not exist (and legacy
* MediaDevices.getUserMedia mediaSource constraint will
* fail).
*/
if (!pageUrl.startsWith("https://")) {
availableMediaTypes &= ~ReceiverSelectorMediaType.Screen;
}
return availableMediaTypes;
}
interface WindowCenteredProps { interface WindowCenteredProps {
width: number; width: number;

View File

@@ -21,22 +21,6 @@ let session: cast.Session;
let wasSessionRequested = false; let wasSessionRequested = false;
let peerConnection: RTCPeerConnection; let peerConnection: RTCPeerConnection;
let drawWindowIntervalId: number;
let availableMediaTypes =
ReceiverSelectorMediaType.Screen
| ReceiverSelectorMediaType.Tab;
/**
* Remove "Screen" option when on an insecure origin as
* MediaDevices.getDisplayMedia will not exist (and legacy
* MediaDevices.getUserMedia mediaSource constraint will
* fail).
*/
if (typeof navigator.mediaDevices.getDisplayMedia === "undefined") {
availableMediaTypes &= ~ReceiverSelectorMediaType.Screen;
}
/** /**
@@ -124,7 +108,7 @@ async function onRequestSessionSuccess (newSession: cast.Session) {
} }
drawWindowIntervalId = window.setInterval(drawWindow, 1000 / 30); window.setInterval(drawWindow, 1000 / 30);
/** /**
* Capture video stream from canvas and feed into the RTC * Capture video stream from canvas and feed into the RTC

View File

@@ -13,8 +13,7 @@ import Media from "../media/classes/Media";
import QueueLoadRequest from "../media/classes/QueueLoadRequest"; import QueueLoadRequest from "../media/classes/QueueLoadRequest";
import { ErrorCode import { ErrorCode
, SessionStatus , SessionStatus } from "../enums";
, VolumeControlType } from "../enums";
import { RepeatMode } from "../media/enums"; import { RepeatMode } from "../media/enums";
@@ -22,8 +21,7 @@ import { ListenerObject
, onMessage , onMessage
, sendMessageResponse } from "../../eventMessageChannel"; , sendMessageResponse } from "../../eventMessageChannel";
import { Callbacks import { CallbacksMap
, CallbacksMap
, ErrorCallback , ErrorCallback
, LoadSuccessCallback , LoadSuccessCallback
, MediaListener , MediaListener
@@ -51,7 +49,7 @@ export default class Session {
public media: Media[]; public media: Media[];
public namespaces: Array<{ name: "string" }>; public namespaces: Array<{ name: "string" }>;
public senderApps: SenderApplication[]; public senderApps: SenderApplication[];
public status: string; public status: SessionStatus;
public statusText: string; public statusText: string;
public transportId: string; public transportId: string;

View File

@@ -5,7 +5,7 @@ import { VolumeControlType } from "../enums";
// https://developers.google.com/cast/docs/reference/chrome/chrome.cast.Volume // https://developers.google.com/cast/docs/reference/chrome/chrome.cast.Volume
export default class Volume { export default class Volume {
public controlType: string; public controlType: VolumeControlType;
public stepInterval: number; public stepInterval: number;
constructor ( constructor (

View File

@@ -1,75 +1,75 @@
"use strict"; "use strict";
export const AutoJoinPolicy = { export enum AutoJoinPolicy {
TAB_AND_ORIGIN_SCOPED: "tab_and_origin_scoped" TAB_AND_ORIGIN_SCOPED = "tab_and_origin_scoped"
, ORIGIN_SCOPED: "origin_scoped" , ORIGIN_SCOPED = "origin_scoped"
, PAGE_SCOPED: "page_scoped" , PAGE_SCOPED = "page_scoped"
, CUSTOM_CONTROLLER_SCOPED: "custom_controller_scoped" , CUSTOM_CONTROLLER_SCOPED = "custom_controller_scoped"
}; }
export const Capability = { export enum Capability {
VIDEO_OUT: "video_out" VIDEO_OUT = "video_out"
, AUDIO_OUT: "audio_out" , AUDIO_OUT = "audio_out"
, VIDEO_IN: "video_in" , VIDEO_IN = "video_in"
, AUDIO_IN: "audio_in" , AUDIO_IN = "audio_in"
, MULTIZONE_GROUP: "multizone_group" , MULTIZONE_GROUP = "multizone_group"
}; }
export const DefaultActionPolicy = { export enum DefaultActionPolicy {
CREATE_SESSION: "create_session" CREATE_SESSION = "create_session"
, CAST_THIS_TAB: "cast_this_tab" , CAST_THIS_TAB = "cast_this_tab"
}; }
export const DialAppState = { export enum DialAppState {
RUNNING: "running" RUNNING = "running"
, STOPPED: "stopped" , STOPPED = "stopped"
, ERROR: "error" , ERROR = "error"
}; }
export const ErrorCode = { export enum ErrorCode {
CANCEL: "cancel" CANCEL = "cancel"
, TIMEOUT: "timeout" , TIMEOUT = "timeout"
, API_NOT_INITIALIZED: "api_not_initialized" , API_NOT_INITIALIZED = "api_not_initialized"
, INVALID_PARAMETER: "invalid_parameter" , INVALID_PARAMETER = "invalid_parameter"
, EXTENSION_NOT_COMPATIBLE: "extension_not_compatible" , EXTENSION_NOT_COMPATIBLE = "extension_not_compatible"
, EXTENSION_MISSING: "extension_missing" , EXTENSION_MISSING = "extension_missing"
, RECEIVER_UNAVAILABLE: "receiver_unavailable" , RECEIVER_UNAVAILABLE = "receiver_unavailable"
, SESSION_ERROR: "session_error" , SESSION_ERROR = "session_error"
, CHANNEL_ERROR: "channel_error" , CHANNEL_ERROR = "channel_error"
, LOAD_MEDIA_FAILED: "load_media_failed" , LOAD_MEDIA_FAILED = "load_media_failed"
}; }
export const ReceiverAction = { export enum ReceiverAction {
CAST: "cast" CAST = "cast"
, STOP: "stop" , STOP = "stop"
}; }
export const ReceiverAvailability = { export enum ReceiverAvailability {
AVAILABLE: "available" AVAILABLE = "available"
, UNAVAILABLE: "unavailable" , UNAVAILABLE = "unavailable"
}; }
export const ReceiverType = { export enum ReceiverType {
CAST: "cast" CAST = "cast"
, DIAL: "dial" , DIAL = "dial"
, HANGOUT: "hangout" , HANGOUT = "hangout"
, CUSTOM: "custom" , CUSTOM = "custom"
}; }
export const SenderPlatform = { export enum SenderPlatform {
CHROME: "chrome" CHROME = "chrome"
, IOS: "ios" , IOS = "ios"
, ANDROID: "android" , ANDROID = "android"
}; }
export const SessionStatus = { export enum SessionStatus {
CONNECTED: "connected" CONNECTED = "connected"
, DISCONNECTED: "disconnected" , DISCONNECTED = "disconnected"
, STOPPED: "stopped" , STOPPED = "stopped"
}; }
export const VolumeControlType = { export enum VolumeControlType {
ATTENUATION: "attenuation" ATTENUATION = "attenuation"
, FIXED: "fixed" , FIXED = "fixed"
, MASTER: "master" , MASTER = "master"
}; }

View File

@@ -26,8 +26,6 @@ import { AutoJoinPolicy
import * as media from "./media"; import * as media from "./media";
import { ReceiverSelectorMediaType } from "../../background/receiverSelector";
import { Receiver } from "../../types"; import { Receiver } from "../../types";
import { onMessage, sendMessageResponse } from "../eventMessageChannel"; import { onMessage, sendMessageResponse } from "../eventMessageChannel";

View File

@@ -25,8 +25,7 @@ import { ErrorCode } from "../../enums";
import { onMessage, sendMessageResponse } from "../../../eventMessageChannel"; import { onMessage, sendMessageResponse } from "../../../eventMessageChannel";
import { Callbacks import { CallbacksMap
, CallbacksMap
, ErrorCallback , ErrorCallback
, SuccessCallback , SuccessCallback
, UpdateListener } from "../../../types"; , UpdateListener } from "../../../types";

View File

@@ -1,93 +1,93 @@
"use strict"; "use strict";
export const IdleReason = { export enum IdleReason {
CANCELLED: "CANCELLED" CANCELLED = "CANCELLED"
, INTERRUPTED: "INTERRUPTED" , INTERRUPTED = "INTERRUPTED"
, FINISHED: "FINISHED" , FINISHED = "FINISHED"
, ERROR: "ERROR" , ERROR = "ERROR"
}; }
export const MediaCommand = { export enum MediaCommand {
PAUSE: "pause" PAUSE = "pause"
, SEEK: "seek" , SEEK = "seek"
, STREAM_VOLUME: "stream_volume" , STREAM_VOLUME = "stream_volume"
, STREAM_MUTE: "stream_mute" , STREAM_MUTE = "stream_mute"
}; }
export const MetadataType = { export enum MetadataType {
GENERIC: 0 GENERIC
, MOVIE: 1 , MOVIE
, TV_SHOW: 2 , TV_SHOW
, MUSIC_TRACK: 3 , MUSIC_TRACK
, PHOTO: 4 , PHOTO
}; }
export const PlayerState = { export enum PlayerState {
IDLE: "IDLE" IDLE = "IDLE"
, PLAYING: "PLAYING" , PLAYING = "PLAYING"
, PAUSED: "PAUSED" , PAUSED = "PAUSED"
, BUFFERING: "BUFFERING" , BUFFERING = "BUFFERING"
}; }
export const RepeatMode = { export enum RepeatMode {
OFF: "REPEAT_OFF" OFF = "REPEAT_OFF"
, ALL: "REPEAT_ALL" , ALL = "REPEAT_ALL"
, SINGLE: "REPEAT_SINGLE" , SINGLE = "REPEAT_SINGLE"
, ALL_AND_SHUFFLE: "REPEAT_ALL_AND_SHUFFLE" , ALL_AND_SHUFFLE = "REPEAT_ALL_AND_SHUFFLE"
}; }
export const ResumeState = { export enum ResumeState {
PLAYBACK_START: "PLAYBACK_START" PLAYBACK_START = "PLAYBACK_START"
, PLAYBACK_PAUSE: "PLAYBACK_PAUSE" , PLAYBACK_PAUSE = "PLAYBACK_PAUSE"
}; }
export const StreamType = { export enum StreamType {
BUFFERED: "BUFFERED" BUFFERED = "BUFFERED"
, LIVE: "LIVE" , LIVE = "LIVE"
, OTHER: "OTHER" , OTHER = "OTHER"
}; }
export const TextTrackEdgeType = { export enum TextTrackEdgeType {
NONE: "NONE" NONE = "NONE"
, OUTLINE: "OUTLINE" , OUTLINE = "OUTLINE"
, DROP_SHADOW: "DROP_SHADOW" , DROP_SHADOW = "DROP_SHADOW"
, RAISED: "RAISED" , RAISED = "RAISED"
, DEPRESSED: "DEPRESSED" , DEPRESSED = "DEPRESSED"
}; }
export const TextTrackFontGenericFamily = { export enum TextTrackFontGenericFamily {
SANS_SERIF: "SANS_SERIF" SANS_SERIF = "SANS_SERIF"
, MONOSPACED_SANS_SERIF: "MONOSPACED_SANS_SERIF" , MONOSPACED_SANS_SERIF = "MONOSPACED_SANS_SERIF"
, SERIF: "SERIF" , SERIF = "SERIF"
, MONOSPACED_SERIF: "MONOSPACED_SERIF" , MONOSPACED_SERIF = "MONOSPACED_SERIF"
, CASUAL: "CASUAL" , CASUAL = "CASUAL"
, CURSIVE: "CURSIVE" , CURSIVE = "CURSIVE"
, SMALL_CAPITALS: "SMALL_CAPITALS" , SMALL_CAPITALS = "SMALL_CAPITALS"
}; }
export const TextTrackFontStyle = { export enum TextTrackFontStyle {
NORMAL: "NORMAL" NORMAL = "NORMAL"
, BOLD: "BOLD" , BOLD = "BOLD"
, BOLD_ITALIC: "BOLD_ITALIC" , BOLD_ITALIC = "BOLD_ITALIC"
, ITALIC: "ITALIC" , ITALIC = "ITALIC"
}; }
export const TextTrackType = { export enum TextTrackType {
SUBTITLES: "SUBTITLES" SUBTITLES = "SUBTITLES"
, CAPTIONS: "CAPTIONS" , CAPTIONS = "CAPTIONS"
, DESCRIPTIONS: "DESCRIPTIONS" , DESCRIPTIONS = "DESCRIPTIONS"
, CHAPTERS: "CHAPTERS" , CHAPTERS = "CHAPTERS"
, METADATA: "METADATA" , METADATA = "METADATA"
}; }
export const TextTrackWindowType = { export enum TextTrackWindowType {
NONE: "NONE" NONE = "NONE"
, NORMAL: "NORMAL" , NORMAL = "NORMAL"
, ROUNDED_CORNERS: "ROUNDED_CORNERS" , ROUNDED_CORNERS = "ROUNDED_CORNERS"
}; }
export const TrackType = { export enum TrackType {
TEXT: "TEXT" TEXT = "TEXT"
, AUDIO: "AUDIO" , AUDIO = "AUDIO"
, VIDEO: "VIDEO" , VIDEO = "VIDEO"
}; }

View File

@@ -1,11 +1,7 @@
"use strict"; "use strict";
import * as cast from "../../cast";
import CastOptions from "./CastOptions"; import CastOptions from "./CastOptions";
import CastSession from "./CastSession"; import CastSession from "./CastSession";
import CastStateEventData from "./CastStateEventData";
import SessionStateEventData from "./SessionStateEventData";
export default class CastContext extends EventTarget { export default class CastContext extends EventTarget {

View File

@@ -2,12 +2,7 @@
import * as cast from "../../cast"; import * as cast from "../../cast";
import ActiveInputStateEventData from "./ActiveInputStateEventData";
import ApplicationMetadata from "./ApplicationMetadata"; import ApplicationMetadata from "./ApplicationMetadata";
import ApplicationMetadataEventData from "./ApplicationMetadataEventData";
import ApplicationStatusEventData from "./ApplicationStatusEventData";
import MediaSessionEventData from "./MediaSessionEventData";
import VolumeEventData from "./VolumeEventData";
type MessageListener = (namespace: string, message: string) => void; type MessageListener = (namespace: string, message: string) => void;

View File

@@ -1,7 +1,6 @@
"use strict"; "use strict";
import RemotePlayer from "./RemotePlayer"; import RemotePlayer from "./RemotePlayer";
import RemotePlayerChangedEvent from "./RemotePlayerChangedEvent";
export default class RemotePlayerController extends EventTarget { export default class RemotePlayerController extends EventTarget {

View File

@@ -1,64 +1,64 @@
"use strict"; "use strict";
export const ActiveInputState = { export enum ActiveInputState {
ACTIVE_INPUT_STATE_UNKNOWN: -1 ACTIVE_INPUT_STATE_UNKNOWN = -1
, ACTIVE_INPUT_STATE_NO: 0 , ACTIVE_INPUT_STATE_NO = 0
, ACTIVE_INPUT_YES: 1 , ACTIVE_INPUT_YES = 1
}; }
export const CastContextEventType = { export enum CastContextEventType {
CAST_STATE_CHANGED: "caststatechanged" CAST_STATE_CHANGED = "caststatechanged"
, SESSION_STATE_CHANGED: "sessionstatechanged" , SESSION_STATE_CHANGED = "sessionstatechanged"
}; }
export const CastState = { export enum CastState {
NO_DEVICES_AVAILABLE: "NO_DEVICES_AVAILABLE" NO_DEVICES_AVAILABLE = "NO_DEVICES_AVAILABLE"
, NOT_CONNECTED: "NOT_CONNECTED" , NOT_CONNECTED = "NOT_CONNECTED"
, CONNECTING: "CONNECTING" , CONNECTING = "CONNECTING"
, CONNECTED: "CONNECTED" , CONNECTED = "CONNECTED"
}; }
export const LoggerLevel = { export enum LoggerLevel {
DEBUG: 0 DEBUG = 0
, INFO: 800 , INFO = 800
, WARNING: 900 , WARNING = 900
, ERROR: 1000 , ERROR = 1000
, NONE: 1500 , NONE = 1500
}; }
export const RemotePlayerEventType = { export enum RemotePlayerEventType {
ANY_CHANGE: "anyChanged" ANY_CHANGE = "anyChanged"
, IS_CONNECTED_CHANGE: "isConnectedChanged" , IS_CONNECTED_CHANGE = "isConnectedChanged"
, IS_MEDIA_LOADED_CHANGED: "isMediaLoadedChanged" , IS_MEDIA_LOADED_CHANGED = "isMediaLoadedChanged"
, DURATION_CHANGED: "durationChanged" , DURATION_CHANGED = "durationChanged"
, CURRENT_TIME_CHANGED: "currentTimeChanged" , CURRENT_TIME_CHANGED = "currentTimeChanged"
, IS_PAUSED_CHANGED: "isPausedChanged" , IS_PAUSED_CHANGED = "isPausedChanged"
, VOLUME_LEVEL_CHANGED: "volumeLevelChanged" , VOLUME_LEVEL_CHANGED = "volumeLevelChanged"
, CAN_CONTROL_VOLUME_CHANGED: "canControlVolumeChanged" , CAN_CONTROL_VOLUME_CHANGED = "canControlVolumeChanged"
, IS_MUTED_CHANGED: "isMutedChanged" , IS_MUTED_CHANGED = "isMutedChanged"
, CAN_PAUSE_CHANGED: "canPauseChanged" , CAN_PAUSE_CHANGED = "canPauseChanged"
, CAN_SEEK_CHANGED: "canSeekChanged" , CAN_SEEK_CHANGED = "canSeekChanged"
, DISPLAY_NAME_CHANGED: "displayNameChanged" , DISPLAY_NAME_CHANGED = "displayNameChanged"
, STATUS_TEXT_CHANGED: "statusTextChanged" , STATUS_TEXT_CHANGED = "statusTextChanged"
, MEDIA_INFO_CHANGED: "mediaInfoChanged" , MEDIA_INFO_CHANGED = "mediaInfoChanged"
, IMAGE_URL_CHANGED: "imageUrlChanged" , IMAGE_URL_CHANGED = "imageUrlChanged"
, PLAYER_STATE_CHANGED: "playerStateChanged" , PLAYER_STATE_CHANGED = "playerStateChanged"
}; }
export const SessionEventType = { export enum SessionEventType {
APPLICATION_STATUS_CHANGED: "applicationstatuschanged" APPLICATION_STATUS_CHANGED = "applicationstatuschanged"
, APPLICATION_METADATA_CHANGED: "applicationmetadatachanged" , APPLICATION_METADATA_CHANGED = "applicationmetadatachanged"
, ACTIVE_INPUT_STATE_CHANGED: "activeinputstatechanged" , ACTIVE_INPUT_STATE_CHANGED = "activeinputstatechanged"
, VOLUME_CHANGED: "volumechanged" , VOLUME_CHANGED = "volumechanged"
, MEDIA_SESSION: "mediasession" , MEDIA_SESSION = "mediasession"
}; }
export const SessionState = { export enum SessionState {
NO_SESSION: "NO_SESSION" NO_SESSION = "NO_SESSION"
, SESSION_STARTING: "SESSION_STARTING" , SESSION_STARTING = "SESSION_STARTING"
, SESSION_STARTED: "SESSION_STARTED" , SESSION_STARTED = "SESSION_STARTED"
, SESSION_START_FAILED: "SESSION_START_FAILED" , SESSION_START_FAILED = "SESSION_START_FAILED"
, SESSION_ENDING: "SESSION_ENDING" , SESSION_ENDING = "SESSION_ENDING"
, SESSION_ENDED: "SESSION_ENDED" , SESSION_ENDED = "SESSION_ENDED"
, SESSION_RESUMED: "SESSION_RESUMED" , SESSION_RESUMED = "SESSION_RESUMED"
}; }

View File

@@ -1,6 +1,5 @@
"use strict"; "use strict";
import * as cast from "../cast";
import ActiveInputStateEventData from "./classes/ActiveInputStateEventData"; import ActiveInputStateEventData from "./classes/ActiveInputStateEventData";
import ApplicationMetadata from "./classes/ApplicationMetadata"; import ApplicationMetadata from "./classes/ApplicationMetadata";
@@ -28,8 +27,6 @@ import { ActiveInputState
import GoogleCastLauncher from "./GoogleCastLauncher"; import GoogleCastLauncher from "./GoogleCastLauncher";
import { onMessage } from "../eventMessageChannel";
export default { export default {
// Enums // Enums

View File

@@ -4,55 +4,12 @@
import React, { Component } from "react"; import React, { Component } from "react";
import semver from "semver"; import semver from "semver";
import { getNextEllipsis
, getWindowCenteredProps } from "../../lib/utils";
import { BridgeInfo } from "../../lib/bridge"; import { BridgeInfo } from "../../lib/bridge";
import { getNextEllipsis } from "../../lib/utils";
const _ = browser.i18n.getMessage; const _ = browser.i18n.getMessage;
const ENDPOINT_URL = "https://api.github.com/repos/hensm/fx_cast/releases/latest";
async function downloadApp (info: any, platform: string) {
const download = browser.downloads.download({
filename: info[platform].name
, url: info[platform].url
});
}
interface BridgeDownloadsProps {
info: any;
}
const BridgeDownloads = (props: BridgeDownloadsProps) => (
<div className="bridge-downloads">
<button className="bridge-downloads__download
bridge-downloads__win"
disabled
onClick={ () => downloadApp(props.info, "win") }>
Windows
</button>
<button className="bridge-downloads__download
bridge-downloads__mac"
onClick={ () => downloadApp(props.info, "mac") }>
macOS
</button>
<div className="bridge-downloads__linux">
<button className="bridge-downloads__download"
onClick={ () => downloadApp(props.info, "deb") }>
Linux (deb)
</button>
<button className="bridge-downloads__download"
onClick={ () => downloadApp(props.info, "rpm") }>
Linux (rpm)
</button>
</div>
</div>
);
interface BridgeStatsProps { interface BridgeStatsProps {
info: BridgeInfo; info: BridgeInfo;
@@ -236,7 +193,7 @@ export default class Bridge extends Component<BridgeProps, BridgeState> {
})); }));
}, 500); }, 500);
fetch(ENDPOINT_URL) fetch("https://api.github.com/repos/hensm/fx_cast/releases/latest")
.then(res => { .then(res => {
window.clearTimeout(timeout); window.clearTimeout(timeout);
return res.json(); return res.json();

View File

@@ -400,19 +400,6 @@ class OptionsApp extends Component<{}, OptionsAppState> {
private getWhitelistItemPatternError (info: string): string { private getWhitelistItemPatternError (info: string): string {
return _("optionsUserAgentWhitelistInvalidMatchPattern", info); return _("optionsUserAgentWhitelistInvalidMatchPattern", info);
} }
private async updateBridgeInfo () {
this.setState({
bridgeLoading: true
});
const bridgeInfo = await bridge.getInfo();
this.setState({
bridgeInfo
, bridgeLoading: false
});
}
} }