Пример #1
0
def get_avatar_pixbuf_encoded_mime(photo):
    """
    Return the pixbuf of the image

    Photo is a dictionary containing PHOTO information.
    """
    if not isinstance(photo, dict):
        return None, None, None
    img_decoded = None
    avatar_encoded = None
    avatar_mime_type = None
    if 'BINVAL' in photo:
        img_encoded = photo['BINVAL']
        avatar_encoded = img_encoded
        try:
            img_decoded = base64.decodestring(img_encoded)
        except Exception:
            pass
    if img_decoded:
        if 'TYPE' in photo:
            avatar_mime_type = photo['TYPE']
            pixbuf = gtkgui_helpers.get_pixbuf_from_data(img_decoded)
        else:
            pixbuf, avatar_mime_type = gtkgui_helpers.get_pixbuf_from_data(
                                            img_decoded, want_type=True)
    else:
        pixbuf = None
    return pixbuf, avatar_encoded, avatar_mime_type
Пример #2
0
def get_avatar_pixbuf_encoded_mime(photo):
    """
    Return the pixbuf of the image

    Photo is a dictionary containing PHOTO information.
    """
    if not isinstance(photo, dict):
        return None, None, None
    img_decoded = None
    avatar_encoded = None
    avatar_mime_type = None
    if 'BINVAL' in photo:
        img_encoded = photo['BINVAL']
        avatar_encoded = img_encoded
        try:
            img_decoded = base64.b64decode(img_encoded.encode('utf-8'))
        except Exception:
            pass
    if img_decoded:
        if 'TYPE' in photo:
            avatar_mime_type = photo['TYPE']
            pixbuf = gtkgui_helpers.get_pixbuf_from_data(img_decoded)
        else:
            pixbuf, avatar_mime_type = gtkgui_helpers.get_pixbuf_from_data(
                img_decoded, want_type=True)
    else:
        pixbuf = None
    return pixbuf, avatar_encoded, avatar_mime_type
Пример #3
0
def get_avatar_pixbuf_encoded_mime(photo):
	'''return the pixbuf of the image
	photo is a dictionary containing PHOTO information'''
	if not isinstance(photo, dict):
		return None, None, None
	img_decoded = None
	avatar_encoded = None
	avatar_mime_type = None
	if photo.has_key('BINVAL') and photo.has_key('TYPE'):
		img_encoded = photo['BINVAL']
		avatar_encoded = img_encoded
		avatar_mime_type = photo['TYPE']
		try:
			img_decoded = base64.decodestring(img_encoded)
		except:
			pass
	elif photo.has_key('EXTVAL'):
		url = photo['EXTVAL']
		try:
			fd = urllib.urlopen(url)
			img_decoded = fd.read()
		except:
			pass
	if img_decoded:
		pixbuf = gtkgui_helpers.get_pixbuf_from_data(img_decoded)
	else:
		pixbuf = None
	return pixbuf, avatar_encoded, avatar_mime_type
Пример #4
0
    def on_set_avatar_button_clicked(self, widget):
        def on_ok(widget, path_to_file):
            must_delete = False
            filesize = os.path.getsize(path_to_file)  # in bytes
            invalid_file = False
            msg = ''
            if os.path.isfile(path_to_file):
                stat = os.stat(path_to_file)
                if stat[6] == 0:
                    invalid_file = True
                    msg = _('File is empty')
            else:
                invalid_file = True
                msg = _('File does not exist')
            if not invalid_file and filesize > 16384:  # 16 kb
                try:
                    pixbuf = gtk.gdk.pixbuf_new_from_file(path_to_file)
                    # get the image at 'notification size'
                    # and hope that user did not specify in ACE crazy size
                    scaled_pixbuf = gtkgui_helpers.get_scaled_pixbuf(
                        pixbuf, 'tooltip')
                except gobject.GError, msg:  # unknown format
                    # msg should be string, not object instance
                    msg = str(msg)
                    invalid_file = True
            if invalid_file:
                if True:  # keep identation
                    dialogs.ErrorDialog(_('Could not load image'), msg)
                    return
            if filesize > 16384:
                if scaled_pixbuf:
                    path_to_file = os.path.join(gajim.TMP, 'avatar_scaled.png')
                    scaled_pixbuf.save(path_to_file, 'png')
                    must_delete = True

            fd = open(path_to_file, 'rb')
            data = fd.read()
            pixbuf = gtkgui_helpers.get_pixbuf_from_data(data)
            try:
                # rescale it
                pixbuf = gtkgui_helpers.get_scaled_pixbuf(pixbuf, 'vcard')
            except AttributeError:  # unknown format
                dialogs.ErrorDialog(_('Could not load image'))
                return
            self.dialog.destroy()
            self.dialog = None
            button = self.xml.get_widget('PHOTO_button')
            image = button.get_image()
            image.set_from_pixbuf(pixbuf)
            button.show()
            text_button = self.xml.get_widget('NOPHOTO_button')
            text_button.hide()
            self.avatar_encoded = base64.encodestring(data)
            # returns None if unknown type
            self.avatar_mime_type = mimetypes.guess_type(path_to_file)[0]
            if must_delete:
                try:
                    os.remove(path_to_file)
                except OSError:
                    gajim.log.debug('Cannot remove %s' % path_to_file)
