Improvements in fanchartwidget, fixed to use as gramplet, preparation for a config dialog

svn: r20287
This commit is contained in:
Benny Malengier 2012-08-30 08:56:09 +00:00
parent 232e76520e
commit 8dc900e046
4 changed files with 46 additions and 28 deletions

View File

@ -1,7 +1,9 @@
# #
# Gramps - a GTK+/GNOME based genealogy program # Gramps - a GTK+/GNOME based genealogy program
# #
# Copyright (C) 2000-2006 Donald N. Allingham # Copyright (C) 2001-2007 Donald N. Allingham, Martin Hawlisch
# Copyright (C) 2009 Douglas S. Blank
# Copyright (C) 2012 Benny Malengier
# #
# This program is free software; you can redistribute it and/or modify # 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 # it under the terms of the GNU General Public License as published by
@ -50,6 +52,7 @@ from gen.display.name import displayer as name_displayer
import gen.lib import gen.lib
import gui.utils import gui.utils
from gui.ddtargets import DdTargets from gui.ddtargets import DdTargets
from gen.utils.alive import probably_alive
#------------------------------------------------------------------------- #-------------------------------------------------------------------------
# #
@ -85,12 +88,13 @@ class FanChartWidget(Gtk.DrawingArea):
NORMAL = 1 NORMAL = 1
EXPANDED = 2 EXPANDED = 2
def __init__(self, generations, context_popup_callback=None): def __init__(self, generations, dbstate, context_popup_callback=None):
""" """
Fan Chart Widget. Handles visualization of data in self.data. Fan Chart Widget. Handles visualization of data in self.data.
See main() of FanChartGramplet for example of model format. See main() of FanChartGramplet for example of model format.
""" """
GObject.GObject.__init__(self) GObject.GObject.__init__(self)
self.dbstate = dbstate
self.translating = False self.translating = False
self.last_x, self.last_y = None, None self.last_x, self.last_y = None, None
self.connect("button_release_event", self.on_mouse_up) self.connect("button_release_event", self.on_mouse_up)
@ -126,6 +130,7 @@ class FanChartWidget(Gtk.DrawingArea):
self.center_xy = [0, 0] # distance from center (x, y) self.center_xy = [0, 0] # distance from center (x, y)
self.set_generations(self.generations) self.set_generations(self.generations)
self.center = 50 # pixel radius of center self.center = 50 # pixel radius of center
self.gen_color = True
self.layout = self.create_pango_layout('cairo') self.layout = self.create_pango_layout('cairo')
self.layout.set_font_description(Pango.FontDescription("sans 8")) self.layout.set_font_description(Pango.FontDescription("sans 8"))
self.set_size_request(120,120) self.set_size_request(120,120)
@ -152,7 +157,7 @@ class FanChartWidget(Gtk.DrawingArea):
gender = True gender = True
for count in range(len(self.data[i])): for count in range(len(self.data[i])):
# start, stop, male, state # start, stop, male, state
self.angle[i].append([angle, angle + slice,gender,self.NORMAL]) self.angle[i].append([angle, angle + slice, gender, self.NORMAL])
angle += slice angle += slice
gender = not gender gender = not gender
@ -213,7 +218,7 @@ class FanChartWidget(Gtk.DrawingArea):
if state in [self.NORMAL, self.EXPANDED]: if state in [self.NORMAL, self.EXPANDED]:
self.draw_person(cr, gender_code(male), self.draw_person(cr, gender_code(male),
text, start, stop, text, start, stop,
generation, state, parents, child) generation, state, parents, child, person)
cr.set_source_rgb(1, 1, 1) # white cr.set_source_rgb(1, 1, 1) # white
cr.move_to(0,0) cr.move_to(0,0)
cr.arc(0, 0, self.center, 0, 2 * math.pi) cr.arc(0, 0, self.center, 0, 2 * math.pi)
@ -242,20 +247,29 @@ class FanChartWidget(Gtk.DrawingArea):
PangoCairo.show_layout(cr, self.layout) PangoCairo.show_layout(cr, self.layout)
def draw_person(self, cr, gender, name, start, stop, generation, def draw_person(self, cr, gender, name, start, stop, generation,
state, parents, child): state, parents, child, person):
""" """
Display the piece of pie for a given person. start and stop Display the piece of pie for a given person. start and stop
are in degrees. are in degrees. Gender is indication of father position or mother
position in the chart
""" """
alloc = self.get_allocation() alloc = self.get_allocation()
x, y, w, h = alloc.x, alloc.y, alloc.width, alloc.height x, y, w, h = alloc.x, alloc.y, alloc.width, alloc.height
start_rad = start * math.pi/180 start_rad = start * math.pi/180
stop_rad = stop * math.pi/180 stop_rad = stop * math.pi/180
if self.gen_color:
r,g,b = self.GENCOLOR[generation % len(self.GENCOLOR)] r,g,b = self.GENCOLOR[generation % len(self.GENCOLOR)]
if gender == gen.lib.Person.MALE: if gender == gen.lib.Person.MALE:
r *= .9 r *= .9
g *= .9 g *= .9
b *= .9 b *= .9
else:
try:
alive = probably_alive(person, self.dbstate.db)
except RuntimeError:
alive = False
backgr, border = gui.utils.color_graph_box(alive, person.gender)
r, g, b = gui.utils.hex_to_rgb(backgr)
radius = generation * self.pixels_per_generation + self.center radius = generation * self.pixels_per_generation + self.center
# If max generation, and they have parents: # If max generation, and they have parents:
if generation == self.generations - 1 and parents: if generation == self.generations - 1 and parents:

