mirror of
https://gitdl.cn/https://github.com/chakralinux/desktop.git
synced 2025-01-24 02:22:13 +08:00
461 lines
17 KiB
Diff
461 lines
17 KiB
Diff
diff --git a/mythtv/configure b/mythtv/configure
|
|
index 7ab8aa7..7d5e39d 100755
|
|
--- a/mythtv/configure
|
|
+++ b/mythtv/configure
|
|
@@ -5178,10 +5178,12 @@ using namespace std;
|
|
using namespace CEC;
|
|
#include <libcec/cecloader.h>
|
|
int main(void) {
|
|
+ if (CEC_LIB_VERSION_MAJOR == 2)
|
|
+ return 1;
|
|
if (CEC_LIB_VERSION_MAJOR < 1 || (CEC_LIB_VERSION_MAJOR == 1 &&
|
|
CEC_LIB_VERSION_MINOR < 5))
|
|
return 0;
|
|
- return (long) LibCecInit;
|
|
+ return 1;
|
|
}
|
|
EOF
|
|
fi
|
|
diff --git a/mythtv/libs/libmythui/cecadapter.cpp b/mythtv/libs/libmythui/cecadapter.cpp
|
|
index edad8f6..5987d5d 100644
|
|
--- a/mythtv/libs/libmythui/cecadapter.cpp
|
|
+++ b/mythtv/libs/libmythui/cecadapter.cpp
|
|
@@ -14,9 +14,28 @@
|
|
#include "cecadapter.h"
|
|
#include <vector>
|
|
|
|
-#define MIN_LIBCEC_VERSION 1
|
|
+#ifdef CEC_CLIENT_VERSION_CURRENT // 2.0.3 and up
|
|
+#define CEC_CONFIG_VERSION CEC_CLIENT_VERSION_CURRENT;
|
|
+#else
|
|
+#ifdef LIBCEC_VERSION_CURRENT // 1.6.2 and up
|
|
+#define CEC_CONFIG_VERSION LIBCEC_VERSION_CURRENT;
|
|
+#else
|
|
+#define CEC_CONFIG_VERSION 0;
|
|
+#endif
|
|
+#endif
|
|
+
|
|
#define MAX_CEC_DEVICES 10
|
|
#define LOC QString("CECAdapter: ")
|
|
+#define OSDNAME "MythTv"
|
|
+
|
|
+// TODO remove if we have a ui.
|
|
+// hard code logical and physical address
|
|
+#define CEC_DEFAULT_DEVICE_TYPE CEC_DEVICE_TYPE_RECORDING_DEVICE
|
|
+#undef CEC_DEFAULT_HDMI_PORT
|
|
+#define CEC_DEFAULT_HDMI_PORT 2
|
|
+#undef CEC_DEFAULT_BASE_DEVICE
|
|
+#define CEC_DEFAULT_BASE_DEVICE CECDEVICE_AUDIOSYSTEM
|
|
+#define CEC_DEFAULT_PHYSICALADDRESS (quint16)0x2200
|
|
|
|
#include <libcec/cec.h>
|
|
#include <iostream>
|
|
@@ -25,17 +44,26 @@ using namespace std;
|
|
#include <libcec/cecloader.h>
|
|
|
|
QMutex* CECAdapter::gLock = new QMutex(QMutex::Recursive);
|
|
+bool resetSafe = false;
|
|
|
|
class CECAdapterPriv
|
|
{
|
|
public:
|
|
CECAdapterPriv()
|
|
- : adapter(NULL), defaultDevice("auto"), defaultHDMIPort(1),
|
|
- defaultDeviceID(CECDEVICE_PLAYBACKDEVICE1), timer(NULL), valid(false),
|
|
+ : adapter(NULL), defaultDevice("auto"), defaultHDMIPort(CEC_DEFAULT_HDMI_PORT),
|
|
+ defaultDeviceID(CEC_DEFAULT_DEVICE_TYPE), timer(NULL), valid(false),
|
|
powerOffTV(false), powerOffTVAllowed(false), powerOffTVOnExit(false),
|
|
powerOnTV(false), powerOnTVAllowed(false), powerOnTVOnStart(false),
|
|
switchInput(false), switchInputAllowed(true)
|
|
{
|
|
+ callbacks.Clear();
|
|
+ callbacks.CBCecLogMessage = LogMessages;
|
|
+ callbacks.CBCecKeyPress = HandleKeyPresses;
|
|
+ callbacks.CBCecCommand = HandleCommands;
|
|
+ callbacks.CBCecConfigurationChanged = HandleConfigurationChanged;
|
|
+ callbacks.CBCecAlert = HandleAlerts;
|
|
+ callbacks.CBCecMenuStateChanged = HandleMenuStateChanged;
|
|
+ callbacks.CBCecSourceActivated = HandleSourceActivated;
|
|
}
|
|
|
|
static QString addressToString(enum cec_logical_address addr, bool source)
|
|
@@ -69,14 +97,15 @@ class CECAdapterPriv
|
|
static QStringList GetDeviceList(void)
|
|
{
|
|
QStringList results;
|
|
- cec_device_type_list list;
|
|
- list.Clear();
|
|
- list.Add(CEC_DEVICE_TYPE_PLAYBACK_DEVICE);
|
|
- ICECAdapter *adapter = LibCecInit("MythTV", list);
|
|
+ libcec_configuration configuration;
|
|
+ configuration.Clear();
|
|
+ ICECAdapter *adapter = LibCecInitialise(&configuration);
|
|
if (!adapter)
|
|
return results;
|
|
cec_adapter *devices = new cec_adapter[MAX_CEC_DEVICES];
|
|
uint8_t num_devices = adapter->FindAdapters(devices, MAX_CEC_DEVICES, NULL);
|
|
+ LOG(VB_GENERAL, LOG_INFO, LOC + QString("GetDeviceList() found %1 devices(s).")
|
|
+ .arg(num_devices));
|
|
if (num_devices < 1)
|
|
return results;
|
|
for (uint8_t i = 0; i < num_devices; i++)
|
|
@@ -89,39 +118,112 @@ class CECAdapterPriv
|
|
{
|
|
// get settings
|
|
// N.B. these do not currently work as there is no UI
|
|
+
|
|
+ // There is no way current CEC adapters can find their physical address
|
|
+ // on their own. The are only connected to the CEC pin of the HDMI connector.
|
|
+ // To construct a valid physical address libCEC needs:
|
|
+ // - the HDMI port (number) Myth is connected to
|
|
+ // - the HDMI device (TV, Receiver) Myth is connected to (the logical address)
|
|
+
|
|
+ //The CEC adapter we want to connect to
|
|
defaultDevice = gCoreContext->GetSetting(LIBCEC_DEVICE, "auto").trimmed();
|
|
+ // The number of the HDMI port Myth is connected to
|
|
QString hdmi_port = gCoreContext->GetSetting(LIBCEC_PORT, "auto");
|
|
+ // The logical address of the HDMI device Myth is connected to
|
|
+ QString base_dev = gCoreContext->GetSetting(LIBCEC_BASE, "auto");
|
|
+ // Device type we want Myth to use
|
|
QString device_id = gCoreContext->GetSetting(LIBCEC_DEVICEID, "auto");
|
|
powerOffTVAllowed = (bool)gCoreContext->GetNumSetting(POWEROFFTV_ALLOWED, 1);
|
|
powerOffTVOnExit = (bool)gCoreContext->GetNumSetting(POWEROFFTV_ONEXIT, 1);
|
|
powerOnTVAllowed = (bool)gCoreContext->GetNumSetting(POWERONTV_ALLOWED, 1);
|
|
powerOnTVOnStart = (bool)gCoreContext->GetNumSetting(POWERONTV_ONSTART, 1);
|
|
|
|
- defaultHDMIPort = 1;
|
|
if ("auto" != hdmi_port)
|
|
{
|
|
defaultHDMIPort = hdmi_port.toInt();
|
|
- if (defaultHDMIPort < 1 || defaultHDMIPort > 3)
|
|
- defaultHDMIPort = 1;
|
|
+ if (defaultHDMIPort < CEC_MIN_HDMI_PORTNUMBER || defaultHDMIPort > CEC_MAX_HDMI_PORTNUMBER)
|
|
+ defaultHDMIPort = CEC_DEFAULT_HDMI_PORT;
|
|
+ }
|
|
+ else
|
|
+ {
|
|
+ defaultHDMIPort = CEC_DEFAULT_HDMI_PORT;
|
|
}
|
|
- defaultHDMIPort = defaultHDMIPort << 12;
|
|
|
|
- defaultDeviceID = CECDEVICE_PLAYBACKDEVICE1;
|
|
if ("auto" != device_id)
|
|
{
|
|
int id = device_id.toInt();
|
|
- if (id < 1 || id > 3)
|
|
- id = 1;
|
|
- defaultDeviceID = (id == 1) ? CECDEVICE_PLAYBACKDEVICE1 :
|
|
- ((id == 2) ? CECDEVICE_PLAYBACKDEVICE2 :
|
|
- CECDEVICE_PLAYBACKDEVICE3);
|
|
+ switch (id)
|
|
+ {
|
|
+ case CEC_DEVICE_TYPE_TV:
|
|
+ case CEC_DEVICE_TYPE_RECORDING_DEVICE:
|
|
+ case CEC_DEVICE_TYPE_RESERVED:
|
|
+ case CEC_DEVICE_TYPE_TUNER:
|
|
+ case CEC_DEVICE_TYPE_PLAYBACK_DEVICE:
|
|
+ case CEC_DEVICE_TYPE_AUDIO_SYSTEM:
|
|
+ defaultDeviceID = (cec_device_type)id;
|
|
+ break;
|
|
+ default:
|
|
+ defaultDeviceID = CEC_DEFAULT_DEVICE_TYPE;
|
|
+ break;
|
|
+ }
|
|
+ }
|
|
+ else
|
|
+ {
|
|
+ defaultDeviceID = CEC_DEFAULT_DEVICE_TYPE;
|
|
}
|
|
|
|
+ LOG(VB_GENERAL, LOG_INFO, LOC + QString("base_dev= %1.")
|
|
+ .arg(base_dev));
|
|
+ if ("auto" != base_dev)
|
|
+ {
|
|
+ base_device = (cec_logical_address)base_dev.toInt();
|
|
+ LOG(VB_GENERAL, LOG_INFO, LOC + QString("base_device= %1.")
|
|
+ .arg(base_device));
|
|
+ switch (base_device)
|
|
+ {
|
|
+ case CECDEVICE_TV:
|
|
+ case CECDEVICE_RECORDINGDEVICE1:
|
|
+ case CECDEVICE_RECORDINGDEVICE2:
|
|
+ case CECDEVICE_TUNER1:
|
|
+ case CECDEVICE_PLAYBACKDEVICE1:
|
|
+ case CECDEVICE_AUDIOSYSTEM:
|
|
+ case CECDEVICE_TUNER2:
|
|
+ case CECDEVICE_TUNER3:
|
|
+ case CECDEVICE_PLAYBACKDEVICE2:
|
|
+ case CECDEVICE_RECORDINGDEVICE3:
|
|
+ case CECDEVICE_TUNER4:
|
|
+ case CECDEVICE_PLAYBACKDEVICE3:
|
|
+ case CECDEVICE_FREEUSE:
|
|
+ break;
|
|
+ case CECDEVICE_UNKNOWN:
|
|
+ case CECDEVICE_RESERVED1:
|
|
+ case CECDEVICE_RESERVED2:
|
|
+ case CECDEVICE_BROADCAST:
|
|
+ default:
|
|
+ base_device = (cec_logical_address)CEC_DEFAULT_BASE_DEVICE;
|
|
+ break;
|
|
+ }
|
|
+ }
|
|
+ else
|
|
+ {
|
|
+ base_device = (cec_logical_address)CEC_DEFAULT_BASE_DEVICE;
|
|
+ }
|
|
+
|
|
// create adapter interface
|
|
- cec_device_type_list list;
|
|
- list.Clear();
|
|
- list.Add(CEC_DEVICE_TYPE_PLAYBACK_DEVICE);
|
|
- adapter = LibCecInit("MythTV", list);
|
|
+ libcec_configuration configuration;
|
|
+ configuration.Clear();
|
|
+ configuration.clientVersion = LIBCEC_VERSION_CURRENT;
|
|
+ snprintf(configuration.strDeviceName, 13, "MythTV");
|
|
+ configuration.deviceTypes.Add(defaultDeviceID);
|
|
+ configuration.iPhysicalAddress = CEC_DEFAULT_PHYSICALADDRESS;
|
|
+ configuration.iHDMIPort = defaultHDMIPort;
|
|
+ LOG(VB_GENERAL, LOG_INFO, LOC + QString("using HDMI port %1.")
|
|
+ .arg(defaultHDMIPort));
|
|
+ configuration.baseDevice = base_device;
|
|
+ LOG(VB_GENERAL, LOG_INFO, LOC + QString("using base device %1.")
|
|
+ .arg(configuration.baseDevice));
|
|
+ configuration.callbacks = &callbacks;
|
|
+ ICECAdapter *adapter = LibCecInitialise(&configuration);
|
|
|
|
if (!adapter)
|
|
{
|
|
@@ -129,12 +231,12 @@ class CECAdapterPriv
|
|
return false;
|
|
}
|
|
|
|
- if (adapter->GetMinLibVersion() > MIN_LIBCEC_VERSION)
|
|
+ if ((configuration.serverVersion >> 12) > CEC_MIN_LIB_VERSION)
|
|
{
|
|
LOG(VB_GENERAL, LOG_ERR, LOC +
|
|
QString("The installed libCEC supports version %1 and above. "
|
|
"This version of MythTV only supports version %2.")
|
|
- .arg(adapter->GetMinLibVersion()).arg(MIN_LIBCEC_VERSION));
|
|
+ .arg(configuration.serverVersion).arg(CEC_MIN_LIB_VERSION));
|
|
return false;
|
|
}
|
|
|
|
@@ -185,12 +287,6 @@ class CECAdapterPriv
|
|
// get the vendor ID (for non-standard implementations)
|
|
adapter->GetDeviceVendorId(CECDEVICE_TV);
|
|
|
|
- // set the physical address
|
|
- adapter->SetPhysicalAddress(defaultHDMIPort);
|
|
-
|
|
- // set the logical address
|
|
- adapter->SetLogicalAddress(defaultDeviceID);
|
|
-
|
|
// switch input (if configured)
|
|
switchInput = true;
|
|
HandleActions();
|
|
@@ -210,7 +306,6 @@ class CECAdapterPriv
|
|
|
|
// delete adapter
|
|
adapter->Close();
|
|
- LogMessages();
|
|
UnloadLibCec(adapter);
|
|
|
|
LOG(VB_GENERAL, LOG_INFO, LOC + "Closing down CEC.");
|
|
@@ -219,14 +314,12 @@ class CECAdapterPriv
|
|
adapter = NULL;
|
|
}
|
|
|
|
- void LogMessages(void)
|
|
+ #if CEC_LIB_VERSION_MAJOR < 2
|
|
+ static int LogMessages(void *, const cec_log_message &message)
|
|
+ #else
|
|
+ static int LogMessages(void *, const cec_log_message message)
|
|
+ #endif
|
|
{
|
|
- if (!adapter || !valid)
|
|
- return;
|
|
-
|
|
- cec_log_message message;
|
|
- while (adapter->GetNextLogMessage(&message))
|
|
- {
|
|
QString msg(message.message);
|
|
int lvl = LOG_UNKNOWN;
|
|
switch (message.level)
|
|
@@ -237,19 +330,15 @@ class CECAdapterPriv
|
|
case CEC_LOG_DEBUG: lvl = LOG_DEBUG; break;
|
|
}
|
|
LOG(VB_GENERAL, lvl, LOC + QString("%1").arg(msg));
|
|
- }
|
|
+ return 0;
|
|
}
|
|
|
|
- void HandleCommands(void)
|
|
+ #if CEC_LIB_VERSION_MAJOR < 2
|
|
+ static int HandleCommands(void * /*cbParam*/, const cec_command &command)
|
|
+ #else
|
|
+ static int HandleCommands(void * /*cbParam*/, const cec_command command)
|
|
+ #endif
|
|
{
|
|
- if (!adapter || !valid)
|
|
- return;
|
|
-
|
|
- LogMessages();
|
|
-
|
|
- cec_command command;
|
|
- while (adapter->GetNextCommand(&command))
|
|
- {
|
|
LOG(VB_GENERAL, LOG_DEBUG, LOC +
|
|
QString("Command %1 from '%2' (%3) - destination '%4' (%5)")
|
|
.arg(command.opcode)
|
|
@@ -260,27 +349,76 @@ class CECAdapterPriv
|
|
|
|
switch (command.opcode)
|
|
{
|
|
- // TODO
|
|
+ // TODO handle CEC commands.
|
|
default:
|
|
break;
|
|
}
|
|
- }
|
|
+ return 0;
|
|
+ }
|
|
|
|
- LogMessages();
|
|
+ #if CEC_LIB_VERSION_MAJOR < 2
|
|
+ static int HandleConfigurationChanged(void * /*cbParam*/, const libcec_configuration &config)
|
|
+ #else
|
|
+ static int HandleConfigurationChanged(void * /*cbParam*/, const libcec_configuration config)
|
|
+ #endif
|
|
+ {
|
|
+ LOG(VB_GENERAL, LOG_INFO, LOC + "Adapter configuration changed.");
|
|
+ return 1;
|
|
}
|
|
|
|
- void HandleKeyPresses(void)
|
|
+ #if CEC_LIB_VERSION_MAJOR < 2
|
|
+ static int HandleAlerts(void * /*cbParam*/, const libcec_alert type, const libcec_parameter & /*param*/)
|
|
+ #else
|
|
+ static int HandleAlerts(void * /*cbParam*/, const libcec_alert type, const libcec_parameter /*param*/)
|
|
+ #endif
|
|
{
|
|
- if (!adapter || !valid)
|
|
- return;
|
|
+ switch (type) // TODO Handle alerts.
|
|
+ {
|
|
+ case CEC_ALERT_CONNECTION_LOST:
|
|
+ LOG(VB_GENERAL, LOG_ERR, LOC + "Connection lost - TODO: need to handle this!");
|
|
+ break;
|
|
+ default:
|
|
+ LOG(VB_GENERAL, LOG_ERR, LOC + "Received unknown alert.");
|
|
+ break;
|
|
+ }
|
|
+ return 0;
|
|
+ }
|
|
|
|
- cec_keypress key;
|
|
- if (!adapter->GetNextKeypress(&key))
|
|
- return;
|
|
+ #if CEC_LIB_VERSION_MAJOR < 2
|
|
+ static int HandleMenuStateChanged(void * /*cbParam*/, const cec_menu_state &state)
|
|
+ #else
|
|
+ static int HandleMenuStateChanged(void * /*cbParam*/, const cec_menu_state state)
|
|
+ #endif
|
|
+ {
|
|
+ LOG(VB_GENERAL, LOG_INFO, LOC + QString("CEC menu state %1")
|
|
+ .arg(state == CEC_MENU_STATE_ACTIVATED ? "Activated" : "Deactivated"));
|
|
+ return 1;
|
|
+ }
|
|
|
|
+ #if CEC_LIB_VERSION_MAJOR < 2
|
|
+ static void HandleSourceActivated(void * /*cbParam*/, const cec_logical_address &address, const &uint8_t activated)
|
|
+ #else
|
|
+ static void HandleSourceActivated(void * /*cbParam*/, const cec_logical_address address, const uint8_t activated)
|
|
+ #endif
|
|
+ {
|
|
+ LOG(VB_GENERAL, LOG_INFO, LOC + QString("Source %1 %2")
|
|
+ .arg(address).arg(activated ? "Activated" : "Deactivated"));
|
|
+
|
|
+ if (activated && resetSafe)
|
|
+ GetMythUI()->ResetScreensaver();
|
|
+ else
|
|
+ resetSafe = true;
|
|
+ }
|
|
+
|
|
+ #if CEC_LIB_VERSION_MAJOR < 2
|
|
+ static int HandleKeyPresses(void * /*cbParam*/, const cec_keypress &key)
|
|
+ #else
|
|
+ static int HandleKeyPresses(void * /*cbParam*/, const cec_keypress key)
|
|
+ #endif
|
|
+ {
|
|
// Ignore key down events and wait for the key 'up'
|
|
if (key.duration < 1)
|
|
- return;
|
|
+ return 0;
|
|
|
|
QString code;
|
|
int action = 0;
|
|
@@ -595,13 +733,12 @@ class CECAdapterPriv
|
|
.arg(code).arg(0 == action ? "(Not actioned)" : ""));
|
|
|
|
if (0 == action)
|
|
- return;
|
|
+ return 0;
|
|
|
|
GetMythUI()->ResetScreensaver();
|
|
QKeyEvent* ke = new QKeyEvent(QEvent::KeyPress, action, Qt::NoModifier);
|
|
qApp->postEvent(GetMythMainWindow(), (QEvent*)ke);
|
|
-
|
|
- LogMessages();
|
|
+ return 0;
|
|
}
|
|
|
|
void HandleActions(void)
|
|
@@ -629,7 +766,7 @@ class CECAdapterPriv
|
|
// HDMI input
|
|
if (switchInput && switchInputAllowed)
|
|
{
|
|
- if (adapter->SetActiveView())
|
|
+ if (adapter->SetActiveSource())
|
|
LOG(VB_GENERAL, LOG_INFO, LOC + "Asked TV to switch to this input.");
|
|
else
|
|
LOG(VB_GENERAL, LOG_ERR, LOC + "Failed to switch to this input.");
|
|
@@ -638,14 +775,14 @@ class CECAdapterPriv
|
|
powerOffTV = false;
|
|
powerOnTV = false;
|
|
switchInput = false;
|
|
-
|
|
- LogMessages();
|
|
}
|
|
|
|
ICECAdapter *adapter;
|
|
+ ICECCallbacks callbacks;
|
|
QString defaultDevice;
|
|
int defaultHDMIPort;
|
|
- cec_logical_address defaultDeviceID;
|
|
+ cec_device_type defaultDeviceID;
|
|
+ cec_logical_address base_device;
|
|
QTimer *timer;
|
|
bool valid;
|
|
bool powerOffTV;
|
|
@@ -728,8 +865,6 @@ void CECAdapter::Action(const QString &action)
|
|
void CECAdapter::Process(void)
|
|
{
|
|
gLock->lock();
|
|
- m_priv->HandleCommands();
|
|
- m_priv->HandleKeyPresses();
|
|
m_priv->HandleActions();
|
|
gLock->unlock();
|
|
}
|
|
diff --git a/mythtv/libs/libmythui/cecadapter.h b/mythtv/libs/libmythui/cecadapter.h
|
|
index e9cf6d6..bb5eba8 100644
|
|
--- a/mythtv/libs/libmythui/cecadapter.h
|
|
+++ b/mythtv/libs/libmythui/cecadapter.h
|
|
@@ -7,6 +7,7 @@
|
|
#define LIBCEC_ENABLED QString("libCECEnabled")
|
|
#define LIBCEC_DEVICE QString("libCECDevice")
|
|
#define LIBCEC_PORT QString("libCECPort")
|
|
+#define LIBCEC_BASE QString("libCECBase")
|
|
#define LIBCEC_DEVICEID QString("libCECDeviceID")
|
|
#define POWEROFFTV_ALLOWED QString("PowerOffTVAllowed")
|
|
#define POWEROFFTV_ONEXIT QString("PowerOffTVOnExit")
|