Пример #5
0
    def on_event_added(self, event):
        account = event.account
        jid = event.jid
        when = time.localtime()
        contact = ""
        key = (account, jid)

        if event.type_ == "chat" or \
        event.type_ == "printed_chat" or \
        event.type_ == "normal" or \
        event.type_ == "printed_normal" or \
        event.type_ == "file-request" or \
        event.type_ == "jingle-incoming":
            contact = gajim.contacts.get_contact_from_full_jid(account, jid)
            if contact:
                contact = contact.get_shown_name()
            else:
                contact = jid
        elif event.type_ == "pm" or event.type_ == "printed_pm":
            contact = gajim.get_nick_from_jid(gajim.get_room_from_fjid(jid)) + \
                    "/" + gajim.get_room_and_nick_from_fjid(jid)[1]
        elif event.type_ == "printed_marked_gc_msg":
            contact = gajim.get_nick_from_jid(gajim.get_room_from_fjid(jid))
        else:
            return
        #print account, jid, when, contact
        event.time = when
        if key not in self.events:
            icon = None
            if gajim.config.get("show_avatars_in_roster"):
                pixbuf = gtkgui_helpers.get_avatar_pixbuf_from_cache(jid)
                if pixbuf not in (None, "ask"):
                    icon = gtk.Image()
                    icon.set_from_pixbuf(pixbuf)
                else:
                    file_path = gtkgui_helpers.get_path_to_generic_or_avatar(jid)
                    if os.path.isfile(file_path):
                        fd = fopen(file_path, 'rb')
                        data = fd.read()
                        icon = gtk.Image()
                        icon.set_from_pixbuf(gtkgui_helpers.get_pixbuf_from_data(data))
            item = gtk.ImageMenuItem(contact + " (1)")
            if icon:
                item.set_image(icon)
                item.set_always_show_image(True)
            item.connect("activate", self.event_raise, event)
            item.show()
            self.menu.insert(item, self.menuEventInsertIndex)
            self.event_separator.show()
            self.events[key] = {}
            self.events[key]['item'] = item
            self.events[key]['contact'] = contact
            self.events[key]['events'] = [event]
        else:
            self.events[key]['events'].append(event)
            item = self.events[key]['item']
            item.set_label(self.events[key]['contact'] +
                " (" + str(len(self.events[key]['events'])) + ")")
        self.indicator.set_status(appindicator.STATUS_ATTENTION)
Пример #6
0
    def on_set_avatar_button_clicked(self, widget):
        def on_ok(widget, path_to_file):
            must_delete = False
            filesize = os.path.getsize(path_to_file)  # in bytes
            invalid_file = False
            msg = ""
            if os.path.isfile(path_to_file):
                stat = os.stat(path_to_file)
                if stat[6] == 0:
                    invalid_file = True
                    msg = _("File is empty")
            else:
                invalid_file = True
                msg = _("File does not exist")
            if not invalid_file and filesize > 16384:  # 16 kb
                try:
                    pixbuf = gtk.gdk.pixbuf_new_from_file(path_to_file)
                    # get the image at 'notification size'
                    # and hope that user did not specify in ACE crazy size
                    scaled_pixbuf = gtkgui_helpers.get_scaled_pixbuf(pixbuf, "tooltip")
                except gobject.GError, msg:  # unknown format
                    # msg should be string, not object instance
                    msg = str(msg)
                    invalid_file = True
            if invalid_file:
                if True:  # keep identation
                    dialogs.ErrorDialog(_("Could not load image"), msg)
                    return
            if filesize > 16384:
                if scaled_pixbuf:
                    path_to_file = os.path.join(gajim.TMP, "avatar_scaled.png")
                    scaled_pixbuf.save(path_to_file, "png")
                    must_delete = True

            fd = open(path_to_file, "rb")
            data = fd.read()
            pixbuf = gtkgui_helpers.get_pixbuf_from_data(data)
            try:
                # rescale it
                pixbuf = gtkgui_helpers.get_scaled_pixbuf(pixbuf, "vcard")
            except AttributeError:  # unknown format
                dialogs.ErrorDialog(_("Could not load image"))
                return
            self.dialog.destroy()
            self.dialog = None
            button = self.xml.get_widget("PHOTO_button")
            image = button.get_image()
            image.set_from_pixbuf(pixbuf)
            button.show()
            text_button = self.xml.get_widget("NOPHOTO_button")
            text_button.hide()
            self.avatar_encoded = base64.encodestring(data)
            # returns None if unknown type
            self.avatar_mime_type = mimetypes.guess_type(path_to_file)[0]
            if must_delete:
                try:
                    os.remove(path_to_file)
                except OSError:
                    gajim.log.debug("Cannot remove %s" % path_to_file)
Пример #7
0
    def on_event_added(self, event):
        account = event.account
        jid = event.jid
        when = time.time()
        contact = ""
        key = (account, jid)

        if event.type_ == "chat" or \
        event.type_ == "printed_chat" or \
        event.type_ == "normal" or \
        event.type_ == "printed_normal" or \
        event.type_ == "file-request" or \
        event.type_ == "jingle-incoming":
            contact = gajim.contacts.get_contact_from_full_jid(account, jid)
            if contact:
                contact = contact.get_shown_name()
            else:
                contact = jid
        elif event.type_ == "pm" or event.type_ == "printed_pm":
            contact = gajim.get_nick_from_jid(gajim.get_room_from_fjid(jid)) + \
                    "/" + gajim.get_room_and_nick_from_fjid(jid)[1]
        elif event.type_ == "printed_marked_gc_msg":
            contact = gajim.get_nick_from_jid(gajim.get_room_from_fjid(jid))
        else:
            return
        #print account, jid, when, contact
        event.time = when
        if key not in self.events:
            icon = None
            if gajim.config.get("show_avatars_in_roster"):
                pixbuf = gtkgui_helpers.get_avatar_pixbuf_from_cache(jid)
                if pixbuf not in (None, "ask"):
                    icon = gtk.Image()
                    icon.set_from_pixbuf(pixbuf)
                else:
                    file_path = gtkgui_helpers.get_path_to_generic_or_avatar(jid)
                    if os.path.isfile(file_path):
                        fd = fopen(file_path, 'rb')
                        data = fd.read()
                        icon = gtk.Image()
                        icon.set_from_pixbuf(gtkgui_helpers.get_pixbuf_from_data(data))
            item = gtk.ImageMenuItem(contact + " (1)")
            if icon:
                item.set_image(icon)
                item.set_always_show_image(True)
            item.connect("activate", self.event_raise, event)
            item.show()
            self.menu.insert(item, self.menuEventInsertIndex)
            self.event_separator.show()
            self.events[key] = {}
            self.events[key]['item'] = item
            self.events[key]['contact'] = contact
            self.events[key]['events'] = [event]
        else:
            self.events[key]['events'].append(event)
            item = self.events[key]['item']
            item.set_label(self.events[key]['contact'] +
                " (" + str(len(self.events[key]['events'])) + ")")
        self.indicator.set_status(appindicator.STATUS_ATTENTION)