View File

@ -535,7 +535,7 @@ class GuiGramplet(object):
labels = Gtk.VBox(True) labels = Gtk.VBox(True)
options = Gtk.VBox(True) options = Gtk.VBox(True)
hbox.pack_start(labels, False, True, 0) hbox.pack_start(labels, False, True, 0)
hbox.pack_start(options, True) hbox.pack_start(options, True, True, 0)
topbox.pack_start(hbox, False, False, 0) topbox.pack_start(hbox, False, False, 0)
for item in self.pui.option_order: for item in self.pui.option_order:
label = Gtk.Label(label=item + ":") label = Gtk.Label(label=item + ":")
@ -543,7 +543,7 @@ class GuiGramplet(object):
labels.pack_start(label, True, True, 0) labels.pack_start(label, True, True, 0)
options.pack_start(self.pui.option_dict[item][0], True, True, 0) # widget options.pack_start(self.pui.option_dict[item][0], True, True, 0) # widget
save_button = Gtk.Button(stock=Gtk.STOCK_SAVE) save_button = Gtk.Button(stock=Gtk.STOCK_SAVE)
topbox.pack_end(save_button, False, False) topbox.pack_end(save_button, False, False, 0)
save_button.connect('clicked', self.pui.save_update_options) save_button.connect('clicked', self.pui.save_update_options)
frame.add(topbox) frame.add(topbox)
frame.show_all() frame.show_all()

View File

@ -68,7 +68,7 @@ class FanChartGramplet(Gramplet):
self.set_tooltip(_("Click to expand/contract person\nRight-click for options\nClick and drag in open area to rotate")) self.set_tooltip(_("Click to expand/contract person\nRight-click for options\nClick and drag in open area to rotate"))
self.generations = 6 self.generations = 6
self.format_helper = FormattingHelper(self.dbstate) self.format_helper = FormattingHelper(self.dbstate)
self.gui.fan = FanChartWidget(self.generations, self.gui.fan = FanChartWidget(self.generations, self.dbstate,
context_popup_callback=self.on_popup) context_popup_callback=self.on_popup)
self.gui.fan.format_helper = self.format_helper self.gui.fan.format_helper = self.format_helper
# Replace the standard textview with the fan chart widget: # Replace the standard textview with the fan chart widget:

View File

