package com.reactnativebluestackmodule;

import com.reactnativebluestackmodule.common.ReactNativeModule;
import com.reactnativebluestackmodule.common.BluestackAdsCommon;

import android.util.Log;
import android.app.Activity;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;

import com.facebook.react.bridge.Arguments;
import com.facebook.react.bridge.LifecycleEventListener;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.bridge.ReactContext;
import com.facebook.react.bridge.ReactContextBaseJavaModule;
import com.facebook.react.bridge.ReactMethod;
import com.facebook.react.bridge.WritableMap;
import com.facebook.react.modules.core.DeviceEventManagerModule;
import com.mngads.MNGAdsFactory;
import com.mngads.listener.MNGClickListener;
import com.mngads.listener.MNGInterstitialListener;
import com.mngads.util.MNGPreference;
import com.mngads.util.MNGGender;
import android.location.Location;

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

// import com.mngads.global.MNGConstants;

public class BluestackInterstitialAdManager extends ReactNativeModule
        implements LifecycleEventListener, MNGInterstitialListener, MNGClickListener {

    private static final String TAG = "BluestackInterstitialAdManager Bridge";
    private static final String REACT_CLASS = "BluestackInterstitialAdManager";
    private static final String EVENT_LOADED_AD = "onAdLoaded";
    private static final String EVENT_DISAPPEAR_AD = "onAdDismissed";
    private static final String EVENT_DID_SHOWN_AD = "onAdDisplayed";
    private static final String EVENT_AD_CLICKED = "onAdClicked";
    private static final String EVENT_AD_ERROR = "onAdFailedError";
    private static final String EVENT_AD_MESSAGE_ERROR_KEY = "errorMessage";

    private static final String EVENT_KEY = "interstitialEvent";
    private static final String EVENT_NAME = "InterstitialAdEvent";

    private MNGAdsFactory mMNGAdsInterstitialAdsFactory;
    private MNGPreference mMNGPreference;

    public BluestackInterstitialAdManager(ReactApplicationContext reactContext) {
        super(reactContext, TAG);
        reactContext.addLifecycleEventListener(this);
    }

    @ReactMethod
    public void loadAd(String placementId, boolean autoDisplay, String jsonPreference) {

        // instantiate mng Ads Factory
        if (mMNGAdsInterstitialAdsFactory == null) {
            mMNGAdsInterstitialAdsFactory = new MNGAdsFactory(getActivity());
        }

        // set MNG placement Id
        mMNGAdsInterstitialAdsFactory.setPlacementId(placementId);

        // set event listeners
        mMNGAdsInterstitialAdsFactory.setClickListener(this);
        mMNGAdsInterstitialAdsFactory.setInterstitialListener(this);

        mMNGPreference = BluestackAdsCommon.getMNGPreference(jsonPreference, getApplicationContext());

        try {
            Activity currentActivity = getActivity();

            if (currentActivity == null) {
                Log.d(TAG, "loadInterstitial attempted but the current Activity was null.");
                return;
            }
            currentActivity.runOnUiThread(
                    () -> mMNGAdsInterstitialAdsFactory.loadInterstitial(mMNGPreference, autoDisplay));
        } catch (Exception e) {
            Log.d(TAG, "loadInterstitial failed with exception: " + e.toString());
        }
    }

    @ReactMethod
    public void displayAd() {
        if (mMNGAdsInterstitialAdsFactory.isInterstitialReady()) {
            try {
                Activity currentActivity = getActivity();

                if (currentActivity == null) {
                    Log.d(TAG, "displayInterstitial attempted but the current Activity was null.");
                    return;
                }
                currentActivity.runOnUiThread(
                        () -> mMNGAdsInterstitialAdsFactory.displayInterstitial());
            } catch (Exception e) {
                Log.d(TAG, "displayInterstitial failed with exception: " + e.toString());
            }

        } else {
            WritableMap params = Arguments.createMap();
            params.putString(EVENT_KEY, EVENT_AD_ERROR);
            params.putString(EVENT_AD_MESSAGE_ERROR_KEY, "Interstitial Ad is not loaded");
            sendEvent(getContext(), params);
        }
    }

    @Override
    public void interstitialDidLoad() {
        // Log.d(TAG, "interstitialDidLoad");
        WritableMap params = Arguments.createMap();
        params.putString(EVENT_KEY, EVENT_LOADED_AD);
        sendEvent(getContext(), params);
    }

    @Override
    public void interstitialDidFail(Exception e) {
        Log.d(TAG, "interstitialDidFail: " + e.getMessage());
        WritableMap params = Arguments.createMap();
        params.putString(EVENT_KEY, EVENT_AD_ERROR);
        params.putString(EVENT_AD_MESSAGE_ERROR_KEY,
                "interstitialDidFail: error code= " + e.hashCode() + " message= " + e.getMessage());
        sendEvent(getContext(), params);
    }

    @Override
    public void interstitialDisappear() {
        // Log.d(TAG, "interstitialDisappear");
        WritableMap params = Arguments.createMap();
        params.putString(EVENT_KEY, EVENT_DISAPPEAR_AD);
        sendEvent(getContext(), params);
    }

    @Override
    public void interstitialDidShown() {
        // Log.d(TAG, "interstitialDidShown");
        WritableMap params = Arguments.createMap();
        params.putString(EVENT_KEY, EVENT_DID_SHOWN_AD);
        sendEvent(getContext(), params);
    }

    @Override
    public void onAdClicked() {
        // Log.d(TAG, "onInterstitialAdClicked");
        WritableMap params = Arguments.createMap();
        params.putString(EVENT_KEY, EVENT_AD_CLICKED);
        sendEvent(getContext(), params);
    }

    @NonNull
    @Override
    public String getName() {
        return REACT_CLASS;
    }

    @Override
    public void initialize() {
        super.initialize();
    }

    @Override
    public void onHostResume() {

    }

    @Override
    public void onHostPause() {

    }

    @Override
    public void onHostDestroy() {
        if (mMNGAdsInterstitialAdsFactory != null) {
            mMNGAdsInterstitialAdsFactory.releaseMemory();
            mMNGAdsInterstitialAdsFactory = null;
        }
    }

    private void sendEvent(ReactContext reactContext, @Nullable WritableMap params) {
        reactContext
                .getJSModule(DeviceEventManagerModule.RCTDeviceEventEmitter.class)
                .emit(EVENT_NAME, params);
    }

    @ReactMethod
    public void addListener(String eventName) {
        // Set up any upstream listeners or background tasks as necessary
    }

    @ReactMethod
    public void removeListeners(Integer count) {
        // Remove upstream listeners, stop unnecessary background tasks
    }

}