Пример #8
0
	def on_set_avatar_button_clicked(self, widget):
		f = None
		dialog = gtk.FileChooserDialog(_('Choose Avatar'), None,
			gtk.FILE_CHOOSER_ACTION_OPEN,
			(gtk.STOCK_CANCEL, gtk.RESPONSE_CANCEL,
			gtk.STOCK_OPEN, gtk.RESPONSE_OK))
		dialog.set_default_response(gtk.RESPONSE_OK)
		filtr = gtk.FileFilter()
		filtr.set_name(_('All files'))
		filtr.add_pattern('*')
		dialog.add_filter(filtr)

		filtr = gtk.FileFilter()
		filtr.set_name(_('Images'))
		filtr.add_mime_type('image/png')
		filtr.add_mime_type('image/jpeg')
		filtr.add_mime_type('image/gif')
		filtr.add_mime_type('image/tiff')
		filtr.add_mime_type('image/x-xpixmap') # xpm
		dialog.add_filter(filtr)
		dialog.set_filter(filtr)
		dialog.set_use_preview_label(False)
		dialog.set_preview_widget(gtk.Image())
		dialog.connect('selection-changed', self.update_preview)

		done = False
		while not done:
			response = dialog.run()
			if response == gtk.RESPONSE_OK:
				f = dialog.get_filename()
				try:
					f = f.decode(sys.getfilesystemencoding())
				except UnicodeError:
					pass
				else:
					filesize = os.path.getsize(f) # in bytes
					if filesize > 32768: # 32 kb
						dialogs.ErrorDialog(_('The filesize of image "%s" is too large')\
							% os.path.basename(f),
						_('The file must not be more than 32 kilobytes.')).get_response()
						continue
				if self.image_is_ok(f):
					done = True
			else: # Cancel or WM X button
				done = True
		dialog.destroy()

		if response == gtk.RESPONSE_OK:
			fd = open(f, 'rb')
			data = fd.read()
			pixbuf = gtkgui_helpers.get_pixbuf_from_data(data)
			image = self.xml.get_widget('PHOTO_image')
			image.set_from_pixbuf(pixbuf)
			self.avatar_encoded = base64.encodestring(data)
			# returns None if unknown type
			self.avatar_mime_type = mimetypes.guess_type(f)[0]
Пример #9
0
    def populate(self, contact):
        """
        Populate the Tooltip Grid with data of from the contact
        """
        self.clear_tooltip()

        self.nick.set_text(contact.get_shown_name())
        self.nick.show()

        # Status Message
        if contact.status:
            status = contact.status.strip()
            if status != '':
                self.status.set_text(status)
                self.status.show()

        # Status
        show = helpers.get_uf_show(contact.show)
        self.user_show.set_markup(colorize_status(show))
        self.user_show.show()

        # JID
        if contact.jid.strip():
            self.jid.set_text(contact.jid)
            self.jid.show()
            self.jid_label.show()
        # Resource
        if hasattr(contact, 'resource') and contact.resource.strip():
            self.resource.set_text(contact.resource)
            self.resource.show()
            self.resource_label.show()

        # Affiliation
        if contact.affiliation != 'none':
            uf_affiliation = helpers.get_uf_affiliation(contact.affiliation)
            uf_affiliation = \
                _('%(owner_or_admin_or_member)s of this group chat') \
                % {'owner_or_admin_or_member': uf_affiliation}
            uf_affiliation = self.colorize_affiliation(uf_affiliation)
            self.affiliation.set_markup(uf_affiliation)
            self.affiliation.show()

        # Avatar
        puny_name = helpers.sanitize_filename(contact.name)
        puny_room = helpers.sanitize_filename(contact.room_jid)
        file_ = helpers.get_avatar_path(os.path.join(gajim.AVATAR_PATH,
            puny_room, puny_name))
        if file_:
            with open(file_, 'rb') as file_data:
                pix = gtkgui_helpers.get_pixbuf_from_data(file_data.read())
            pix = gtkgui_helpers.get_scaled_pixbuf(pix, 'tooltip')
            self.avatar.set_from_pixbuf(pix)
            self.avatar.show()
            self.fillelement.show()
Пример #10
0
        def on_ok(widget, path_to_file):
            must_delete = False
            filesize = os.path.getsize(path_to_file) # in bytes
            invalid_file = False
            msg = ''
            if os.path.isfile(path_to_file):
                stat = os.stat(path_to_file)
                if stat[6] == 0:
                    invalid_file = True
                    msg = _('File is empty')
            else:
                invalid_file = True
                msg = _('File does not exist')
            if not invalid_file and filesize > 16384: # 16 kb
                try:
                    pixbuf = GdkPixbuf.Pixbuf.new_from_file(path_to_file)
                    # get the image at 'notification size'
                    # and hope that user did not specify in ACE crazy size
                    scaled_pixbuf = gtkgui_helpers.get_scaled_pixbuf(pixbuf,
                            'tooltip')
                except GObject.GError as msg: # unknown format
                    # msg should be string, not object instance
                    msg = str(msg)
                    invalid_file = True
            if invalid_file:
                if True: # keep identation
                    dialogs.ErrorDialog(_('Could not load image'), msg,
                        transient_for=self.window)
                    return
            if filesize > 16384:
                if scaled_pixbuf:
                    path_to_file = os.path.join(gajim.TMP,
                            'avatar_scaled.png')
                    scaled_pixbuf.savev(path_to_file, 'png', [], [])
                    must_delete = True

            with open(path_to_file, 'rb') as fd:
                data = fd.read()
            pixbuf = gtkgui_helpers.get_pixbuf_from_data(data)
            try:
                # rescale it
                pixbuf = gtkgui_helpers.get_scaled_pixbuf(pixbuf, 'vcard')
            except AttributeError: # unknown format
                dialogs.ErrorDialog(_('Could not load image'),
                    transient_for=self.window)
                return
            self.dialog.destroy()
            self.dialog = None
            button = self.xml.get_object('PHOTO_button')
            image = button.get_image()
            image.set_from_pixbuf(pixbuf)
            button.show()
            text_button = self.xml.get_object('NOPHOTO_button')
            text_button.hide()
            self.avatar_encoded = base64.b64encode(data).decode('utf-8')
            # returns None if unknown type
            self.avatar_mime_type = mimetypes.guess_type(path_to_file)[0]
            if must_delete:
                try:
                    os.remove(path_to_file)
                except OSError:
                    gajim.log.debug('Cannot remove %s' % path_to_file)
