package com.instabug.reactlibrary;

import android.app.Application;

import com.facebook.react.ReactPackage;
import com.facebook.react.bridge.JavaScriptModule;
import com.facebook.react.bridge.NativeModule;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.uimanager.ViewManager;
import com.instabug.bug.BugReporting;
import com.instabug.library.Feature;
import com.instabug.library.Instabug;
import com.instabug.library.InstabugColorTheme;
import com.instabug.library.invocation.InstabugInvocationEvent;
import com.instabug.library.invocation.util.InstabugFloatingButtonEdge;
import com.instabug.library.visualusersteps.State;
import android.graphics.Color;
import android.util.Log;

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

public class RNInstabugReactnativePackage implements ReactPackage {

    private static final String TAG = RNInstabugReactnativePackage.class.getSimpleName();

    private Application androidApplication;
    private String mAndroidApplicationToken;
    private Instabug mInstabug;
    private Instabug.Builder mBuilder;
    private ArrayList<InstabugInvocationEvent> invocationEvents = new ArrayList<>();
    private InstabugColorTheme instabugColorTheme = InstabugColorTheme.InstabugColorThemeLight;

    public RNInstabugReactnativePackage(String androidApplicationToken, Application androidApplication,
                                        String[] invocationEventValues, String primaryColor,
                                        InstabugFloatingButtonEdge floatingButtonEdge, Integer offset) {
        this.androidApplication = androidApplication;
        this.mAndroidApplicationToken = androidApplicationToken;

        //setting invocation event
        this.parseInvocationEvent(invocationEventValues);

        mInstabug = new Instabug.Builder(this.androidApplication, this.mAndroidApplicationToken)
                .setInvocationEvents(this.invocationEvents.toArray(new InstabugInvocationEvent[0]))
                .setCrashReportingState(Feature.State.ENABLED)
                .setReproStepsState(State.DISABLED)
                .build();

        if(primaryColor != null)
            Instabug.setPrimaryColor(Color.parseColor(primaryColor));
        if(floatingButtonEdge != null)
            BugReporting.setFloatingButtonEdge(floatingButtonEdge);
        if(offset != null)
            BugReporting.setFloatingButtonOffset(offset);

    }

    public RNInstabugReactnativePackage(String androidApplicationToken, Application androidApplication,
                                        String[] invocationEventValues, String primaryColor) {
        new RNInstabugReactnativePackage(androidApplicationToken,androidApplication,invocationEventValues,primaryColor,
                InstabugFloatingButtonEdge.LEFT,250);
    }

    private void parseInvocationEvent(String[] invocationEventValues) {

        for (int i = 0; i < invocationEventValues.length; i++) {
            if (invocationEventValues[i].equals("button")) {
                this.invocationEvents.add(InstabugInvocationEvent.FLOATING_BUTTON);
            } else if (invocationEventValues[i].equals("swipe")) {
                this.invocationEvents.add(InstabugInvocationEvent.TWO_FINGER_SWIPE_LEFT);

            } else if (invocationEventValues[i].equals("shake")) {
                this.invocationEvents.add(InstabugInvocationEvent.SHAKE);

            } else if (invocationEventValues[i].equals("screenshot")) {
                this.invocationEvents.add(InstabugInvocationEvent.SCREENSHOT_GESTURE);

            } else if (invocationEventValues[i].equals("none")) {
                this.invocationEvents.add(InstabugInvocationEvent.NONE);
            }
        }

        if (invocationEvents.isEmpty()) {
            invocationEvents.add(InstabugInvocationEvent.SHAKE);
        }
    }

    @Override
    public List<NativeModule> createNativeModules(ReactApplicationContext reactContext) {
        List<NativeModule> modules = new ArrayList<>();
        modules.add(new RNInstabugReactnativeModule(reactContext, this.androidApplication, this.mInstabug));
        return modules;
    }

    public List<Class<? extends JavaScriptModule>> createJSModules() {
        return Collections.emptyList();
    }

    @Override
    public List<ViewManager> createViewManagers(ReactApplicationContext reactContext) {
        return Collections.emptyList();
    }


    public static class Builder {
        //FloatingButtonEdge
        private final String FLOATING_BUTTON_EDGE_RIGHT = "right";
        private final String FLOATING_BUTTON_EDGE_LEFT = "left";

        String androidApplicationToken;
        Application application;
        String[] invocationEvents;
        String primaryColor;
        InstabugFloatingButtonEdge floatingButtonEdge;
        int offset;

        public Builder(String androidApplicationToken, Application application) {
            this.androidApplicationToken = androidApplicationToken;
            this.application = application;
        }

        public Builder setInvocationEvent(String... invocationEvents) {
            this.invocationEvents = invocationEvents;
            return this;
        }

        public Builder setPrimaryColor(String primaryColor) {
            this.primaryColor = primaryColor;
            return this;
        }

        public Builder setFloatingEdge(String floatingEdge) {
            this.floatingButtonEdge = getFloatingButtonEdge(floatingEdge);
            return this;
        }

        public Builder setFloatingButtonOffsetFromTop(int offset) {
            this.offset = offset;
            return this;
        }

        public RNInstabugReactnativePackage build() {
            return new RNInstabugReactnativePackage(androidApplicationToken,application,invocationEvents,primaryColor,floatingButtonEdge,offset);
        }

        private InstabugFloatingButtonEdge getFloatingButtonEdge(String floatingButtonEdgeValue) {
            InstabugFloatingButtonEdge floatingButtonEdge = InstabugFloatingButtonEdge.RIGHT;
            try {
                if (floatingButtonEdgeValue.equals(FLOATING_BUTTON_EDGE_LEFT)) {
                    floatingButtonEdge = InstabugFloatingButtonEdge.LEFT;
                } else if (floatingButtonEdgeValue.equals(FLOATING_BUTTON_EDGE_RIGHT)) {
                    floatingButtonEdge = InstabugFloatingButtonEdge.RIGHT;
                }
                return floatingButtonEdge;

            } catch(Exception e) {
                e.printStackTrace();
                return floatingButtonEdge;
            }
        }
    }

}

@@ -974,25 +974,29 @@
 mpleName();%0A
+    
 %0A
-
     private 
@@ -1619,24 +1619,55 @@
 teger offset
+, boolean crashReportingEnabled
 ) %7B%0A        
@@ -2113,24 +2113,72 @@
 ate(
-Feature.State.EN
+crashReportingEnabled ? Feature.State.ENABLED: Feature.State.DIS
 ABLE
@@ -2932,16 +2932,22 @@
 LEFT,250
+, true
 );%0A    %7D
@@ -4954,16 +4954,64 @@
  offset;
+%0A        boolean isCrashReportingEnabled = true;
 %0A%0A      
@@ -5363,32 +5363,187 @@
 his;%0A        %7D%0A%0A
+        public Builder setCrashReportingEnabled(boolean enabled) %7B%0A            this.isCrashReportingEnabled = enabled;%0A            return this;%0A        %7D%0A%0A
         public B
@@ -6031,24 +6031,24 @@
 e build() %7B%0A
-
             
@@ -6178,16 +6178,41 @@
 e,offset
+, isCrashReportingEnabled
 );%0A     

allow RN package to configure crash reporting