package com.vaguehope.onosendai.ui;
import java.util.concurrent.Executor;
import twitter4j.Relationship;
import twitter4j.TwitterException;
import twitter4j.User;
import android.app.AlertDialog;
import android.app.ProgressDialog;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.AsyncTask;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.TextView;
import com.vaguehope.onosendai.R;
import com.vaguehope.onosendai.config.Account;
import com.vaguehope.onosendai.images.ImageLoadRequest;
import com.vaguehope.onosendai.images.ImageLoader;
import com.vaguehope.onosendai.provider.twitter.TwitterProvider;
import com.vaguehope.onosendai.util.DialogHelper;
import com.vaguehope.onosendai.util.LogWrapper;
public class ProfileDialog {
private static final String PROFILE_URL_TEMPLATE = "https://twitter.com/%s";
private static final LogWrapper LOG = new LogWrapper("PD");
public static void show (final Context context, final Executor executor, final ImageLoader imageLoader, final Account account, final String username) {
final ProfileDialog pDlg = new ProfileDialog(context, imageLoader, account, username);
final AlertDialog.Builder dlgBuilder = new AlertDialog.Builder(context);
dlgBuilder.setView(pDlg.getRootView());
final AlertDialog dlg = dlgBuilder.create();
dlg.show();
new FetchUserTask(pDlg, account, username).executeOnExecutor(executor);
}
private final Context context;
private final ImageLoader imageLoader;
private final Account account;
private final View parentView;
private final View lUser;
private final ImageView imgAvatar;
private final TextView txtFullname;
private final TextView txtUsername;
private final TextView txtDescription;
private final Button btnProfile;
private final Button btnFollowUnfollow;
private ProfileDialog (final Context context, final ImageLoader imageLoader, final Account account, final String username) {
this.context = context;
this.imageLoader = imageLoader;
this.account = account;
this.parentView = LayoutInflater.from(context).inflate(R.layout.profile, null);
this.lUser = this.parentView.findViewById(R.id.lUser);
this.imgAvatar = (ImageView) this.parentView.findViewById(R.id.imgAvatar);
this.txtFullname = (TextView) this.parentView.findViewById(R.id.txtFullname);
this.txtUsername = (TextView) this.parentView.findViewById(R.id.txtUsername);
this.txtDescription = (TextView) this.parentView.findViewById(R.id.txtDescription);
this.btnProfile = (Button) this.parentView.findViewById(R.id.btnProfile);
this.btnFollowUnfollow = (Button) this.parentView.findViewById(R.id.btnFollowUnfollow);
this.txtFullname.setText("...");
this.txtUsername.setText(username);
final String profileUrl = String.format(PROFILE_URL_TEMPLATE, username);
this.btnProfile.setText(profileUrl);
this.btnProfile.setOnClickListener(new GoToUrlClickListener(profileUrl));
}
public Context getContext () {
return this.context;
}
private View getRootView () {
return this.parentView;
}
public void showUser (final User user) {
this.txtFullname.setText(user.getName());
this.txtUsername.setText(user.getScreenName());
this.txtDescription.setText(user.getDescription());
this.imageLoader.loadImage(new ImageLoadRequest(user.getBiggerProfileImageURLHttps(), this.imgAvatar));
if (user.isFollowRequestSent()) this.btnFollowUnfollow.setText("Follow requested");
}
public void showRelationship (final Relationship rel, final User targetUser) {
final UserActionTask.UserAction action;
if (rel.isSourceFollowingTarget()) {
action = UserActionTask.UserAction.UNFOLLOW;
}
else {
action = UserActionTask.UserAction.FOLLOW;
}
this.btnFollowUnfollow.setText(action.getVerbInfinitive());
this.btnFollowUnfollow.setOnClickListener(new TaskClickListener(action.getVerbInfinitive(), new UserActionTask(getContext(), this.account, action, targetUser)));
this.btnFollowUnfollow.setEnabled(true);
}
private static class FetchUserTask extends AsyncTask<Void, Object, Exception> {
private final ProfileDialog pDlg;
private final Account account;
private final String username;
public FetchUserTask (final ProfileDialog pDlg, final Account account, final String username) {
this.pDlg = pDlg;
this.account = account;
this.username = username;
}
@Override
protected Exception doInBackground (final Void... params) {
try {
switch (this.account.getProvider()) {
case TWITTER:
fromTwitter();
return null;
default:
return new UnsupportedOperationException("Currently show profile is only supported via Twitter accounts.");
}
}
catch (final Exception e) {
return e;
}
}
private void fromTwitter () throws TwitterException {
final TwitterProvider p = new TwitterProvider();
try {
final User otherUser = p.getUser(this.account, this.username);
publishProgress(otherUser);
if (!otherUser.isFollowRequestSent()) {
publishProgress(p.getRelationship(this.account, otherUser));
}
}
finally {
p.shutdown();
}
}
private User targetUser;
@Override
protected void onProgressUpdate (final Object... values) {
for (final Object val : values) {
if (val instanceof User) {
this.targetUser = (User) val;
this.pDlg.showUser(this.targetUser);
}
else if (val instanceof Relationship) {
this.pDlg.showRelationship((Relationship) val, this.targetUser);
}
}
}
@Override
protected void onPostExecute (final Exception e) {
if (e != null) {
LOG.e("Failed fetch user details.", e);
DialogHelper.alert(this.pDlg.getContext(), e);
}
}
}
private static class GoToUrlClickListener implements OnClickListener {
private final String url;
public GoToUrlClickListener (final String url) {
this.url = url;
}
@Override
public void onClick (final View v) {
v.getContext().startActivity(new Intent(Intent.ACTION_VIEW)
.setData(Uri.parse(this.url)));
}
}
private static class TaskClickListener implements OnClickListener {
private final String yesLbl;
private final AsyncTask<?, ?, ?> task;
public TaskClickListener (final String yesLbl, final AsyncTask<?, ?, ?> task) {
this.yesLbl = yesLbl;
this.task = task;
}
@Override
public void onClick (final View v) {
DialogHelper.askYesNo(v.getContext(), "Are you sure?", this.yesLbl, "Cancel", new Runnable() {
@Override
public void run () {
TaskClickListener.this.task.execute();
}
});
}
}
private static class UserActionTask extends AsyncTask<Void, Void, Exception> {
public enum UserAction {
FOLLOW("Follow", "Following"),
UNFOLLOW("Unfollow", "Unfollowing");
private final String verbInfinitive;
private final String verbPresentParticiple;
private UserAction (final String verbInfinitive, final String verbPresentParticiple) {
this.verbInfinitive = verbInfinitive;
this.verbPresentParticiple = verbPresentParticiple;
}
public String getVerbInfinitive () {
return this.verbInfinitive;
}
public String getVerbPresentParticiple () {
return this.verbPresentParticiple;
}
}
private final Context context;
private final Account account;
private final UserAction action;
private final User targetUser;
private ProgressDialog dialog;
public UserActionTask (final Context context, final Account account, final UserAction action, final User targetUser) {
this.context = context;
this.account = account;
this.action = action;
this.targetUser = targetUser;
}
@Override
protected void onPreExecute () {
this.dialog = ProgressDialog.show(this.context, this.action.getVerbPresentParticiple(), "Please wait...", true);
}
@Override
protected Exception doInBackground (final Void... params) {
try {
switch (this.account.getProvider()) {
case TWITTER:
viaTwitter();
return null;
default:
return new UnsupportedOperationException("Currently show profile is only supported via Twitter accounts.");
}
}
catch (final Exception e) {
return e;
}
}
private void viaTwitter () throws TwitterException {
final TwitterProvider p = new TwitterProvider();
try {
switch (this.action) {
case FOLLOW:
p.follow(this.account, this.targetUser);
break;
case UNFOLLOW:
p.unfollow(this.account, this.targetUser);
break;
default:
throw new UnsupportedOperationException("Unknown action: " + this.action);
}
}
finally {
p.shutdown();
}
}
@Override
protected void onPostExecute (final Exception result) {
this.dialog.dismiss();
if (result == null) {
DialogHelper.alert(this.context, "Success.");
}
else {
LOG.e("Failed.", result);
DialogHelper.alert(this.context, result);
}
}
}
}