Пример #11
0
    def populate(self, contacts):
        self.create_window()

        self.create_table()
        if not contacts or len(contacts) == 0:
            # Tooltip for merged accounts row
            accounts = helpers.get_notification_icon_tooltip_dict()
            self.spacer_label = ''
            self.fill_table_with_accounts(accounts)
            self.win.add(self.table)
            return

        # primary contact
        prim_contact = gajim.contacts.get_highest_prio_contact_from_contacts(
            contacts)

        puny_jid = helpers.sanitize_filename(prim_contact.jid)
        table_size = 3

        file_ = helpers.get_avatar_path(os.path.join(gajim.AVATAR_PATH,
            puny_jid))
        if file_:
            with open(file_, 'rb') as file_data:
                pix = gtkgui_helpers.get_pixbuf_from_data(file_data.read())
            pix = gtkgui_helpers.get_scaled_pixbuf(pix, 'tooltip')
            self.avatar_image.set_from_pixbuf(pix)
            table_size = 4
        else:
            self.avatar_image.set_from_pixbuf(None)
        vcard_table = Gtk.Grid()
        vcard_table.insert_row(0)
        for i in range(0, table_size):
            vcard_table.insert_column(0)
        vcard_table.set_property('column-spacing', 2)
        vcard_current_row = 1
        properties = []

        name_markup = '<span weight="bold">' + GLib.markup_escape_text(
            prim_contact.get_shown_name()) + '</span>'
        if gajim.config.get('mergeaccounts'):
            name_markup += " <span foreground='%s'>(%s)</span>" % (
                gajim.config.get('tooltip_account_name_color'),
                GLib.markup_escape_text(prim_contact.account.name))

        if self.account and helpers.jid_is_blocked(self.account,
        prim_contact.jid):
            name_markup += _(' [blocked]')
        if self.account and \
        self.account in gajim.interface.minimized_controls and \
        prim_contact.jid in gajim.interface.minimized_controls[self.account]:
            name_markup += _(' [minimized]')
        properties.append((name_markup, None))

        num_resources = 0
        # put contacts in dict, where key is priority
        contacts_dict = {}
        for contact in contacts:
            if contact.resource:
                num_resources += 1
                if contact.priority in contacts_dict:
                    contacts_dict[int(contact.priority)].append(contact)
                else:
                    contacts_dict[int(contact.priority)] = [contact]

        if num_resources > 1:
            properties.append((_('Status: '),       ' '))
            transport = gajim.get_transport_name_from_jid(prim_contact.jid)
            if transport:
                file_path = os.path.join(helpers.get_transport_path(transport),
                    '16x16')
            else:
                iconset = gajim.config.get('iconset')
                if not iconset:
                    iconset = 'dcraven'
                file_path = os.path.join(helpers.get_iconset_path(iconset),
                    '16x16')

            contact_keys = sorted(contacts_dict.keys())
            contact_keys.reverse()
            for priority in contact_keys:
                for acontact in contacts_dict[priority]:
                    status_line = self.get_status_info(acontact.resource,
                        acontact.priority, acontact.show, acontact.status)

                    icon_name = self._get_icon_name_for_tooltip(acontact)
                    self.add_status_row(file_path, icon_name, status_line,
                        acontact.last_status_time)
            properties.append((self.table,  None))

        else: # only one resource
            if contact.show:
                show = helpers.get_uf_show(contact.show)
                if not self.check_last_time and self.account:
                    if contact.show == 'offline':
                        if not contact.last_status_time:
                            gajim.connections[self.account].\
                                request_last_status_time(contact.jid, '')
                        else:
                            self.check_last_time = contact.last_status_time
                    elif contact.resource:
                        gajim.connections[self.account].\
                            request_last_status_time(
                            contact.jid, contact.resource)
                        if contact.last_activity_time:
                            self.check_last_time = contact.last_activity_time
                else:
                    self.check_last_time = None
                if contact.last_status_time:
                    vcard_current_row += 1
                    if contact.show == 'offline':
                        text = ' - ' + _('Last status: %s')
                    else:
                        text = _(' since %s')

                    if time.strftime('%j', time.localtime()) == \
                        time.strftime('%j', contact.last_status_time):
                        # it's today, show only the locale hour representation
                        local_time = time.strftime('%X',
                            contact.last_status_time)
                    else:
                        # time.strftime returns locale encoded string
                        local_time = time.strftime('%c',
                            contact.last_status_time)

                    text = text % local_time
                    show += text
                if self.account and \
                prim_contact.jid in gajim.gc_connected[self.account]:
                    if gajim.gc_connected[self.account][prim_contact.jid]:
                        show = _('Connected')
                    else:
                        show = _('Disconnected')
                show = self.colorize_status(show)

                if contact.status:
                    status = contact.status.strip()
                    if status:
                        # reduce long status
                        # (no more than 300 chars on line and no more than
                        # 5 lines)
                        # status is wrapped
                        status = helpers.reduce_chars_newlines(status, 300, 5)
                        # escape markup entities.
                        status = GLib.markup_escape_text(status)
                        properties.append(('<i>%s</i>' % status, None))
                properties.append((show, None))

        self._append_pep_info(contact, properties)

        properties.append((_('Jabber ID: '), '\u200E' + "<b>%s</b>" % \
            prim_contact.jid))

        # contact has only one ressource
        if num_resources == 1 and contact.resource:
            properties.append((_('Resource: '), GLib.markup_escape_text(
                contact.resource) + ' (' + str(contact.priority) + ')'))

        if self.account and prim_contact.sub and prim_contact.sub != 'both' and\
        prim_contact.jid not in gajim.gc_connected[self.account]:
            # ('both' is the normal sub so we don't show it)
            properties.append(( _('Subscription: '), GLib.markup_escape_text(
                helpers.get_uf_sub(prim_contact.sub))))

        if prim_contact.keyID:
            keyID = None
            if len(prim_contact.keyID) == 8:
                keyID = prim_contact.keyID
            elif len(prim_contact.keyID) == 16:
                keyID = prim_contact.keyID[8:]
            if keyID:
                properties.append((_('OpenPGP: '), GLib.markup_escape_text(
                    keyID)))

        if contact.last_activity_time:
            last_active = datetime(*contact.last_activity_time[:6])
            current = datetime.now()

            diff = current - last_active
            diff = timedelta(diff.days, diff.seconds)

            if last_active.date() == current.date():
                formatted = last_active.strftime("%X")
            else:
                formatted = last_active.strftime("%c")

            # Do not show the "Idle since" and "Idle for" items if there
            # is no meaningful difference between last activity time and
            # current time.
            if diff.days > 0 or diff.seconds > 0:
                cs = "<span foreground='%s'>" % gajim.config.get(
                    'tooltip_idle_color')
                cs += '%s</span>'
                properties.append((str(), None))
                idle_since = cs % _("Idle since %s")
                properties.append((idle_since % formatted, None))
                idle_for = cs % _("Idle for %s")
                properties.append((idle_for % str(diff), None))

        while properties:
            property_ = properties.pop(0)
            vcard_current_row += 1
            label = Gtk.Label()
            if not properties and table_size == 4:
                label.set_vexpand(True)
            label.set_halign(Gtk.Align.START)
            label.set_valign(Gtk.Align.START)
            if property_[1]:
                label.set_markup(property_[0])
                vcard_table.attach(label, 1, vcard_current_row, 1, 1)
                label = Gtk.Label()
                if not properties and table_size == 4:
                    label.set_vexpand(True)
                label.set_halign(Gtk.Align.START)
                label.set_valign(Gtk.Align.START)
                label.set_markup(property_[1])
                label.set_line_wrap(True)
                vcard_table.attach(label, 2, vcard_current_row, 1, 1)
            else:
                if isinstance(property_[0], str):
                    label.set_markup(property_[0])
                    label.set_line_wrap(True)
                else:
                    label = property_[0]
                vcard_table.attach(label, 1, vcard_current_row, 2, 1)
        self.avatar_image.set_halign(Gtk.Align.START)
        self.avatar_image.set_valign(Gtk.Align.START)
        if table_size == 4:
            vcard_table.attach(self.avatar_image, 3, 2, 1, vcard_current_row - 1)

        gajim.plugin_manager.gui_extension_point('roster_tooltip_populate',
            self, contacts, vcard_table)
        self.win.add(vcard_table)
