def findChildren(self): # we need to start with all of our "people of interest" childrenNotYetProcessed = set(self._interest_set) childrenToInclude = set() # now we find all the children of our people of interest while len(childrenNotYetProcessed) > 0: handle = childrenNotYetProcessed.pop() if handle not in childrenToInclude: person = self._db.get_person_from_handle(handle) # if this is a private record, and we're not # including private records, then go back to the # top of the while loop to get the next person if person.private and not self._incprivate: continue # remember this person! childrenToInclude.add(handle) # if we have a limit on the number of people, and we've # reached that limit, then don't attempt to find any # more children if self._limitchildren and ( self._maxchildren < (len(childrenNotYetProcessed) + len(childrenToInclude))): # get back to the top of the while loop so we can finish # processing the people queued up in the "not yet processed" list continue # iterate through this person's families for family_handle in person.get_family_handle_list(): family = self._db.get_family_from_handle(family_handle) if (family.private and self._incprivate) or not family.private: # queue up any children from this person's family for childRef in family.get_child_ref_list(): child = self._db.get_person_from_handle( childRef.ref) if (child.private and self._incprivate) or not child.private: childrenNotYetProcessed.add(child.get_handle()) self._families.add(family_handle) # include the spouse from this person's family spouse_handle = ReportUtils.find_spouse(person, family) if spouse_handle: spouse = self._db.get_person_from_handle( spouse_handle) if (spouse.private and self._incprivate) or not spouse.private: childrenToInclude.add(spouse_handle) self._families.add(family_handle) # we now merge our temp set "childrenToInclude" into our master set self._people.update(childrenToInclude)
def __rec_fill_data(self, gen, person, pos): """ Recursively fill in the data """ totdesc = 0 nrfam = len(person.get_family_handle_list()) self.gen2people[gen][pos][6] = nrfam for family_handle in person.get_family_handle_list(): totdescfam = 0 family = self.dbstate.db.get_family_from_handle(family_handle) spouse_handle = find_spouse(person, family) if spouse_handle: spouse = self.dbstate.db.get_person_from_handle(spouse_handle) spname = name_displayer.display(spouse) else: spname = '' spouse = None if family_handle in self.famhandle2desc: #family occurs via father and via mother in the chart, only #first to show and count. famdup = True else: famdup = False # family, duplicate or not, start angle, slice size, # text, spouse pos in gen, nrchildren, userdata, parnter, status self.gen2fam[gen].append( [family, famdup, 0, 0, spname, pos, 0, [], spouse, NORMAL]) posfam = len(self.gen2fam[gen]) - 1 if not famdup: nrchild = len(family.get_child_ref_list()) self.gen2fam[gen][-1][6] = nrchild for child_ref in family.get_child_ref_list(): child = self.dbstate.db.get_person_from_handle( child_ref.ref) chname = name_displayer.display(child) if child_ref.ref in self.handle2desc: dup = True else: dup = False self.handle2desc[child_ref.ref] = 0 # person, duplicate or not, start angle, slice size, # text, parent pos in fam, nrfam, userdata, status self.gen2people[gen + 1].append( [child, dup, 0, 0, chname, posfam, 0, [], NORMAL]) totdescfam += 1 #add this person as descendant pospers = len(self.gen2people[gen + 1]) - 1 if not dup and not (self.generations == gen + 2): nrdesc = self.__rec_fill_data(gen + 1, child, pospers) self.handle2desc[child_ref.ref] += nrdesc totdescfam += nrdesc # add children of him as descendants self.famhandle2desc[family_handle] = totdescfam totdesc += totdescfam return totdesc
def recurse(self, level, person, curdepth): person_handle = person.get_handle() display_num = self.objPrint.print_person(level, person) if curdepth is None: ref_str = display_num else: ref_str = curdepth + " " + display_num if person_handle not in self.person_printed: self.person_printed[person_handle] = ref_str report_person_ref[person_handle] = (self.report_count, ref_str) for family_handle in person.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) spouse_handle = ReportUtils.find_spouse(person, family) if not self.showdups and spouse_handle in self.person_printed: # Just print a reference spouse = self.database.get_person_from_handle(spouse_handle) self.objPrint.print_reference( level, spouse, self.person_printed[person_handle]) else: if not self.showdups and self.report_count > 1: if spouse_handle in report_person_ref: self.objPrint.print_spouse(level, spouse_handle, family) childlist = family.get_child_ref_list()[:] if len(childlist) > 0: spouse = \ self.database.get_person_from_handle( spouse_handle) self.objPrint.print_report_reference( level + 1, person, spouse, report_person_ref[spouse_handle]) return self.objPrint.print_spouse(level, spouse_handle, family) if spouse_handle: spouse_num = _("%s sp." % (ref_str)) self.person_printed[spouse_handle] = spouse_num report_person_ref[spouse_handle] = \ (self.report_count, spouse_num) if level >= self.max_generations: continue childlist = family.get_child_ref_list()[:] for child_ref in childlist: child = self.database.get_person_from_handle(child_ref.ref) self.recurse(level + 1, child, ref_str)
def __rec_fill_data(self, gen, person, pos): """ Recursively fill in the data """ totdesc = 0 nrfam = len(person.get_family_handle_list()) self.gen2people[gen][pos][6] = nrfam for family_handle in person.get_family_handle_list(): totdescfam = 0 family = self.dbstate.db.get_family_from_handle(family_handle) spouse_handle = find_spouse(person, family) if spouse_handle: spouse = self.dbstate.db.get_person_from_handle(spouse_handle) spname = name_displayer.display(spouse) else: spname = '' spouse = None if family_handle in self.famhandle2desc: #family occurs via father and via mother in the chart, only #first to show and count. famdup = True else: famdup = False # family, duplicate or not, start angle, slice size, # text, spouse pos in gen, nrchildren, userdata, parnter, status self.gen2fam[gen].append([family, famdup, 0, 0, spname, pos, 0, [], spouse, NORMAL]) posfam = len(self.gen2fam[gen]) - 1 if not famdup: nrchild = len(family.get_child_ref_list()) self.gen2fam[gen][-1][6] = nrchild for child_ref in family.get_child_ref_list(): child = self.dbstate.db.get_person_from_handle(child_ref.ref) chname = name_displayer.display(child) if child_ref.ref in self.handle2desc: dup = True else: dup = False self.handle2desc[child_ref.ref] = 0 # person, duplicate or not, start angle, slice size, # text, parent pos in fam, nrfam, userdata, status self.gen2people[gen+1].append([child, dup, 0, 0, chname, posfam, 0, [], NORMAL]) totdescfam += 1 #add this person as descendant pospers = len(self.gen2people[gen+1]) - 1 if not dup and not(self.generations == gen+2): nrdesc = self.__rec_fill_data(gen+1, child, pospers) self.handle2desc[child_ref.ref] += nrdesc totdescfam += nrdesc # add children of him as descendants self.famhandle2desc[family_handle] = totdescfam totdesc += totdescfam return totdesc
def recurse(self, level, person, curdepth): person_handle = person.get_handle() display_num = self.objPrint.print_person(level, person) if curdepth is None: ref_str = display_num else: ref_str = curdepth + " " + display_num if person_handle not in self.person_printed: self.person_printed[person_handle] = ref_str report_person_ref[person_handle] = (self.report_count, ref_str) for family_handle in person.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) spouse_handle = ReportUtils.find_spouse(person, family) if not self.showdups and spouse_handle in self.person_printed: # Just print a reference spouse = self.database.get_person_from_handle(spouse_handle) self.objPrint.print_reference(level, spouse, self.person_printed[person_handle]) else: if not self.showdups and self.report_count > 1: if spouse_handle in report_person_ref: self.objPrint.print_spouse(level, spouse_handle, family) childlist = family.get_child_ref_list()[:] if len(childlist) > 0: spouse = \ self.database.get_person_from_handle( spouse_handle) self.objPrint.print_report_reference( level+1, person, spouse, report_person_ref[spouse_handle]) return self.objPrint.print_spouse(level, spouse_handle, family) if spouse_handle: spouse_num = _("%s sp." % (ref_str)) self.person_printed[spouse_handle] = spouse_num report_person_ref[spouse_handle] = \ (self.report_count, spouse_num) if level >= self.max_generations: continue childlist = family.get_child_ref_list()[:] for child_ref in childlist: child = self.database.get_person_from_handle(child_ref.ref) self.recurse(level+1, child, ref_str)
def display_family(self, family, active_person): """ Display the events for the given family. """ spouse_handle = find_spouse(active_person, family) if spouse_handle: spouse = self.dbstate.db.get_person_from_handle(spouse_handle) else: spouse = None if family: for event_ref in family.get_event_ref_list(): self.add_event_ref(event_ref, spouse)
def display_family(self, family, active_person): """ Display the children of given family. """ spouse_handle = find_spouse(active_person, family) if spouse_handle: spouse = self.dbstate.db.get_person_from_handle(spouse_handle) else: spouse = None for child_ref in family.get_child_ref_list(): child = self.dbstate.db.get_person_from_handle(child_ref.ref) self.add_child(child, spouse)
def __get_spouse(self, person, family): spouse_handle = utils.find_spouse(person, family) if not spouse_handle: if family.get_relationship() == FamilyRelType.MARRIED: return UnknownPerson else: return None spouse = self.dbstate.db.get_person_from_handle(spouse_handle) if self.__ignore_handle is not None and self.__ignore_handle in spouse.get_tag_list(): return None else: return spouse
def _rec_fill_data(self, gen, person, pos, maxgen): """ Recursively fill in the data """ totdesc = 0 marriage_handle_list = person.get_family_handle_list() self.gen2people[gen][pos][5] = len(marriage_handle_list) for family_handle in marriage_handle_list: totdescfam = 0 family = self.dbstate.db.get_family_from_handle(family_handle) spouse_handle = find_spouse(person, family) if spouse_handle: spouse = self.dbstate.db.get_person_from_handle(spouse_handle) else: spouse = None # family may occur via father and via mother in the chart, only # first to show and count. fam_duplicate = family_handle in self.famhandle2desc # family, duplicate or not, start angle, slice size, # spouse pos in gen, nrchildren, userdata, parnter, status self.gen2fam[gen].append( [family, fam_duplicate, 0, 0, pos, 0, [], spouse, NORMAL]) posfam = len(self.gen2fam[gen]) - 1 if not fam_duplicate and gen < maxgen - 1: nrchild = len(family.get_child_ref_list()) self.gen2fam[gen][posfam][5] = nrchild for child_ref in family.get_child_ref_list(): chld = self.dbstate.db.get_person_from_handle( child_ref.ref) child_dup = child_ref.ref in self.handle2desc if not child_dup: # mark this child as processed self.handle2desc[child_ref.ref] = 0 # person, duplicate or not, start angle, slice size, # parent pos in fam, nrfam, userdata, status self.gen2people[gen + 1].append( [chld, child_dup, 0, 0, posfam, 0, [], NORMAL]) totdescfam += 1 #add this person as descendant pospers = len(self.gen2people[gen + 1]) - 1 if not child_dup: nrdesc = self._rec_fill_data(gen + 1, chld, pospers, maxgen) self.handle2desc[child_ref.ref] += nrdesc # add children of him as descendants totdescfam += nrdesc if not fam_duplicate: self.famhandle2desc[family_handle] = totdescfam totdesc += totdescfam return totdesc
def __get_spouse(self, person, family): spouse_handle = utils.find_spouse(person, family) if not spouse_handle: if family.get_relationship() == FamilyRelType.MARRIED: return UnknownPerson else: return None spouse = self.dbstate.db.get_person_from_handle(spouse_handle) if self.__ignore_handle is not None and \ self.__ignore_handle in spouse.get_tag_list(): return None else: return spouse
def find_children(self): """ find any children """ # we need to start with all of our "people of interest" children_not_yet_processed = set(self._interest_set) children_to_include = set() # now we find all the children of our people of interest while len(children_not_yet_processed) > 0: handle = children_not_yet_processed.pop() if handle not in children_to_include: person = self._db.get_person_from_handle(handle) # remember this person! children_to_include.add(handle) # if we have a limit on the number of people, and we've # reached that limit, then don't attempt to find any # more children if (self._limitchildren and (self._maxchildren < len(children_not_yet_processed) + len(children_to_include) )): # get back to the top of the while loop # so we can finish processing the people # queued up in the "not yet processed" list continue # iterate through this person's families for family_handle in person.get_family_handle_list(): family = self._db.get_family_from_handle(family_handle) # queue up any children from this person's family for childref in family.get_child_ref_list(): child = self._db.get_person_from_handle(childref.ref) children_not_yet_processed.add(child.get_handle()) self._families.add(family_handle) # include the spouse from this person's family spouse_handle = utils.find_spouse(person, family) if spouse_handle: children_to_include.add(spouse_handle) self._families.add(family_handle) # we now merge our temp set "children_to_include" into our master set self._people.update(children_to_include)
def _recurse(self, handle): if not handle: return if handle in self._people: return person = self._db.get_person_from_handle(handle) # if this is a private record, and we're not # including private records, then go back to the # top of the while loop to get the next person if person.private and not self._incprivate: return # remember this person! self._people.add(handle) # if this person is an edge-case, we are done if handle in self._edgepeople: return ## find spouses and children ## by walking through all families were we are parent for family_handle in person.get_family_handle_list(): if not family_handle in self._families: self._families.add(family_handle) family = self._db.get_family_from_handle(family_handle) ## add spouse spouse_handle = ReportUtils.find_spouse(person, family) self._recurse(spouse_handle) ## add children for child_ref in family.get_child_ref_list(): self._recurse(child_ref.ref) ## find parents for family_handle in person.get_parent_family_handle_list(): if not family_handle in self._families: self._families.add(family_handle) family = self._db.get_family_from_handle(family_handle) ## add parents self._recurse(family.get_father_handle()) self._recurse(family.get_mother_handle()) ## add siblings for sibling_ref in family.get_child_ref_list(): self._recurse(sibling_ref.ref)
def write_marriage(self, person): """ Output marriage sentence. """ is_first = True for family_handle in person.get_family_handle_list(): family = self.db.get_family_from_handle(family_handle) spouse_handle = ReportUtils.find_spouse(person,family) spouse = self.db.get_person_from_handle(spouse_handle) spouse_mark = ReportUtils.get_person_mark(self.db, spouse) text = "" text = self.__narrator.get_married_string(family, is_first, self._name_display) if text: self.doc.write_text_citation(text, spouse_mark) is_first = False
def _rec_fill_data(self, gen, person, pos, maxgen): """ Recursively fill in the data """ totdesc = 0 marriage_handle_list = person.get_family_handle_list() self.gen2people[gen][pos][5] = len(marriage_handle_list) for family_handle in marriage_handle_list: totdescfam = 0 family = self.dbstate.db.get_family_from_handle(family_handle) spouse_handle = find_spouse(person, family) if spouse_handle: spouse = self.dbstate.db.get_person_from_handle(spouse_handle) else: spouse = None # family may occur via father and via mother in the chart, only # first to show and count. fam_duplicate = family_handle in self.famhandle2desc # family, duplicate or not, start angle, slice size, # spouse pos in gen, nrchildren, userdata, parnter, status self.gen2fam[gen].append([family, fam_duplicate, 0, 0, pos, 0, [], spouse, NORMAL]) posfam = len(self.gen2fam[gen]) - 1 if not fam_duplicate and gen < maxgen-1: nrchild = len(family.get_child_ref_list()) self.gen2fam[gen][posfam][5] = nrchild for child_ref in family.get_child_ref_list(): child = self.dbstate.db.get_person_from_handle(child_ref.ref) child_dup = child_ref.ref in self.handle2desc if not child_dup: self.handle2desc[child_ref.ref] = 0 # mark this child as processed # person, duplicate or not, start angle, slice size, # parent pos in fam, nrfam, userdata, status self.gen2people[gen+1].append([child, child_dup, 0, 0, posfam, 0, [], NORMAL]) totdescfam += 1 #add this person as descendant pospers = len(self.gen2people[gen+1]) - 1 if not child_dup: nrdesc = self._rec_fill_data(gen+1, child, pospers, maxgen) self.handle2desc[child_ref.ref] += nrdesc totdescfam += nrdesc # add children of him as descendants if not fam_duplicate: self.famhandle2desc[family_handle] = totdescfam totdesc += totdescfam return totdesc
def add_children(self, person): self._people.add(person.get_handle()) for family_handle in person.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) for childref in family.get_child_ref_list(): child = self.database.get_person_from_handle(childref.ref) if (self._withchildren or child.get_gramps_id() in self._gidlist): self.add_children(child) self._families.add(family_handle) spouse_handle = utils.find_spouse(person, family) if spouse_handle: spouse = self.database.get_person_from_handle(spouse_handle) if self._withspouses or spouse.get_gramps_id( ) in self._gidlist: self._people.add(spouse_handle) self._families.add(family_handle)
def write_marriage(self, person): """ Output marriage sentence. """ is_first = True for family_handle in person.get_family_handle_list(): family = self._db.get_family_from_handle(family_handle) spouse_handle = utils.find_spouse(person, family) if spouse_handle: spouse = self._db.get_person_from_handle(spouse_handle) spouse_mark = utils.get_person_mark(self._db, spouse) else: spouse_mark = None text = self.__narrator.get_married_string(family, is_first, self._nd) if text: self.doc.write_text_citation(text, spouse_mark) if self.want_ids: self.doc.write_text(' (%s)' % family.get_gramps_id()) is_first = False
def recurse(self, level, person, curdepth): """ recurse """ person_handle = person.get_handle() display_num = self.obj_print.print_person(level, person) if curdepth is None: ref_str = display_num else: ref_str = curdepth + " " + display_num if person_handle not in self.person_printed: self.person_printed[person_handle] = ref_str for family_handle in person.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) spouse_handle = utils.find_spouse(person, family) if not self.showdups and spouse_handle in self.person_printed: # Just print a reference spouse = self.database.get_person_from_handle(spouse_handle) self.obj_print.print_reference( level, spouse, self.person_printed[spouse_handle]) else: self.obj_print.print_spouse(level, spouse_handle, family) if spouse_handle: spouse_num = self._("%s sp.") % ref_str self.person_printed[spouse_handle] = spouse_num if level >= self.max_generations: continue childlist = family.get_child_ref_list()[:] for child_ref in childlist: child = self.database.get_person_from_handle(child_ref.ref) self.recurse(level + 1, child, ref_str)
def recurse(self, level, person, curdepth): """ recurse """ person_handle = person.get_handle() display_num = self.obj_print.print_person(level, person) if curdepth is None: ref_str = display_num else: ref_str = curdepth + " " + display_num if person_handle not in self.person_printed: self.person_printed[person_handle] = ref_str for family_handle in person.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) spouse_handle = utils.find_spouse(person, family) if not self.showdups and spouse_handle in self.person_printed: # Just print a reference spouse = self.database.get_person_from_handle(spouse_handle) self.obj_print.print_reference( level, spouse, self.person_printed[spouse_handle]) else: self.obj_print.print_spouse(level, spouse_handle, family) if spouse_handle: spouse_num = self._("%s sp.") % ref_str self.person_printed[spouse_handle] = spouse_num if level >= self.max_generations: continue childlist = family.get_child_ref_list()[:] for child_ref in childlist: child = self.database.get_person_from_handle(child_ref.ref) self.recurse(level+1, child, ref_str)
def findParents(self): # we need to start with all of our "people of interest" ancestorsNotYetProcessed = set(self._interest_set) # now we find all the immediate ancestors of our people of interest while ancestorsNotYetProcessed: handle = ancestorsNotYetProcessed.pop() # One of 2 things can happen here: # 1) we've already know about this person and he/she is already # in our list # 2) this is someone new, and we need to remember him/her # # In the first case, there isn't anything else to do, so we simply # go back to the top and pop the next person off the list. # # In the second case, we need to add this person to our list, and # then go through all of the parents this person has to find more # people of interest. if handle not in self._people: person = self.database.get_person_from_handle(handle) # if this is a private record, and we're not # including private records, then go back to the # top of the while loop to get the next person if person.private and not self._incprivate: continue # remember this person! self._people.add(handle) # see if a family exists between this person and someone else # we have on our list of people we're going to output -- if # there is a family, then remember it for when it comes time # to link spouses together for family_handle in person.get_family_handle_list(): family = self.database.get_family_from_handle( family_handle) spouse_handle = ReportUtils.find_spouse(person, family) if spouse_handle: if (spouse_handle in self._people or spouse_handle in ancestorsNotYetProcessed): self._families.add(family_handle) # if we have a limit on the number of people, and we've # reached that limit, then don't attempt to find any # more ancestors if self._limitparents and ( self._maxparents < len(ancestorsNotYetProcessed) + len(self._people)): # get back to the top of the while loop so we can finish # processing the people queued up in the "not yet # processed" list continue # queue the parents of the person we're processing for family_handle in person.get_parent_family_handle_list(): family = self.database.get_family_from_handle( family_handle) if not family.private or self._incprivate: try: father = self.database.get_person_from_handle( family.get_father_handle()) except AttributeError: father = None try: mother = self.database.get_person_from_handle( family.get_mother_handle()) except AttributeError: mother = None if father: if not father.private or self._incprivate: ancestorsNotYetProcessed.add( family.get_father_handle()) self._families.add(family_handle) if mother: if not mother.private or self._incprivate: ancestorsNotYetProcessed.add( family.get_mother_handle()) self._families.add(family_handle) for sib in family.get_child_ref_list(): sibling = self.database.get_person_from_handle( sib.ref) if sibling and (not sibling.private or self._incprivate): ancestorsNotYetProcessed.add(sib.ref) self._families.add(family_handle)
def display(self, tobj, person): """Fill text buffer tobj with detailed info on person person.""" normal = tobj.create_tag() normal.set_property('indent', 10) normal.set_property('pixels-above-lines', 1) normal.set_property('pixels-below-lines', 1) indent = tobj.create_tag() indent.set_property('indent', 30) indent.set_property('pixels-above-lines', 1) indent.set_property('pixels-below-lines', 1) title = tobj.create_tag() title.set_property('weight', Pango.Weight.BOLD) title.set_property('scale', 1.2) self.add(tobj, title, name_displayer.display(person)) self.add(tobj, normal, "%s:\t%s" % (_('ID'), person.get_gramps_id())) self.add(tobj, normal, "%s:\t%s" % (_('Gender'), sex[person.get_gender()])) bref = person.get_birth_ref() if bref: self.add(tobj, normal, "%s:\t%s" % (_('Birth'), self.get_event_info(bref.ref))) dref = person.get_death_ref() if dref: self.add(tobj, normal, "%s:\t%s" % (_('Death'), self.get_event_info(dref.ref))) nlist = person.get_alternate_names() if len(nlist) > 0: self.add(tobj, title, _("Alternate Names")) for name in nlist: self.add(tobj, normal, name_displayer.display_name(name)) elist = person.get_event_ref_list() if len(elist) > 0: self.add(tobj, title, _("Events")) for event_ref in person.get_event_ref_list(): event_handle = event_ref.ref role = event_ref.get_role() name = str( self.database.get_event_from_handle( event_handle).get_type()) if role.is_primary(): self.add( tobj, normal, "%s:\t%s" % (name, self.get_event_info(event_handle))) else: self.add( tobj, normal, "%s (%s):\t%s" % (name, role, self.get_event_info(event_handle))) plist = person.get_parent_family_handle_list() if len(plist) > 0: self.add(tobj, title, _("Parents")) for fid in person.get_parent_family_handle_list(): (fname, mname, gid) = self.get_parent_info(fid) self.add(tobj, normal, "%s:\t%s" % (_('Family ID'), gid)) if fname: self.add(tobj, indent, "%s:\t%s" % (_('Father'), fname)) if mname: self.add(tobj, indent, "%s:\t%s" % (_('Mother'), mname)) else: self.add(tobj, normal, _("No parents found")) self.add(tobj, title, _("Spouses")) slist = person.get_family_handle_list() if len(slist) > 0: for fid in slist: (fname, mname, pid) = self.get_parent_info(fid) family = self.database.get_family_from_handle(fid) self.add(tobj, normal, "%s:\t%s" % (_('Family ID'), pid)) spouse_id = ReportUtils.find_spouse(person, family) if spouse_id: spouse = self.database.get_person_from_handle(spouse_id) self.add(tobj, indent, "%s:\t%s" % (_('Spouse'), name_of(spouse))) relstr = str(family.get_relationship()) self.add(tobj, indent, "%s:\t%s" % (_('Type'), relstr)) event = ReportUtils.find_marriage(self.database, family) if event: self.add( tobj, indent, "%s:\t%s" % (_('Marriage'), self.get_event_info(event.get_handle()))) for child_ref in family.get_child_ref_list(): child = self.database.get_person_from_handle(child_ref.ref) self.add(tobj, indent, "%s:\t%s" % (_('Child'), name_of(child))) else: self.add(tobj, normal, _("No spouses or children found")) alist = person.get_address_list() if len(alist) > 0: self.add(tobj, title, _("Addresses")) for addr in alist: location = ", ".join([ addr.get_street(), addr.get_city(), addr.get_state(), addr.get_country(), addr.get_postal_code(), addr.get_phone() ]) self.add(tobj, normal, location.strip())
def display(self, tobj, person): """Fill text buffer tobj with detailed info on person person.""" normal = tobj.create_tag() normal.set_property('indent', 10) normal.set_property('pixels-above-lines', 1) normal.set_property('pixels-below-lines', 1) indent = tobj.create_tag() indent.set_property('indent', 30) indent.set_property('pixels-above-lines', 1) indent.set_property('pixels-below-lines', 1) title = tobj.create_tag() title.set_property('weight', Pango.Weight.BOLD) title.set_property('scale', 1.2) self.add(tobj, title, name_displayer.display(person)) self.add(tobj, normal, KEYVAL % { 'key': _('ID'), 'value': person.get_gramps_id() }) self.add( tobj, normal, KEYVAL % { 'key': _('Gender'), 'value': sex[person.get_gender()] }) bref = person.get_birth_ref() if bref: self.add( tobj, normal, KEYVAL % { 'key': _('Birth'), 'value': self.get_event_info(bref.ref) }) dref = person.get_death_ref() if dref: self.add( tobj, normal, KEYVAL % { 'key': _('Death'), 'value': self.get_event_info(dref.ref) }) nlist = person.get_alternate_names() if len(nlist) > 0: self.add(tobj, title, _("Alternate Names")) for name in nlist: self.add(tobj, normal, name_displayer.display_name(name)) elist = person.get_event_ref_list() if len(elist) > 0: self.add(tobj, title, _("Events")) for event_ref in person.get_event_ref_list(): event_handle = event_ref.ref role = event_ref.get_role() name = str( self.database.get_event_from_handle( event_handle).get_type()) ev_info = self.get_event_info(event_handle) if role.is_primary(): self.add(tobj, normal, KEYVAL % { 'key': name, 'value': ev_info }) else: self.add( tobj, normal, # translators: needed for French "%(name)s (%(role)s):\t%(info)s" % { 'name': name, 'role': role, 'info': ev_info }) plist = person.get_parent_family_handle_list() if len(plist) > 0: self.add(tobj, title, _("Parents")) for fid in person.get_parent_family_handle_list(): (fname, mname, gid) = self.get_parent_info(fid) self.add(tobj, normal, KEYVAL % { 'key': _('Family ID'), 'value': gid }) if fname: self.add(tobj, indent, KEYVAL % { 'key': _('Father'), 'value': fname }) if mname: self.add(tobj, indent, KEYVAL % { 'key': _('Mother'), 'value': mname }) else: self.add(tobj, normal, _("No parents found")) self.add(tobj, title, _("Spouses")) slist = person.get_family_handle_list() if len(slist) > 0: for fid in slist: (fname, mname, pid) = self.get_parent_info(fid) family = self.database.get_family_from_handle(fid) self.add(tobj, normal, KEYVAL % { 'key': _('Family ID'), 'value': pid }) spouse_id = utils.find_spouse(person, family) if spouse_id: spouse = self.database.get_person_from_handle(spouse_id) self.add( tobj, indent, KEYVAL % { 'key': _('Spouse'), 'value': name_of(spouse) }) relstr = str(family.get_relationship()) self.add(tobj, indent, KEYVAL % { 'key': _('Type'), 'value': relstr }) event = utils.find_marriage(self.database, family) if event: m_info = self.get_event_info(event.get_handle()) self.add(tobj, indent, KEYVAL % { 'key': _('Marriage'), 'value': m_info }) for child_ref in family.get_child_ref_list(): child = self.database.get_person_from_handle(child_ref.ref) self.add( tobj, indent, KEYVAL % { 'key': _('Child'), 'value': name_of(child) }) else: self.add(tobj, normal, _("No spouses or children found")) alist = person.get_address_list() if len(alist) > 0: self.add(tobj, title, _("Addresses")) for addr in alist: # TODO for Arabic, should the next line's comma be translated? location = ", ".join([ addr.get_street(), addr.get_city(), addr.get_state(), addr.get_country(), addr.get_postal_code(), addr.get_phone() ]) self.add(tobj, normal, location.strip())
def __calc_person_key(self, person): """ The person key is a unique identifier that is built from the relationship to the default person. It consists of the "Ahnentafel" number of the common ancestor of the person with the default person, and then a letter representing the child number for each generation from the common ancestor to the person. If more than one common ancestor exists, the common ancestor with the lowest "Ahnentafel" number has precedence. For example, the second child of the third child of the father of the mother of the central person gets the person key "6cb". """ relationship = get_relationship_calculator() default_person = self.database.get_default_person() # No home person set. if default_person is None: return (-1, 0, "") # First try direct relationship. spousestring = "" info, msg = relationship.get_relationship_distance_new(self.database, default_person, person, all_dist=True) info = relationship.collapse_relations(info)[0] (rank, ancestor_handle, default_rel, default_fam, person_rel, person_fam) = info # Then try relationship to any spouse. if rank == -1: index = 0 for family_handle in default_person.get_family_handle_list(): index += 1 family = self.database.get_family_from_handle(family_handle) spouse_handle = utils.find_spouse(default_person, family) spouse = self.database.get_person_from_handle(spouse_handle) info, msg = relationship.get_relationship_distance_new(self.database, spouse, person, all_dist=True) info = relationship.collapse_relations(info)[0] (rank, ancestor_handle, default_rel, default_fam, person_rel, person_fam) = info if rank != -1: spousestring = utils.roman(index) break # If no relationship found at all, exit here. if rank == -1: return (rank, 0, "") # Calculate Ahnentafel number of common ancestor. ahnentafel = 1 for rel in default_rel: ahnentafel *= 2 if rel in (relationship.REL_MOTHER, relationship.REL_MOTHER_NOTBIRTH): ahnentafel += 1 # Find out child letters. child = person childletters = "" for rel in person_rel: family_handle = child.get_main_parents_family_handle() family = self.database.get_family_from_handle(family_handle) if rel in (relationship.REL_MOTHER, relationship.REL_MOTHER_NOTBIRTH): parent_handle = family.get_mother_handle() else: parent_handle = family.get_father_handle() parent = self.database.get_person_from_handle(parent_handle) # Count *all* children from this parent childletter = "?" index = 0 for family_handle in parent.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) for child_ref in family.get_child_ref_list(): if child_ref.ref == child.get_handle(): childletter = string.ascii_lowercase[index] break index += 1 else: continue break childletters = childletter + childletters child = parent return (rank, ahnentafel, "%s%s%s" % (spousestring, ahnentafel, childletters))
def __process_person(self, person, rank, ahnentafel, person_key): """ Recursively build the Family Sheet for this person and all children with spouses. @param person: Person object for the key person of the Family Sheet. @param rank: Numerical distance between the central person in the database and the person in the parameter (the number of births needed to connect them). @param ahnentafel: "Ahnentafel" number of the common ancestor of the central person in the database and the person in the parameter, seen from the side of the central person in the database. @param person_key: Family Sheet key to be printed on the top right of the corner. """ # List of (person, rank, ahnentafel, person_key) tuples for persons to # process recursively after this one. more_sheets = [] # Numbering of spouses (integer, but printed in roman numbers). spouse_index = 0 # Numbering of children (integer, but printed as lowercase letters). child_index = 0 # Source references to print as footnotes. self.__citation_index = 0 self.__citations = [] # Notes to print as footnotes. self.__note_index = 0 self.__notes = [] # --- Now let the party begin! --- self.doc.start_paragraph("FSR-Key") self.doc.write_text(person_key) self.doc.end_paragraph() self.doc.start_table(None, "FSR-Table") # Main person self.doc.start_row() self.doc.start_cell("FSR-HeadCell", 3) self.__dump_person(person, False, None) self.doc.end_cell() self.doc.end_row() # Spouses for family_handle in person.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) spouse_index += 1 spouse_handle = utils.find_spouse(person, family) spouse = self.database.get_person_from_handle(spouse_handle) # Determine relationship between the center person and the spouse. # If the spouse has a closer blood relationship than the current # person, we refer to the Family Sheet of the spouse instead of # printing the child list, because all children are more closely # related to the center person via the spouse than via the current # person. The same happens if the relationship is on the same # level, but the relationship via the spouse goes via a common # ancestor with a lower Ahnentafel numbering (i.e. a relationship # stronger father-sided). In these cases, refer_spouse will be set # to True. (spouse_rank, spouse_at, spouse_key) = self.__calc_person_key(spouse) if self.recurse != RelationsOptions.RECURSE_ALL: refer_spouse = spouse_rank != -1 and ( spouse_rank < rank or (spouse_rank == rank and spouse_at < ahnentafel) ) else: refer_spouse = False self.doc.start_row() self.doc.start_cell("FSR-NumberCell", 1) self.doc.start_paragraph("FSR-Number") self.doc.write_text(utils.roman(spouse_index)) self.doc.end_paragraph() self.doc.end_cell() self.doc.start_cell("FSR-DataCell", 2) self.__dump_family(family, spouse) if refer_spouse: self.doc.start_paragraph("FSR-Normal") self.doc.write_text(_("\u2192 %s") % spouse_key) self.doc.end_paragraph() self.doc.end_cell() self.doc.end_row() if refer_spouse: # Spouse with closer relationship than current person? Don't # print children on this Family Sheet (but count them for the # numbering). child_index += len(family.get_child_ref_list()) continue # Children for child_ref in family.get_child_ref_list(): child = self.database.get_person_from_handle(child_ref.ref) child_letter = string.ascii_lowercase[child_index] self.doc.start_row() self.doc.start_cell("FSR-EmptyCell", 1) self.doc.end_cell() self.doc.start_cell("FSR-NumberCell", 1) self.doc.start_paragraph("FSR-Number") self.doc.write_text(child_letter) self.doc.end_paragraph() self.doc.end_cell() self.doc.start_cell("FSR-DataCell", 1) has_spouses = child.get_family_handle_list() != [] self.__dump_person(child, has_spouses, child_ref) if has_spouses: # We have to recalculate the key for this person, it could # be closer related if it is a direct ancestor of the # central person or one of its spouses. (child_rank, child_at, child_key) = self.__calc_person_key(child) self.doc.start_paragraph("FSR-Normal") self.doc.write_text(_("\u2192 %s") % child_key) self.doc.end_paragraph() # We recursively print this child *only* if its # relationship with the central person is closest via the # current person. This way, we avoid that a person is # printed recursively from more than one of its ancestors. if child_key == person_key + child_letter or self.recurse == RelationsOptions.RECURSE_ALL: more_sheets.append((child, child_rank, child_at, child_key)) self.doc.end_cell() self.doc.end_row() child_index += 1 self.doc.start_row() self.doc.start_cell("FSR-FootCell", 3) self.doc.end_cell() self.doc.end_row() self.doc.end_table() self.__dump_sources() self.__dump_notes() # Now print the sheets for the children. if self.recurse != RelationsOptions.RECURSE_NONE: for (child, child_rank, child_at, child_key) in more_sheets: self.doc.page_break() self.__process_person(child, child_rank, child_at, child_key)
def display(self, tobj, person): """Fill text buffer tobj with detailed info on person person.""" normal = tobj.create_tag() normal.set_property('indent', 10) normal.set_property('pixels-above-lines', 1) normal.set_property('pixels-below-lines', 1) indent = tobj.create_tag() indent.set_property('indent', 30) indent.set_property('pixels-above-lines', 1) indent.set_property('pixels-below-lines', 1) title = tobj.create_tag() title.set_property('weight', Pango.Weight.BOLD) title.set_property('scale', 1.2) self.add(tobj, title, name_displayer.display(person)) self.add(tobj, normal, KEYVAL % {'key': _('ID'), 'value': person.get_gramps_id()}) self.add(tobj, normal, KEYVAL % {'key': _('Gender'), 'value': sex[person.get_gender()]}) bref = person.get_birth_ref() if bref: self.add(tobj, normal, KEYVAL % {'key': _('Birth'), 'value': self.get_event_info(bref.ref)}) dref = person.get_death_ref() if dref: self.add(tobj, normal, KEYVAL % {'key': _('Death'), 'value': self.get_event_info(dref.ref)}) nlist = person.get_alternate_names() if len(nlist) > 0: self.add(tobj, title, _("Alternate Names")) for name in nlist: self.add(tobj, normal, name_displayer.display_name(name)) elist = person.get_event_ref_list() if len(elist) > 0: self.add(tobj, title, _("Events")) for event_ref in person.get_event_ref_list(): event_handle = event_ref.ref role = event_ref.get_role() name = str( self.database.get_event_from_handle(event_handle).get_type()) ev_info = self.get_event_info(event_handle) if role.is_primary(): self.add(tobj, normal, KEYVAL % {'key': name, 'value': ev_info}) else: self.add(tobj, normal, # translators: needed for French "%(name)s (%(role)s):\t%(info)s" % {'name': name, 'role': role, 'info': ev_info}) plist = person.get_parent_family_handle_list() if len(plist) > 0: self.add(tobj, title, _("Parents")) for fid in person.get_parent_family_handle_list(): (fname, mname, gid) = self.get_parent_info(fid) self.add(tobj, normal, KEYVAL % {'key': _('Family ID'), 'value': gid}) if fname: self.add(tobj, indent, KEYVAL % {'key': _('Father'), 'value': fname}) if mname: self.add(tobj, indent, KEYVAL % {'key': _('Mother'), 'value': mname}) else: self.add(tobj, normal, _("No parents found")) self.add(tobj, title, _("Spouses")) slist = person.get_family_handle_list() if len(slist) > 0: for fid in slist: (fname, mname, pid) = self.get_parent_info(fid) family = self.database.get_family_from_handle(fid) self.add(tobj, normal, KEYVAL % {'key': _('Family ID'), 'value': pid}) spouse_id = utils.find_spouse(person, family) if spouse_id: spouse = self.database.get_person_from_handle(spouse_id) self.add(tobj, indent, KEYVAL % {'key': _('Spouse'), 'value': name_of(spouse)}) relstr = str(family.get_relationship()) self.add(tobj, indent, KEYVAL % {'key': _('Type'), 'value': relstr}) event = utils.find_marriage(self.database, family) if event: m_info = self.get_event_info(event.get_handle()) self.add(tobj, indent, KEYVAL % {'key': _('Marriage'), 'value': m_info}) for child_ref in family.get_child_ref_list(): child = self.database.get_person_from_handle(child_ref.ref) self.add(tobj, indent, KEYVAL % {'key': _('Child'), 'value': name_of(child)}) else: self.add(tobj, normal, _("No spouses or children found")) alist = person.get_address_list() if len(alist) > 0: self.add(tobj, title, _("Addresses")) for addr in alist: location = ", ".join([addr.get_street(), addr.get_city(), addr.get_state(), addr.get_country(), addr.get_postal_code(), addr.get_phone()]) self.add(tobj, normal, location.strip())
def __init__(self, report, title, surname, ppl_handle_list): """ @param: report -- The instance of the main report class for this report @param: title -- Is the title of the web page @param: surname -- The surname to use @param: ppl_handle_list -- The list of people for whom we need to create a page. """ BasePage.__init__(self, report, title) # module variables showbirth = report.options['showbirth'] showdeath = report.options['showdeath'] showpartner = report.options['showpartner'] showparents = report.options['showparents'] if surname == '': surname = self._("<absent>") output_file, sio = self.report.create_file(name_to_md5(surname), "srn") self.uplink = True (surnamepage, head, body) = self.write_header("%s - %s" % (self._("Surname"), surname)) ldatec = 0 # begin SurnameDetail division with Html("div", class_="content", id="SurnameDetail") as surnamedetail: body += surnamedetail # section title surnamedetail += Html("h3", html_escape(surname), inline=True) # feature request 2356: avoid genitive form msg = self._("This page contains an index of all the individuals " "in the database with the surname of %s. " "Selecting the person’s name " "will take you to that person’s " "individual page.") % html_escape(surname) surnamedetail += Html("p", msg, id="description") # begin surname table and thead with Html("table", class_="infolist primobjlist surname") as table: surnamedetail += table thead = Html("thead") table += thead trow = Html("tr") thead += trow # Name Column trow += Html("th", self._("Given Name"), class_="ColumnName", inline=True) if showbirth: trow += Html("th", self._("Birth"), class_="ColumnDate", inline=True) if showdeath: trow += Html("th", self._("Death"), class_="ColumnDate", inline=True) if showpartner: trow += Html("th", self._("Partner"), class_="ColumnPartner", inline=True) if showparents: trow += Html("th", self._("Parents"), class_="ColumnParents", inline=True) # begin table body tbody = Html("tbody") table += tbody for person_handle in sorted(ppl_handle_list, key=self.sort_on_name_and_grampsid): person = self.r_db.get_person_from_handle(person_handle) if person.get_change_time() > ldatec: ldatec = person.get_change_time() trow = Html("tr") tbody += trow # firstname column link = self.new_person_link(person_handle, uplink=True, person=person, name_style=_NAME_STYLE_FIRST) trow += Html("td", link, class_="ColumnName") # birth column if showbirth: tcell = Html("td", class_="ColumnBirth", inline=True) trow += tcell birth_date = _find_birth_date(self.r_db, person) if birth_date is not None: if birth_date.fallback: tcell += Html('em', self.rlocale.get_date(birth_date), inline=True) else: tcell += self.rlocale.get_date(birth_date) else: tcell += " " # death column if showdeath: tcell = Html("td", class_="ColumnDeath", inline=True) trow += tcell death_date = _find_death_date(self.r_db, person) if death_date is not None: if death_date.fallback: tcell += Html('em', self.rlocale.get_date(death_date), inline=True) else: tcell += self.rlocale.get_date(death_date) else: tcell += " " # partner column if showpartner: tcell = Html("td", class_="ColumnPartner") trow += tcell family_list = person.get_family_handle_list() if family_list: fam_count = 0 for family_handle in family_list: fam_count += 1 family = self.r_db.get_family_from_handle( family_handle) partner_handle = utils.find_spouse( person, family) if partner_handle: link = self.new_person_link(partner_handle, uplink=True) if fam_count < len(family_list): if isinstance(link, Html): link.inside += "," else: link += ',' tcell += link else: tcell += " " # parents column if showparents: parent_hdl_list = person.get_parent_family_handle_list() if parent_hdl_list: parent_hdl = parent_hdl_list[0] fam = self.r_db.get_family_from_handle(parent_hdl) f_id = fam.get_father_handle() m_id = fam.get_mother_handle() mother = father = None if f_id: father = self.r_db.get_person_from_handle(f_id) if father: father_name = self.get_name(father) if m_id: mother = self.r_db.get_person_from_handle(m_id) if mother: mother_name = self.get_name(mother) if mother and father: tcell = Html("span", father_name, class_="father fatherNmother") tcell += Html("span", mother_name, class_="mother") elif mother: tcell = Html("span", mother_name, class_="mother", inline=True) elif father: tcell = Html("span", father_name, class_="father", inline=True) samerow = False else: tcell = " " # pylint: disable=R0204 samerow = True trow += Html("td", tcell, class_="ColumnParents", inline=samerow) # add clearline for proper styling # add footer section footer = self.write_footer(ldatec) body += (FULLCLEAR, footer) # send page out for processing # and close the file self.xhtml_writer(surnamepage, output_file, sio, ldatec)
def find_parents(self): """ find the parents """ # we need to start with all of our "people of interest" ancestors_not_yet_processed = set(self._interest_set) # now we find all the immediate ancestors of our people of interest while ancestors_not_yet_processed: handle = ancestors_not_yet_processed.pop() # One of 2 things can happen here: # 1) we already know about this person and he/she is already # in our list # 2) this is someone new, and we need to remember him/her # # In the first case, there isn't anything else to do, so we simply # go back to the top and pop the next person off the list. # # In the second case, we need to add this person to our list, and # then go through all of the parents this person has to find more # people of interest. if handle not in self._people: person = self._db.get_person_from_handle(handle) # remember this person! self._people.add(handle) # see if a family exists between this person and someone else # we have on our list of people we're going to output -- if # there is a family, then remember it for when it comes time # to link spouses together for family_handle in person.get_family_handle_list(): family = self._db.get_family_from_handle(family_handle) if not family: continue spouse_handle = utils.find_spouse(person, family) if spouse_handle: if (spouse_handle in self._people or spouse_handle in ancestors_not_yet_processed): self._families.add(family_handle) # if we have a limit on the number of people, and we've # reached that limit, then don't attempt to find any # more ancestors if (self._limitparents and (self._maxparents < len(ancestors_not_yet_processed) + len(self._people))): # get back to the top of the while loop so we can finish # processing the people queued up in the "not yet # processed" list continue # queue the parents of the person we're processing for family_handle in person.get_parent_family_handle_list(): family = self._db.get_family_from_handle(family_handle) father_handle = family.get_father_handle() if father_handle: father = self._db.get_person_from_handle(father_handle) if father: ancestors_not_yet_processed.add(father_handle) self._families.add(family_handle) mother_handle = family.get_mother_handle() if mother_handle: mother = self._db.get_person_from_handle(mother_handle) if mother: ancestors_not_yet_processed.add(mother_handle) self._families.add(family_handle)
def recurse(self, person_handle, g_level, s_level): """traverse the descendants recursively until either the end of a line is found, or until we reach the maximum number of generations or we reach the max number of spouses that we want to deal with""" if not person_handle: return if g_level > self.max_generations: return # one generation too many if s_level > 0 and s_level == self.max_spouses: return #if person_handle in self.people_seen: return person = self.database.get_person_from_handle(person_handle) family_handles = person.get_family_handle_list() if s_level == 0: val = family_handles[0] if family_handles else None self.__this_slevel = s_level self._add_person((g_level, s_level), person_handle, val) if self.__bold_now == 1: self.__bold_now = 0 if not self.can_recurse(): self.continue_recursion() return if s_level == 1: tmp_bold = self.__bold_now self.__bold_now = 0 for family_handle in family_handles: #Marriage box if the option is there. self._add_marriage((g_level, s_level + 1), person_handle, family_handle) if not self.can_recurse(): self.continue_recursion() return family = self.database.get_family_from_handle(family_handle) spouse_handle = ReportUtils.find_spouse(person, family) if self.max_spouses > s_level: self.__this_slevel = s_level + 1 self._add_person((g_level, s_level + 1), spouse_handle, family_handle) if not self.can_recurse: self.continue_recursion() return mykids = [kid.ref for kid in family.get_child_ref_list()] if self.can_recurse(): for child_ref in mykids: self.recurse(child_ref, g_level + 1, 0) else: self.continue_recursion() if self.max_spouses > s_level: #spouse_handle = ReportUtils.find_spouse(person,family) self.recurse(spouse_handle, g_level, s_level + 1) if s_level == 1: self.__bold_now = tmp_bold
def __init__(self, report, title, surname, ppl_handle_list): """ @param: report -- The instance of the main report class for this report @param: title -- Is the title of the web page @param: surname -- The surname to use @param: ppl_handle_list -- The list of people for whom we need to create a page. """ BasePage.__init__(self, report, title) # module variables showbirth = report.options['showbirth'] showdeath = report.options['showdeath'] showpartner = report.options['showpartner'] showparents = report.options['showparents'] if surname == '': surname = self._("<absent>") output_file, sio = self.report.create_file(name_to_md5(surname), "srn") self.uplink = True (surnamepage, head, body) = self.write_header("%s - %s" % (self._("Surname"), surname)) ldatec = 0 # begin SurnameDetail division with Html("div", class_="content", id="SurnameDetail") as surnamedetail: body += surnamedetail # section title # In case the user choose a format name like "*SURNAME*" # We must display this field in upper case. So we use # the english format of format_name to find if this is # the case. name_format = self.report.options['name_format'] nme_format = _nd.name_formats[name_format][1] if "SURNAME" in nme_format: surnamed = surname.upper() else: surnamed = surname surnamedetail += Html("h3", html_escape(surnamed), inline=True) # feature request 2356: avoid genitive form msg = self._("This page contains an index of all the individuals " "in the database with the surname of %s. " "Selecting the person’s name " "will take you to that person’s " "individual page.") % html_escape(surname) surnamedetail += Html("p", msg, id="description") # begin surname table and thead with Html("table", class_="infolist primobjlist surname") as table: surnamedetail += table thead = Html("thead") table += thead trow = Html("tr") thead += trow # Name Column trow += Html("th", self._("Given Name"), class_="ColumnName", inline=True) if showbirth: trow += Html("th", self._("Birth"), class_="ColumnDate", inline=True) if showdeath: trow += Html("th", self._("Death"), class_="ColumnDate", inline=True) if showpartner: trow += Html("th", self._("Partner"), class_="ColumnPartner", inline=True) if showparents: trow += Html("th", self._("Parents"), class_="ColumnParents", inline=True) # begin table body tbody = Html("tbody") table += tbody for person_handle in sorted(ppl_handle_list, key=self.sort_on_given_and_birth): person = self.r_db.get_person_from_handle(person_handle) if person.get_change_time() > ldatec: ldatec = person.get_change_time() trow = Html("tr") tbody += trow # firstname column link = self.new_person_link(person_handle, uplink=True, person=person, name_style=_NAME_STYLE_FIRST) trow += Html("td", link, class_="ColumnName") # birth column if showbirth: tcell = Html("td", class_="ColumnBirth", inline=True) trow += tcell birth_date = _find_birth_date(self.r_db, person) if birth_date is not None: if birth_date.fallback: tcell += Html('em', self.rlocale.get_date(birth_date), inline=True) else: tcell += self.rlocale.get_date(birth_date) else: tcell += " " # death column if showdeath: tcell = Html("td", class_="ColumnDeath", inline=True) trow += tcell death_date = _find_death_date(self.r_db, person) if death_date is not None: if death_date.fallback: tcell += Html('em', self.rlocale.get_date(death_date), inline=True) else: tcell += self.rlocale.get_date(death_date) else: tcell += " " # partner column if showpartner: tcell = Html("td", class_="ColumnPartner") trow += tcell family_list = person.get_family_handle_list() if family_list: fam_count = 0 for family_handle in family_list: fam_count += 1 family = self.r_db.get_family_from_handle( family_handle) partner_handle = utils.find_spouse( person, family) if partner_handle: link = self.new_person_link(partner_handle, uplink=True) if fam_count < len(family_list): if isinstance(link, Html): link.inside += "," else: link += ',' tcell += link else: tcell += " " # parents column if showparents: parent_hdl_list = person.get_parent_family_handle_list() if parent_hdl_list: parent_hdl = parent_hdl_list[0] fam = self.r_db.get_family_from_handle(parent_hdl) f_id = fam.get_father_handle() m_id = fam.get_mother_handle() mother = father = None if f_id: father = self.r_db.get_person_from_handle(f_id) if father: father_name = self.get_name(father) if m_id: mother = self.r_db.get_person_from_handle(m_id) if mother: mother_name = self.get_name(mother) if mother and father: tcell = Html("span", father_name, class_="father fatherNmother") tcell += Html("span", mother_name, class_="mother") elif mother: tcell = Html("span", mother_name, class_="mother", inline=True) elif father: tcell = Html("span", father_name, class_="father", inline=True) samerow = False else: tcell = " " # pylint: disable=R0204 samerow = True trow += Html("td", tcell, class_="ColumnParents", inline=samerow) # add clearline for proper styling # add footer section footer = self.write_footer(ldatec) body += (FULLCLEAR, footer) # send page out for processing # and close the file self.xhtml_writer(surnamepage, output_file, sio, ldatec)
def findRelatedPeople(self) : self.progress.set_pass( # translators: leave all/any {...} untranslated #TRANS: No singular form is needed. ngettext("Finding relationships between {number_of} person", "Finding relationships between {number_of} people", self.numberOfPeopleInDatabase ).format(number_of=self.numberOfPeopleInDatabase), self.numberOfPeopleInDatabase) # as long as we have people we haven't processed yet, keep looping while len(self.handlesOfPeopleToBeProcessed) > 0: handle = self.handlesOfPeopleToBeProcessed.pop() ### DEBUG DEBUG DEBUG # if len(self.handlesOfPeopleAlreadyProcessed) > 50: # break ### # see if we've already processed this person if handle in self.handlesOfPeopleAlreadyProcessed: continue person = self.db.get_person_from_handle(handle) # if we get here, then we're dealing with someone new self.progress.step() # remember that we've now seen this person self.handlesOfPeopleAlreadyProcessed.add(handle) # we have 4 things to do: find (1) spouses, (2) parents, siblings(3), and (4) children # step 1 -- spouses for familyHandle in person.get_family_handle_list(): family = self.db.get_family_from_handle(familyHandle) spouseHandle = utils.find_spouse(person, family) if spouseHandle and \ spouseHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(spouseHandle) # step 2 -- parents for familyHandle in person.get_parent_family_handle_list(): family = self.db.get_family_from_handle(familyHandle) fatherHandle = family.get_father_handle() motherHandle = family.get_mother_handle() if fatherHandle and \ fatherHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(fatherHandle) if motherHandle and \ motherHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(motherHandle) # step 3 -- siblings for familyHandle in person.get_parent_family_handle_list(): family = self.db.get_family_from_handle(familyHandle) for childRef in family.get_child_ref_list(): childHandle = childRef.ref if childHandle and \ childHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(childHandle) # step 4 -- children for familyHandle in person.get_family_handle_list(): family = self.db.get_family_from_handle(familyHandle) for childRef in family.get_child_ref_list(): childHandle = childRef.ref if childHandle and \ childHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(childHandle)
def findRelatedPeople(self): self.progress.set_pass( # translators: leave all/any {...} untranslated #TRANS: No singular form is needed. ngettext("Finding relationships between {number_of} person", "Finding relationships between {number_of} people", self.numberOfPeopleInDatabase).format( number_of=self.numberOfPeopleInDatabase), self.numberOfPeopleInDatabase) # as long as we have people we haven't processed yet, keep looping while len(self.handlesOfPeopleToBeProcessed) > 0: handle = self.handlesOfPeopleToBeProcessed.pop() ### DEBUG DEBUG DEBUG # if len(self.handlesOfPeopleAlreadyProcessed) > 50: # break ### # see if we've already processed this person if handle in self.handlesOfPeopleAlreadyProcessed: continue person = self.db.get_person_from_handle(handle) # if we get here, then we're dealing with someone new self.progress.step() # remember that we've now seen this person self.handlesOfPeopleAlreadyProcessed.add(handle) # we have 4 things to do: find (1) spouses, (2) parents, siblings(3), and (4) children # step 1 -- spouses for familyHandle in person.get_family_handle_list(): family = self.db.get_family_from_handle(familyHandle) spouseHandle = utils.find_spouse(person, family) if spouseHandle and \ spouseHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(spouseHandle) # step 2 -- parents for familyHandle in person.get_parent_family_handle_list(): family = self.db.get_family_from_handle(familyHandle) fatherHandle = family.get_father_handle() motherHandle = family.get_mother_handle() if fatherHandle and \ fatherHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(fatherHandle) if motherHandle and \ motherHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(motherHandle) # step 3 -- siblings for familyHandle in person.get_parent_family_handle_list(): family = self.db.get_family_from_handle(familyHandle) for childRef in family.get_child_ref_list(): childHandle = childRef.ref if childHandle and \ childHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(childHandle) # step 4 -- children for familyHandle in person.get_family_handle_list(): family = self.db.get_family_from_handle(familyHandle) for childRef in family.get_child_ref_list(): childHandle = childRef.ref if childHandle and \ childHandle not in self.handlesOfPeopleAlreadyProcessed: self.handlesOfPeopleToBeProcessed.add(childHandle)
def recurse(self, person_handle, g_level, s_level): """traverse the descendants recursively until either the end of a line is found, or until we reach the maximum number of generations or we reach the max number of spouses that we want to deal with""" if not person_handle: return if g_level > self.max_generations: return # one generation too many if s_level > 0 and s_level == self.max_spouses: return #if person_handle in self.people_seen: return person = self.database.get_person_from_handle(person_handle) family_handles = person.get_family_handle_list() if s_level == 0: val = family_handles[0] if family_handles else None self.__this_slevel = s_level self._add_person((g_level, s_level), person_handle, val) if self.__bold_now == 1: self.__bold_now = 0 if not self.can_recurse(): self.continue_recursion() return if s_level == 1: tmp_bold = self.__bold_now self.__bold_now = 0 for family_handle in family_handles: #Marriage box if the option is there. self._add_marriage((g_level, s_level + 1), person_handle, family_handle) if not self.can_recurse(): self.continue_recursion() return family = self.database.get_family_from_handle(family_handle) spouse_handle = utils.find_spouse(person, family) if self.max_spouses > s_level: self.__this_slevel = s_level + 1 self._add_person((g_level, s_level + 1), spouse_handle, family_handle) if not self.can_recurse: self.continue_recursion() return mykids = [kid.ref for kid in family.get_child_ref_list()] if self.can_recurse(): for child_ref in mykids: self.recurse(child_ref, g_level + 1, 0) else: self.continue_recursion() if self.max_spouses > s_level: #spouse_handle = utils.find_spouse(person,family) self.recurse(spouse_handle, g_level, s_level + 1) if s_level == 1: self.__bold_now = tmp_bold
def remove_uninteresting_parents(self): """ remove any uninteresting parents """ # start with all the people we've already identified unprocessed_parents = set(self._people) while len(unprocessed_parents) > 0: handle = unprocessed_parents.pop() person = self._db.get_person_from_handle(handle) if not person: continue # There are a few things we're going to need, # so look it all up right now; such as: # - who is the child? # - how many children? # - parents? # - spouse? # - is a person of interest? # - spouse of a person of interest? # - same surname as a person of interest? # - spouse has the same surname as a person of interest? child_handle = None child_count = 0 spouse_handle = None spouse_count = 0 father_handle = None mother_handle = None spouse_father_handle = None spouse_mother_handle = None spouse_surname = "" surname = person.get_primary_name().get_surname() surname = surname.encode('iso-8859-1', 'xmlcharrefreplace') # first we get the person's father and mother for family_handle in person.get_parent_family_handle_list(): family = self._db.get_family_from_handle(family_handle) handle = family.get_father_handle() if handle in self._people: father_handle = handle handle = family.get_mother_handle() if handle in self._people: mother_handle = handle # now see how many spouses this person has for family_handle in person.get_family_handle_list(): family = self._db.get_family_from_handle(family_handle) handle = utils.find_spouse(person, family) if handle in self._people: spouse_count += 1 spouse = self._db.get_person_from_handle(handle) spouse_handle = handle spouse_surname = spouse.get_primary_name().get_surname() spouse_surname = spouse_surname.encode( 'iso-8859-1', 'xmlcharrefreplace') # see if the spouse has parents if not spouse_father_handle and not spouse_mother_handle: for family_handle in \ spouse.get_parent_family_handle_list(): family = self._db.get_family_from_handle( family_handle) handle = family.get_father_handle() if handle in self._people: spouse_father_handle = handle handle = family.get_mother_handle() if handle in self._people: spouse_mother_handle = handle # get the number of children that we think might be interesting for family_handle in person.get_family_handle_list(): family = self._db.get_family_from_handle(family_handle) for child_ref in family.get_child_ref_list(): if child_ref.ref in self._people: child_count += 1 child_handle = child_ref.ref # we now have everything we need -- start looking for reasons # why this is a person we need to keep in our list, and loop # back to the top as soon as a reason is discovered # if this person has many children of interest, then we # automatically keep this person if child_count > 1: continue # if this person has many spouses of interest, then we # automatically keep this person if spouse_count > 1: continue # if this person has parents, then we automatically keep # this person if father_handle is not None or mother_handle is not None: continue # if the spouse has parents, then we automatically keep # this person if (spouse_father_handle is not None or spouse_mother_handle is not None): continue # if this is a person of interest, then we automatically keep if person.get_handle() in self._interest_set: continue # if the spouse is a person of interest, then we keep if spouse_handle in self._interest_set: continue # if the surname (or the spouse's surname) matches a person # of interest, then we automatically keep this person keep_this_person = False for person_of_interest_handle in self._interest_set: person_of_interest = self._db.get_person_from_handle( person_of_interest_handle) surname_of_interest = person_of_interest.get_primary_name() surname_of_interest = surname_of_interest.get_surname().encode( 'iso-8859-1', 'xmlcharrefreplace') if (surname_of_interest == surname or surname_of_interest == spouse_surname): keep_this_person = True break if keep_this_person: continue # if we have a special colour to use for this person, # then we automatically keep this person if surname in self._surnamecolors: continue # if we have a special colour to use for the spouse, # then we automatically keep this person if spouse_surname in self._surnamecolors: continue # took us a while, # but if we get here then we can remove this person self._deleted_people += 1 self._people.remove(person.get_handle()) # we can also remove any families to which this person belonged for family_handle in person.get_family_handle_list(): if family_handle in self._families: self._deleted_families += 1 self._families.remove(family_handle) # if we have a spouse, then ensure we queue up the spouse if spouse_handle: if spouse_handle not in unprocessed_parents: unprocessed_parents.add(spouse_handle) # if we have a child, then ensure we queue up the child if child_handle: if child_handle not in unprocessed_parents: unprocessed_parents.add(child_handle)
def __process_person(self, person, rank, ahnentafel, person_key): """ Recursively build the Family Sheet for this person and all children with spouses. @param person: Person object for the key person of the Family Sheet. @param rank: Numerical distance between the central person in the database and the person in the parameter (the number of births needed to connect them). @param ahnentafel: "Ahnentafel" number of the common ancestor of the central person in the database and the person in the parameter, seen from the side of the central person in the database. @param person_key: Family Sheet key to be printed on the top right of the corner. """ # List of (person, rank, ahnentafel, person_key) tuples for persons to # process recursively after this one. more_sheets = [] # Numbering of spouses (integer, but printed in roman numbers). spouse_index = 0 # Numbering of children (integer, but printed as lowercase letters). child_index = 0 # Source references to print as footnotes. self.__citation_index = 0 self.__citations = [] # Notes to print as footnotes. self.__note_index = 0 self.__notes = [] # --- Now let the party begin! --- head_name = str( _Name_get_styled(person.get_primary_name(), _Name_CALLNAME_DONTUSE)) mark2 = docgen.IndexMark(head_name, docgen.INDEX_TYPE_TOC, 2) self.doc.start_paragraph('FSR-Key') self.doc.write_text(person_key, mark2) self.doc.end_paragraph() self.doc.start_table(None, 'FSR-Table') # Main person self.doc.start_row() self.doc.start_cell('FSR-HeadCell', 3) self.__dump_person(person, False, None) self.doc.end_cell() self.doc.end_row() # Spouses for family_handle in person.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) spouse_index += 1 spouse_handle = utils.find_spouse(person, family) if spouse_handle: spouse = self.database.get_person_from_handle(spouse_handle) else: spouse = None # Determine relationship between the center person and the spouse. # If the spouse has a closer blood relationship than the current # person, we refer to the Family Sheet of the spouse instead of # printing the child list, because all children are more closely # related to the center person via the spouse than via the current # person. The same happens if the relationship is on the same # level, but the relationship via the spouse goes via a common # ancestor with a lower Ahnentafel numbering (i.e. a relationship # stronger father-sided). In these cases, refer_spouse will be set # to True. (spouse_rank, spouse_at, spouse_key) = \ self.__calc_person_key(spouse) if self.recurse != FamilySheetOptions.RECURSE_ALL: refer_spouse = (spouse_rank != -1 and \ (spouse_rank < rank or (spouse_rank == rank and spouse_at < ahnentafel))) else: refer_spouse = False self.doc.start_row() self.doc.start_cell('FSR-NumberCell', 1) self.doc.start_paragraph('FSR-Number') self.doc.write_text(utils.roman(spouse_index)) self.doc.end_paragraph() self.doc.end_cell() self.doc.start_cell('FSR-DataCell', 2) self.__dump_family(family, spouse) if refer_spouse: self.doc.start_paragraph('FSR-Normal') self.doc.write_text(_("\u2192 %s") % spouse_key) self.doc.end_paragraph() self.doc.end_cell() self.doc.end_row() if refer_spouse: # Spouse with closer relationship than current person? Don't # print children on this Family Sheet (but count them for the # numbering). child_index += len(family.get_child_ref_list()) continue # Children for child_ref in family.get_child_ref_list(): child = self.database.get_person_from_handle(child_ref.ref) child_letter = string.ascii_lowercase[child_index] self.doc.start_row() self.doc.start_cell('FSR-EmptyCell', 1) self.doc.end_cell() self.doc.start_cell('FSR-NumberCell', 1) self.doc.start_paragraph('FSR-Number') self.doc.write_text(child_letter) self.doc.end_paragraph() self.doc.end_cell() self.doc.start_cell('FSR-DataCell', 1) has_spouses = (child.get_family_handle_list() != []) self.__dump_person(child, has_spouses, child_ref) if has_spouses: # We have to recalculate the key for this person, it could # be closer related if it is a direct ancestor of the # central person or one of its spouses. (child_rank, child_at, child_key) = \ self.__calc_person_key(child) self.doc.start_paragraph('FSR-Normal') self.doc.write_text(_("\u2192 %s") % child_key) self.doc.end_paragraph() # We recursively print this child *only* if its # relationship with the central person is closest via the # current person. This way, we avoid that a person is # printed recursively from more than one of its ancestors. if child_key == person_key + child_letter or \ self.recurse == FamilySheetOptions.RECURSE_ALL: more_sheets.append( (child, child_rank, child_at, child_key)) self.doc.end_cell() self.doc.end_row() child_index += 1 self.doc.start_row() self.doc.start_cell('FSR-FootCell', 3) self.doc.end_cell() self.doc.end_row() self.doc.end_table() self.__dump_sources() self.__dump_notes() # Now print the sheets for the children. if self.recurse != FamilySheetOptions.RECURSE_NONE: for (child, child_rank, child_at, child_key) in more_sheets: self.doc.page_break() self.__process_person(child, child_rank, child_at, child_key)
def display(self, tobj, person): """Fill text buffer tobj with detailed info on person person.""" normal = tobj.create_tag() normal.set_property("indent", 10) normal.set_property("pixels-above-lines", 1) normal.set_property("pixels-below-lines", 1) indent = tobj.create_tag() indent.set_property("indent", 30) indent.set_property("pixels-above-lines", 1) indent.set_property("pixels-below-lines", 1) title = tobj.create_tag() title.set_property("weight", Pango.Weight.BOLD) title.set_property("scale", 1.2) self.add(tobj, title, name_displayer.display(person)) self.add(tobj, normal, "%s:\t%s" % (_("ID"), person.get_gramps_id())) self.add(tobj, normal, "%s:\t%s" % (_("Gender"), sex[person.get_gender()])) bref = person.get_birth_ref() if bref: self.add(tobj, normal, "%s:\t%s" % (_("Birth"), self.get_event_info(bref.ref))) dref = person.get_death_ref() if dref: self.add(tobj, normal, "%s:\t%s" % (_("Death"), self.get_event_info(dref.ref))) nlist = person.get_alternate_names() if len(nlist) > 0: self.add(tobj, title, _("Alternate Names")) for name in nlist: self.add(tobj, normal, name_displayer.display_name(name)) elist = person.get_event_ref_list() if len(elist) > 0: self.add(tobj, title, _("Events")) for event_ref in person.get_event_ref_list(): event_handle = event_ref.ref role = event_ref.get_role() name = str(self.database.get_event_from_handle(event_handle).get_type()) if role.is_primary(): self.add(tobj, normal, "%s:\t%s" % (name, self.get_event_info(event_handle))) else: self.add(tobj, normal, "%s (%s):\t%s" % (name, role, self.get_event_info(event_handle))) plist = person.get_parent_family_handle_list() if len(plist) > 0: self.add(tobj, title, _("Parents")) for fid in person.get_parent_family_handle_list(): (fname, mname, gid) = self.get_parent_info(fid) self.add(tobj, normal, "%s:\t%s" % (_("Family ID"), gid)) if fname: self.add(tobj, indent, "%s:\t%s" % (_("Father"), fname)) if mname: self.add(tobj, indent, "%s:\t%s" % (_("Mother"), mname)) else: self.add(tobj, normal, _("No parents found")) self.add(tobj, title, _("Spouses")) slist = person.get_family_handle_list() if len(slist) > 0: for fid in slist: (fname, mname, pid) = self.get_parent_info(fid) family = self.database.get_family_from_handle(fid) self.add(tobj, normal, "%s:\t%s" % (_("Family ID"), pid)) spouse_id = ReportUtils.find_spouse(person, family) if spouse_id: spouse = self.database.get_person_from_handle(spouse_id) self.add(tobj, indent, "%s:\t%s" % (_("Spouse"), name_of(spouse))) relstr = str(family.get_relationship()) self.add(tobj, indent, "%s:\t%s" % (_("Type"), relstr)) event = ReportUtils.find_marriage(self.database, family) if event: self.add(tobj, indent, "%s:\t%s" % (_("Marriage"), self.get_event_info(event.get_handle()))) for child_ref in family.get_child_ref_list(): child = self.database.get_person_from_handle(child_ref.ref) self.add(tobj, indent, "%s:\t%s" % (_("Child"), name_of(child))) else: self.add(tobj, normal, _("No spouses or children found")) alist = person.get_address_list() if len(alist) > 0: self.add(tobj, title, _("Addresses")) for addr in alist: location = ", ".join( [ addr.get_street(), addr.get_city(), addr.get_state(), addr.get_country(), addr.get_postal_code(), addr.get_phone(), ] ) self.add(tobj, normal, location.strip())
def __calc_person_key(self, person): """ The person key is a unique identifier that is built from the relationship to the default person. It consists of the "Ahnentafel" number of the common ancestor of the person with the default person, and then a letter representing the child number for each generation from the common ancestor to the person. If more than one common ancestor exists, the common ancestor with the lowest "Ahnentafel" number has precedence. For example, the second child of the third child of the father of the mother of the central person gets the person key "6cb". """ relationship = get_relationship_calculator() default_person = self.database.get_default_person() # No home person set. if default_person is None: return (-1, 0, "") # First try direct relationship. spousestring = "" info, msg = relationship.get_relationship_distance_new(self.database, default_person, person, all_dist=True) info = relationship.collapse_relations(info)[0] (rank, ancestor_handle, default_rel, default_fam, person_rel, person_fam) = info # Then try relationship to any spouse. if rank == -1: index = 0 for family_handle in default_person.get_family_handle_list(): index += 1 family = self.database.get_family_from_handle(family_handle) spouse_handle = utils.find_spouse(default_person, family) spouse = self.database.get_person_from_handle(spouse_handle) info, msg = relationship.get_relationship_distance_new( self.database, spouse, person, all_dist=True) info = relationship.collapse_relations(info)[0] (rank, ancestor_handle, default_rel, default_fam, person_rel, person_fam) = info if rank != -1: spousestring = utils.roman(index) break # If no relationship found at all, exit here. if rank == -1: return (rank, 0, "") # Calculate Ahnentafel number of common ancestor. ahnentafel = 1 for rel in default_rel: ahnentafel *= 2 if rel in (relationship.REL_MOTHER, relationship.REL_MOTHER_NOTBIRTH): ahnentafel += 1 # Find out child letters. child = person childletters = "" for rel in person_rel: family_handle = child.get_main_parents_family_handle() family = self.database.get_family_from_handle(family_handle) if rel in (relationship.REL_MOTHER, relationship.REL_MOTHER_NOTBIRTH): parent_handle = family.get_mother_handle() else: parent_handle = family.get_father_handle() parent = self.database.get_person_from_handle(parent_handle) # Count *all* children from this parent childletter = "?" index = 0 for family_handle in parent.get_family_handle_list(): family = self.database.get_family_from_handle(family_handle) for child_ref in family.get_child_ref_list(): if child_ref.ref == child.get_handle(): childletter = string.ascii_lowercase[index] break index += 1 else: continue break childletters = childletter + childletters child = parent return (rank, ahnentafel, "%s%s%s" % (spousestring, ahnentafel, childletters))