fix history window

This commit is contained in:
Yann Leboulanger 2013-01-03 23:30:17 +01:00
parent 1f7d676248
commit 80fcd4d577
2 changed files with 71 additions and 95 deletions

View File

@ -1,63 +1,49 @@
<?xml version="1.0"?> <?xml version="1.0" encoding="UTF-8"?>
<interface> <interface>
<requires lib="gtk+" version="2.16"/> <!-- interface-requires gtk+ 3.0 -->
<!-- interface-naming-policy toplevel-contextual -->
<object class="GtkListStore" id="liststore1">
<columns>
<!-- column-name item -->
<column type="gchararray"/>
</columns>
<data>
<row>
<col id="0" translatable="yes">Enter JID or Contact name</col>
</row>
<row>
<col id="0" translatable="yes">Groupchat Histories</col>
</row>
<row>
<col id="0" translatable="yes">All Chat Histories</col>
</row>
</data>
</object>
<object class="GtkWindow" id="history_window"> <object class="GtkWindow" id="history_window">
<property name="can_focus">False</property>
<property name="title" translatable="yes">Conversation History</property> <property name="title" translatable="yes">Conversation History</property>
<property name="role">history</property> <property name="role">history</property>
<property name="default_width">650</property> <property name="default_width">650</property>
<property name="default_height">450</property> <property name="default_height">450</property>
<signal name="destroy" handler="on_history_window_destroy"/> <signal name="destroy" handler="on_history_window_destroy" swapped="no"/>
<signal name="key_press_event" handler="on_history_window_key_press_event"/> <signal name="key-press-event" handler="on_history_window_key_press_event" swapped="no"/>
<child> <child>
<object class="GtkVBox" id="vbox"> <object class="GtkVBox" id="vbox">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">False</property>
<property name="border_width">12</property> <property name="border_width">12</property>
<property name="orientation">vertical</property>
<property name="spacing">6</property> <property name="spacing">6</property>
<child> <child>
<object class="GtkVBox" id="vbox1"> <object class="GtkVBox" id="vbox1">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">False</property>
<property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property>
<property name="orientation">vertical</property>
<property name="spacing">6</property> <property name="spacing">6</property>
<child> <child>
<object class="GtkHBox" id="hbox1"> <object class="GtkHBox" id="hbox1">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">False</property>
<property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property>
<property name="spacing">6</property> <property name="spacing">6</property>
<child> <child>
<object class="GtkComboBoxEntry" id="query_combobox"> <object class="GtkEntry" id="query_entry">
<property name="visible">True</property> <property name="can_focus">True</property>
<property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> <property name="invisible_char">●</property>
<property name="model">liststore1</property> <property name="invisible_char_set">True</property>
<property name="text_column">0</property> <property name="placeholder_text">Enter name / JID of contact or groupchat</property>
<signal name="changed" handler="on_query_combobox_changed"/>
</object> </object>
<packing> <packing>
<property name="expand">True</property>
<property name="fill">True</property>
<property name="position">0</property> <property name="position">0</property>
</packing> </packing>
</child> </child>
<child> <child>
<object class="GtkLabel" id="label3"> <object class="GtkLabel" id="label3">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">False</property>
<property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property>
<property name="label" translatable="yes">Search:</property> <property name="label" translatable="yes">Search:</property>
</object> </object>
@ -68,26 +54,30 @@
</packing> </packing>
</child> </child>
<child> <child>
<object class="GtkEntry" id="query_entry"> <object class="GtkEntry" id="search_entry">
<property name="visible">True</property> <property name="visible">True</property>
<property name="sensitive">False</property> <property name="sensitive">False</property>
<property name="can_focus">True</property> <property name="can_focus">True</property>
<property name="activates_default">True</property> <property name="activates_default">True</property>
<signal name="activate" handler="on_query_entry_activate"/> <signal name="activate" handler="on_search_entry_activate" swapped="no"/>
</object> </object>
<packing> <packing>
<property name="expand">False</property> <property name="expand">False</property>
<property name="fill">True</property>
<property name="position">2</property> <property name="position">2</property>
</packing> </packing>
</child> </child>
<child> <child>
<object class="GtkCheckButton" id="search_in_date"> <object class="GtkCheckButton" id="search_in_date">
<property name="label" translatable="yes">_In date search</property> <property name="label" translatable="yes">_In date search</property>
<property name="use_action_appearance">False</property>
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">False</property> <property name="can_focus">False</property>
<property name="receives_default">False</property> <property name="receives_default">False</property>
<property name="tooltip_text" translatable="yes">searching only in the selected day </property> <property name="tooltip_text" translatable="yes">searching only in the selected day </property>
<property name="use_action_appearance">False</property>
<property name="use_underline">True</property> <property name="use_underline">True</property>
<property name="xalign">0.5</property>
<property name="draw_indicator">True</property> <property name="draw_indicator">True</property>
</object> </object>
<packing> <packing>
@ -99,6 +89,7 @@
</object> </object>
<packing> <packing>
<property name="expand">False</property> <property name="expand">False</property>
<property name="fill">True</property>
<property name="position">0</property> <property name="position">0</property>
</packing> </packing>
</child> </child>
@ -114,17 +105,18 @@
<child> <child>
<object class="GtkVBox" id="vbox2"> <object class="GtkVBox" id="vbox2">
<property name="visible">True</property> <property name="visible">True</property>
<property name="orientation">vertical</property> <property name="can_focus">False</property>
<property name="spacing">6</property> <property name="spacing">6</property>
<child> <child>
<object class="GtkCalendar" id="calendar"> <object class="GtkCalendar" id="calendar">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">True</property> <property name="can_focus">True</property>
<signal name="month_changed" handler="on_calendar_month_changed"/> <signal name="month-changed" handler="on_calendar_month_changed" swapped="no"/>
<signal name="day_selected" handler="on_calendar_day_selected"/> <signal name="day-selected" handler="on_calendar_day_selected" swapped="no"/>
</object> </object>
<packing> <packing>
<property name="expand">False</property> <property name="expand">False</property>
<property name="fill">True</property>
<property name="position">0</property> <property name="position">0</property>
</packing> </packing>
</child> </child>
@ -141,8 +133,6 @@
<object class="GtkScrolledWindow" id="scrolledwindow"> <object class="GtkScrolledWindow" id="scrolledwindow">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">True</property> <property name="can_focus">True</property>
<property name="hscrollbar_policy">automatic</property>
<property name="vscrollbar_policy">automatic</property>
<property name="shadow_type">etched-in</property> <property name="shadow_type">etched-in</property>
<child> <child>
<placeholder/> <placeholder/>
@ -163,15 +153,16 @@
<object class="GtkScrolledWindow" id="results_scrolledwindow"> <object class="GtkScrolledWindow" id="results_scrolledwindow">
<property name="can_focus">True</property> <property name="can_focus">True</property>
<property name="no_show_all">True</property> <property name="no_show_all">True</property>
<property name="hscrollbar_policy">automatic</property>
<property name="vscrollbar_policy">automatic</property>
<property name="shadow_type">in</property> <property name="shadow_type">in</property>
<child> <child>
<object class="GtkTreeView" id="results_treeview"> <object class="GtkTreeView" id="results_treeview">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">True</property> <property name="can_focus">True</property>
<property name="rules_hint">True</property> <property name="rules_hint">True</property>
<signal name="row_activated" handler="on_results_treeview_row_activated"/> <signal name="row-activated" handler="on_results_treeview_row_activated" swapped="no"/>
<child internal-child="selection">
<object class="GtkTreeSelection" id="treeview-selection1"/>
</child>
</object> </object>
</child> </child>
</object> </object>
@ -182,25 +173,33 @@
</child> </child>
</object> </object>
<packing> <packing>
<property name="expand">True</property>
<property name="fill">True</property>
<property name="position">1</property> <property name="position">1</property>
</packing> </packing>
</child> </child>
</object> </object>
<packing> <packing>
<property name="expand">True</property>
<property name="fill">True</property>
<property name="position">0</property> <property name="position">0</property>
</packing> </packing>
</child> </child>
<child> <child>
<object class="GtkHBox" id="hbox2"> <object class="GtkHBox" id="hbox2">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">False</property>
<property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property> <property name="events">GDK_POINTER_MOTION_MASK | GDK_POINTER_MOTION_HINT_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK</property>
<child> <child>
<object class="GtkCheckButton" id="log_history_checkbutton"> <object class="GtkCheckButton" id="log_history_checkbutton">
<property name="label" translatable="yes">_Log conversation history</property> <property name="label" translatable="yes">_Log conversation history</property>
<property name="use_action_appearance">False</property>
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">True</property> <property name="can_focus">True</property>
<property name="receives_default">False</property> <property name="receives_default">False</property>
<property name="use_action_appearance">False</property>
<property name="use_underline">True</property> <property name="use_underline">True</property>
<property name="xalign">0.5</property>
<property name="active">True</property> <property name="active">True</property>
<property name="draw_indicator">True</property> <property name="draw_indicator">True</property>
</object> </object>
@ -216,23 +215,27 @@
</object> </object>
<packing> <packing>
<property name="expand">False</property> <property name="expand">False</property>
<property name="fill">True</property>
<property name="position">1</property> <property name="position">1</property>
</packing> </packing>
</child> </child>
<child> <child>
<object class="GtkHButtonBox" id="hbuttonbox"> <object class="GtkHButtonBox" id="hbuttonbox">
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">False</property>
<property name="spacing">6</property> <property name="spacing">6</property>
<property name="layout_style">end</property> <property name="layout_style">end</property>
<child> <child>
<object class="GtkButton" id="close_button"> <object class="GtkButton" id="close_button">
<property name="label">gtk-close</property> <property name="label">gtk-close</property>
<property name="use_action_appearance">False</property>
<property name="visible">True</property> <property name="visible">True</property>
<property name="can_focus">True</property> <property name="can_focus">True</property>
<property name="can_default">True</property> <property name="can_default">True</property>
<property name="receives_default">False</property> <property name="receives_default">False</property>
<property name="use_action_appearance">False</property>
<property name="use_stock">True</property> <property name="use_stock">True</property>
<signal name="clicked" handler="on_close_button_clicked"/> <signal name="clicked" handler="on_close_button_clicked" swapped="no"/>
</object> </object>
<packing> <packing>
<property name="expand">False</property> <property name="expand">False</property>

