package com.tomas.ht_ydt;

import android.annotation.SuppressLint;
import android.app.DatePickerDialog;
import android.app.Dialog;
import android.graphics.Color;
import android.graphics.drawable.ColorDrawable;
import android.os.Bundle;
import android.text.InputType;
import android.util.Log;
import android.view.KeyEvent;
import android.view.View;
import android.view.WindowManager;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.DatePicker;
import android.widget.EditText;
import android.widget.ImageButton;
import android.widget.ListView;
import android.widget.SearchView;
import android.widget.Spinner;
import android.widget.TextView;

import androidx.activity.EdgeToEdge;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.graphics.Insets;
import androidx.core.view.ViewCompat;
import androidx.core.view.WindowInsetsCompat;

import com.keyence.autoid.sdk.scan.DecodeResult;
import com.tomas.ht_ydt.ListData.LabelItem_list;
import com.tomas.ht_ydt.ListData.OutBom_list;
import com.tomas.ht_ydt.ListData.OutProdFIFO;
import com.tomas.ht_ydt.lib.ActionType;
import com.tomas.ht_ydt.lib.AlertProgress;
import com.tomas.ht_ydt.lib.KeyMapping;
import com.tomas.ht_ydt.lib.Scanner;
import com.tomas.ht_ydt.lib.Settings;
import com.tomas.ht_ydt.lib.common.AsyncHttpClient;
import com.tomas.ht_ydt.lib.common.AsyncTcpClient;
import com.tomas.ht_ydt.lib.common.Utils;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Calendar;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.Map;

import cn.pedant.SweetAlert.SweetAlertDialog;

public class InboundScheduleDetail_Activity extends Scanner implements View.OnClickListener {
    TextView txt_user, txt_device, txt_part_no, txt_part_name, txt_total, txt_unit_ok, txt_unit_ng;
    EditText edt_ok, edt_ng, edt_lot_date;
    Spinner spinner_lo_ok, spinner_lo_ng;
    Button btn_print, btn_clear, btn_confirm;
    ImageButton imb_back;
    Calendar calendar;
    private JSONArray j_schedules;

    SimpleDateFormat date;
    String str_today, str_lot_no, str_menu,str_sch_id, str_order, str_part_no, str_part_name, str_supplier, str_location,
            str_plan_qty, str_act_qty,str_unit_qty , str_status, l_part_no, l_lot_no, l_serial, l_label_id, key_label,
            s_location, s_list_item, str_action_det, str_ref_id, str_product_no;//str_control_unit
    Bundle bundle;
    Dialog dialog_search;
    Double sum_total = 0.0, d_plan_qty = 0.0, d_act_qty = 0.0, d_input_ok = 0.0, d_input_ng = 0.0;;

    DecimalFormat decimalFormat;
    AlertProgress alert;
    boolean b_confirm;
    Map<String, LabelItem_list> map_label;
    Map<String, OutBom_list>map_bom;
    Map<String, OutProdFIFO>map_out_fifo;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_inbound_schedule_detail);

        default_view = (EditText) findViewById(R.id.txt_label_issue_tmp);

        b_confirm = false;
        decimalFormat = new DecimalFormat("#,##0.00");

        map_label = new LinkedHashMap<>();
        map_bom = new LinkedHashMap<>();
        map_out_fifo = new LinkedHashMap<>();

        alert = new AlertProgress(InboundScheduleDetail_Activity.this);
        calendar = Calendar.getInstance();
        date = new SimpleDateFormat("yyyy-MM-dd");
        str_today = date.format(calendar.getTime());

        txt_user = (TextView) findViewById(R.id.txt_user);
        txt_user.setText("User : " + Settings.getLoginUser().getName());

        txt_device = (TextView) findViewById(R.id.txt_device);
        txt_device.setText("Device : " + Settings.getDeviceNo());

        bundle = getIntent().getExtras();
        str_menu = Settings.getMENU().toString();
        Log.d(getString(R.string.tag), "Menu: " + str_menu);

        txt_part_no = (TextView) findViewById(R.id.txt_part_no);
        txt_part_name = (TextView) findViewById(R.id.txt_part_name);
        txt_unit_ok = (TextView) findViewById(R.id.txt_unit_ok);
        txt_unit_ng = (TextView) findViewById(R.id.txt_unit_ng);
        txt_total = (TextView) findViewById(R.id.txt_total);

        edt_ng = (EditText) findViewById(R.id.edt_qty_ng);
        edt_ok = (EditText) findViewById(R.id.edt_qty_ok);

        edt_lot_date = (EditText) findViewById(R.id.edt_lot_date);
        edt_lot_date.setText(str_today);
        edt_lot_date.setInputType(InputType.TYPE_NULL);
        edt_lot_date.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {

                final Calendar currentDate = Calendar.getInstance();
                new DatePickerDialog(InboundScheduleDetail_Activity.this, new DatePickerDialog.OnDateSetListener() {
                    @Override
                    public void onDateSet(DatePicker view, int year, int monthOfYear, int dayOfMonth) {
                        str_lot_no = (year + "-" +
                                (String.format("%2s", monthOfYear + 1).replace(' ', '0')) + "-" +
                                (String.format("%2s", dayOfMonth).replace(' ', '0')));
                        edt_lot_date.setText(str_lot_no);
                    }
                }, currentDate.get(Calendar.YEAR), currentDate.get(Calendar.MONTH), currentDate.get(Calendar.DATE)).show();
            }
        });

        spinner_lo_ok = (Spinner) findViewById(R.id.spinner_lo_ok);
        ArrayAdapter<String> dataAdapter = new ArrayAdapter<String>
                (getApplicationContext(), R.layout.spinner_list, Settings.getList_location_ok());
        dataAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
        spinner_lo_ok.setAdapter(dataAdapter);

        spinner_lo_ng = (Spinner) findViewById(R.id.spinner_lo_ng);
        ArrayAdapter<String> dataAdapter2 = new ArrayAdapter<String>
                (getApplicationContext(), R.layout.spinner_list, Settings.getList_location_ng());
        dataAdapter2.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
        spinner_lo_ng.setAdapter(dataAdapter2);

        spinner_lo_ok.setEnabled(false);
        spinner_lo_ok.setBackgroundResource(R.drawable.button_background_gray);
        spinner_lo_ng.setEnabled(false);
        spinner_lo_ng.setBackgroundResource(R.drawable.button_background_gray);

        imb_back =(ImageButton)findViewById(R.id.imb_back);
        btn_print = (Button) findViewById(R.id.btn_print);
        btn_clear = (Button)findViewById(R.id.btn_clear);
        btn_confirm = (Button) findViewById(R.id.btn_confirm);
        btn_confirm.setBackgroundResource(R.drawable.button_background_gray);
        btn_confirm.setEnabled(false);
        str_sch_id = bundle.getString("schedule_id");
        str_ref_id = bundle.getString("ref_id");
        str_product_no = bundle.getString("product_no");
        str_order = bundle.getString("order_no");
        str_part_no = bundle.getString("part_no");
        str_part_name = bundle.getString("part_name");
        str_location = bundle.getString("dest_location_id");
        str_plan_qty = bundle.getString("plan_qty");
        str_act_qty = bundle.getString("act_qty");
        str_supplier = bundle.getString("supplier");