Пример #12
0
    def populate(self, contact):
        if not contact:
            return
        self.create_window()
        vcard_table = Gtk.Grid()
        vcard_table.insert_row(0)
        vcard_table.insert_row(0)
        vcard_table.insert_row(0)
        vcard_table.insert_column(0)
        vcard_table.set_property('column-spacing', 2)
        vcard_current_row = 1
        properties = []

        nick_markup = '<b>' + GLib.markup_escape_text(contact.get_shown_name())\
            + '</b>'
        properties.append((nick_markup, None))

        if contact.status: # status message
            status = contact.status.strip()
            if status != '':
                # escape markup entities
                status = helpers.reduce_chars_newlines(status, 300, 5)
                status = '<i>' + GLib.markup_escape_text(status) + '</i>'
                properties.append((status, None))

        show = helpers.get_uf_show(contact.show)
        show = self.colorize_status(show)
        properties.append((show, None))

        if contact.jid.strip():
            properties.append((_('Jabber ID: '), '\u200E' + "<b>%s</b>" % \
                contact.jid))

        if hasattr(contact, 'resource') and contact.resource.strip():
            properties.append((_('Resource: '), GLib.markup_escape_text(
                contact.resource)))

        if contact.affiliation != 'none':
            uf_affiliation = helpers.get_uf_affiliation(contact.affiliation)
            uf_affiliation = \
                _('%(owner_or_admin_or_member)s of this group chat') % \
                {'owner_or_admin_or_member': uf_affiliation}
            uf_affiliation = self.colorize_affiliation(uf_affiliation)
            properties.append((uf_affiliation, None))

        # Add avatar
        puny_name = helpers.sanitize_filename(contact.name)
        puny_room = helpers.sanitize_filename(contact.room_jid)
        file_ = helpers.get_avatar_path(os.path.join(gajim.AVATAR_PATH,
            puny_room, puny_name))
        if file_:
            with open(file_, 'rb') as file_data:
                pix = gtkgui_helpers.get_pixbuf_from_data(file_data.read())
            pix = gtkgui_helpers.get_scaled_pixbuf(pix, 'tooltip')
            self.avatar_image.set_from_pixbuf(pix)
        else:
            self.avatar_image.set_from_pixbuf(None)
        while properties:
            property_ = properties.pop(0)
            vcard_current_row += 1
            label = Gtk.Label()
            if not properties:
                label.set_vexpand(True)
            label.set_halign(Gtk.Align.START)
            label.set_valign(Gtk.Align.START)
            if property_[1]:
                label.set_markup(property_[0])
                vcard_table.attach(label, 1, vcard_current_row, 1, 1)
                label = Gtk.Label()
                if not properties:
                    label.set_vexpand(True)
                label.set_halign(Gtk.Align.START)
                label.set_valign(Gtk.Align.START)
                label.set_markup(property_[1])
                label.set_line_wrap(True)
                vcard_table.attach(label, 2, vcard_current_row, 1, 1)
            else:
                label.set_markup(property_[0])
                label.set_line_wrap(True)
                vcard_table.attach(label, 1, vcard_current_row, 2, 1)

        self.avatar_image.set_halign(Gtk.Align.START)
        self.avatar_image.set_valign(Gtk.Align.START)
        vcard_table.attach(self.avatar_image, 3, 2, 1, vcard_current_row - 1)
        gajim.plugin_manager.gui_extension_point('gc_tooltip_populate',
            self, contact, vcard_table)
        self.win.add(vcard_table)
