package com.bolan.android.modules.huashi;

import android.media.AudioAttributes;
import android.media.AudioManager;
import android.media.SoundPool;
import android.os.Build;
import android.os.Environment;
import android.os.IPowerManager;
import android.os.ServiceManager;
import android.util.Base64;
import android.util.Log;

import com.bolanmanagerapp.R;
import com.facebook.react.bridge.Arguments;
import com.facebook.react.bridge.Promise;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.bridge.ReactContextBaseJavaModule;
import com.facebook.react.bridge.ReactMethod;
import com.facebook.react.bridge.WritableMap;
import com.huashi.lua.HsUtlis;
import com.huashi.serialport.sdk.HsSerialPortSDK;
import com.huashi.serialport.sdk.IDCardInfo;

import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Locale;

/**
 * Created by yaohx_169 on 2017/9/27.
 */

public class IDCard extends ReactContextBaseJavaModule {

    private IPowerManager mPower;
    private HsSerialPortSDK sdk;
    private SoundPool soundPool;

    public IDCard(ReactApplicationContext reactContext) {
        super(reactContext);
    }

    @Override
    public String getName() {
        return "IDCard";
    }

    private int getVersion() {
        return Build.VERSION.SDK_INT;
    }

    private void powerOn() throws Exception {
        if (getVersion() == 22) {
            mPower = IPowerManager.Stub.asInterface(ServiceManager.getService("power"));
            mPower.SetCardPower(1);
        } else {
            HsUtlis.IDCardPonwer1();
        }
    }

    private void powerOff() throws Exception {
        if (getVersion() == 22) {
            mPower.SetCardPower(0);
        } else {
            HsUtlis.IDCardPonoff1();
        }
    }

    private void createSoundPool(int maxStreams, int streamType) {
        if (Build.VERSION.SDK_INT >= 21) {
            SoundPool.Builder builder = new SoundPool.Builder();
            builder.setMaxStreams(maxStreams);
            AudioAttributes.Builder attrBuilder = new AudioAttributes.Builder();
            attrBuilder.setLegacyStreamType(streamType);
            builder.setAudioAttributes(attrBuilder.build());
            soundPool = builder.build();
        } else {
            //noinspection deprecation
            soundPool = new SoundPool(maxStreams, streamType, 5);
        }
        soundPool.load(getCurrentActivity(), R.raw.bi, 1);
    }

    private void destroySoundPool() {
        if (soundPool != null) {
            soundPool.release();
            soundPool = null;
        }
    }

    private void bee(int count) {
        if (soundPool != null) {
            soundPool.play(1, 1, 1, 0, count, 1);
        }
    }

    @ReactMethod
    public void open(Promise promise) {
        Log.i("IDCard-Native", "open");
        try {
            if (sdk != null) {
                sdk.close();
                sdk = null;
                destroySoundPool();
                powerOff();
            }
            powerOn();
            sdk = new HsSerialPortSDK(getCurrentActivity());
            int ret = sdk.init("/dev/ttyMT1", 115200, 0);
            if (ret == 0) {
                createSoundPool(10, AudioManager.STREAM_SYSTEM);
                WritableMap result = Arguments.createMap();
                result.putString("msg", "身份证模块开启成功。");
                result.putString("sam", sdk.GetSAM());
                promise.resolve(result);
            } else {
                promise.reject("INIT_FAILED_" + ret, "身份证模块准备失败，错误号：" + ret);
            }
        } catch (Exception e) {
            try {
                if (sdk != null) {
                    sdk.close();
                    sdk = null;
                    destroySoundPool();
                    powerOff();
                }
                promise.reject(e);
            } catch (Exception e0) {
                promise.reject(e0);
            }
        }
    }

    @ReactMethod
    public void close(Promise promise) {
        Log.i("IDCard-Native", "close");
        if (sdk != null) {
            try {
                sdk.close();
                sdk = null;
                destroySoundPool();
                powerOff();
                promise.resolve("身份证模块关闭成功。");
            } catch (Exception e) {
                promise.reject(e);
            }
        }
    }

    @ReactMethod
    public void authenticate(int timeout, Promise promise) {
        Log.i("IDCard-Native", "authenticate");
        if (sdk == null) {
            promise.reject("NOT_OPEN_YET", "请先开启身份证认证模块。");
            return;
        }
        try {
            int ret = sdk.Authenticate(timeout);
            if (ret == 0) {
                promise.resolve("身份证认证成功。");
            } else {
                promise.reject("AUTH_FAILED_" + ret, "身份证认证失败。");
            }
        } catch (Exception e) {
            promise.reject(e);
        }
    }

    @ReactMethod
    public void read(int timeout, Promise promise) {
        Log.i("IDCard-Native", "read");
        if (sdk == null) {
            promise.reject("NOT_OPEN_YET", "请先开启身份证认证模块。");
            return;
        }
        try {
            IDCardInfo ic = new IDCardInfo();
            int ret = sdk.Read_Card(ic, timeout);
            if (getVersion() == 22) {
                bee(1);
            } else {
                bee(2);
            }
            ret = sdk.Unpack(ic.getwltdata());
            if (ret != 0) {
                promise.reject("READ_PHOTO_FAILED", "读取身份证照片失败。");
                return;
            }
            DateFormat df = new SimpleDateFormat("yyyy/MM/dd", Locale.getDefault());
            WritableMap result = Arguments.createMap();
            result.putString("peopleName", ic.getPeopleName());
            result.putString("sex", ic.getSex());
            result.putString("people", ic.getPeople());
            result.putString("birthDay", df.format(ic.getBirthDay()));
            result.putString("addr", ic.getAddr());
            result.putString("idcard", ic.getIDCard());
            result.putString("department", ic.getDepartment());
            result.putString("startDate", ic.getStrartDate());
            result.putString("endDate", ic.getEndDate());
            result.putString("newAddr", ic.getNewAddr());
            result.putString("faData", Base64.encodeToString(ic.getFpDate(), Base64.DEFAULT));
            result.putString("wltData", Base64.encodeToString(ic.getwltdata(), Base64.DEFAULT));
            result.putString("photoUri", Environment.getExternalStorageDirectory().toURI().resolve("wltlib/zp.bmp").toASCIIString());
            promise.resolve(result);
        } catch (Exception e) {
            promise.reject(e);
        }
    }

}
