2006-07-09 Don Allingham <don@gramps-project.org>
* configure.in: up the version number * src/DataViews/_FamilyList.py: add support for sidebar filter * src/DisplayModels/_BaseModel.py: handle generic model filtering * src/PageView.py: Add support for generic modeling * src/Filters/__init__.py: generic family rule support * src/Filters/_GenericFilter.py: generic family rule support * help/C/gramps-manual.xml: updates * help/Makefile.am: remove old files svn: r7013
This commit is contained in:
		| @@ -1,3 +1,13 @@ | ||||
| 2006-07-09  Don Allingham  <don@gramps-project.org> | ||||
| 	* configure.in: up the version number | ||||
| 	* src/DataViews/_FamilyList.py: add support for sidebar filter | ||||
| 	* src/DisplayModels/_BaseModel.py: handle generic model filtering | ||||
| 	* src/PageView.py: Add support for generic modeling | ||||
| 	* src/Filters/__init__.py: generic family rule support | ||||
| 	* src/Filters/_GenericFilter.py: generic family rule support | ||||
| 	* help/C/gramps-manual.xml: updates | ||||
| 	* help/Makefile.am: remove old files | ||||
|  | ||||
| 2006-07-08  Don Allingham  <don@gramps-project.org> | ||||
| 	* src/ScratchPad.py (ScratchPersonLink.tooltip): fix tooltip for | ||||
| 	person | ||||
|   | ||||
| @@ -4,15 +4,15 @@ dnl Process this file with autoconf to produce a configure script. | ||||
| dnl May need to run automake && aclocal first | ||||
|  | ||||
| AC_PREREQ(2.57) | ||||
| AC_INIT(gramps, 2.1.6, [gramps-bugs@lists.sourceforge.net]) | ||||
| AC_INIT(gramps, 2.1.8, [gramps-bugs@lists.sourceforge.net]) | ||||
| AC_CONFIG_SRCDIR(configure.in) | ||||
| AM_INIT_AUTOMAKE(1.6.3) | ||||
|  | ||||
| AC_CONFIG_MACRO_DIR([m4]) | ||||
| GNOME_DOC_INIT | ||||
|  | ||||
| dnl RELEASE=0.SVN$(svnversion -n .) | ||||
| RELEASE=1 | ||||
| RELEASE=0.SVN$(svnversion -n .) | ||||
| dnl RELEASE=1 | ||||
|  | ||||
| VERSIONSTRING=$VERSION | ||||
| if test x"$RELEASE" != "x" | ||||
|   | ||||
| @@ -26,7 +26,7 @@ | ||||
|   <!-- appropriate code --> | ||||
|  | ||||
|   <bookinfo> | ||||
|     <title>GRAMPS Manual V3.0</title> | ||||
|     <title>GRAMPS Manual V2.8</title> | ||||
|  | ||||
|     <copyright> | ||||
|       <year>2001</year> | ||||
| @@ -143,11 +143,11 @@ | ||||
|  | ||||
|     <!-- When the desktop release version changes to V3.x, the revision number of the manual changes --> | ||||
|  | ||||
|     <!-- to V3.0, and so on. --> | ||||
|     <!-- to V2.8, and so on. --> | ||||
|  | ||||
|     <revhistory> | ||||
|       <revision> | ||||
|         <revnumber>GRAMPS Manual V3.0</revnumber> | ||||
|         <revnumber>GRAMPS Manual V2.8</revnumber> | ||||
|  | ||||
|         <date>July 2006</date> | ||||
|  | ||||
|   | ||||
| @@ -6,72 +6,70 @@ dist-hook: doc-dist-hook | ||||
|  | ||||
| DOC_MODULE = gramps-manual | ||||
| DOC_ENTITIES = \ | ||||
| 	authors.xml \ | ||||
| 	bugs.xml \ | ||||
| 	cmdline.xml \ | ||||
| 	cmdplug.xml \ | ||||
| 	custom.xml \ | ||||
| 	faq.xml \ | ||||
| 	filtref.xml \ | ||||
| 	getstart.xml \ | ||||
| 	keybind.xml \ | ||||
| 	legal.xml \ | ||||
| 	mainwin.xml \ | ||||
| 	manual.xml \ | ||||
| 	preface.xml \ | ||||
| 	usage.xml | ||||
| 	gramps-manual.xml | ||||
|  | ||||
| DOC_FIGURES = \ | ||||
| 	figures/bookreport.png \ | ||||
| 	figures/cfe-ar.png \ | ||||
| 	figures/cfe-df.png \ | ||||
| 	figures/column-editor.png \ | ||||
| 	figures/comp-people.png \ | ||||
| 	figures/date-selection.png \ | ||||
| 	figures/edit-ad.png \ | ||||
| 	figures/edit-an.png \ | ||||
| 	figures/edit-at.png \ | ||||
| 	figures/edit-bm.png \ | ||||
| 	figures/edit-ev.png \ | ||||
| 	figures/edit-media.png \ | ||||
| 	figures/edit-person-addresses.png \ | ||||
| 	figures/edit-person-attributes.png \ | ||||
| 	figures/edit-person-events.png \ | ||||
| 	figures/edit-person-gallery.png \ | ||||
| 	figures/edit-person-internet.png \ | ||||
| 	figures/edit-person-lds.png \ | ||||
| 	figures/edit-person-names.png \ | ||||
| 	figures/edit-person-notes.png \ | ||||
| 	figures/edit-person.png \ | ||||
| 	figures/edit-person-sources.png \ | ||||
| 	figures/edit-plc.png \ | ||||
| 	figures/edit-rel.png \ | ||||
| 	figures/edit-si.png \ | ||||
| 	figures/edit-src.png \ | ||||
| 	figures/edit-wi.png \ | ||||
| 	figures/export-druid.png \ | ||||
| 	figures/family-alt.png \ | ||||
| 	figures/family.png \ | ||||
| 	figures/find-people.png \ | ||||
| 	figures/first-open.png \ | ||||
| 	figures/gedcom-export.png \ | ||||
| 	figures/gedcom-export-progress.png \ | ||||
| 	figures/gedcom-import.png \ | ||||
| 	figures/mainwin.png \ | ||||
| 	figures/media.png \ | ||||
| 	figures/merge-people.png \ | ||||
| 	figures/merge-plc.png \ | ||||
| 	figures/merge-src.png \ | ||||
| 	figures/missing-media.png \ | ||||
| 	figures/noside-nofilt.png \ | ||||
| 	figures/pedigree-anchor.png \ | ||||
| 	figures/pedigree-child-cut.png \ | ||||
| 	figures/pedigree.png \ | ||||
| 	figures/pedigree-siblings-cut.png \ | ||||
| 	figures/places.png \ | ||||
| 	figures/prefs.png \ | ||||
| 	figures/researcher.png \ | ||||
| 	figures/scratch-pad.png \ | ||||
| 	figures/side-filt.png \ | ||||
| 	figures/bookreport.png\ | ||||
| 	figures/cfe-ar.png\ | ||||
| 	figures/cfe-df.png\ | ||||
| 	figures/child-ref.png\ | ||||
| 	figures/column-editor.png\ | ||||
| 	figures/comp-people.png\ | ||||
| 	figures/date-selection.png\ | ||||
| 	figures/edit-ad.png\ | ||||
| 	figures/edit-an.png\ | ||||
| 	figures/edit-at.png\ | ||||
| 	figures/edit-bm.png\ | ||||
| 	figures/edit-ev.png\ | ||||
| 	figures/edit-ev-ref.png\ | ||||
| 	figures/edit-family.png\ | ||||
| 	figures/edit-media.png\ | ||||
| 	figures/edit-person-addresses.png\ | ||||
| 	figures/edit-person-assoc.png\ | ||||
| 	figures/edit-person-attributes.png\ | ||||
| 	figures/edit-person-events.png\ | ||||
| 	figures/edit-person-gallery.png\ | ||||
| 	figures/edit-person-internet.png\ | ||||
| 	figures/edit-person-lds.png\ | ||||
| 	figures/edit-person-names.png\ | ||||
| 	figures/edit-person-notes.png\ | ||||
| 	figures/edit-person.png\ | ||||
| 	figures/edit-person-sources.png\ | ||||
| 	figures/edit-plc.png\ | ||||
| 	figures/edit-rel.png\ | ||||
| 	figures/edit-si.png\ | ||||
| 	figures/edit-src.png\ | ||||
| 	figures/edit-wi.png\ | ||||
| 	figures/events.png\ | ||||
| 	figures/export-druid.png\ | ||||
| 	figures/family-alt.png\ | ||||
| 	figures/family-list.png\ | ||||
| 	figures/family.png\ | ||||
| 	figures/family-warn.png\ | ||||
| 	figures/find-people.png\ | ||||
| 	figures/first-open.png\ | ||||
| 	figures/gedcom-export.png\ | ||||
| 	figures/gedcom-export-progress.png\ | ||||
| 	figures/gedcom-import.png\ | ||||
| 	figures/mainwin.png\ | ||||
| 	figures/media.png\ | ||||
| 	figures/merge-people.png\ | ||||
| 	figures/merge-plc.png\ | ||||
| 	figures/merge-src.png\ | ||||
| 	figures/missing-media.png\ | ||||
| 	figures/noside-nofilt.png\ | ||||
| 	figures/pedigree-anchor.png\ | ||||
| 	figures/pedigree-child-cut.png\ | ||||
| 	figures/pedigree.png\ | ||||
| 	figures/pedigree-siblings-cut.png\ | ||||
| 	figures/places.png\ | ||||
| 	figures/prefs.png\ | ||||
| 	figures/repository.png\ | ||||
| 	figures/researcher.png\ | ||||
| 	figures/scratch-pad.png\ | ||||
| 	figures/select-family.png\ | ||||
| 	figures/select-person.png\ | ||||
| 	figures/side-filt.png\ | ||||
| 	figures/sources.png | ||||
|  | ||||
| DOC_LINGUAS =  | ||||
|   | ||||
| @@ -29,6 +29,7 @@ import PageView | ||||
| import DisplayModels | ||||
| import Bookmarks | ||||
| import Errors | ||||
| from Filters import FamilySidebarFilter | ||||
|  | ||||
| #------------------------------------------------------------------------- | ||||
| # | ||||
| @@ -69,7 +70,7 @@ class FamilyListView(PageView.ListView): | ||||
|             self, _('Family List'), dbstate, uistate, | ||||
|             column_names, len(column_names), DisplayModels.FamilyModel, | ||||
|             signal_map, dbstate.db.get_family_bookmarks(), | ||||
|             Bookmarks.FamilyBookmarks) | ||||
|             Bookmarks.FamilyBookmarks, filter_class=FamilySidebarFilter) | ||||
|          | ||||
|         self.updating = False | ||||
|  | ||||
| @@ -97,6 +98,9 @@ class FamilyListView(PageView.ListView): | ||||
|     def ui_definition(self): | ||||
|         return '''<ui> | ||||
|           <menubar name="MenuBar"> | ||||
|             <menu action="ViewMenu"> | ||||
|               <menuitem action="Filter"/> | ||||
|             </menu> | ||||
|             <menu action="EditMenu"> | ||||
|               <placeholder name="CommonEdit"> | ||||
|                 <menuitem action="Add"/> | ||||
|   | ||||
| @@ -61,15 +61,24 @@ class BaseModel(gtk.GenericTreeModel): | ||||
|         self.sort_func = self.smap[scol] | ||||
|         self.sort_col = scol | ||||
|         self.skip = skip | ||||
|          | ||||
|  | ||||
|         if search: | ||||
|             col = search[0] | ||||
|             text = search[1] | ||||
|             inv = search[2] | ||||
|             func = lambda x: self.on_get_value(x, col) or u"" | ||||
|             self.search = SearchFilter(func, text, inv) | ||||
|             if search[0]: | ||||
|                 self.search = search[1] | ||||
|                 self.rebuild_data = self._rebuild_filter | ||||
|             else: | ||||
|                 if search[1]: | ||||
|                     col = search[1][0] | ||||
|                     text = search[1][1] | ||||
|                     inv = search[1][2] | ||||
|                     func = lambda x: self.on_get_value(x, col) or u"" | ||||
|                     self.search = SearchFilter(func, text, inv) | ||||
|                 else: | ||||
|                     self.search = None | ||||
|                 self.rebuild_data = self._rebuild_search | ||||
|         else: | ||||
|             self.search = None | ||||
|             self.rebuild_data = self._rebuild_search | ||||
|              | ||||
|         self.reverse = (order == gtk.SORT_DESCENDING) | ||||
|         self.tooltip_column = tooltip_column | ||||
| @@ -96,7 +105,7 @@ class BaseModel(gtk.GenericTreeModel): | ||||
|  | ||||
|         return [ x[1] for x in sarray ] | ||||
|  | ||||
|     def rebuild_data(self): | ||||
|     def _rebuild_search(self): | ||||
|         if self.db.is_open(): | ||||
|             if self.search: | ||||
|                 self.datalist = [h for h in self.sort_keys()\ | ||||
| @@ -112,6 +121,23 @@ class BaseModel(gtk.GenericTreeModel): | ||||
|         else: | ||||
|             self.datalist = [] | ||||
|             self.indexlist = {} | ||||
|  | ||||
|     def _rebuild_filter(self): | ||||
|         if self.db.is_open(): | ||||
|             if self.search: | ||||
|                 self.datalist = self.search.apply(self.db, self.sort_keys()) | ||||
|             else: | ||||
|                 self.datalist = self.sort_keys() | ||||
|  | ||||
|             i = 0 | ||||
|             self.indexlist = {} | ||||
|             for key in self.datalist: | ||||
|                 if key not in self.skip: | ||||
|                     self.indexlist[key] = i | ||||
|                     i += 1 | ||||
|         else: | ||||
|             self.datalist = [] | ||||
|             self.indexlist = {} | ||||
|          | ||||
|     def add_row_by_handle(self,handle): | ||||
|         self.datalist = self.sort_keys() | ||||
|   | ||||
| @@ -89,21 +89,30 @@ class GenericFilter: | ||||
|     def get_rules(self): | ||||
|         return self.flist | ||||
|  | ||||
|     def get_cursor(db, self): | ||||
|         return db.get_person_cursor() | ||||
|  | ||||
|     def make_obj(self): | ||||
|         return RelLib.Person() | ||||
|  | ||||
|     def find_from_handle(self, db, handle): | ||||
|         return db.get_person_from_handle(handle) | ||||
|  | ||||
|     def check_func(self,db,id_list,task): | ||||
|         final_list = [] | ||||
|          | ||||
|         if id_list == None: | ||||
|             cursor = db.get_person_cursor() | ||||
|             cursor = self.get_cursor(db) | ||||
|             data = cursor.next() | ||||
|             while data: | ||||
|                 person = RelLib.Person() | ||||
|                 person = self.make_obj() | ||||
|                 person.unserialize(data[1]) | ||||
|                 if task(db,person): | ||||
|                     final_list.append(data[0]) | ||||
|                 data = cursor.next() | ||||
|         else: | ||||
|             for handle in id_list: | ||||
|                 person = db.get_person_from_handle(handle) | ||||
|                 person = self.find_from_handle(db, handle) | ||||
|                 if task(db,person): | ||||
|                     final_list.append(handle) | ||||
|         return final_list | ||||
| @@ -115,11 +124,11 @@ class GenericFilter: | ||||
|         final_list = [] | ||||
|         flist = self.flist | ||||
|         if id_list == None: | ||||
|             cursor = db.get_person_cursor() | ||||
|             cursor = self.get_cursor(db) | ||||
|             data = cursor.next() | ||||
|             p = RelLib.Person | ||||
|             while data: | ||||
|                 person = p(data[1]) | ||||
|                 person = self.make_obj() | ||||
|                 person.unserialize(data[1]) | ||||
|                 val = True | ||||
|                 for rule in flist: | ||||
|                     if not rule.apply(db,person): | ||||
| @@ -130,7 +139,7 @@ class GenericFilter: | ||||
|                 data = cursor.next() | ||||
|         else: | ||||
|             for handle in id_list: | ||||
|                 person = db.get_person_from_handle(handle) | ||||
|                 person = self.find_from_handle(db, handle) | ||||
|                 val = True | ||||
|                 for rule in flist: | ||||
|                     if not rule.apply(db,person): | ||||
| @@ -185,3 +194,19 @@ class GenericFilter: | ||||
|         for rule in self.flist: | ||||
|             rule.reset() | ||||
|         return res | ||||
|  | ||||
| class GenericFamilyFilter(GenericFilter): | ||||
|  | ||||
|     def __init__(self, source=None): | ||||
|         GenericFilter.__init__(self, source) | ||||
|  | ||||
|     def get_cursor(db, self): | ||||
|         return db.get_family_cursor() | ||||
|  | ||||
|     def make_obj(self): | ||||
|         return RelLib.Family() | ||||
|  | ||||
|     def find_from_handle(self, db, handle): | ||||
|         return db.get_family_from_handle(handle) | ||||
|  | ||||
|      | ||||
|   | ||||
| @@ -31,7 +31,7 @@ CustomFilters = None | ||||
|  | ||||
| from const import system_filters, custom_filters | ||||
| from _FilterList import FilterList | ||||
| from _GenericFilter import GenericFilter | ||||
| from _GenericFilter import GenericFilter, GenericFamilyFilter | ||||
| from _ParamFilter import ParamFilter | ||||
|  | ||||
| def reload_system_filters(): | ||||
| @@ -58,3 +58,4 @@ from _SearchBar import SearchBar | ||||
| from _SearchFilter import SearchFilter | ||||
| from _SidebarFilter import SidebarFilter | ||||
| from _PersonSidebarFilter import PersonSidebarFilter | ||||
| from _FamilySidebarFilter import FamilySidebarFilter | ||||
|   | ||||
| @@ -293,8 +293,8 @@ class PersonNavView(BookMarkView): | ||||
|                         tip=_("Go to the default person"), callback=self.home) | ||||
|         self.add_action('SetActive', gtk.STOCK_HOME, _("Set _Home Person"), | ||||
|                         callback=self.set_default_person) | ||||
|         self.add_action('FilterEdit', None, | ||||
|                         _('Filter Editor'), callback=self.filter_editor,) | ||||
|         self.add_action('FilterEdit', None, _('Person Filter Editor'), | ||||
|                         callback=self.filter_editor,) | ||||
|  | ||||
|         self.add_action_group(self.back_action) | ||||
|         self.add_action_group(self.fwd_action) | ||||
| @@ -441,11 +441,13 @@ class ListView(BookMarkView): | ||||
|     DEL_MSG = "" | ||||
|  | ||||
|     def __init__(self, title, dbstate, uistate, columns, handle_col, | ||||
|                  make_model, signal_map, get_bookmarks, bm_type, multiple=False): | ||||
|                  make_model, signal_map, get_bookmarks, bm_type, | ||||
|                  multiple=False, filter_class=None): | ||||
|  | ||||
|         BookMarkView.__init__(self, title, dbstate, uistate, | ||||
|                               get_bookmarks, bm_type) | ||||
|          | ||||
|  | ||||
|         self.filter_class = filter_class | ||||
|         self.renderer = gtk.CellRendererText() | ||||
|         self.renderer.set_property('ellipsize',pango.ELLIPSIZE_END) | ||||
|         self.sort_col = 0 | ||||
| @@ -455,8 +457,37 @@ class ListView(BookMarkView): | ||||
|         self.make_model = make_model | ||||
|         self.signal_map = signal_map | ||||
|         self.multiple_selection = multiple | ||||
|         self.generic_filter = None | ||||
|         dbstate.connect('database-changed',self.change_db) | ||||
|  | ||||
|     def build_filter_container(self, box, filter_class): | ||||
|         self.filter_sidebar = filter_class(self.filter_clicked) | ||||
|         self.filter_pane = self.filter_sidebar.get_widget() | ||||
|  | ||||
|         hpaned = gtk.HBox() | ||||
|         hpaned.pack_start(self.vbox, True, True) | ||||
|         hpaned.pack_end(self.filter_pane, False, False) | ||||
|         return hpaned | ||||
|  | ||||
|     def post(self): | ||||
|         if self.filter_class: | ||||
|             if Config.get(Config.FILTER): | ||||
|                 self.search_bar.hide() | ||||
|                 self.filter_pane.show() | ||||
|             else: | ||||
|                 self.search_bar.show() | ||||
|                 self.filter_pane.hide() | ||||
|  | ||||
|     def filter_clicked(self): | ||||
|         self.generic_filter = self.filter_sidebar.get_filter() | ||||
|         self.build_tree() | ||||
|  | ||||
|     def define_actions(self): | ||||
|         BookMarkView.define_actions(self) | ||||
|         self.add_toggle_action('Filter', None, _('_Show filter sidebar'), | ||||
|                                None, None, | ||||
|                                self.filter_toggle, Config.get(Config.FILTER)) | ||||
|  | ||||
|     def add_bookmark(self, obj): | ||||
|         mlist = [] | ||||
|         self.selection.selected_foreach(self.blist, mlist) | ||||
| @@ -524,7 +555,10 @@ class ListView(BookMarkView): | ||||
|  | ||||
|         self.setup_filter() | ||||
|  | ||||
|         return self.vbox | ||||
|         if self.filter_class: | ||||
|             return self.build_filter_container(self.vbox, self.filter_class) | ||||
|         else: | ||||
|             return self.vbox | ||||
|      | ||||
|     def row_changed(self,obj): | ||||
|         """Called with a row is changed. Check the selected objects from | ||||
| @@ -631,22 +665,34 @@ class ListView(BookMarkView): | ||||
|         if self.active: | ||||
|  | ||||
|             if Config.get(Config.FILTER): | ||||
|                 search = EMPTY_SEARCH | ||||
|                 filter_info = (True, self.generic_filter) | ||||
|             else: | ||||
|                 search = self.search_bar.get_value() | ||||
|                 filter_info = (False, self.search_bar.get_value()) | ||||
|  | ||||
|             self.model = self.make_model(self.dbstate.db,self.sort_col, | ||||
|                                          search=search) | ||||
|                                          search=filter_info) | ||||
|             self.list.set_model(self.model) | ||||
|             self.selection = self.list.get_selection() | ||||
|  | ||||
|             if const.use_tips and self.model.tooltip_column != None: | ||||
|                 self.tooltips = TreeTips.TreeTips(self.list, | ||||
|                                                   self.model.tooltip_column,True) | ||||
|                 self.tooltips = TreeTips.TreeTips( | ||||
|                     self.list, self.model.tooltip_column, True) | ||||
|             self.dirty = False | ||||
|         else: | ||||
|             self.dirty = True | ||||
|          | ||||
|     def filter_toggle(self,obj): | ||||
|         if obj.get_active(): | ||||
|             self.search_bar.hide() | ||||
|             self.filter_pane.show() | ||||
|             active = True | ||||
|         else: | ||||
|             self.search_bar.show() | ||||
|             self.filter_pane.hide() | ||||
|             active = False | ||||
|         Config.set(Config.FILTER, active) | ||||
|         self.build_tree() | ||||
|  | ||||
|     def change_db(self,db): | ||||
|         for sig in self.signal_map: | ||||
|             db.connect(sig, self.signal_map[sig]) | ||||
| @@ -730,9 +776,4 @@ class ListView(BookMarkView): | ||||
|     def double_click(self,obj,event): | ||||
|         return False | ||||
|  | ||||
|     def filter_toggle(self,obj): | ||||
|         if obj.get_active(): | ||||
|             self.search_bar.show() | ||||
|         else: | ||||
|             self.search_bar.hide() | ||||
|  | ||||
|   | ||||
		Reference in New Issue
	
	Block a user