* business-core/gncTaxTable*: Create a preliminary implementation

of Tax Tables.  They are currently not saved, and nothing uses
	them.  Link the initialization into the module.

	* business-gnome/dialog-tax-table*: Create a tax table GUI to
	create and edit tax tables.  G-wrap the editor-window create
	routine.

	* business-gnome.scm: add the Tax Table gui; rename the 'Invoice'
	option page to "Business".  Fix dialog-invoice to use the new
	option name.


git-svn-id: svn+ssh://svn.gnucash.org/repo/gnucash/trunk@6963 57a11ea4-9604-0410-9ed3-97b8803252fd
This commit is contained in:
Derek Atkins 2002-06-14 17:08:19 +00:00
parent 00a88c5d4b
commit f55d4caaa1
13 changed files with 1907 additions and 3 deletions

View File

@ -1,3 +1,17 @@
2002-06-14 Derek Atkins <derek@ihtfp.com>
* business-core/gncTaxTable*: Create a preliminary implementation
of Tax Tables. They are currently not saved, and nothing uses
them. Link the initialization into the module.
* business-gnome/dialog-tax-table*: Create a tax table GUI to
create and edit tax tables. G-wrap the editor-window create
routine.
* business-gnome.scm: add the Tax Table gui; rename the 'Invoice'
option page to "Business". Fix dialog-invoice to use the new
option name.
2002-06-11 David Hampton <hampton@employees.org>
* src/gnome/druid-stock-split.c: Add automatic focusing on a

View File

@ -21,6 +21,7 @@ libgncmod_business_core_la_SOURCES = \
gncJob.c \
gncOrder.c \
gncOwner.c \
gncTaxTable.c \
gncVendor.c
noinst_HEADERS = \
@ -42,6 +43,8 @@ noinst_HEADERS = \
gncOrderP.h \
gncOwner.h \
gncOwnerP.h \
gncTaxTable.h \
gncTaxTableP.h \
gncVendor.h \
gncVendorP.h

View File

@ -62,6 +62,7 @@ gnc_module_init(int refcount)
gncJobRegister ();
gncOrderRegister ();
gncOwnerRegister ();
gncTaxTableRegister ();
gncVendorRegister ();
}

View File

