GnuCash c935c2f+
Loading...
Searching...
No Matches
top-level.c
1/********************************************************************\
2 * top-level.c -- Gnome GUI main for GnuCash *
3 * Copyright (C) 1997 Robin D. Clark *
4 * Copyright (C) 1998-2000 Linas Vepstas *
5 * *
6 * This program is free software; you can redistribute it and/or *
7 * modify it under the terms of the GNU General Public License as *
8 * published by the Free Software Foundation; either version 2 of *
9 * the License, or (at your option) any later version. *
10 * *
11 * This program is distributed in the hope that it will be useful, *
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
14 * GNU General Public License for more details. *
15 * *
16 * You should have received a copy of the GNU General Public License*
17 * along with this program; if not, contact: *
18 * *
19 * Free Software Foundation Voice: +1-617-542-5942 *
20 * 51 Franklin Street, Fifth Floor Fax: +1-617-542-2652 *
21 * Boston, MA 02110-1301, USA gnu@gnu.org *
22 * *
23\********************************************************************/
24
25#include <config.h>
26
27#include <gtk/gtk.h>
28#include <glib/gi18n.h>
29#include <stdlib.h>
30
31#include "TransLog.h"
32#include "business-options-gnome.h"
33#include "business-urls.h"
34#include "combocell.h"
35#include "dialog-account.h"
36#include "dialog-doclink.h"
37#include "dialog-commodity.h"
38#include "dialog-invoice.h"
39#include "dialog-preferences.h"
40#include "dialog-sx-editor.h"
41#include "dialog-transfer.h"
42#include "dialog-totd.h"
43#include "assistant-hierarchy.h"
44#include "file-utils.h"
45#include "gnc-component-manager.h"
46#include "gnc-engine.h"
47#include "gnc-file.h"
48#include "gnc-hooks.h"
49#include "gncInvoice.h"
50#include "gfec.h"
51#include "gnc-main-window.h"
52#include "gnc-menu-extensions.h"
53#include "gnc-plugin-menu-additions.h" /* FIXME Remove this line*/
54#include "gnc-plugin-account-tree.h" /* FIXME Remove this line*/
55#include "gnc-plugin-basic-commands.h" /* FIXME Remove this line*/
56#include "gnc-plugin-file-history.h" /* FIXME Remove this line*/
57#include "gnc-plugin-register.h" /* FIXME Remove this line*/
58#include "gnc-plugin-budget.h"
59#include "gnc-plugin-business.h"
61#include "gnc-plugin-manager.h" /* FIXME Remove this line*/
62#include "gnc-html.h"
63#include "gnc-gnome-utils.h"
64#include "gnc-report.h"
65#include "gnc-split-reg.h"
66#include "gnc-state.h"
67#include "gnc-ui.h"
68#include "gnc-ui-util.h"
69#include "gnucash-color.h"
70#include "gnucash-sheet.h"
71#include "gnucash-style.h"
72#include "search-core-type.h"
73#include "search-owner.h"
74#include "top-level.h"
75#include "window-report.h"
76#include "gnc-window.h"
77#include "gnc-gkeyfile-utils.h"
78
79
81/* This static indicates the debugging module that this .o belongs to. */
82static QofLogModule log_module = GNC_MOD_GUI;
83
84/* ============================================================== */
85/* HTML Handler for reports. */
86
87static gboolean
88validate_type(const char *url_type, const char *location,
89 const char *entity_type, GNCURLResult *result,
90 GncGUID *guid, QofInstance **entity)
91{
92 QofCollection *col;
93 QofBook * book = gnc_get_current_book();
94 if (!string_to_guid (location + strlen(url_type), guid))
95 {
96 result->error_message = g_strdup_printf (_("Bad URL: %s"), location);
97 return FALSE;
98 }
99 col = qof_book_get_collection (book, entity_type);
100 *entity = qof_collection_lookup_entity (col, guid);
101 if (NULL == *entity)
102 {
103 result->error_message = g_strdup_printf (_("Entity Not Found: %s"),
104 location);
105 return FALSE;
106 }
107
108 return TRUE;
109}
110
111
112static gboolean
113gnc_html_register_url_cb (const char *location, const char *label,
114 gboolean new_window, GNCURLResult *result)
115{
116 GncPluginPage *page = NULL;
117 GNCSplitReg * gsr = NULL;
118 Split * split = NULL;
119 Account * account = NULL;
120 Transaction * trans;
121 GncInvoice * invoice;
122 GList * node;
123 GncGUID guid;
124 QofInstance * entity = NULL;
125
126 g_return_val_if_fail (location != NULL, FALSE);
127 g_return_val_if_fail (result != NULL, FALSE);
128
129 result->load_to_stream = FALSE;
130
131 /* href="gnc-register:account=My Bank Account" */
132 if (strncmp("account=", location, 8) == 0)
133 {
134 account = gnc_account_lookup_by_full_name (gnc_get_current_root_account (),
135 location + 8);
136 }
137
138 /* href="gnc-register:guid=12345678901234567890123456789012" */
139 else if (strncmp ("acct-guid=", location, strlen ("acct-guid=")) == 0)
140 {
141 if (!validate_type("acct-guid=", location, GNC_ID_ACCOUNT, result, &guid, &entity))
142 return FALSE;
143
144 account = GNC_ACCOUNT(entity);
145 }
146
147 else if (strncmp ("trans-guid=", location, strlen ("trans-guid=")) == 0)
148 {
149 if (!validate_type("trans-guid=", location, GNC_ID_TRANS, result, &guid, &entity))
150 return FALSE;
151
152 trans = (Transaction *) entity;
153
154 for (node = xaccTransGetSplitList (trans); node; node = node->next)
155 {
156 split = node->data;
157 account = xaccSplitGetAccount(split);
158 if (account) break;
159 }
160
161 if (!account)
162 {
163 result->error_message =
164 g_strdup_printf (_("Transaction with no Accounts: %s"), location);
165 return FALSE;
166 }
167 }
168
169 else if (strncmp ("trans-doclink-guid=", location,
170 strlen ("trans-doclink-guid=")) == 0)
171 {
172 if (!validate_type("trans-doclink-guid=", location, GNC_ID_TRANS,
173 result, &guid, &entity))
174 return FALSE;
175
176 trans = (Transaction *) entity;
177 gnc_doclink_open_uri (gnc_ui_get_gtk_window (GTK_WIDGET (result->parent)),
178 xaccTransGetDocLink (trans));
179 return TRUE;
180 }
181
182 else if (strncmp ("invoice-doclink-guid=", location,
183 strlen ("invoice-doclink-guid=")) == 0)
184 {
185 if (!validate_type("invoice-doclink-guid=", location, GNC_ID_INVOICE,
186 result, &guid, &entity))
187 return FALSE;
188
189 invoice = (GncInvoice *) entity;
190 gnc_doclink_open_uri (gnc_ui_get_gtk_window (GTK_WIDGET (result->parent)),
191 gncInvoiceGetDocLink (invoice));
192 return TRUE;
193 }
194
195 else if (strncmp ("split-guid=", location, strlen ("split-guid=")) == 0)
196 {
197 if (!validate_type("split-guid=", location, GNC_ID_SPLIT, result, &guid, &entity))
198 return FALSE;
199
200 split = (Split *) entity;
201 account = xaccSplitGetAccount(split);
202 }
203
204 else
205 {
206 result->error_message =
207 g_strdup_printf (_("Unsupported entity type: %s"), location);
208 return FALSE;
209 }
210
211 page = gnc_plugin_page_register_new (account, FALSE);
212 gnc_main_window_open_page (GNC_MAIN_WINDOW (result->parent), page);
213 if (split)
214 {
216
217 /* Test for visibility of split */
218 if (gnc_split_reg_clear_filter_for_split (gsr, split))
220
221 gnc_split_reg_jump_to_split (gsr, split);
222 }
223 return TRUE;
224}
225
226/* ============================================================== */
227
228static gboolean
229gnc_html_price_url_cb (const char *location, const char *label,
230 gboolean new_window, GNCURLResult *result)
231{
232 GncGUID guid;
233 QofInstance * entity = NULL;
234
235 g_return_val_if_fail (location != NULL, FALSE);
236 g_return_val_if_fail (result != NULL, FALSE);
237
238 result->load_to_stream = FALSE;
239
240 /* href="gnc-register:guid=12345678901234567890123456789012" */
241 if (strncmp ("price-guid=", location, strlen ("price-guid=")) == 0)
242 {
243 if (!validate_type("price-guid=", location, GNC_ID_PRICE, result, &guid, &entity))
244 return FALSE;
245
246 if (!gnc_price_edit_by_guid (GTK_WIDGET (result->parent), &guid))
247 {
248 result->error_message = g_strdup_printf (_("No such price: %s"),
249 location);
250 return FALSE;
251 }
252 }
253 else
254 {
255 result->error_message = g_strdup_printf (_("Badly formed URL %s"),
256 location);
257 return FALSE;
258 }
259
260 return TRUE;
261}
262
277static void
278gnc_restore_all_state (gpointer session, gpointer unused)
279{
280 GKeyFile *keyfile = NULL;
281 gchar *file_guid = NULL;
282 GError *error = NULL;
283
284 keyfile = gnc_state_load (session);
285
286#ifdef DEBUG
287 /* Debugging: dump a copy to the trace log */
288 {
289 gchar *file_data;
290 gsize file_length;
291 file_data = g_key_file_to_data(keyfile, &file_length, NULL);
292 DEBUG("=== File Data Read===\n%s\n=== File End ===\n", file_data);
293 g_free(file_data);
294 }
295#endif
296
297 /* If no state file was found, keyfile will be empty
298 * In that case, let's load the default state */
299 if (!g_key_file_has_group (keyfile, STATE_FILE_TOP))
300 {
302 LEAVE("no state file");
303 goto cleanup;
304 }
305
306 /* report any other keyfile read error as a warning
307 * but still load default state */
308 file_guid = g_key_file_get_string(keyfile, STATE_FILE_TOP,
309 STATE_FILE_BOOK_GUID, &error);
310 if (error)
311 {
313 g_warning("error reading group %s key %s: %s",
314 STATE_FILE_TOP, STATE_FILE_BOOK_GUID, error->message);
315 LEAVE("no guid in state file");
316 goto cleanup;
317 }
318
320
321 /* Clean up */
322 LEAVE("ok");
323cleanup:
324 if (error)
325 g_error_free(error);
326 if (file_guid)
327 g_free(file_guid);
328
329 gnc_totd_dialog_reparent ();
330}
331
332
347static void
348gnc_save_all_state (gpointer session, gpointer unused)
349{
350 QofBook *book;
351 gchar guid_string[GUID_ENCODING_LENGTH+1];
352 const GncGUID *guid;
353 GKeyFile *keyfile = NULL;
354
355 keyfile = gnc_state_get_current ();
356 if (keyfile)
357 {
358 /* Remove existing Window and Page groups from the keyfile
359 * They will be regenerated.
360 */
361 gsize num_groups, curr;
362 gchar **groups = g_key_file_get_groups (keyfile, &num_groups);
363 for (curr=0; curr < num_groups; curr++)
364 {
365 if (g_str_has_prefix (groups[curr], "Window ") ||
366 g_str_has_prefix (groups[curr], "Page "))
367 {
368 DEBUG ("Removing state group %s", groups[curr]);
369 g_key_file_remove_group (keyfile, groups[curr], NULL);
370 }
371 }
372 g_strfreev (groups);
373 }
374
375 /* Store the book's GncGUID in the top level group */
376 book = qof_session_get_book(session);
377 if (!book)
378 {
379 PERR("Session has no book!");
380 return;
381 }
382 guid = qof_entity_get_guid(QOF_INSTANCE(book));
383 guid_to_string_buff(guid, guid_string);
384 g_key_file_set_string(keyfile, STATE_FILE_TOP, STATE_FILE_BOOK_GUID,
385 guid_string);
386
388
389#ifdef DEBUG
390 /* Debugging: dump a copy to the trace log */
391 {
392 gchar *file_data;
393 gsize file_length;
394 file_data = g_key_file_to_data(keyfile, &file_length, NULL);
395 DEBUG("=== File Data Written===\n%s\n=== File End ===\n", file_data);
396 g_free(file_data);
397 }
398#endif
399 LEAVE("");
400}
401
402void
403gnc_main_gui_init (void)
404{
405 ENTER(" ");
406
407 if (!gnucash_style_init())
408 gnc_shutdown(1);
409 gnucash_color_init();
410
411 gnc_html_register_url_handler (URL_TYPE_REGISTER,
412 gnc_html_register_url_cb);
413
414 gnc_html_register_url_handler (URL_TYPE_PRICE,
415 gnc_html_price_url_cb);
416
417 /* Register the Owner search type */
418 gnc_search_core_register_type (GNC_OWNER_MODULE_NAME,
419 (GNCSearchCoreNew) gnc_search_owner_new);
420 gnc_business_urls_initialize ();
422
423 /* FIXME Remove this test code */
433 gnc_plugin_manager_get (), gnc_plugin_register_new ());
435 gnc_plugin_manager_get (), gnc_plugin_business_new ());
436 /* I'm not sure why the FIXME note says to remove this. Maybe
437 each module should be adding its own plugin to the manager?
438 Anyway... Oh, maybe... nah */
440 gnc_plugin_budget_new ());
441 gnc_ui_hierarchy_assistant_initialize();
442
443 /* Run the ui startup hooks. */
444 gnc_hook_run(HOOK_UI_STARTUP, NULL);
445
446 gnc_hook_add_dangler(HOOK_BOOK_OPENED,
447 gnc_restore_all_state, NULL, NULL);
448 gnc_hook_add_dangler(HOOK_BOOK_CLOSED,
449 gnc_save_all_state, NULL, NULL);
450 gnc_hook_add_dangler(HOOK_BOOK_CLOSED,
451 (GFunc)gnc_reports_flush_global, NULL, NULL);
452 gnc_hook_add_dangler(HOOK_BOOK_OPENED,
453 (GFunc)gnc_invoice_remind_bills_due_cb, NULL, NULL);
454 gnc_hook_add_dangler(HOOK_BOOK_OPENED,
455 (GFunc)gnc_invoice_remind_invoices_due_cb, NULL, NULL);
456
457 gnc_ui_sx_initialize();
458
459 /* Add to preferences under Business */
460 /* The parameters are; glade file, items to add from glade file - last being the dialog, preference tab name */
461 gnc_preferences_add_page("business-prefs.glade", "liststore_printinvoice,days_in_adj,cust_days_in_adj,business_prefs",
462 _("Business"));
463
464 LEAVE(" ");
465 return;
466}
467
468/****************** END OF FILE **********************/
API for the transaction logger.
This file contains the functions to present a gui to the user for creating a new account or editing a...
"select" and "new" commodity windows
Dialog for handling user preferences.
Utility functions for file access.
All type declarations for the whole Gnucash engine.
GKeyFile helper routines.
Gnome specific utility functions.
Functions for adding content to a window.
Provide the menus to create a chart of account page.
Functions providing a basic set of menu items.
Functions providing the file history menu.
Plugin management functions for the GnuCash UI.
Functions providing menu items from scheme code.
Functions providing a register page for the GnuCash UI.
Functions to load, save and get gui state.
utility functions for the GnuCash UI
Functions that are supported by all types of windows.
Business Invoice Interface.
Convenience wrapper around GdkRGBA for use in Register Gnome classes.
Public declarations of GnucashRegister class.
Styling functions for RegisterGnome.
QofBook * qof_session_get_book(const QofSession *session)
Returns the QofBook of this session.
QofCollection * qof_book_get_collection(const QofBook *book, QofIdType entity_type)
Return The table of entities of the given type.
Definition qofbook.cpp:521
const char * xaccTransGetDocLink(const Transaction *trans)
Gets the transaction Document Link.
SplitList * xaccTransGetSplitList(const Transaction *trans)
The xaccTransGetSplitList() method returns a GList of the splits in a transaction.
Account * gnc_account_lookup_by_full_name(const Account *any_acc, const gchar *name)
The gnc_account_lookup_full_name() subroutine works like gnc_account_lookup_by_name,...
Definition Account.cpp:3163
QofInstance * qof_collection_lookup_entity(const QofCollection *col, const GncGUID *guid)
Find the entity going only from its guid.
Definition qofid.cpp:209
#define GUID_ENCODING_LENGTH
Number of characters needed to encode a guid as a string not including the null terminator.
Definition guid.h:84
gchar * guid_to_string_buff(const GncGUID *guid, gchar *str)
The guid_to_string_buff() routine puts a null-terminated string encoding of the id into the memory po...
Definition guid.cpp:208
void gnc_main_window_save_all_windows(GKeyFile *keyfile)
Save the persistent state of all windows.
void gnc_main_window_restore_all_windows(const GKeyFile *keyfile)
Restore the persistent state of all windows.
GtkWindow * gnc_ui_get_gtk_window(GtkWidget *widget)
Get a pointer to the widget's immediate top level GtkWindow.
void gnc_main_window_restore_default_state(GncMainWindow *window)
Restore the persistent state of one window to a sane default.
void gnc_main_window_open_page(GncMainWindow *window, GncPluginPage *page)
Display a data plugin page in a window.
GncPlugin * gnc_plugin_account_tree_new(void)
Create a new account tree menu plugin.
GncPlugin * gnc_plugin_basic_commands_new(void)
Create a new basic commands menu plugin.
GKeyFile * gnc_state_load(const QofSession *session)
Load the state from a state file on disk for the given session.
Definition gnc-state.c:202
GKeyFile * gnc_state_get_current(void)
Returns a pointer to the most recently loaded state.
Definition gnc-state.c:248
void gnc_shutdown(int exit_status)
Shutdown gnucash.
void gnc_business_options_gnome_initialize(void)
Set up the business and counters pages in the File Preferences dialog.
const GncGUID * qof_entity_get_guid(gconstpointer ent)
#define DEBUG(format, args...)
Print a debugging message.
Definition qoflog.h:264
#define LEAVE(format, args...)
Print a function exit debugging message.
Definition qoflog.h:282
#define PERR(format, args...)
Log a serious error.
Definition qoflog.h:244
#define ENTER(format, args...)
Print a function entry debugging message.
Definition qoflog.h:272
GncPlugin * gnc_plugin_file_history_new(void)
Create a new file history plugin.
void gnc_plugin_manager_add_plugin(GncPluginManager *manager, GncPlugin *plugin)
Add a plugin to the list maintained by the plugin manager.
GncPluginManager * gnc_plugin_manager_get(void)
Retrieve a pointer to the plugin manager.
GncPlugin * gnc_plugin_menu_additions_new(void)
Create a new menu_additions plugin.
void gnc_preferences_add_page(const gchar *filename, const gchar *widgetname, const gchar *tabname)
This function adds a full page of preferences to the preferences dialog.
void gnc_plugin_page_register_clear_current_filter(GncPluginPage *plugin_page)
This function clears the registers current filter.
GncPluginPage * gnc_plugin_page_register_new(Account *account, gboolean subaccounts)
Create a new "register" plugin page, given a pointer to an account.
GNCSplitReg * gnc_plugin_page_register_get_gsr(GncPluginPage *plugin_page)
Get the GNCSplitReg data structure associated with this register page.
Account * xaccSplitGetAccount(const Split *split)
Returns the account of this split, which was set through xaccAccountInsertSplit().
STRUCTS.
The type used to store guids in C.
Definition guid.h:75
The instance data structure for a content plugin.
QofBook reference.
Definition qofbook-p.hpp:47