X-Git-Url: https://git.piment-noir.org/?a=blobdiff_plain;f=src%2FLibCecSharp%2FLibCecSharp.cpp;h=81c857fb2fed67c2475365eab980289d32aaf21b;hb=1664420dd2cd46c9daafeb541c45d055d176bcdc;hp=4e76ead7a6ab264252ef97040448e9909fb93729;hpb=7e24a7d2d1984468c562277965ab0768f5458549;p=deb_libcec.git diff --git a/src/LibCecSharp/LibCecSharp.cpp b/src/LibCecSharp/LibCecSharp.cpp index 4e76ead..81c857f 100644 --- a/src/LibCecSharp/LibCecSharp.cpp +++ b/src/LibCecSharp/LibCecSharp.cpp @@ -45,19 +45,20 @@ namespace CecSharp public: LibCecSharp(LibCECConfiguration ^config) { - m_configuration = config; - CecCallbackMethods::EnableCallbacks(m_configuration->Callbacks); - if (!InitialiseLibCec()) + m_callbacks = config->Callbacks; + CecCallbackMethods::EnableCallbacks(m_callbacks); + if (!InitialiseLibCec(config)) throw gcnew Exception("Could not initialise LibCecSharp"); } LibCecSharp(String ^ strDeviceName, CecDeviceTypeList ^ deviceTypes) { - m_configuration = gcnew LibCECConfiguration(); - m_configuration->SetCallbacks(this); - m_configuration->DeviceName = strDeviceName; - m_configuration->DeviceTypes = deviceTypes; - if (!InitialiseLibCec()) + m_callbacks = gcnew CecCallbackMethods(); + LibCECConfiguration ^config = gcnew LibCECConfiguration(); + config->SetCallbacks(this); + config->DeviceName = strDeviceName; + config->DeviceTypes = deviceTypes; + if (!InitialiseLibCec(config)) throw gcnew Exception("Could not initialise LibCecSharp"); } @@ -74,35 +75,69 @@ namespace CecSharp m_libCec = NULL; } - bool InitialiseLibCec(void) + bool InitialiseLibCec(LibCECConfiguration ^config) { marshal_context ^ context = gcnew marshal_context(); - libcec_configuration config; - GetConfiguration(context, config); + libcec_configuration libCecConfig; + ConvertConfiguration(context, config, libCecConfig); - m_libCec = (ICECAdapter *) CECInitialise(&config); + m_libCec = (ICECAdapter *) CECInitialise(&libCecConfig); + config->Update(libCecConfig); delete context; return m_libCec != NULL; } - void GetConfiguration(marshal_context ^context, libcec_configuration &config) + void ConvertConfiguration(marshal_context ^context, LibCECConfiguration ^netConfig, CEC::libcec_configuration &config) { config.Clear(); - _snprintf_s(config.strDeviceName, 13, context->marshal_as(m_configuration->DeviceName)); + const char *strDeviceName = context->marshal_as(netConfig->DeviceName); + memcpy_s(config.strDeviceName, 13, strDeviceName, 13); for (unsigned int iPtr = 0; iPtr < 5; iPtr++) - config.deviceTypes.types[iPtr] = (cec_device_type)m_configuration->DeviceTypes->Types[iPtr]; - - config.iPhysicalAddress = m_configuration->PhysicalAddress; - config.baseDevice = (cec_logical_address)m_configuration->BaseDevice; - config.iHDMIPort = m_configuration->HDMIPort; - config.clientVersion = (cec_client_version)m_configuration->ClientVersion; - config.bGetSettingsFromROM = m_configuration->GetSettingsFromROM; - config.bPowerOnStartup = m_configuration->PowerOnStartup; - config.bPowerOffShutdown = m_configuration->PowerOffShutdown; - config.bPowerOffScreensaver = m_configuration->PowerOffScreensaver; - config.bPowerOffOnStandby = m_configuration->PowerOffOnStandby; + config.deviceTypes.types[iPtr] = (cec_device_type)netConfig->DeviceTypes->Types[iPtr]; + + config.bAutodetectAddress = netConfig->AutodetectAddress ? 1 : 0; + config.iPhysicalAddress = netConfig->PhysicalAddress; + config.baseDevice = (cec_logical_address)netConfig->BaseDevice; + config.iHDMIPort = netConfig->HDMIPort; + config.clientVersion = (cec_client_version)netConfig->ClientVersion; + config.bGetSettingsFromROM = netConfig->GetSettingsFromROM ? 1 : 0; + config.bActivateSource = netConfig->ActivateSource ? 1 : 0; + config.tvVendor = (cec_vendor_id)netConfig->TvVendor; + config.wakeDevices.Clear(); + for (int iPtr = 0; iPtr < 16; iPtr++) + { + if (netConfig->WakeDevices->IsSet((CecLogicalAddress)iPtr)) + config.wakeDevices.Set((cec_logical_address)iPtr); + } + config.powerOffDevices.Clear(); + for (int iPtr = 0; iPtr < 16; iPtr++) + { + if (netConfig->PowerOffDevices->IsSet((CecLogicalAddress)iPtr)) + config.powerOffDevices.Set((cec_logical_address)iPtr); + } + config.bPowerOffScreensaver = netConfig->PowerOffScreensaver ? 1 : 0; + config.bPowerOffOnStandby = netConfig->PowerOffOnStandby ? 1 : 0; + + if (netConfig->ServerVersion >= CecServerVersion::Version1_5_1) + config.bSendInactiveSource = netConfig->SendInactiveSource ? 1 : 0; + + if (netConfig->ServerVersion >= CecServerVersion::Version1_6_0) + { + config.bPowerOffDevicesOnStandby = netConfig->PowerOffDevicesOnStandby ? 1 : 0; + config.bShutdownOnStandby = netConfig->ShutdownOnStandby ? 1 : 0; + } + + if (netConfig->ServerVersion >= CecServerVersion::Version1_6_2) + { + const char *strDeviceLanguage = context->marshal_as(netConfig->DeviceLanguage); + memcpy_s(config.strDeviceLanguage, 3, strDeviceLanguage, 3); + } + + if (netConfig->ServerVersion >= CecServerVersion::Version1_6_3) + config.bMonitorOnly = netConfig->MonitorOnlyClient ? 1 : 0; + config.callbacks = &g_cecCallbacks; } @@ -127,6 +162,8 @@ namespace CecSharp bool Open(String ^ strPort, int iTimeoutMs) { + CecCallbackMethods::EnableCallbacks(m_callbacks); + EnableCallbacks(m_callbacks); marshal_context ^ context = gcnew marshal_context(); const char* strPortC = context->marshal_as(strPort); bool bReturn = m_libCec->Open(strPortC, iTimeoutMs); @@ -136,15 +173,22 @@ namespace CecSharp void Close(void) { - // delete the callbacks, since these might already have been destroyed in .NET - m_libCec->EnableCallbacks(NULL, NULL); + DisableCallbacks(); m_libCec->Close(); } + virtual void DisableCallbacks(void) override + { + // delete the callbacks, since these might already have been destroyed in .NET + CecCallbackMethods::DisableCallbacks(); + if (m_libCec) + m_libCec->EnableCallbacks(NULL, NULL); + } + virtual bool EnableCallbacks(CecCallbackMethods ^ callbacks) override { if (m_libCec && CecCallbackMethods::EnableCallbacks(callbacks)) - return m_libCec->EnableCallbacks(NULL, &g_cecCallbacks); + return m_libCec->EnableCallbacks((void*)GetCallbackPtr(), &g_cecCallbacks); return false; } @@ -190,7 +234,7 @@ namespace CecSharp cec_keypress key; if (m_libCec->GetNextKeypress(&key)) { - return gcnew CecKeypress(key.keycode, key.duration); + return gcnew CecKeypress((CecUserControlCode)key.keycode, key.duration); } return gcnew CecKeypress(); @@ -315,6 +359,11 @@ namespace CecSharp return (CecPowerStatus) m_libCec->GetDevicePowerStatus((cec_logical_address) logicalAddress); } + void RescanActiveDevices(void) + { + m_libCec->RescanActiveDevices(); + } + CecLogicalAddresses ^ GetActiveDevices(void) { CecLogicalAddresses ^ retVal = gcnew CecLogicalAddresses(); @@ -417,17 +466,7 @@ namespace CecSharp if (m_libCec->GetCurrentConfiguration(&config)) { - configuration->BaseDevice = (CecLogicalAddress)config.baseDevice; - configuration->DeviceName = gcnew String(config.strDeviceName); - configuration->HDMIPort = config.iHDMIPort; - configuration->PhysicalAddress = config.iPhysicalAddress; - configuration->PowerOffOnStandby = config.bPowerOffOnStandby == 1; - configuration->PowerOffScreensaver = config.bPowerOffScreensaver == 1; - configuration->PowerOffShutdown = config.bPowerOffShutdown == 1; - configuration->PowerOnStartup = config.bPowerOnStartup == 1; - configuration->UseTVMenuLanguage = config.bUseTVMenuLanguage == 1; - for (unsigned int iPtr = 0; iPtr < 5; iPtr++) - m_configuration->DeviceTypes->Types[iPtr] = (CecDeviceType)config.deviceTypes.types[iPtr]; + configuration->Update(config); return true; } return false; @@ -442,7 +481,7 @@ namespace CecSharp { marshal_context ^ context = gcnew marshal_context(); libcec_configuration config; - GetConfiguration(context, config); + ConvertConfiguration(context, configuration, config); bool bReturn = m_libCec->PersistConfiguration(&config); @@ -450,6 +489,43 @@ namespace CecSharp return bReturn; } + bool SetConfiguration(LibCECConfiguration ^configuration) + { + marshal_context ^ context = gcnew marshal_context(); + libcec_configuration config; + ConvertConfiguration(context, configuration, config); + + bool bReturn = m_libCec->SetConfiguration(&config); + + delete context; + return bReturn; + } + + bool IsLibCECActiveSource() + { + return m_libCec->IsLibCECActiveSource(); + } + + bool GetDeviceInformation(String ^ port, LibCECConfiguration ^configuration, uint32_t timeoutMs) + { + bool bReturn(false); + marshal_context ^ context = gcnew marshal_context(); + + libcec_configuration config; + config.Clear(); + + const char* strPortC = port->Length > 0 ? context->marshal_as(port) : NULL; + + if (m_libCec->GetDeviceInformation(strPortC, &config, timeoutMs)) + { + configuration->Update(config); + bReturn = true; + } + + delete context; + return bReturn; + } + String ^ ToString(CecLogicalAddress iAddress) { const char *retVal = m_libCec->ToString((cec_logical_address)iAddress); @@ -510,8 +586,31 @@ namespace CecSharp return gcnew String(retVal); } + String ^ ToString(CecClientVersion version) + { + const char *retVal = m_libCec->ToString((cec_client_version)version); + return gcnew String(retVal); + } + + String ^ ToString(CecServerVersion version) + { + const char *retVal = m_libCec->ToString((cec_server_version)version); + return gcnew String(retVal); + } + + String ^ GetLibInfo() + { + const char *retVal = m_libCec->GetLibInfo(); + return gcnew String(retVal); + } + + void InitVideoStandalone() + { + m_libCec->InitVideoStandalone(); + } + private: ICECAdapter * m_libCec; - LibCECConfiguration ^m_configuration; + CecCallbackMethods ^ m_callbacks; }; }