@ -0,0 +1,486 @@
/*
* gncTaxTable.c -- the Gnucash Tax Table interface
* Copyright (C) 2002 Derek Atkins
* Author: Derek Atkins <warlord@MIT.EDU>
*/
#include "config.h"
#include <glib.h>
#include "messages.h"
#include "gnc-numeric.h"
#include "gnc-engine-util.h"
#include "gnc-book-p.h"
#include "GNCIdP.h"
#include "QueryObject.h"
#include "gnc-event-p.h"
#include "gncBusiness.h"
#include "gncTaxTableP.h"
struct _gncTaxTable {
GUID guid;
char * name;
GList * entries;
gint64 refcount;
GNCBook * book;
GncTaxTable * parent; /* if non-null, we are an immutable child */
GncTaxTable * child; /* if non-null, we have not changed */
gboolean invisible;
gboolean dirty;
};
struct _gncTaxTableEntry {
GncTaxTable * table;
Account * account;
GncTaxType type;
gnc_numeric amount;
};
struct _book_info {
GncBookInfo bi;
GList * tables; /* visible tables */
};
#define _GNC_MOD_NAME GNC_TAXTABLE_MODULE_NAME
#define CACHE_INSERT(str) g_cache_insert(gnc_engine_get_string_cache(), (gpointer)(str));
#define CACHE_REMOVE(str) g_cache_remove(gnc_engine_get_string_cache(), (str));
#define SET_STR(member, str) { \
char * tmp; \
\
if (!safe_strcmp (member, str)) return; \
tmp = CACHE_INSERT (str); \
CACHE_REMOVE (member); \
member = tmp; \
}
static void add_or_rem_object (GncTaxTable *table, gboolean add);
static void addObj (GncTaxTable *table);
static void remObj (GncTaxTable *table);
G_INLINE_FUNC void mark_table (GncTaxTable *table);
G_INLINE_FUNC void
mark_table (GncTaxTable *table)
{
table->dirty = TRUE;
gnc_engine_generate_event (&table->guid, GNC_EVENT_MODIFY);
}
/* Create/Destroy Functions */
GncTaxTable * gncTaxTableCreate (GNCBook *book)
{
GncTaxTable *table;
if (!book) return NULL;
table = g_new0 (GncTaxTable, 1);
table->book = book;
table->name = CACHE_INSERT ("");
xaccGUIDNew (&table->guid, book);
addObj (table);
gnc_engine_generate_event (&table->guid, GNC_EVENT_CREATE);
return table;
}
void gncTaxTableDestroy (GncTaxTable *table)
{
GList *list;
if (!table) return;
gnc_engine_generate_event (&table->guid, GNC_EVENT_DESTROY);
CACHE_REMOVE (table->name);
remObj (table);
for (list = table->entries; list; list=list->next)
gncTaxTableEntryDestroy (list->data);
g_list_free (table->entries);
g_free (table);
}
GncTaxTableEntry * gncTaxTableEntryCreate (void)
{
GncTaxTableEntry *entry;
entry = g_new0 (GncTaxTableEntry, 1);
entry->amount = gnc_numeric_zero ();
return entry;
}
void gncTaxTableEntryDestroy (GncTaxTableEntry *entry)
{
if (!entry) return;
g_free (entry);
}
/* Set Functions */
void gncTaxTableSetGUID (GncTaxTable *table, const GUID *guid)
{
if (!table || !guid) return;
if (guid_equal (guid, &table->guid)) return;
remObj (table);
table->guid = *guid;
addObj (table);
}
void gncTaxTableSetName (GncTaxTable *table, const char *name)
{
if (!table || !name) return;
SET_STR (table->name, name);
mark_table (table);
}
void gncTaxTableSetParent (GncTaxTable *table, GncTaxTable *parent)
{
if (!table) return;
table->parent = parent;
gncTaxTableMakeInvisible (table);
}
void gncTaxTableSetChild (GncTaxTable *table, GncTaxTable *child)
{
if (!table) return;
table->child = child;
}
void gncTaxTableIncRef (GncTaxTable *table)
{
if (!table) return;
table->refcount++;
}
void gncTaxTableDecRef (GncTaxTable *table)
{
if (!table) return;
table->refcount--;
g_return_if_fail (table->refcount < 0);
}
void gncTaxTableSetRefcount (GncTaxTable *table, gint64 refcount)
{
if (!table) return;
table->refcount = refcount;
}
void gncTaxTableMakeInvisible (GncTaxTable *table)
{
if (!table) return;
table->invisible = TRUE;
add_or_rem_object (table, FALSE);
}
void gncTaxTableEntrySetAccount (GncTaxTableEntry *entry, Account *account)
{
if (!entry || !account) return;
if (entry->account == account) return;
entry->account = account;
if (entry->table)
mark_table (entry->table);
}
void gncTaxTableEntrySetType (GncTaxTableEntry *entry, GncTaxType type)
{
if (!entry) return;
if (entry->type == type) return;
entry->type = type;
if (entry->table)
mark_table (entry->table);
}
void gncTaxTableEntrySetAmount (GncTaxTableEntry *entry, gnc_numeric amount)
{
if (!entry) return;
if (gnc_numeric_eq (entry->amount, amount)) return;
entry->amount = amount;
if (entry->table)
mark_table (entry->table);
}
void gncTaxTableAddEntry (GncTaxTable *table, GncTaxTableEntry *entry)
{
if (!table || !entry) return;
if (entry->table == table) return; /* already mine */
if (entry->table)
gncTaxTableRemoveEntry (entry->table, entry);
entry->table = table;
table->entries = g_list_insert_sorted (table->entries, entry,
(GCompareFunc)gncTaxTableEntryCompare);
mark_table (table);
}
void gncTaxTableRemoveEntry (GncTaxTable *table, GncTaxTableEntry *entry)
{
if (!table || !entry) return;
entry->table = NULL;
table->entries = g_list_remove (table->entries, entry);
mark_table (table);
}
void gncTaxTableChanged (GncTaxTable *table)
{
if (!table) return;
table->child = NULL;
}
void gncTaxTableCommitEdit (GncTaxTable *table)
{
}
/* Get Functions */
GncTaxTable *gncTaxTableLookupByName (GNCBook *book, const char *name)
{
GList *list = gncTaxTableGetTables (book);
for ( ; list; list = list->next) {
GncTaxTable *table = list->data;
if (!safe_strcmp (table->name, name))
return list->data;
}
return NULL;
}
GList * gncTaxTableGetTables (GNCBook *book)
{
struct _book_info *bi;
if (!book) return NULL;
bi = gnc_book_get_data (book, _GNC_MOD_NAME);
return bi->tables;
}
const GUID *gncTaxTableGetGUID (GncTaxTable *table)
{
if (!table) return NULL;
return &table->guid;
}
GNCBook *gncTaxTableGetBook (GncTaxTable *table)
{
if (!table) return NULL;
return table->book;
}
const char *gncTaxTableGetName (GncTaxTable *table)
{
if (!table) return NULL;
return table->name;
}
static GncTaxTableEntry *gncTaxTableEntryCopy (GncTaxTableEntry *entry)
{
GncTaxTableEntry *e;
if (!entry) return NULL;
e = gncTaxTableEntryCreate ();
gncTaxTableEntrySetAccount (e, entry->account);
gncTaxTableEntrySetType (e, entry->type);
gncTaxTableEntrySetAmount (e, entry->amount);
return e;
}
static GncTaxTable *gncTaxTableCopy (GncTaxTable *table)
{
GncTaxTable *t;
GList *list;
if (!table) return NULL;
t = gncTaxTableCreate (table->book);
gncTaxTableSetName (t, table->name);
for (list = table->entries; list; list=list->next) {
GncTaxTableEntry *entry, *e;
entry = list->data;
e = gncTaxTableEntryCopy (entry);
gncTaxTableAddEntry (t, e);
}
return t;
}
GncTaxTable *gncTaxTableGetChild (GncTaxTable *table, gboolean make_new)
{
GncTaxTable *child = NULL;
if (!table) return NULL;
if (table->child) return table->child;
if (make_new) {
child = gncTaxTableCopy (table);
gncTaxTableSetChild (table, child);
gncTaxTableSetParent (child, table);
}
return child;
}
GncTaxTable *gncTaxTableGetParent (GncTaxTable *table)
{
if (!table) return NULL;
return table->parent;
}
GList *gncTaxTableGetEntries (GncTaxTable *table)
{
if (!table) return NULL;
return table->entries;
}
gint64 gncTaxTableGetRefcount (GncTaxTable *table)
{
if (!table) return 0;
return table->refcount;
}
gboolean gncTaxTableGetInvisible (GncTaxTable *table)
{
if (!table) return FALSE;
return table->invisible;
}
Account * gncTaxTableEntryGetAccount (GncTaxTableEntry *entry)
{
if (!entry) return NULL;
return entry->account;
}
GncTaxType gncTaxTableEntryGetType (GncTaxTableEntry *entry)
{
if (!entry) return GNC_TAX_TYPE_NONE;
return entry->type;
}
gnc_numeric gncTaxTableEntryGetAmount (GncTaxTableEntry *entry)
{
if (!entry) return gnc_numeric_zero();
return entry->amount;
}
int gncTaxTableEntryCompare (GncTaxTableEntry *a, GncTaxTableEntry *b)
{
char *name_a, *name_b;
int retval;
if (!a && !b) return 0;
if (!a) return -1;
if (!b) return 1;
name_a = xaccAccountGetFullName (a->account, ':');
name_b = xaccAccountGetFullName (b->account, ':');
/* for comparison purposes it doesn't matter what we use as a separator */
retval = safe_strcmp(name_a, name_b);
g_free(name_a);
g_free(name_b);
if (retval)
return retval;
return gnc_numeric_compare (a->amount, b->amount);
}
int gncTaxTableCompare (GncTaxTable *a, GncTaxTable *b)
{
if (!a && !b) return 0;
if (!a) return -1;
if (!b) return 1;
return safe_strcmp (a->name, b->name);
}
/* Package-Private functions */
static void add_or_rem_object (GncTaxTable *table, gboolean add)
{
struct _book_info *bi;
if (!table) return;
bi = gnc_book_get_data (table->book, _GNC_MOD_NAME);
if (add)
bi->tables = g_list_insert_sorted (bi->tables, table,
(GCompareFunc)gncTaxTableCompare);
else
bi->tables = g_list_remove (bi->tables, table);
}
static void addObj (GncTaxTable *table)
{
gncBusinessAddObject (table->book, _GNC_MOD_NAME, table, &table->guid);
add_or_rem_object (table, TRUE);
}
static void remObj (GncTaxTable *table)
{
gncBusinessRemoveObject (table->book, _GNC_MOD_NAME, &table->guid);
add_or_rem_object (table, FALSE);
}
static void _gncTaxTableCreate (GNCBook *book)
{
struct _book_info *bi;
if (!book) return;
bi = g_new0 (struct _book_info, 1);
bi->bi.ht = guid_hash_table_new ();
gnc_book_set_data (book, _GNC_MOD_NAME, bi);
}
static void _gncTaxTableDestroy (GNCBook *book)
{
struct _book_info *bi;
if (!book) return;
bi = gnc_book_get_data (book, _GNC_MOD_NAME);
/* XXX : Destroy the objects? */
g_hash_table_destroy (bi->bi.ht);
g_list_free (bi->tables);
g_free (bi);
}
static gboolean _gncTaxTableIsDirty (GNCBook *book)
{
return gncBusinessIsDirty (book, _GNC_MOD_NAME);
}
static void _gncTaxTableMarkClean (GNCBook *book)
{
gncBusinessSetDirtyFlag (book, _GNC_MOD_NAME, FALSE);
}
static void _gncTaxTableForeach (GNCBook *book, foreachObjectCB cb,
gpointer user_data)
{
gncBusinessForeach (book, _GNC_MOD_NAME, cb, user_data);
}
static GncObject_t gncTaxTableDesc = {
GNC_OBJECT_VERSION,
_GNC_MOD_NAME,
"Tax Table",
_gncTaxTableCreate,
_gncTaxTableDestroy,
_gncTaxTableIsDirty,
_gncTaxTableMarkClean,
_gncTaxTableForeach,
NULL /* printable */
};
gboolean gncTaxTableRegister (void)
{
static QueryObjectDef params[] = {
{ QUERY_PARAM_BOOK, GNC_ID_BOOK, (QueryAccess)gncTaxTableGetBook },
{ QUERY_PARAM_GUID, QUERYCORE_GUID, (QueryAccess)gncTaxTableGetGUID },
{ NULL },
};
gncQueryObjectRegister (_GNC_MOD_NAME, (QuerySort)gncTaxTableCompare, params);
return gncObjectRegister (&gncTaxTableDesc);
}

