X-Git-Url: https://git.cweiske.de/enigma2.git/blobdiff_plain/ff84dc4ee5f57e24a0777930d5482ee4ff53da0e..cd038ce28d53719a27e7009365dd74fec19357df:/lib/service/servicedvb.cpp diff --git a/lib/service/servicedvb.cpp b/lib/service/servicedvb.cpp index 51061c37..b3c15738 100644 --- a/lib/service/servicedvb.cpp +++ b/lib/service/servicedvb.cpp @@ -25,9 +25,40 @@ DEFINE_REF(eStaticServiceDVBInformation); RESULT eStaticServiceDVBInformation::getName(const eServiceReference &ref, std::string &name) { - if ( ref.name.length() ) + eServiceReferenceDVB &service = (eServiceReferenceDVB&)ref; + if ( !ref.name.empty() ) { - name = ref.name; + if (service.getParentTransportStreamID().get()) // linkage subservice + { + ePtr service_center; + if (!eServiceCenter::getInstance(service_center)) + { + eServiceReferenceDVB parent = service; + parent.setTransportStreamID( service.getParentTransportStreamID() ); + parent.setServiceID( service.getParentServiceID() ); + parent.setParentTransportStreamID(eTransportStreamID(0)); + parent.setParentServiceID(eServiceID(0)); + parent.name=""; + ePtr service_info; + if (!service_center->info(parent, service_info)) + { + if (!service_info->getName(parent, name)) + { + // just show short name + unsigned int pos = name.find("\xc2\x86"); + if ( pos != std::string::npos ) + name.erase(0, pos+2); + pos = name.find("\xc2\x87"); + if ( pos != std::string::npos ) + name.erase(pos); + name+=" - "; + } + } + } + } + else + name=""; + name += ref.name; return 0; } else @@ -66,7 +97,7 @@ RESULT eStaticServiceDVBBouquetInformation::getName(const eServiceReference &ref return err; } - const eBouquet *bouquet=0; + eBouquet *bouquet=0; if ((err = db->getBouquet(ref, bouquet)) != 0) { eDebug("eStaticServiceDVBBouquetInformation::getName failed.. getBouquet failed!"); @@ -173,11 +204,10 @@ RESULT eDVBPVRServiceOfflineOperations::getListOfFilenames(std::list q; - if (m_parent.path.size()) + if (!m_parent.path.empty()) { eDVBChannelQuery::compile(q, m_parent.path); if (!q) @@ -271,6 +301,55 @@ int eDVBServiceList::compareLessEqual(const eServiceReference &a, const eService return m_query->compareLessEqual((const eServiceReferenceDVB&)a, (const eServiceReferenceDVB&)b); } +RESULT eDVBServiceList::startEdit(ePtr &res) +{ + if (m_parent.flags & eServiceReference::flagDirectory) // bouquet + { + ePtr db; + ePtr resm; + + if (eDVBResourceManager::getInstance(resm) || resm->getChannelList(db)) + return -1; + + if (db->getBouquet(m_parent, m_bouquet) != 0) + return -1; + + res = this; + + return 0; + } + res = 0; + return -1; +} + +RESULT eDVBServiceList::addService(eServiceReference &ref) +{ + if (!m_bouquet) + return -1; + return m_bouquet->addService(ref); +} + +RESULT eDVBServiceList::removeService(eServiceReference &ref) +{ + if (!m_bouquet) + return -1; + return m_bouquet->removeService(ref); +} + +RESULT eDVBServiceList::moveService(eServiceReference &ref, int pos) +{ + if (!m_bouquet) + return -1; + return m_bouquet->moveService(ref, pos); +} + +RESULT eDVBServiceList::flushChanges() +{ + if (!m_bouquet) + return -1; + return m_bouquet->flushChanges(); +} + RESULT eServiceFactoryDVB::play(const eServiceReference &ref, ePtr &ptr) { ePtr service; @@ -284,8 +363,15 @@ RESULT eServiceFactoryDVB::play(const eServiceReference &ref, ePtr &ptr) { - ptr = new eDVBServiceRecord((eServiceReferenceDVB&)ref); - return 0; + if (ref.path.empty()) + { + ptr = new eDVBServiceRecord((eServiceReferenceDVB&)ref); + return 0; + } else + { + ptr = 0; + return -1; + } } RESULT eServiceFactoryDVB::list(const eServiceReference &ref, ePtr &ptr) @@ -303,34 +389,39 @@ RESULT eServiceFactoryDVB::list(const eServiceReference &ref, ePtr &ptr) { - /* do we have a PVR service? */ - if (ref.flags & eServiceReference::flagDirectory) // bouquet + /* is a listable service? */ + if ((ref.flags & eServiceReference::flagDirectory) == eServiceReference::flagDirectory) // bouquet { - ptr = new eStaticServiceDVBBouquetInformation; - return 0; + if ( !ref.name.empty() ) // satellites or providers list + ptr = new eStaticServiceDVBInformation; + else // a dvb bouquet + ptr = new eStaticServiceDVBBouquetInformation; } - else if (ref.path.size()) - { + else if (!ref.path.empty()) /* do we have a PVR service? */ ptr = new eStaticServiceDVBPVRInformation(ref); - return 0; - } - else + else // normal dvb service { ePtr service; - int r = lookupService(service, ref); - if (r) + if (lookupService(service, ref)) // no eDVBService avail for this reference ( Linkage Services... ) ptr = new eStaticServiceDVBInformation; else /* eDVBService has the iStaticServiceInformation interface, so we pass it here. */ ptr = service; - return 0; } + return 0; } -RESULT eServiceFactoryDVB::offlineOperations(const eServiceReference &, ePtr &ptr) +RESULT eServiceFactoryDVB::offlineOperations(const eServiceReference &ref, ePtr &ptr) { - ptr = 0; - return -1; + if (ref.path.empty()) + { + ptr = 0; + return -1; + } else + { + ptr = new eDVBPVRServiceOfflineOperations(ref); + return 0; + } } RESULT eServiceFactoryDVB::lookupService(ePtr &service, const eServiceReference &ref) @@ -365,18 +456,16 @@ RESULT eServiceFactoryDVB::lookupService(ePtr &service, const eServ } eDVBServicePlay::eDVBServicePlay(const eServiceReference &ref, eDVBService *service): - m_reference(ref), m_dvb_service(service), m_service_handler(0) + m_reference(ref), m_dvb_service(service), m_service_handler(0), m_is_paused(0) { m_is_pvr = !ref.path.empty(); CONNECT(m_service_handler.serviceEvent, eDVBServicePlay::serviceEvent); CONNECT(m_event_handler.m_eit_changed, eDVBServicePlay::gotNewEvent); - eDebug("DVB start (play)"); } eDVBServicePlay::~eDVBServicePlay() { - eDebug("DVB stop (play)"); } void eDVBServicePlay::gotNewEvent() @@ -397,7 +486,6 @@ void eDVBServicePlay::gotNewEvent() void eDVBServicePlay::serviceEvent(int event) { - eDebug("service event %d", event); switch (event) { case eDVBServicePMTHandler::eventTuned: @@ -405,16 +493,27 @@ void eDVBServicePlay::serviceEvent(int event) ePtr m_demux; if (!m_service_handler.getDemux(m_demux)) { -// eventStartedEventAcquisition - m_event_handler.start(m_demux, ((eServiceReferenceDVB&)m_reference).getServiceID().get()); - } else - eDebug("no event data available :( "); -// eventNoEvent + eServiceReferenceDVB &ref = (eServiceReferenceDVB&) m_reference; + int sid = ref.getParentServiceID().get(); + if (!sid) + sid = ref.getServiceID().get(); + if ( ref.getParentTransportStreamID().get() && + ref.getParentTransportStreamID() != ref.getTransportStreamID() ) + m_event_handler.startOther(m_demux, sid); + else + m_event_handler.start(m_demux, sid); + } + break; + } + case eDVBServicePMTHandler::eventTuneFailed: + { + eDebug("DVB service failed to tune"); + m_event((iPlayableService*)this, evTuneFailed); break; } case eDVBServicePMTHandler::eventNewProgramInfo: { - int vpid = -1, apid = -1, pcrpid = -1; + int vpid = -1, apid = -1, apidtype = -1, pcrpid = -1; eDVBServicePMTHandler::program program; if (m_service_handler.getProgramInfo(program)) eDebug("getting program info failed."); @@ -445,7 +544,10 @@ void eDVBServicePlay::serviceEvent(int event) i != program.audioStreams.end(); ++i) { if (apid == -1) + { apid = i->pid; + apidtype = i->type; + } if (i != program.audioStreams.begin()) eDebugNoNewLine(", "); eDebugNoNewLine("%04x", i->pid); @@ -468,7 +570,8 @@ void eDVBServicePlay::serviceEvent(int event) if (m_decoder) { m_decoder->setVideoPID(vpid); - m_decoder->setAudioPID(apid, 0); + m_current_audio_stream = 0; + m_decoder->setAudioPID(apid, apidtype); if (!m_is_pvr) m_decoder->setSyncPCR(pcrpid); else @@ -497,6 +600,7 @@ RESULT eDVBServicePlay::start() int r; eDebug("starting DVB service"); r = m_service_handler.tune((eServiceReferenceDVB&)m_reference); + eDebug("tune result: %d", r); m_event(this, evStart); return 0; } @@ -515,11 +619,32 @@ RESULT eDVBServicePlay::connectEvent(const Slot2 &ev RESULT eDVBServicePlay::pause(ePtr &ptr) { - // not yet possible, maybe later... + if (m_is_pvr) + { + ptr = this; + return 0; + } + ptr = 0; return -1; } +RESULT eDVBServicePlay::setSlowMotion(int ratio) +{ + if (m_decoder) + return m_decoder->setSlowMotion(ratio); + else + return -1; +} + +RESULT eDVBServicePlay::setFastForward(int ratio) +{ + if (m_decoder) + m_decoder->setFastForward(ratio); + else + return -1; +} + RESULT eDVBServicePlay::seek(ePtr &ptr) { if (m_is_pvr) @@ -545,11 +670,50 @@ RESULT eDVBServicePlay::getLength(pts_t &len) return pvr_channel->getLength(len); } +RESULT eDVBServicePlay::pause() +{ + if (!m_is_paused && m_decoder) + { + m_is_paused = 1; + return m_decoder->freeze(0); + } else + return -1; +} + +RESULT eDVBServicePlay::unpause() +{ + if (m_is_paused && m_decoder) + { + m_is_paused = 0; + return m_decoder->unfreeze(); + } else + return -1; +} + RESULT eDVBServicePlay::seekTo(pts_t to) { return -1; } +RESULT eDVBServicePlay::seekRelative(int direction, pts_t to) +{ + eDebug("eDVBServicePlay::seekRelative: jump %d, %lld", direction, to); + + ePtr pvr_channel; + + if (m_service_handler.getPVRChannel(pvr_channel)) + return -1; + + to *= direction; + + ePtr demux; + m_service_handler.getDemux(demux); + if (!demux) + return -1; + + return pvr_channel->seekTo(demux, 1, to); +} + RESULT eDVBServicePlay::getPlayPosition(pts_t &pos) { ePtr pvr_channel; @@ -557,7 +721,18 @@ RESULT eDVBServicePlay::getPlayPosition(pts_t &pos) if (m_service_handler.getPVRChannel(pvr_channel)) return -1; - return pvr_channel->getCurrentPosition(pos); + ePtr demux; + m_service_handler.getDemux(demux); + if (!demux) + return -1; + + return pvr_channel->getCurrentPosition(demux, pos); +} + +RESULT eDVBServicePlay::frontendStatusInfo(ePtr &ptr) +{ + ptr = this; + return 0; } RESULT eDVBServicePlay::info(ePtr &ptr) @@ -566,6 +741,18 @@ RESULT eDVBServicePlay::info(ePtr &ptr) return 0; } +RESULT eDVBServicePlay::audioTracks(ePtr &ptr) +{ + ptr = this; + return 0; +} + +RESULT eDVBServicePlay::subServices(ePtr &ptr) +{ + ptr = this; + return 0; +} + RESULT eDVBServicePlay::getName(std::string &name) { if (m_dvb_service) @@ -573,7 +760,10 @@ RESULT eDVBServicePlay::getName(std::string &name) m_dvb_service->getName(m_reference, name); if (name.empty()) name = "(...)"; - } else + } + else if (!m_reference.name.empty()) + eStaticServiceDVBInformation().getName(m_reference, name); + else name = "DVB service"; return 0; } @@ -583,6 +773,172 @@ RESULT eDVBServicePlay::getEvent(ePtr &evt, int nownext) return m_event_handler.getEvent(evt, nownext); } +int eDVBServicePlay::getInfo(int w) +{ + eDVBServicePMTHandler::program program; + + if (m_service_handler.getProgramInfo(program)) + return -1; + + switch (w) + { + case sVideoPID: if (program.videoStreams.empty()) return -1; return program.videoStreams[0].pid; + case sAudioPID: if (program.audioStreams.empty()) return -1; return program.audioStreams[m_current_audio_stream].pid; + case sPCRPID: return program.pcrPid; + case sPMTPID: return program.pmtPid; + case sTXTPID: return -1; + + case sSID: return ((const eServiceReferenceDVB&)m_reference).getServiceID().get(); + case sONID: return ((const eServiceReferenceDVB&)m_reference).getOriginalNetworkID().get(); + case sTSID: return ((const eServiceReferenceDVB&)m_reference).getTransportStreamID().get(); + case sNamespace: return ((const eServiceReferenceDVB&)m_reference).getDVBNamespace().get(); + case sProvider: if (!m_dvb_service) return -1; return -2; + default: + return -1; + } +} + +std::string eDVBServicePlay::getInfoString(int w) +{ + switch (w) + { + case sProvider: + if (!m_dvb_service) return ""; + return m_dvb_service->m_provider_name; + default: + return ""; + } +} + +int eDVBServicePlay::getNumberOfTracks() +{ + eDVBServicePMTHandler::program program; + if (m_service_handler.getProgramInfo(program)) + return 0; + return program.audioStreams.size(); +} + +RESULT eDVBServicePlay::selectTrack(unsigned int i) +{ + int ret = selectAudioStream(i); + + if (m_decoder->start()) + return -5; + + return ret; +} + +RESULT eDVBServicePlay::getTrackInfo(struct iAudioTrackInfo &info, unsigned int i) +{ + eDVBServicePMTHandler::program program; + + if (m_service_handler.getProgramInfo(program)) + return -1; + + if (i >= program.audioStreams.size()) + return -2; + + if (program.audioStreams[i].type == eDVBServicePMTHandler::audioStream::atMPEG) + info.m_description = "MPEG"; + else if (program.audioStreams[i].type == eDVBServicePMTHandler::audioStream::atAC3) + info.m_description = "AC3"; + else if (program.audioStreams[i].type == eDVBServicePMTHandler::audioStream::atDTS) + info.m_description = "DTS"; + else + info.m_description = "???"; + + if (program.audioStreams[i].component_tag != -1) + { + ePtr evt; + if (!m_event_handler.getEvent(evt, 0)) + { + ePtr data; + if (!evt->getComponentData(data, program.audioStreams[i].component_tag)) + info.m_language = data->getText(); + } + } + + if (info.m_language.empty()) + info.m_language = program.audioStreams[i].language_code; + + return 0; +} + +int eDVBServicePlay::selectAudioStream(int i) +{ + eDVBServicePMTHandler::program program; + + if (m_service_handler.getProgramInfo(program)) + return -1; + + if ((unsigned int)i >= program.audioStreams.size()) + return -2; + + if (!m_decoder) + return -3; + + if (m_decoder->setAudioPID(program.audioStreams[i].pid, program.audioStreams[i].type)) + return -4; + + m_current_audio_stream = i; + + return 0; +} + +int eDVBServicePlay::getFrontendInfo(int w) +{ + if (m_is_pvr) + return 0; + eUsePtr channel; + if(m_service_handler.getChannel(channel)) + return 0; + ePtr fe; + if(channel->getFrontend(fe)) + return 0; + return fe->readFrontendData(w); +} + +int eDVBServicePlay::getNumberOfSubservices() +{ + ePtr evt; + if (!m_event_handler.getEvent(evt, 0)) + return evt->getNumOfLinkageServices(); + return 0; +} + +RESULT eDVBServicePlay::getSubservice(eServiceReference &sub, unsigned int n) +{ + ePtr evt; + if (!m_event_handler.getEvent(evt, 0)) + { + if (!evt->getLinkageService(sub, n)) + { + eServiceReferenceDVB &subservice = (eServiceReferenceDVB&) sub; + eServiceReferenceDVB ¤t = (eServiceReferenceDVB&) m_reference; + subservice.setDVBNamespace(current.getDVBNamespace()); + if ( current.getParentTransportStreamID().get() ) + { + subservice.setParentTransportStreamID( current.getParentTransportStreamID() ); + subservice.setParentServiceID( current.getParentServiceID() ); + } + else + { + subservice.setParentTransportStreamID( current.getTransportStreamID() ); + subservice.setParentServiceID( current.getServiceID() ); + } + if ( subservice.getParentTransportStreamID() == subservice.getTransportStreamID() && + subservice.getParentServiceID() == subservice.getServiceID() ) + { + subservice.setParentTransportStreamID( eTransportStreamID(0) ); + subservice.setParentServiceID( eServiceID(0) ); + } + return 0; + } + } + sub.type=eServiceReference::idInvalid; + return -1; +} + DEFINE_REF(eDVBServicePlay) eAutoInitPtr init_eServiceFactoryDVB(eAutoInitNumbers::service+1, "eServiceFactoryDVB");