Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions app/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -325,6 +325,7 @@
</string>
<string name="label_dismiss">Dismiss</string>
<string name="toast_transanction_amount_required">Enter an amount to save the transaction</string>
<string name="toast_error_edit_multi_currency_transaction">Multi-currency transactions cannot be modified</string>
<string name="menu_import_accounts">Import GnuCash Accounts</string>
<string name="btn_import_accounts">Import Accounts</string>
<string name="toast_error_importing_accounts">An error occurred while importing the GnuCash accounts</string>
Expand Down
3 changes: 2 additions & 1 deletion app/src/org/gnucash/android/db/DatabaseAdapter.java
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,8 @@ private void createTempView() {
// ) ,
// 2
// ) as trans_acct_a_uid ,
// TOTAL ( CASE WHEN splits_type = 'DEBIT' THEN splits_amount ELSE - splits_amount END ) AS trans_acct_balance
// TOTAL ( CASE WHEN splits_type = 'DEBIT' THEN splits_amount ELSE - splits_amount END ) AS trans_acct_balance,
// COUNT ( DISTINCT accounts_currency ) as trans_currency_count
// FROM trans_split_acct GROUP BY transactions_uid
//
// This temporary view would pick one Account_UID for each
Expand Down
18 changes: 18 additions & 0 deletions app/src/org/gnucash/android/db/TransactionsDbAdapter.java
Original file line number Diff line number Diff line change
Expand Up @@ -597,4 +597,22 @@ public void scheduleTransaction(Transaction recurringTransaction) {
public Transaction getTransaction(String transactionUID) {
return getTransaction(getID(transactionUID));
}

public int getNumCurrencies(String transactionUID) {
Cursor cursor = mDb.query("trans_extra_info",
new String[]{"trans_currency_count"},
"trans_acct_t_uid=?",
new String[]{transactionUID},
null, null, null);
int numCurrencies = 0;
try {
if (cursor.moveToFirst()) {
numCurrencies = cursor.getInt(0);
}
}
finally {
cursor.close();
}
return numCurrencies;
}
}
5 changes: 1 addition & 4 deletions app/src/org/gnucash/android/model/Transaction.java
Original file line number Diff line number Diff line change
Expand Up @@ -185,10 +185,7 @@ public List<Split> getSplits(String accountUID){
* @param splitList List of splits for this transaction
*/
public void setSplits(List<Split> splitList){
mSplitList.clear();
for (Split split : splitList) {
addSplit(split);
}
mSplitList = splitList;
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -160,6 +160,11 @@ public class TransactionFormFragment extends SherlockFragment implements
*/
private boolean mUseDoubleEntry;

/**
* Flag to not if the transaction involves multiple currency
*/
private boolean mMultiCurrency;

/**
* The AccountType of the account to which this transaction belongs.
* Used for determining the accounting rules for credits and debits
Expand Down Expand Up @@ -220,9 +225,6 @@ public void onActivityCreated(Bundle savedInstanceState) {
mAccountsDbAdapter = new AccountsDbAdapter(getActivity());
mAccountType = mAccountsDbAdapter.getAccountType(mAccountUID);

//updateTransferAccountsList must only be called after initializing mAccountsDbAdapter
updateTransferAccountsList();

ArrayAdapter<CharSequence> recurrenceAdapter = ArrayAdapter.createFromResource(getActivity(),
R.array.recurrence_period_strings, android.R.layout.simple_spinner_item);
recurrenceAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
Expand All @@ -231,6 +233,13 @@ public void onActivityCreated(Bundle savedInstanceState) {
String transactionUID = getArguments().getString(UxArgument.SELECTED_TRANSACTION_UID);
mTransactionsDbAdapter = new TransactionsDbAdapter(getActivity());
mTransaction = mTransactionsDbAdapter.getTransaction(transactionUID);
if (mTransaction != null) {
mMultiCurrency = mTransactionsDbAdapter.getNumCurrencies(mTransaction.getUID()) > 1;
}

//updateTransferAccountsList must only be called after initializing mAccountsDbAdapter
// it needs mMultiCurrency to be properly initialized
updateTransferAccountsList();

mDoubleAccountSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
@Override
Expand Down Expand Up @@ -361,6 +370,23 @@ private void initializeViewsWithTransaction(){
mCurrencyTextView.setText(accountCurrency.getSymbol());

setSelectedRecurrenceOption();
if (mMultiCurrency) {
enableControls(false);
}
}

private void enableControls(boolean b) {
mDescriptionEditText.setEnabled(b);
mNotesEditText.setEnabled(b);
mDateTextView.setEnabled(b);
mTimeTextView.setEnabled(b);
mAmountEditText.setEnabled(b);
mCurrencyTextView.setEnabled(b);
mTransactionTypeButton.setEnabled(b);
mDoubleAccountSpinner.setEnabled(b);
// the next is always enabled, so the user can check the detailed info of splits
// mOpenSplitsButton;
mRecurringTransactionSpinner.setEnabled(b);
}

private void setAmountEditViewVisible(int visibility) {
Expand Down Expand Up @@ -426,8 +452,8 @@ private void updateTransferAccountsList(){
String accountUID = ((TransactionsActivity)getActivity()).getCurrentAccountUID();

String conditions = "(" + DatabaseSchema.AccountEntry.COLUMN_UID + " != '" + accountUID
+ "' AND " + DatabaseSchema.AccountEntry.COLUMN_CURRENCY + " = '" + mAccountsDbAdapter.getCurrencyCode(accountUID)
+ "' AND " + DatabaseSchema.AccountEntry.COLUMN_UID + " != '" + mAccountsDbAdapter.getGnuCashRootAccountUID()
+ "' AND " + (mMultiCurrency ? "" : (DatabaseSchema.AccountEntry.COLUMN_CURRENCY + " = '" + mAccountsDbAdapter.getCurrencyCode(accountUID)
+ "' AND ")) + DatabaseSchema.AccountEntry.COLUMN_UID + " != '" + mAccountsDbAdapter.getGnuCashRootAccountUID()
+ "' AND " + DatabaseSchema.AccountEntry.COLUMN_PLACEHOLDER + " = 0"
+ ")";

Expand Down Expand Up @@ -459,7 +485,7 @@ private void openSplitEditor(){
} else {
Money biggestAmount = Money.createZeroInstance(mTransaction.getCurrencyCode());
for (Split split : mTransaction.getSplits()) {
if (split.getAmount().compareTo(biggestAmount) > 0)
if (split.getAmount().asBigDecimal().compareTo(biggestAmount.asBigDecimal()) > 0)
biggestAmount = split.getAmount();
}
baseAmountString = biggestAmount.toPlainString();
Expand Down Expand Up @@ -545,19 +571,23 @@ public void run() {
* Callback when the account in the navigation bar is changed by the user
* @param newAccountId Database record ID of the newly selected account
*/
public void onAccountChanged(long newAccountId){
AccountsDbAdapter accountsDbAdapter = new AccountsDbAdapter(getActivity());
String currencyCode = accountsDbAdapter.getCurrencyCode(newAccountId);
Currency currency = Currency.getInstance(currencyCode);
mCurrencyTextView.setText(currency.getSymbol(Locale.getDefault()));
public void onAccountChanged(long newAccountId) {
if (mMultiCurrency) {
Toast.makeText(getActivity(), R.string.toast_error_edit_multi_currency_transaction, Toast.LENGTH_LONG).show();
return;
}
AccountsDbAdapter accountsDbAdapter = new AccountsDbAdapter(getActivity());
String currencyCode = accountsDbAdapter.getCurrencyCode(newAccountId);
Currency currency = Currency.getInstance(currencyCode);
mCurrencyTextView.setText(currency.getSymbol(Locale.getDefault()));

mAccountType = accountsDbAdapter.getAccountType(newAccountId);
mTransactionTypeButton.setAccountType(mAccountType);

updateTransferAccountsList();
updateTransferAccountsList();

accountsDbAdapter.close();
}
}

/**
* Collects information from the fragment views and uses it to create
Expand Down Expand Up @@ -700,7 +730,11 @@ public boolean onOptionsItemSelected(MenuItem item) {
return true;

case R.id.menu_save:
if (mAmountEditText.getText().length() == 0){
if (mMultiCurrency) {
Toast.makeText(getActivity(), R.string.toast_error_edit_multi_currency_transaction, Toast.LENGTH_LONG).show();
finish();
}
else if (mAmountEditText.getText().length() == 0) {
Toast.makeText(getActivity(), R.string.toast_transanction_amount_required, Toast.LENGTH_SHORT).show();
} else
saveNewTransaction();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,8 @@ public class SplitEditorDialogFragment extends DialogFragment {
private BigDecimal mBaseAmount = BigDecimal.ZERO;

private List<String> mRemovedSplitUIDs = new ArrayList<String>();

private boolean mMultiCurrency = false;
/**
* Create and return a new instance of the fragment with the appropriate paramenters
* @param baseAmountString String with base amount which is being split
Expand Down Expand Up @@ -102,13 +104,24 @@ public void onActivityCreated(Bundle savedInstanceState) {

getDialog().setTitle("Transaction splits");

initArgs();
mSplitItemViewList = new ArrayList<View>();
mSplitsDbAdapter = new SplitsDbAdapter(getActivity());

//we are editing splits for a new transaction.
// But the user may have already created some splits before. Let's check
List<Split> splitList = ((TransactionFormFragment) getTargetFragment()).getSplitList();
{
Currency currency = null;
for (Split split : splitList) {
if (currency == null) {
currency = split.getAmount().getCurrency();
} else if (currency != split.getAmount().getCurrency()) {
mMultiCurrency = true;
}
}
}

initArgs();
if (!splitList.isEmpty()) {
//aha! there are some splits. Let's load those instead
loadSplitViews(splitList);
Expand All @@ -131,6 +144,28 @@ private void loadSplitViews(List<Split> splitList) {
for (Split split : splitList) {
addSplitView(split);
}
if (mMultiCurrency) {
enableAllControls(false);
}
}

private void enableAllControls(boolean b) {
for (View splitView : mSplitItemViewList) {
EditText splitMemoEditText = (EditText) splitView.findViewById(R.id.input_split_memo);
final EditText splitAmountEditText = (EditText) splitView.findViewById(R.id.input_split_amount);
ImageButton removeSplitButton = (ImageButton) splitView.findViewById(R.id.btn_remove_split);
Spinner accountsSpinner = (Spinner) splitView.findViewById(R.id.input_accounts_spinner);
final TextView splitCurrencyTextView = (TextView) splitView.findViewById(R.id.split_currency_symbol);
final TextView splitUidTextView = (TextView) splitView.findViewById(R.id.split_uid);
final TransactionTypeToggleButton splitTypeButton = (TransactionTypeToggleButton) splitView.findViewById(R.id.btn_split_type);
splitMemoEditText.setEnabled(b);
splitAmountEditText.setEnabled(b);
removeSplitButton.setEnabled(b);
accountsSpinner.setEnabled(b);
splitCurrencyTextView.setEnabled(b);
splitUidTextView.setEnabled(b);
splitTypeButton.setEnabled(b);
}
}

/**
Expand Down Expand Up @@ -158,8 +193,8 @@ private void initArgs() {
mBaseAmount = new BigDecimal(args.getString(UxArgument.AMOUNT_STRING));

String conditions = "(" //+ AccountEntry._ID + " != " + mAccountId + " AND "
+ DatabaseSchema.AccountEntry.COLUMN_CURRENCY + " = '" + mAccountsDbAdapter.getCurrencyCode(mAccountUID)
+ "' AND " + DatabaseSchema.AccountEntry.COLUMN_UID + " != '" + mAccountsDbAdapter.getGnuCashRootAccountUID()
+ (mMultiCurrency ? "" : (DatabaseSchema.AccountEntry.COLUMN_CURRENCY + " = '" + mAccountsDbAdapter.getCurrencyCode(mAccountUID)
+ "' AND ")) + DatabaseSchema.AccountEntry.COLUMN_UID + " != '" + mAccountsDbAdapter.getGnuCashRootAccountUID()
+ "' AND " + DatabaseSchema.AccountEntry.COLUMN_PLACEHOLDER + " = 0"
+ ")";
mCursor = mAccountsDbAdapter.fetchAccountsOrderedByFullName(conditions);
Expand Down Expand Up @@ -194,7 +229,7 @@ public void onClick(View view) {
updateTransferAccountsList(accountsSpinner);
accountsSpinner.setOnItemSelectedListener(new TypeButtonLabelUpdater(splitTypeButton));

Currency accountCurrency = Currency.getInstance(mAccountsDbAdapter.getCurrencyCode(mAccountUID));
Currency accountCurrency = Currency.getInstance(mAccountsDbAdapter.getCurrencyCode(split.getAccountUID()));
splitCurrencyTextView.setText(accountCurrency.getSymbol());
splitTypeButton.setAmountFormattingListener(splitAmountEditText, splitCurrencyTextView);
splitTypeButton.setChecked(mBaseAmount.signum() > 0);
Expand Down Expand Up @@ -258,17 +293,26 @@ public void onClick(View view) {
mSaveButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
List<Split> splitList = extractSplitsFromView();
((TransactionFormFragment) getTargetFragment()).setSplitList(splitList, mRemovedSplitUIDs);

if (mMultiCurrency) {
Toast.makeText(getActivity(), R.string.toast_error_edit_multi_currency_transaction, Toast.LENGTH_LONG).show();
}
else {
List<Split> splitList = extractSplitsFromView();
((TransactionFormFragment) getTargetFragment()).setSplitList(splitList, mRemovedSplitUIDs);
}
dismiss();
}
});

mAddSplit.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
addSplitView(null);
if (mMultiCurrency) {
Toast.makeText(getActivity(), R.string.toast_error_edit_multi_currency_transaction, Toast.LENGTH_LONG).show();
}
else {
addSplitView(null);
}
}
});
}
Expand Down Expand Up @@ -307,15 +351,15 @@ private void updateTotal(){
List<Split> splitList = extractSplitsFromView();
String currencyCode = mAccountsDbAdapter.getCurrencyCode(mAccountUID);
Money splitSum = Money.createZeroInstance(currencyCode);

for (Split split : splitList) {
Money amount = split.getAmount().absolute();
if (split.getType() == TransactionType.DEBIT)
splitSum = splitSum.subtract(amount);
else
splitSum = splitSum.add(amount);
if (!mMultiCurrency) {
for (Split split : splitList) {
Money amount = split.getAmount().absolute();
if (split.getType() == TransactionType.DEBIT)
splitSum = splitSum.subtract(amount);
else
splitSum = splitSum.add(amount);
}
}

TransactionsActivity.displayBalance(mImbalanceTextView, splitSum);
}

Expand Down