View File

@ -0,0 +1,70 @@
/*
* gncTaxTable.h -- the Gnucash Tax Table interface
* Copyright (C) 2002 Derek Atkins
* Author: Derek Atkins <warlord@MIT.EDU>
*/
#ifndef GNC_TAXTABLE_H_
#define GNC_TAXTABLE_H_
typedef struct _gncTaxTable GncTaxTable;
typedef struct _gncTaxTableEntry GncTaxTableEntry;
#include "gnc-numeric.h"
#include "gnc-book.h"
#include "Account.h"
#define GNC_TAXTABLE_MODULE_NAME "gncTaxTable"
/*
* How to interpret the amount.
* You can interpret it as a VALUE or a PERCENT.
*/
typedef enum {
GNC_TAX_TYPE_VALUE = 0,
GNC_TAX_TYPE_PERCENT = 1,
GNC_TAX_TYPE_NONE = 2,
} GncTaxType;
/* Create/Destroy Functions */
GncTaxTable * gncTaxTableCreate (GNCBook *book);
void gncTaxTableDestroy (GncTaxTable *table);
GncTaxTableEntry * gncTaxTableEntryCreate (void);
void gncTaxTableEntryDestroy (GncTaxTableEntry *entry);
/* Set Functions */
void gncTaxTableSetName (GncTaxTable *table, const char *name);
void gncTaxTableIncRef (GncTaxTable *table);
void gncTaxTableDecRef (GncTaxTable *table);
void gncTaxTableEntrySetAccount (GncTaxTableEntry *entry, Account *account);
void gncTaxTableEntrySetType (GncTaxTableEntry *entry, GncTaxType type);
void gncTaxTableEntrySetAmount (GncTaxTableEntry *entry, gnc_numeric amount);
void gncTaxTableAddEntry (GncTaxTable *table, GncTaxTableEntry *entry);
void gncTaxTableRemoveEntry (GncTaxTable *table, GncTaxTableEntry *entry);
void gncTaxTableChanged (GncTaxTable *table);
void gncTaxTableCommitEdit (GncTaxTable *table);
/* Get Functions */
GncTaxTable *gncTaxTableLookupByName (GNCBook *book, const char *name);
GList * gncTaxTableGetTables (GNCBook *book);
const GUID *gncTaxTableGetGUID (GncTaxTable *table);
GNCBook *gncTaxTableGetBook (GncTaxTable *table);
const char *gncTaxTableGetName (GncTaxTable *table);
GncTaxTable *gncTaxTableGetParent (GncTaxTable *table);
GncTaxTable *gncTaxTableGetChild (GncTaxTable *table, gboolean make_new);
#define gncTaxTableReturnChild(t) gncTaxTableGetChild((t),FALSE)
GList *gncTaxTableGetEntries (GncTaxTable *table);
gint64 gncTaxTableGetRefcount (GncTaxTable *table);
Account * gncTaxTableEntryGetAccount (GncTaxTableEntry *entry);
GncTaxType gncTaxTableEntryGetType (GncTaxTableEntry *entry);
gnc_numeric gncTaxTableEntryGetAmount (GncTaxTableEntry *entry);
int gncTaxTableCompare (GncTaxTable *a, GncTaxTable *b);
int gncTaxTableEntryCompare (GncTaxTableEntry *a, GncTaxTableEntry *b);
#endif /* GNC_TAXTABLE_H_ */

View File

@ -0,0 +1,22 @@
/*
* gncTaxTableP.h -- the Gnucash Tax Table interface: private interface
* Copyright (C) 2002 Derek Atkins
* Author: Derek Atkins <warlord@MIT.EDU>
*/
#ifndef GNC_TAXTABLEP_H_
#define GNC_TAXTABLEP_H_
#include "gncTaxTable.h"
gboolean gncTaxTableRegister (void);
void gncTaxTableSetGUID (GncTaxTable *table, const GUID *guid);
void gncTaxTableSetParent (GncTaxTable *table, GncTaxTable *parent);
void gncTaxTableSetChild (GncTaxTable *table, GncTaxTable *child);
void gncTaxTableSetRefcount (GncTaxTable *table, gint64 refcount);
void gncTaxTableMakeInvisible (GncTaxTable *table);
gboolean gncTaxTableGetInvisible (GncTaxTable *table);
#endif /* GNC_TAXTABLEP_H_ */

View File

@ -33,6 +33,7 @@ libgncmod_business_gnome_la_SOURCES = \
dialog-job.c \
dialog-order.c \
dialog-payment.c \
dialog-tax-table.c \
dialog-vendor.c \
search-owner.c \
gnc-business-utils.c
@ -46,6 +47,7 @@ noinst_HEADERS = \
dialog-job.h \
dialog-order.h \
dialog-payment.h \
dialog-tax-table.h \
dialog-vendor.h \
search-owner.h \
gnc-business-utils.h
@ -86,6 +88,7 @@ glade_DATA = \
job.glade \
order.glade \
payment.glade \
tax-tables.glade \
vendor.glade
gwmoddir = ${GNC_GWRAP_LIBDIR}

View File

@ -176,6 +176,13 @@
;;(gnc:add-extension find)
;;(gnc:add-extension new)
(gnc:add-extension
(gnc:make-menu-item (N_ "Tax Tables")
(N_ "View and Edit the available Tax Tables")
(list top-level "")
(lambda ()
(gnc:tax-table-new (gnc:get-current-book)))))
(add-vendor-items)
(add-customer-items)
)
@ -325,8 +332,8 @@
(gnc:register-configuration-option
(gnc:make-number-range-option
(N_ "Invoice") (N_ "Number of Rows")
"d" (N_ "Default number of register rows to display.")
(N_ "Business") (N_ "Number of Rows")
"a" (N_ "Default number of register rows to display in Invoices.")
10.0 ;; default
1.0 ;; lower bound
200.0 ;; upper bound
@ -334,4 +341,5 @@
1.0 ;; step size
))
(load-from-path "business-options.scm")

View File

