package com.mygeopay.wallet.ui;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.Toast;
import com.mygeopay.core.coins.CoinType;
import com.mygeopay.core.wallet.AbstractWallet;
import com.mygeopay.wallet.Constants;
import com.mygeopay.wallet.R;
import com.mygeopay.wallet.WalletApplication;
import com.mygeopay.wallet.util.ThrottlingWalletChangeListener;
import com.mygeopay.wallet.util.UiUtils;
import com.mygeopay.wallet.util.WeakHandler;
import org.bitcoinj.core.Address;
import org.bitcoinj.core.Sha256Hash;
import org.bitcoinj.core.Transaction;
import org.bitcoinj.core.TransactionConfidence;
import org.bitcoinj.core.TransactionOutput;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* Fragment that restores a wallet
*/
public class TransactionDetailsFragment extends Fragment {
private static final Logger log = LoggerFactory.getLogger(TransactionDetailsFragment.class);
private static final int UPDATE_VIEW = 0;
private Sha256Hash txId;
private String accountId;
private AbstractWallet pocket;
private CoinType type;
private ListView outputRows;
private TransactionAmountVisualizerAdapter adapter;
private TextView txStatusView;
private TextView txIdView;
private TextView blockExplorerLink;
private final Handler handler = new MyHandler(this);
private static class MyHandler extends WeakHandler<TransactionDetailsFragment> {
public MyHandler(TransactionDetailsFragment ref) { super(ref); }
@Override
protected void weakHandleMessage(TransactionDetailsFragment ref, Message msg) {
switch (msg.what) {
case UPDATE_VIEW:
ref.updateView();
}
}
}
public TransactionDetailsFragment() {
// Required empty public constructor
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if (getArguments() != null) {
accountId = getArguments().getString(Constants.ARG_ACCOUNT_ID);
}
// TODO
pocket = (AbstractWallet) getWalletApplication().getAccount(accountId);
if (pocket == null) {
Toast.makeText(getActivity(), R.string.no_such_pocket_error, Toast.LENGTH_LONG).show();
return;
}
type = pocket.getCoinType();
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_transaction_details, container, false);
outputRows = (ListView) view.findViewById(R.id.output_rows);
outputRows.setOnItemClickListener(getListener());
// Header
View header = inflater.inflate(R.layout.fragment_transaction_details_header, null);
outputRows.addHeaderView(header, null, false);
txStatusView = (TextView) header.findViewById(R.id.tx_status);
// Footer
View footer = inflater.inflate(R.layout.fragment_transaction_details_footer, null);
outputRows.addFooterView(footer, null, false);
txIdView = (TextView) footer.findViewById(R.id.tx_id);
blockExplorerLink = (TextView) footer.findViewById(R.id.block_explorer_link);
pocket.addEventListener(walletListener);
adapter = new TransactionAmountVisualizerAdapter(inflater.getContext(), pocket);
outputRows.setAdapter(adapter);
String txIdString = getArguments().getString(Constants.ARG_TRANSACTION_ID);
if (txIdString != null) {
txId = new Sha256Hash(txIdString);
}
updateView();
return view;
}
private AdapterView.OnItemClickListener getListener() {
return new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
if (position >= outputRows.getHeaderViewsCount()) {
Object obj = parent.getItemAtPosition(position);
if (obj != null && obj instanceof TransactionOutput) {
TransactionOutput txo = (TransactionOutput) obj;
Address address = txo.getScriptPubKey().getToAddress(type);
UiUtils.startAddressActionMode(address, getActivity(), getFragmentManager());
}
}
}
};
}
@Override
public void onDestroyView() {
pocket.removeEventListener(walletListener);
walletListener.removeCallbacks();
super.onDestroyView();
}
private void updateView() {
if (isRemoving() || isDetached()) return;
if (txId == null) {
cannotShowTxDetails();
} else {
Transaction tx = pocket.getTransaction(txId);
if (tx == null) {
cannotShowTxDetails();
} else {
showTxDetails(pocket, tx);
}
}
}
private void showTxDetails(AbstractWallet pocket, Transaction tx) {
TransactionConfidence confidence = tx.getConfidence();
String txStatusText;
switch (confidence.getConfidenceType()) {
case BUILDING:
txStatusText = getResources().getQuantityString(R.plurals.status_building,
confidence.getDepthInBlocks(), confidence.getDepthInBlocks());
break;
case PENDING:
txStatusText = getString(R.string.status_pending);
break;
default:
case DEAD:
case UNKNOWN:
txStatusText = getString(R.string.status_unknown);
}
txStatusView.setText(txStatusText);
adapter.setTransaction(tx);
txIdView.setText(tx.getHashAsString());
setupBlockExplorerLink(pocket.getCoinType(), tx.getHashAsString());
}
private void setupBlockExplorerLink(CoinType type, String txHash) {
if (Constants.COINS_BLOCK_EXPLORERS.containsKey(type)) {
final String url = String.format(Constants.COINS_BLOCK_EXPLORERS.get(type), txHash);
blockExplorerLink.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent i = new Intent(Intent.ACTION_VIEW);
i.setData(Uri.parse(url));
startActivity(i);
}
});
} else {
blockExplorerLink.setVisibility(View.GONE);
}
}
private void cannotShowTxDetails() {
Toast.makeText(getActivity(), getString(R.string.get_tx_info_error), Toast.LENGTH_LONG).show();
getActivity().finish();
}
WalletApplication getWalletApplication() {
return (WalletApplication) getActivity().getApplication();
}
private final ThrottlingWalletChangeListener walletListener = new ThrottlingWalletChangeListener() {
@Override
public void onThrottledWalletChanged() {
handler.sendMessage(handler.obtainMessage(UPDATE_VIEW));
}
};
}