@ -75,7 +75,7 @@ class FanChartView(NavigationView):
return 'Person' return 'Person'
def build_widget(self): def build_widget(self):
self.fan = FanChartWidget(self.generations, self.fan = FanChartWidget(self.generations, self.dbstate,
context_popup_callback=self.on_popup) context_popup_callback=self.on_popup)
self.fan.format_helper = self.format_helper self.fan.format_helper = self.format_helper
self.scrolledwindow = Gtk.ScrolledWindow(None, None) self.scrolledwindow = Gtk.ScrolledWindow(None, None)
@ -141,8 +141,8 @@ class FanChartView(NavigationView):
Returns True if a person has parents. Returns True if a person has parents.
""" """
if person: if person:
m = self.get_parent(person, "female") m = self.get_parent(person, False)
f = self.get_parent(person, "male") f = self.get_parent(person, True)
return not m is f is None return not m is f is None
return False return False
@ -157,9 +157,9 @@ class FanChartView(NavigationView):
return True return True
return False return False
def get_parent(self, person, gender): def get_parent(self, person, father):
""" """
Get the father if gender == "male", or get mother otherwise. Get the father of the family if father == True, otherwise mother
""" """
if person: if person:
parent_handle_list = person.get_parent_family_handle_list() parent_handle_list = person.get_parent_family_handle_list()
@ -167,7 +167,7 @@ class FanChartView(NavigationView):
family_id = parent_handle_list[0] family_id = parent_handle_list[0]
family = self.dbstate.db.get_family_from_handle(family_id) family = self.dbstate.db.get_family_from_handle(family_id)
if family: if family:
if gender == "male": if father:
person_handle = gen.lib.Family.get_father_handle(family) person_handle = gen.lib.Family.get_father_handle(family)
else: else:
person_handle = gen.lib.Family.get_mother_handle(family) person_handle = gen.lib.Family.get_mother_handle(family)
@ -194,7 +194,7 @@ class FanChartView(NavigationView):
# name, person, parents, children # name, person, parents, children
for (n,p,q,c) in self.fan.data[current - 1]: for (n,p,q,c) in self.fan.data[current - 1]:
# Get father's details: # Get father's details:
person = self.get_parent(p, "male") person = self.get_parent(p, True)
if person: if person:
name = name_displayer.display(person) name = name_displayer.display(person)
else: else:
@ -209,7 +209,7 @@ class FanChartView(NavigationView):
self.fan.angle[current][parent][3] = self.fan.COLLAPSED self.fan.angle[current][parent][3] = self.fan.COLLAPSED
parent += 1 parent += 1
# Get mother's details: # Get mother's details:
person = self.get_parent(p, "female") person = self.get_parent(p, False)
if person: if person:
name = name_displayer.display(person) name = name_displayer.display(person)
else: else:
@ -225,7 +225,7 @@ class FanChartView(NavigationView):
parent += 1 parent += 1
self.fan.queue_draw() self.fan.queue_draw()
def on_childmenu_changed(self, obj,person_handle): def on_childmenu_changed(self, obj, person_handle):
"""Callback for the pulldown menu selection, changing to the person """Callback for the pulldown menu selection, changing to the person
attached with menu item.""" attached with menu item."""
self.change_active(person_handle) self.change_active(person_handle)
@ -235,12 +235,16 @@ class FanChartView(NavigationView):
person = self.dbstate.db.get_person_from_handle(person_handle) person = self.dbstate.db.get_person_from_handle(person_handle)
if person: if person:
try: try:
EditPerson(self.dbstate, self.uistate, [], person) EditPerson(self.dbstate, self.uistate, [], person,
callback=self.edit_callback)
except WindowActiveError: except WindowActiveError:
pass pass
return True return True
return False return False
def edit_callback(self, *args):
self.update()
def copy_person_to_clipboard_cb(self, obj, person_handle): def copy_person_to_clipboard_cb(self, obj, person_handle):
"""Renders the person data into some lines of text and puts that into the clipboard""" """Renders the person data into some lines of text and puts that into the clipboard"""
person = self.dbstate.db.get_person_from_handle(person_handle) person = self.dbstate.db.get_person_from_handle(person_handle)
@ -274,7 +278,7 @@ class FanChartView(NavigationView):
menu.append(go_item) menu.append(go_item)
edit_item = Gtk.ImageMenuItem.new_from_stock(stock_id=Gtk.STOCK_EDIT, accel_group=None) edit_item = Gtk.ImageMenuItem.new_from_stock(stock_id=Gtk.STOCK_EDIT, accel_group=None)
edit_item.connect("activate",self.edit_person_cb,person_handle) edit_item.connect("activate", self.edit_person_cb, person_handle)
edit_item.show() edit_item.show()
menu.append(edit_item) menu.append(edit_item)
@ -354,7 +358,7 @@ class FanChartView(NavigationView):
label.set_alignment(0,0) label.set_alignment(0,0)
sib_item.add(label) sib_item.add(label)
linked_persons.append(sib_id) linked_persons.append(sib_id)
sib_item.connect("activate",self.on_childmenu_changed,sib_id) sib_item.connect("activate", self.on_childmenu_changed, sib_id)
sib_item.show() sib_item.show()
sib_menu.append(sib_item) sib_menu.append(sib_item)
@ -366,7 +370,7 @@ class FanChartView(NavigationView):
# Go over children and build their menu # Go over children and build their menu
item = Gtk.MenuItem(label=_("Children")) item = Gtk.MenuItem(label=_("Children"))
no_children = 1 no_children = 1
childlist = find_children(self.dbstate.db,person) childlist = find_children(self.dbstate.db, person)
for child_handle in childlist: for child_handle in childlist:
child = self.dbstate.db.get_person_from_handle(child_handle) child = self.dbstate.db.get_person_from_handle(child_handle)
if not child: if not child:
@ -391,7 +395,7 @@ class FanChartView(NavigationView):
label.set_alignment(0,0) label.set_alignment(0,0)
child_item.add(label) child_item.add(label)
linked_persons.append(child_handle) linked_persons.append(child_handle)
child_item.connect("activate",self.on_childmenu_changed,child_handle) child_item.connect("activate", self.on_childmenu_changed, child_handle)
child_item.show() child_item.show()
child_menu.append(child_item) child_menu.append(child_item)