// Copyright (C) 2016 The Android Open Source Project
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package com.google.reviewit;

import android.app.Fragment;
import android.content.Context;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.annotation.LayoutRes;
import android.util.Log;
import android.util.TypedValue;
import android.view.KeyEvent;
import android.view.inputmethod.EditorInfo;
import android.widget.ArrayAdapter;
import android.widget.AutoCompleteTextView;
import android.widget.Filter;
import android.widget.Filterable;
import android.widget.ImageView;
import android.widget.TableLayout;
import android.widget.TableRow;
import android.widget.TextView;

import com.google.gerrit.extensions.common.AccountInfo;
import com.google.gerrit.extensions.restapi.RestApiException;
import com.google.reviewit.app.Change;
import com.google.reviewit.util.ChangeUtil;
import com.google.reviewit.widget.ChangeBox;
import com.google.reviewit.util.FormatUtil;
import com.google.reviewit.util.WidgetUtil;
import com.urswolfer.gerrit.client.rest.http.HttpStatusException;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;

import static com.google.reviewit.util.LayoutUtil.matchAndWrapTableLayout;
import static com.google.reviewit.util.LayoutUtil.matchAndWrapTableRowLayout;
import static com.google.reviewit.util.LayoutUtil.wrapTableRowLayout;

/**
 * Fragment to add a reviewer to a change.
 * On typing reviewer names are auto-completed.
 */
