def _start_show(self, items): # we need to start the update thread after the deep copy of self.items finishes thread = img_update(data=self._get_items) thread.start() # start with image 1 cur_img = self.image1 order = [1, 2] # loop until onScreensaverDeactivated is called while (not self.Monitor.abortRequested()) and (not self.stop): # keep track of image position, needed to save the offset self.position = self.offset # iterate through all the images for img in items[self.offset:]: # cache file may be outdated if self.slideshow_type == '2' and not xbmcvfs.exists(img[0]): continue # add image to gui cur_img.setImage(img[0], False) # add background image to gui if self.slideshow_scale == 'false' and self.slideshow_bg == 'true': if order[0] == 1: self.image3.setImage(img[0], False) else: self.image4.setImage(img[0], False) # give xbmc some time to load the image if not self.startup: xbmc.sleep(1000) else: self.startup = False # get exif and iptc tags if enabled in settings and we have an image that can contain this data datetime = '' title = '' description = '' keywords = '' exif = False iptc_ti = False iptc_de = False iptc_ke = False if self.slideshow_type == '2' and ( (self.slideshow_date == 'true') or (self.slideshow_iptc == 'true')) and (os.path.splitext( img[0])[1].lower() in EXIF_TYPES): imgfile = xbmcvfs.File(img[0]) # get exif date if self.slideshow_date == 'true': try: exiftags = EXIFvfs.process_file( imgfile, details=False, stop_tag='DateTimeOriginal') if exiftags.has_key('EXIF DateTimeOriginal'): datetime = str( exiftags['EXIF DateTimeOriginal']).decode( 'utf-8') # sometimes exif date returns useless data, probably no date set on camera if datetime == '0000:00:00 00:00:00': datetime = '' else: try: # localize the date format date = datetime[:10].split(':') time = datetime[10:] if DATEFORMAT[1] == 'm': datetime = date[1] + '-' + date[ 2] + '-' + date[0] + ' ' + time elif DATEFORMAT[1] == 'd': datetime = date[2] + '-' + date[ 1] + '-' + date[0] + ' ' + time else: datetime = date[0] + '-' + date[ 1] + '-' + date[2] + ' ' + time except: pass exif = True except: pass # get iptc title, description and keywords if self.slideshow_iptc == 'true': try: iptc = IPTCInfo(imgfile) iptctags = iptc.data if iptctags.has_key(105): title = iptctags[105].decode('utf-8') iptc_ti = True if iptctags.has_key(120): description = iptctags[120].decode('utf-8') iptc_de = True if iptctags.has_key(25): keywords = ', '.join( iptctags[25]).decode('utf-8') iptc_ke = True except: pass if (not iptc_ti or not iptc_de or not iptc_ke): try: tags = XMP_Tags().get_xmp( img[0] ) # passing the imgfile object does not work for some reason if (not iptc_ti) and tags.has_key('dc:title'): title = tags['dc:title'] iptc_ti = True if (not iptc_de ) and tags.has_key('dc:description'): description = tags['dc:description'] iptc_de = True if (not iptc_ke ) and tags.has_key('dc:subject'): keywords = tags['dc:subject'].replace( '||', ', ') iptc_ke = True except: pass imgfile.close() # display exif date if we have one if exif: self.datelabel.setLabel('[I]' + datetime + '[/I]') self.datelabel.setVisible(True) else: self.datelabel.setVisible(False) # display iptc data if we have any if iptc_ti or iptc_de or iptc_ke: self.textbox.setText( '[CR]'.join([title, keywords] if title == description else [title, description, keywords])) self.textbox.setVisible(True) else: self.textbox.setVisible(False) # get the file or foldername if enabled in settings if self.slideshow_name != '0': if self.slideshow_name == '1': if self.slideshow_type == '2': NAME, EXT = os.path.splitext( os.path.basename(img[0])) else: NAME = img[1] elif self.slideshow_name == '2': ROOT, NAME = os.path.split(os.path.dirname(img[0])) elif self.slideshow_name == '3': if self.slideshow_type == '2': ROOT, FOLDER = os.path.split( os.path.dirname(img[0])) FILE, EXT = os.path.splitext( os.path.basename(img[0])) NAME = FOLDER + ' / ' + FILE else: ROOT, FOLDER = os.path.split( os.path.dirname(img[0])) NAME = FOLDER + ' / ' + img[1] self.namelabel.setLabel(NAME) # set animations if self.slideshow_effect == '0': # add slide anim self._set_prop('Slide%d' % order[0], '0') self._set_prop('Slide%d' % order[1], '1') else: # add random slide/zoom anim if self.slideshow_effect == '2': # add random slide/zoom anim self._anim(cur_img) # add fade anim, used for both fade and slide/zoom anim self._set_prop('Fade%d' % order[0], '0') self._set_prop('Fade%d' % order[1], '1') # add fade anim to background images if self.slideshow_bg == 'true': self._set_prop('Fade1%d' % order[0], '0') self._set_prop('Fade1%d' % order[1], '1') # define next image if cur_img == self.image1: cur_img = self.image2 order = [2, 1] else: cur_img = self.image1 order = [1, 2] # slideshow time in secs (we already slept for 1 second) count = self.slideshow_time - 1 # display the image for the specified amount of time while (not self.Monitor.abortRequested()) and ( not self.stop) and count > 0: count -= 1 xbmc.sleep(1000) # break out of the for loop if onScreensaverDeactivated is called if self.stop or self.Monitor.abortRequested(): break self.position += 1 self.offset = 0 items = copy.deepcopy(self.items)
def _start_show(self, items): # we need to start the update thread after the deep copy of self.items finishes thread = img_update(data=self._get_items) thread.start() music_thread = mpd_update(server="localhost", port=6600, data=self.mpd_data) music_thread.start() # start with image 1 cur_img = self.image1 order = [1,2] # loop until onScreensaverDeactivated is called while (not self.Monitor.abortRequested()) and (not self.stop): # keep track of image position, needed to save the offset self.position = self.offset # iterate through all the images for img in items[self.offset:]: # cache file may be outdated if self.slideshow_type == 2 and not xbmcvfs.exists(img[0]): continue # add image to gui cur_img.setImage(img[0],False) # add background image to gui if (not self.slideshow_scale) and self.slideshow_bg: if order[0] == 1: self.image3.setImage(img[0],False) else: self.image4.setImage(img[0],False) # give xbmc some time to load the image if not self.startup: xbmc.sleep(1000) else: self.startup = False # get exif and iptc tags if enabled in settings and we have an image that can contain this data datetime = '' title = '' description = '' keywords = '' exif = False iptc_ti = False iptc_de = False iptc_ke = False if self.slideshow_type == 2 and (self.slideshow_date or self.slideshow_iptc) and (os.path.splitext(img[0])[1].lower() in EXIF_TYPES): # get exif date if self.slideshow_date: exiffile = xbmcvfs.File(img[0]) try: exiftags = exifreadvfs.process_file(exiffile, details=False, stop_tag='DateTimeOriginal') if 'EXIF DateTimeOriginal' in exiftags: datetime = bytes(exiftags['EXIF DateTimeOriginal'].values).decode('utf-8') # sometimes exif date returns useless data, probably no date set on camera if datetime == '0000:00:00 00:00:00': datetime = '' else: try: # localize the date format date = datetime[:10].split(':') time = datetime[10:] if DATEFORMAT[1] == 'm': datetime = date[1] + '-' + date[2] + '-' + date[0] + ' ' + time elif DATEFORMAT[1] == 'd': datetime = date[2] + '-' + date[1] + '-' + date[0] + ' ' + time else: datetime = date[0] + '-' + date[1] + '-' + date[2] + ' ' + time except: pass exif = True except: pass exiffile.close() # get iptc title, description and keywords if self.slideshow_iptc: iptcfile = xbmcvfs.File(img[0]) try: iptc = IPTCInfo(iptcfile) if 105 in iptc.data and iptc.data[105]: title = bytes(iptc.data[105]).decode('utf-8') iptc_ti = True if 120 in iptc.data and iptc.data[120]: description = bytes(iptc.data[120]).decode('utf-8') iptc_de = True if 25 in iptc.data and iptc.data[25]: tags = [] for tag in iptc.data[25]: tags.append(bytes(tag).decode('utf-8')) keywords = ', '.join(tags) iptc_ke = True except: pass iptcfile.close() # get xmp title, description and subject if (not iptc_ti or not iptc_de or not iptc_ke): try: # why do i need to recreate the file object? xmpfile = xbmcvfs.File(img[0]) data = xmpfile.readBytes().decode('cp437') titlematch = re.search(r'<dc:title.*?rdf:Alt.*?rdf:li.*?>(.*?)<', data, flags=re.DOTALL) if titlematch and not iptc_ti: title = titlematch.group(1) iptc_ti = True descmatch = re.search(r'<dc:description.*?rdf:Alt.*?rdf:li.*?>(.*?)<', data, flags=re.DOTALL) if descmatch and not iptc_de: description = descmatch.group(1) iptc_de = True subjmatch = re.search(r'<dc:subject.*?rdf:Bag.*?>(.*?)</rdf:Bag', data, flags=re.DOTALL) if subjmatch and not iptc_ke: subjectpart = ''.join(subjmatch.group(1).split()) subjectgroup = subjectpart.replace('<rdf:li>','').split('</rdf:li>') keywords = ' '.join(subjectgroup) iptc_ke = True except: pass xmpfile.close() # display exif date if we have one if exif: self.datelabel.setLabel('[I]' + datetime + '[/I]') self.datelabel.setVisible(True) else: self.datelabel.setVisible(False) # get the file or foldername if enabled in settings if self.slideshow_name != 0: if self.slideshow_name == 1: if self.slideshow_type == 2: NAME, EXT = os.path.splitext(os.path.basename(img[0])) else: NAME = img[1] elif self.slideshow_name == 2: ROOT, NAME = os.path.split(os.path.dirname(img[0])) elif self.slideshow_name == 3: if self.slideshow_type == 2: ROOT, FOLDER = os.path.split(os.path.dirname(img[0])) FILE, EXT = os.path.splitext(os.path.basename(img[0])) NAME = FOLDER + ' / ' + FILE else: ROOT, FOLDER = os.path.split(os.path.dirname(img[0])) NAME = FOLDER + ' / ' + img[1] self.namelabel.setLabel(NAME) nameback_left = 1270 - len(NAME)*14 if nameback_left < 626: nameback_left = 626 self.namebackground.setPosition(nameback_left , 625) # set animations if self.slideshow_effect == 0: # add slide anim self._set_prop('Slide%d' % order[0], '0') self._set_prop('Slide%d' % order[1], '1') elif self.slideshow_effect == 1 or self.slideshow_effect == 2: # add random slide/zoom anim if self.slideshow_effect == 2: # add random slide/zoom anim self._anim(cur_img) # add fade anim, used for both fade and slide/zoom anim self._set_prop('Fade%d' % order[0], '0') self._set_prop('Fade%d' % order[1], '1') # add fade anim to background images if self.slideshow_bg: self._set_prop('Fade1%d' % order[0], '0') self._set_prop('Fade1%d' % order[1], '1') # define next image if cur_img == self.image1: cur_img = self.image2 order = [2,1] else: cur_img = self.image1 order = [1,2] # slideshow time in secs (we already slept for 1 second) count = self.slideshow_time - 1 # display the image for the specified amount of time while (not self.Monitor.abortRequested()) and (not self.stop) and count > 0: self._update_song_info() count -= 0.2 xbmc.sleep(200) # break out of the for loop if onScreensaverDeactivated is called if self.stop or self.Monitor.abortRequested(): break self.position += 1 self.offset = 0 items = copy.deepcopy(self.items)