/********************************************************************\ * gnc_stock_split_dialog * * opens up a window to record a stock split * * * * Args: parent - the parent ofthis window * * initial - the initial account to use * * Return: nothing * \********************************************************************/ void gnc_stock_split_dialog (GtkWidget *parent, Account * initial) { StockSplitInfo *info; gint component_id; info = g_new0 (StockSplitInfo, 1); info->acct = NULL; gnc_stock_split_assistant_create (info); component_id = gnc_register_gui_component (ASSISTANT_STOCK_SPLIT_CM_CLASS, refresh_handler, close_handler, info); gnc_gui_component_watch_entity_type (component_id, GNC_ID_ACCOUNT, QOF_EVENT_MODIFY | QOF_EVENT_DESTROY); if (fill_account_list (info, initial) == 0) { gnc_warning_dialog (parent, "%s", _("You don't have any stock accounts with balances!")); gnc_close_gui_component_by_data (ASSISTANT_STOCK_SPLIT_CM_CLASS, info); return; } gtk_widget_show_all (info->window); gnc_window_adjust_for_screen (GTK_WINDOW(info->window)); }
static void gnc_price_cell_leave (BasicCell *_cell) { gint error_position = -1; PriceCell *cell = (PriceCell *) _cell; error_position = gnc_price_cell_parse (cell, TRUE); if (error_position != -1) { gnc_warning_dialog(NULL, _("An error occurred while processing %s."), cell->cell.value); } }
gboolean gnc_account_separator_validate_cb (GtkEntry *entry, GdkEvent *event, GtkWidget *dialog) { gchar *separator; gchar *conflict_msg = gnc_account_separator_is_valid (gtk_entry_get_text (entry), &separator); /* Check if the new separator clashes with existing account names */ if (conflict_msg) { gnc_warning_dialog(dialog, "%s", conflict_msg); g_free ( conflict_msg ); } g_free (separator); return FALSE; }
static void remove_clicked (CommoditiesDialog *cd) { GNCPriceDB *pdb; GList *prices; gboolean can_delete; gnc_commodity *commodity; GtkWidget *dialog; const gchar *message, *warning; gint response; commodity = gnc_tree_view_commodity_get_selected_commodity (cd->commodity_tree); if (commodity == NULL) return; AccountList_t accounts = gnc_account_get_descendants (gnc_book_get_root_account(cd->book)); can_delete = TRUE; for (AccountList_t::const_iterator node = accounts.begin(); node != accounts.end(); node++) { Account *account = *node; if (commodity == xaccAccountGetCommodity (account)) { can_delete = FALSE; break; } } /* FIXME check for transaction references */ if (!can_delete) { const char *message = _("That commodity is currently used by " "at least one of your accounts. You may " "not delete it."); gnc_warning_dialog (cd->dialog, "%s", message); return; } pdb = gnc_pricedb_get_db (cd->book); prices = gnc_pricedb_get_prices(pdb, commodity, NULL); if (prices) { message = _("This commodity has price quotes. Are " "you sure you want to delete the selected " "commodity and its price quotes?"); warning = "delete_commodity2"; } else { message = _("Are you sure you want to delete the " "selected commodity?"); warning = "delete_commodity"; } dialog = gtk_message_dialog_new(GTK_WINDOW(cd->dialog), GTK_DIALOG_DESTROY_WITH_PARENT, GTK_MESSAGE_QUESTION, GTK_BUTTONS_NONE, "%s", _("Delete commodity?")); gtk_message_dialog_format_secondary_text(GTK_MESSAGE_DIALOG(dialog), "%s", message); gtk_dialog_add_buttons(GTK_DIALOG(dialog), GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, GTK_STOCK_DELETE, GTK_RESPONSE_OK, (gchar *)NULL); response = gnc_dialog_run(GTK_DIALOG(dialog), warning); gtk_widget_destroy(dialog); if (response == GTK_RESPONSE_OK) { gnc_commodity_table *ct; ct = gnc_commodity_table_get_table (cd->book); for (GList *node = prices; node; node = node->next) gnc_pricedb_remove_price(pdb, node->data); gnc_commodity_table_remove (ct, commodity); gnc_commodity_destroy (commodity); commodity = NULL; } gnc_price_list_destroy(prices); gnc_gui_refresh_all (); }
static PaymentWindow * new_payment_window (GncOwner *owner, QofBook *book, GncInvoice *invoice) { PaymentWindow *pw; GtkBuilder *builder; GtkWidget *box, *label, *credit_box, *debit_box; GtkTreeSelection *selection; GtkTreeViewColumn *column; GtkCellRenderer *renderer; char * cm_class = (gncOwnerGetType (owner) == GNC_OWNER_CUSTOMER ? DIALOG_PAYMENT_CUSTOMER_CM_CLASS : DIALOG_PAYMENT_VENDOR_CM_CLASS); /* * Find an existing payment window. If found, bring it to * the front. If we have an actual owner, then set it in * the window. */ pw = gnc_find_first_gui_component (cm_class, find_handler, NULL); if (pw) { if (gncOwnerIsValid(owner)) gnc_payment_set_owner (pw, owner); // Reset the setting about the pre-existing TXN pw->pre_existing_txn = NULL; gtk_window_present (GTK_WINDOW(pw->dialog)); return(pw); } /* Ok, we need a new window */ pw = g_new0 (PaymentWindow, 1); pw->book = book; gncOwnerCopy (owner, &(pw->owner)); /* Compute the post-to account types */ pw->acct_types = gncOwnerGetAccountTypesList (owner); if (gncOwnerIsValid(owner)) pw->acct_commodities = gncOwnerGetCommoditiesList (owner); /* Open and read the Glade File */ builder = gtk_builder_new(); gnc_builder_add_from_file (builder, "dialog-payment.glade", "docs_list_hor_adj"); gnc_builder_add_from_file (builder, "dialog-payment.glade", "docs_list_vert_adj"); gnc_builder_add_from_file (builder, "dialog-payment.glade", "docs_list_model"); gnc_builder_add_from_file (builder, "dialog-payment.glade", "post_combo_model"); gnc_builder_add_from_file (builder, "dialog-payment.glade", "Payment Dialog"); pw->dialog = GTK_WIDGET (gtk_builder_get_object (builder, "Payment Dialog")); /* Grab the widgets and build the dialog */ pw->payment_warning = GTK_WIDGET (gtk_builder_get_object (builder, "payment_warning")); pw->ok_button = GTK_WIDGET (gtk_builder_get_object (builder, "okbutton")); pw->num_entry = GTK_WIDGET (gtk_builder_get_object (builder, "num_entry")); pw->memo_entry = GTK_WIDGET (gtk_builder_get_object (builder, "memo_entry")); pw->post_combo = GTK_WIDGET (gtk_builder_get_object (builder, "post_combo")); gtk_combo_box_set_entry_text_column( GTK_COMBO_BOX( pw->post_combo ), 0 ); gnc_cbwe_require_list_item(GTK_COMBO_BOX(pw->post_combo)); label = GTK_WIDGET (gtk_builder_get_object (builder, "owner_label")); box = GTK_WIDGET (gtk_builder_get_object (builder, "owner_box")); pw->owner_choice = gnc_owner_select_create (label, box, book, owner); /* Some terminology: * Invoices are paid, credit notes are refunded. * A customer payment is a credit action, paying a vendor is debit * * So depending on the owner the payment amount should be considered * credit (customer) or debit (vendor/employee) and refunds should be * considered debit (customer) or credit (vendor/employee). * For visual consistency, the dialog box will always show a payment and * a refund field. Internally they are treated as credit or debit depending * on the owner type. */ if (gncOwnerGetType (owner) == GNC_OWNER_CUSTOMER) { debit_box = GTK_WIDGET (gtk_builder_get_object (builder, "amount_refund_box")); credit_box = GTK_WIDGET (gtk_builder_get_object (builder, "amount_payment_box")); } else { debit_box = GTK_WIDGET (gtk_builder_get_object (builder, "amount_payment_box")); credit_box = GTK_WIDGET (gtk_builder_get_object (builder, "amount_refund_box")); } pw->amount_debit_edit = gnc_amount_edit_new (); gtk_box_pack_start (GTK_BOX (debit_box), pw->amount_debit_edit, TRUE, TRUE, 0); gnc_amount_edit_set_evaluate_on_enter (GNC_AMOUNT_EDIT (pw->amount_debit_edit), TRUE); gnc_amount_edit_set_amount (GNC_AMOUNT_EDIT (pw->amount_debit_edit), gnc_numeric_zero()); g_signal_connect(G_OBJECT(gnc_amount_edit_gtk_entry(GNC_AMOUNT_EDIT(pw->amount_debit_edit))), "focus-out-event", G_CALLBACK(gnc_payment_leave_amount_cb), pw); pw->amount_credit_edit = gnc_amount_edit_new (); gtk_box_pack_start (GTK_BOX (credit_box), pw->amount_credit_edit, TRUE, TRUE, 0); gnc_amount_edit_set_evaluate_on_enter (GNC_AMOUNT_EDIT (pw->amount_credit_edit), TRUE); gnc_amount_edit_set_amount (GNC_AMOUNT_EDIT (pw->amount_credit_edit), gnc_numeric_zero()); g_signal_connect(G_OBJECT(gnc_amount_edit_gtk_entry(GNC_AMOUNT_EDIT(pw->amount_credit_edit))), "focus-out-event", G_CALLBACK(gnc_payment_leave_amount_cb), pw); box = GTK_WIDGET (gtk_builder_get_object (builder, "date_box")); pw->date_edit = gnc_date_edit_new (time(NULL), FALSE, FALSE); gtk_box_pack_start (GTK_BOX (box), pw->date_edit, TRUE, TRUE, 0); pw->docs_list_tree_view = GTK_WIDGET (gtk_builder_get_object (builder, "docs_list_tree_view")); selection = gtk_tree_view_get_selection (GTK_TREE_VIEW(pw->docs_list_tree_view)); gtk_tree_selection_set_mode (selection, GTK_SELECTION_MULTIPLE); /* Configure date column */ renderer = gtk_cell_renderer_text_new (); column = gtk_tree_view_get_column (GTK_TREE_VIEW (pw->docs_list_tree_view), 0); gtk_tree_view_column_pack_start (column, renderer, TRUE); tree_view_column_set_default_width (GTK_TREE_VIEW (pw->docs_list_tree_view), column, "31-12-2013"); gtk_tree_view_column_set_cell_data_func (column, renderer, (GtkTreeCellDataFunc) print_date, NULL, NULL); /* Configure document number column */ column = gtk_tree_view_get_column (GTK_TREE_VIEW (pw->docs_list_tree_view), 1); tree_view_column_set_default_width (GTK_TREE_VIEW (pw->docs_list_tree_view), column, "INV2013-016"); /* Configure document type column */ column = gtk_tree_view_get_column (GTK_TREE_VIEW (pw->docs_list_tree_view), 2); tree_view_column_set_default_width (GTK_TREE_VIEW (pw->docs_list_tree_view), column, _("Credit Note")); /* Configure debit column */ column = gtk_tree_view_get_column (GTK_TREE_VIEW (pw->docs_list_tree_view), 3); tree_view_column_set_default_width (GTK_TREE_VIEW (pw->docs_list_tree_view), column, "11,999.00"); /* Configure credit column */ column = gtk_tree_view_get_column (GTK_TREE_VIEW (pw->docs_list_tree_view), 4); tree_view_column_set_default_width (GTK_TREE_VIEW (pw->docs_list_tree_view), column, "11,999.00"); gtk_tree_sortable_set_sort_column_id ( GTK_TREE_SORTABLE (gtk_tree_view_get_model (GTK_TREE_VIEW (pw->docs_list_tree_view))), 0, GTK_SORT_ASCENDING); box = GTK_WIDGET (gtk_builder_get_object (builder, "acct_window")); pw->acct_tree = GTK_WIDGET(gnc_tree_view_account_new (FALSE)); gtk_container_add (GTK_CONTAINER (box), pw->acct_tree); gtk_tree_view_set_headers_visible (GTK_TREE_VIEW(pw->acct_tree), FALSE); gnc_payment_set_account_types (GNC_TREE_VIEW_ACCOUNT (pw->acct_tree)); /* Set the dialog for the 'new' owner. * Note that this also sets the post account tree. */ gnc_payment_dialog_owner_changed(pw); /* Set the dialog for the 'new' invoice */ pw->invoice = invoice; if (invoice) { Account *postacct = gncInvoiceGetPostedAcc (invoice); if (postacct) { gchar *acct_string = gnc_account_get_full_name (postacct); gnc_cbwe_set_by_string(GTK_COMBO_BOX(pw->post_combo), acct_string); gnc_payment_dialog_post_to_changed_cb (pw->post_combo, pw); g_free(acct_string); } } /* Setup signals */ gtk_builder_connect_signals_full( builder, gnc_builder_connect_full_func, pw); g_signal_connect (G_OBJECT (pw->owner_choice), "changed", G_CALLBACK (gnc_payment_dialog_owner_changed_cb), pw); g_signal_connect (G_OBJECT (pw->acct_tree), "row-activated", G_CALLBACK (gnc_payment_acct_tree_row_activated_cb), pw); selection = gtk_tree_view_get_selection (GTK_TREE_VIEW(pw->acct_tree)); g_signal_connect (G_OBJECT (selection), "changed", G_CALLBACK (gnc_payment_dialog_xfer_acct_changed_cb), pw); /* Register with the component manager */ pw->component_id = gnc_register_gui_component (cm_class, gnc_payment_window_refresh_handler, gnc_payment_window_close_handler, pw); /* Watch for any new or changed accounts */ gnc_gui_component_watch_entity_type (pw->component_id, GNC_ID_ACCOUNT, QOF_EVENT_CREATE | QOF_EVENT_MODIFY | QOF_EVENT_DESTROY); /* Show it all */ gtk_widget_show_all (pw->dialog); g_object_unref(G_OBJECT(builder)); // The customer choice widget should have keyboard focus if (GNC_IS_GENERAL_SEARCH(pw->owner_choice)) { gnc_general_search_grab_focus(GNC_GENERAL_SEARCH(pw->owner_choice)); } /* Reflect if the payment could complete now */ gnc_payment_window_check_payment (pw); /* Warn the user if they have no valid post-to accounts */ { const gchar *text; const char *acct_type; text = gtk_entry_get_text(GTK_ENTRY (gtk_bin_get_child(GTK_BIN (GTK_COMBO_BOX(pw->post_combo))))); if (!text || g_strcmp0 (text, "") == 0) { /* The code below assumes there will only be one account type. * Let's assert this to protect from potential future changes. */ g_assert (g_list_length (pw->acct_types) == 1); acct_type = xaccAccountGetTypeStr(GPOINTER_TO_INT(pw->acct_types->data)); gnc_warning_dialog(pw->dialog, _("You have no valid \"Post To\" accounts. " "Please create an account of type \"%s\" " "before you continue to process this payment. " "Perhaps you want to create an Invoice or " "Bill first?"), acct_type); } } return pw; }
/* This routine checks to see if GnuCash's gconf schemas are visible * to the user. The schemas typically should be visible, as rpm and * deb installs will put the schemas in the default system location. * For things like network installs or developers, this function will * present a warning dialog that asks the user whether to setup * gconf, continue without the schemas, or quit. If the user chooses * to set up the schemas, this function will invoke an assistant to * walk the user through making the schemas visible. */ void assistant_gconf_install_check_schemas (void) { GtkBuilder *builder; GtkWidget *dialog; gboolean done = FALSE; gint response; if (gnc_gconf_schemas_found()) { gnc_gconf_unset_dir(GCONF_WARNINGS_TEMP, NULL); return; } #ifdef G_OS_WIN32 { /* automatically update the search path on windows */ GError *error = NULL; if (!assistant_gconf_update_path (&error)) { gnc_error_dialog (NULL, error->message); g_error_free (error); exit(42); } else { if (!g_spawn_command_line_sync("gconftool-2 --shutdown", NULL, NULL, NULL, &error)) { gnc_warning_dialog(NULL, error->message); g_error_free(error); } return; } } #endif /* G_OS_WIN32 */ builder = gtk_builder_new(); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "GConf Query"); if (!builder) { gnc_error_dialog(NULL, "The glade UI files were not found. Your installation is incomplete and cannot be run."); exit(-1); /* quit immediately */ } g_assert(builder); dialog = GTK_WIDGET(gtk_builder_get_object (builder, "GConf Query")); g_assert(dialog); do { response = gtk_dialog_run(GTK_DIALOG(dialog)); switch (response) { case GTK_RESPONSE_CANCEL: default: exit(42); /* never returns */ case GTK_RESPONSE_NO: /* User wants to run without setting up gconf */ done = TRUE; break; case GTK_RESPONSE_ACCEPT: gtk_widget_hide(dialog); gnc_gnome_install_gconf_schemas(); done = TRUE; break; case GTK_RESPONSE_HELP: gnc_gnome_help(HF_HELP, HL_GCONF); break; } } while (!done); g_object_unref(G_OBJECT(builder)); gtk_widget_destroy(dialog); }
/** This function build and presents the assistant that presents the user * with the two methods of making the gconf schemas visible, and * learns whether gnucash should do the work or the user will do the * work. This function then blocks in a call to gtk_main(), while * all of the work happens in callback functions. Once the dialog is * finished, this function kills off any existing gconf daemon so * that the changes will be noticed upon daemon restart. */ static GtkWidget * gnc_gnome_install_gconf_schemas (void) { gconf_data *data; GtkBuilder *builder; GtkWidget *dialog; GError *error = NULL; data = g_new0 (gconf_data, 1); builder = gtk_builder_new(); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "textbuffer1"); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "textbuffer2"); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "textbuffer3"); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "textbuffer4"); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "textbuffer5"); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "textbuffer6"); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "textbuffer7"); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "textbuffer8"); gnc_builder_add_from_file (builder, "assistant-gconf-setup.glade", "GConf Setup Assistant"); dialog = GTK_WIDGET(gtk_builder_get_object (builder, "GConf Setup Assistant")); data->dialog = dialog; /* Set the colors for the assistant */ gnc_assistant_set_colors (GTK_ASSISTANT (data->dialog)); /* Enable buttons on all pages. */ gtk_assistant_set_page_complete (GTK_ASSISTANT (dialog), GTK_WIDGET(gtk_builder_get_object(builder, "start_page")), TRUE); gtk_assistant_set_page_complete (GTK_ASSISTANT (dialog), GTK_WIDGET(gtk_builder_get_object(builder, "choose_page")), TRUE); gtk_assistant_set_page_complete (GTK_ASSISTANT (dialog), GTK_WIDGET(gtk_builder_get_object(builder, "update_page")), TRUE); gtk_assistant_set_page_complete (GTK_ASSISTANT (dialog), GTK_WIDGET(gtk_builder_get_object(builder, "step_page")), TRUE); gtk_assistant_set_page_complete (GTK_ASSISTANT (dialog), GTK_WIDGET(gtk_builder_get_object(builder, "install_page")), TRUE); gtk_assistant_set_page_complete (GTK_ASSISTANT (dialog), GTK_WIDGET(gtk_builder_get_object(builder, "finish_page")), TRUE); /* Choose page */ data->update_path = GTK_WIDGET(gtk_builder_get_object (builder, "update_path")); /* Update page */ data->program1 = GTK_WIDGET(gtk_builder_get_object (builder, "program1")); data->user1 = GTK_WIDGET(gtk_builder_get_object (builder, "user1")); data->update_text = GTK_WIDGET(gtk_builder_get_object (builder, "update_text")); /* Install page */ data->program2 = GTK_WIDGET(gtk_builder_get_object (builder, "program2")); data->user2 = GTK_WIDGET(gtk_builder_get_object (builder, "user2")); data->install_text = GTK_WIDGET(gtk_builder_get_object (builder, "install_text")); /* Finish page */ data->finish_page = GTK_WIDGET(gtk_builder_get_object (builder, "finish_page")); gtk_builder_connect_signals(builder, data); g_object_unref(G_OBJECT(builder)); gtk_widget_show_all(dialog); /* This won't return until the dialog is finished */ gtk_main(); /* Destroy the Assistant dialog */ gtk_widget_destroy(GTK_WIDGET(data->dialog)); /* Kill the backend daemon. When it restarts it will find our changes */ if (!g_spawn_command_line_sync("gconftool-2 --shutdown", NULL, NULL, NULL, &error)) { gnc_warning_dialog(NULL, "%s", error->message); g_error_free(error); } return dialog; }