Пример #13
0
    def populate(self, contacts):
        self.create_window()

        self.create_table()
        if not contacts or len(contacts) == 0:
            # Tooltip for merged accounts row
            accounts = helpers.get_notification_icon_tooltip_dict()
            self.spacer_label = ''
            self.fill_table_with_accounts(accounts)
            self.win.add(self.table)
            return

        # primary contact
        prim_contact = gajim.contacts.get_highest_prio_contact_from_contacts(
            contacts)

        puny_jid = helpers.sanitize_filename(prim_contact.jid)
        table_size = 3

        file_ = helpers.get_avatar_path(os.path.join(gajim.AVATAR_PATH,
            puny_jid))
        if file_:
            with open(file_, 'rb') as file_data:
                pix = gtkgui_helpers.get_pixbuf_from_data(file_data.read())
            pix = gtkgui_helpers.get_scaled_pixbuf(pix, 'tooltip')
            self.avatar_image.set_from_pixbuf(pix)
            table_size = 4
        else:
            self.avatar_image.set_from_pixbuf(None)
        vcard_table = Gtk.Grid()
        vcard_table.insert_row(0)
        for i in range(0, table_size):
            vcard_table.insert_column(0)
        vcard_table.set_property('column-spacing', 2)
        vcard_current_row = 1
        properties = []

        name_markup = '<span weight="bold">' + GLib.markup_escape_text(
            prim_contact.get_shown_name()) + '</span>'
        if gajim.config.get('mergeaccounts'):
            name_markup += " <span foreground='%s'>(%s)</span>" % (
                gajim.config.get('tooltip_account_name_color'),
                GLib.markup_escape_text(prim_contact.account.name))

        if self.account and helpers.jid_is_blocked(self.account,
        prim_contact.jid):
            name_markup += _(' [blocked]')
        if self.account and \
        self.account in gajim.interface.minimized_controls and \
        prim_contact.jid in gajim.interface.minimized_controls[self.account]:
            name_markup += _(' [minimized]')
        properties.append((name_markup, None))

        num_resources = 0
        # put contacts in dict, where key is priority
        contacts_dict = {}
        for contact in contacts:
            if contact.resource:
                num_resources += 1
                if contact.priority in contacts_dict:
                    contacts_dict[int(contact.priority)].append(contact)
                else:
                    contacts_dict[int(contact.priority)] = [contact]

        if num_resources > 1:
            properties.append((_('Status: '),       ' '))
            transport = gajim.get_transport_name_from_jid(prim_contact.jid)
            if transport:
                file_path = os.path.join(helpers.get_transport_path(transport),
                    '16x16')
            else:
                iconset = gajim.config.get('iconset')
                if not iconset:
                    iconset = 'dcraven'
                file_path = os.path.join(helpers.get_iconset_path(iconset),
                    '16x16')

            contact_keys = sorted(contacts_dict.keys())
            contact_keys.reverse()
            for priority in contact_keys:
                for acontact in contacts_dict[priority]:
                    status_line = self.get_status_info(acontact.resource,
                        acontact.priority, acontact.show, acontact.status)

                    icon_name = self._get_icon_name_for_tooltip(acontact)
                    self.add_status_row(file_path, icon_name, status_line,
                        acontact.last_status_time)
            properties.append((self.table,  None))

        else: # only one resource
            if contact.show:
                show = helpers.get_uf_show(contact.show)
                if not self.check_last_time and self.account:
                    if contact.show == 'offline':
                        if not contact.last_status_time:
                            gajim.connections[self.account].\
                                request_last_status_time(contact.jid, '')
                        else:
                            self.check_last_time = contact.last_status_time
                    elif contact.resource:
                        gajim.connections[self.account].\
                            request_last_status_time(
                            contact.jid, contact.resource)
                        if contact.last_activity_time:
                            self.check_last_time = contact.last_activity_time
                else:
                    self.check_last_time = None
                if contact.last_status_time:
                    vcard_current_row += 1
                    if contact.show == 'offline':
                        text = ' - ' + _('Last status: %s')
                    else:
                        text = _(' since %s')

                    if time.strftime('%j', time.localtime()) == \
                        time.strftime('%j', contact.last_status_time):
                        # it's today, show only the locale hour representation
                        local_time = time.strftime('%X',
                            contact.last_status_time)
                    else:
                        # time.strftime returns locale encoded string
                        local_time = time.strftime('%c',
                            contact.last_status_time)

                    text = text % local_time
                    show += text
                if self.account and \
                prim_contact.jid in gajim.gc_connected[self.account]:
                    if gajim.gc_connected[self.account][prim_contact.jid]:
                        show = _('Connected')
                    else:
                        show = _('Disconnected')
                show = self.colorize_status(show)

                if contact.status:
                    status = contact.status.strip()
                    if status:
                        # reduce long status
                        # (no more than 300 chars on line and no more than
                        # 5 lines)
                        # status is wrapped
                        status = helpers.reduce_chars_newlines(status, 300, 5)
                        # escape markup entities.
                        status = GLib.markup_escape_text(status)
                        properties.append(('<i>%s</i>' % status, None))
                properties.append((show, None))

        self._append_pep_info(contact, properties)

        properties.append((_('Jabber ID: '), '\u200E' + "<b>%s</b>" % \
            prim_contact.jid))

        # contact has only one ressource
        if num_resources == 1 and contact.resource:
            properties.append((_('Resource: '), GLib.markup_escape_text(
                contact.resource) + ' (' + str(contact.priority) + ')'))

        if self.account and prim_contact.sub and prim_contact.sub != 'both' and\
        prim_contact.jid not in gajim.gc_connected[self.account]:
            # ('both' is the normal sub so we don't show it)
            properties.append(( _('Subscription: '), GLib.markup_escape_text(
                helpers.get_uf_sub(prim_contact.sub))))

        if prim_contact.keyID:
            keyID = None
            if len(prim_contact.keyID) == 8:
                keyID = prim_contact.keyID
            elif len(prim_contact.keyID) == 16:
                keyID = prim_contact.keyID[8:]
            if keyID:
                properties.append((_('OpenPGP: '), GLib.markup_escape_text(
                    keyID)))

        if contact.last_activity_time:
            last_active = datetime(*contact.last_activity_time[:6])
            current = datetime.now()

            diff = current - last_active
            diff = timedelta(diff.days, diff.seconds)

            if last_active.date() == current.date():
                formatted = last_active.strftime("%X")
            else:
                formatted = last_active.strftime("%c")

            # Do not show the "Idle since" and "Idle for" items if there
            # is no meaningful difference between last activity time and
            # current time.
            if diff.days > 0 or diff.seconds > 0:
                cs = "<span foreground='%s'>" % gajim.config.get(
                    'tooltip_idle_color')
                cs += '%s</span>'
                properties.append((str(), None))
                idle_since = cs % _("Idle since %s")
                properties.append((idle_since % formatted, None))
                idle_for = cs % _("Idle for %s")
                properties.append((idle_for % str(diff), None))

        while properties:
            property_ = properties.pop(0)
            vcard_current_row += 1
            label = Gtk.Label()
            if not properties and table_size == 4:
                label.set_vexpand(True)
            label.set_alignment(0, 0)
            if property_[1]:
                label.set_markup(property_[0])
                vcard_table.attach(label, 1, vcard_current_row, 1, 1)
                label = Gtk.Label()
                if not properties and table_size == 4:
                    label.set_vexpand(True)
                label.set_alignment(0, 0)
                label.set_markup(property_[1])
                label.set_line_wrap(True)
                vcard_table.attach(label, 2, vcard_current_row, 1, 1)
            else:
                if isinstance(property_[0], str):
                    label.set_markup(property_[0])
                    label.set_line_wrap(True)
                else:
                    label = property_[0]
                vcard_table.attach(label, 1, vcard_current_row, 2, 1)
        self.avatar_image.set_alignment(0, 0)
        if table_size == 4:
            vcard_table.attach(self.avatar_image, 3, 2, 1, vcard_current_row - 1)

        gajim.plugin_manager.gui_extension_point('roster_tooltip_populate',
            self, contacts, vcard_table)
        self.win.add(vcard_table)
