@Override
  public View onCreateView(
      LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    final MyExpenses ctx = (MyExpenses) getActivity();
    if (mAccount == null) {
      TextView tv = new TextView(ctx);
      tv.setText(
          "Error loading transaction list for account " + getArguments().getLong(KEY_ACCOUNTID));
      return tv;
    }
    mManager = getLoaderManager();
    setGrouping();
    setColors();

    View v = inflater.inflate(R.layout.expenses_list, null, false);
    // TODO check if still needed with Appcompat
    // work around the problem that the view pager does not display its background correctly with
    // Sherlock
    if (Build.VERSION.SDK_INT < 11) {
      v.setBackgroundColor(
          ctx.getResources()
              .getColor(
                  MyApplication.PrefKey.UI_THEME_KEY.value("dark").equals("light")
                      ? android.R.color.white
                      : android.R.color.black));
    }
    mListView = (StickyListHeadersListView) v.findViewById(R.id.list);
    setAdapter();
    mListView.setOnHeaderClickListener(this);
    mListView.setDrawingListUnderStickyHeader(false);
    mManager.initLoader(GROUPING_CURSOR, null, this);
    mManager.initLoader(TRANSACTION_CURSOR, null, this);
    mManager.initLoader(SUM_CURSOR, null, this);
    // Now create a simple cursor adapter and set it to display

    mListView.setEmptyView(v.findViewById(R.id.empty));
    mListView.setOnItemClickListener(
        new OnItemClickListener() {
          @Override
          public void onItemClick(AdapterView<?> a, View v, int position, long id) {
            FragmentManager fm = ctx.getSupportFragmentManager();
            DialogFragment f = (DialogFragment) fm.findFragmentByTag("TRANSACTION_DETAIL");
            if (f == null) {
              FragmentTransaction ft = getFragmentManager().beginTransaction();
              ft.add(TransactionDetailFragment.newInstance(id), "TRANSACTION_DETAIL");
              ft.commitAllowingStateLoss();
            }
          }
        });
    registerForContextualActionBar(mListView.getWrappedList());
    return v;
  }
 @Override
 public void onClick(DialogInterface dialog, int which) {
   MyExpenses ctx = (MyExpenses) getActivity();
   if (ctx == null) {
     return;
   }
   Bundle b = getArguments();
   b.putBoolean(
       "deleteP",
       ((CheckBox) ((AlertDialog) dialog).findViewById(R.id.balance_delete)).isChecked());
   b.putInt(ConfirmationDialogFragment.KEY_COMMAND_POSITIVE, R.id.BALANCE_COMMAND_DO);
   ctx.onPositive(b);
 }
 @Override
 public void onHeaderClick(
     StickyListHeadersListView l,
     View header,
     int itemPosition,
     long headerId,
     boolean currentlySticky) {
   MyExpenses ctx = (MyExpenses) getActivity();
   if (mappedCategoriesPerGroup.get(itemPosition)) {
     if (MyApplication.getInstance().isContribEnabled()) {
       ctx.contribFeatureCalled(Feature.DISTRIBUTION, headerId);
     } else {
       CommonCommands.showContribDialog(ctx, Feature.DISTRIBUTION, headerId);
     }
   } else {
     Toast.makeText(ctx, getString(R.string.no_mapped_transactions), Toast.LENGTH_LONG).show();
   }
 }
 @Override
 public void onClick(DialogInterface dialog, int which) {
   MyExpenses ctx = (MyExpenses) getActivity();
   if (ctx != null && which == AlertDialog.BUTTON_POSITIVE) {
     if (mTransaction.transfer_peer != null && DbUtils.hasParent(mTransaction.transfer_peer)) {
       Toast.makeText(
               getActivity(),
               getString(R.string.warning_splitpartcategory_context),
               Toast.LENGTH_LONG)
           .show();
       return;
     }
     Intent i = new Intent(ctx, ExpenseEdit.class);
     i.putExtra(KEY_ROWID, mTransaction.getId());
     i.putExtra(DatabaseConstants.KEY_TRANSFER_ENABLED, ctx.transferEnabled());
     // i.putExtra("operationType", operationType);
     ctx.startActivityForResult(i, MyExpenses.EDIT_TRANSACTION_REQUEST);
   } else {
     this.dismiss();
   }
 }
 @Override
 public boolean dispatchCommandSingle(int command, ContextMenu.ContextMenuInfo info) {
   AdapterContextMenuInfo acmi = (AdapterContextMenuInfo) info;
   MyExpenses ctx = (MyExpenses) getActivity();
   switch (command) {
     case R.id.EDIT_COMMAND:
       mTransactionsCursor.moveToPosition(acmi.position);
       if (DbUtils.getLongOrNull(mTransactionsCursor, "transfer_peer_parent") != null) {
         Toast.makeText(
                 getActivity(),
                 getString(R.string.warning_splitpartcategory_context),
                 Toast.LENGTH_LONG)
             .show();
       } else {
         Intent i = new Intent(ctx, ExpenseEdit.class);
         i.putExtra(KEY_ROWID, acmi.id);
         i.putExtra(DatabaseConstants.KEY_TRANSFER_ENABLED, ctx.transferEnabled());
         ctx.startActivityForResult(i, MyExpenses.EDIT_TRANSACTION_REQUEST);
       }
       // super is handling deactivation of mActionMode
       break;
     case R.id.CREATE_TEMPLATE_COMMAND:
       mTransactionsCursor.moveToPosition(acmi.position);
       String label = mTransactionsCursor.getString(columnIndexPayee);
       if (TextUtils.isEmpty(label)) label = mTransactionsCursor.getString(columnIndexLabelSub);
       if (TextUtils.isEmpty(label)) label = mTransactionsCursor.getString(columnIndexLabelMain);
       Bundle args = new Bundle();
       args.putLong(KEY_ROWID, acmi.id);
       args.putString(
           EditTextDialog.KEY_DIALOG_TITLE, getString(R.string.dialog_title_template_title));
       args.putString(EditTextDialog.KEY_VALUE, label);
       EditTextDialog.newInstance(args).show(ctx.getSupportFragmentManager(), "TEMPLATE_TITLE");
       return true;
   }
   return super.dispatchCommandSingle(command, info);
 }
  @Override
  public Dialog onCreateDialog(Bundle savedInstanceState) {
    final MyExpenses ctx = (MyExpenses) getActivity();
    Context wrappedCtx = DialogUtils.wrapContext2(ctx);
    if (mTransaction == null) {
      return new AlertDialog.Builder(wrappedCtx)
          .setMessage("Transaction has been deleted")
          .create();
    }
    final LayoutInflater li = LayoutInflater.from(wrappedCtx);
    View view = li.inflate(R.layout.transaction_detail, null);
    int title;
    boolean type =
        mTransaction.amount.getAmountMinor() > 0 ? ExpenseEdit.INCOME : ExpenseEdit.EXPENSE;
    if (mTransaction instanceof SplitTransaction) {
      // TODO: refactor duplicated code with SplitPartList
      title = R.string.split_transaction;
      View emptyView = view.findViewById(R.id.empty);
      Resources.Theme theme = ctx.getTheme();
      TypedValue color = new TypedValue();
      theme.resolveAttribute(R.attr.colorExpense, color, true);
      final int colorExpense = color.data;
      theme.resolveAttribute(R.attr.colorIncome, color, true);
      final int colorIncome = color.data;

      ListView lv = (ListView) view.findViewById(R.id.list);
      // Create an array to specify the fields we want to display in the list
      String[] from = new String[] {KEY_LABEL_MAIN, KEY_AMOUNT};

      // and an array of the fields we want to bind those fields to
      int[] to = new int[] {R.id.category, R.id.amount};

      final String categorySeparator, commentSeparator;
      categorySeparator = " : ";
      commentSeparator = " / ";
      // Now create a simple cursor adapter and set it to display
      mAdapter =
          new SimpleCursorAdapter(ctx, R.layout.split_part_row, null, from, to, 0) {
            /* (non-Javadoc)
             * calls {@link #convText for formatting the values retrieved from the cursor}
             * @see android.widget.SimpleCursorAdapter#setViewText(android.widget.TextView, java.lang.String)
             */
            @Override
            public void setViewText(TextView v, String text) {
              switch (v.getId()) {
                case R.id.amount:
                  text = Utils.convAmount(text, mTransaction.amount.getCurrency());
              }
              super.setViewText(v, text);
            }
            /* (non-Javadoc)
             * manipulates the view for amount (setting expenses to red) and
             * category (indicate transfer direction with => or <=
             * @see android.widget.CursorAdapter#getView(int, android.view.View, android.view.ViewGroup)
             */
            @Override
            public View getView(int position, View convertView, ViewGroup parent) {
              View row = super.getView(position, convertView, parent);
              TextView tv1 = (TextView) row.findViewById(R.id.amount);
              Cursor c = getCursor();
              c.moveToPosition(position);
              int col = c.getColumnIndex(KEY_AMOUNT);
              long amount = c.getLong(col);
              if (amount < 0) {
                tv1.setTextColor(colorExpense);
                // Set the background color of the text.
              } else {
                tv1.setTextColor(colorIncome);
              }
              TextView tv2 = (TextView) row.findViewById(R.id.category);
              if (Build.VERSION.SDK_INT < 11) tv2.setTextColor(Color.WHITE);
              String catText = tv2.getText().toString();
              if (DbUtils.getLongOrNull(c, KEY_TRANSFER_PEER) != null) {
                catText = ((amount < 0) ? "=&gt; " : "&lt;= ") + catText;
              } else {
                Long catId = DbUtils.getLongOrNull(c, KEY_CATID);
                if (catId == null) {
                  catText = getString(R.string.no_category_assigned);
                } else {
                  col = c.getColumnIndex(KEY_LABEL_SUB);
                  String label_sub = c.getString(col);
                  if (label_sub != null && label_sub.length() > 0) {
                    catText += categorySeparator + label_sub;
                  }
                }
              }
              col = c.getColumnIndex(KEY_COMMENT);
              String comment = c.getString(col);
              if (comment != null && comment.length() > 0) {
                catText += (catText.equals("") ? "" : commentSeparator) + "<i>" + comment + "</i>";
              }
              tv2.setText(Html.fromHtml(catText));
              return row;
            }
          };
      lv.setAdapter(mAdapter);
      lv.setEmptyView(emptyView);
      LoaderManager manager = ctx.getSupportLoaderManager();
      if (manager.getLoader(MyExpenses.SPLIT_PART_CURSOR) != null
          && !manager.getLoader(MyExpenses.SPLIT_PART_CURSOR).isReset())
        manager.restartLoader(MyExpenses.SPLIT_PART_CURSOR, null, this);
      else manager.initLoader(MyExpenses.SPLIT_PART_CURSOR, null, this);
    } else {
      view.findViewById(R.id.SplitContainer).setVisibility(View.GONE);
      if (mTransaction instanceof Transfer) {
        title = R.string.transfer;
        ((TextView) view.findViewById(R.id.AccountLabel)).setText(R.string.transfer_from_account);
        ((TextView) view.findViewById(R.id.CategoryLabel)).setText(R.string.transfer_to_account);
      } else title = type ? R.string.income : R.string.expense;
    }
    String accountLabel = Account.getInstanceFromDb(mTransaction.accountId).label;
    if (mTransaction instanceof Transfer) {
      ((TextView) view.findViewById(R.id.Account))
          .setText(type ? mTransaction.label : accountLabel);
      ((TextView) view.findViewById(R.id.Category))
          .setText(type ? accountLabel : mTransaction.label);
    } else {
      ((TextView) view.findViewById(R.id.Account)).setText(accountLabel);
      if ((mTransaction.catId != null && mTransaction.catId > 0)) {
        ((TextView) view.findViewById(R.id.Category)).setText(mTransaction.label);
      } else {
        view.findViewById(R.id.CategoryRow).setVisibility(View.GONE);
      }
    }
    ((TextView) view.findViewById(R.id.Date))
        .setText(
            DateFormat.getDateInstance(DateFormat.FULL).format(mTransaction.getDate())
                + " "
                + DateFormat.getTimeInstance(DateFormat.SHORT).format(mTransaction.getDate()));
    ((TextView) view.findViewById(R.id.Amount))
        .setText(
            Utils.formatCurrency(
                new Money(
                    mTransaction.amount.getCurrency(),
                    Math.abs(mTransaction.amount.getAmountMinor()))));
    if (!mTransaction.comment.equals(""))
      ((TextView) view.findViewById(R.id.Comment)).setText(mTransaction.comment);
    else view.findViewById(R.id.CommentRow).setVisibility(View.GONE);
    if (!mTransaction.referenceNumber.equals(""))
      ((TextView) view.findViewById(R.id.Number)).setText(mTransaction.referenceNumber);
    else view.findViewById(R.id.NumberRow).setVisibility(View.GONE);
    if (!mTransaction.payee.equals(""))
      ((TextView) view.findViewById(R.id.Payee)).setText(mTransaction.payee);
    else view.findViewById(R.id.PayeeRow).setVisibility(View.GONE);
    if (mTransaction.methodId != null)
      ((TextView) view.findViewById(R.id.Method))
          .setText(PaymentMethod.getInstanceFromDb(mTransaction.methodId).getDisplayLabel());
    else view.findViewById(R.id.MethodRow).setVisibility(View.GONE);
    if (Account.getInstanceFromDb(mTransaction.accountId).type.equals(Type.CASH))
      view.findViewById(R.id.StatusRow).setVisibility(View.GONE);
    else {
      TextView tv = (TextView) view.findViewById(R.id.Status);
      tv.setBackgroundColor(mTransaction.crStatus.color);
      tv.setText(mTransaction.crStatus.toString());
    }
    return new AlertDialog.Builder(getActivity())
        .setTitle(title)
        .setView(view)
        .setNegativeButton(android.R.string.ok, this)
        .setPositiveButton(R.string.menu_edit, this)
        .create();
  }
  @TargetApi(Build.VERSION_CODES.HONEYCOMB)
  @Override
  public Dialog onCreateDialog(Bundle savedInstanceState) {
    MyExpenses ctx = (MyExpenses) getActivity();
    Bundle args = getArguments();
    Long accountId = args != null ? args.getLong(KEY_ACCOUNTID) : null;
    boolean allP = false, hasExported;
    String warningText;
    final String fileName;
    String now = new SimpleDateFormat("yyyMMdd-HHmmss", Locale.US).format(new Date());

    if (accountId == null) {
      allP = true;
      warningText = getString(R.string.warning_reset_account_all);
      // potential Strict mode violation (currently exporting all accounts with different currencies
      // is not active in the UI)
      hasExported = Account.getHasExported(null);
      fileName = "export" + "-" + now;
    } else {
      Account a = Account.getInstanceFromDb(accountId);
      hasExported = ctx.hasExported();
      if (accountId < 0L) {
        allP = true;
        currency = a.currency.getCurrencyCode();
        fileName = "export" + "-" + currency + "-" + now;
        warningText = getString(R.string.warning_reset_account_all, " (" + currency + ")");
      } else {
        fileName = Utils.escapeForFileName(a.label) + "-" + now;
        warningText = getString(R.string.warning_reset_account);
      }
    }

    LayoutInflater li = LayoutInflater.from(ctx);
    View view = li.inflate(R.layout.export_dialog, null);

    if (args.getBoolean(KEY_IS_FILTERED)) {
      view.findViewById(R.id.with_filter).setVisibility(View.VISIBLE);
      warningText = getString(R.string.warning_reset_account_matched);
    }

    dateFormatET = (EditText) view.findViewById(R.id.date_format);
    String dateFormatDefault =
        ((SimpleDateFormat) DateFormat.getDateInstance(DateFormat.SHORT)).toPattern();
    String dateFormat =
        MyApplication.getInstance().getSettings().getString(PREFKEY_EXPORT_DATE_FORMAT, "");
    if (dateFormat.equals("")) dateFormat = dateFormatDefault;
    else {
      try {
        new SimpleDateFormat(dateFormat, Locale.US);
      } catch (IllegalArgumentException e) {
        dateFormat = dateFormatDefault;
      }
    }
    dateFormatET.setText(dateFormat);
    dateFormatET.addTextChangedListener(
        new TextWatcher() {
          public void afterTextChanged(Editable s) {
            try {
              new SimpleDateFormat(s.toString(), Locale.US);
              mDialog.getButton(AlertDialog.BUTTON_POSITIVE).setEnabled(true);
            } catch (IllegalArgumentException e) {
              dateFormatET.setError(getString(R.string.date_format_illegal));
              mDialog.getButton(AlertDialog.BUTTON_POSITIVE).setEnabled(false);
            }
          }

          public void beforeTextChanged(CharSequence s, int start, int count, int after) {}

          public void onTextChanged(CharSequence s, int start, int before, int count) {}
        });

    fileNameET = (EditText) view.findViewById(R.id.file_name);
    fileNameET.setText(fileName);
    fileNameET.addTextChangedListener(
        new TextWatcher() {
          public void afterTextChanged(Editable s) {
            int error = 0;
            if (s.toString().length() > 0) {
              if (s.toString().indexOf('/') > -1) {
                error = R.string.slash_forbidden_in_filename;
              }
            } else {
              error = R.string.no_title_given;
            }
            mDialog.getButton(AlertDialog.BUTTON_POSITIVE).setEnabled(error == 0);
            if (error != 0) {
              fileNameET.setError(getString(error));
            }
          }

          public void beforeTextChanged(CharSequence s, int start, int count, int after) {}

          public void onTextChanged(CharSequence s, int start, int before, int count) {}
        });

    notYetExportedCB = (CheckBox) view.findViewById(R.id.export_not_yet_exported);
    deleteCB = (CheckBox) view.findViewById(R.id.export_delete);
    warningTV = (TextView) view.findViewById(R.id.warning_reset);

    String encoding =
        MyApplication.getInstance().getSettings().getString(PREFKEY_EXPORT_ENCODING, "UTF-8");

    ((Spinner) view.findViewById(R.id.Encoding))
        .setSelection(
            Arrays.asList(getResources().getStringArray(R.array.pref_qif_export_file_encoding))
                .indexOf(encoding));

    formatRBCSV = (RadioButton) view.findViewById(R.id.csv);
    String format = MyApplication.PrefKey.EXPORT_FORMAT.getString("QIF");
    if (format.equals("CSV")) {
      formatRBCSV.setChecked(true);
    }

    separatorRBComma = (RadioButton) view.findViewById(R.id.comma);
    char separator =
        (char)
            MyApplication.getInstance()
                .getSettings()
                .getInt(ExportTask.KEY_DECIMAL_SEPARATOR, Utils.getDefaultDecimalSeparator());
    if (separator == ',') {
      separatorRBComma.setChecked(true);
    }

    handleDeletedGroup = (RadioGroup) view.findViewById(R.id.handle_deleted);
    View.OnClickListener radioClickListener =
        new View.OnClickListener() {
          public void onClick(View v) {
            int mappedAction =
                v.getId() == R.id.create_helper
                    ? Account.EXPORT_HANDLE_DELETED_CREATE_HELPER
                    : Account.EXPORT_HANDLE_DELETED_UPDATE_BALANCE;
            if (handleDeletedAction == mappedAction) {
              handleDeletedAction = Account.EXPORT_HANDLE_DELETED_DO_NOTHING;
              handleDeletedGroup.clearCheck();
            } else {
              handleDeletedAction = mappedAction;
            }
          }
        };

    final RadioButton updateBalanceRadioButton =
        (RadioButton) view.findViewById(R.id.update_balance);
    final RadioButton createHelperRadioButton = (RadioButton) view.findViewById(R.id.create_helper);
    updateBalanceRadioButton.setOnClickListener(radioClickListener);
    createHelperRadioButton.setOnClickListener(radioClickListener);

    if (savedInstanceState == null) {
      handleDeletedAction =
          MyApplication.getInstance()
              .getSettings()
              .getInt(
                  ExportTask.KEY_EXPORT_HANDLE_DELETED, Account.EXPORT_HANDLE_DELETED_DO_NOTHING);
      if (handleDeletedAction == Account.EXPORT_HANDLE_DELETED_UPDATE_BALANCE) {
        updateBalanceRadioButton.setChecked(true);
      } else if (handleDeletedAction == Account.EXPORT_HANDLE_DELETED_CREATE_HELPER) {
        createHelperRadioButton.setChecked(true);
      }
    }

    deleteCB.setOnCheckedChangeListener(this);
    if (hasExported) {
      notYetExportedCB.setChecked(true);
      notYetExportedCB.setVisibility(View.VISIBLE);
    }

    warningTV.setText(warningText);
    if (allP) {
      ((TextView) view.findViewById(R.id.file_name_label)).setText(R.string.folder_name);
    }
    AlertDialog.Builder builder =
        new AlertDialog.Builder(ctx)
            .setTitle(allP ? R.string.menu_reset_all : R.string.menu_reset)
            .setView(view)
            .setPositiveButton(android.R.string.ok, this)
            .setNegativeButton(android.R.string.cancel, null);
    if (Build.VERSION.SDK_INT < 11) builder.setIcon(android.R.drawable.ic_dialog_alert);
    else builder.setIconAttribute(android.R.attr.alertDialogIcon);
    mDialog = builder.create();
    return mDialog;
  }