UNPKG

homebridge-oppo-udp

Version:
839 lines (830 loc) 276 kB
"use strict"; const PLATFORM_NAME = 'oppoPlugin'; const PLUGIN_NAME = 'homebridge-oppo-udp'; const net = require("net"); const request = require('http') const OPPO_PORT = 23; const timeout = 2000; const udp = require('dgram'); module.exports = (api) => { api.registerPlatform(PLATFORM_NAME, oppoPlatform); }; //// Platform///////////////////////////////////////////////////////////////////////////////////////////////// class oppoPlatform { constructor(log, config, api) { this.log = log; this.config = config; this.api = api; this.Service = this.api.hap.Service; this.Characteristic = this.api.hap.Characteristic; this.config.name = this.config.name || 'Oppo UDP'; this.config.newPlatformUUID = this.config.newPlatformUUID || false; // this is used to track restored cached accessories this.accessories = []; this.log.debug('Finished initializing platform:', this.config.name); this.api.on('didFinishLaunching', () => { log.debug('didFinishLaunching callback'); this.iniDevice(); }); } configureAccessory(accessory) { this.log.info('Loading accessory from cache:', accessory.displayName); this.accessories.push(accessory); } removeAccessory(accessory) { this.api.unregisterPlatformAccessories(PLUGIN_NAME, PLATFORM_NAME, [accessory]); } iniDevice() { if (this.config.newPlatformUUID === false) { this.oppoDevice = { oppoUniqueId: 'AB1212D', oppoDisplayName: `${this.config.name}` }; } if (this.config.newPlatformUUID === true) { this.oppoDevice = { oppoUniqueId: `${this.config.name}AB1212D`, oppoDisplayName: `${this.config.name}` }; this.log.debug('Generationg a new UUID'); } const uuid = this.api.hap.uuid.generate(this.oppoDevice.oppoUniqueId); this.log.debug('Adding new accessory:', this.oppoDevice.oppoDisplayName); const accessory = new this.api.platformAccessory(this.oppoDevice.oppoDisplayName, uuid); accessory.category = this.api.hap.Accessory.Categories.TV_SET_TOP_BOX; accessory.context.device = this.oppoDevice; new oppoAccessory(this, accessory); this.api.publishExternalAccessories(PLUGIN_NAME, [accessory]); } } class oppoAccessory { constructor(platform, accessory) { this.platform = platform; this.accessory = accessory; this.config = platform.config; this.OPPO_IP = this.config.ip; this.IPReceived = false; this.localIP = '192.168.0.2' this.statelessTimeOut = 1000; //////Initial Switch and sensors state/////////////////////////////////////////////////////////////////////////////////////////////// this.powerState = false; this.playBackState = [false, false, false]; this.inputState = [false, false, false, false, false, false, false, false, false, false]; this.HDROutput = [false, false, false]; this.audioType = [false, false]; this.powerStateTV = 0; this.currentVolume = 0; this.targetVolume = 100; this.currentTime = 0; this.currentMuteState = true; this.currentVolumeSwitch = false; this.inputID = 1; this.mediaState = 4; this.loginTimeOut = true; this.netConnectTimeOut = true; this.turnOffAllUsed = false; this.videoState = false; this.audioState = false; this.inputName = 'Blu-ray'; //this.newEmbyName = ''; this.mediaDuration = 'Runtime'; this.mediaChapter = 'Current Chapter'; this.mediaAudioFormat = 'Video and Audio Format'; this.language = 'Audio Language'; this.latestAudioType = ''; this.latestAudioName = ''; this.newSubtitle = ''; this.showState = false; this.firstHttp = true; this.continueSendingUpdate = true this.key = this.query('VERBOSE MODE'); this.httpNotResponding = 0; this.turnOffCommandOn = false; this.turnOnCommandOn = false; /////MovieConstants this.currentMovieProgress = 0; this.currentChapterSelector = [0, 0]; this.currentChapterTime = 0; this.currentChapterTimeState = false; this.currentChapterSelectorState = false; this.currentMovieProgressState = false; this.movieRemaining = 0; this.firstElapsedMovie = 0; this.chapterRemaining = 0; this.currentMovieProgressFirst = true; this.chapterFirstUpdate = true; this.chapterFirstUpdateRemaining = true; this.chapterRemainingFirst = 0; this.chapterElapsedFirst = 0; this.chapterCounter = 0; this.chapterUpdateSec = 60; this.movieType = ''; this.diskType = '' this.chapterProgressUpdate = true; this.chapterNumberRequest = true; ////Connection parameters this.reconnectionCounter = 0; this.reconnectionTry = 10; this.connectionLimit = false; this.connectionLimitStatus = 0; this.mediaDetailsCounter = 0; this.reconnectionWait = platform.config.pollingInterval || 10000; this.firstConnection = false; this.continueSending = true; this.newResponse = ''; this.videoIn3D = ''; this.loginCounter = 0; this.mediaHoursOrMinutes = ''; this.chapterHoursOrMinutes = ''; //Device Information////////////////////////////////////////////////////////////////////////////////////// this.config.name = platform.config.name || 'Oppo 203'; this.config.manufacture = platform.config.manufacture || 'Oppo'; this.config.pollingInterval = platform.config.pollingInterval || 1000; this.config.modelName = platform.config.modelName || 'UDP-203'; this.config.serialN = platform.config.serialN || 'B210U71647033894'; this.config.autoIP = platform.config.autoIP || false; this.config.inputButtons = platform.config.inputButtons || false; this.config.oppo205 = platform.config.oppo205 || false; this.config.volume = platform.config.volume || false; this.config.mediaButtons = platform.config.mediaButtons || false; this.config.cursorUpB = platform.config.cursorUpB || false; this.config.cursorDownB = platform.config.cursorDownB || false; this.config.cursorLeftB = platform.config.cursorLeftB || false; this.config.cursorRightB = platform.config.cursorRightB || false; this.config.cursorEnterB = platform.config.cursorEnterB || false; this.config.menuB = platform.config.menuB || false; this.config.backButtonB = platform.config.backButtonB || false; this.config.clearB = platform.config.clearB || false; this.config.topMenuB = platform.config.topMenuB || false; this.config.optionB = platform.config.optionB || false; this.config.homeMenuB = platform.config.homeMenuB || false; this.config.infoB = platform.config.infoB || false; this.config.setupB = platform.config.setupB || false; this.config.goToB = platform.config.goToB || false; this.config.pageUpB = platform.config.pageUpB || false; this.config.pageDownB = platform.config.pageDownB || false; this.config.popUpMenuB = platform.config.popUpMenuB || false; this.config.dimmerB = platform.config.dimmerB || false; this.config.pureAudioB = platform.config.pureAudioB || false; this.config.redB = platform.config.redB || false; this.config.yellowB = platform.config.yellowB || false; this.config.blueB = platform.config.blueB || false; this.config.audioB = platform.config.audioB || false; this.config.greenB = platform.config.greenB || false; this.config.subtitleB = platform.config.subtitleB || false; this.config.angleB = platform.config.angleB || false; this.config.zoomB = platform.config.zoomB || false; this.config.sapB = platform.config.sapB || false; this.config.abReplayB = platform.config.abReplayB || false; this.config.repeatB = platform.config.repeatB || false; this.config.pipB = platform.config.pipB || false; this.config.resolutionB = platform.config.resolutionB || false; this.config.threeDB = platform.config.threeDB || false; this.config.pictureB = platform.config.pictureB || false; this.config.hdrButtonB = platform.config.hdrButtonB || false; this.config.subtitleHoldB = platform.config.subtitleHoldB || false; this.config.infoHoldB = platform.config.infoHoldB || false; this.config.resolutionHoldB = platform.config.resolutionHoldB || false; this.config.avSyncB = platform.config.avSyncB || false; this.config.gaplessPlayB = platform.config.gaplessPlayB || false; this.config.inputB = platform.config.inputB || false; this.config.ejectDiscB = platform.config.ejectDiscB || false; this.config.movieControl = platform.config.movieControl || false; this.config.chapterControl = platform.config.chapterControl || false; this.config.chapterSelector = platform.config.chapterSelector || false; this.config.chinoppo = platform.config.chinoppo || false; this.config.powerB = platform.config.powerB || false; this.config.mediaAudioVideoState = platform.config.mediaAudioVideoState || false; this.config.changeDimmersToFan = platform.config.changeDimmersToFan || false; this.config.remainMovieTimer = platform.config.remainMovieTimer || false; this.config.infoToMenu = platform.config.infoToMenu || false; if (this.config.autoIP === true) { //this.platform.log('set to false'); this.config.autoIP = false; } else { // this.platform.log('set to true'); this.config.autoIP = true; } ////Checking if the necessary information was given by the user//////////////////////////////////////////////////// try { if (!this.OPPO_IP && this.config.autoIP === false) { throw new Error(`Oppo IP address is required for ${this.config.name}`); } } catch (error) { this.platform.log(error); this.platform.log('Failed to create platform device, missing mandatory information!'); this.platform.log('Please check your device config!'); return; } // set accessory information////////////////////////////////////////////////////////////////////////////////////////// this.accessory.getService(this.platform.Service.AccessoryInformation) .setCharacteristic(this.platform.Characteristic.Manufacturer, this.config.manufacture) .setCharacteristic(this.platform.Characteristic.Model, this.config.modelName) .setCharacteristic(this.platform.Characteristic.SerialNumber, this.config.serialN); /////////Television Controls/////////////////////////////////////////////////////////////////////////////////////////// // add the tv service this.tvService = this.accessory.getService(this.config.name) || this.accessory.addService(this.platform.Service.Television, this.config.name, 'YourUniqueIdentifier-7'); this.tvService.setCharacteristic(this.platform.Characteristic.ConfiguredName, this.config.name); this.tvService.setCharacteristic(this.platform .Characteristic.SleepDiscoveryMode, this.platform.Characteristic.SleepDiscoveryMode.ALWAYS_DISCOVERABLE); this.tvService.getCharacteristic(this.platform.Characteristic.Active) .on('set', (newValue, callback) => { this.platform.log.debug('Set Oppo Active to: ' + newValue); if (newValue === 1) { this.turnOffCommandOn = false; this.turnOnCommandOn = true; ///this.platform.log('Hello33');//////////////// this.sending([this.pressedButton('POWER ON')]); if (this.turnOnCommandOn === true) { setTimeout(() => { this.turnOnCommandOn = false; }, 3000); } } else { this.turnOnCommandOn = false; this.turnOffCommandOn = true; if (this.playBackState[0] === true || this.playBackState[1] === true) { this.sending([this.pressedButton('STOP')]); setTimeout(() => { this.turnOffAll(); this.sending([this.pressedButton('POWER OFF')]); if (this.turnOffCommandOn === true) { setTimeout(() => { this.turnOffCommandOn = false; }, 3000); } }, 1000); } else { this.turnOffAll(); this.sending([this.pressedButton('POWER OFF')]); if (this.turnOffCommandOn === true) { setTimeout(() => { this.turnOffCommandOn = false; }, 3000); } } } callback(null); }) .on('get', (callback) => { let currentValue = this.powerStateTV; callback(null, currentValue); }); this.tvService.getCharacteristic(this.platform.Characteristic.ClosedCaptions) .on('get', (callback) => { this.platform.log.debug('Subtitle GET On'); let currentValue = 0; callback(null, currentValue); }) .on('set', (value, callback) => { this.platform.log.debug('Subtitle SET On:', value); if (value === 1) { this.sending([this.pressedButton('SUBTITLE')]); } this.tvService.updateCharacteristic(this.platform.Characteristic.ClosedCaptions, 0); callback(null); }); //////Things to remove this.tvService.getCharacteristic(this.platform.Characteristic.Brightness) .on('get', (callback) => { let currentValue = this.currentVolume; callback(null, currentValue); }) .on('set', (newValue, callback) => { this.sending([this.volumeChange(newValue)]); this.platform.log.debug('Volume Value set to: ' + newValue); callback(null); }); this.tvService.getCharacteristic(this.platform.Characteristic.PictureMode) .on('set', (newValue, callback) => { if (newValue === 1) { this.sending([this.pressedButton('VOLUME DOWN')]); } if (newValue === 0) { this.sending([this.pressedButton('VOLUME UP')]); } this.platform.log('Volume Value moved by: ' + newValue); callback(null); }); //////////////// this.tvService.getCharacteristic(this.platform.Characteristic.RemoteKey) .on('set', (newValue, callback) => { switch (newValue) { case this.platform.Characteristic.RemoteKey.REWIND: { this.platform.log.debug('set Remote Key Pressed: REWIND'); this.sending([this.pressedButton('REWIND')]); break; } case this.platform.Characteristic.RemoteKey.FAST_FORWARD: { this.platform.log.debug('set Remote Key Pressed: FAST_FORWARD'); this.sending([this.pressedButton('FORWARD')]); break; } case this.platform.Characteristic.RemoteKey.NEXT_TRACK: { this.platform.log.debug('set Remote Key Pressed: NEXT_TRACK'); this.sending([this.pressedButton('NEXT')]); break; } case this.platform.Characteristic.RemoteKey.PREVIOUS_TRACK: { this.platform.log.debug('set Remote Key Pressed: PREVIOUS_TRACK'); this.sending([this.pressedButton('PREVIOUS')]); break; } case this.platform.Characteristic.RemoteKey.ARROW_UP: { this.platform.log.debug('set Remote Key Pressed: ARROW_UP'); this.sending([this.pressedButton('CURSOR UP')]); break; } case this.platform.Characteristic.RemoteKey.ARROW_DOWN: { this.platform.log.debug('set Remote Key Pressed: ARROW_DOWN'); this.sending([this.pressedButton('CURSOR DOWN')]); break; } case this.platform.Characteristic.RemoteKey.ARROW_LEFT: { this.platform.log.debug('set Remote Key Pressed: ARROW_LEFT'); this.sending([this.pressedButton('CURSOR LEFT')]); break; } case this.platform.Characteristic.RemoteKey.ARROW_RIGHT: { this.platform.log.debug('set Remote Key Pressed: ARROW_RIGHT'); this.sending([this.pressedButton('CURSOR RIGHT')]); break; } case this.platform.Characteristic.RemoteKey.SELECT: { this.platform.log.debug('set Remote Key Pressed: SELECT'); this.sending([this.pressedButton('CURSOR ENTER')]); break; } case this.platform.Characteristic.RemoteKey.BACK: { this.platform.log.debug('set Remote Key Pressed: BACK'); this.sending([this.pressedButton('BACK')]); break; } case this.platform.Characteristic.RemoteKey.EXIT: { this.platform.log.debug('set Remote Key Pressed: EXIT'); this.sending([this.pressedButton('HOME MENU')]); break; } case this.platform.Characteristic.RemoteKey.PLAY_PAUSE: { this.platform.log.debug('set Remote Key Pressed: PLAY_PAUSE'); if (this.playBackState[0] === false) { this.sending([this.pressedButton('PLAY')]); } else { this.sending([this.pressedButton('PAUSE')]); } break; } case this.platform.Characteristic.RemoteKey.INFORMATION: { if (this.config.infoToMenu) { if (this.movieType === 'C') { this.platform.log.debug('set Remote Key Pressed: OPTION'); this.sending([this.pressedButton('OPTION')]); } else { this.platform.log.debug('set Remote Key Pressed: MENU'); this.sending([this.pressedButton('POP-UP MENU')]); } } else { this.platform.log.debug('set Remote Key Pressed: INFORMATION'); this.sending([this.pressedButton('INFO')]); } break; } } callback(null); }); //////////////////////////////////TV Service////////////////////////////////////////////////////////////////////////// this.tvService .setCharacteristic(this.platform.Characteristic.ActiveIdentifier, this.inputID); this.tvService .getCharacteristic(this.platform.Characteristic.ActiveIdentifier) .on('set', (inputIdentifier, callback) => { this.platform.log.debug('Active Identifier set to:', inputIdentifier); if (inputIdentifier === 999999) { this.newInputState([false, false, false, false, false, false, false, false, false, false]); this.inputID = 1; } if (inputIdentifier === 0) { this.inputID = 1; this.newInputState([false, false, false, false, false, false, false, false, false, false]); } else if (inputIdentifier === 1) { this.inputID = inputIdentifier; this.sending([this.pressedButton('BLURAY INPUT')]); } else if (inputIdentifier === 2) { this.inputID = inputIdentifier; } else if (inputIdentifier === 3) { this.inputID = inputIdentifier; } else if (inputIdentifier === 4) { this.inputID = inputIdentifier; } else if (inputIdentifier === 5) { this.inputID = inputIdentifier; } else if (inputIdentifier === 6) { this.inputID = inputIdentifier; this.sending([this.pressedButton('HDMI IN')]); } else if (inputIdentifier === 7) { this.inputID = inputIdentifier; this.sending([this.pressedButton('HDMI OUT')]); } else if (inputIdentifier === 8) { this.inputID = inputIdentifier; this.sending([this.pressedButton('OPTICAL INPUT')]); } else if (inputIdentifier === 9) { this.inputID = inputIdentifier; this.sending([this.pressedButton('COAXIAL INPUT')]); } else if (inputIdentifier === 10) { this.inputID = inputIdentifier; this.sending([this.pressedButton('USB AUDIO INPUT')]); } else { this.inputID = 1; } callback(); }) .on('get', (callback) => { let currentValue = this.inputID; this.platform.log.debug('Active Identifier set to:', currentValue); callback(null, currentValue); }); this.tvService .getCharacteristic(this.platform.Characteristic.PowerModeSelection) .on('set', (newValue, callback) => { this.platform.log.debug('Requested Oppo Settings ' + newValue); if (this.playBackState[0] === false && this.playBackState[1] === false && this.playBackState[2] === false) { this.sending([this.pressedButton('SETUP')]); } else { this.sending([this.pressedButton('POP-UP MENU')]); } callback(); }); // Input Sources/////////////////////////////////////////////////////////////////////////////////////////////////////////// this.bluRay = this.accessory.getService('Blu-ray') || this.accessory.addService(this.platform.Service.InputSource, 'Blu-ray', 'YourUniqueIdentifier-1003') .setCharacteristic(this.platform.Characteristic.Identifier, 1) .setCharacteristic(this.platform.Characteristic.ConfiguredName, this.inputName) .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.APPLICATION) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.platform.Characteristic.CurrentVisibilityState.SHOWN); this.bluRay.getCharacteristic(this.platform.Characteristic.ConfiguredName) .on('get', (callback) => { let currentValue = this.inputName; callback(null, currentValue); }); this.tvService.addLinkedService(this.bluRay); this.runtime = this.accessory.getService('Runtime') || this.accessory.addService(this.platform.Service.InputSource, 'Runtime', 'NicoCata-1004') .setCharacteristic(this.platform.Characteristic.Identifier, 2) .setCharacteristic(this.platform.Characteristic.ConfiguredName, this.mediaDuration) .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.HDMI) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.showState ? this.platform.Characteristic.CurrentVisibilityState.SHOWN : this.platform.Characteristic.CurrentVisibilityState.HIDDEN); this.runtime.getCharacteristic(this.platform.Characteristic.ConfiguredName) .on('get', (callback) => { let currentValue = this.mediaDuration; this.platform.log.debug('Getting' + currentValue); callback(null, currentValue); }); this.tvService.addLinkedService(this.runtime); this.currentChaper = this.accessory.getService('Current Chapter') || this.accessory.addService(this.platform.Service.InputSource, 'Current Chapter', 'NicoCata-4005') .setCharacteristic(this.platform.Characteristic.Identifier, 3) .setCharacteristic(this.platform.Characteristic.ConfiguredName, this.mediaChapter) .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.HDMI) .setCharacteristic(this.platform.Characteristic.TargetVisibilityState, this.showState ? this.platform.Characteristic.TargetVisibilityState.SHOWN : this.platform.Characteristic.TargetVisibilityState.HIDDEN) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.showState ? this.platform.Characteristic.CurrentVisibilityState.SHOWN : this.platform.Characteristic.CurrentVisibilityState.HIDDEN); this.currentChaper.getCharacteristic(this.platform.Characteristic.ConfiguredName) .on('get', (callback) => { let currentValue = this.mediaChapter; this.platform.log.debug('Getting' + currentValue); callback(null, currentValue); }); this.tvService.addLinkedService(this.currentChaper); this.audioFormat = this.accessory.getService('Video and Audio Format') || this.accessory.addService(this.platform.Service.InputSource, 'Video and Audio Format', 'NicoCata-4006') .setCharacteristic(this.platform.Characteristic.Identifier, 4) .setCharacteristic(this.platform.Characteristic.ConfiguredName, this.mediaAudioFormat) .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.HDMI) .setCharacteristic(this.platform.Characteristic.TargetVisibilityState, this.showState ? this.platform.Characteristic.TargetVisibilityState.SHOWN : this.platform.Characteristic.TargetVisibilityState.HIDDEN) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.showState ? this.platform.Characteristic.CurrentVisibilityState.SHOWN : this.platform.Characteristic.CurrentVisibilityState.HIDDEN); this.audioFormat.getCharacteristic(this.platform.Characteristic.ConfiguredName) .on('get', (callback) => { let currentValue = this.mediaAudioFormat; this.platform.log.debug('Getting' + currentValue); callback(null, currentValue); }); this.tvService.addLinkedService(this.audioFormat); this.audioLanguage = this.accessory.getService('Audio Language') || this.accessory.addService(this.platform.Service.InputSource, 'Audio Language', 'NicoCata-4007') .setCharacteristic(this.platform.Characteristic.Identifier, 5) .setCharacteristic(this.platform.Characteristic.ConfiguredName, this.language) .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.HDMI) .setCharacteristic(this.platform.Characteristic.TargetVisibilityState, this.showState ? this.platform.Characteristic.TargetVisibilityState.SHOWN : this.platform.Characteristic.TargetVisibilityState.HIDDEN) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.showState ? this.platform.Characteristic.CurrentVisibilityState.SHOWN : this.platform.Characteristic.CurrentVisibilityState.HIDDEN); this.audioLanguage.getCharacteristic(this.platform.Characteristic.ConfiguredName) .on('get', (callback) => { let currentValue = this.language; this.platform.log.debug('Getting' + currentValue); callback(null, currentValue); }); this.tvService.addLinkedService(this.audioLanguage); this.hdmi1 = this.accessory.getService('HDMI In') || this.accessory.addService(this.platform.Service.InputSource, 'HDMI In', 'YourUniqueIdentifier-1004') .setCharacteristic(this.platform.Characteristic.Identifier, 6) .setCharacteristic(this.platform.Characteristic.ConfiguredName, 'HDMI In') .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.APPLICATION) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.platform.Characteristic.CurrentVisibilityState.SHOWN); this.tvService.addLinkedService(this.hdmi1); this.hdmi2 = this.accessory.getService('HDMI Out') || this.accessory.addService(this.platform.Service.InputSource, 'HDMI Out', 'YourUniqueIdentifier-1005') .setCharacteristic(this.platform.Characteristic.Identifier, 7) .setCharacteristic(this.platform.Characteristic.ConfiguredName, 'HDMI Out') .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.APPLICATION) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.platform.Characteristic.CurrentVisibilityState.SHOWN); this.tvService.addLinkedService(this.hdmi2); this.opticalIn = this.accessory.getService('Optical In') || this.accessory.addService(this.platform.Service.InputSource, 'Optical In', 'YourUniqueIdentifier-4005') .setCharacteristic(this.platform.Characteristic.Identifier, 8) .setCharacteristic(this.platform.Characteristic.ConfiguredName, 'Optical In') .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.HDMI) .setCharacteristic(this.platform.Characteristic.TargetVisibilityState, this.config.oppo205 ? this.platform.Characteristic.TargetVisibilityState.SHOWN : this.platform.Characteristic.TargetVisibilityState.HIDDEN) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.config.oppo205 ? this.platform.Characteristic.CurrentVisibilityState.SHOWN : this.platform.Characteristic.CurrentVisibilityState.HIDDEN); this.tvService.addLinkedService(this.opticalIn); this.coaxialIn = this.accessory.getService('Coaxial In') || this.accessory.addService(this.platform.Service.InputSource, 'Coaxial In', 'YourUniqueIdentifier-4006') .setCharacteristic(this.platform.Characteristic.Identifier, 9) .setCharacteristic(this.platform.Characteristic.ConfiguredName, 'Coaxial In') .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.HDMI) .setCharacteristic(this.platform.Characteristic.TargetVisibilityState, this.config.oppo205 ? this.platform.Characteristic.TargetVisibilityState.SHOWN : this.platform.Characteristic.TargetVisibilityState.HIDDEN) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.config.oppo205 ? this.platform.Characteristic.CurrentVisibilityState.SHOWN : this.platform.Characteristic.CurrentVisibilityState.HIDDEN); this.tvService.addLinkedService(this.coaxialIn); this.usbAudioIn = this.accessory.getService('USB Audio In') || this.accessory.addService(this.platform.Service.InputSource, 'USB Audio In', 'YourUniqueIdentifier-4007') .setCharacteristic(this.platform.Characteristic.Identifier, 10) .setCharacteristic(this.platform.Characteristic.ConfiguredName, 'USB Audio In') .setCharacteristic(this.platform.Characteristic.IsConfigured, this.platform.Characteristic.IsConfigured.CONFIGURED) .setCharacteristic(this.platform.Characteristic.InputSourceType, this.platform.Characteristic.InputSourceType.HDMI) .setCharacteristic(this.platform.Characteristic.TargetVisibilityState, this.config.oppo205 ? this.platform.Characteristic.TargetVisibilityState.SHOWN : this.platform.Characteristic.TargetVisibilityState.HIDDEN) .setCharacteristic(this.platform.Characteristic.CurrentVisibilityState, this.config.oppo205 ? this.platform.Characteristic.CurrentVisibilityState.SHOWN : this.platform.Characteristic.CurrentVisibilityState.HIDDEN); this.tvService.addLinkedService(this.usbAudioIn); /////Media State///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// this.tvService.getCharacteristic(this.platform.Characteristic.CurrentMediaState) .on('get', (callback) => { let currentValue = this.mediaState; this.platform.log.debug('Current Playback State', currentValue); callback(null, currentValue); }); this.tvService.getCharacteristic(this.platform.Characteristic.TargetMediaState) .on('get', (callback) => { let currentValue = this.mediaState; if (this.mediaState === 4) { currentValue = 2; } this.platform.log.debug('Current Playback State', currentValue); callback(null, currentValue); }) .on('set', (value, callback) => { if (value === 0) { this.sending([this.pressedButton('PLAY')]); } else if (value === 1) { this.sending([this.pressedButton('PAUSE')]); } else if (value === 2) { this.sending([this.pressedButton('STOP')]); } this.platform.log.debug('Playback State set to:', value); callback(null); }); ////////Volume services for the Oppo///////////////////////////////////////////////////////////////////////////////// this.speakerService = this.accessory.getService('Oppo Volume Control') || this.accessory.addService(this.platform.Service.TelevisionSpeaker, 'Oppo Volume Control', 'YourUniqueIdentifier-20'); this.speakerService .setCharacteristic(this.platform.Characteristic.Active, this.platform.Characteristic.Active.ACTIVE) .setCharacteristic(this.platform.Characteristic.VolumeControlType, this.platform.Characteristic.VolumeControlType.ABSOLUTE); this.speakerService.getCharacteristic(this.platform.Characteristic.VolumeSelector) .on('set', (newValue, callback) => { if (newValue === 1) { this.sending([this.pressedButton('VOLUME DOWN')]); } if (newValue === 0) { this.sending([this.pressedButton('VOLUME UP')]); } this.platform.log('Volume Value moved by: ' + newValue); callback(null); }); this.speakerService.getCharacteristic(this.platform.Characteristic.Mute) .on('get', (callback) => { let currentValue = this.currentMuteState; callback(null, currentValue); }) .on('set', (newValue, callback) => { let newVolume = this.targetVolume; if (newValue === false) { this.sending([this.volumeChange(newVolume)]); this.platform.log.debug('Volume Value set to: Unmute'); } if (newValue === true) { newVolume = 0; this.sending([this.volumeChange(newVolume)]); this.platform.log.debug('Volume Value set to: Mute'); } callback(null); }); this.speakerService.addCharacteristic(this.platform.Characteristic.Volume) .on('get', (callback) => { let currentValue = this.currentVolume; callback(null, currentValue); }) .on('set', (newValue, callback) => { this.sending([this.volumeChange(newValue)]); this.platform.log.debug('Volume Value set to: ' + newValue); callback(null); }); this.tvService.addLinkedService(this.speakerService); /////Video/Movie Controls///////////////////////////////////////////////////////////////////// if (this.config.movieControl === true) { if (this.config.changeDimmersToFan === false) { this.movieControlL = this.accessory.getService('Movie Progress') || this.accessory.addService(this.platform.Service.Lightbulb, 'Movie Progress', 'YourUniqueIdentifier-301'); this.movieControlL.setCharacteristic(this.platform.Characteristic.Name, 'Movie Progress'); this.movieControlL.addOptionalCharacteristic(this.platform.Characteristic.ConfiguredName); this.movieControlL.setCharacteristic(this.platform.Characteristic.ConfiguredName, 'Movie Progress'); this.movieControlL.getCharacteristic(this.platform.Characteristic.On) .on('get', (callback) => { let currentValue = this.currentMovieProgressState; callback(null, currentValue); }) .on('set', (newValue, callback) => { this.platform.log('Movie progress state set to: ' + newValue); callback(null); }); this.movieControlL.addCharacteristic(new this.platform.Characteristic.Brightness()) .on('get', (callback) => { let currentValue = this.currentMovieProgress; callback(null, currentValue); }) .on('set', (newValue, callback) => { let newSendValue = Math.round(newValue * (this.firstElapsedMovie + this.movieRemaining) / 100); let totalMovieTime = this.firstElapsedMovie + this.movieRemaining; if (newSendValue > totalMovieTime) { newSendValue = totalMovieTime; } this.sending([this.movieTime(this.secondsToTime(newSendValue))]); this.platform.log('Movie progress set to: ' + newValue + '%'); callback(null); }); } else { this.movieControlF = this.accessory.getService('Movie Progress') || this.accessory.addService(this.platform.Service.Fanv2, 'Movie Progress', 'YourUniqueIdentifier-301F'); this.movieControlF.setCharacteristic(this.platform.Characteristic.Name, 'Movie Progress'); this.movieControlF.addOptionalCharacteristic(this.platform.Characteristic.ConfiguredName); this.movieControlF.setCharacteristic(this.platform.Characteristic.ConfiguredName, 'Movie Progress'); this.movieControlF.getCharacteristic(this.platform.Characteristic.Active) .on('get', (callback) => { let currentValue = 0; if (this.currentMovieProgressState === true) { currentValue = 1; } callback(null, currentValue); }) .on('set', (newValue, callback) => { this.platform.log('Movie progress state set to: ' + newValue); callback(null); }); this.movieControlF.addCharacteristic(new this.platform.Characteristic.RotationSpeed) .on('get', (callback) => { let currentValue = this.currentMovieProgress; callback(null, currentValue); }) .on('set', (newValue, callback) => { let newSendValue = Math.round(newValue * (this.firstElapsedMovie + this.movieRemaining) / 100); let totalMovieTime = this.firstElapsedMovie + this.movieRemaining; if (newSendValue > totalMovieTime) { newSendValue = totalMovieTime; } this.sending([this.movieTime(this.secondsToTime(newSendValue))]); this.platform.log('Movie progress set to: ' + newValue + '%'); callback(null); }); } } if (this.config.chapterSelector === true) { if (this.config.changeDimmersToFan === false) { this.chapterSelectorL = this.accessory.getService('Chapter Number') || this.accessory.addService(this.platform.Service.Lightbulb, 'Chapter Number', 'YourUniqueIdentifier-302'); this.chapterSelectorL.setCharacteristic(this.platform.Characteristic.Name, 'Chapter Number'); this.chapterSelectorL.addOptionalCharacteristic(this.platform.Characteristic.ConfiguredName); this.chapterSelectorL.setCharacteristic(this.platform.Characteristic.ConfiguredName, 'Chapter Number'); this.chapterSelectorL.getCharacteristic(this.platform.Characteristic.On) .on('get', (callback) => { let currentValue = this.currentChapterSelectorState; callback(null, currentValue); }) .on('set', (newValue, callback) => { this.platform.log('Chapter state set to: ' + newValue); callback(null); }); this.chapterSelectorL.addCharacteristic(new this.platform.Characteristic.Brightness()) .setProps({ minValue: 0, maxValue: 100, minStep: 1, }) .on('get', (callback) => { let currentValue = this.currentChapterSelector[0]; callback(null, currentValue); }) .on('set', (newValue, callback) => { if (newValue >= this.currentChapterSelector[1]) { newValue = this.currentChapterSelector[1] } this.sending([this.chapterChange(newValue)]); this.platform.log('Chapter number set to: ' + newValue); callback(null); }); } else { this.chapterSelectorF = this.accessory.getService('Chapter Number') || this.accessory.addService(this.platform.Service.Fanv2, 'Chapter Number', 'YourUniqueIdentifier-302F'); this.chapterSelectorF.setCharacteristic(this.platform.Characteristic.Name, 'Chapter Number'); this.chapterSelectorF.addOptionalCharacteristic(this.platform.Characteristic.ConfiguredName); this.chapterSelectorF.setCharacteristic(this.platform.Characteristic.ConfiguredName, 'Chapter Number'); this.chapterSelectorF.getCharacteristic(this.platform.Characteristic.Active) .on('get', (callback) => { let currentValue = 0; if (this.currentChapterSelectorState === true) { currentValue = 1; } callback(null, currentValue); }) .on('set', (newValue, callback) => { this.platform.log('Chapter state set to: ' + newValue); callback(null); }); this.chapterSelectorF.addCharacteristic(new this.platform.Characteristic.RotationSpeed) .setProps({ minValue: 0, maxValue: 100, minStep: 1, }) .on('get', (callback) => { let currentValue = this.currentChapterSelector[0]; callback(null, currentValue); }) .on('set', (newValue, callback) => { if (newValue >= this.currentChapterSelector[1]) { newValue = this.currentChapterSelector[1] } this.sending([this.chapterChange(newValue)]); this.platform.log('Chapter number set to: ' + newValue); callback(null); }); } } if (this.config.chapterControl === true) { if (this.config.changeDimmersToFan === false) { this.chapterControlL = this.accessory.getService('Chapter Progress') || this.accessory.addService(this.platform.Service.Lightbulb, 'Chapter Progress', 'YourUniqueIdentifier-303'); this.chapterControlL.setCharacteristic(this.platform.Characteristic.Name, 'Chapter Progress'); this.chapterControlL.addOptionalCharacteristic(this.platform.Characteristic.ConfiguredName); this.chapterControlL.setCharacteristic(this.platform.Characteristic.ConfiguredName, 'Chapter Progress'); this.chapterControlL.getCharacteristic(this.platform.Characteristic.On) .on('get', (callback) => { let currentValue = this.currentChapterTimeState; callback(null, currentValue); }) .on('set', (newValue, callback) => { this.platform.log('Chapter progress status set to: ' + newValue); callback(null); }); this.chapterControlL.addCharacteristic(new this.platform.Characteristic.Brightness()) .on('get', (callback) => { let currentValue = this.currentChapterTime; callback(null, currentValue); }) .on('set', (newValue, callback) => { let newSendValue = Math.round(newValue * (this.chapterElapsedFirst + this.chapterRemainingFirst) / 100); let totalChapterTime = this.chapterElapsedFirst + this.chapterRemainingFirst; if (newSendValue > totalChapterTime) { newSendValue = totalChapterTime; } this.chapterCounter = newSendValu