Пример #14
0
    def populate(self, contact):
        if not contact:
            return
        self.create_window()
        vcard_table = Gtk.Grid()
        vcard_table.insert_row(0)
        vcard_table.insert_row(0)
        vcard_table.insert_row(0)
        vcard_table.insert_column(0)
        vcard_table.set_property('column-spacing', 2)
        vcard_current_row = 1
        properties = []

        nick_markup = '<b>' + GLib.markup_escape_text(contact.get_shown_name())\
            + '</b>'
        properties.append((nick_markup, None))

        if contact.status: # status message
            status = contact.status.strip()
            if status != '':
                # escape markup entities
                status = helpers.reduce_chars_newlines(status, 300, 5)
                status = '<i>' + GLib.markup_escape_text(status) + '</i>'
                properties.append((status, None))

        show = helpers.get_uf_show(contact.show)
        show = self.colorize_status(show)
        properties.append((show, None))

        if contact.jid.strip():
            properties.append((_('Jabber ID: '), '\u200E' + "<b>%s</b>" % \
                contact.jid))

        if hasattr(contact, 'resource') and contact.resource.strip():
            properties.append((_('Resource: '), GLib.markup_escape_text(
                contact.resource)))

        if contact.affiliation != 'none':
            uf_affiliation = helpers.get_uf_affiliation(contact.affiliation)
            uf_affiliation = \
                _('%(owner_or_admin_or_member)s of this group chat') % \
                {'owner_or_admin_or_member': uf_affiliation}
            uf_affiliation = self.colorize_affiliation(uf_affiliation)
            properties.append((uf_affiliation, None))

        # Add avatar
        puny_name = helpers.sanitize_filename(contact.name)
        puny_room = helpers.sanitize_filename(contact.room_jid)
        file_ = helpers.get_avatar_path(os.path.join(gajim.AVATAR_PATH,
            puny_room, puny_name))
        if file_:
            with open(file_, 'rb') as file_data:
                pix = gtkgui_helpers.get_pixbuf_from_data(file_data.read())
            pix = gtkgui_helpers.get_scaled_pixbuf(pix, 'tooltip')
            self.avatar_image.set_from_pixbuf(pix)
        else:
            self.avatar_image.set_from_pixbuf(None)
        while properties:
            property_ = properties.pop(0)
            vcard_current_row += 1
            label = Gtk.Label()
            if not properties:
                label.set_vexpand(True)
            label.set_alignment(0, 0)
            if property_[1]:
                label.set_markup(property_[0])
                vcard_table.attach(label, 1, vcard_current_row, 1, 1)
                label = Gtk.Label()
                if not properties:
                    label.set_vexpand(True)
                label.set_alignment(0, 0)
                label.set_markup(property_[1])
                label.set_line_wrap(True)
                vcard_table.attach(label, 2, vcard_current_row, 1, 1)
            else:
                label.set_markup(property_[0])
                label.set_line_wrap(True)
                vcard_table.attach(label, 1, vcard_current_row, 2, 1)

        self.avatar_image.set_alignment(0, 0)
        vcard_table.attach(self.avatar_image, 3, 2, 1, vcard_current_row - 1)
        gajim.plugin_manager.gui_extension_point('gc_tooltip_populate',
            self, contact, vcard_table)
        self.win.add(vcard_table)
