import bookmark_list
import bookmark_window
import thread_view
+import thread_popup
+import submit_window
GLADE_FILENAME = "thread_window.glade"
class HTMLParserToThreadView:
- def __init__(self, threadview, resnum):
+ def __init__(self, threadview, resnum, left_margin):
self.threadview = threadview
self.resnum = resnum
+ self.left_margin = left_margin
self.initialize()
+ def set_left_margin(self, left_margin):
+ self.left_margin = left_margin
+
def initialize(self):
- self.buf = ""
- self.attrlist = pango.AttrList()
- self.urilist = []
+ self.layout = None
+
+ def on_new_line(self):
+ self.to_thread_view()
+ self.layout = self.threadview.create_res_layout(
+ self.left_margin, self.resnum)
def from_html_parser(self, data, bold, href):
- data = data.encode("utf8")
- start = len(self.buf)
- end = start + len(data)
- self.buf += data
- if bold:
- attr = pango.AttrWeight(pango.WEIGHT_BOLD, start, end)
- self.attrlist.insert(attr)
- if href:
- attr = pango.AttrUnderline(pango.UNDERLINE_SINGLE, start, end)
- self.attrlist.insert(attr)
- self.urilist.append((start, end, href))
-
- def to_thread_view(self, marginleft):
- layout = self.threadview.create_pango_layout(self.buf)
- layout.posY = 0
- layout.resnum = self.resnum
- layout.marginleft = marginleft
- layout.set_attributes(self.attrlist)
- layout.urilist = self.urilist
- gobject.idle_add(self.threadview.add_layout, layout)
- self.initialize()
+ if self.layout == None:
+ self.layout = self.threadview.create_res_layout(
+ self.left_margin, self.resnum)
+
+ self.layout.add_text(data, bold, href)
+
+ def to_thread_view(self):
+ if self.layout is not None:
+ # gobject.idle_add(self.threadview.add_layout, self.layout)
+ gtk.gdk.threads_enter()
+ self.threadview.add_layout(self.layout)
+ gtk.gdk.threads_leave()
+ self.initialize()
class WinWrap(winwrapbase.WinWrapBase):
glade_path = os.path.join(config.glade_dir, GLADE_FILENAME)
self.widget_tree = gtk.glade.XML(glade_path)
- self.window = self.widget_tree.get_widget("thread_window")
- self.toolbar = self.widget_tree.get_widget("toolbar")
+ self._get_widgets()
+ self.widget_tree.signal_autoconnect(self)
+
self.toolbar.unset_style()
- self.statusbar = self.widget_tree.get_widget("statusbar")
- self.vbox = self.widget_tree.get_widget("vbox")
self.threadview = thread_view.ThreadView()
+ self.threadpopup = thread_popup.ThreadPopup(self.bbs_type)
+ self.threadpopup.push_thread_view(self.threadview)
self.vbox.pack_start(self.threadview)
self.vbox.reorder_child(self.threadview, 2)
+ self.window.set_focus(self.threadview.drawingarea)
- self.threadview.on_uri_clicked = self.on_threadview_uri_clicked
+ self._get_popupmenu_widgets()
- self.initialize_buffer()
+ self.threadview.connect(
+ "uri-clicked-event", self.on_thread_view_uri_clicked)
+ self.threadpopup.connect(
+ "uri-clicked-event", self.on_thread_popup_uri_clicked)
+
+ self.statusbar_context_id = self.statusbar.get_context_id(
+ "Thread Window Status")
+ self.statusbar.push(self.statusbar_context_id, "OK.")
- sigdic = {"on_refresh_activate": self.update,
- "on_compose_activate": self.on_compose_clicked,
- "on_toolbar_activate": self.on_toolbar_activate,
- "on_statusbar_activate": self.on_statusbar_activate,
- "on_refresh_activate": self.update,
- "on_close_activate": self.on_close_activate,
- "on_quit_activate": self.on_quit_activate,
- "on_show_board_activate": self.on_show_board_activate,
- "on_delete_activate": self.on_delete_activate,
- "on_thread_window_delete_event":
- self.on_thread_window_delete_event,
- "on_add_bookmark_activate": self.on_add_bookmark_activate,
- "on_manage_bookmarks_activate": \
- self.on_manage_bookmarks_activate,
- "on_thread_window_destroy": self.on_thread_window_destroy}
- self.widget_tree.signal_autoconnect(sigdic)
+ self.initialize_buffer()
self.restore()
self.window.show_all()
self.created()
- def initialize_buffer(self):
- self.textbuffer = gtk.TextBuffer()
+ def _get_widgets(self):
+ self.window = self.widget_tree.get_widget("thread_window")
+ self.toolbar = self.widget_tree.get_widget("toolbar")
+ self.statusbar = self.widget_tree.get_widget("statusbar")
+ self.vbox = self.widget_tree.get_widget("vbox")
- self.enditer = self.textbuffer.get_end_iter()
- self.boldtag = self.textbuffer.create_tag(weight=pango.WEIGHT_BOLD)
- self.leftmargintag = self.textbuffer.create_tag()
- self.leftmargintag.set_property("left-margin", 20)
+ def _get_popupmenu_widgets(self):
+ self.threadview.popupmenu = self.widget_tree.get_widget(
+ "popup_threadview_menu")
+ self.threadview.menu_openuri = self.widget_tree.get_widget(
+ "popup_threadview_menu_openuri")
+ self.threadview.menu_copylinkaddress = self.widget_tree.get_widget(
+ "popup_threadview_menu_copylinkaddress")
+ self.threadview.menu_separator_link = self.widget_tree.get_widget(
+ "popup_threadview_menu_separator_link")
+ self.threadview.menu_copyselection = self.widget_tree.get_widget(
+ "popup_threadview_menu_copyselection")
+ self.threadview.menu_openasuri = self.widget_tree.get_widget(
+ "popup_threadview_menu_openasuri")
+ self.threadview.menu_separator_selection = self.widget_tree.get_widget(
+ "popup_threadview_menu_separator_selection")
+ def initialize_buffer(self):
self.threadview.initialize_buffer()
def destroy(self):
def get_uri(self):
return self.bbs_type.get_thread_uri()
- def on_compose_clicked(self, widget):
- import submit_window
+ def show(self):
+ self.window.deiconify()
+
+ def hide(self):
+ self.window.iconify()
+
+ def _show_submit_window(self):
submit_window.open(self.bbs_type.get_thread_uri())
- def on_toolbar_activate(self, widget):
+ def _toggle_toolbar(self):
if self.toolbar.get_property("visible"):
self.toolbar.hide()
else:
self.toolbar.show()
- def on_statusbar_activate(self, widget):
+ def _toggle_statusbar(self):
if self.statusbar.get_property("visible"):
self.statusbar.hide()
else:
self.statusbar.show()
- def on_close_activate(self, widget):
+ def _close_window(self):
self.destroy()
- def on_thread_window_delete_event(self, widget, event):
- self.save()
- return False
-
- def on_thread_window_destroy(self, widget):
- self.destroyed()
-
- def on_quit_activate(self, widget):
+ def _quit_session(self):
session.main_quit()
- def on_add_bookmark_activate(self, widget):
+ def _regist_as_bookmark(self):
bookmark_list.bookmark_list.add_bookmark_with_edit(
name=self.title, uri=self.bbs_type.uri)
- def on_manage_bookmarks_activate(self, widget):
+ def _manage_bookmarks(self):
bookmark_window.open()
- def on_show_board_activate(self, widget):
+ def _show_board(self):
board_window.open_board(self.bbs_type.get_uri_base())
- def on_delete_activate(self, widget):
+ def _delete_log(self):
try:
dat_path = misc.get_thread_dat_path(self.bbs_type)
os.remove(dat_path)
except OSError:
traceback.print_exc()
- def on_threadview_uri_clicked(self, uri):
-
+ def _open_uri(self, uri):
if not uri.startswith("http://"):
# maybe a relative uri.
uri = urlparse.urljoin(self.bbs_type.get_uri_base(), uri)
except bbs_type_exception.BbsTypeError:
# not supported, show with the web browser.
gnome.url_show(uri)
-
+
+ def _copy_text_to_clipboard(self, text):
+ if text and len(text) > 0:
+ clip = gtk.Clipboard()
+ text = text.encode("utf8")
+ clip.set_text(text, len(text))
+
+ def _modify_uri(self, uri):
+ if not uri.startswith("http://"):
+ uri = "http://" + uri
+ return uri
+
def http_get_dat(self, on_get_res):
datfile_url = self.bbs_type.get_dat_uri()
if etag:
req.add_header("If-None-Match", etag)
+ def push():
+ self.statusbar.pop(self.statusbar_context_id)
+ self.statusbar.push(self.statusbar_context_id, "GET...")
+ gobject.idle_add(push)
+
req = self.bbs_type.set_extra_dat_request(req, self)
opener = urllib2.build_opener(HTTPRedirectHandler302, HTTPDebugHandler)
try:
res = opener.open(req)
except urllib2.HTTPError, e:
- pass
-# gobject.idle_add(
-# lambda x: self.statusbar.push(0, x), "%d %s" % (e.code, e.msg))
+ def push(code, msg):
+ message = "%d %s" % (code, msg)
+ self.statusbar.pop(self.statusbar_context_id)
+ self.statusbar.push(self.statusbar_context_id, message)
+ gobject.idle_add(push, e.code, e.msg)
else:
headers = res.info()
-# gobject.idle_add(
-# lambda x: self.statusbar.push(0, x), "%d %s" % (res.code, res.msg))
+
+ if "Last-Modified" in headers:
+ la = headers["Last-Modified"]
+ def push(code, msg, lastm):
+ message = "%d %s [%s]" % (code, msg, lastm)
+ self.statusbar.pop(self.statusbar_context_id)
+ self.statusbar.push(self.statusbar_context_id, message)
+ gobject.idle_add(push, res.code, res.msg, la)
+ else:
+ def push(code, msg):
+ message = "%d %s" % (code, msg)
+ self.statusbar.pop(self.statusbar_context_id)
+ self.statusbar.push(self.statusbar_context_id, message)
+ gobject.idle_add(push, res.code, res.msg)
maybe_incomplete = False
for line in res:
gobject.idle_add(session.thread_idx_updated,
self.bbs_type.get_thread_uri(), idx_dic)
- def update(self, widget=None):
+ def update(self):
self.jump_request_num = 0
def load():
- if self.num == 0:
- def create_mark():
- self.textbuffer.create_mark("1", self.enditer, True)
- gobject.idle_add(create_mark)
-
line_count = datfile.get_dat_line_count(self.bbs_type)
if line_count < self.num:
self.num = 0
self.append_rawres_to_buffer(line)
self.http_get_dat(save_line_and_append_to_buffer)
+ gtk.gdk.threads_enter()
+ self.threadview.redraw()
+ gtk.gdk.threads_leave()
dat_file.close()
def do_jump():
print "maybe syntax error.", self.num, line
def reselems_to_buffer(self, num, name, mail, date, msg):
- pipe = HTMLParserToThreadView(self.threadview, num)
- p = barehtmlparser.BareHTMLParser(pipe.from_html_parser)
+ pipe = HTMLParserToThreadView(self.threadview, num, 0)
+ p = barehtmlparser.BareHTMLParser(
+ pipe.from_html_parser, pipe.on_new_line)
# First, create a pango layout for num,name,mail,date
# 'margin left' is 0
p.feed(date)
p.flush()
- pipe.to_thread_view(0)
+ pipe.to_thread_view()
# Second, create a pango layout for message
# 'margin left' is 20
# msg
+ pipe.set_left_margin(20)
p.feed(msg.lstrip(" "))
p.feed("<br>")
p.close()
- pipe.to_thread_view(20)
-
- def href_tag(self, href):
- tag = self.textbuffer.create_tag(underline=pango.UNDERLINE_SINGLE)
- tag.set_data("href", href)
- return tag
+ pipe.to_thread_view()
def jump(self, value):
gobject.idle_add(self.threadview.jump, value)
priority=gobject.PRIORITY_HIGH)
except:
traceback.print_exc()
+
+
+ # signal handlers
+
+ def on_thread_view_uri_clicked(self, widget, uri):
+ self._open_uri(uri)
+
+ def on_thread_popup_uri_clicked(self, widget, threadview, uri):
+ self._open_uri(uri)
+
+ def on_thread_window_delete_event(self, widget, event):
+ self.save()
+ return False
+
+ def on_thread_window_destroy(self, widget):
+ self.destroyed()
+
+
+
+
+ # menu commands
+
+ # menu file
+
+ def on_menu_file_show_board_activate(self, widget):
+ self._show_board()
+
+ def on_menu_file_compose_activate(self, widget):
+ self._show_submit_window()
+
+ def on_menu_file_delete_activate(self, widget):
+ self._delete_log()
+
+ def on_menu_file_close_activate(self, widget):
+ self._close_window()
+
+ def on_menu_file_quit_activate(self, widget):
+ self._quit_session()
+
+ # menu view
+
+ def on_menu_view_refresh_activate(self, widget):
+ self.update()
+
+ def on_menu_view_toolbar_activate(self, widget):
+ self._toggle_toolbar()
+
+ def on_menu_view_statusbar_activate(self, widget):
+ self._toggle_statusbar()
+
+ # menu bookmarks
+
+ def on_menu_bookmarks_bookmarkthispage_activate(self, widget):
+ self._regist_as_bookmark()
+
+ def on_menu_bookmarks_showbookmarks_activate(self, widget):
+ self._manage_bookmarks()
+
+ # toolbuttons
+
+ def on_toolbutton_refresh_activate(self, widget):
+ self.update()
+
+ def on_toolbutton_showboard_activate(self, widget):
+ self._show_board()
+
+ def on_toolbutton_compose_activate(self, widget):
+ self._show_submit_window()
+
+ def on_toolbutton_delete_activate(self, widget):
+ self._delete_log()
+
+ # popup menus
+
+ def on_popup_threadview_menu_openuri_activate(self, widget):
+ self._open_uri(widget.uri)
+
+ def on_popup_threadview_menu_copylinkaddress_activate(self, widget):
+ self._copy_text_to_clipboard(widget.uri)
+
+ def on_popup_threadview_menu_copyselection_activate(self, widget):
+ text = self.threadview.get_selected_text()
+ self._copy_text_to_clipboard(text)
+
+ def on_popup_threadview_menu_openasuri_activate(self, widget):
+ text = self.threadview.get_selected_text()
+ uri = self._modify_uri(text)
+ self._open_uri(uri)
+
+ def on_popup_threadview_menu_refresh_activate(self, widget):
+ self.update()