diff --git a/addon.xml b/addon.xml index 9bdb785..0777a50 100644 --- a/addon.xml +++ b/addon.xml @@ -1,5 +1,5 @@ - + diff --git a/ardundzdf.py b/ardundzdf.py index f80a3a0..6679f02 100644 --- a/ardundzdf.py +++ b/ardundzdf.py @@ -57,8 +57,8 @@ # VERSION -> addon.xml aktualisieren # 200 # Numerierung für Einzelupdate -VERSION = '5.0.3' -VDATE = '18.05.2024' +VERSION = '5.0.4' +VDATE = '26.05.2024' # (c) 2019 by Roland Scholz, rols1@gmx.de @@ -110,16 +110,7 @@ ICON_ZDF_BARRIEREARM = 'zdf-barrierearm.png' ICON_ZDF_BILDERSERIEN = 'zdf-bilderserien.png' -ICON_MAIN_POD = 'radio-podcasts.png' -ICON_POD_AZ = 'pod-az.png' -ICON_POD_FEATURE = 'pod-feature.png' -ICON_POD_TATORT = 'pod-tatort.png' -ICON_POD_RUBRIK = 'pod-rubriken.png' -ICON_POD_NEU = 'pod-neu.png' -ICON_POD_MEIST = 'pod-meist.png' -ICON_POD_REFUGEE = 'pod-refugee.png' -ICON_POD_FAVORITEN = 'pod-favoriten.png' - +ICON_MAIN_POD = 'radio-podcasts.png' # childs: Tonschnipsel ICON_MAIN_AUDIO = 'ard-audiothek.png' ICON_AUDIO_LIVE = 'ard-audio-live.png' ICON_AUDIO_AZ = 'ard-audio-az.png' @@ -7344,31 +7335,34 @@ def SenderLiveListe(title, listname, fanart, offset=0, onlySender=''): epg_date=''; epg_title=''; epg_text=''; summary=''; tagline='' EPG_ID = stringextract('', '', element) # -> EPG.EPG und Kontextmenü - PLog(EPG_ID) - # PLog(SETTINGS.getSetting('pref_use_epg')) # Voreinstellung: EPG nutzen? - nur mit Schema nutzbar - PLog('setting: ' + str(SETTINGS.getSetting('pref_use_epg'))) - if SETTINGS.getSetting('pref_use_epg') == 'true' and EPG_ID: # hier nur aktuelle Sendung - # Indices EPG_rec: 0=starttime, 1=href, 2=img, 3=sname, 4=stime, 5=summ, 6=vonbis: - try: - rec = EPG.EPG(ID=EPG_ID, mode='OnlyNow') # Daten holen - nur aktuelle Sendung - sname=''; stime=''; summ=''; vonbis='' # Fehler, ev. Sender EPG_ID nicht bekannt - if rec: - sname=py2_encode(rec[3]); stime=py2_encode(rec[4]); - summ=py2_encode(rec[5]); vonbis=py2_encode(rec[6]) - except: - sname=''; stime=''; summ=''; vonbis='' - - if sname: - title=py2_encode(title); - title = "%s: %s" % (title, sname) - if summ: - summary = py2_encode(summ) - else: - summary = '' - if vonbis: - tagline = u'Sendung: %s Uhr' % vonbis - else: - tagline = '' + if EPG_ID.strip() == "": + EPG_ID="dummy" # Kodi-Problem: ohne Wert verwendet addDir vorige EPG_ID + PLog("set_dummmy_EPG_ID: " + title) + PLog('setting: ' + str(SETTINGS.getSetting('pref_use_epg')))# EPG nutzen? + if SETTINGS.getSetting('pref_use_epg') == 'true': # hier nur aktuelle Sendung + if EPG_ID and EPG_ID != "dummy": + # Indices EPG_rec: 0=starttime, 1=href, 2=img, 3=sname, 4=stime, 5=summ, 6=vonbis: + try: + rec = EPG.EPG(ID=EPG_ID, mode='OnlyNow') # Daten holen - nur aktuelle Sendung + sname=''; stime=''; summ=''; vonbis='' # Fehler, ev. Sender EPG_ID nicht bekannt + if rec: + sname=py2_encode(rec[3]); stime=py2_encode(rec[4]); + summ=py2_encode(rec[5]); vonbis=py2_encode(rec[6]) + except: + sname=''; stime=''; summ=''; vonbis='' + + if sname: + title=py2_encode(title); + title = "%s: %s" % (title, sname) + if summ: + summary = py2_encode(summ) + else: + summary = '' + if vonbis: + tagline = u'[B]Sendung: %s Uhr[/B]' % vonbis + else: + tagline = '' + tagline = "%s\n[B]Tages-EPG[/B] via Kontext-Menü aufrufen." % tagline title = unescape(title) title = title.replace('JETZT:', '') # 'JETZT:' hier überflüssig @@ -7389,14 +7383,15 @@ def SenderLiveListe(title, listname, fanart, offset=0, onlySender=''): geo = stringextract('', '', element) PLog('geo: ' + geo) if geo: - tagline = 'Livestream nur in Deutschland zu empfangen!' + tagline = '%s\nLivestream nur in Deutschland zu empfangen!' % tagline PLog("Satz8:") PLog(title); PLog(link); PLog(img); PLog(summary); PLog(tagline[0:80]); descr = summary.replace('\n', '||') if tagline: - descr = "%s %s" % (tagline, descr) # -> Plot (PlayVideo) + descr = "%s %s" % (tagline, descr) # -> Plot (PlayVideo) + descr = descr.replace("\n", "||") title=py2_encode(title); link=py2_encode(link); img=py2_encode(img); descr=py2_encode(descr); fparams="&fparams={'path': '%s', 'thumb': '%s', 'title': '%s', 'descr': '%s'}" % (quote(link), diff --git a/changelog.txt b/changelog.txt index c3749b1..16d99ab 100644 --- a/changelog.txt +++ b/changelog.txt @@ -10,6 +10,42 @@ CHANGE HISTORY max_col 97 -------------- +26.05.2024 5.0.4 + AudioStartLive: Fix Variable für RadioPlaylist-Button PlayList statt + streamList. + Audio_get_cluster_single: Playlist-Erweiterung für Livestreams wie Sender- + links in AudioStartLive. + AudioPlayMP3: Erweiterung für Livestreams - Download als m3u-Datei (wie + AudioStartLive). + Download- und Aufnahme-Tools: Integration von m3u-Dateien - Anpassung in + DownloadsList und VideoTools. + Haupt-PRG + Module: Fix "SyntaxWarning: invalid escape sequence" - Verwendung + raw-String statt unicode in allen re.search-Statements, Bsp.: (u'\((.*?)\) -> + (r'\((.*?)\). + ARDStartSingle: Umstellung auf api-Web-Quellen für alle Streams - Abzweig + Livestreams angepasst (direkt -> PlayVideo), weitere Anpassungen in s.u. + Funktion ARDStartVideoWebUTget entfernt (subtitle-Extrakt in ARDStartSingle). + XLGetVideoLists (TagesschauXL): entfernt - seit 01.05.2023 nicht genutzt. + ARDStartVideoMP4get, ARDStartVideoHBBTVget: Auswertung Bitraten entfernt + (nicht mehr genutzt) - Anpassung StreamsShow (Haupt-PRG). + ARDStartVideoHBBTVget: dash-Streams ausgenommen (./tagesschau_1.mpd läuft + nicht). + ARDStartVideoHLSget: Einzelauflösungen via Parseplaylist vorerst deaktiviert + (unübersichtl. Liste), Anpassung PlayVideo_Direct (Beibehaltung des 1. Links + als Default-URL. + ARD_get_strmStream: Nutzung Web-api-Quellen - Angleichung an ARDStartSingle. + HBBTV- und MP4-Listen: Bitraten-Auswertung entfernt - Anpassung in Haupt- + PRG und den Modulen. + Codec-Fixes (relevant für PYTHON2): py2_decode(tag) in AudioStartLive + (Audiothek), py2_decode(page) in get_json_content (ARDnew). + thread_getepg (EPG Nachladen im Hintergrund): Nutzung concurrent.futures für + Python ab V3.2 - wegen möglicher Klemmer vorerst deaktivert. + leer-Rückgabe in EPG - Kodi-Problem: ohne Wert verwendet addDir vorige EPG_ID + im Kontext-Menü. Anpassung SenderLiveListe (Ersatz leeren EPG_ID-Wert durch + "dummy"). + Haupt-PRG, Verz. ../resources/images: obsolete Icons pod-favoriten, pod-meist, + pod-feature, pod-neu, pod-refugee, pod-rubriken, pod-tatort entfernt (obsolet). + 12.05.2024 5.0.3 ZDF-Funktion International gelöscht. Api-Aufruf in Main_ZDF->ZDF_RubrikSingle. ZDF-Startseite: Menüs ergänzt: "Livestreams im Ausland", "Terra X plus Schule" diff --git a/resources/lib/EPG.py b/resources/lib/EPG.py index f10e31c..75daaf6 100644 --- a/resources/lib/EPG.py +++ b/resources/lib/EPG.py @@ -33,7 +33,7 @@ # für Python 2.* muss der Aufruf Kontextmenü unterdrückt # werden, sonst öffnet das Modul bei jedem Menüwechsel # ein leeres textviewer-Fenster -if "'context'" in str(sys.argv): # Aufruf Kontextmenü +if "'context'" in str(sys.argv): # Aufruf Kontextmenü from util import * msg = "callfrom_context" else: @@ -67,6 +67,7 @@ # Dateilock nicht erf. # 26.10.2020 Update der Datei livesenderTV.xml hinzugefügt - entf. ab # 09.10.2021 siehe update_single +# 21.05.2024 Nutzung concurrent.futures. Aufruf als Thread (ohne: Klemmer) # def thread_getepg(EPGACTIVE, DICTSTORE, PLAYLIST): PLog('thread_getepg:') @@ -74,25 +75,34 @@ def thread_getepg(EPGACTIVE, DICTSTORE, PLAYLIST): open(EPGACTIVE, 'w').close() # Aktiv-Signal setzen (DICT "EPGActive") icon = R('tv-EPG-all.png') xbmcgui.Dialog().notification("EPG-Download", "gestartet",icon,3000) - xbmc.sleep(1000 * 10) # verzög. Start (klemmt vor Notification) - + xbmc.sleep(1000) # Klemmer bei sleep vor Notification sort_playlist = get_sort_playlist(PLAYLIST) - PLog(len(sort_playlist)) - + PLog("Sender: %d" % len(sort_playlist)) + ID_list=[] for i in range(len(sort_playlist)): rec = sort_playlist[i] - title = rec[0] # Debug - ID = rec[1] - - if ID: + ID = rec[1] + if ID: # Sender mit tvtoday-ID + ID_list.append(ID) fname = os.path.join(DICTSTORE, "EPG_%s" % ID) if os.path.exists(fname): # n.v. oder soeben entfernt? os.remove(fname) # entf. -> erneuern - rec = EPG(ID=ID, load_only=True) # Seite laden + speichern - xbmc.sleep(250) # Systemlast verringern - - xbmcgui.Dialog().notification("EPG-Download", "fertig: %d Sender" % (i+1),icon,3000) + + PLog("ID_list: " + str(ID_list)) + # ID_list = ['3SAT', 'SWR'] # Debug + # 23.05.2024 Testbetrieb concurrent.futures, wg. möglicher Klemmer bei + # Menüwechseln deaktiviert + #if sys.version_info.major >= 3 and sys.version_info.minor >= 2: + # import concurrent.futures # concurrent.futures ab PY 3.2 + # with concurrent.futures.ThreadPoolExecutor() as executor: + # futures = {executor.submit(EPG, ID, load_only=True): ID for ID in ID_list} + # PLog("futures: %d" % len(futures)) + #else: + for ID in ID_list: + EPG(ID=ID, load_only=True) # Seite laden + speichern + + xbmcgui.Dialog().notification("EPG-Download", "fertig: %d Sender" % len(sort_playlist),icon,3000) return @@ -310,10 +320,13 @@ def update_single(PluginAbsPath): # def EPG(ID, mode=None, day_offset=None, load_only=False): PLog('EPG_ID: ' + ID) - PLog(mode) + PLog(mode); PLog(day_offset); PLog(load_only); + url="http://www.tvtoday.de/programm/standard/sender/%s.html" % ID Dict_ID = "EPG_%s" % ID PLog(url) + if ID == "dummy": + return [] page = Dict("load", Dict_ID, CacheTime=EPGCacheTime) PLog(type(page)) @@ -556,11 +569,10 @@ def get_unixtime(day_offset=None, onlynow=False): for rec in EPG_rec: sname=rec[3] if 'JETZT' in sname: - PLog(str(rec)) + PLog("context_now: " + str(rec)) break cnt=cnt+1 EPG_rec = EPG_rec[cnt:] - PLog(str(EPG_rec[cnt:])) lines=[] for rec in EPG_rec: @@ -574,10 +586,13 @@ def get_unixtime(day_offset=None, onlynow=False): except Exception as exception: PLog("EPG_rec_error: " + str(exception)) + #PLog(lines) # Debug if len(lines) == 0: - title = "%s | keine EPG-Daten gefunden" % title - lines = "\n".join(lines) - xbmcgui.Dialog().textviewer(title , lines ,usemono=True) + icon = R('tv-EPG-all.png') + xbmcgui.Dialog().notification(title, "keine EPG-Daten vorhanden",icon,3000) + else: + lines = "\n".join(lines) + xbmcgui.Dialog().textviewer(title , lines ,usemono=True) diff --git a/resources/lib/TagesschauXL.py b/resources/lib/TagesschauXL.py index a5a3276..556a28e 100644 --- a/resources/lib/TagesschauXL.py +++ b/resources/lib/TagesschauXL.py @@ -4,7 +4,7 @@ # Modul für für die Inhalte von tagesschau.de ################################################################################ # 14 # Numerierung für Einzelupdate -# Stand: 13.03.2024 +# Stand: 16.05.2024 # # Anpassung Python3: Modul future # Anpassung Python3: Modul kodi_six + manuelle Anpassungen @@ -775,30 +775,6 @@ def get_content_json(item): return typ,av_typ,title,tag,summ,img,stream # ---------------------------------------------------------------------- -# Bau HBBTV_List (leer), HLS_List, MP4_List via Modul ARDnew -# page -> json -# 01.05.2023 z.Z. nicht genutzt - häufige Beiträge mit nur 1 Stream -def XLGetVideoLists(li, title, StreamArray): - PLog('XLGetVideoLists:') - PLog('import_ARDnew:'); # ARDStartVideoHLSget, ARDStartVideoMP4get - import resources.lib.ARDnew as ARDnew - - # Formate siehe StreamsShow # HLS_List + MP4_List anlegen - # generisch: "Label | Bandbreite | Auflösung | Titel#Url" - # fehlende Bandbreiten + Auflösungen werden ergänzt - HBBTV_List='' # nur ZDF - HLS_List = ARDnew.ARDStartVideoHLSget(title, StreamArray) # Extrakt HLS - PLog("HLS_List: " + str(HLS_List)[:80]) - MP4_List = ARDnew.ARDStartVideoMP4get(title, StreamArray) # Extrakt MP4 - Dict("store", 'TXL_HLS_List', HLS_List) - Dict("store", 'TXL_MP4_List', MP4_List) - PLog("download_list: " + str(MP4_List)[:80]) - PLog(str(MP4_List)) - - return HLS_List,MP4_List,HBBTV_List - -# ---------------------------------------------------------------------- - diff --git a/resources/lib/arte.py b/resources/lib/arte.py index 61ad111..039d6d5 100644 --- a/resources/lib/arte.py +++ b/resources/lib/arte.py @@ -858,7 +858,6 @@ def get_streams_api_v2(page, title, summ): if url.find("Trailer") > 0: trailer = True mediaType = stringextract('"protocol":"', '"', rec) - bitrate = "" mainQuality = stringextract('"mainQuality":', '}', rec) quality = stringextract('"code":"', '"', mainQuality) # Bsp.: "XQ" @@ -931,6 +930,7 @@ def get_streams_api_v2(page, title, summ): # Streamdetails via api-opa-Call # Arte verwendet bei HBBTV MP4-Formate wie ZDF (HLS_List bleibt leer) # audioLabel: Abgleich setting pref_arte_streams in get_bestdownload +# 16.05.2024 Auswertung Bitraten entfernt # def get_streams_api_opa(page, title,summ, mode="hls_mp4"): PLog("get_streams_api_opa: " + mode) @@ -944,7 +944,6 @@ def get_streams_api_opa(page, title,summ, mode="hls_mp4"): versions = stringextract('"versions":', '"creationDate', rec) mediaType = stringextract('"mediaType": "', '"', rec) - bitrate = stringextract('"bitrate":', ',', rec) quality = stringextract('"quality": "', '"', rec) width = stringextract('"width": ', ',', rec) height = stringextract('"height": ', ',', rec) @@ -979,8 +978,8 @@ def get_streams_api_opa(page, title,summ, mode="hls_mp4"): if ".mp4" in url: # MP4 title_url = u"%s#%s" % (title, url) mp4 = "MP4 [B]%s[/B]" % (lang) - item = u"%s | %s ** Bitrate %s ** Auflösung %s ** %s" %\ - (mp4, quality, bitrate, size, title_url) + item = u"%s | %s ** Auflösung %s ** %s" %\ + (mp4, quality, size, title_url) MP4_List.append(item) return trailer,MP4_List diff --git a/resources/lib/util.py b/resources/lib/util.py index 5af91c9..6a070a4 100644 --- a/resources/lib/util.py +++ b/resources/lib/util.py @@ -137,7 +137,6 @@ def check_AddonXml(mark): PLAYLIST_ALIVE = os.path.join(ADDON_DATA, "playlist_alive") # Lebendsignal für PlayMonitor (leer) PLAYLIST = 'livesenderTV.xml' # TV-Sender-Logos erstellt von: Arauco (Plex-Forum). -ICON_MAIN_POD = 'radio-podcasts.png' ICON_MAIN_AUDIO = 'ard-audiothek.png' ICON_MAIN_ZDFMOBILE = 'zdf-mobile.png' ICON_PHOENIX = 'phoenix.png' @@ -4108,8 +4107,8 @@ def ShowSeekPos(player, url): # "Streamuhrzeit" if linkid: # Sendungsnavigation: ARD-EPG für Zeitstrahl laden buf_events, event_end = get_ARD_LiveEPG(epg_url, title_sender, date_format, now, TotalTime) event_end = int(event_end) - header = u"Sendungen: zurück-, Maus-Taste r.)" - txt = "Anzahl Sendungen: %d" % len(buf_events) + txt = u"Liste: #-Taste, Maus-Taste rechts" + header = "Anzahl Sendungen: %d" % len(buf_events) dur=10000 if len(buf_events) == 0: header = u"Sendungen" @@ -4245,7 +4244,7 @@ def ShowSeekPos(player, url): # "Streamuhrzeit" # 14.1.2023 ohne Timer (Aufruf sekündlich durch ShowSeekPos) # class KeyListener(xbmcgui.WindowXMLDialog): - PLog("KeyListener: started") + PLog("KeyListener: loaded") ACTION_MOUSE_LEFT_CLICK = 100 ACTION_MOUSE_RIGHT_CLICK = 101 @@ -4268,10 +4267,10 @@ def onInit(self): def onAction(self, action): actionId = action.getId() if actionId == self.ACTION_MOUSE_RIGHT_CLICK: - self.key = "61467" # hier für rechte Maustaste + self.key = "61467" # hier für rechte Maustaste else: code = action.getButtonCode() - #PLog("code: " + str(code)) # Debug + PLog("code: " + str(code)) # Debug self.key = None if code == 0 else str(code) self.close()