r20620 - gnucash/trunk/src - Add Tree view widget for owner objects, not used yet
Geert Janssens
gjanssens at code.gnucash.org
Wed May 11 17:51:04 EDT 2011
Author: gjanssens
Date: 2011-05-11 17:51:03 -0400 (Wed, 11 May 2011)
New Revision: 20620
Trac: http://svn.gnucash.org/trac/changeset/20620
Added:
gnucash/trunk/src/gnome-utils/gnc-tree-view-owner.c
gnucash/trunk/src/gnome-utils/gnc-tree-view-owner.h
gnucash/trunk/src/gnome/gtkbuilder/owner.ui
Modified:
gnucash/trunk/src/gnome-utils/Makefile.am
gnucash/trunk/src/gnome/gtkbuilder/Makefile.am
Log:
Add Tree view widget for owner objects, not used yet
Modified: gnucash/trunk/src/gnome/gtkbuilder/Makefile.am
===================================================================
--- gnucash/trunk/src/gnome/gtkbuilder/Makefile.am 2011-05-11 21:50:54 UTC (rev 20619)
+++ gnucash/trunk/src/gnome/gtkbuilder/Makefile.am 2011-05-11 21:51:03 UTC (rev 20620)
@@ -8,6 +8,7 @@
fincalc.glade \
lots.glade \
newuser.glade \
+ owner.ui \
price.glade \
print.glade \
progress.glade \
Added: gnucash/trunk/src/gnome/gtkbuilder/owner.ui
===================================================================
--- gnucash/trunk/src/gnome/gtkbuilder/owner.ui (rev 0)
+++ gnucash/trunk/src/gnome/gtkbuilder/owner.ui 2011-05-11 21:51:03 UTC (rev 20620)
@@ -0,0 +1,96 @@
+<?xml version="1.0"?>
+<interface>
+ <requires lib="gtk+" version="2.16"/>
+ <!-- interface-naming-policy toplevel-contextual -->
+ <object class="GtkDialog" id="Filter By">
+ <property name="visible">True</property>
+ <property name="border_width">6</property>
+ <property name="title" translatable="yes">Filter By...</property>
+ <property name="type_hint">dialog</property>
+ <signal name="response" handler="gppot_filter_response_cb"/>
+ <child internal-child="vbox">
+ <object class="GtkVBox" id="dialog-vbox13">
+ <property name="visible">True</property>
+ <property name="orientation">vertical</property>
+ <property name="spacing">6</property>
+ <child>
+ <object class="GtkCheckButton" id="show_hidden">
+ <property name="label" translatable="yes">Only show _active owners</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="receives_default">False</property>
+ <property name="use_underline">True</property>
+ <property name="draw_indicator">True</property>
+ <signal name="toggled" handler="gppot_filter_show_inactive_toggled_cb"/>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="fill">False</property>
+ <property name="position">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkCheckButton" id="show_zero">
+ <property name="label" translatable="yes">Show _zero balance owners</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="receives_default">False</property>
+ <property name="use_underline">True</property>
+ <property name="draw_indicator">True</property>
+ <signal name="toggled" handler="gppot_filter_show_zero_toggled_cb"/>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="fill">False</property>
+ <property name="position">2</property>
+ </packing>
+ </child>
+ <child internal-child="action_area">
+ <object class="GtkHButtonBox" id="dialog-action_area13">
+ <property name="visible">True</property>
+ <property name="layout_style">end</property>
+ <child>
+ <object class="GtkButton" id="cancelbutton1">
+ <property name="label">gtk-cancel</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="can_default">True</property>
+ <property name="receives_default">False</property>
+ <property name="use_stock">True</property>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="fill">False</property>
+ <property name="position">0</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkButton" id="okbutton1">
+ <property name="label">gtk-ok</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="can_default">True</property>
+ <property name="receives_default">False</property>
+ <property name="use_stock">True</property>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="fill">False</property>
+ <property name="position">1</property>
+ </packing>
+ </child>
+ </object>
+ <packing>
+ <property name="expand">False</property>
+ <property name="pack_type">end</property>
+ <property name="position">0</property>
+ </packing>
+ </child>
+ </object>
+ </child>
+ <action-widgets>
+ <action-widget response="-6">cancelbutton1</action-widget>
+ <action-widget response="-5">okbutton1</action-widget>
+ </action-widgets>
+ </object>
+</interface>
Modified: gnucash/trunk/src/gnome-utils/Makefile.am
===================================================================
--- gnucash/trunk/src/gnome-utils/Makefile.am 2011-05-11 21:50:54 UTC (rev 20619)
+++ gnucash/trunk/src/gnome-utils/Makefile.am 2011-05-11 21:51:03 UTC (rev 20620)
@@ -93,6 +93,7 @@
gnc-tree-model-price.c \
gnc-tree-view-account.c \
gnc-tree-view-commodity.c \
+ gnc-tree-view-owner.c \
gnc-tree-view-price.c \
gnc-tree-view-sx-list.c \
gnc-tree-view.c \
@@ -164,6 +165,7 @@
gnc-tree-model-price.h \
gnc-tree-view-account.h \
gnc-tree-view-commodity.h \
+ gnc-tree-view-owner.h \
gnc-tree-view-price.h \
gnc-tree-view-sx-list.h \
gnc-tree-view.h \
Added: gnucash/trunk/src/gnome-utils/gnc-tree-view-owner.c
===================================================================
--- gnucash/trunk/src/gnome-utils/gnc-tree-view-owner.c (rev 0)
+++ gnucash/trunk/src/gnome-utils/gnc-tree-view-owner.c 2011-05-11 21:51:03 UTC (rev 20620)
@@ -0,0 +1,1654 @@
+/********************************************************************\
+ * gnc-tree-view-owner.c -- GtkTreeView implementation to display *
+ * owners in a GtkTreeView. *
+ * Copyright (C) 2011 Geert Janssens <geert at kobaltwit.be> *
+ * *
+ * 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 the Free Software Foundation; either version 2 of *
+ * the License, or (at your option) any later version. *
+ * *
+ * This program is distributed in the hope that it will be useful, *
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of *
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
+ * GNU General Public License for more details. *
+ * *
+ * You should have received a copy of the GNU General Public License*
+ * along with this program; if not, contact: *
+ * *
+ * Free Software Foundation Voice: +1-617-542-5942 *
+ * 51 Franklin Street, Fifth Floor Fax: +1-617-542-2652 *
+ * Boston, MA 02110-1301, USA gnu at gnu.org *
+ * *
+\********************************************************************/
+
+#include "config.h"
+
+#include <gtk/gtk.h>
+#include <glib/gi18n.h>
+#include <string.h>
+
+#include "gnc-tree-view.h"
+#include "gnc-tree-model-owner.h"
+#include "gnc-tree-view-owner.h"
+
+#include "gncOwner.h"
+#include "gnc-accounting-period.h"
+#include "gnc-commodity.h"
+#include "gnc-component-manager.h"
+#include "gnc-engine.h"
+#include "gnc-glib-utils.h"
+#include "gnc-gobject-utils.h"
+#include "gnc-hooks.h"
+#include "gnc-session.h"
+#include "gnc-icons.h"
+#include "gnc-ui-util.h"
+#include "dialog-utils.h"
+#include "window-main-summarybar.h"
+#include "assistant-utils.h"
+
+#define SAMPLE_OWNER_VALUE "$1,000,000.00"
+
+/** Static Globals *******************************************************/
+
+/* This static indicates the debugging module that this .o belongs to. */
+static QofLogModule log_module = GNC_MOD_GUI;
+
+/** Declarations *********************************************************/
+static void gnc_tree_view_owner_class_init (GncTreeViewOwnerClass *klass);
+static void gnc_tree_view_owner_init (GncTreeViewOwner *view);
+static void gnc_tree_view_owner_finalize (GObject *object);
+
+static void gtvo_update_column_names (GncTreeView *view);
+static void gtvo_currency_changed_cb (void);
+
+static gboolean gnc_tree_view_owner_filter_helper (GtkTreeModel *model,
+ GtkTreeIter *iter,
+ gpointer data);
+
+static void gtvo_setup_column_renderer_edited_cb(GncTreeViewOwner *owner_view,
+ GtkTreeViewColumn *column,
+ GtkCellRenderer *renderer,
+ GncTreeViewOwnerColumnTextEdited col_edited_cb);
+
+typedef struct GncTreeViewOwnerPrivate
+{
+ OwnerViewInfo ovi;
+
+ gnc_tree_view_owner_filter_func filter_fn;
+ gpointer filter_data;
+ GtkFunction filter_destroy;
+
+ GtkTreeViewColumn *name_column;
+ GtkTreeViewColumn *id_column;
+ GtkTreeViewColumn *balance_report_column;
+ GtkTreeViewColumn *notes_column;
+} GncTreeViewOwnerPrivate;
+
+#define GNC_TREE_VIEW_OWNER_GET_PRIVATE(o) \
+ (G_TYPE_INSTANCE_GET_PRIVATE ((o), GNC_TYPE_TREE_VIEW_OWNER, GncTreeViewOwnerPrivate))
+
+
+/************************************************************/
+/* g_object required functions */
+/************************************************************/
+
+static GObjectClass *parent_class = NULL;
+
+GType
+gnc_tree_view_owner_get_type (void)
+{
+ static GType gnc_tree_view_owner_type = 0;
+
+ if (gnc_tree_view_owner_type == 0)
+ {
+ static const GTypeInfo our_info =
+ {
+ sizeof (GncTreeViewOwnerClass),
+ NULL,
+ NULL,
+ (GClassInitFunc) gnc_tree_view_owner_class_init,
+ NULL,
+ NULL,
+ sizeof (GncTreeViewOwner),
+ 0,
+ (GInstanceInitFunc) gnc_tree_view_owner_init
+ };
+
+ gnc_tree_view_owner_type = g_type_register_static (
+ GNC_TYPE_TREE_VIEW, GNC_TREE_VIEW_OWNER_NAME,
+ &our_info, 0);
+ }
+
+ return gnc_tree_view_owner_type;
+}
+
+static void
+gnc_tree_view_owner_class_init (GncTreeViewOwnerClass *klass)
+{
+ GObjectClass *o_class;
+
+ parent_class = g_type_class_peek_parent (klass);
+
+ /* GObject signals */
+ o_class = G_OBJECT_CLASS (klass);
+ o_class->finalize = gnc_tree_view_owner_finalize;
+
+ g_type_class_add_private(klass, sizeof(GncTreeViewOwnerPrivate));
+
+ gnc_hook_add_dangler(HOOK_CURRENCY_CHANGED,
+ (GFunc)gtvo_currency_changed_cb, NULL);
+}
+
+/********************************************************************\
+ * gnc_init_owner_view_info *
+ * initialize an owner view info structure with default values *
+ * *
+ * Args: ovi - structure to initialize *
+ * Returns: nothing *
+\********************************************************************/
+static void
+gnc_init_owner_view_info(OwnerViewInfo *ovi)
+{
+ ovi->show_inactive = FALSE;
+}
+
+static void
+gnc_tree_view_owner_init (GncTreeViewOwner *view)
+{
+ GncTreeViewOwnerPrivate *priv;
+
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(view);
+ gnc_init_owner_view_info(&priv->ovi);
+}
+
+static void
+gnc_tree_view_owner_finalize (GObject *object)
+{
+ GncTreeViewOwner *owner_view;
+ GncTreeViewOwnerPrivate *priv;
+
+ ENTER("view %p", object);
+ g_return_if_fail (object != NULL);
+ g_return_if_fail (GNC_IS_TREE_VIEW_OWNER (object));
+
+ owner_view = GNC_TREE_VIEW_OWNER (object);
+
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(owner_view);
+ if (priv->filter_destroy)
+ {
+ priv->filter_destroy(priv->filter_data);
+ priv->filter_destroy = NULL;
+ }
+ priv->filter_fn = NULL;
+
+ if (G_OBJECT_CLASS (parent_class)->finalize)
+ (* G_OBJECT_CLASS (parent_class)->finalize) (object);
+ LEAVE(" ");
+}
+
+
+/************************************************************
+ * Callbacks *
+ ************************************************************/
+static void
+gnc_tree_view_owner_active_toggled (GtkCellRendererToggle *cell,
+ const gchar *s_path_str,
+ gpointer user_data)
+{
+ GncTreeViewOwner *tree_view;
+ GtkTreePath *s_path;
+ GncOwner *owner;
+ gboolean active;
+
+ /* Change the requested owner */
+ tree_view = user_data;
+ s_path = gtk_tree_path_new_from_string (s_path_str);
+ owner = gnc_tree_view_owner_get_owner_from_path (tree_view, s_path);
+ if (owner)
+ {
+ active = !gtk_cell_renderer_toggle_get_active (cell); // hasn't changed yet.
+ gncOwnerSetActive (owner, active);
+ }
+
+ /* Clean up */
+ gtk_tree_path_free (s_path);
+}
+
+
+/************************************************************/
+/* sort functions */
+/************************************************************/
+
+static GtkTreeModel *
+sort_cb_setup_w_iters (GtkTreeModel *f_model,
+ GtkTreeIter *f_iter_a,
+ GtkTreeIter *f_iter_b,
+ GtkTreeIter *iter_a,
+ GtkTreeIter *iter_b,
+ const GncOwner **owner_a,
+ const GncOwner **owner_b)
+{
+ GtkTreeModel *model;
+
+ model = gtk_tree_model_filter_get_model(GTK_TREE_MODEL_FILTER(f_model));
+ gtk_tree_model_filter_convert_iter_to_child_iter (GTK_TREE_MODEL_FILTER(f_model),
+ iter_a,
+ f_iter_a);
+ gtk_tree_model_filter_convert_iter_to_child_iter (GTK_TREE_MODEL_FILTER(f_model),
+ iter_b,
+ f_iter_b);
+ *owner_a = gnc_tree_model_owner_get_owner (GNC_TREE_MODEL_OWNER(model), iter_a);
+ *owner_b = gnc_tree_model_owner_get_owner (GNC_TREE_MODEL_OWNER(model), iter_b);
+ return model;
+}
+
+static void
+sort_cb_setup (GtkTreeModel *f_model,
+ GtkTreeIter *f_iter_a,
+ GtkTreeIter *f_iter_b,
+ const GncOwner **owner_a,
+ const GncOwner **owner_b)
+{
+ GtkTreeIter iter_a, iter_b;
+
+ sort_cb_setup_w_iters (f_model, f_iter_a, f_iter_b,
+ &iter_a, &iter_b, owner_a, owner_b);
+}
+
+static gint
+sort_by_string (GtkTreeModel *f_model,
+ GtkTreeIter *f_iter1,
+ GtkTreeIter *f_iter2,
+ gpointer user_data)
+{
+ GtkTreeModel *model;
+ GtkTreeIter iter1, iter2;
+ const GncOwner *owner1, *owner2;
+ gchar *str1, *str2;
+ gint column = GPOINTER_TO_INT(user_data);
+ gint result;
+
+ model = sort_cb_setup_w_iters(f_model, f_iter1, f_iter2, &iter1, &iter2, &owner1, &owner2);
+
+ /* Get the strings. */
+ gtk_tree_model_get(GTK_TREE_MODEL(model), &iter1, column, &str1, -1);
+ gtk_tree_model_get(GTK_TREE_MODEL(model), &iter2, column, &str2, -1);
+
+ result = safe_utf8_collate(str1, str2);
+ g_free(str1);
+ g_free(str2);
+ if (result != 0)
+ return result;
+ return gncOwnerCompare(owner1, owner2);
+}
+
+static gint
+sort_by_boolean (GtkTreeModel *f_model,
+ GtkTreeIter *f_iter1,
+ GtkTreeIter *f_iter2,
+ gpointer user_data)
+{
+ GtkTreeModel *model;
+ GtkTreeIter iter1, iter2;
+ const GncOwner *owner1, *owner2;
+ gboolean *bool1, *bool2;
+ gint column = GPOINTER_TO_INT(user_data);
+
+ model = sort_cb_setup_w_iters(f_model, f_iter1, f_iter2, &iter1, &iter2, &owner1, &owner2);
+
+ /* Get the strings. */
+ gtk_tree_model_get(GTK_TREE_MODEL(model), &iter1, column, &bool1, -1);
+ gtk_tree_model_get(GTK_TREE_MODEL(model), &iter2, column, &bool2, -1);
+
+ if (bool1)
+ {
+ if (!bool2)
+ return 1; /* bool1 > bool2 */
+ }
+ else
+ {
+ if (bool2)
+ return -1; /* bool2 > bool1 */
+ }
+ return gncOwnerCompare(owner1, owner2);
+}
+
+static gint
+sort_by_xxx_value (xaccGetBalanceInCurrencyFn fn,
+ gboolean recurse,
+ GtkTreeModel *f_model,
+ GtkTreeIter *f_iter_a,
+ GtkTreeIter *f_iter_b,
+ gpointer user_data)
+{
+ const GncOwner *owner_a, *owner_b;
+ gnc_numeric balance_a, balance_b;
+ gint result;
+
+ /* Find the owners */
+ sort_cb_setup (f_model, f_iter_a, f_iter_b, &owner_a, &owner_b);
+
+ /* Get balances */
+ /* FIXME I'm not aware of any functions to get an owner's "balance" yet.
+ * This should be implemented before this function does anything useful.
+ * The code below is copied from the tree-view-account source to serve
+ * as an example.
+ balance_a = gnc_ui_owner_get_balance_full(fn, owner_a, recurse, NULL, NULL);
+ balance_b = gnc_ui_owner_get_balance_full(fn, owner_b, recurse, NULL, NULL);
+ */
+ balance_a = gnc_numeric_zero();
+ balance_b = gnc_numeric_zero();
+
+ result = gnc_numeric_compare(balance_a, balance_b);
+ if (result != 0)
+ return result;
+ return gncOwnerCompare(owner_a, owner_b);
+}
+
+static gint
+sort_by_balance_value (GtkTreeModel *f_model,
+ GtkTreeIter *f_iter_a,
+ GtkTreeIter *f_iter_b,
+ gpointer user_data)
+{
+ /* FIXME I'm not aware of any functions to get an owner's "balance" yet.
+ * This should be implemented before this function does anything useful.
+ * The code below is copied from the tree-view-account source to serve
+ * as an example.
+ return sort_by_xxx_value (gncOwnerGetBalanceInCurrency, TRUE,
+ f_model, f_iter_a, f_iter_b, user_data);
+ */
+ return sort_by_xxx_value (NULL, TRUE,
+ f_model, f_iter_a, f_iter_b, user_data);
+}
+static gint
+sort_by_xxx_period_value (GtkTreeModel *f_model,
+ GtkTreeIter *f_iter_a,
+ GtkTreeIter *f_iter_b,
+ gboolean recurse)
+{
+ GncOwner *owner1, *owner2;
+ time_t t1, t2;
+ gnc_numeric b1, b2;
+ gint result;
+
+ sort_cb_setup (f_model, f_iter_a, f_iter_b,
+ (const GncOwner **)&owner1, (const GncOwner **)&owner2);
+
+ t1 = gnc_accounting_period_fiscal_start();
+ t2 = gnc_accounting_period_fiscal_end();
+
+ /* FIXME I'm not aware of any functions to get an owner's "balance" yet.
+ * This should be implemented before this function does anything useful.
+ * The code below is copied from the tree-view-account source to serve
+ * as an example.
+ b1 = gncOwnerGetBalanceChangeForPeriod(owner1, t1, t2, recurse);
+ b2 = gncOwnerGetBalanceChangeForPeriod(owner2, t1, t2, recurse);
+ */
+ b1 = gnc_numeric_zero();
+ b2 = gnc_numeric_zero();
+
+ result = gnc_numeric_compare(b1, b2);
+ if (result != 0)
+ return result;
+ return gncOwnerCompare(owner1, owner2);
+}
+
+static gint
+sort_by_balance_period_value (GtkTreeModel *f_model,
+ GtkTreeIter *f_iter_a,
+ GtkTreeIter *f_iter_b,
+ gpointer user_data)
+{
+ return sort_by_xxx_period_value (f_model, f_iter_a, f_iter_b, FALSE);
+}
+
+/************************************************************/
+/* New View Creation */
+/************************************************************/
+
+/*
+ * Create a new owner tree view for one type of owners.
+ * This view will be based on a model that is common to all views of
+ * the same set of books, but will have its own private filter on that
+ * model.
+ */
+GtkTreeView *
+gnc_tree_view_owner_new (GncOwnerType owner_type)
+{
+ GncTreeView *view;
+ GtkTreeModel *model, *f_model, *s_model;
+ const gchar *sample_type, *sample_currency;
+ GncTreeViewOwnerPrivate *priv;
+ GtkTreeViewColumn *tax_info_column;
+ GtkCellRenderer *renderer;
+
+ ENTER(" ");
+ /* Create our view */
+ view = g_object_new (GNC_TYPE_TREE_VIEW_OWNER,
+ "name", "owner_tree", NULL);
+
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(GNC_TREE_VIEW_OWNER (view));
+
+ /* Create/get a pointer to the existing model for this set of books. */
+ model = gnc_tree_model_owner_new (owner_type);
+
+ /* Set up the view private filter layer on the common model. */
+ f_model = gtk_tree_model_filter_new (model, NULL);
+ /* A GncTreeModelOwner is based on a GncTreeModel, which is a
+ * GObject that provides a GtkTreeModel interface. */
+ g_object_unref(G_OBJECT(model));
+
+ /* Set up the view private sort layer on the common model. */
+ s_model = gtk_tree_model_sort_new_with_model(f_model);
+ g_object_unref(G_OBJECT(f_model));
+ gnc_tree_view_set_model (view, s_model);
+ g_object_unref(G_OBJECT(s_model));
+
+ /* Set default visibilities */
+ gtk_tree_view_set_headers_visible (GTK_TREE_VIEW(view), FALSE);
+
+ sample_type = gncOwnerTypeToQofIdType (GNC_OWNER_CUSTOMER);
+ sample_currency = gnc_commodity_get_fullname(gnc_default_currency());
+
+ priv->name_column
+ = gnc_tree_view_add_text_column(view, _("Owner Name"), "name",
+ NULL, "GnuCash Inc.",
+ GNC_TREE_MODEL_OWNER_COL_NAME,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Type"), "type", NULL, sample_type,
+ GNC_TREE_MODEL_OWNER_COL_TYPE,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ priv->id_column
+ = gnc_tree_view_add_text_column(view, _("Owner ID"), "owner-id", NULL,
+ "1-123-1234",
+ GNC_TREE_MODEL_OWNER_COL_ID,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Currency"), "currency", NULL,
+ sample_currency,
+ GNC_TREE_MODEL_OWNER_COL_CURRENCY,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Address Name"), "address-name", NULL,
+ "GnuCash Inc.",
+ GNC_TREE_MODEL_OWNER_COL_ADDRESS_NAME,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Address 1"), "address-1", NULL,
+ "Free Software Foundation",
+ GNC_TREE_MODEL_OWNER_COL_ADDRESS_1,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Address 2"), "address-2", NULL,
+ "51 Franklin Street, Fifth Floor",
+ GNC_TREE_MODEL_OWNER_COL_ADDRESS_2,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Address 3"), "address-3", NULL,
+ "Boston, MA 02110-1301",
+ GNC_TREE_MODEL_OWNER_COL_ADDRESS_3,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Address 4"), "address-4", NULL,
+ "USA",
+ GNC_TREE_MODEL_OWNER_COL_ADDRESS_4,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Phone"), "phone", NULL,
+ "+1-617-542-5942",
+ GNC_TREE_MODEL_OWNER_COL_PHONE,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("Fax"), "fax", NULL,
+ "+1-617-542-2652",
+ GNC_TREE_MODEL_OWNER_COL_FAX,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_text_column(view, _("E-mail"), "email", NULL,
+ "gnu at gnu.org",
+ GNC_TREE_MODEL_OWNER_COL_EMAIL,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_numeric_column(view, _("Balance"), "balance",
+ SAMPLE_OWNER_VALUE,
+ GNC_TREE_MODEL_OWNER_COL_BALANCE,
+ GNC_TREE_MODEL_OWNER_COL_COLOR_BALANCE,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_balance_value);
+ priv->balance_report_column
+ = gnc_tree_view_add_numeric_column(view, _("Balance (Report)"), "balance_report",
+ SAMPLE_OWNER_VALUE,
+ GNC_TREE_MODEL_OWNER_COL_BALANCE_REPORT,
+ GNC_TREE_MODEL_OWNER_COL_COLOR_BALANCE,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_balance_value);
+
+ gnc_tree_view_add_numeric_column(view, _("Balance (Period)"), "balance-period",
+ SAMPLE_OWNER_VALUE,
+ GNC_TREE_MODEL_OWNER_COL_BALANCE_PERIOD,
+ GNC_TREE_MODEL_OWNER_COL_COLOR_BALANCE_PERIOD,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_balance_period_value);
+ priv->notes_column
+ = gnc_tree_view_add_text_column(view, _("Notes"), "notes", NULL,
+ "Sample owner notes.",
+ GNC_TREE_MODEL_OWNER_COL_NOTES,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_string);
+ gnc_tree_view_add_toggle_column (view, _("Active"),
+ /* Translators: This string has a context prefix; the translation
+ must only contain the part after the | character. */
+ Q_("Column letter for 'Active'|A"), "active",
+ GNC_TREE_MODEL_OWNER_COL_ACTIVE,
+ GNC_TREE_VIEW_COLUMN_VISIBLE_ALWAYS,
+ sort_by_boolean,
+ gnc_tree_view_owner_active_toggled);
+
+ /* Update column titles to use the currency name. */
+ gtvo_update_column_names(view);
+
+ /* By default only the first column is visible. */
+ gnc_tree_view_configure_columns(view);
+ gtk_tree_model_filter_set_visible_func (GTK_TREE_MODEL_FILTER (f_model),
+ gnc_tree_view_owner_filter_helper,
+ view,
+ NULL);
+
+ /* Default the sorting to owner name */
+ gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(s_model),
+ GNC_TREE_MODEL_OWNER_COL_NAME,
+ GTK_SORT_ASCENDING);
+
+ gtk_widget_show(GTK_WIDGET(view));
+ LEAVE("%p", view);
+ return GTK_TREE_VIEW(view);
+}
+
+/************************************************************/
+/* Auxiliary Functions */
+/************************************************************/
+
+#define debug_path(fn, path) { \
+ gchar *path_string = gtk_tree_path_to_string(path); \
+ fn("tree path %s", path_string); \
+ g_free(path_string); \
+ }
+
+static GtkTreePath *
+gnc_tree_view_owner_get_path_from_owner (GncTreeViewOwner *view,
+ GncOwner *owner)
+{
+ GtkTreeModel *model, *f_model, *s_model;
+ GtkTreePath *path, *f_path, *s_path;
+
+ ENTER("view %p, owner %p (%s)", view, owner, gncOwnerGetName(owner));
+
+ if (owner == NULL)
+ {
+ LEAVE("no owner");
+ return NULL;
+ }
+
+ /* Reach down to the real model and get a path for this owner */
+ s_model = gtk_tree_view_get_model(GTK_TREE_VIEW(view));
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ model = gtk_tree_model_filter_get_model(GTK_TREE_MODEL_FILTER(f_model));
+ path = gnc_tree_model_owner_get_path_from_owner (GNC_TREE_MODEL_OWNER(model), owner);
+ if (path == NULL)
+ {
+ LEAVE("no path");
+ return NULL;
+ }
+
+ /* convert back to a filtered path */
+ f_path = gtk_tree_model_filter_convert_child_path_to_path (GTK_TREE_MODEL_FILTER (f_model), path);
+ gtk_tree_path_free(path);
+ if (!f_path)
+ {
+ LEAVE("no filter path");
+ return NULL;
+ }
+
+ /* convert back to a sorted path */
+ s_path = gtk_tree_model_sort_convert_child_path_to_path (GTK_TREE_MODEL_SORT (s_model), f_path);
+ gtk_tree_path_free(f_path);
+ debug_path(LEAVE, s_path);
+ return s_path;
+}
+
+static gboolean
+gnc_tree_view_owner_get_iter_from_owner (GncTreeViewOwner *view,
+ GncOwner *owner,
+ GtkTreeIter *s_iter)
+{
+ GtkTreeModel *model, *f_model, *s_model;
+ GtkTreeIter iter, f_iter;
+
+ g_return_val_if_fail(GNC_IS_TREE_VIEW_OWNER(view), FALSE);
+ g_return_val_if_fail(owner != NULL, FALSE);
+ g_return_val_if_fail(s_iter != NULL, FALSE);
+
+ ENTER("view %p, owner %p (%s)", view, owner, gncOwnerGetName(owner));
+
+ /* Reach down to the real model and get an iter for this owner */
+ s_model = gtk_tree_view_get_model(GTK_TREE_VIEW(view));
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ model = gtk_tree_model_filter_get_model(GTK_TREE_MODEL_FILTER(f_model));
+ if (!gnc_tree_model_owner_get_iter_from_owner (
+ GNC_TREE_MODEL_OWNER(model), owner, &iter))
+ {
+ LEAVE("model_get_iter_from_owner failed");
+ return FALSE;
+ }
+
+ /* convert back to a sort iter */
+ gtk_tree_model_filter_convert_child_iter_to_iter (
+ GTK_TREE_MODEL_FILTER(f_model), &f_iter, &iter);
+ gtk_tree_model_sort_convert_child_iter_to_iter (GTK_TREE_MODEL_SORT(s_model),
+ s_iter, &f_iter);
+ LEAVE(" ");
+ return TRUE;
+}
+
+/************************************************************/
+/* Owner Tree View Filter Functions */
+/************************************************************/
+
+/*
+ * Get a copy of the owner view info structure in use by the
+ * specified tree.
+ */
+void
+gnc_tree_view_owner_get_view_info (GncTreeViewOwner *owner_view,
+ OwnerViewInfo *ovi)
+{
+ GncTreeViewOwnerPrivate *priv;
+
+ g_return_if_fail(GNC_IS_TREE_VIEW_OWNER(owner_view));
+ g_return_if_fail(ovi != NULL);
+
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(owner_view);
+
+ *ovi = priv->ovi;
+}
+
+/*
+ * Set the owner view info data in use by the specified tree to
+ * match the callers request.
+ *
+ * DRH - COMPATIBILITY WARNING
+ *
+ * This function does not do anything with the 'include_type' field.
+ * Should there be a automatic filter for backward compatibility
+ * that uses these flags, or should all uses of this be converted to
+ * a GtkTreeModelFilter?
+ *
+ * CAS - For now, I'll try the automatic filter approach by making
+ * this function use GtkTreeModelFilter.
+ */
+void
+gnc_tree_view_owner_set_view_info (GncTreeViewOwner *owner_view,
+ OwnerViewInfo *ovi)
+{
+ GncTreeViewOwnerPrivate *priv;
+ gint i;
+ guint sel_bits = 0;
+
+ ENTER("%p", owner_view);
+ g_return_if_fail(GNC_IS_TREE_VIEW_OWNER(owner_view));
+ g_return_if_fail(ovi != NULL);
+
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(owner_view);
+ priv->ovi = *ovi;
+
+ LEAVE(" ");
+}
+
+static gboolean
+gnc_tree_view_owner_filter_helper (GtkTreeModel *model,
+ GtkTreeIter *iter,
+ gpointer data)
+{
+ GncOwner *owner;
+ GncTreeViewOwner *view = data;
+ GncTreeViewOwnerPrivate *priv;
+
+ g_return_val_if_fail (GNC_IS_TREE_MODEL_OWNER (model), FALSE);
+ g_return_val_if_fail (iter != NULL, FALSE);
+
+ owner = gnc_tree_model_owner_get_owner (
+ GNC_TREE_MODEL_OWNER(model), iter);
+
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(view);
+ if (priv->filter_fn)
+ return priv->filter_fn(owner, priv->filter_data);
+ else return TRUE;
+}
+
+/*
+ * Set an GtkTreeModel visible filter on this owner. This filter will be
+ * called for each owner that the tree is about to show, and the
+ * owner will be passed to the callback function.
+ *
+ * Use NULL as func to remove filter.
+ */
+void
+gnc_tree_view_owner_set_filter (GncTreeViewOwner *view,
+ gnc_tree_view_owner_filter_func func,
+ gpointer data,
+ GtkFunction destroy)
+{
+ GncTreeViewOwnerPrivate *priv;
+
+ ENTER("view %p, filter func %p, data %p, destroy %p",
+ view, func, data, destroy);
+
+ g_return_if_fail(GNC_IS_TREE_VIEW_OWNER(view));
+
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(view);
+ if (priv->filter_destroy)
+ {
+ priv->filter_destroy(priv->filter_data);
+ }
+ priv->filter_destroy = destroy;
+ priv->filter_data = data;
+ priv->filter_fn = func;
+
+ gnc_tree_view_owner_refilter(view);
+ LEAVE(" ");
+}
+
+/*
+ * Forces the entire owner tree to be re-evaluated for visibility.
+ */
+void
+gnc_tree_view_owner_refilter (GncTreeViewOwner *view)
+{
+ GtkTreeModel *f_model, *s_model;
+
+ g_return_if_fail(GNC_IS_TREE_VIEW_OWNER(view));
+
+ s_model = gtk_tree_view_get_model(GTK_TREE_VIEW(view));
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ gtk_tree_model_filter_refilter (GTK_TREE_MODEL_FILTER (f_model));
+}
+
+/************************************************************/
+/* Owner Tree View Get/Set Functions */
+/************************************************************/
+
+/*
+ * Retrieve the selected owner from an owner tree view. The
+ * owner tree must be in single selection mode.
+ */
+GncOwner *
+gnc_tree_view_owner_get_owner_from_path (GncTreeViewOwner *view,
+ GtkTreePath *s_path)
+{
+ GtkTreeModel *model, *f_model, *s_model;
+ GtkTreePath *path, *f_path;
+ GtkTreeIter iter;
+ GncOwner *owner;
+
+ ENTER("view %p", view);
+ g_return_val_if_fail (GNC_IS_TREE_VIEW_OWNER (view), NULL);
+ g_return_val_if_fail (s_path != NULL, NULL);
+
+ s_model = gtk_tree_view_get_model(GTK_TREE_VIEW(view));
+ f_path = gtk_tree_model_sort_convert_path_to_child_path (
+ GTK_TREE_MODEL_SORT (s_model), s_path);
+ if (!f_path)
+ {
+ LEAVE("no filter path");
+ return NULL;
+ }
+
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ path = gtk_tree_model_filter_convert_path_to_child_path (
+ GTK_TREE_MODEL_FILTER (f_model), f_path);
+ gtk_tree_path_free(f_path);
+ if (!path)
+ {
+ LEAVE("no path");
+ return NULL;
+ }
+
+ model = gtk_tree_model_filter_get_model(GTK_TREE_MODEL_FILTER(f_model));
+ if (!gtk_tree_model_get_iter (model, &iter, path))
+ {
+ LEAVE("no iter");
+ return NULL;
+ }
+
+ owner = iter.user_data;
+ gtk_tree_path_free(path);
+ LEAVE("owner %p (%s)", owner, gncOwnerGetName (owner));
+ return owner;
+}
+
+
+GncOwner *
+gnc_tree_view_owner_get_owner_from_iter (GtkTreeModel *s_model,
+ GtkTreeIter *s_iter)
+{
+ GtkTreeModel *model, *f_model;
+ GtkTreeIter iter, f_iter;
+ GncOwner *owner;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_SORT(s_model), NULL);
+ g_return_val_if_fail (s_iter != NULL, NULL);
+
+ ENTER("model %p, iter %p", s_model, s_iter);
+
+ gtk_tree_model_sort_convert_iter_to_child_iter (GTK_TREE_MODEL_SORT(s_model),
+ &f_iter,
+ s_iter);
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ gtk_tree_model_filter_convert_iter_to_child_iter (
+ GTK_TREE_MODEL_FILTER(f_model), &iter, &f_iter);
+ model = gtk_tree_model_filter_get_model(GTK_TREE_MODEL_FILTER(f_model));
+ owner = gnc_tree_model_owner_get_owner (
+ GNC_TREE_MODEL_OWNER(model), &iter);
+ LEAVE("owner %p (%s)", owner, gncOwnerGetName (owner));
+ return owner;
+}
+
+
+/*
+ * Retrieve the selected owner from an owner tree view. The
+ * owner tree must be in single selection mode.
+ */
+GncOwner *
+gnc_tree_view_owner_get_selected_owner (GncTreeViewOwner *view)
+{
+ GtkTreeSelection *selection;
+ GtkTreeModel *f_model, *s_model;
+ GtkTreeIter iter, f_iter, s_iter;
+ GncOwner *owner;
+ GtkSelectionMode mode;
+
+ ENTER("view %p", view);
+ g_return_val_if_fail (GNC_IS_TREE_VIEW_OWNER (view), NULL);
+
+ selection = gtk_tree_view_get_selection (GTK_TREE_VIEW(view));
+ mode = gtk_tree_selection_get_mode(selection);
+ if ((mode != GTK_SELECTION_SINGLE) && (mode != GTK_SELECTION_BROWSE))
+ {
+ return NULL;
+ }
+ if (!gtk_tree_selection_get_selected (selection, &s_model, &s_iter))
+ {
+ LEAVE("no owner, get_selected failed");
+ return FALSE;
+ }
+
+ gtk_tree_model_sort_convert_iter_to_child_iter (GTK_TREE_MODEL_SORT (s_model),
+ &f_iter, &s_iter);
+
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ gtk_tree_model_filter_convert_iter_to_child_iter (
+ GTK_TREE_MODEL_FILTER (f_model), &iter, &f_iter);
+
+ owner = iter.user_data;
+ LEAVE("owner %p (%s)", owner, gncOwnerGetName (owner));
+ return owner;
+}
+
+/*
+ * Selects a single owner in the owner tree view. The owner
+ * tree must be in single selection mode.
+ */
+void
+gnc_tree_view_owner_set_selected_owner (GncTreeViewOwner *view,
+ GncOwner *owner)
+{
+ GtkTreeModel *model, *f_model, *s_model;
+ GtkTreePath *path, *f_path, *s_path, *parent_path;
+ GtkTreeSelection *selection;
+
+ ENTER("view %p, owner %p (%s)", view,
+ owner, gncOwnerGetName (owner));
+ g_return_if_fail (GNC_IS_TREE_VIEW_OWNER (view));
+
+ /* Clear any existing selection. */
+ selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view));
+ gtk_tree_selection_unselect_all (selection);
+
+ if (owner == NULL)
+ return;
+
+ s_model = gtk_tree_view_get_model(GTK_TREE_VIEW(view));
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ model = gtk_tree_model_filter_get_model(GTK_TREE_MODEL_FILTER(f_model));
+
+ path = gnc_tree_model_owner_get_path_from_owner (
+ GNC_TREE_MODEL_OWNER(model), owner);
+ if (path == NULL)
+ {
+ LEAVE("no path");
+ return;
+ }
+ debug_path(DEBUG, path);
+
+ f_path = gtk_tree_model_filter_convert_child_path_to_path (
+ GTK_TREE_MODEL_FILTER (f_model), path);
+ gtk_tree_path_free(path);
+ if (f_path == NULL)
+ {
+ LEAVE("no filter path");
+ return;
+ }
+ debug_path(DEBUG, f_path);
+
+ s_path = gtk_tree_model_sort_convert_child_path_to_path (GTK_TREE_MODEL_SORT (s_model),
+ f_path);
+ gtk_tree_path_free(f_path);
+ if (s_path == NULL)
+ {
+ LEAVE("no sort path");
+ return;
+ }
+
+ gtk_tree_selection_select_path (selection, s_path);
+
+ /* give gtk+ a chance to resize the tree view first by handling pending
+ * configure events */
+ while (gtk_events_pending ())
+ gtk_main_iteration ();
+ gtk_tree_view_scroll_to_cell (GTK_TREE_VIEW(view), s_path, NULL, FALSE, 0.0, 0.0);
+ debug_path(LEAVE, s_path);
+ gtk_tree_path_free(s_path);
+}
+
+/* Information re selection process */
+typedef struct
+{
+ GList* return_list;
+ GncTreeViewOwnerPrivate* priv;
+} GncTreeViewSelectionInfo;
+
+/*
+ * This helper function is called once for each row in the tree view
+ * that is currently selected. Its task is to append the corresponding
+ * owner to the end of a glist.
+ */
+static void
+get_selected_owners_helper (GtkTreeModel *s_model,
+ GtkTreePath *s_path,
+ GtkTreeIter *s_iter,
+ gpointer data)
+{
+ GncTreeViewSelectionInfo *gtvsi = data;
+ GtkTreeModel *f_model;
+ GtkTreeIter iter, f_iter;
+ GncOwner *owner;
+
+ gtk_tree_model_sort_convert_iter_to_child_iter (GTK_TREE_MODEL_SORT (s_model),
+ &f_iter, s_iter);
+
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ gtk_tree_model_filter_convert_iter_to_child_iter (GTK_TREE_MODEL_FILTER (f_model),
+ &iter, &f_iter);
+ owner = iter.user_data;
+
+ /* Only selected if it passes the filter */
+ if (gtvsi->priv->filter_fn == NULL || gtvsi->priv->filter_fn(owner, gtvsi->priv->filter_data))
+ {
+ gtvsi->return_list = g_list_append(gtvsi->return_list, owner);
+ }
+}
+
+/*
+ * Given an owner tree view, return a list of the selected owners. The
+ * owner tree must be in multiple selection mode.
+ *
+ * Note: It is the responsibility of the caller to free the returned
+ * list.
+ */
+GList *
+gnc_tree_view_owner_get_selected_owners (GncTreeViewOwner *view)
+{
+ GtkTreeSelection *selection;
+ GncTreeViewSelectionInfo info;
+
+ g_return_val_if_fail (GNC_IS_TREE_VIEW_OWNER (view), NULL);
+
+ info.return_list = NULL;
+ info.priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(view);
+ selection = gtk_tree_view_get_selection (GTK_TREE_VIEW(view));
+ gtk_tree_selection_selected_foreach(selection, get_selected_owners_helper, &info);
+ return info.return_list;
+}
+
+/*
+ * Given an owner tree view and a list of owners, select those
+ * owners in the tree view.
+ */
+void
+gnc_tree_view_owner_set_selected_owners (GncTreeViewOwner *view,
+ GList *owner_list,
+ gboolean show_last)
+{
+ GtkTreeModel *model, *f_model, *s_model;
+ GtkTreePath *path, *f_path, *s_path, *parent_path;
+ GtkTreeSelection *selection;
+ GList *element;
+ GncOwner *owner;
+
+ g_return_if_fail (GNC_IS_TREE_VIEW_OWNER (view));
+
+ s_model = gtk_tree_view_get_model(GTK_TREE_VIEW(view));
+ f_model = gtk_tree_model_sort_get_model(GTK_TREE_MODEL_SORT(s_model));
+ model = gtk_tree_model_filter_get_model(GTK_TREE_MODEL_FILTER(f_model));
+
+ /* Clear any existing selection. */
+ selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(view));
+ gtk_tree_selection_unselect_all (selection);
+
+ /* Now go select what the user requested. */
+ for (element = owner_list; element; )
+ {
+ owner = element->data;
+ element = g_list_next(element);
+
+ path = gnc_tree_model_owner_get_path_from_owner (GNC_TREE_MODEL_OWNER(model), owner);
+ if (path == NULL)
+ {
+ /*
+ * Oops. Someone must have deleted this owner and not cleaned
+ * up all references to it.
+ */
+ continue;
+ }
+
+ f_path = gtk_tree_model_filter_convert_child_path_to_path (GTK_TREE_MODEL_FILTER (f_model),
+ path);
+ gtk_tree_path_free(path);
+ if (f_path == NULL)
+ continue;
+
+ s_path = gtk_tree_model_sort_convert_child_path_to_path (GTK_TREE_MODEL_SORT (s_model),
+ f_path);
+ gtk_tree_path_free(f_path);
+ if (s_path == NULL)
+ continue;
+
+ gtk_tree_selection_select_path (selection, s_path);
+ if (show_last && (element == NULL))
+ gtk_tree_view_scroll_to_cell (GTK_TREE_VIEW(view), s_path, NULL, FALSE, 0.0, 0.0);
+ gtk_tree_path_free(s_path);
+ }
+}
+
+
+/*
+ * Retrieve the owner currently under the cursor.
+ */
+GncOwner *
+gnc_tree_view_owner_get_cursor_owner (GncTreeViewOwner *view)
+{
+ GtkTreeModel *s_model;
+ GtkTreePath *s_path;
+ GncOwner *owner;
+
+ ENTER("view %p", view);
+ g_return_val_if_fail (GNC_IS_TREE_VIEW_OWNER (view), NULL);
+
+ s_model = gtk_tree_view_get_model (GTK_TREE_VIEW(view));
+ gtk_tree_view_get_cursor (GTK_TREE_VIEW(view), &s_path, NULL);
+ if (!s_path)
+ {
+ LEAVE("no owner");
+ return NULL;
+ }
+
+ owner = gnc_tree_view_owner_get_owner_from_path (view, s_path);
+ gtk_tree_path_free(s_path);
+ LEAVE("owner %p (%s)", owner, gncOwnerGetName (owner));
+ return owner;
+}
+
+
+/************************************************************/
+/* Owner Tree View Add Column Functions */
+/************************************************************/
+
+static void
+gtvo_update_column_name (GtkTreeViewColumn *column,
+ const gchar *fmt,
+ const gchar *mnemonic)
+{
+ gchar *name;
+
+ g_return_if_fail(column);
+
+ name = g_strdup_printf(fmt, mnemonic);
+ gtk_tree_view_column_set_title(column, name);
+ g_free(name);
+}
+
+
+static void
+gtvo_update_column_names (GncTreeView *view)
+{
+ GncTreeViewOwnerPrivate *priv;
+ const gchar *mnemonic;
+
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(view);
+ mnemonic = gnc_commodity_get_mnemonic(gnc_default_report_currency());
+
+ gtvo_update_column_name(priv->balance_report_column,
+ /* Translators: %s is a currency mnemonic.*/
+ _("Balance (%s)"), mnemonic);
+ gnc_tree_view_set_show_column_menu(view, FALSE);
+ gnc_tree_view_set_show_column_menu(view, TRUE);
+}
+
+
+static void
+gtvo_currency_changed_cb (void)
+{
+ const GList *views, *ptr;
+
+ views = gnc_gobject_tracking_get_list (GNC_TREE_VIEW_OWNER_NAME);
+ for (ptr = views; ptr; ptr = g_list_next(ptr))
+ {
+ gtvo_update_column_names (ptr->data);
+ }
+}
+/* This function implements a custom mapping between an owner's KVP
+ * and the cell renderer's 'text' property. */
+static void
+owner_cell_kvp_data_func (GtkTreeViewColumn *tree_column,
+ GtkCellRenderer *cell,
+ GtkTreeModel *s_model,
+ GtkTreeIter *s_iter,
+ gpointer key)
+{
+ GncOwner *owner;
+ kvp_frame * frame;
+
+ g_return_if_fail (GTK_IS_TREE_MODEL_SORT (s_model));
+ owner = gnc_tree_view_owner_get_owner_from_iter(s_model, s_iter);
+ frame = gncOwnerGetSlots(owner);
+
+ g_object_set (G_OBJECT (cell),
+ "text", kvp_frame_get_string(frame, (gchar *)key),
+ "xalign", 0.0,
+ NULL);
+
+}
+
+
+GtkTreeViewColumn *
+gnc_tree_view_owner_add_kvp_column (GncTreeViewOwner *view,
+ const gchar *column_title,
+ const gchar *kvp_key)
+{
+ GtkCellRenderer *renderer;
+ GtkTreeViewColumn *column;
+
+ g_return_val_if_fail (GNC_IS_TREE_VIEW_OWNER (view), NULL);
+ g_return_val_if_fail (kvp_key != NULL, NULL);
+
+ column = gnc_tree_view_add_text_column(GNC_TREE_VIEW(view), column_title,
+ kvp_key, NULL, "Sample text",
+ -1, -1, NULL);
+
+ /* This new kvp column has only had one renderer added to it so
+ * far. Find that renderer. */
+ renderer = gnc_tree_view_column_get_renderer(column);
+ g_object_set (G_OBJECT (renderer), "xalign", 1.0, NULL);
+
+ gtk_tree_view_column_set_cell_data_func (column, renderer,
+ owner_cell_kvp_data_func,
+ g_strdup(kvp_key), g_free);
+ return column;
+}
+
+static void col_edited_helper(GtkCellRendererText *cell, gchar *path_string,
+ gchar *new_text, gpointer _s_model)
+{
+ GncOwner *owner;
+ GtkTreeModel *s_model;
+ GtkTreeIter s_iter;
+ GncTreeViewOwnerColumnTextEdited col_edited_cb;
+ GtkTreeViewColumn *col;
+
+ col_edited_cb = g_object_get_data(G_OBJECT(cell),
+ "column_edited_callback");
+ col = GTK_TREE_VIEW_COLUMN(g_object_get_data(G_OBJECT(cell),
+ "column_view"));
+ s_model = GTK_TREE_MODEL(_s_model);
+
+ if (!gtk_tree_model_get_iter_from_string(s_model, &s_iter, path_string))
+ return;
+
+ owner = gnc_tree_view_owner_get_owner_from_iter(s_model, &s_iter);
+ col_edited_cb(owner, col, new_text);
+}
+
+static void col_source_helper(GtkTreeViewColumn *col, GtkCellRenderer *cell,
+ GtkTreeModel *s_model, GtkTreeIter *s_iter,
+ gpointer _col_source_cb)
+{
+ GncOwner *owner;
+ gchar *text;
+ GncTreeViewOwnerColumnSource col_source_cb;
+
+ g_return_if_fail (GTK_IS_TREE_MODEL_SORT (s_model));
+ col_source_cb = (GncTreeViewOwnerColumnSource) _col_source_cb;
+ owner = gnc_tree_view_owner_get_owner_from_iter(s_model, s_iter);
+ text = col_source_cb(owner, col, cell);
+ g_object_set (G_OBJECT (cell), "text", text, "xalign", 1.0, NULL);
+ g_free(text);
+}
+
+/**
+ * If col_edited_cb is null, the editing callback (helper) will be
+ * effectively disconnected.
+ **/
+void
+gtvo_setup_column_renderer_edited_cb(GncTreeViewOwner *owner_view,
+ GtkTreeViewColumn *column,
+ GtkCellRenderer *renderer,
+ GncTreeViewOwnerColumnTextEdited col_edited_cb)
+{
+ GtkTreeModel *s_model;
+
+ if (col_edited_cb == NULL)
+ {
+ g_object_set(G_OBJECT(renderer), "editable", FALSE, NULL);
+ g_object_set_data(G_OBJECT(renderer), "column_edited_callback", col_edited_cb);
+ s_model = gtk_tree_view_get_model(GTK_TREE_VIEW(owner_view));
+ g_signal_handlers_disconnect_by_func(G_OBJECT(renderer), col_edited_cb, s_model);
+ g_object_set_data(G_OBJECT(renderer), "column_view", column);
+ }
+ else
+ {
+ g_object_set(G_OBJECT(renderer), "editable", TRUE, NULL);
+ g_object_set_data(G_OBJECT(renderer), "column_edited_callback",
+ col_edited_cb);
+ s_model = gtk_tree_view_get_model(GTK_TREE_VIEW(owner_view));
+ g_signal_connect(G_OBJECT(renderer), "edited",
+ (GCallback) col_edited_helper, s_model);
+ g_object_set_data(G_OBJECT(renderer), "column_view", column);
+ }
+}
+
+GtkTreeViewColumn *
+gnc_tree_view_owner_add_custom_column(GncTreeViewOwner *owner_view,
+ const gchar *column_title,
+ GncTreeViewOwnerColumnSource
+ col_source_cb,
+ GncTreeViewOwnerColumnTextEdited
+ col_edited_cb)
+{
+ GtkCellRenderer *renderer;
+ GtkTreeViewColumn *column;
+
+ g_return_val_if_fail (GNC_IS_TREE_VIEW_OWNER (owner_view), NULL);
+
+ renderer = gtk_cell_renderer_text_new ();
+ g_object_set (G_OBJECT (renderer), "xalign", 1.0, NULL);
+
+ column = gtk_tree_view_column_new_with_attributes (column_title,
+ renderer, NULL);
+ if (col_edited_cb)
+ {
+ gtvo_setup_column_renderer_edited_cb(owner_view, column,
+ renderer, col_edited_cb);
+ }
+ gtk_tree_view_column_set_cell_data_func (column, renderer,
+ col_source_helper,
+ col_source_cb, NULL);
+ gnc_tree_view_append_column (GNC_TREE_VIEW(owner_view), column);
+ return column;
+}
+
+
+/* BEGIN FILTER FUNCTIONS */
+#define FILTER_TREE_VIEW "types_tree_view"
+
+/** This function tells the owner tree view whether or not to filter
+ * out a particular owner. Owners may be filtered if the user
+ * has decided not to display inactive owners, or if the
+ * user has requested that owners with a zero total not be shown.
+ *
+ * @param owner The owner that is being evaluated.
+ *
+ * @param user_data A pointer to the OwnerFilterDialog struct.
+ *
+ * @return TRUE if the owner should be visible. FALSE if the
+ * owner should be hidden. */
+gboolean
+gnc_plugin_page_owner_tree_filter_owners (GncOwner *owner,
+ gpointer user_data)
+{
+ OwnerFilterDialog *fd = user_data;
+ gnc_numeric total;
+
+ ENTER("owner %p:%s", owner, gncOwnerGetName(owner));
+
+ if (!fd->show_inactive && !gncOwnerGetActive (owner))
+ {
+ LEAVE(" hide: inactive");
+ return FALSE;
+ }
+
+ if (!fd->show_zero_total)
+ {
+ /* FIXME I'm not aware of any functions to get an owner's "balance" yet.
+ * This should be implemented before this function does anything useful.
+ * The code below is copied from the tree-view-account source to serve
+ * as an example.
+ total = gncOwnerGetBalanceInCurrency (owner, NULL, TRUE);
+ */
+ total = gnc_numeric_zero();
+ if (gnc_numeric_zero_p(total))
+ {
+ LEAVE(" hide: zero balance");
+ return FALSE;
+ }
+ }
+
+ return TRUE;
+}
+
+/** The "only show active" button in the Filter dialog changed state.
+ * Update the page to reflect these changes.
+ *
+ * @param button The GtkCheckButton that was toggled.
+ *
+ * @param fd A pointer to the owner filter dialog struct. */
+void
+gppot_filter_show_inactive_toggled_cb (GtkToggleButton *button,
+ OwnerFilterDialog *fd)
+{
+ g_return_if_fail(GTK_IS_TOGGLE_BUTTON(button));
+
+ ENTER("button %p", button);
+ fd->show_inactive = gtk_toggle_button_get_active(button);
+ gnc_tree_view_owner_refilter(fd->tree_view);
+ LEAVE("show_inactive %d", fd->show_inactive);
+}
+
+/** The "show zero totals" button in the Filter dialog changed state.
+ * Update the page to reflect these changes.
+ *
+ * @param button The GtkCheckButton that was toggled.
+ *
+ * @param fd A pointer to the owner filter dialog struct. */
+void
+gppot_filter_show_zero_toggled_cb (GtkToggleButton *button,
+ OwnerFilterDialog *fd)
+{
+ g_return_if_fail(GTK_IS_TOGGLE_BUTTON(button));
+
+ ENTER("button %p", button);
+ fd->show_zero_total = gtk_toggle_button_get_active(button);
+ gnc_tree_view_owner_refilter(fd->tree_view);
+ LEAVE("show_zero %d", fd->show_zero_total);
+}
+
+/** The Filter dialog was closed. Check to see if this was done via
+ * the OK button. If so, make the changes permanent. If not, revert
+ * any changes.
+ *
+ * @param dialog A pointer to the "Filter By" dialog.
+ *
+ * @param response The response code from closing the dialog.
+ *
+ * @param fd A pointer to the owner filter dialog struct. */
+void
+gppot_filter_response_cb (GtkWidget *dialog,
+ gint response,
+ OwnerFilterDialog *fd)
+{
+ GtkWidget *view;
+ gpointer gptemp;
+
+ g_return_if_fail(GTK_IS_DIALOG(dialog));
+
+ ENTER("dialog %p, response %d", dialog, response);
+ view = gnc_glade_lookup_widget(dialog, FILTER_TREE_VIEW);
+
+ if (response != GTK_RESPONSE_OK)
+ {
+ fd->show_inactive = fd->original_show_inactive;
+ fd->show_zero_total = fd->original_show_zero_total;
+ gnc_tree_view_owner_refilter(fd->tree_view);
+ }
+
+ /* Clean up and delete dialog */
+ gptemp = (gpointer *)fd->dialog;
+ g_atomic_pointer_compare_and_exchange(&gptemp,
+ dialog, NULL);
+ fd->dialog = gptemp;
+ gtk_widget_destroy(dialog);
+ LEAVE("");
+}
+
+void
+owner_filter_dialog_create(OwnerFilterDialog *fd, GncPluginPage *page)
+{
+ GtkWidget *dialog, *button;
+ GtkBuilder *builder;
+ gchar *title;
+
+ ENTER("(fd %p, page %p)", fd, page);
+
+ if (fd->dialog)
+ {
+ gtk_window_present(GTK_WINDOW(fd->dialog));
+ LEAVE("existing dialog");
+ return;
+ }
+
+ /* Create the dialog */
+ builder = gtk_builder_new();
+ gnc_builder_add_from_file (builder, "owner.ui", "Filter By");
+ dialog = GTK_WIDGET(gtk_builder_get_object (builder, "Filter By"));
+ fd->dialog = dialog;
+ gtk_window_set_transient_for(GTK_WINDOW(dialog),
+ GTK_WINDOW(GNC_PLUGIN_PAGE(page)->window));
+ /* Translators: The %s is the name of the plugin page */
+ title = g_strdup_printf(_("Filter %s by..."),
+ gnc_plugin_page_get_page_name(GNC_PLUGIN_PAGE(page)));
+ gtk_window_set_title(GTK_WINDOW(dialog), title);
+ g_free(title);
+
+ /* Remember current state */
+ fd->original_show_inactive = fd->show_inactive;
+ fd->original_show_zero_total = fd->show_zero_total;
+
+ /* Update the dialog widgets for the current state */
+ button = GTK_WIDGET(gtk_builder_get_object (builder, "show_inactive"));
+ gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON(button),
+ fd->show_inactive);
+ button = GTK_WIDGET(gtk_builder_get_object (builder, "show_zero"));
+ gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON(button),
+ fd->show_zero_total);
+
+ /* Wire up the rest of the callbacks */
+ gtk_builder_connect_signals (builder, fd);
+ g_object_unref(G_OBJECT(builder));
+
+ /* Show it */
+ gtk_widget_show_all (dialog);
+ LEAVE(" ");
+}
+
+#define OWNER_SELECTED_LABEL "SelectedOwner"
+#define SHOW_INACTIVE_LABEL "ShowInactive"
+#define SHOW_ZERO_LABEL "ShowZeroTotal"
+
+typedef struct foo
+{
+ GKeyFile *key_file;
+ const gchar *group_name;
+} bar_t;
+
+/** Save information about the selected row. Its job is to write the
+ * full owner name of the row out to the state file.
+ *
+ * @param view A pointer to the GtkTreeView embedded in an
+ * owner tree page.
+ *
+ * @param path A pointer to a particular entry in the tree.
+ *
+ * @param data A pointer to a data structure holding the information
+ * related to the state file. */
+static void
+tree_save_selected_row (GncTreeViewOwner *view,
+ gpointer user_data)
+{
+ GncOwner *owner;
+ GncOwnerType owner_type;
+ bar_t *bar = user_data;
+ const gchar *owner_name;
+
+ owner = gnc_tree_view_owner_get_selected_owner(view);
+ if (owner == NULL)
+ return;
+
+ owner_name = gncOwnerGetName (owner);
+ if (owner_name == NULL)
+ return;
+
+ g_key_file_set_string(bar->key_file, bar->group_name, OWNER_SELECTED_LABEL,
+ owner_name);
+}
+
+void
+gnc_tree_view_owner_save(GncTreeViewOwner *view,
+ OwnerFilterDialog *fd,
+ GKeyFile *key_file, const gchar *group_name)
+{
+ bar_t bar;
+
+ g_return_if_fail (key_file != NULL);
+ g_return_if_fail (group_name != NULL);
+
+ ENTER("view %p, key_file %p, group_name %s", view, key_file,
+ group_name);
+
+ g_key_file_set_boolean(key_file, group_name, SHOW_INACTIVE_LABEL,
+ fd->show_inactive);
+ g_key_file_set_boolean(key_file, group_name, SHOW_ZERO_LABEL,
+ fd->show_zero_total);
+
+ bar.key_file = key_file;
+ bar.group_name = group_name;
+ tree_save_selected_row(view, &bar);
+ LEAVE(" ");
+
+}
+
+/** Select the row in the tree that was selected when the user last
+ * quit gnucash. Its job is to map from owner name to tree row and
+ * select the row.
+ *
+ * @param tree A pointer to the GncTreeViewOwner embedded.
+ *
+ * @param owner_name A pointer to the full owner name. */
+static void
+tree_restore_selected_row (GncTreeViewOwner *view,
+ GncOwnerType owner_type,
+ const gchar *owner_guid_str)
+{
+ GncOwner *owner=gncOwnerCreate();
+ QofBook *book;
+ GncGUID owner_guid;
+
+ book = qof_session_get_book (gnc_get_current_session());
+ if (string_to_guid (owner_guid_str, &owner_guid))
+ if (gncOwnerGetOwnerFromTypeGuid (book, owner, gncOwnerTypeToQofIdType(owner_type), &owner_guid))
+ gnc_tree_view_owner_set_selected_owner(view, owner);
+}
+
+void
+gnc_tree_view_owner_restore(GncTreeViewOwner *view,
+ OwnerFilterDialog *fd,
+ GKeyFile *key_file, const gchar *group_name,
+ GncOwnerType owner_type)
+{
+ GError *error = NULL;
+ gchar *key, *value;
+ gint i, count;
+ gboolean show;
+
+ /* Filter information. Ignore missing keys. */
+ show = g_key_file_get_boolean(key_file, group_name, SHOW_INACTIVE_LABEL, &error);
+ if (error)
+ {
+ g_warning("error reading group %s key %s: %s",
+ group_name, SHOW_INACTIVE_LABEL, error->message);
+ g_error_free(error);
+ error = NULL;
+ show = TRUE;
+ }
+ fd->show_inactive = show;
+
+ show = g_key_file_get_boolean(key_file, group_name, SHOW_ZERO_LABEL, &error);
+ if (error)
+ {
+ g_warning("error reading group %s key %s: %s",
+ group_name, SHOW_ZERO_LABEL, error->message);
+ g_error_free(error);
+ error = NULL;
+ show = TRUE;
+ }
+ fd->show_zero_total = show;
+
+ /* Selected owner (if any) */
+ value = g_key_file_get_string(key_file, group_name, OWNER_SELECTED_LABEL, NULL);
+ if (value)
+ {
+ tree_restore_selected_row(view, owner_type, value);
+ g_free(value);
+ }
+
+ /* Update tree view for any changes */
+ gnc_tree_view_owner_refilter(view);
+}
+
+void
+gnc_tree_view_owner_name_edited_cb(GncOwner *owner, GtkTreeViewColumn *col, const gchar *new_name)
+{
+ if (safe_strcmp(gncOwnerGetName(owner), new_name) == 0)
+ return;
+ gncOwnerSetName(owner, new_name);
+}
+
+static void
+gtvo_set_column_editor(GncTreeViewOwner *view,
+ GtkTreeViewColumn *column,
+ GncTreeViewOwnerColumnTextEdited edited_cb)
+{
+ GList *renderers_orig, *renderers;
+ GtkCellRenderer *renderer;
+
+ // look for the first text-renderer; on the 0th column of the owner tree,
+ // there are two renderers: pixbuf and text. So find the text one.
+ for (renderers_orig = renderers = gtk_tree_view_column_get_cell_renderers(column);
+ renderers && !GTK_IS_CELL_RENDERER_TEXT(renderers->data);
+ renderers = renderers->next);
+ renderer = GTK_CELL_RENDERER(renderers->data);
+ g_list_free(renderers_orig);
+ g_return_if_fail(renderer != NULL);
+ gtvo_setup_column_renderer_edited_cb(GNC_TREE_VIEW_OWNER(view), column, renderer, edited_cb);
+}
+
+void
+gnc_tree_view_owner_set_name_edited(GncTreeViewOwner *view,
+ GncTreeViewOwnerColumnTextEdited edited_cb)
+{
+ GncTreeViewOwnerPrivate *priv;
+ priv = GNC_TREE_VIEW_OWNER_GET_PRIVATE(view);
+ gtvo_set_column_editor(view, priv->name_column, edited_cb);
+}
Added: gnucash/trunk/src/gnome-utils/gnc-tree-view-owner.h
===================================================================
--- gnucash/trunk/src/gnome-utils/gnc-tree-view-owner.h (rev 0)
+++ gnucash/trunk/src/gnome-utils/gnc-tree-view-owner.h 2011-05-11 21:51:03 UTC (rev 20620)
@@ -0,0 +1,383 @@
+/********************************************************************\
+ * gnc-tree-view-owner.h -- GtkTreeView implementation to display *
+ * owners in a GtkTreeView. *
+ * Copyright (C) 2011 Geert Janssens <geert at kobaltwit.be> *
+ * *
+ * 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 the Free Software Foundation; either version 2 of *
+ * the License, or (at your option) any later version. *
+ * *
+ * This program is distributed in the hope that it will be useful, *
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of *
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
+ * GNU General Public License for more details. *
+ * *
+ * You should have received a copy of the GNU General Public License*
+ * along with this program; if not, contact: *
+ * *
+ * Free Software Foundation Voice: +1-617-542-5942 *
+ * 51 Franklin Street, Fifth Floor Fax: +1-617-542-2652 *
+ * Boston, MA 02110-1301, USA gnu at gnu.org *
+ * *
+\********************************************************************/
+
+/** @addtogroup GUI
+ @{ */
+/** @addtogroup GuiTreeModel
+ * @{ */
+/** @file gnc-tree-view-owner.h
+ @brief GtkTreeView implementation for gnucash owner tree.
+ @author Copyright (C) 2003,2005,2006 David Hampton <hampton at employees.org>
+*/
+
+#ifndef __GNC_TREE_VIEW_OWNER_H
+#define __GNC_TREE_VIEW_OWNER_H
+
+#include <gtk/gtk.h>
+#include "gncOwner.h"
+#include "gnc-tree-view.h"
+
+#include "gnc-ui-util.h"
+#include "gnc-plugin-page.h"
+
+G_BEGIN_DECLS
+
+/* type macros */
+#define GNC_TYPE_TREE_VIEW_OWNER (gnc_tree_view_owner_get_type ())
+#define GNC_TREE_VIEW_OWNER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GNC_TYPE_TREE_VIEW_OWNER, GncTreeViewOwner))
+#define GNC_TREE_VIEW_OWNER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GNC_TYPE_TREE_VIEW_OWNER, GncTreeViewOwnerClass))
+#define GNC_IS_TREE_VIEW_OWNER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GNC_TYPE_TREE_VIEW_OWNER))
+#define GNC_IS_TREE_VIEW_OWNER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GNC_TYPE_TREE_VIEW_OWNER))
+#define GNC_TREE_VIEW_OWNER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GNC_TYPE_TREE_VIEW_OWNER, GncTreeViewOwnerClass))
+#define GNC_TREE_VIEW_OWNER_NAME "GncTreeViewOwner"
+
+/* typedefs & structures */
+typedef struct OwnerViewInfo_s OwnerViewInfo;
+
+
+struct OwnerViewInfo_s
+{
+ gboolean show_inactive;
+};
+
+
+typedef struct
+{
+ GncTreeView gnc_tree_view;
+ int stamp;
+} GncTreeViewOwner;
+
+typedef struct
+{
+ GncTreeViewClass gnc_tree_view;
+} GncTreeViewOwnerClass;
+
+typedef struct
+{
+ GtkWidget *dialog;
+ GncTreeViewOwner *tree_view;
+ gboolean show_inactive;
+ gboolean original_show_inactive;
+ gboolean show_zero_total;
+ gboolean original_show_zero_total;
+} OwnerFilterDialog;
+
+void owner_filter_dialog_create(OwnerFilterDialog *fd,
+ GncPluginPage *page);
+
+gboolean gnc_plugin_page_owner_tree_filter_owners (GncOwner *owner,
+ gpointer user_data);
+
+/* "Filter By" dialog callbacks */
+void gppot_filter_show_inactive_toggled_cb (GtkToggleButton *togglebutton,
+ OwnerFilterDialog *fd);
+void gppot_filter_show_zero_toggled_cb (GtkToggleButton *togglebutton,
+ OwnerFilterDialog *fd);
+void gppot_filter_response_cb (GtkWidget *dialog, gint response,
+ OwnerFilterDialog *fd);
+
+/* Saving/Restoring */
+void gnc_tree_view_owner_save(GncTreeViewOwner *tree_view,
+ OwnerFilterDialog *fd,
+ GKeyFile *key_file, const gchar *group_name);
+void gnc_tree_view_owner_restore(GncTreeViewOwner *view,
+ OwnerFilterDialog *fd,
+ GKeyFile *key_file,
+ const gchar *group_name,
+ GncOwnerType owner_type);
+
+
+/* Get the GType for an GncTreeViewOwner object. */
+GType gnc_tree_view_owner_get_type (void);
+
+
+/** @name Owner Tree View Constructor
+ @{ */
+
+/** Create a new owner tree view for one type of owners.
+ *
+ * @param owner_type The type of owners to use in the view.
+ *
+ * @return A pointer to a new owner tree view.
+ */
+GtkTreeView *gnc_tree_view_owner_new (GncOwnerType owner_type);
+
+/** @} */
+
+
+/** @name Owner Tree View Configuration
+ @{ */
+
+typedef gchar * (*GncTreeViewOwnerColumnSource) (GncOwner *owner,
+ GtkTreeViewColumn *col,
+ GtkCellRenderer *cell);
+
+typedef void (*GncTreeViewOwnerColumnTextEdited) (GncOwner *owner,
+ GtkTreeViewColumn *col,
+ const gchar *new_text);
+
+
+/** Add a new custom column to the set of columns in an owner tree
+ * view. This column will be visible as soon as it is added and will
+ * query the provided functions to determine what data to display.
+ * The TreeView will own the resulting TreeViewColumn, but caller may
+ * set any additional properties they wish.
+ *
+ * @param view A pointer to an owner tree view.
+ *
+ * @param column_title The title for this new column.
+ *
+ * @param source_cb A callback function that is expected to provide
+ * the data to be displayed.
+ *
+ * @param edited_cb A callback function that will be called if the
+ * user edits the displayed data.
+ */
+GtkTreeViewColumn * gnc_tree_view_owner_add_custom_column(
+ GncTreeViewOwner *view, const gchar *column_title,
+ GncTreeViewOwnerColumnSource source_cb,
+ GncTreeViewOwnerColumnTextEdited edited_cb);
+
+void gnc_tree_view_owner_set_name_edited(GncTreeViewOwner *view,
+ GncTreeViewOwnerColumnTextEdited edited_cb);
+void gnc_tree_view_owner_name_edited_cb(GncOwner *owner, GtkTreeViewColumn *col, const gchar *new_name);
+
+/** Add a new column to the set of columns in an owner tree view.
+ * This column will be visible as soon as it is added and will
+ * display the contents of the specified KVP slot.
+ *
+ * @param view A pointer to an owner tree view.
+ *
+ * @param column_title The title for this new column.
+ *
+ * @param kvp_key The lookup key to use for looking up data in the
+ * owner KVP structures. The value associated with this key is what
+ * will be displayed in the column.
+ */
+GtkTreeViewColumn *
+gnc_tree_view_owner_add_kvp_column (GncTreeViewOwner *view,
+ const gchar *column_title,
+ const gchar *kvp_key);
+
+/** @} */
+
+
+/** @name Owner Tree View Filtering
+ @{ */
+
+/** Given pointers to an owner tree and old style filter block, this
+ * function will copy the current configuration of the owner tree
+ * widget into the data block. This may be used in conjunction with
+ * the gnc_tree_view_owner_set_view_info function to modify the
+ * filters on an existing owner tree.
+ *
+ * @param owner_view A pointer to an owner tree view.
+ *
+ * @param avi A pointer to an old style filter block to fill in.
+ */
+void gnc_tree_view_owner_get_view_info (GncTreeViewOwner *owner_view,
+ OwnerViewInfo *avi);
+
+/** Given pointers to an owner tree and old style filter block, this
+ * function will applies the settings specified to the current
+ * configuration of the owner tree widget. This may be used in
+ * conjunction with the gnc_tree_view_owner_get_view_info function
+ * to modify the filters on an existing owner tree.
+ *
+ * @param owner_view A pointer to an owner tree view.
+ *
+ * @param avi A pointer to an old style filter block to apply to the
+ * view.
+ */
+void gnc_tree_view_owner_set_view_info (GncTreeViewOwner *owner_view,
+ OwnerViewInfo *avi);
+
+
+/** This is the description of a filter function used by the owner tree.
+ *
+ * @param owner The owner to be tested.
+ *
+ * @param data The data provided when the filter function was added.
+ *
+ * @return TRUE if the owner should be displayed.
+ */
+typedef gboolean (*gnc_tree_view_owner_filter_func)(GncOwner *owner, gpointer data);
+
+
+/** This function attaches a filter function to the given owner
+ * tree. This function will be called for each owner that the view
+ * thinks should possibly show. The filter may perform any actions
+ * necessary on the owner to decide whether it should be shown or
+ * not. (I.E. Check type, placeholder status, etc.) If the filter
+ * returns TRUE then the owner will be displayed.
+ *
+ * @param owner_view A pointer to an owner tree view.
+ *
+ * @param func A filtration function that is called on individual
+ * elements in the tree. If this function returns TRUE, the owner
+ * will be displayed.
+ *
+ * @param data A data block passed into each instance of the function.
+ *
+ * @param destroy A function to destroy the data block. This
+ * function will be called when the filter is destroyed. may be
+ * NULL.
+ */
+void gnc_tree_view_owner_set_filter (GncTreeViewOwner *owner_view,
+ gnc_tree_view_owner_filter_func func,
+ gpointer data,
+ GtkFunction destroy);
+
+
+/** This function forces the owner tree filter to be evaluated. It
+ * may be necessary to call this function if the initial state of the
+ * view is incorrect. This appears to only be necessary if the
+ * filter affects one of the top level owners in gnucash.
+ *
+ * @note This calls a function in gtk that is annotated in the
+ * sources as being slow. You have been warned.
+ *
+ * @param view A pointer to an owner tree view.
+ */
+void gnc_tree_view_owner_refilter (GncTreeViewOwner *view);
+/** @} */
+
+
+/** @name Owner Tree View Get/Set Functions
+ @{ */
+
+/** This function returns the owner associated with the specified
+ * path. This function is useful in selection callbacks on an
+ * owner tree widget.
+ *
+ * @param view A pointer to an owner tree view.
+ *
+ * @param path A path specifying a node in the owner tree.
+ *
+ * @return The owner associated with this path.
+ */
+GncOwner * gnc_tree_view_owner_get_owner_from_path (GncTreeViewOwner *view,
+ GtkTreePath *path);
+
+
+/** This function returns the owner associated with the specified
+ * iter. This function is useful in selection callbacks on an
+ * owner tree widget.
+ *
+ * @param model The model provided to the callback function.
+ *
+ * @param iter The iter provided to the callback function.
+ *
+ * @return The owner associated with this iter.
+ */
+GncOwner * gnc_tree_view_owner_get_owner_from_iter (GtkTreeModel *model,
+ GtkTreeIter *iter);
+
+
+/** This function returns the owner in the owner tree view at the
+ * current location of the cursor. (The outline frame. Usually is
+ * selected and therefore filled in, but not always.)
+ *
+ * @param view A pointer to an owner tree view.
+ *
+ * @return The owner at the cursor.
+ */
+GncOwner * gnc_tree_view_owner_get_cursor_owner (GncTreeViewOwner *view);
+
+
+/** This function returns the owner associated with the selected
+ * item in the owner tree view.
+ *
+ * @note It only makes sense to call this function when the owner
+ * tree is set to select a single item. There is a different
+ * function to use when the tree supports multiple selections.
+ *
+ * @param view A pointer to an owner tree view.
+ *
+ * @return The selected owner, or NULL if no owner was selected.
+ */
+GncOwner * gnc_tree_view_owner_get_selected_owner (GncTreeViewOwner *view);
+
+
+/** This function selects an owner in the owner tree view. All
+ * other owners will be unselected. In addition, this function
+ * collapses the entitre tree and then expands only the path to the
+ * selected owner, making the item easy to find. In general, this
+ * routine only need be called when initially putting up a window
+ * containing an owner tree view widget.
+ *
+ * @note It only makes sense to call this function when the owner
+ * tree is set to select a single item. There is a different
+ * function to use when the tree supports multiple selections.
+ *
+ * @param view A pointer to an owner tree view.
+ *
+ * @param owner A pointer to the owner to select.
+ */
+void gnc_tree_view_owner_set_selected_owner (GncTreeViewOwner *view,
+ GncOwner *owner);
+
+
+/** This function returns a list of the owners associated with the
+ * selected items in the owner tree view.
+ *
+ * @note It only makes sense to call this function when the owner
+ * tree is set to select multiple items. There is a different
+ * function to use when the tree supports single selection.
+ *
+ * @param view A pointer to an owner tree view.
+ *
+ * @return A list of owners, or NULL if no owner was selected.
+ */
+GList * gnc_tree_view_owner_get_selected_owners (GncTreeViewOwner *view);
+
+
+/** This function selects a set of owners in the owner tree view.
+ * All other owners will be unselected. In addition, this function
+ * collapses the entitre tree and then expands only the path to the
+ * selected owners, making them easy to find. In general, this
+ * routine only need be called when initially putting up a window
+ * containing an owner tree view widget.
+ *
+ * @note It only makes sense to call this function when the owner
+ * tree is set to select a single item. There is a different
+ * function to use when the tree supports multiple selections.
+ *
+ * @note It is the responsibility of the caller to free the returned
+ * list.
+ *
+ * @param view A pointer to an owner tree view.
+ *
+ * @param owner_list A list of owners to select.
+ *
+ * @param show_last Force the window to scroll to the last owner
+ * selected.
+ */
+void gnc_tree_view_owner_set_selected_owners (GncTreeViewOwner *view,
+ GList *owner_list,
+ gboolean show_last);
+
+G_END_DECLS
+
+#endif /* __GNC_TREE_VIEW_OWNER_H */
More information about the gnucash-changes
mailing list