View File

@ -26,6 +26,7 @@
## ##
from gi.repository import Gtk from gi.repository import Gtk
from gi.repository import Gdk
from gi.repository import GObject from gi.repository import GObject
import time import time
import calendar import calendar
@ -69,18 +70,17 @@ class HistoryWindow:
self.calendar = xml.get_object('calendar') self.calendar = xml.get_object('calendar')
scrolledwindow = xml.get_object('scrolledwindow') scrolledwindow = xml.get_object('scrolledwindow')
self.history_textview = conversation_textview.ConversationTextview( self.history_textview = conversation_textview.ConversationTextview(
account, used_in_history_window = True) account, used_in_history_window = True)
scrolledwindow.add(self.history_textview.tv) scrolledwindow.add(self.history_textview.tv)
self.history_buffer = self.history_textview.tv.get_buffer() self.history_buffer = self.history_textview.tv.get_buffer()
self.history_buffer.create_tag('highlight', background = 'yellow') self.history_buffer.create_tag('highlight', background = 'yellow')
self.checkbutton = xml.get_object('log_history_checkbutton') self.checkbutton = xml.get_object('log_history_checkbutton')
self.checkbutton.connect('toggled', self.checkbutton.connect('toggled',
self.on_log_history_checkbutton_toggled) self.on_log_history_checkbutton_toggled)
self.query_entry = xml.get_object('query_entry') self.search_entry = xml.get_object('search_entry')
self.query_combobox = xml.get_object('query_combobox') self.query_liststore = xml.get_object('query_liststore')
self.jid_entry = self.query_combobox.get_child() self.jid_entry = xml.get_object('query_entry')
self.jid_entry.connect('activate', self.on_jid_entry_activate) self.jid_entry.connect('activate', self.on_jid_entry_activate)
self.query_combobox.set_active(0)
self.results_treeview = xml.get_object('results_treeview') self.results_treeview = xml.get_object('results_treeview')
self.results_window = xml.get_object('results_scrolledwindow') self.results_window = xml.get_object('results_scrolledwindow')
self.search_in_date = xml.get_object('search_in_date') self.search_in_date = xml.get_object('search_in_date')
@ -91,24 +91,24 @@ class HistoryWindow:
col = Gtk.TreeViewColumn(_('Name')) col = Gtk.TreeViewColumn(_('Name'))
self.results_treeview.append_column(col) self.results_treeview.append_column(col)
renderer = Gtk.CellRendererText() renderer = Gtk.CellRendererText()
col.pack_start(renderer, True, True, 0) col.pack_start(renderer, True)
col.set_attributes(renderer, text = C_CONTACT_NAME) col.add_attribute(renderer, 'text', C_CONTACT_NAME)
col.set_sort_column_id(C_CONTACT_NAME) # user can click this header and sort col.set_sort_column_id(C_CONTACT_NAME) # user can click this header and sort
col.set_resizable(True) col.set_resizable(True)
col = Gtk.TreeViewColumn(_('Date')) col = Gtk.TreeViewColumn(_('Date'))
self.results_treeview.append_column(col) self.results_treeview.append_column(col)
renderer = Gtk.CellRendererText() renderer = Gtk.CellRendererText()
col.pack_start(renderer, True, True, 0) col.pack_start(renderer, True)
col.set_attributes(renderer, text = C_UNIXTIME) col.add_attribute(renderer, 'text', C_UNIXTIME)
col.set_sort_column_id(C_UNIXTIME) # user can click this header and sort col.set_sort_column_id(C_UNIXTIME) # user can click this header and sort
col.set_resizable(True) col.set_resizable(True)
col = Gtk.TreeViewColumn(_('Message')) col = Gtk.TreeViewColumn(_('Message'))
self.results_treeview.append_column(col) self.results_treeview.append_column(col)
renderer = Gtk.CellRendererText() renderer = Gtk.CellRendererText()
col.pack_start(renderer, True, True, 0) col.pack_start(renderer, True)
col.set_attributes(renderer, text = C_MESSAGE) col.add_attribute(renderer, 'text', C_MESSAGE)
col.set_resizable(True) col.set_resizable(True)
self.jid = None # The history we are currently viewing self.jid = None # The history we are currently viewing
@ -118,7 +118,8 @@ class HistoryWindow:
self.jids_to_search = [] self.jids_to_search = []
# This will load history too # This will load history too
GObject.idle_add(self._fill_completion_dict().next) task = self._fill_completion_dict()
GObject.idle_add(next, task)
if jid: if jid:
self.jid_entry.set_text(jid) self.jid_entry.set_text(jid)
@ -152,7 +153,7 @@ class HistoryWindow:
db_jids = gajim.logger.get_jids_in_db() db_jids = gajim.logger.get_jids_in_db()
completion_dict = dict.fromkeys(db_jids) completion_dict = dict.fromkeys(db_jids)
self.accounts_seen_online = gajim.contacts.get_accounts()[:] self.accounts_seen_online = list(gajim.contacts.get_accounts())
# Enhance contacts of online accounts with contact. Needed for mapping below # Enhance contacts of online accounts with contact. Needed for mapping below
for account in self.accounts_seen_online: for account in self.accounts_seen_online:
@ -163,14 +164,14 @@ class HistoryWindow:
muc_active_pix = muc_active_img.get_pixbuf() muc_active_pix = muc_active_img.get_pixbuf()
contact_pix = contact_img.get_pixbuf() contact_pix = contact_img.get_pixbuf()
keys = completion_dict.keys() keys = list(completion_dict.keys())
# Move the actual jid at first so we load history faster # Move the actual jid at first so we load history faster
actual_jid = self.jid_entry.get_text() actual_jid = self.jid_entry.get_text()
if actual_jid in keys: if actual_jid in keys:
keys.remove(actual_jid) keys.remove(actual_jid)
keys.insert(0, actual_jid) keys.insert(0, actual_jid)
if None in keys: if '' in keys:
keys.remove(None) keys.remove('')
# Map jid to info tuple # Map jid to info tuple
# Warning : This for is time critical with big DB # Warning : This for is time critical with big DB
for key in keys: for key in keys:
@ -240,10 +241,6 @@ class HistoryWindow:
self.window.destroy() self.window.destroy()
def on_jid_entry_activate(self, widget): def on_jid_entry_activate(self, widget):
if not self.query_combobox.get_active() < 0:
# Don't disable querybox when we have changed the combobox
# to GC or All and hit enter
return
jid = self.jid_entry.get_text() jid = self.jid_entry.get_text()
account = None # we don't know the account, could be any. Search for it! account = None # we don't know the account, could be any. Search for it!
self._load_history(jid, account) self._load_history(jid, account)
@ -300,8 +297,8 @@ class HistoryWindow:
self.calendar.select_month(gtk_month, y) self.calendar.select_month(gtk_month, y)
self.calendar.select_day(d) self.calendar.select_day(d)
self.query_entry.set_sensitive(True) self.search_entry.set_sensitive(True)
self.query_entry.grab_focus() self.search_entry.grab_focus()
title = _('Conversation History with %s') % info_name title = _('Conversation History with %s') % info_name
self.window.set_title(title) self.window.set_title(title)
@ -313,7 +310,7 @@ class HistoryWindow:
self.account = None self.account = None
self.history_buffer.set_text('') # clear the buffer self.history_buffer.set_text('') # clear the buffer
self.query_entry.set_sensitive(False) self.search_entry.set_sensitive(False)
self.checkbutton.set_sensitive(False) self.checkbutton.set_sensitive(False)
self.calendar.set_sensitive(False) self.calendar.set_sensitive(False)
@ -491,8 +488,8 @@ class HistoryWindow:
xhtml=xhtml) xhtml=xhtml)
self.history_textview.print_real_text('\n') self.history_textview.print_real_text('\n')
def on_query_entry_activate(self, widget): def on_search_entry_activate(self, widget):
text = self.query_entry.get_text() text = self.search_entry.get_text()
model = self.results_treeview.get_model() model = self.results_treeview.get_model()
model.clear() model.clear()
if text == '': if text == '':
@ -502,7 +499,7 @@ class HistoryWindow:
self.results_window.set_property('visible', True) self.results_window.set_property('visible', True)
# perform search in preselected jids # perform search in preselected jids
# jids are preselected with the query_combobox (all, single jid...) # jids are preselected with the query_entry
for jid in self.jids_to_search: for jid in self.jids_to_search:
account = self.completion_dict[jid][C_INFO_ACCOUNT] account = self.completion_dict[jid][C_INFO_ACCOUNT]
if account is None: if account is None:
@ -538,31 +535,7 @@ class HistoryWindow:
# jid (to which log is assigned to), name, date, message, # jid (to which log is assigned to), name, date, message,
# time (full unix time) # time (full unix time)
model.append((jid, contact_name, date, message, tim)) model.append((jid, contact_name, date, message, str(tim)))
def on_query_combobox_changed(self, widget):
if self.query_combobox.get_active() < 0:
return # custom entry
self.account = None
self.jid = None
self.jids_to_search = []
self._load_history(None) # clear textview
if self.query_combobox.get_active() == 0:
# JID or Contact name
self.query_entry.set_sensitive(False)
self.jid_entry.grab_focus()
if self.query_combobox.get_active() == 1:
# Groupchat Histories
self.query_entry.set_sensitive(True)
self.query_entry.grab_focus()
self.jids_to_search = (jid for jid in gajim.logger.get_jids_in_db()
if gajim.logger.jid_is_room_jid(jid))
if self.query_combobox.get_active() == 2:
# All Chat Histories
self.query_entry.set_sensitive(True)
self.query_entry.grab_focus()
self.jids_to_search = gajim.logger.get_jids_in_db()
def on_results_treeview_row_activated(self, widget, path, column): def on_results_treeview_row_activated(self, widget, path, column):
""" """
@ -641,7 +614,7 @@ class HistoryWindow:
self.jid_entry.set_text(jid) self.jid_entry.set_text(jid)
if account and account not in self.accounts_seen_online: if account and account not in self.accounts_seen_online:
# Update dict to not only show bare jid # Update dict to not only show bare jid
GObject.idle_add(self._fill_completion_dict().next) GObject.idle_add(next, self._fill_completion_dict())
else: else:
# Only in that case because it's called by self._fill_completion_dict() # Only in that case because it's called by self._fill_completion_dict()
# otherwise # otherwise
@ -649,7 +622,7 @@ class HistoryWindow:
self.results_window.set_property('visible', False) self.results_window.set_property('visible', False)
def save_state(self): def save_state(self):
x, y = self.window.window.get_root_origin() x, y = self.window.get_window().get_root_origin()
width, height = self.window.get_size() width, height = self.window.get_size()
gajim.config.set('history_window_x-position', x) gajim.config.set('history_window_x-position', x)