Пример #15
0
    def populate(self, contacts, account, typ):
        """
        Populate the Tooltip Grid with data of from the contact
        """
        self.current_row = 0
        self.account = account
        if self.last_widget:
            self.last_widget.set_vexpand(False)

        self.clear_tooltip()

        if account == 'all':
            # Tooltip for merged accounts row
            accounts = helpers.get_notification_icon_tooltip_dict()
            self.spacer_label = ''
            self.fill_table_with_accounts(accounts)
            self.tooltip_grid.attach(self.table, 0, 3, 2, 1)
            self.table.show_all()
            return

        if typ == 'account':
            jid = gajim.get_jid_from_account(account)
            contacts = []
            connection = gajim.connections[account]
            # get our current contact info

            nbr_on, nbr_total = gajim.\
                contacts.get_nb_online_total_contacts(
                accounts=[account])
            account_name = account
            if gajim.account_is_connected(account):
                account_name += ' (%s/%s)' % (repr(nbr_on),
                    repr(nbr_total))
            contact = gajim.contacts.create_self_contact(jid=jid,
                account=account, name=account_name,
                show=connection.get_status(), status=connection.status,
                resource=connection.server_resource,
                priority=connection.priority)
            if gajim.connections[account].gpg:
                contact.keyID = gajim.config.get_per('accounts',
                    connection.name, 'keyid')
            contacts.append(contact)
            # if we're online ...
            if connection.connection:
                roster = connection.connection.getRoster()
                # in threadless connection when no roster stanza is sent
                # 'roster' is None
                if roster and roster.getItem(jid):
                    resources = roster.getResources(jid)
                    # ...get the contact info for our other online
                    # resources
                    for resource in resources:
                        # Check if we already have this resource
                        found = False
                        for contact_ in contacts:
                            if contact_.resource == resource:
                                found = True
                                break
                        if found:
                            continue
                        show = roster.getShow(jid + '/' + resource)
                        if not show:
                            show = 'online'
                        contact = gajim.contacts.create_self_contact(
                            jid=jid, account=account, show=show,
                            status=roster.getStatus(
                            jid + '/' + resource),
                            priority=roster.getPriority(
                            jid + '/' + resource), resource=resource)
                        contacts.append(contact)

        # Username/Account/Groupchat
        self.prim_contact = gajim.contacts.get_highest_prio_contact_from_contacts(
            contacts)
        self.contact_jid = self.prim_contact.jid
        name = GLib.markup_escape_text(self.prim_contact.get_shown_name())
        name_markup = '<b>{}</b>'.format(name)
        if gajim.config.get('mergeaccounts'):
            color = gajim.config.get('tooltip_account_name_color')
            account_name = GLib.markup_escape_text(self.prim_contact.account.name)
            name_markup += " <span foreground='{}'>({})</span>".format(
                color, account_name)

        if account and helpers.jid_is_blocked(account, self.prim_contact.jid):
            name_markup += _(' [blocked]')

        try:
            if self.prim_contact.jid in gajim.interface.minimized_controls[account]:
                name_markup += _(' [minimized]')
        except KeyError:
            pass

        self.name.set_markup(name_markup)
        self.name.show()

        self.num_resources = 0
        # put contacts in dict, where key is priority
        contacts_dict = {}
        for contact in contacts:
            if contact.resource:
                self.num_resources += 1
                priority = int(contact.priority)
                if priority in contacts_dict:
                    contacts_dict[priority].append(contact)
                else:
                    contacts_dict[priority] = [contact]
        if self.num_resources > 1:
            self.status_label.show()
            transport = gajim.get_transport_name_from_jid(self.prim_contact.jid)
            if transport:
                file_path = os.path.join(helpers.get_transport_path(transport),
                    '16x16')
            else:
                iconset = gajim.config.get('iconset')
                if not iconset:
                    iconset = 'dcraven'
                file_path = os.path.join(helpers.get_iconset_path(iconset),
                    '16x16')

            contact_keys = sorted(contacts_dict.keys())
            contact_keys.reverse()
            for priority in contact_keys:
                for acontact in contacts_dict[priority]:
                    icon_name = self._get_icon_name_for_tooltip(acontact)
                    if acontact.status and len(acontact.status) > 25:
                        status = ''
                        add_text = True
                    else:
                        status = acontact.status
                        add_text = False

                    status_line = self.get_status_info(acontact.resource,
                    acontact.priority, acontact.show, status)
                    self.add_status_row(file_path, icon_name, status_line,
                        acontact.last_status_time)
                    if add_text:
                        self.add_text_row(acontact.status, 2)

            self.tooltip_grid.attach(self.table, 0, 3, 2, 1)
            self.table.show_all()

        else:  # only one resource
            if contact.show:
                request_time = False
                try:
                    last_time = self.check_last_time[contact]
                    if isinstance(last_time, float) and last_time < time.time() - 60:
                        request_time = True
                except KeyError:
                    request_time = True

                if request_time:
                    if contact.show == 'offline':
                        gajim.connections[account].\
                            request_last_status_time(contact.jid, '')
                    elif contact.resource:
                        gajim.connections[account].\
                            request_last_status_time(
                            contact.jid, contact.resource)
                    self.check_last_time[contact] = time.time()

                if contact.status:
                    status = contact.status.strip()
                    if status:
                        self.status.set_text(status)
                        self.status.show()
                        self.status_label.show()

        # PEP Info
        self._append_pep_info(contact)

        # JID
        self.jid.set_text(self.prim_contact.jid)
        self.jid.show()
        self.jid_label.show()

        # contact has only one ressource
        if self.num_resources == 1 and contact.resource:
            res = GLib.markup_escape_text(contact.resource)
            prio = str(contact.priority)
            self.resource.set_text("{} ({})".format(res, prio))
            self.resource.show()
            self.resource_label.show()

        if self.prim_contact.jid not in gajim.gc_connected[account]:
            if (account and
                self.prim_contact.sub and
                    self.prim_contact.sub != 'both'):
                # ('both' is the normal sub so we don't show it)
                self.sub.set_text(helpers.get_uf_sub(self.prim_contact.sub))
                self.sub.show()
                self.sub_label.show()

        if self.prim_contact.keyID:
            keyID = None
            if len(self.prim_contact.keyID) == 8:
                keyID = self.prim_contact.keyID
            elif len(self.prim_contact.keyID) == 16:
                keyID = self.prim_contact.keyID[8:]
            if keyID:
                self.pgp.set_text(keyID)
                self.pgp.show()
                self.pgp_label.show()

        self._set_idle_time(contact)

        # Avatar
        puny_jid = helpers.sanitize_filename(self.prim_contact.jid)
        file_ = helpers.get_avatar_path(os.path.join(gajim.AVATAR_PATH,
            puny_jid))
        if file_:
            with open(file_, 'rb') as file_data:
                pix = gtkgui_helpers.get_pixbuf_from_data(file_data.read())
            pix = gtkgui_helpers.get_scaled_pixbuf(pix, 'tooltip')
            self.avatar.set_from_pixbuf(pix)
            self.avatar.show()

            # Sets the Widget that is at the bottom to expand.
            # This is needed in case the Picture takes more Space then the Labels
            i = 1
            while i < 15:
                if self.tooltip_grid.get_child_at(0, i):
                    if self.tooltip_grid.get_child_at(0, i).get_visible():
                        self.last_widget = self.tooltip_grid.get_child_at(0, i)
                i += 1
            self.last_widget.set_vexpand(True)