Improvements in fanchartwidget, fixed to use as gramplet, preparation for a config dialog
svn: r20287
This commit is contained in:
parent
232e76520e
commit
8dc900e046
@ -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:
|
||||||
|
@ -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()
|
||||||
|
@ -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:
|
||||||
|
@ -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)
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user