@ -1223,7 +1223,7 @@ gnc_invoice_new_window (GNCBook *bookp, InvoiceDialogType type,
GtkWidget *popup;
guint num_rows;
num_rows = (guint) gnc_lookup_number_option ("Invoice",
num_rows = (guint) gnc_lookup_number_option ("Business",
"Number of Rows", 10.0);
gnucash_register_set_initial_rows( num_rows );

View File

@ -0,0 +1,680 @@
/*
* dialog-tax-table.c -- Dialog to create and edit tax-tables
* Copyright (C) 2002 Derek Atkins
* Author: Derek Atkins <warlord@MIT.EDU>
*/
#include "config.h"
#include <gnome.h>
#include "dialog-utils.h"
#include "global-options.h"
#include "gnc-component-manager.h"
#include "gnc-ui.h"
#include "gnc-gui-query.h"
#include "gnc-ui-util.h"
#include "gnc-engine-util.h"
#include "gnc-amount-edit.h"
#include "gnc-account-tree.h"
#include "gnc-numeric.h"
#include "gncTaxTable.h"
#include "dialog-tax-table.h"
#define DIALOG_TAX_TABLE_CM_CLASS "tax-table-dialog"
struct _taxtable_window {
GtkWidget * dialog;
GtkWidget * names_clist;
GtkWidget * entries_clist;
GncTaxTable * current_table;
GncTaxTableEntry * current_entry;
GNCBook * book;
gint component_id;
};
typedef struct _new_taxtable {
GtkWidget * dialog;
GtkWidget * name_entry;
GtkWidget * amount_entry;
GtkWidget * acct_tree;
TaxTableWindow * ttw;
GncTaxTableEntry * entry;
gint type;
gboolean new_table;
} NewTaxTable;
static void
new_tax_table_ok_cb (GtkWidget *widget, gpointer data)
{
NewTaxTable *ntt = data;
TaxTableWindow *ttw;
char *name = NULL;
char *message;
Account *acc;
gnc_numeric amount;
g_return_if_fail (ntt);
ttw = ntt->ttw;
/* Verify that we've got real, valid data */
/* verify the name, maybe */
if (ntt->new_table) {
name = gtk_entry_get_text (GTK_ENTRY (ntt->name_entry));
if (name == NULL || *name == '\0') {
message = _("You must provide a name for this Tax Table.");
gnc_error_dialog_parented (GTK_WINDOW (ntt->dialog), message);
return;
}
if (gncTaxTableLookupByName (ttw->book, name)) {
message = g_strdup_printf(_(
"You must provide a unique name for this Tax Table.\n"
"Your choice \"%s\" is already in use."), name);
gnc_error_dialog_parented (GTK_WINDOW (ntt->dialog), message);
g_free (message);
return;
}
}
/* verify the amount */
amount = gnc_amount_edit_get_amount (GNC_AMOUNT_EDIT (ntt->amount_entry));
if (gnc_numeric_negative_p (amount)) {
message = _("Negative amounts are not allowed.");
gnc_error_dialog_parented (GTK_WINDOW (ntt->dialog), message);
return;
}
if (ntt->type == GNC_TAX_TYPE_PERCENT &&
gnc_numeric_compare (amount,
gnc_numeric_create (100, 1)) > 0) {
message = _("Percentage amount must be between 0 and 100.");
gnc_error_dialog_parented (GTK_WINDOW (ntt->dialog), message);
return;
}
/* verify the account */
acc =
gnc_account_tree_get_current_account (GNC_ACCOUNT_TREE (ntt->acct_tree));
if (acc == NULL) {
message = _("You must choose a Tax Account.");
gnc_error_dialog_parented (GTK_WINDOW (ntt->dialog), message);
return;
}
gnc_suspend_gui_refresh ();
/* Ok, it's all valid, now either change to add this thing */
if (ntt->new_table) {
GncTaxTable *table = gncTaxTableCreate (ttw->book);
gncTaxTableSetName (table, name);
/* Reset the current table */
ttw->current_table = table;
}
/* Create/edit the entry */
{
GncTaxTableEntry *entry;
if (ntt->entry) {
entry = ntt->entry;
} else {
entry = gncTaxTableEntryCreate ();
gncTaxTableAddEntry (ttw->current_table, entry);
ttw->current_entry = entry;
}
gncTaxTableEntrySetAccount (entry, acc);
gncTaxTableEntrySetType (entry, ntt->type);
gncTaxTableEntrySetAmount (entry, amount);
}
/* Mark the table as changed and commit it */
gncTaxTableChanged (ttw->current_table);
gncTaxTableCommitEdit (ttw->current_table);
gnc_resume_gui_refresh();
/* Then close/refresh the dialog/window */
gnome_dialog_close (GNOME_DIALOG (ntt->dialog));
}
static void
new_tax_table_cancel_cb (GtkWidget *widget, gpointer data)
{
NewTaxTable *ntt = data;
g_return_if_fail (ntt);
gnome_dialog_close (GNOME_DIALOG (ntt->dialog));
}
static void
new_tax_table_dialog_destroy_cb (GtkWidget *widget, gpointer data)
{
NewTaxTable *ntt = data;
if (!ntt) return;
g_free (ntt);
}
static void
optionmenu_changed (GtkWidget *widget, NewTaxTable *ntt)
{
g_return_if_fail (ntt);
ntt->type = GPOINTER_TO_INT (gtk_object_get_data (GTK_OBJECT (widget),
"option"));
}
static GtkWidget *
add_menu_item (GtkWidget *menu, NewTaxTable *ntt, char *label, gint type)
{
GtkWidget *item;
item = gtk_menu_item_new_with_label (label);
gtk_object_set_data (GTK_OBJECT (item), "option", GINT_TO_POINTER (type));
gtk_signal_connect (GTK_OBJECT (item), "activate", optionmenu_changed, ntt);
gtk_menu_append (GTK_MENU (menu), item);
gtk_widget_show (item);
return item;
}
static GtkWidget *
make_menu (GtkWidget *omenu, NewTaxTable *ntt)
{
GtkWidget *menu, *value, *percent;
int current = ntt->type;
menu = gtk_menu_new ();
value= add_menu_item (menu, ntt, _("Value $"), GNC_TAX_TYPE_VALUE);
percent = add_menu_item (menu, ntt, _("Percent %"), GNC_TAX_TYPE_PERCENT);
gtk_option_menu_set_menu (GTK_OPTION_MENU (omenu), menu);
gtk_signal_emit_by_name (GTK_OBJECT ((current == GNC_TAX_TYPE_VALUE ?
value : percent)), "activate", ntt);
gtk_option_menu_set_history (GTK_OPTION_MENU (omenu), current);
return menu;
}
static NewTaxTable *
new_tax_table_dialog (TaxTableWindow *ttw, gboolean new_table,
GncTaxTableEntry *entry)
{
NewTaxTable *ntt;
GladeXML *xml;
GtkWidget *box, *widget;
if (!ttw) return NULL;
if (new_table && entry) return NULL;
ntt = g_new0 (NewTaxTable, 1);
ntt->ttw = ttw;
ntt->entry = entry;
ntt->new_table = new_table;
if (entry)
ntt->type = gncTaxTableEntryGetType (entry);
else
ntt->type = GNC_TAX_TYPE_PERCENT;
/* Open and read the XML */
xml = gnc_glade_xml_new ("tax-tables.glade", "New Tax Table Dialog");
ntt->dialog = glade_xml_get_widget (xml, "New Tax Table Dialog");
ntt->name_entry = glade_xml_get_widget (xml, "name_entry");
/* Create the menu */
make_menu (glade_xml_get_widget (xml, "type_menu"), ntt);
/* Attach our own widgets */
box = glade_xml_get_widget (xml, "amount_box");
ntt->amount_entry = widget = gnc_amount_edit_new ();
gnc_amount_edit_set_evaluate_on_enter (GNC_AMOUNT_EDIT (widget), TRUE);
gtk_box_pack_start (GTK_BOX (box), widget, TRUE, TRUE, 0);
box = glade_xml_get_widget (xml, "account_frame");
ntt->acct_tree = widget = gnc_account_tree_new ();
gtk_clist_column_titles_hide (GTK_CLIST (widget));
gnc_account_tree_hide_all_but_name (GNC_ACCOUNT_TREE (widget));
gtk_container_add (GTK_CONTAINER (box), widget);
gnc_account_tree_refresh(GNC_ACCOUNT_TREE(ntt->acct_tree));
/* Make 'enter' do the right thing */
gnome_dialog_set_default (GNOME_DIALOG (ntt->dialog), 0);
gnome_dialog_editable_enters (GNOME_DIALOG (ntt->dialog),
GTK_EDITABLE (ntt->name_entry));
gnome_dialog_editable_enters (GNOME_DIALOG (ntt->dialog),
GTK_EDITABLE (gnc_amount_edit_gtk_entry
(GNC_AMOUNT_EDIT (ntt->amount_entry))));
/* Connect the dialog buttons */
gnome_dialog_button_connect (GNOME_DIALOG (ntt->dialog), 0,
new_tax_table_ok_cb, ntt);
gnome_dialog_button_connect (GNOME_DIALOG (ntt->dialog), 1,
new_tax_table_cancel_cb, ntt);
/* Fill in the widgets appropriately */
if (entry) {
gnc_amount_edit_set_amount (GNC_AMOUNT_EDIT (ntt->amount_entry),
gncTaxTableEntryGetAmount (entry));
gnc_account_tree_select_account (GNC_ACCOUNT_TREE (ntt->acct_tree),
gncTaxTableEntryGetAccount (entry), TRUE);
}
/* Set our modality */
gnome_dialog_set_parent (GNOME_DIALOG (ntt->dialog),
GTK_WINDOW (ttw->dialog));
gtk_window_set_modal (GTK_WINDOW (ntt->dialog), TRUE);
gtk_signal_connect (GTK_OBJECT (ntt->dialog), "destroy",
new_tax_table_dialog_destroy_cb, ntt);
/* Show what we should */
gtk_widget_show_all (ntt->dialog);
if (new_table == FALSE) {
widget = glade_xml_get_widget (xml, "table_frame");
gtk_widget_hide_all (widget);
gtk_widget_grab_focus (gnc_amount_edit_gtk_entry
(GNC_AMOUNT_EDIT (ntt->amount_entry)));
} else
gtk_widget_grab_focus (ntt->name_entry);
return ntt;
}
/***********************************************************************/
static void
tax_table_entries_refresh (TaxTableWindow *ttw, gboolean new_table)
{
GList *list;
GtkAdjustment *vadjustment = NULL;
GtkCList *clist;
gfloat save_value = 0.0;
g_return_if_fail (ttw);
clist = GTK_CLIST (ttw->entries_clist);
if (!new_table) {
vadjustment = gtk_clist_get_vadjustment (clist);
if (vadjustment)
save_value = vadjustment->value;
}
/* Clear the list */
gtk_clist_freeze (clist);
gtk_clist_clear (clist);
/* Add the items to the list */
list = gncTaxTableGetEntries (ttw->current_table);
for ( ; list; list = list->next) {
char *row_text[3];
gint row;
GncTaxTableEntry *entry = list->data;
Account *acc = gncTaxTableEntryGetAccount (entry);
gnc_numeric amount = gncTaxTableEntryGetAmount (entry);
row_text[0] = xaccAccountGetFullName (acc, gnc_get_account_separator ());
switch (gncTaxTableEntryGetType (entry)) {
case GNC_TAX_TYPE_PERCENT:
row_text[1] =
g_strdup_printf ("%s%%",
xaccPrintAmount (amount,
gnc_default_print_info (FALSE)));
break;
default:
row_text[1] =
g_strdup_printf ("%s",
xaccPrintAmount (amount,
gnc_default_print_info (TRUE)));
break;
}
row_text[2] = NULL;
row = gtk_clist_prepend (clist, row_text);
gtk_clist_set_row_data (clist, row, entry);
gtk_clist_set_selectable (clist, row, TRUE);
g_free (row_text[0]);
g_free (row_text[1]);
}
if (!new_table) {
if (vadjustment) {
save_value = CLAMP (save_value, vadjustment->lower,
vadjustment->upper - vadjustment->page_size);
gtk_adjustment_set_value (vadjustment, save_value);
}
}
gtk_clist_thaw (clist);
{
gint row = gtk_clist_find_row_from_data (clist, ttw->current_entry);
if (row < 0)
row = 0;
gtk_clist_select_row (clist, row, 0);
/* If this row isn't visible, move it to the center */
if (gtk_clist_row_is_visible (clist, row) != GTK_VISIBILITY_FULL)
gtk_clist_moveto (clist, row, 0, 0.5, 0);
}
}
static void
tax_table_window_refresh (TaxTableWindow *ttw)
{
GList *list;
GtkAdjustment *vadjustment;
GtkCList *clist;
gfloat save_value = 0.0;
g_return_if_fail (ttw);
clist = GTK_CLIST (ttw->names_clist);
vadjustment = gtk_clist_get_vadjustment (clist);
if (vadjustment)
save_value = vadjustment->value;
/* Clear the list */
gtk_clist_freeze (clist);
gtk_clist_clear (clist);
gnc_gui_component_clear_watches (ttw->component_id);
/* Add the items to the list */
list = gncTaxTableGetTables (ttw->book);
/* If there are no tables, clear the entries list */
if (list == NULL)
gtk_clist_clear (GTK_CLIST (ttw->entries_clist));
for ( ; list; list = list->next) {
char *row_text[2];
gint row;
GncTaxTable *table = list->data;
gnc_gui_component_watch_entity (ttw->component_id,
gncTaxTableGetGUID (table),
GNC_EVENT_MODIFY);
row_text[0] = (char *)gncTaxTableGetName (table);
row_text[1] = NULL;
row = gtk_clist_prepend (clist, row_text);
gtk_clist_set_row_data (clist, row, table);
gtk_clist_set_selectable (clist, row, TRUE);
}
gnc_gui_component_watch_entity_type (ttw->component_id,
GNC_TAXTABLE_MODULE_NAME,
GNC_EVENT_CREATE | GNC_EVENT_DESTROY);
if (vadjustment) {
save_value = CLAMP (save_value, vadjustment->lower,
vadjustment->upper - vadjustment->page_size);
gtk_adjustment_set_value (vadjustment, save_value);
}
gtk_clist_thaw (clist);
{
gint row = gtk_clist_find_row_from_data (clist, ttw->current_table);
if (row < 0)
row = 0;
gtk_clist_select_row (clist, row, 0);
/* If this row isn't visible, move it to the center */
if (gtk_clist_row_is_visible (clist, row) != GTK_VISIBILITY_FULL)
gtk_clist_moveto (clist, row, 0, 0.5, 0);
}
/* select_row() above will refresh the entries window */
}
static void
tax_table_row_selected (GtkCList *clist, gint row, gint column,
GdkEventButton *event, gpointer user_data)
{
TaxTableWindow *ttw = user_data;
GncTaxTable *table = gtk_clist_get_row_data (clist, row);
g_return_if_fail (ttw);
g_return_if_fail (table);
/* If we've changed, then reset the entry list */
if (table != ttw->current_table) {
ttw->current_table = table;
ttw->current_entry = NULL;
}
/* And force a refresh of the entries */
tax_table_entries_refresh (ttw, TRUE);
}
static void
tax_table_entry_row_selected (GtkCList *clist, gint row, gint column,
GdkEventButton *event, gpointer user_data)
{
TaxTableWindow *ttw = user_data;
GncTaxTableEntry *entry = gtk_clist_get_row_data (clist, row);
g_return_if_fail (ttw);
g_return_if_fail (entry);
ttw->current_entry = entry;
/* If we double-click an item, then pop up an 'edit' window */
if (event && event->type == GDK_2BUTTON_PRESS)
new_tax_table_dialog (ttw, FALSE, entry);
}
static void
tax_table_new_table_cb (GtkButton *button, TaxTableWindow *ttw)
{
g_return_if_fail (ttw);
new_tax_table_dialog (ttw, TRUE, NULL);
}
static void
tax_table_delete_table_cb (GtkButton *button, TaxTableWindow *ttw)
{
g_return_if_fail (ttw);
if (!ttw->current_table)
return;
if (gncTaxTableGetRefcount (ttw->current_table) > 0) {
char *message =
g_strdup_printf (_("Tax table \"%s\" is in use. You cannot delete it."),
gncTaxTableGetName (ttw->current_table));
gnc_error_dialog_parented (GTK_WINDOW (ttw->dialog), message);
g_free (message);
return;
}
if (gnc_verify_dialog_parented (ttw->dialog, FALSE,
_("Are you sure you want to delete \"%s\"?"),
gncTaxTableGetName (ttw->current_table))) {
/* Ok, let's remove it */
gnc_suspend_gui_refresh ();
gncTaxTableDestroy (ttw->current_table);
gncTaxTableCommitEdit (ttw->current_table);
ttw->current_table = NULL;
gnc_resume_gui_refresh ();
}
}
static void
tax_table_new_entry_cb (GtkButton *button, TaxTableWindow *ttw)
{
g_return_if_fail (ttw);
if (!ttw->current_table)
return;
new_tax_table_dialog (ttw, FALSE, NULL);
}
static void
tax_table_edit_entry_cb (GtkButton *button, TaxTableWindow *ttw)
{
g_return_if_fail (ttw);
if (!ttw->current_entry)
return;
new_tax_table_dialog (ttw, FALSE, ttw->current_entry);
}
static void
tax_table_delete_entry_cb (GtkButton *button, TaxTableWindow *ttw)
{
g_return_if_fail (ttw);
if (!ttw->current_table || !ttw->current_entry)
return;
if (gnc_verify_dialog_parented (ttw->dialog, FALSE,
_("Are you sure you want to delete this entry?"))) {
/* Ok, let's remove it */
gnc_suspend_gui_refresh ();
gncTaxTableRemoveEntry (ttw->current_table, ttw->current_entry);
gncTaxTableEntryDestroy (ttw->current_entry);
gncTaxTableChanged (ttw->current_table);
gncTaxTableCommitEdit (ttw->current_table);
ttw->current_entry = NULL;
gnc_resume_gui_refresh ();
}
}
static void
tax_table_window_refresh_handler (GHashTable *changes, gpointer data)
{
TaxTableWindow *ttw = data;
g_return_if_fail (data);
tax_table_window_refresh (ttw);
}
static void
tax_table_window_close_handler (gpointer data)
{
TaxTableWindow *ttw = data;
g_return_if_fail (ttw);
gnome_dialog_close (GNOME_DIALOG (ttw->dialog));
}
static void
tax_table_window_close (GtkWidget *widget, gpointer data)
{
TaxTableWindow *ttw = data;
gnc_ui_tax_table_window_destroy (ttw);
}
static void
tax_table_window_destroy_cb (GtkWidget *widget, gpointer data)
{
TaxTableWindow *ttw = data;
if (!ttw) return;
gnc_unregister_gui_component (ttw->component_id);
g_free (ttw);
}
static gboolean
find_handler (gpointer find_data, gpointer user_data)
{
TaxTableWindow *ttw = user_data;
GNCBook *book = find_data;
return (ttw != NULL && ttw->book == book);
}
/* Create a tax-table window */
TaxTableWindow *
gnc_ui_tax_table_window_new (GNCBook *book)
{
TaxTableWindow *ttw;
GladeXML *xml;
GtkWidget *button;
if (!book) return NULL;
/*
* Find an existing tax-tab;e window. If found, bring it to
* the front. If we have an actual owner, then set it in
* the window.
*/
ttw = gnc_find_first_gui_component (DIALOG_TAX_TABLE_CM_CLASS, find_handler,
book);
if (ttw) {
gtk_window_present (GTK_WINDOW(ttw->dialog));
return ttw;
}
/* Didn't find one -- create a new window */
ttw = g_new0 (TaxTableWindow, 1);
ttw->book = book;
/* Open and read the XML */
xml = gnc_glade_xml_new ("tax-tables.glade", "Tax Table Window");
ttw->dialog = glade_xml_get_widget (xml, "Tax Table Window");
ttw->names_clist = glade_xml_get_widget (xml, "tax_tables_clist");
ttw->entries_clist = glade_xml_get_widget (xml, "tax_table_entries");
/* Connect all the buttons */
button = glade_xml_get_widget (xml, "new_table_button");
gtk_signal_connect (GTK_OBJECT (button), "clicked",
tax_table_new_table_cb, ttw);
button = glade_xml_get_widget (xml, "delete_table_button");
gtk_signal_connect (GTK_OBJECT (button), "clicked",
tax_table_delete_table_cb, ttw);
button = glade_xml_get_widget (xml, "new_entry_button");
gtk_signal_connect (GTK_OBJECT (button), "clicked",
tax_table_new_entry_cb, ttw);
button = glade_xml_get_widget (xml, "edit_entry_button");
gtk_signal_connect (GTK_OBJECT (button), "clicked",
tax_table_edit_entry_cb, ttw);
button = glade_xml_get_widget (xml, "delete_entry_button");
gtk_signal_connect (GTK_OBJECT (button), "clicked",
tax_table_delete_entry_cb, ttw);
/* Set the row-select callbacks */
gtk_signal_connect (GTK_OBJECT (ttw->names_clist), "select-row",
tax_table_row_selected, ttw);
gtk_signal_connect (GTK_OBJECT (ttw->entries_clist), "select-row",
tax_table_entry_row_selected, ttw);
/* Connect the dialog buttons */
gnome_dialog_button_connect (GNOME_DIALOG (ttw->dialog), 0,
tax_table_window_close, ttw);
gtk_signal_connect (GTK_OBJECT (ttw->dialog), "destroy",
tax_table_window_destroy_cb, ttw);
/* register with component manager */
ttw->component_id =
gnc_register_gui_component (DIALOG_TAX_TABLE_CM_CLASS,
tax_table_window_refresh_handler,
tax_table_window_close_handler,
ttw);
tax_table_window_refresh (ttw);
gtk_widget_show_all (ttw->dialog);
return ttw;
}
/* Destroy a tax-table window */
void
gnc_ui_tax_table_window_destroy (TaxTableWindow *ttw)
{
if (!ttw)
return;
gnc_close_gui_component (ttw->component_id);
}

View File

@ -0,0 +1,20 @@
/*
* dialog-tax-table.h -- Dialog to create and edit tax-tables
* Copyright (C) 2002 Derek Atkins
* Author: Derek Atkins <warlord@MIT.EDU>
*/
#ifndef _DIALOG_TAX_TABLE_H
#define _DIALOG_TAX_TABLE_H
typedef struct _taxtable_window TaxTableWindow;
#include "gnc-book.h"
/* Create a tax-table window */
TaxTableWindow * gnc_ui_tax_table_window_new (GNCBook *book);
/* Destroy a tax-table window */
void gnc_ui_tax_table_window_destroy (TaxTableWindow *ttw);
#endif /* _DIALOG_TAX-TABLE_H */

View File

@ -38,6 +38,7 @@
"#include <dialog-job.h>\n"
"#include <dialog-order.h>\n"
"#include <dialog-payment.h>\n"
"#include <dialog-tax-table.h>\n"
"#include <dialog-vendor.h>\n"
)))
@ -205,6 +206,18 @@
'((<gnc:GncOwner*> owner) (<gnc:Book*> book))
"Dialog: Enter a payment. The owner may be NULL.")
;;
;; dialog-tax-table.h
;;
(gw:wrap-function
ws
'gnc:tax-table-new
'<gw:void>
"gnc_ui_tax_table_window_new"
'((<gnc:Book*> book))
"Dialog: Edit the Tax Tables.")
;;
;; dialog-vendor.h
;;