public class AddReviewerFragment extends BaseFragment
    implements OnBackPressedAware {
  private static final String TAG = AddReviewerFragment.class.getName();
  private static final String ORIGIN =
      "com.google.reviewit.AddReviewerFragment.ORIGIN";

  public static AddReviewerFragment create(Class<? extends Fragment> origin) {
    AddReviewerFragment fragment = new AddReviewerFragment();
    Bundle bundle = new Bundle();
    bundle.putSerializable(ORIGIN, origin);
    fragment.setArguments(bundle);
    return fragment;
  }

  @Override
  protected @LayoutRes int getLayout() {
    return R.layout.content_add_reviewer;
  }

  @Override
  public void onActivityCreated(Bundle savedInstanceState) {
    super.onActivityCreated(savedInstanceState);

    Change change = getApp().getActionHandler().getCurrentChange();
    initInputField(change);
    try {
      displayReviewers(change);
      displayCCs(change);
      ChangeUtil.colorBackground(root, change);
      ((ChangeBox) v(R.id.changeBox)).display(getApp(), change);
    } catch (Throwable t) {
      Log.e(TAG, "Failed to display change", t);
      display(ErrorFragment.create(t));
    }
  }

  private void initInputField(final Change change) {
    AutoCompleteTextView editText =
        (AutoCompleteTextView) v(R.id.reviewerInput);
    editText.setOnEditorActionListener(new TextView.OnEditorActionListener() {
      @Override
      public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
        boolean handled = false;
        if (actionId == EditorInfo.IME_ACTION_SEND) {
          addReviewer(change, v.getText().toString());
          handled = true;
        }
        return handled;
      }
    });
    editText.setAdapter(new SuggestReviewerAdapter(getContext()));
  }

  private void addReviewer(Change change, final String reviewerId) {
    new AsyncTask<Change, Void, String>() {
      @Override
      protected String doInBackground(Change... changes) {
        Change change = changes[0];
        try {
          change.addReviewer(reviewerId);
          return null;
        } catch (RestApiException e) {
          Log.w(TAG, "Adding reviewer failed", e);
          if (e instanceof HttpStatusException) {
            HttpStatusException se = (HttpStatusException) e;
            return getString(R.string.add_reviewer_error, se.getStatusCode(),
                se.getStatusText());
          } else {
            return e.getMessage();
          }
        }
      }

      protected void onPostExecute(String errorMsg) {
        if (errorMsg != null) {
          widgetUtil.showError(errorMsg);
        } else {
          AddReviewerFragment fragment = new AddReviewerFragment();
          Bundle bundle = new Bundle();
          bundle.putAll(getArguments());
          fragment.setArguments(bundle);
          display(fragment, false);
        }
      }
    }.execute(change);
  }


  private void displayReviewers(Change change) {
    TableLayout tl = (TableLayout) v(R.id.reviewerTable);
    Collection<AccountInfo> reviewers = change.reviewers(false);
    if (!reviewers.isEmpty()) {
      for (AccountInfo reviewer : reviewers) {
        addReviewerRow(tl, reviewer);
      }
    } else {
      WidgetUtil.setText(v(R.id.reviewersLabel),
          getString(R.string.no_reviewers));
    }
  }

  private void displayCCs(Change change) {
    TableLayout tl = (TableLayout) v(R.id.reviewerTable);
    Collection<AccountInfo> ccs = change.ccs();
    if (!ccs.isEmpty()) {
      TableRow tr = new TableRow(getContext());
      tr.setLayoutParams(matchAndWrapTableRowLayout());
      TextView ccsTitle = new TextView(getContext());
      TableRow.LayoutParams params = wrapTableRowLayout(2);
      params.bottomMargin = widgetUtil.dpToPx(3);
      ccsTitle.setLayoutParams(params);
      ccsTitle.setTextSize(TypedValue.COMPLEX_UNIT_SP, 20);
      ccsTitle.setText(getString(R.string.ccs));
      tr.addView(ccsTitle);
      tl.addView(tr, matchAndWrapTableLayout());
      for (AccountInfo cc : ccs) {
        addReviewerRow(tl, cc);
      }
    }
  }

  private void addReviewerRow(TableLayout tl, AccountInfo reviewer) {
    TableRow tr = new TableRow(getContext());
    tr.setLayoutParams(matchAndWrapTableRowLayout());
    ImageView avatar = new ImageView(getContext());
    TableRow.LayoutParams layoutParams = new TableRow.LayoutParams(
        widgetUtil.dpToPx(20), widgetUtil.dpToPx(20));
    layoutParams.setMargins(0, 0, widgetUtil.dpToPx(5), widgetUtil.dpToPx(2));
    avatar.setLayoutParams(layoutParams);

    WidgetUtil.displayAvatar(getApp(), reviewer, avatar);
    tr.addView(avatar);
    TextView reviewerName = new TextView(getContext());
    reviewerName.setLayoutParams(wrapTableRowLayout());
    reviewerName.setText(FormatUtil.format(reviewer));
    tr.addView(reviewerName);
    tl.addView(tr, matchAndWrapTableLayout());
  }

  @Override
  public boolean onBackPressed() {
    display((Class<? extends Fragment>) getArguments().get(ORIGIN),
        getArguments(), false);
    return true;
  }

  private class SuggestReviewerAdapter extends ArrayAdapter<String>
      implements Filterable {
    private List<String> suggestions;

    public SuggestReviewerAdapter(Context context) {
      super(context, android.R.layout.simple_dropdown_item_1line);
      suggestions = Collections.emptyList();
    }

    @Override
    public int getCount() {
      return suggestions.size();
    }

    @Override
    public String getItem(int index) {
      return suggestions.get(index);
    }

    @Override
    public Filter getFilter() {
      return new Filter() {
        @Override
        protected FilterResults performFiltering(CharSequence constraint) {
          FilterResults filterResults = new FilterResults();
          if (constraint != null) {
            suggestions = suggest(constraint.toString());
            filterResults.values = suggestions;
            filterResults.count = suggestions.size();
          }
          return filterResults;
        }

        @Override
        protected void publishResults(
            CharSequence constraint, FilterResults results) {
          if (results != null && results.count > 0) {
            notifyDataSetChanged();
          } else {
            notifyDataSetInvalidated();
          }
        }
      };
    }

    private List<String> suggest(String text) {
      List<String> suggestions = new ArrayList<>();
      try {
        for (AccountInfo a
            : getApp().getApi()
                .accounts()
                .suggestAccounts(text)
                .withLimit(10)
                .get()) {
          suggestions.add(FormatUtil.format(a));
        }
      } catch (RestApiException e) {
        Log.e(TAG, "Suggesting reviewers failed", e);
      }
      return suggestions;
    }
  }
}
