From ba01db947b23d0bdf9712c4d1a0ca4b4f8370a96 Mon Sep 17 00:00:00 2001 From: Gary Burton Date: Sat, 30 May 2009 11:58:03 +0000 Subject: [PATCH] Bug 2950. Made subgraph optional for Relationship Graph as discussed in bug report. Moved the option to GraphvizReportDialog and refactored FamilyLines to use it. svn: r12595 --- src/ReportBase/_GraphvizReportDialog.py | 38 ++++++---- src/plugins/graph/GVFamilyLines.py | 7 -- src/plugins/graph/GVRelGraph.py | 96 +++++++++++++++---------- 3 files changed, 81 insertions(+), 60 deletions(-) diff --git a/src/ReportBase/_GraphvizReportDialog.py b/src/ReportBase/_GraphvizReportDialog.py index 93e33427a..0880c5251 100644 --- a/src/ReportBase/_GraphvizReportDialog.py +++ b/src/ReportBase/_GraphvizReportDialog.py @@ -3,6 +3,7 @@ # # Copyright (C) 2007-2008 Brian G. Matherly # Copyright (C) 2007-2009 Stephane Charette +# Copyright (C) 2009 Gary Burton # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by @@ -53,7 +54,8 @@ import Config from ReportBase import CATEGORY_GRAPHVIZ from _ReportDialog import ReportDialog from _PaperMenu import PaperFrame -from gen.plug.menu import NumberOption, TextOption, EnumeratedListOption +from gen.plug.menu import NumberOption, TextOption, EnumeratedListOption, \ + BooleanOption #------------------------------------------------------------------------------- # @@ -159,19 +161,20 @@ class GVDocBase(BaseDoc.BaseDoc, BaseDoc.GVDoc): menu = options.menu - self.dpi = menu.get_option_by_name('dpi').get_value() - self.fontfamily = menu.get_option_by_name('font_family').get_value() - self.fontsize = menu.get_option_by_name('font_size').get_value() - self.hpages = menu.get_option_by_name('h_pages').get_value() - self.nodesep = menu.get_option_by_name('nodesep').get_value() - self.noteloc = menu.get_option_by_name('noteloc').get_value() - self.notesize = menu.get_option_by_name('notesize').get_value() - self.note = menu.get_option_by_name('note').get_value() - self.pagedir = menu.get_option_by_name('page_dir').get_value() - self.rankdir = menu.get_option_by_name('rank_dir').get_value() - self.ranksep = menu.get_option_by_name('ranksep').get_value() - self.ratio = menu.get_option_by_name('ratio').get_value() - self.vpages = menu.get_option_by_name('v_pages').get_value() + self.dpi = menu.get_option_by_name('dpi').get_value() + self.fontfamily = menu.get_option_by_name('font_family').get_value() + self.fontsize = menu.get_option_by_name('font_size').get_value() + self.hpages = menu.get_option_by_name('h_pages').get_value() + self.nodesep = menu.get_option_by_name('nodesep').get_value() + self.noteloc = menu.get_option_by_name('noteloc').get_value() + self.notesize = menu.get_option_by_name('notesize').get_value() + self.note = menu.get_option_by_name('note').get_value() + self.pagedir = menu.get_option_by_name('page_dir').get_value() + self.rankdir = menu.get_option_by_name('rank_dir').get_value() + self.ranksep = menu.get_option_by_name('ranksep').get_value() + self.ratio = menu.get_option_by_name('ratio').get_value() + self.vpages = menu.get_option_by_name('v_pages').get_value() + self.usesubgraphs = menu.get_option_by_name('usesubgraphs').get_value() paper_size = paper_style.get_size() @@ -1035,6 +1038,13 @@ class GraphvizReportDialog(ReportDialog): "between columns.")) self.options.add_menu_option(category, "ranksep", ranksep) + use_subgraphs = BooleanOption(_('Use subgraphs'), True) + use_subgraphs.set_help(_("Subgraphs can help GraphViz position " + "spouses together, but with non-trivial " + "graphs will result in longer lines and " + "larger graphs.")) + self.options.add_menu_option(category, "usesubgraphs", use_subgraphs) + ################################ category = _("Note") ################################ diff --git a/src/plugins/graph/GVFamilyLines.py b/src/plugins/graph/GVFamilyLines.py index 2bebda2d3..696da72e1 100644 --- a/src/plugins/graph/GVFamilyLines.py +++ b/src/plugins/graph/GVFamilyLines.py @@ -218,13 +218,6 @@ class FamilyLinesOptions(MenuReportOptions): 'between women and men.')) menu.add_option(category, "useroundedcorners", use_roundedcorners) - use_subgraphs = BooleanOption(_('Use subgraphs'), False) - use_subgraphs.set_help(_("Subgraphs can help GraphViz position " - "certain linked nodes closer together, " - "but with non-trivial graphs will result " - "in longer lines and larger graphs.")) - menu.add_option(category, "usesubgraphs", use_subgraphs) - self.include_dates = BooleanOption(_('Include dates'), True) self.include_dates.set_help(_('Whether to include dates for people ' \ 'and families.')) diff --git a/src/plugins/graph/GVRelGraph.py b/src/plugins/graph/GVRelGraph.py index 96116e481..e88ab83e7 100644 --- a/src/plugins/graph/GVRelGraph.py +++ b/src/plugins/graph/GVRelGraph.py @@ -125,6 +125,7 @@ class RelGraphReport(Report): self.show_families = menu.get_option_by_name('showfamily').get_value() self.just_years = menu.get_option_by_name('justyears').get_value() self.use_place = menu.get_option_by_name('use_place').get_value() + self.use_subgraphs = menu.get_option_by_name('usesubgraphs').get_value() self.colorize = menu.get_option_by_name('color').get_value() color_males = menu.get_option_by_name('colormales').get_value() @@ -243,48 +244,65 @@ class RelGraphReport(Report): if self.show_families: family_list = person.get_family_handle_list() for fam_handle in family_list: - fam = self.database.get_family_from_handle(fam_handle) - fam_id = fam.get_gramps_id() + family = self.database.get_family_from_handle(fam_handle) + fam_id = family.get_gramps_id() if fam_handle not in families_done: families_done[fam_handle] = 1 - label = "" - for event_ref in fam.get_event_ref_list(): - event = self.database.get_event_from_handle( - event_ref.ref) - if event.type == gen.lib.EventType.MARRIAGE: - label = self.get_event_string(event) - break - if self.includeid: - label = "%s (%s)" % (label, fam_id) - color = "" - fill = "" - style = "solid" - if self.colorize == 'colored': - color = self.colors['family'] - elif self.colorize == 'filled': - fill = self.colors['family'] - style = "filled" - self.doc.add_node(fam_id, label, "ellipse", - color, style, fill) + self.__add_family(fam_handle) + # If subgraphs are not chosen then each parent is linked + # separately to the family. This gives Graphviz greater + # control over the layout of the whole graph but + # may leave spouses not positioned together. + if not self.use_subgraphs: + self.doc.add_link(fam_id, p_id, "", + self.arrowheadstyle, + self.arrowtailstyle) - f_handle = fam.get_father_handle() - m_handle = fam.get_mother_handle() - self.doc.start_subgraph(fam_id) - if f_handle: - father = \ - self.database.get_person_from_handle(f_handle) - self.doc.add_link(fam_id, - father.get_gramps_id(), "", - self.arrowheadstyle, - self.arrowtailstyle ) - if m_handle: - mother = \ - self.database.get_person_from_handle(m_handle) - self.doc.add_link(fam_id, - mother.get_gramps_id(), "", - self.arrowheadstyle, - self.arrowtailstyle ) - self.doc.end_subgraph() + def __add_family(self, fam_handle): + """Add a node for a family and optionally link the spouses to it""" + fam = self.database.get_family_from_handle(fam_handle) + fam_id = fam.get_gramps_id() + + label = "" + for event_ref in fam.get_event_ref_list(): + event = self.database.get_event_from_handle(event_ref.ref) + if event.type == gen.lib.EventType.MARRIAGE: + label = self.get_event_string(event) + break + if self.includeid: + label = "%s (%s)" % (label, fam_id) + color = "" + fill = "" + style = "solid" + if self.colorize == 'colored': + color = self.colors['family'] + elif self.colorize == 'filled': + fill = self.colors['family'] + style = "filled" + self.doc.add_node(fam_id, label, "ellipse", color, style, fill) + + # If subgraphs are used then we add both spouses here and Graphviz + # will attempt to position both spouses closely together. + # TODO: A person who is a parent in more than one family may only be + # positioned next to one of their spouses. The code currently + # does not take into account multiple spouses. + if self.use_subgraphs: + self.doc.start_subgraph(fam_id) + f_handle = fam.get_father_handle() + m_handle = fam.get_mother_handle() + if f_handle: + father = self.database.get_person_from_handle(f_handle) + self.doc.add_link(fam_id, + father.get_gramps_id(), "", + self.arrowheadstyle, + self.arrowtailstyle) + if m_handle: + mother = self.database.get_person_from_handle(m_handle) + self.doc.add_link(fam_id, + mother.get_gramps_id(), "", + self.arrowheadstyle, + self.arrowtailstyle) + self.doc.end_subgraph() def get_gender_style(self, person): "return gender specific person style"