def refresh_users(self): now = frozenset(self.users.keys()) diff = now.difference(self.userids) for uid in diff: user = self.users[uid] text = "<b>%s</b>\n<small><span foreground='#666666'>%s</span></small>" % ( user.screen_name, TwitterTools.replace_amp(user.name)) is_friend = user.id in self.twitter.following is_follower = user.id in self.twitter.followers icon = self.iconstore.get(user) following = self.pix_follow if is_friend else self.pix_nofollow follower = self.pix_follow if is_follower else self.pix_nofollow completion_text = "@%s - %s" % ( user.screen_name, TwitterTools.replace_amp(user.name)) gtk.gdk.threads_enter() self.store.append((icon, text, user.id, user.screen_name, following, follower, is_friend, is_follower, completion_text)) gtk.gdk.threads_leave() self.userids = now
def status_pack(self, i): status = self.twitter.statuses[i] background = None footer = "" name = status.user.screen_name if TwitterTools.isretweet(status): rtstatus = status status = self.twitter.statuses[status.retweeted_status.id] # status.favorited = False # FIX? rtstatus.favorited name = "%s <span foreground='#333333'><small>- Retweeted by %s</small></span>" % ( status.user.screen_name, rtstatus.user.screen_name, ) if status.user.id in self.twitter.followers or status.user.id == self.twitter.my_id: # Bold screen_name if follower tmpl = "<b>%s</b>\n%s" elif not self.twitter.followers: tmpl = "<b><i>%s</i></b>\n%s" else: # or gray tmpl = "<span foreground='#666666'><b>%s</b></span>\n%s" # status decoration text = TwitterTools.get_decoration_text(status) # screen_name + text message = tmpl % (name, text) # replace no entity & -> & message = TwitterTools.replace_amp(message) # deleted if "deleted" in status: message = "<span foreground='#666666'><s>%s</s></span>" % message # Faved by if "faved_by" in status and status["faved_by"]: footer += "\n<small>Faved by: %s</small>" % ( ", ".join([self.twitter.users[u].screen_name for u in status["faved_by"]]) ) # geo tag if status["place"]: footer += "\n<small>Place: %s</small>" % (status["place"]["full_name"]) if footer: message = "%s\n%s" % (message, footer) # Favorite, RT favico = self.favico_on if status.favorited else self.favico_off rtico = self.rtico_on if status.retweeted else self.rtico_off return (self.iconstore.get(status.user), message, long(i), long(status.user.id), background, favico, rtico)
def on_textbuffer1_changed(self, buf): text = self.get_textview().decode("utf-8") # reply to user suggesstions cursor = buf.get_property("cursor-position") rspace = text.rfind(" ", 0, cursor) rat = text.rfind("@", 0, cursor) rhash = text.rfind("#", 0, cursor) prefix = postfix = None # is reply? if rat == 0 or (rspace > 0 and rat > rspace): prefix = text[rat + 1:cursor] users = self.twitter.get_users_startswith(prefix) if users: users.sort(key = lambda u: u.screen_name) postfix = users[0].screen_name[len(prefix):] # is hash? if rhash == 0 or (rspace > 0 and rhash > rspace): prefix = text[rhash + 1:cursor] hashtags = [h for h in self.twitter.hashtags if h.startswith(prefix)] if hashtags: hashtags.sort() postfix = hashtags[0][len(prefix):] # clear old suggesstions if buf.get_has_selection(): buf.delete_selection(True, True) self._text_delete_flag = False # print screen_name suggesstions if prefix and postfix and not self._text_delete_flag: cursor_iter = buf.get_iter_at_mark(buf.get_insert()) buf.insert_at_cursor(postfix) buf.select_range(buf.get_iter_at_offset(cursor), buf.get_iter_at_mark(buf.get_insert())) self._text_delete_flag = False # add footer if self.msgfooter != "" and self.twparams.get("reply_to", None): text = u"%s %s" % (text, self.msgfooter) # calculate tweet length n = TwitterTools.get_tweet_length( text, len(self.twparams.get("media", [])), self.twitter.configuration.get("short_url_length", 20), self.twitter.configuration.get("short_url_length_https", 20), self.twitter.configuration.get("characters_reserved_per_media", 20) ) if n <= 140: self.charcount.set_text(str(n)) self.btnupdate.set_sensitive(True) else: self.charcount.set_markup( "<b><span foreground='#FF0000'>%s</span></b>" % n) self.btnupdate.set_sensitive(False)
def reset_fav_rt_ico(self, path, fav=True, rt=True): if path != None: status = self.get_status(path) if TwitterTools.isretweet(status): status = self.twitter.statuses[status.retweeted_status.id] if fav: self.store[path][5] = self.favico_on if status.favorited else self.favico_off if rt: self.store[path][6] = self.rtico_on if status.retweeted else self.rtico_off
def refresh_user_information(self, user): bio = """ <big><b>%s</b></big> - %s <b>%d</b> following, <b>%d</b> followers, <b>%d</b> tweets, <b>%d</b> favs <small><span foreground='#666666'>Location: %s Bio: %s Web: %s</span></small> """ % ( user.screen_name, user.name, user.friends_count, user.followers_count, user.statuses_count, user.favourites_count, user.location, unicode(user.description).replace("\n", ""), "<a href='%s'>%s</a>" % (user.url, user.url) if user.url != None else None, ) if user.protected: bio += "\n[Protected user]" bio = TwitterTools.replace_amp(bio) img = gtk.image_new_from_pixbuf(self.iconstore.get(user)) is_follow = user.id in self.twitter.following button = gtk.ToggleButton("Following" if is_follow else "Follow") button.set_active(is_follow) button.set_image(gtk.image_new_from_stock("gtk-apply", gtk.ICON_SIZE_BUTTON) if is_follow else gtk.image_new_from_stock("gtk-add", gtk.ICON_SIZE_BUTTON)) button.connect("toggled", self.on_follow_button_toggled) vbox = gtk.VBox() vbox.set_spacing(10) vbox.pack_start(img) vbox.pack_end(button, expand = False) label = gtk.Label() label.set_padding(30, 0) label.set_alignment(0, 0.5) label.set_line_wrap(True) label.set_markup(bio) label.set_property("height-request", 150) hbox = gtk.HBox() hbox.set_border_width(10) hbox.pack_start(vbox, expand = False) hbox.pack_end(label) img.show() label.show() hbox.show_all() self.paned.remove(self._now_box) self._now_box = hbox self.paned.pack1(self._now_box, shrink = False)
def load(self): if self.memberships: data = self.twitter.api_wrapper(self.twitter.api.lists_memberships, self.user, cursor = self._cursor) lists = data["lists"] else: data = self.twitter.api_wrapper(self.twitter.api.lists_subscriptions, self.user, cursor = self._cursor) lists = data["lists"] # get all my lists if first load if self._cursor == -1: c = -1 mylists = list() while c != 0: mydata = self.twitter.api_wrapper(self.twitter.api.lists_index, self.user, cursor = c) mylists.extend(mydata["lists"]) c = int(mydata["next_cursor"]) lists[0:0] = mylists for l in lists: user = twoauth.TwitterUser(l["user"]) self.twitter.add_user(user) listid = int(l["id"]) listname = l["name"] description = TwitterTools.replace_amp(l["description"]) text = "@%s/<b>%s</b>" % (user.screen_name, listname) if description != None: text += "\n<small><span foreground='#666666'>%s</span></small>" % description count = "Following: %s\nFollowers: %s" % (l["member_count"], l["subscriber_count"]) if l["mode"] == "private": private_ico = self.render_icon("gtk-dialog-authentication", gtk.ICON_SIZE_BUTTON) else: private_ico = None self.lists[listid] = l self.store.append((self.iconstore.get(user), text, user.id, listid, private_ico, count)) self._cursor = int(data["next_cursor"]) if self._cursor == 0: self.btn_more.set_sensitive(False) self.btn_more.hide() else: self.btn_more.set_label("Get more 20 lists.")
def __init__(self, status): gtk.VPaned.__init__(self) ico = gtk.image_new_from_pixbuf(self.iconstore.get(status.user)) markup = "<big><b>%s</b></big> - %s\n%s\n<small><span foreground='#666666'>%s via %s</span></small>" text = gtk.Label() text.set_padding(30, 10) text.set_alignment(0, 0.5) text.set_line_wrap(True) label_text = markup % ( status.user.screen_name, status.user.name, status.text, status.created_at.strftime("%Y/%m/%d %H:%M:%S"), status.source_name) label_text = TwitterTools.replace_amp(label_text) text.set_markup(label_text) hbox = gtk.HBox() hbox.set_border_width(10) hbox.pack_start(ico, expand = False, fill = False) hbox.pack_start(text) self._box = gtk.VBox() self._box.pack_start(hbox) self.view = StatusView() win = gtk.ScrolledWindow() win.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC) win.add(self.view) self.pack1(self._box, shrink = False) self.pack2(win) t = threading.Thread(target = self.get_conversation, args = (status,)) t.setDaemon(True) t.start() self.show_all()
def add_status(self, status, overwrite = True): found = self.statuses.get(status.id, None) if not found: self.statuses[status.id] = status elif overwrite: # FIXME: twitter api response is broken? status.retweeted = found.retweeted status.favorited = found.favorited status["faved_by"] = found.get("faved_by", set()) found.update(status) # user self.add_user(status.user) status["user"] = self.users[status.user.id] # hashtag self.hashtags.update(TwitterTools.get_hashtags(status)) # RT if status.retweeted_status: self.add_status(status.retweeted_status, False) status["retweeted_status"] = self.statuses[status.retweeted_status.id]
def _destroy_tweet_in_thread(self, status): self.api_wrapper(self.api.status_destroy, status.id) status["deleted"] = True if TwitterTools.isretweet(status): self.statuses[status.retweeted_status.id]["retweeted"] = False
def menu_setup(self, status): # Get Urls urls = TwitterTools.get_urls(status) urls.extend(TwitterTools.get_media_urls(status)) # Get mentioned users users = TwitterTools.get_user_mentions(status) # Get Hashtags hashes = TwitterTools.get_hashtags(status) # URL Menu urlmenu = gtk.Menu() if urls: # delete multiple urls urls = dict(urls).items() # if exist url in text, add menu for url, display_url in urls: label = "%s..." % display_url[:47] if len(display_url) > 50 else display_url # Menuitem create item = gtk.ImageMenuItem(label) item.set_image(gtk.image_new_from_stock("gtk-open", gtk.ICON_SIZE_MENU)) item.set_always_show_image(True) # Connect click event (open browser) item.connect("activate", self.on_menuitem_url_clicked, url) # append to menu urlmenu.append(item) else: # not, show None item = gtk.MenuItem("None") item.set_sensitive(False) urlmenu.append(item) # Mentioned User Menu usermenu = gtk.Menu() if users: for i in users: # Menuitem create item = gtk.ImageMenuItem("@%s" % i.replace("_", "__")) item.set_image(gtk.image_new_from_stock("gtk-add", gtk.ICON_SIZE_MENU)) item.set_always_show_image(True) # Connect click event (add tab) item.connect("activate", self.on_menuitem_user_clicked, i) # append to menu usermenu.append(item) else: # not, show None item = gtk.MenuItem("None") item.set_sensitive(False) usermenu.append(item) # Hashtags Menu hashmenu = gtk.Menu() if hashes: for i in hashes: # Menuitem create item = gtk.ImageMenuItem("#%s" % i.replace("_", "__")) item.set_image(gtk.image_new_from_stock("gtk-add", gtk.ICON_SIZE_MENU)) item.set_always_show_image(True) # Connect click event (Streaming API) item.connect("activate", self.on_menuitem_hash_clicked, i) # append to menu hashmenu.append(item) else: # not, show None item = gtk.MenuItem("None") item.set_sensitive(False) hashmenu.append(item) # urls submenu append self.pmenu.get_children()[10].set_submenu(usermenu) self.pmenu.get_children()[11].set_submenu(hashmenu) self.pmenu.get_children()[12].set_submenu(urlmenu) self.pmenu.get_children()[6].set_label("@%s Timeline" % status.user.screen_name) # geo if status.geo: self.pmenu.get_children()[13].show() self.pmenu.get_children()[13].set_label( "Geo: %.6f, %.6f" % (status.geo.coordinates[0], status.geo.coordinates[1]) ) if self._geo_handler_id: self.pmenu.get_children()[13].disconnect(self._geo_handler_id) self._geo_handler_id = self.pmenu.get_children()[13].connect( "activate", self.on_menuitem_url_clicked, "http://maps.google.com/?q=%s" % (",".join(map(str, status.geo.coordinates))), ) else: self.pmenu.get_children()[13].hide() # Show popup menu urlmenu.show_all() usermenu.show_all() hashmenu.show_all()
def on_status_selection_changed(self, status): self.builder.get_object("menuitem_tweet").set_sensitive(True) self.statusbar.pop(0) self.statusbar.push(0, TwitterTools.get_footer(status))