//        str_control_unit = bundle.getString("control_unit");
        str_action_det = bundle.getString("action_det");
        str_unit_qty = bundle.getString("unit_qty");
        str_status = bundle.getString("status");
        Log.d(getString(R.string.tag), "str_action_det: " + str_action_det);

        d_plan_qty = Double.parseDouble(str_plan_qty);
        d_act_qty = Double.parseDouble(str_act_qty);

        spinner_lo_ok.setSelection(Settings.getList_location_ok().indexOf(str_location));
        txt_part_no.setText(str_part_no);
        txt_part_name.setText(str_part_name);
        txt_unit_ok.setText(str_unit_qty);
        txt_unit_ng.setText(str_unit_qty);
        txt_total.setText(String.valueOf( decimalFormat.format(Math.round(d_act_qty)))+"/"+String.valueOf(decimalFormat.format(Math.round(d_plan_qty)))+"  "+str_unit_qty);

    }


    @Override
    public void onClick(View view) {
        switch (view.getId()) {
            case R.id.imb_back:
                finish();
                break;

            case R.id.btn_print:
                if (b_confirm == false) {
                    Block_button();
                    Check_Qty();
                }
                break;

            case R.id.btn_clear:
                Clear_layout();
                break;
            case R.id.btn_confirm:
                if (b_confirm == false) {
                    Block_button();
                    Check_Confirm();
                }
                break;

        }
    }


    private void Block_button() {
        b_confirm = true;
        btn_confirm.setEnabled(false);
        btn_confirm.setBackgroundResource(R.drawable.button_background_gray);
        btn_print.setEnabled(false);
        btn_print.setBackgroundResource(R.drawable.button_background_gray);
    }

    private void Unblock_button() {
        b_confirm = false;
        btn_confirm.setEnabled(true);
        btn_confirm.setBackgroundResource(R.drawable.button_background_blue);

        if (map_label.size() > 0) {
            btn_print.setEnabled(false);
            btn_print.setBackgroundResource(R.drawable.button_background_gray);
        } else {
            btn_print.setEnabled(true);
            btn_print.setBackgroundResource(R.drawable.button_background_green);
        }
    }

    @Override
    public void processData(String data, DecodeResult.Result result, String codeType) {
        if (data.trim().equals(""))
            return;
        try {
            Log.d(getString(R.string.tag), "data read:" + data);
            String[] tokens = data.split(getString(R.string.DELIMITER_SCAN_TOKEN), -1);
            Log.d(getString(R.string.tag), Arrays.deepToString(tokens));

            if (tokens.length == 2) {//scan location [LOCATION CODE] │[ITEM CODE1],[ITEM CODE2],…
                if (map_label.size() > 0) {
                    s_location = tokens[0].trim();
                    s_list_item = tokens[1].trim();
                    String[] tokens_part = s_list_item.split(",", -1);

                    if (Settings.getMap_location().containsKey(s_location)) {
                        if (s_list_item.trim().equals("")) {//free location
                            spinner_lo_ok.setSelection(Settings.getList_location_ok().indexOf(s_location));

                        } else {
                            Boolean search = false;
                            for (int i = 0; i < tokens_part.length; i++) { //for check part can use
                                if (str_part_no.trim().equals(tokens_part[i])) {
                                    search = true;
                                    spinner_lo_ok.setSelection(Settings.getList_location_ok().indexOf(s_location));
                                    break;
                                } else {
                                    search = false;
                                }
                            }//for

                            if (search == false) {
                                showWarning("Location not match!");
                                return;
                            }
                        }
                    } else {
                        showWarning("Location not found!");
                    }

                } else {
                    showWarning("Please scan label!");
                    return;
                }

            } else if (tokens.length == 4) {//scab label [PART CODE] | [LOT] | [SERIAL NO] | [LABEL ID]
                key_label = data.trim();
                l_part_no = tokens[0].trim();
                l_lot_no = tokens[1].trim();
                l_serial = tokens[2].trim();
                l_label_id = tokens[3].trim();

                if (map_label.size() > 0) {
                    if (str_part_no.trim().equals(l_part_no)) {
                        Check_Map_Label();
                    } else {
                        showWarning("Parts No or Lot. not match!");
                        return;
                    }
                } else {
                    Check_Label();
                }

            } else {
                showWarning("Invalid QR code!");
            }

            Utils.hideKeyboardFrom(getApplicationContext(), default_view);
        } catch (Exception e) {
            Log.e(getString(R.string.tag), "ERROR: " + e.getMessage());
        }
    }


    private void Check_Map_Label() {
        Log.d(getString(R.string.tag), "KEY : " + key_label);
        if (map_label.containsKey(key_label)) {
            SweetAlertDialog d = new SweetAlertDialog(InboundScheduleDetail_Activity.this, SweetAlertDialog.WARNING_TYPE);
            d.setCancelable(false);
            d.setTitleText("WARNING");
            d.setContentText("This label has been scanned.");
            d.setCancelText("Delete");
            d.setCancelClickListener(new SweetAlertDialog.OnSweetClickListener() {
                @Override
                public void onClick(SweetAlertDialog sd) {
                    sd.dismiss();
                    map_label.remove(key_label);
                    Log.d(getString(R.string.tag), "delete size = " + map_label.size());
                    Summary_data_scan();
                }
            });
            d.setConfirmText("Continue");
            d.setConfirmClickListener(new SweetAlertDialog.OnSweetClickListener() {
                @Override
                public void onClick(SweetAlertDialog sd) {
                    sd.dismiss();
                }
            });
            d.show();

        } else {
            Check_Label();
        }
    }

    private void Check_Label() {
        Log.d(getString(R.string.tag), "Check_Label : " + key_label + ": " + l_label_id + " " + l_part_no + " " + l_lot_no + " " + l_serial);
        try {
            JSONObject json = new JSONObject();
            json.put("cmd", "LABEL/DETAIL");
            json.put("id", l_label_id);
            json.put("parts_no", l_part_no);
            json.put("lot_no", l_lot_no);
            json.put("serial_no", l_serial);

            new AsyncHttpClient(getApplicationContext(),
                    Settings.getMgmtList().get("web_api") + "/ht_api.php",
                    json.toString()) {
                @SuppressLint("StaticFieldLeak")
                @Override
                protected void onFinished(String response, int resp_code) {
                    Log.d(getString(R.string.tag), "response: " + response);

                    try {
                        JSONObject jsonObject = new JSONObject(response);
                        String value = jsonObject.getString("value");
                        JSONArray jArray = new JSONArray(value);
                        if (jArray.length() == 0) {
                            showWarning("Label not found!");

                        } else {
                            String status_label = jArray.getJSONObject(0).getString("status").trim();
                            Log.d(getString(R.string.tag), "status_label: " + status_label);
                            if (status_label.trim().equals("1") || status_label.trim().equals("3")) {
                                str_part_no = jArray.getJSONObject(0).getString("lbl_part_no").trim();
                                str_lot_no = jArray.getJSONObject(0).getString("lot_no").trim();
                                str_part_name = jArray.getJSONObject(0).getString("lbl_part_name").trim();
//                                map_label.clear();
                                map_label.put(key_label, new LabelItem_list(
                                        "",
                                        jArray.getJSONObject(0).getString("id").trim(),
                                        str_lot_no,
                                        jArray.getJSONObject(0).getString("serial_no").trim(),
                                        jArray.getJSONObject(0).getString("status").trim(),
                                        String.valueOf(Math.round(Double.parseDouble(jArray.getJSONObject(0).getString("issue_qty").trim()))),
                                        jArray.getJSONObject(0).getString("issue_stock_qty").trim(),
                                        jArray.getJSONObject(0).getString("act_stock_qty").trim(),
                                        jArray.getJSONObject(0).getString("control_unit").trim(),
                                        jArray.getJSONObject(0).getString("lbl_supplier_id").trim(),
                                        jArray.getJSONObject(0).getString("lbl_supplier").trim(),
                                        str_part_no,
                                        str_part_name,
                                        jArray.getJSONObject(0).getString("lbl_unit").trim(),
                                        jArray.getJSONObject(0).getString("lbl_ng").trim(),
                                        jArray.getJSONObject(0).getString("last_location_id").trim().equals("null") ? "" : jArray.getJSONObject(0).getString("last_location_id").trim(),
                                        jArray.getJSONObject(0).getString("last_location_name").trim().equals("null") ? "" : jArray.getJSONObject(0).getString("last_location_name").trim(),
                                        "",
                                        "",
                                        jArray.getJSONObject(0).getString("lbl_order_no").trim()));

                                txt_part_no.setText(str_part_no);
                                txt_part_name.setText(str_part_name);
                                edt_lot_date.setText(str_lot_no);
                                Summary_data_scan();
                            } else {
                                showWarning("Invalid Label Status! : " + status_label);
                            }
                        }
                    } catch (JSONException e) {
                        showError(e.getMessage());

                    }
                }
            }.execute();

        } catch (JSONException e) {
            showError(e.getMessage());
        }
    }

    private void Summary_data_scan() {
        sum_total = 0.0;
        Double sum_ok = 0.0, sum_ng = 0.0;
        for (String key : map_label.keySet()){
            LabelItem_list item = map_label.get(key);
            String lbl_ng = item.getLbl_ng();
            String issue_qty = item.getIssue_qty();
//            str_control_unit = item.getControl_unit();
//            str_control_unit = item.getLbl_unit();
            Double qty = Double.parseDouble(issue_qty);

            if (lbl_ng.trim().equals("0")){//OK
                sum_ok = (sum_ok + qty);

            }else {//NG
                sum_ng = (sum_ng + qty);

            }
        }

        if (sum_ok > 0){
            edt_ok.setBackgroundResource(R.drawable.button_background_ok);
        }else {
            edt_ok.setBackgroundResource(R.drawable.button_background_menu_);
        }

        if (sum_ng > 0){
            edt_ng.setBackgroundResource(R.drawable.button_background_ok);
        }else {
            edt_ng.setBackgroundResource(R.drawable.img_background_gray);
        }

        edt_lot_date.setEnabled(false);
        edt_lot_date.setBackgroundResource(R.drawable.button_background_gray);

        edt_ok.setText(String.valueOf(decimalFormat.format(sum_ok)));
        edt_ok.setEnabled(false);
        edt_ng.setText(String.valueOf(decimalFormat.format(sum_ng)));
        edt_ng.setEnabled(false);

        spinner_lo_ok.setEnabled(true);
        spinner_lo_ok.setBackgroundResource(R.drawable.button_background_menu_);
        spinner_lo_ng.setEnabled(true);
        spinner_lo_ng.setBackgroundResource(R.drawable.button_background_menu_);

        btn_confirm.setBackgroundResource(R.drawable.button_background_blue);
        btn_confirm.setEnabled(true);
        btn_print.setBackgroundResource(R.drawable.button_background_gray);
        btn_print.setEnabled(false);

        sum_total = (d_act_qty + sum_ok + sum_ng);
        txt_total.setText(String.valueOf(decimalFormat.format(Math.round(sum_total))) + "/" + String.valueOf(decimalFormat.format(Math.round(d_plan_qty))) + " " + str_unit_qty);
        txt_unit_ok.setText(str_unit_qty);
        txt_unit_ng.setText(str_unit_qty);
    }

    private void Check_Confirm() {
        if (map_label.size() == 0) {
            Unblock_button();
            return;
        } else {
            Update_Location();
        }
    }

    private void Update_Location() {
        String lo_ok_id = spinner_lo_ok.getSelectedItem().toString().trim();
        String lo_ok_name = Settings.getMap_location_ok().get(lo_ok_id).getName();
        String lo_ng_id = spinner_lo_ng.getSelectedItem().toString().trim();
        String lo_ng_name = Settings.getMap_location_ng().get(lo_ng_id).getName();
        for (String key : map_label.keySet()) {
            LabelItem_list item = map_label.get(key);
            String lbl_ng = item.getLbl_ng();
            if (lbl_ng.trim().equals("0")) {//label status : OK
                item.setLocation(lo_ok_id);
                item.setLocation_name(lo_ok_name);
                map_label.put(key, item);

            } else {//label status : NG
                item.setLocation(lo_ng_id);
                item.setLocation_name(lo_ng_name);
                map_label.put(key, item);

            }
        }
        Confirm_Inbound();
    }

    private void Confirm_Inbound() {
        try {
            JSONObject json = new JSONObject();
            Map<String, String> jsonParams = new HashMap<>();//sample data
            json.put("cmd", "INBOUND/SCHEDULE/DETAIL/CONFIRM");

            JSONArray jsonArray = new JSONArray();
            for (String key : map_label.keySet()){
                LabelItem_list item = map_label.get(key);
                jsonParams.put("ref_sch_id", str_sch_id);
                jsonParams.put("label_id", item.getLabel_id());
                jsonParams.put("item_id", txt_part_no.getText().toString().trim());
                jsonParams.put("item_name", txt_part_name.getText().toString().trim());
                jsonParams.put("supplier_id", item.getLbl_supplier_id().trim().equals("null") ? "" : item.getLbl_supplier_id().trim());
                jsonParams.put("supplier_name", item.getLbl_supplier().trim().equals("null") ? "" : item.getLbl_supplier().trim());
                jsonParams.put("package_id", item.getLbl_unit());
                jsonParams.put("unit_qty", item.getControl_unit());
                jsonParams.put("package_qty",item.getIssue_qty());
                jsonParams.put("qty",item.getIssue_stock_qty());
                jsonParams.put("lot_no", item.getLot_no().trim());
                jsonParams.put("order_no", item.getLbl_order_no());
                jsonParams.put("location_id", item.getLocation());
                jsonParams.put("location_name", item.getLocation_name().trim().equals("null") ? "" : item.getLocation_name().trim() );
                jsonParams.put("status",  "1");
                jsonParams.put("slip_divide", "3");
                jsonParams.put("create_user_id", Settings.getLoginUser().getId());
                jsonParams.put("inspection_flg", "0");
                jsonParams.put("ng", item.getLbl_ng());

                JSONObject jsonObject = new JSONObject(jsonParams);
                jsonArray.put(jsonObject);
            }
            json.put("value",jsonArray);

            new AsyncHttpClient(getApplicationContext(),
                    Settings.getMgmtList().get("web_api") + "/ht_api.php",
                    json.toString()) {
                @Override
                protected void onFinished(String response, int resp_code) {
                    try {
                        JSONObject jsonObject = new JSONObject(response);
                        Log.d(getString(R.string.tag), "response" + response);
                        String status = jsonObject.getString("status");
                        int affected_rows = jsonObject.getInt("affected_rows");

                        if (status.trim().equals("success") && affected_rows > 0) {
                            //SUCCESS
                            if (str_action_det.trim().equals("Inbound Material")){
                                finish();

                            }else if (str_action_det.trim().equals("Inbound Production Inj")){
                                if (str_status.trim().equals("IMPORTED")) {
                                    Get_Virgin_Inj();

                                }else {
                                    finish();
                                }

                            } else {//Inbound Production Press & Inbound Production Assy
                                Get_parts_BOM();//
                            }
                        } else {
                            String error = jsonObject.getString("error");
                            showError(error);
                            Unblock_button();
                        }
                    } catch (JSONException e) {
                        showError(e.getMessage());
                        Unblock_button();
                    }
                }
            }.execute();
        } catch (Exception e) {
            showError(e.getMessage());
            Unblock_button();
        }
    }

    private void Get_Virgin_Inj() {
        map_bom.clear();
        try {
            JSONObject json = new JSONObject();
            json.put("cmd", "GET/VIRGIN/INJ");
            json.put("ref_id", str_ref_id);
            json.put("order_no", str_order);
            json.put("product_no", str_part_no);

            new AsyncHttpClient(getApplicationContext(),
                    Settings.getMgmtList().get("web_api") + "/ht_api.php",
                    json.toString()) {
                @Override
                protected void onFinished(String response, int resp_code) {
                    Log.d(getString(R.string.tag), "response: " + response);

                    try {
                        JSONArray jArray = new JSONArray(response);
                        if (jArray.length() == 0){
                            //No crusher
                            finish();

                        }else {
                            for (int i = 0; i < jArray.length(); i++) {
                                map_bom.put(jArray.getJSONObject(i).getString("parts_no").trim(),
                                        new OutBom_list(
                                                jArray.getJSONObject(i).getString("product_no").trim(),
                                                jArray.getJSONObject(i).getString("ref_parts_no").trim(),
                                                jArray.getJSONObject(i).getString("parts_no").trim(),
                                                jArray.getJSONObject(i).getString("parts_name").trim(),
                                                jArray.getJSONObject(i).getString("virgin_qty").trim(),
                                                jArray.getJSONObject(i).getString("control_unit").trim()));
                            }
                            Log.d(getString(R.string.tag), "map_bom: " + map_bom.size());
                            Get_FIFO();

                        }
                    } catch (JSONException e) {
                        Unblock_button();
                        showError(e.getMessage());
                    }
                }
            }.execute();

        } catch (JSONException e) {
            Unblock_button();
            showError(e.getMessage());
        }
    }

    private void Get_parts_BOM() {
        map_bom.clear();
        try {
            JSONObject json = new JSONObject();
            json.put("cmd", "GET/BOM/PART");
            json.put("product_no", str_product_no);
            json.put("ref_parts_no", str_part_no);

            new AsyncHttpClient(getApplicationContext(),
                    Settings.getMgmtList().get("web_api") + "/ht_api.php",
                    json.toString()) {
                @Override
                protected void onFinished(String response, int resp_code) {
                    Log.d(getString(R.string.tag), "response: " + response);

                    try {
                        JSONObject jsonObject = new JSONObject(response);
                        String value = jsonObject.getString("value");
                        JSONArray jArray = new JSONArray(value);
                        if (jArray.length() == 0){
                            showWarning("BOM not found! " +
                                    "\n product_no:"+str_product_no+" " +
                                    "\n ref_parts_no:"+str_part_no);

                        }else {
                            for (int i = 0; i < jArray.length(); i++) {
                                //calculate qty bom
                                String qty_ratio = jArray.getJSONObject(i).getString("qty_ratio").trim();
                                String[] tokens = qty_ratio.split(":", -1);
                                Double qty_item = Double.parseDouble(tokens[0]);
                                Double act_scan = (sum_total - d_act_qty);
                                Double sum_qty = (qty_item * act_scan);
                                Log.d(getString(R.string.tag), "sum_total: " + sum_total);
                                Log.d(getString(R.string.tag), "d_act_qty: " + d_act_qty);
                                Log.d(getString(R.string.tag), "act_scan: " + act_scan);
                                Log.d(getString(R.string.tag), "sum_qty: " + sum_qty);

                                map_bom.put(jArray.getJSONObject(i).getString("parts_no").trim(),
                                        new OutBom_list(
                                                jArray.getJSONObject(i).getString("product_no").trim(),
                                                jArray.getJSONObject(i).getString("ref_parts_no").trim(),
                                                jArray.getJSONObject(i).getString("parts_no").trim(),
                                                jArray.getJSONObject(i).getString("parts_name").trim(),
                                                String.format("%.2f",sum_qty),
                                                jArray.getJSONObject(i).getString("unit_qty").trim()));
                            }
                            Log.d(getString(R.string.tag), "map_bom: " + map_bom.size());
                            Get_FIFO();

                        }
                    } catch (JSONException e) {
                        Unblock_button();
                        showError(e.getMessage());
                    }
                }
            }.execute();

        } catch (JSONException e) {
            Unblock_button();
            showError(e.getMessage());
        }
    }

    private void Get_FIFO() {
        map_out_fifo.clear();
        try {
            JSONObject json = new JSONObject();
            Map<String, String> jsonParams = new HashMap<>();

            json.put("cmd", "QUERY/STOCK/FIFO/OUTBOUND");

            JSONArray jsonArray = new JSONArray();
            for (String key : map_bom.keySet()) {
                OutBom_list item = map_bom.get(key);
                jsonParams.put("parts_no", item.getParts_no());
                jsonParams.put("qty", item.getQty_ratio());
                jsonParams.put("unit_qty", item.getUnit_qty());
                jsonParams.put("section", Settings.getLoginUser().getDepartment());

                JSONObject jsonObject = new JSONObject(jsonParams);
                jsonArray.put(jsonObject);
            }
            json.put("value",jsonArray);

            new AsyncHttpClient(getApplicationContext(),
                    Settings.getMgmtList().get("web_api") + "/ht_api.php",
                    json.toString()) {
                @Override
                protected void onFinished(String response, int resp_code) {
                    Log.d(getString(R.string.tag), "response: " + response);

                    try {
                        JSONObject jsonObject = new JSONObject(response);
                        String value = jsonObject.getString("value");
                        JSONArray jArray = new JSONArray(value);
                        Log.d(getString(R.string.tag), "jArray: " + jArray.toString());
                        if (jArray.length() == 0){
//                            showWarning("QUERY/STOCK/FIFO/OUTBOUND not found!");
                            finish();

                        }else {
                            for (int i = 0; i < jArray.length(); i++) {
                                JSONArray innerArray = jArray.getJSONArray(i);
                                for (int j = 0; j < innerArray.length(); j++) {
                                    JSONObject itemObject = innerArray.getJSONObject(j);
                                    String item_id = itemObject.getString("item_id").trim();
                                    String lot_no = itemObject.getString("lot_no").trim();
                                    String location_id = itemObject.getString("location_id").trim();
                                    String qty = itemObject.getString("qty").trim();
                                    String key = item_id+lot_no+location_id;

                                    map_out_fifo.put(key,
                                            new OutProdFIFO(
                                                    item_id,
                                                    lot_no,
                                                    location_id,
                                                    qty));

                                }
                            }
                            OutboundProductionFIFO();
                            Log.d(getString(R.string.tag), "map_out_fifo: " + map_out_fifo.size());
                        }
                    } catch (JSONException e) {
                        Unblock_button();
                        showError(e.getMessage());
                    }
                }
            }.execute();

        } catch (JSONException e) {
            Unblock_button();
            showError(e.getMessage());
        }

    }

    private void OutboundProductionFIFO() {
        try {
            JSONObject json = new JSONObject();
            Map<String, String> jsonParams = new HashMap<>();
            json.put("cmd", "OUTBOUND/PRODUCTION/MANUAL/FIFO/CONFIRM");
            JSONArray jsonArray = new JSONArray();

            for (String key : map_out_fifo.keySet()){
                OutProdFIFO item = map_out_fifo.get(key);
//             ไม่ส่ง  jsonParams.put("ref_sch_id", str_sch_id);
                jsonParams.put("order_no", str_order);
//             ไม่ส่ง   jsonParams.put("label_id", item.getLabel_id());
                jsonParams.put("item_id",item.getItem_id());
                jsonParams.put("item_name", map_bom.get(item.getItem_id()).getParts_name());
                jsonParams.put("lot_no", item.getLot_no());
                jsonParams.put("package_id", map_bom.get(item.getItem_id()).getUnit_qty());
                jsonParams.put("unit_qty", map_bom.get(item.getItem_id()).getUnit_qty());
                jsonParams.put("package_qty", item.getQty());
                jsonParams.put("qty", item.getQty());
                jsonParams.put("location_id", item.getLocation_id());
//            ไม่ส่ง    jsonParams.put("location_name", item.getLast_location_name().trim().equals("null") ? "" : item.getLast_location_name());
//            ไม่ส่ง    jsonParams.put("ng", item.getLbl_ng());
//            ไม่ส่ง    jsonParams.put("supplier_id", item.getLbl_supplier_id().trim().equals("null") ? "" : item.getLbl_supplier_id().trim());
//            ไม่ส่ง    jsonParams.put("supplier_name", item.getLbl_supplier().trim().equals("null") ? "" : item.getLbl_supplier().trim());
                jsonParams.put("inspection_flg", "0");
                jsonParams.put("status", "2"); // OUT_STORE = 3;
                jsonParams.put("slip_divide", "4");
                jsonParams.put("create_user_id", Settings.getLoginUser().getId());

                JSONObject jsonObject = new JSONObject(jsonParams);
                jsonArray.put(jsonObject);
            }

            json.put("value",jsonArray);
            if (jsonArray.length() == 0)
                return;

            new AsyncHttpClient(getApplicationContext(),
                    Settings.getMgmtList().get("web_api") + "/ht_api.php",
                    json.toString()) {
                @Override
                protected void onFinished(String response, int resp_code) {
                    Log.d(getString(R.string.tag), "response: " + response);
                    try {
                        JSONObject jsonObject = new JSONObject(response);
                        String status = jsonObject.getString("status");
                        int affected_rows = jsonObject.getInt("affected_rows");

                        if (status.equals("success") && affected_rows > 0) {
                            Log.d(getString(R.string.tag), "success: " + response);
                            finish();

                        }else{
                            Unblock_button();
                            showWarning("Can't Outbound");
                        }

                    } catch (JSONException e) {
                        Unblock_button();
                        showError(e.getMessage());
                    }
                }
            }.execute();

        } catch (Exception e) {
            Unblock_button();
            showError(e.getMessage());
        }

    }


    private void Check_Qty() {
        if (txt_part_no.getText().toString().trim().equals("")) {
            Unblock_button();
            showWarning("Please select Part No.");

        } else {
            String str_input_ok = edt_ok.getText().toString().trim().equals("") ? "0" : edt_ok.getText().toString().trim();
            String str_input_ng = edt_ng.getText().toString().trim().equals("") ? "0" : edt_ng.getText().toString().trim();
            d_input_ok = Double.parseDouble(str_input_ok);
            d_input_ng = Double.parseDouble(str_input_ng);
            if (Utils.CompareDouble(d_input_ok, 0.0) && Utils.CompareDouble(d_input_ng, 0.0)) {
                Unblock_button();
                showWarning("Quantity is in error");

            } else {
                Prepare_Label();
            }
        }
    }

    private void Prepare_Label() {
        try {
            JSONObject json = new JSONObject();
            json.put("cmd", "SCHEDULE/LABEL/DETAILS/CONFIRM/PREPARE");
            json.put("sch_id", str_sch_id);
            json.put("lot_no", edt_lot_date.getText().toString().trim());
            json.put("ok_act_qty", String.valueOf(decimalFormat.format(d_input_ok)));
            json.put("ok_qty_per_box", String.valueOf(decimalFormat.format(d_input_ok)));
            json.put("ng_act_qty", String.valueOf(decimalFormat.format(d_input_ng)));
            json.put("ng_qty_per_box", String.valueOf(decimalFormat.format(d_input_ng)));
            json.put("user_id",Settings.getLoginUser().getId());


            new AsyncHttpClient(getApplicationContext(),
                    Settings.getMgmtList().get("web_api") + "/ht_api.php",
                    json.toString()) {
                @Override
                protected void onFinished(String response, int resp_code) {
                    Log.d(getString(R.string.tag), "response: " + response);

                    try{
                        JSONObject jsonObject = new JSONObject(response);
                        String status = jsonObject.getString("status");
                        if (status.trim().equals("error")){
                            String error = jsonObject.getString("error");
                            showError(error);
                            Unblock_button();
                        }else {
                            String value = jsonObject.getString("value");
                            j_schedules = new JSONArray(value);
//                            Log.d(getString(R.string.tag), "j_schedules: " + j_schedules.length());

                            if (Settings.getMgmtList().get("skip_print").trim().equals("1")) {
                                AlertConfirmPrint();

                            } else {
                                if (Settings.getPrinter().trim().equals("")
                                        ||Settings.getPrinter().trim().equals(null)
                                        ||Settings.getPrinter().trim().equals("null")){
                                    Unblock_button();
                                    showWarning("Please setting printer");

                                }else {
                                    Print_Label();
                                }
                            }
                        }
                    }catch (JSONException e) {
                        Unblock_button();
                        showError(e.getMessage());
                    }
                }
            }.execute();

        }catch (JSONException e) {
            Unblock_button();
            showError(e.getMessage());
        }
    }

    private void Print_Label() {
        alert.setMessage("           Printing label....         ");
        alert.show();

        String tmp_label = "";
        try {
            for (int i = 0; i < j_schedules.length(); i++) {
                String payload = j_schedules.getJSONObject(i).getString("payload");
                String content_label = j_schedules.getJSONObject(i).getString("content_label");
                String tmp = String.format(
                        "%s %s-%s%s\n%s"
                        , "PST"
                        , Settings.getPrinter()
                        , content_label
                        , ""
                        , payload + "\n");

                tmp_label = (tmp_label + tmp);

                Log.e(getString(R.string.tag), "payload tmp: " + tmp);
            }
            Log.e(getString(R.string.tag), "payload tmp_label: " + tmp_label);

            String err_msg = "";
            try {
                err_msg = "Server connection failed!\nPlease contact leader.";

                new AsyncTcpClient(getApplicationContext(),
                        Settings.getMgmtList().get("lpc_host"),
                        Integer.parseInt(Settings.getMgmtList().get("lpc_port")),
                        tmp_label + "\n\n\n"
                ) {
                    @Override
                    protected void onFinished(String response) {
                        Log.d(getString(R.string.tag), "TCP response: " + response);

                        if (response.equals("OK")) {
                            alert.dismiss();
                            AlertConfirmPrint();

                        } else {
                            alert.dismiss();
                            Unblock_button();
                            showError("Can't connect to print server");

                        }
                    }
                }.execute();
                throw new JSONException(err_msg);

            } catch (JSONException e) {
                Log.e(getString(R.string.tag), "ERROR: " + e.getMessage());
            }
        } catch (JSONException e) {
            Log.e(getString(R.string.tag), "ERROR: " + e.getMessage());
        }
    }

    private void AlertConfirmPrint() {
        try {
            SweetAlertDialog d = new SweetAlertDialog(this, SweetAlertDialog.WARNING_TYPE);
            d.setCancelable(false);
            d.setTitleText("WARNING");
            d.setContentText("Click 'No' if nothing printed out?");
            d.setCancelText("No");
            d.setCancelClickListener(new SweetAlertDialog.OnSweetClickListener() {
                @Override
                public void onClick(SweetAlertDialog sDialog) {
                    sDialog.dismiss();
                    Unblock_button();
                }
            });
            d.setConfirmText("Yes");
            d.setConfirmClickListener(new SweetAlertDialog.OnSweetClickListener() {
                @Override
                public void onClick(SweetAlertDialog sDialog) {
                    sDialog.dismiss();
                    Confirm_Label();
                }
            });
            d.show();
        } catch (WindowManager.BadTokenException e) {
            Unblock_button();
            showWarning("Please check the label status on Pegasus!");

        } catch (Exception e) {
            Unblock_button();
            showWarning("Please check the label status on Pegasus!");
        }
    }

    private void Confirm_Label() {
        try {
            JSONObject json = new JSONObject();
            json.put("cmd", "SCHEDULE/LABEL/DETAILS/CONFIRM/CONFIRM");

            JSONArray jArray = new JSONArray();
            for (int i = 0; i < j_schedules.length(); i++) {
                String label_id = j_schedules.getJSONObject(i).getString("id").trim();
                Map<String, String> jsParams = new HashMap<>();
                jsParams.put("label_id", label_id);
                JSONObject jsonObject = new JSONObject(jsParams);
                jArray.put(jsonObject);
            }
            json.put("value",jArray);

            new AsyncHttpClient(getApplicationContext(),
                    Settings.getMgmtList().get("web_api") + "/ht_api.php",
                    json.toString()) {
                @Override
                protected void onFinished(String response, int resp_code) {
                    Log.d(getString(R.string.tag), "response: " + response);

                    try{
                        JSONObject jsonObject = new JSONObject(response);
                        String status = jsonObject.getString("status");
                        int affected_rows = jsonObject.getInt("affected_rows");

                        if (status.trim().equals("success") && affected_rows > 0){
                            Clear_layout();
                        }else {
                            String error = jsonObject.getString("error");
                            showError(error);
                            Unblock_button();
                        }
                    }catch (JSONException e) {
                        showError(e.getMessage());
                        Unblock_button();
                    }
                }
            }.execute();

        } catch (JSONException e) {
            Unblock_button();
            showError(e.getMessage());
        }
    }



    private void Clear_layout() {
        Unblock_button();
        b_confirm = false;
        j_schedules = null;
        map_label.clear();
        edt_lot_date.setText(str_today);
        edt_lot_date.setEnabled(true);
        edt_lot_date.setBackgroundResource(R.drawable.button_background_menu_);

        edt_ok.setText("");
        edt_ok.setHint("0");
        edt_ok.setEnabled(true);

        edt_ng.setBackgroundResource(R.drawable.img_background_gray);
        edt_ok.setBackgroundResource(R.drawable.button_background_menu_);
        btn_print.setBackgroundResource(R.drawable.button_background_green);
        btn_print.setEnabled(true);
        btn_confirm.setBackgroundResource(R.drawable.button_background_gray);
        btn_confirm.setEnabled(false);

        spinner_lo_ok.setEnabled(false);
        spinner_lo_ok.setBackgroundResource(R.drawable.button_background_gray);
        edt_ng.setText("0");
        spinner_lo_ng.setEnabled(false);
        spinner_lo_ng.setBackgroundResource(R.drawable.button_background_gray);

        txt_total.setText(String.valueOf( decimalFormat.format(Math.round(d_act_qty)))+"/"+String.valueOf(decimalFormat.format(Math.round(d_plan_qty)))+ " "+str_unit_qty);
        spinner_lo_ok.setSelection(Settings.getList_location_ok().indexOf(str_location));

    }

    @Override
    public boolean onKeyUp(int keyCode, KeyEvent event) {
        if (keyCode >= KeyMapping.P1.getId()
                && keyCode <= KeyMapping.P4.getId())
        {
            switch (KeyMapping.fromId(keyCode)) {
                case P1:
                    imb_back.performClick();
                    break;

                case P2:
                    btn_print.performClick();
                    break;
                case P3:
                    btn_clear.performClick();
                    break;
                case P4:
                    btn_confirm.performClick();
                    break;
            }
        }

        return super.onKeyUp(keyCode, event);
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
    }
}