package com.mozu.mozuandroidinstoreassistant.app.order;
import android.app.AlertDialog;
import android.app.Dialog;
import android.app.DialogFragment;
import android.content.DialogInterface;
import android.graphics.Bitmap;
import android.graphics.drawable.BitmapDrawable;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.util.ArrayMap;
import android.text.TextUtils;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.Window;
import android.widget.BaseAdapter;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.ProgressBar;
import android.widget.Spinner;
import android.widget.TextView;
import com.mozu.api.ApiException;
import com.mozu.api.contracts.commerceruntime.orders.Order;
import com.mozu.api.contracts.commerceruntime.orders.OrderItem;
import com.mozu.api.contracts.commerceruntime.products.ProductOption;
import com.mozu.api.contracts.productadmin.ProductVariation;
import com.mozu.api.contracts.productadmin.ProductVariationOption;
import com.mozu.api.contracts.productadmin.ProductVariationPagedCollection;
import com.mozu.api.contracts.productruntime.ProductOptionValue;
import com.mozu.mozuandroidinstoreassistant.MozuApplication;
import com.mozu.mozuandroidinstoreassistant.app.R;
import com.mozu.mozuandroidinstoreassistant.app.data.product.FulfillmentInfo;
import com.mozu.mozuandroidinstoreassistant.app.dialog.ErrorMessageAlertDialog;
import com.mozu.mozuandroidinstoreassistant.app.models.ImageURLConverter;
import com.mozu.mozuandroidinstoreassistant.app.models.authentication.UserAuthenticationStateMachine;
import com.mozu.mozuandroidinstoreassistant.app.models.authentication.UserAuthenticationStateMachineProducer;
import com.mozu.mozuandroidinstoreassistant.app.order.loaders.NewOrderManager;
import com.mozu.mozuandroidinstoreassistant.app.utils.ProductUtils;
import com.mozu.mozuandroidinstoreassistant.app.views.ProductOptionsLayout;
import com.squareup.picasso.Callback;
import com.squareup.picasso.Picasso;
import com.squareup.picasso.RequestCreator;
import java.text.NumberFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import butterknife.ButterKnife;
import butterknife.InjectView;
import rx.Subscriber;
import rx.android.observables.AndroidObservable;
import rx.subscriptions.CompositeSubscription;
public class NewOrderItemEditFragment extends DialogFragment implements ProductOptionsLayout.onOptionChangeListener {
private static final String ORDER_ITEM = "orderItem";
private static final String ORDER_ID = "orderId";
private static final String EDIT_MODE = "editmode";
@InjectView(R.id.product_code)
public TextView productCode;
@InjectView(R.id.product_name)
public TextView productName;
@InjectView(R.id.product_price)
public TextView productPrice;
@InjectView(R.id.product_quantity)
public EditText productQuantity;
@InjectView(R.id.product_total)
public TextView productTotal;
@InjectView(R.id.product_save)
public Button productSave;
@InjectView(R.id.order_item_delete)
public Button orderItemDelete;
@InjectView(R.id.fulfillment_type)
public Spinner fulfillmentType;
@InjectView(R.id.product_variation_layout)
public LinearLayout productVariationLayout;
@InjectView(R.id.product_variation_progress)
public ProgressBar productVariationProgress;
@InjectView(R.id.fulfillment_spinner_progress)
public ProgressBar fulfillmentSpinnerProgress;
@InjectView(R.id.options_layout)
public LinearLayout mOptionsLayout;
@InjectView(R.id.product_loading)
public LinearLayout mProductLoading;
@InjectView(R.id.main_product_image)
public ImageView mMainProductImage;
private OrderItem mOrderItem;
private String mOrderId;
private View mView;
private boolean isEditMode = false;
private int mTenantId;
private int mSiteId;
private onItemEditDoneListener mEditDoneListener;
private SpinnerAdapter mSpinnerAdapter;
private ProductVariationPagedCollection mProductVariationCollection;
private CompositeSubscription mCompositeSubscription;
private String mSiteDomain;
public static NewOrderItemEditFragment getInstance(OrderItem orderItem, String orderId, Boolean isEditMode) {
NewOrderItemEditFragment newOrderItemEditFragment = new NewOrderItemEditFragment();
Bundle b = new Bundle();
b.putSerializable(ORDER_ITEM, orderItem);
b.putString(ORDER_ID, orderId);
b.putBoolean(EDIT_MODE, isEditMode);
newOrderItemEditFragment.setArguments(b);
return newOrderItemEditFragment;
}
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
UserAuthenticationStateMachine userAuthenticationStateMachine = UserAuthenticationStateMachineProducer.getInstance(getActivity());
mCompositeSubscription = new CompositeSubscription();
mTenantId = userAuthenticationStateMachine.getTenantId();
mSiteId = userAuthenticationStateMachine.getSiteId();
mSiteDomain = userAuthenticationStateMachine.getSiteDomain();
if (getArguments() != null) {
mOrderId = getArguments().getString(ORDER_ID);
mOrderItem = (OrderItem) getArguments().getSerializable(ORDER_ITEM);
isEditMode = getArguments().getBoolean(EDIT_MODE);
}
mView = inflater.inflate(R.layout.neworder_item_edit_fragment, null);
ButterKnife.inject(this, mView);
if (mOrderItem != null) {
setupViews();
}
return mView;
}
@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
if (ProductUtils.isProductConfigurable(mOrderItem.getProduct())) {
if (!isEditMode) {
loadProductVariations(mOrderItem.getProduct().getProductCode());
} else {
mProductVariationCollection = new ProductVariationPagedCollection();
List<ProductVariation> productVariations = new ArrayList<>();
ProductVariation productVariation = new ProductVariation();
if (!TextUtils.isEmpty(mOrderItem.getProduct().getVariationProductCode())) {
productVariation.setVariationProductCode(mOrderItem.getProduct().getVariationProductCode());
} else {
productVariation.setVariationProductCode(mOrderItem.getProduct().getProductCode());
}
List<ProductVariationOption> productVariationOptions = new ArrayList<>();
for (ProductOption productOption : mOrderItem.getProduct().getOptions()) {
ProductVariationOption productVariationOption = new ProductVariationOption();
productVariationOption.setAttributeFQN(productOption.getAttributeFQN());
productVariationOption.setValue(productOption.getValue());
productVariationOptions.add(productVariationOption);
}
productVariation.setOptions(productVariationOptions);
productVariations.add(productVariation);
mProductVariationCollection.setItems(productVariations);
setVariations();
onOptionChanged();
}
} else {
productVariationLayout.setVisibility(View.GONE);
loadLocations(mOrderItem.getProduct().getProductCode());
}
}
private void setImage(String productImageUrl) {
ImageURLConverter mImageUrlConverter = new ImageURLConverter(mTenantId, mSiteId, mSiteDomain);
String imageUrl = mImageUrlConverter.getFullImageUrl(productImageUrl);
if (TextUtils.isEmpty(imageUrl)) {
return;
}
RequestCreator creator = Picasso.with(getActivity())
.load(imageUrl);
creator = creator.placeholder(R.drawable.icon_noproductphoto).fit().centerInside();
mMainProductImage.setBackgroundColor(getActivity().getResources().getColor(R.color.darker_grey));
creator.into(mMainProductImage, new Callback() {
@Override
public void onSuccess() {
Bitmap bitmap = ((BitmapDrawable) mMainProductImage.getDrawable()).getBitmap();
mMainProductImage.setBackgroundColor(bitmap.getPixel(0, 0));
}
@Override
public void onError() {
}
});
}
private void loadProductVariations(String productCode) {
productSave.setEnabled(false);
productVariationProgress.setVisibility(View.VISIBLE);
mCompositeSubscription.add(AndroidObservable.bindFragment(this, NewOrderManager.getInstance().getProductVariationCodes(mTenantId, mSiteId, productCode))
.subscribe(new Subscriber<ProductVariationPagedCollection>() {
@Override
public void onCompleted() {
productVariationProgress.setVisibility(View.GONE);
productSave.setEnabled(true);
setVariations();
onOptionChanged();
}
@Override
public void onError(Throwable e) {
ErrorMessageAlertDialog.getStandardErrorMessageAlertDialog(getActivity(), e.getMessage());
}
@Override
public void onNext(ProductVariationPagedCollection productVariationPagedCollection) {
if (productVariationPagedCollection != null) {
mProductVariationCollection = productVariationPagedCollection;
}
}
}));
}
private void setVariations() {
HashMap<String, Set<String>> optionsMap = new HashMap<>();
for (ProductVariation productVariation : mProductVariationCollection.getItems()) {
for (ProductVariationOption option : productVariation.getOptions()) {
if (optionsMap.containsKey(option.getAttributeFQN())) {
Set<String> optionsList = optionsMap.get(option.getAttributeFQN());
optionsList.add(option.getValue().toString());
} else {
Set<String> optionsList = new HashSet<>();
optionsList.add(option.getValue().toString());
optionsMap.put(option.getAttributeFQN(), optionsList);
}
}
}
for (String attributeFQN : optionsMap.keySet()) {
ProductOptionsLayout optionsLayout = new ProductOptionsLayout(getActivity(), this);
optionsLayout.setAttributeFQN(attributeFQN);
optionsLayout.setTitle(attributeFQN.substring(attributeFQN.indexOf("~") + 1, attributeFQN.length()));
List<ProductOptionValue> productOptionValues = new ArrayList<>();
for (String value : optionsMap.get(attributeFQN)) {
ProductOptionValue productOptionValue = new ProductOptionValue();
productOptionValue.setValue(value);
productOptionValues.add(productOptionValue);
}
optionsLayout.setSpinnerOptions(productOptionValues);
mOptionsLayout.addView(optionsLayout);
}
}
@Override
public void onDestroyView() {
super.onDestroyView();
if (mCompositeSubscription != null && !mCompositeSubscription.isUnsubscribed()) {
mCompositeSubscription.unsubscribe();
}
}
private void loadLocations(final String productCode) {
final ArrayMap<String, String> mLocationMap = ((MozuApplication) getActivity().getApplication()).getLocations();
if (mLocationMap.size() < 1) {
mCompositeSubscription.add(AndroidObservable.bindFragment(this, NewOrderManager.getInstance().getLocationsData(mTenantId, mSiteId, false))
.subscribe(new Subscriber<ArrayMap<String, String>>() {
@Override
public void onCompleted() {
}
@Override
public void onError(Throwable e) {
ErrorMessageAlertDialog.getStandardErrorMessageAlertDialog(getActivity(), getResources().getString(R.string.order_fulfillment_error));
productSave.setVisibility(View.GONE);
}
@Override
public void onNext(ArrayMap<String, String> locationMap) {
((MozuApplication) getActivity().getApplication()).setLocations(locationMap);
loadInventory(productCode, locationMap);
}
}));
} else {
loadInventory(productCode, mLocationMap);
}
}
private void loadInventory(final String productCode, ArrayMap<String, String> locationMap) {
if (locationMap.size() < 1) {
ErrorMessageAlertDialog.getStandardErrorMessageAlertDialog(getActivity(), getResources().getString(R.string.order_fulfillment_error));
return;
}
productSave.setEnabled(false);
fulfillmentSpinnerProgress.setVisibility(View.VISIBLE);
mCompositeSubscription.add(AndroidObservable.bindFragment(this, NewOrderManager.getInstance().getInventory(mTenantId, mSiteId, productCode, locationMap))
.subscribe(new Subscriber<List<FulfillmentInfo>>() {
@Override
public void onCompleted() {
fulfillmentSpinnerProgress.setVisibility(View.GONE);
productSave.setEnabled(true);
setSpinnerSelection(mSpinnerAdapter, mOrderItem.getFulfillmentMethod(), mOrderItem.getFulfillmentLocationCode());
}
@Override
public void onError(Throwable e) {
ErrorMessageAlertDialog.getStandardErrorMessageAlertDialog(getActivity(), getResources().getString(R.string.order_fulfillment_error));
productSave.setVisibility(View.GONE);
}
@Override
public void onNext(List<FulfillmentInfo> fulfillmentInfos) {
mSpinnerAdapter.setData(fulfillmentInfos);
mSpinnerAdapter.notifyDataSetChanged();
}
}));
}
@Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
Dialog dialog = super.onCreateDialog(savedInstanceState);
dialog.getWindow().requestFeature(Window.FEATURE_NO_TITLE);
return dialog;
}
private Subscriber<Order> getOrderUpdateSubscriber() {
return new Subscriber<Order>() {
@Override
public void onCompleted() {
getDialog().dismiss();
mProductLoading.setVisibility(View.GONE);
}
@Override
public void onError(Throwable e) {
mProductLoading.setVisibility(View.GONE);
if (e instanceof ApiException) {
ErrorMessageAlertDialog.getStandardErrorMessageAlertDialog(getActivity(), ((ApiException) e).getApiError().getMessage()).show();
} else {
ErrorMessageAlertDialog.getStandardErrorMessageAlertDialog(getActivity(), e.getMessage()).show();
}
}
@Override
public void onNext(Order order) {
mEditDoneListener.onEditDone(order);
}
};
}
private void deleteOrderItem(String orderItemId, String orderId) {
AndroidObservable.bindFragment(this, NewOrderManager.getInstance().getDeleteOrderItemObservable(mTenantId, mSiteId, orderItemId, orderId)).subscribe(getOrderUpdateSubscriber());
}
private void setupViews() {
mProductLoading.setVisibility(View.GONE);
NumberFormat format = NumberFormat.getCurrencyInstance();
Double productPriceVal = mOrderItem.getProduct().getPrice().getPrice();
productPrice.setText(format.format(productPriceVal));
productQuantity.setText(String.valueOf(mOrderItem.getQuantity()));
productCode.setText(mOrderItem.getProduct().getProductCode());
productName.setText(mOrderItem.getProduct().getName());
productTotal.setText(format.format(mOrderItem.getQuantity() * productPriceVal));
mSpinnerAdapter = new SpinnerAdapter();
fulfillmentType.setAdapter(mSpinnerAdapter);
setImage(mOrderItem.getProduct().getImageUrl());
orderItemDelete.setVisibility(isEditMode ? View.VISIBLE : View.GONE);
orderItemDelete.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
new AlertDialog.Builder(getActivity())
.setMessage(getString(R.string.orderitem_remove_confirm))
.setPositiveButton(R.string.ok, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
deleteOrderItem(mOrderItem.getId(), mOrderId);
}
})
.setNegativeButton(R.string.cancel, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int i) {
dialog.dismiss();
}
})
.create().show();
}
});
productSave.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if (isEditMode) {
String updatedProductQuantityVal = productQuantity.getText().toString();
FulfillmentInfo updatedFulFillmentType = (FulfillmentInfo) fulfillmentType.getSelectedItem();
if (updatedFulFillmentType.mType.equalsIgnoreCase(mOrderItem.getFulfillmentMethod()) && updatedFulFillmentType.mLocation.equalsIgnoreCase(mOrderItem.getFulfillmentLocationCode())) {
updatedFulFillmentType = null;
}
if (TextUtils.isEmpty(updatedProductQuantityVal) || updatedProductQuantityVal.equals(String.valueOf(mOrderItem.getQuantity()))) {
updatedProductQuantityVal = null;
}
if (updatedProductQuantityVal != null || updatedFulFillmentType != null) {
mProductLoading.setVisibility(View.VISIBLE);
AndroidObservable.bindFragment(NewOrderItemEditFragment.this, NewOrderManager
.getInstance()
.getOrderItemUpdateQuantityObservable(mTenantId, mSiteId, mOrderItem, mOrderId, updatedProductQuantityVal == null ? null : Integer.valueOf(updatedProductQuantityVal), updatedFulFillmentType))
.subscribe(getOrderUpdateSubscriber());
} else {
getDialog().dismiss();
}
} else {
FulfillmentInfo updatedFulFillmentType = (FulfillmentInfo) fulfillmentType.getSelectedItem();
mOrderItem.setFulfillmentLocationCode(updatedFulFillmentType.mLocation);
mOrderItem.setFulfillmentMethod(updatedFulFillmentType.mType);
mOrderItem.setQuantity(Integer.valueOf(productQuantity.getText().toString()));
if (ProductUtils.isProductConfigurable(mOrderItem.getProduct())) {
ProductVariation productVariation = getSelectedVariation();
mOrderItem.getProduct().setVariationProductCode(productVariation.getVariationProductCode());
for (ProductOption productOption : mOrderItem.getProduct().getOptions()) {
productOption.getAttributeFQN();
for (ProductVariationOption productVariationOption : productVariation.getOptions()) {
if (productVariationOption.getAttributeFQN().equals(productOption.getAttributeFQN())) {
productOption.setShopperEnteredValue(productVariationOption.getValue());
productOption.setStringValue(productVariationOption.getContent().getStringValue());
productOption.setValue(productVariationOption.getValue());
}
}
}
} else {
mOrderItem.getProduct().setVariationProductCode(mOrderItem.getProduct().getProductCode());
}
mProductLoading.setVisibility(View.VISIBLE);
AndroidObservable.bindFragment(NewOrderItemEditFragment.this, NewOrderManager
.getInstance()
.getOrderItemCreateObservable(mTenantId, mSiteId, mOrderItem, mOrderId))
.subscribe(getOrderUpdateSubscriber());
}
}
});
}
public void setSpinnerSelection(SpinnerAdapter spinnerAdapter, String fulfillmentMethod, String locationCode) {
if (locationCode != null && fulfillmentMethod != null && spinnerAdapter.getCount() > 1) {
for (int i = 1; i < spinnerAdapter.getCount(); i++) {
FulfillmentInfo fulfillmentInfo = spinnerAdapter.getItem(i);
if (locationCode.equalsIgnoreCase(fulfillmentInfo.mLocation) && fulfillmentMethod.equalsIgnoreCase(fulfillmentInfo.mType)) {
fulfillmentType.setSelection(i);
return;
}
}
}
fulfillmentType.setSelection(0);
}
public void setOnEditDoneListener(onItemEditDoneListener onEditDoneListener) {
mEditDoneListener = onEditDoneListener;
}
@Override
public void onOptionChanged() {
ProductVariation productVariation = getSelectedVariation();
loadLocations(productVariation.getVariationProductCode());
}
private ProductVariation getSelectedVariation() {
List<ProductVariation> productVariations = new ArrayList<>(mProductVariationCollection.getItems());
for (int i = 0; i < mOptionsLayout.getChildCount(); i++) {
if (mOptionsLayout.getChildAt(i) instanceof ProductOptionsLayout) {
ProductOptionsLayout productOptionsLayout = (ProductOptionsLayout) mOptionsLayout.getChildAt(i);
String attributeFQN = productOptionsLayout.getAttributeFQN();
String attributeOption = productOptionsLayout.getAttributeValue();
for (int k = productVariations.size() - 1; k >= 0; k--) {
boolean isValidVariation = false;
List<ProductVariationOption> productOptions = productVariations.get(k).getOptions();
for (ProductVariationOption variationOption : productOptions) {
if (variationOption.getAttributeFQN().equalsIgnoreCase(attributeFQN) && variationOption.getValue().equals(attributeOption)) {
isValidVariation = true;
}
}
if (!isValidVariation) {
productVariations.remove(k);
}
}
}
}
if (productVariations.size() > 0) {
return productVariations.get(0);
} else {
return null;
}
}
public interface onItemEditDoneListener {
public void onEditDone(Order order);
}
class ProductVariationAdapter extends BaseAdapter {
private List<ProductVariation> mData;
public ProductVariationAdapter() {
mData = new ArrayList<>();
}
public void setData(List<ProductVariation> data) {
mData = data;
}
@Override
public View getDropDownView(int position, View convertView, ViewGroup parent) {
if (convertView == null) {
LayoutInflater inflater = LayoutInflater.from(parent.getContext());
convertView = inflater.inflate(R.layout.orderfulfillment_spinner_item, parent, false);
}
TextView mTextView = (TextView) convertView.findViewById(R.id.order_fulfillment);
ProductVariation productVariation = getItem(position);
StringBuffer fulFillmentDisplay = new StringBuffer(productVariation.getVariationProductCode());
for (ProductVariationOption option : productVariation.getOptions()) {
fulFillmentDisplay.append("- " + option.getValue());
}
mTextView.setText(fulFillmentDisplay.toString());
return convertView;
}
@Override
public int getCount() {
return mData.size();
}
@Override
public ProductVariation getItem(int i) {
return mData.get(i);
}
@Override
public long getItemId(int i) {
return i;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
TextView textView = (TextView) View.inflate(parent.getContext(), R.layout.orderfulfillment_dropdown_resource, null);
ProductVariation productVariation = getItem(position);
StringBuffer fulFillmentDisplay = new StringBuffer(productVariation.getVariationProductCode());
for (ProductVariationOption option : productVariation.getOptions()) {
fulFillmentDisplay.append("- " + option.getValue());
}
textView.setText(fulFillmentDisplay.toString());
return textView;
}
}
class SpinnerAdapter extends BaseAdapter {
private List<FulfillmentInfo> mData;
public SpinnerAdapter() {
mData = new ArrayList<>();
}
public void setData(List<FulfillmentInfo> data) {
mData = data;
}
@Override
public View getDropDownView(int position, View convertView, ViewGroup parent) {
if (convertView == null) {
LayoutInflater inflater = LayoutInflater.from(parent.getContext());
convertView = inflater.inflate(R.layout.orderfulfillment_spinner_item, parent, false);
}
TextView mTextView = (TextView) convertView.findViewById(R.id.order_fulfillment);
FulfillmentInfo fulfillmentInfo = getItem(position);
String fulFillmentDisplay = fulfillmentInfo.mType + "_" + fulfillmentInfo.mLocation;
mTextView.setText(fulFillmentDisplay);
return convertView;
}
@Override
public int getCount() {
return mData.size();
}
@Override
public FulfillmentInfo getItem(int i) {
return mData.get(i);
}
@Override
public long getItemId(int i) {
return i;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
TextView textView = (TextView) View.inflate(parent.getContext(), R.layout.orderfulfillment_dropdown_resource, null);
FulfillmentInfo fulfillmentInfo = getItem(position);
String fulFillmentDisplay = fulfillmentInfo.mType + "_" + fulfillmentInfo.mLocation;
textView.setText(fulFillmentDisplay);
return textView;
}
}
}