View File

@ -0,0 +1,584 @@
<?xml version="1.0"?>
<GTK-Interface>
<project>
<name>Tax Tables</name>
<program_name>tax-tables</program_name>
<directory></directory>
<source_directory>src</source_directory>
<pixmaps_directory>pixmaps</pixmaps_directory>
<language>C</language>
<gnome_support>True</gnome_support>
<gettext_support>True</gettext_support>
<output_main_file>False</output_main_file>
<output_support_files>False</output_support_files>
<output_build_files>False</output_build_files>
</project>
<widget>
<class>GnomeDialog</class>
<name>Tax Table Window</name>
<title>Tax Tables</title>
<type>GTK_WINDOW_TOPLEVEL</type>
<position>GTK_WIN_POS_NONE</position>
<modal>False</modal>
<allow_shrink>False</allow_shrink>
<allow_grow>False</allow_grow>
<auto_shrink>False</auto_shrink>
<auto_close>False</auto_close>
<hide_on_close>False</hide_on_close>
<widget>
<class>GtkVBox</class>
<child_name>GnomeDialog:vbox</child_name>
<name>dialog-vbox1</name>
<homogeneous>False</homogeneous>
<spacing>8</spacing>
<child>
<padding>4</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkHButtonBox</class>
<child_name>GnomeDialog:action_area</child_name>
<name>dialog-action_area1</name>
<layout_style>GTK_BUTTONBOX_END</layout_style>
<spacing>8</spacing>
<child_min_width>85</child_min_width>
<child_min_height>27</child_min_height>
<child_ipad_x>7</child_ipad_x>
<child_ipad_y>0</child_ipad_y>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>True</fill>
<pack>GTK_PACK_END</pack>
</child>
<widget>
<class>GtkButton</class>
<name>close_button</name>
<can_default>True</can_default>
<can_focus>True</can_focus>
<stock_button>GNOME_STOCK_BUTTON_CLOSE</stock_button>
</widget>
</widget>
<widget>
<class>GtkHBox</class>
<name>hbox1</name>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkFrame</class>
<name>frame1</name>
<border_width>1</border_width>
<label>Tax Tables</label>
<label_xalign>0</label_xalign>
<shadow_type>GTK_SHADOW_ETCHED_IN</shadow_type>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkVBox</class>
<name>vbox1</name>
<border_width>2</border_width>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<widget>
<class>GtkScrolledWindow</class>
<name>scrolledwindow1</name>
<hscrollbar_policy>GTK_POLICY_AUTOMATIC</hscrollbar_policy>
<vscrollbar_policy>GTK_POLICY_AUTOMATIC</vscrollbar_policy>
<hupdate_policy>GTK_UPDATE_CONTINUOUS</hupdate_policy>
<vupdate_policy>GTK_UPDATE_CONTINUOUS</vupdate_policy>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkCList</class>
<name>tax_tables_clist</name>
<can_focus>True</can_focus>
<columns>1</columns>
<column_widths>80</column_widths>
<selection_mode>GTK_SELECTION_SINGLE</selection_mode>
<show_titles>False</show_titles>
<shadow_type>GTK_SHADOW_IN</shadow_type>
<widget>
<class>GtkLabel</class>
<child_name>CList:title</child_name>
<name>label1</name>
<label>label1</label>
<justify>GTK_JUSTIFY_CENTER</justify>
<wrap>False</wrap>
<xalign>0.5</xalign>
<yalign>0.5</yalign>
<xpad>0</xpad>
<ypad>0</ypad>
</widget>
</widget>
</widget>
<widget>
<class>GtkHBox</class>
<name>hbox2</name>
<homogeneous>True</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkButton</class>
<name>new_table_button</name>
<can_focus>True</can_focus>
<label>New...</label>
<relief>GTK_RELIEF_NORMAL</relief>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
<widget>
<class>GtkButton</class>
<name>delete_table_button</name>
<can_focus>True</can_focus>
<label>Delete</label>
<relief>GTK_RELIEF_NORMAL</relief>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
</widget>
</widget>
</widget>
<widget>
<class>GtkFrame</class>
<name>frame2</name>
<border_width>1</border_width>
<label>Tax Table Entries</label>
<label_xalign>0</label_xalign>
<shadow_type>GTK_SHADOW_ETCHED_IN</shadow_type>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkVBox</class>
<name>vbox2</name>
<border_width>2</border_width>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<widget>
<class>GtkScrolledWindow</class>
<name>scrolledwindow2</name>
<hscrollbar_policy>GTK_POLICY_AUTOMATIC</hscrollbar_policy>
<vscrollbar_policy>GTK_POLICY_AUTOMATIC</vscrollbar_policy>
<hupdate_policy>GTK_UPDATE_CONTINUOUS</hupdate_policy>
<vupdate_policy>GTK_UPDATE_CONTINUOUS</vupdate_policy>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkCList</class>
<name>tax_table_entries</name>
<can_focus>True</can_focus>
<columns>2</columns>
<column_widths>80,80</column_widths>
<selection_mode>GTK_SELECTION_SINGLE</selection_mode>
<show_titles>False</show_titles>
<shadow_type>GTK_SHADOW_IN</shadow_type>
<widget>
<class>GtkLabel</class>
<child_name>CList:title</child_name>
<name>label8</name>
<label>label8</label>
<justify>GTK_JUSTIFY_CENTER</justify>
<wrap>False</wrap>
<xalign>0.5</xalign>
<yalign>0.5</yalign>
<xpad>0</xpad>
<ypad>0</ypad>
</widget>
<widget>
<class>GtkLabel</class>
<child_name>CList:title</child_name>
<name>label9</name>
<label>label9</label>
<justify>GTK_JUSTIFY_CENTER</justify>
<wrap>False</wrap>
<xalign>0.5</xalign>
<yalign>0.5</yalign>
<xpad>0</xpad>
<ypad>0</ypad>
</widget>
</widget>
</widget>
<widget>
<class>GtkHBox</class>
<name>hbox3</name>
<homogeneous>True</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkButton</class>
<name>new_entry_button</name>
<can_focus>True</can_focus>
<label>New...</label>
<relief>GTK_RELIEF_NORMAL</relief>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
<widget>
<class>GtkButton</class>
<name>edit_entry_button</name>
<can_focus>True</can_focus>
<label>Edit...</label>
<relief>GTK_RELIEF_NORMAL</relief>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
<widget>
<class>GtkButton</class>
<name>delete_entry_button</name>
<can_focus>True</can_focus>
<label>Delete</label>
<relief>GTK_RELIEF_NORMAL</relief>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
</widget>
</widget>
</widget>
</widget>
</widget>
</widget>
<widget>
<class>GnomeDialog</class>
<name>New Tax Table Dialog</name>
<type>GTK_WINDOW_TOPLEVEL</type>
<position>GTK_WIN_POS_NONE</position>
<modal>False</modal>
<allow_shrink>False</allow_shrink>
<allow_grow>False</allow_grow>
<auto_shrink>False</auto_shrink>
<auto_close>False</auto_close>
<hide_on_close>False</hide_on_close>
<widget>
<class>GtkVBox</class>
<child_name>GnomeDialog:vbox</child_name>
<name>dialog-vbox2</name>
<homogeneous>False</homogeneous>
<spacing>8</spacing>
<child>
<padding>4</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkHButtonBox</class>
<child_name>GnomeDialog:action_area</child_name>
<name>dialog-action_area2</name>
<layout_style>GTK_BUTTONBOX_END</layout_style>
<spacing>8</spacing>
<child_min_width>85</child_min_width>
<child_min_height>27</child_min_height>
<child_ipad_x>7</child_ipad_x>
<child_ipad_y>0</child_ipad_y>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>True</fill>
<pack>GTK_PACK_END</pack>
</child>
<widget>
<class>GtkButton</class>
<name>ok_button</name>
<can_default>True</can_default>
<can_focus>True</can_focus>
<stock_button>GNOME_STOCK_BUTTON_OK</stock_button>
</widget>
<widget>
<class>GtkButton</class>
<name>cancel_button</name>
<can_default>True</can_default>
<can_focus>True</can_focus>
<stock_button>GNOME_STOCK_BUTTON_CANCEL</stock_button>
</widget>
</widget>
<widget>
<class>GtkVBox</class>
<name>vbox3</name>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkFrame</class>
<name>table_frame</name>
<border_width>2</border_width>
<label>Tax Table</label>
<label_xalign>0</label_xalign>
<shadow_type>GTK_SHADOW_ETCHED_IN</shadow_type>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkHBox</class>
<name>hbox4</name>
<border_width>3</border_width>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<widget>
<class>GtkLabel</class>
<name>label5</name>
<label>Name: </label>
<justify>GTK_JUSTIFY_RIGHT</justify>
<wrap>False</wrap>
<xalign>1</xalign>
<yalign>0.5</yalign>
<xpad>0</xpad>
<ypad>0</ypad>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
<widget>
<class>GtkEntry</class>
<name>name_entry</name>
<can_focus>True</can_focus>
<editable>True</editable>
<text_visible>True</text_visible>
<text_max_length>0</text_max_length>
<text></text>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
</widget>
</widget>
</widget>
<widget>
<class>GtkFrame</class>
<name>frame4</name>
<border_width>3</border_width>
<label>Tax Table Entry</label>
<label_xalign>0</label_xalign>
<shadow_type>GTK_SHADOW_ETCHED_IN</shadow_type>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkVBox</class>
<name>vbox4</name>
<border_width>3</border_width>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<widget>
<class>GtkHBox</class>
<name>hbox5</name>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkVBox</class>
<name>vbox5</name>
<homogeneous>True</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkLabel</class>
<name>label6</name>
<label>Type: </label>
<justify>GTK_JUSTIFY_RIGHT</justify>
<wrap>False</wrap>
<xalign>1</xalign>
<yalign>0.5</yalign>
<xpad>0</xpad>
<ypad>0</ypad>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
<widget>
<class>GtkLabel</class>
<name>label7</name>
<label>Value: </label>
<justify>GTK_JUSTIFY_RIGHT</justify>
<wrap>False</wrap>
<xalign>1</xalign>
<yalign>0.5</yalign>
<xpad>0</xpad>
<ypad>0</ypad>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
</widget>
<widget>
<class>GtkVBox</class>
<name>vbox6</name>
<homogeneous>True</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>GtkHBox</class>
<name>hbox7</name>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
<widget>
<class>GtkOptionMenu</class>
<name>type_menu</name>
<can_focus>True</can_focus>
<items>Value ($)
Percent (%)
</items>
<initial_choice>1</initial_choice>
<child>
<padding>0</padding>
<expand>False</expand>
<fill>False</fill>
</child>
</widget>
</widget>
<widget>
<class>GtkHBox</class>
<name>amount_box</name>
<homogeneous>False</homogeneous>
<spacing>0</spacing>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>Placeholder</class>
</widget>
</widget>
</widget>
</widget>
<widget>
<class>GtkFrame</class>
<name>account_frame</name>
<border_width>4</border_width>
<label>Tax Account</label>
<label_xalign>0</label_xalign>
<shadow_type>GTK_SHADOW_NONE</shadow_type>
<child>
<padding>0</padding>
<expand>True</expand>
<fill>True</fill>
</child>
<widget>
<class>Placeholder</class>
</widget>
</widget>
</widget>
</widget>
</widget>
</widget>
</widget>
</GTK-Interface>