package com.revoapp.calendar;

import android.annotation.SuppressLint;
import android.content.Context;
import android.os.Bundle;
import android.text.format.DateFormat;
import android.text.format.Time;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnTouchListener;
import android.view.ViewGroup;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.Button;
import android.widget.GridView;
import android.widget.ImageButton;
import android.widget.ListView;
import android.widget.TextView;

import com.revoapp.api.database.calendar.pojo.Events;
import com.revoapp.api.database.calendar.pojo.Pills;
import com.revoapp.api.utils.DateTimeConvert;
import com.revoapp.api.utils.ImageHelper;
import com.revoapp.api.utils.Utils;
import com.revoapp.calendar.adapter.DayNameAdapter;
import com.revoapp.calendar.adapter.WeekAdapter;
import com.revoapp.calendar.adapter.WeekDayHoursAdapter;
import com.revoapp.calendar.database.DatabaseHandler;
import com.revoapp.calendar.database.PillsDatabaseHandler;
import com.revoapp.calendar.dialogs.AddEventDialog;
import com.revoapp.calendar.helper.SimpleDialogItem;
import com.revoapp.calendar.helper.ThemeHelper;
import com.revoapp.calendarapp.R;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.GregorianCalendar;
import java.util.Locale;

public class WeekActivity extends ParentActivity {
    private Context context;
    private GridView gridView, dayOfWeek;
    private ListView weekDayHours;
    private WeekAdapter adapter;
    private ArrayList<SimpleDialogItem> days;
    private ArrayList<SimpleDialogItem> hours;
    private TextView monthInfo;
    private Calendar globalCalendar;
    private int currentWeek;
    private int selectedGridViewItem = -1;
    private int firstDayOfWeek;
    private Calendar selectedDay;
    private ArrayList<Integer> icons;
    private ArrayList<Pills> pillsList;
    private ArrayList<Events> eventsList;
    private WeekActivity weekActivity;
    private AddEventDialog addEventDialog;

    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        setContentView(R.layout.week_activity);

        weekActivity = this;
        context = this;

        Utils.disableLockScreen(this);

        init();
        calendarDayHours();
        initCalendar();

        if (savedInstanceState != null) {
            if (savedInstanceState.getBoolean("dialogAdd")) {
                addEventDialog = new AddEventDialog(context, weekActivity, savedInstanceState.getInt("numberOfScreen"), savedInstanceState.getStringArrayList("data"), savedInstanceState.getString("title"));
                addEventDialog.show();
//                InputMethodManager imm = (InputMethodManager) context.getSystemService(Context.INPUT_METHOD_SERVICE);
            }
        }
    }

    @Override
    protected void onResume() {
        super.onResume();
        refreshView();
    }

    @Override
    public void onStop() {
        super.onStop();

        if (addEventDialog != null) {
            if (addEventDialog.isShowing()) {
                addEventDialog.dismiss();
            }
        }
    }

    @Override
    public void refreshView() {
        init();
        calendarDayHours();
        initCalendar();
        CalendarActivity.setTab(CalendarActivity.tabHost.getCurrentTab());
        if (adapter != null)
            adapter.notifyDataSetChanged();
    }

    private void init() {
        PillsDatabaseHandler db = new PillsDatabaseHandler(this);
        DatabaseHandler database = new DatabaseHandler(context);
        pillsList = db.getAllPills(false);
        eventsList = database.getAllEvents();

        weekDayHours = (ListView) findViewById(R.id.week_hour_listView);
        weekDayHours.setOnTouchListener(disableScrollListener);

        gridView = (GridView) findViewById(R.id.week_gridView);
        gridView.setOnTouchListener(disableScrollListener);
        gridView.setOnItemClickListener(gridViewItemListener);

        dayOfWeek = (GridView) findViewById(R.id.week_day_gridView);
        dayOfWeek.setOnTouchListener(disableScrollListener);

        ImageButton weekLeft = (ImageButton) findViewById(R.id.month_left);
        weekLeft.setBackgroundResource(ThemeHelper.get_button_selector());
        weekLeft.setImageResource(ThemeHelper.get_icon50_arrow_left());
        weekLeft.setOnClickListener(chooseWeekListener);

        ImageButton weekRight = (ImageButton) findViewById(R.id.month_right);
        weekRight.setBackgroundResource(ThemeHelper.get_button_selector());
        weekRight.setImageResource(ThemeHelper.get_icon50_arrow_right());
        weekRight.setOnClickListener(chooseWeekListener);

        View todayV = findViewById(R.id.today_linear);
        todayV.setBackgroundResource(ThemeHelper.get_button_selector());
        todayV.setOnClickListener(todayListener);

        TextView todayIcon = (TextView) findViewById(R.id.today_icon);
        todayIcon.setBackgroundResource(ThemeHelper.get_icon50_today());
        todayIcon.setText(new GregorianCalendar().get(GregorianCalendar.DAY_OF_MONTH) + "");
        todayIcon.setTextColor(context.getResources().getColorStateList(
                ThemeHelper.get_button_color_selector()));
        todayIcon.setTextSize((int) getResources().getDimension(R.dimen.calendar_header_text));

        TextView todayText = (TextView) findViewById(R.id.today_text);
        todayText.setTextColor(context.getResources().getColorStateList(
                ThemeHelper.get_button_color_selector()));
        todayText.setTextSize((int) getResources().getDimension(R.dimen.calendar_header_text));
        todayText.setTypeface(ThemeHelper.get_primary_font());

        Button butAddEvent = (Button) findViewById(R.id.add_event);
        butAddEvent.setOnClickListener(eventAddListener);
        butAddEvent.setCompoundDrawablesWithIntrinsicBounds(R.drawable.b0_icon50_add, 0, 0, 0);
    }

    private void initCalendar() {
        selectedDay = Calendar.getInstance();
        selectedDay.set(MonthActivity.currentYear, MonthActivity.currentMonth, MonthActivity.selectedDay);
        globalCalendar = Calendar.getInstance();
        globalCalendar.setFirstDayOfWeek(Calendar.MONDAY);
        globalCalendar.set(MonthActivity.currentYear, MonthActivity.currentMonth, MonthActivity.selectedDay);
        currentWeek = globalCalendar.get(Calendar.WEEK_OF_YEAR);
        if (globalCalendar.get(Calendar.DAY_OF_WEEK) != 1) {
            globalCalendar.set(Calendar.DAY_OF_WEEK, 1);
        }

        firstDayOfWeek = globalCalendar.get(Calendar.DAY_OF_MONTH);

        monthInfo = (TextView) findViewById(R.id.month_info);
        monthInfo.setText(getWeekName());
        monthInfo.setTextSize((int) getResources().getDimension(R.dimen.calendar_header_text));

        calendarDaysName();
    }

    private void calendarWeekDays() {
        Time time = new Time();
        time.setToNow();
        int dayTime = 0;
        int dayOfWeek;
        if (time.hour >= 0 && time.hour < 6)
            dayTime = 0;
        else if (time.hour >= 6 && time.hour < 12)
            dayTime = 1;
        else if (time.hour >= 12 && time.hour < 18)
            dayTime = 2;
        else if (time.hour >= 18 && time.hour < 24)
            dayTime = 3;
        Calendar cal = Calendar.getInstance();
        setCalendarDate(cal);
        cal.add(Calendar.DAY_OF_MONTH, -6);
        dayOfWeek = Calendar.getInstance().get(Calendar.DAY_OF_WEEK);
        dayOfWeek -= 2;
        if (dayOfWeek == -1)
            dayOfWeek = 6;

        days = new ArrayList<SimpleDialogItem>();
        SimpleDialogItem item;
        for (int i = 0; i < 28; i++) {
            item = new SimpleDialogItem("");
            initIcons(i);
            if (icons != null && !icons.isEmpty())
                item.setIcons(icons);
            if (i == ((dayTime * 7) + dayOfWeek)) {
                if (cal.get(Calendar.WEEK_OF_YEAR) == Calendar.getInstance().get(Calendar.WEEK_OF_YEAR)) {
                    item.setDrawable(R.drawable.b0_icon_time_pointer);
                }
            }

            days.add(item);
        }
    }

    private Calendar setCalendarDate(Calendar calendar) {
        calendar.set(globalCalendar.get(Calendar.YEAR), globalCalendar.get(Calendar.MONTH), firstDayOfWeek);
        return calendar;
    }

    private void initIcons(int i) {
        icons = new ArrayList<Integer>();
        int day = i % 7;
        int dayTime = -1;
        if (i < 7)
            dayTime = 0;
        else if (i < 14)
            dayTime = 1;
        else if (i < 21)
            dayTime = 2;
        else if (i < 28)
            dayTime = 3;

        Calendar curCal = Calendar.getInstance();
        setCalendarDate(curCal);
        curCal.add(Calendar.DAY_OF_MONTH, -(6 - day));

        if (!pillsList.isEmpty()) {
            for (Pills pill : pillsList) {
                if (DateTimeConvert.compareDate(context, pill.getmDateTime(),
                        curCal.get(Calendar.YEAR), curCal.get(Calendar.MONTH),
                        curCal.get(Calendar.DAY_OF_MONTH))) {
                    int hour = DateTimeConvert.getHour(context, pill.getmDateTime());
                    if ((hour < 6 || hour == 24) && dayTime == 0) {
                        icons.add(ThemeHelper.get_icon50_menu_pill());
                        break;
                    }
                    if ((hour >= 6 && hour < 12) && dayTime == 1) {
                        icons.add(ThemeHelper.get_icon50_menu_pill());
                        break;
                    }
                    if ((hour >= 12 && hour < 18) && dayTime == 2) {
                        icons.add(ThemeHelper.get_icon50_menu_pill());
                        break;
                    }
                    if ((hour >= 18 && hour < 24) && dayTime == 3) {
                        icons.add(ThemeHelper.get_icon50_menu_pill());
                        break;
                    }
                }
            }
        }

        if (!eventsList.isEmpty()) {
            int h;

            for (Events event : eventsList) {
                if (DateTimeConvert.compareDate(context, event.getDate(),
                        curCal.get(Calendar.YEAR), curCal.get(Calendar.MONTH),
                        curCal.get(Calendar.DAY_OF_MONTH))) {
                    h = DateTimeConvert.getHour(context, event.getDate());

                    if ((h < 6 || h == 24) && dayTime == 0) {
                        icons.add(ThemeHelper.get_icon50_menu_event());
                        break;
                    }
                    if ((h >= 6 && h < 12) && dayTime == 1) {
                        icons.add(ThemeHelper.get_icon50_menu_event());
                        break;
                    }
                    if ((h >= 12 && h < 18) && dayTime == 2) {
                        icons.add(ThemeHelper.get_icon50_menu_event());
                        break;
                    }
                    if ((h >= 18 && h < 24) && dayTime == 3) {
                        icons.add(ThemeHelper.get_icon50_menu_event());
                        break;
                    }
                }
            }
        }
    }

    private void calendarDayHours() {
        hours = new ArrayList<SimpleDialogItem>();

        if (DateFormat.is24HourFormat(context)) {
            hours.add(new SimpleDialogItem("06"));
            hours.add(new SimpleDialogItem("12"));
            hours.add(new SimpleDialogItem("18"));
            hours.add(new SimpleDialogItem("24"));
        } else {
            hours.add(new SimpleDialogItem("06 AM"));
            hours.add(new SimpleDialogItem("12 AM"));
            hours.add(new SimpleDialogItem("06 PM"));
            hours.add(new SimpleDialogItem("12 PM"));
        }
    }

    @SuppressLint("NewApi")
    private String getWeekName() {
        Calendar cal = Calendar.getInstance();
        setCalendarDate(cal);

        Calendar calendar = Calendar.getInstance();
        setCalendarDate(calendar);

        String date;
        int monthNum;

        cal.add(Calendar.DAY_OF_MONTH, -6);

        date = cal.get(Calendar.DAY_OF_MONTH) + "";
        monthNum = cal.get(Calendar.MONTH);

        cal.add(Calendar.DAY_OF_YEAR, 6);

        if (cal.get(Calendar.MONTH) != monthNum) {
            cal.set(Calendar.MONTH, monthNum);
            date += " " + cal.getDisplayName(Calendar.MONTH, Calendar.SHORT, Locale.getDefault());
            cal.set(Calendar.MONTH, monthNum + 1);
        }

        date += " - " + cal.get(Calendar.DAY_OF_MONTH) + " ";
        date += cal.getDisplayName(Calendar.MONTH, Calendar.SHORT, Locale.getDefault()) + " ";
        date += globalCalendar.get(Calendar.YEAR);
        return date;
    }

    @SuppressLint("NewApi")
    private void calendarDaysName() {
        calendarWeekDays();
        String dayName;
        int dayNum;

        Calendar calNum = Calendar.getInstance();

        setCalendarDate(calNum);
        calNum.add(Calendar.DAY_OF_MONTH, -6);

        Calendar calName = Calendar.getInstance();

        ArrayList<SimpleDialogItem> daysName = new ArrayList<SimpleDialogItem>();
        for (int i = 0; i <= 6; i++) {
            if (i == 6)
                calName.set(Calendar.DAY_OF_WEEK, Calendar.SUNDAY);
            else
                calName.set(Calendar.DAY_OF_WEEK, (i + 2));

            dayNum = calNum.get(Calendar.DAY_OF_MONTH);

            dayName = calName.getDisplayName(Calendar.DAY_OF_WEEK, Calendar.SHORT, Locale.getDefault());

            String plus = "";
            int orientation = getResources().getConfiguration().orientation;
            if (orientation == ImageHelper.LANDSCAPE) {
                plus = " ";
            } else if (orientation == ImageHelper.PORTRAIT) {
                plus = "\n";
            }

            if (dayNum == Calendar.getInstance().get(Calendar.DAY_OF_MONTH) &&
                    calNum.get(Calendar.YEAR) == Calendar.getInstance().get(Calendar.YEAR) &&
                    calNum.get(Calendar.MONTH) == Calendar.getInstance().get(Calendar.MONTH)) {
                if (dayNum == MonthActivity.selectedDay) {
                    daysName.add(new SimpleDialogItem(true, true, dayNum + plus + dayName));
                    selectedGridViewItem = i;
                } else
                    daysName.add(new SimpleDialogItem(false, true, dayNum + plus + dayName));
            } else if (dayNum == MonthActivity.selectedDay) {
                daysName.add(new SimpleDialogItem(true, dayNum + plus + dayName));
                selectedGridViewItem = i;
            } else
                daysName.add(new SimpleDialogItem(dayNum + plus + dayName));

            calNum.add(Calendar.DAY_OF_YEAR, 1);
        }

        adapter = new WeekAdapter(context, R.layout.week_gridview_item, days);
        gridView.setAdapter(adapter);
        DayNameAdapter dayNameAdapter = new DayNameAdapter(context, R.layout.month_day_name_gridview_item, daysName);
        dayOfWeek.setAdapter(dayNameAdapter);

        WeekDayHoursAdapter hoursAdapter = new WeekDayHoursAdapter(context, R.layout.week_day_hours_row, hours);
        weekDayHours.setAdapter(hoursAdapter);
    }

    private OnItemClickListener gridViewItemListener = new OnItemClickListener() {
        @SuppressLint("NewApi")
        @Override
        public void onItemClick(AdapterView<?> arg0, View arg1, int position,
                                long arg3) {
            int pos = position % 7;

            if (selectedGridViewItem != -1) {
                ViewGroup gc = (ViewGroup) dayOfWeek.getChildAt(selectedGridViewItem);
                gc.getChildAt(0).setBackgroundResource(ThemeHelper.get_component_cell());
            }

            boolean temp = false;
            if (selectedGridViewItem != pos) {
                selectedGridViewItem = pos;
            } else
                temp = true;

            setCalendarDate(selectedDay);

            selectedDay.add(Calendar.DAY_OF_MONTH, -(6 - pos));
            MonthActivity.selectedDay = selectedDay.get(Calendar.DAY_OF_MONTH);
            MonthActivity.currentMonth = selectedDay.get(Calendar.MONTH);
            MonthActivity.currentYear = selectedDay.get(Calendar.YEAR);

            initCalendar();

            Calendar curCal = Calendar.getInstance();
            curCal.set(MonthActivity.currentYear, MonthActivity.currentMonth, MonthActivity.selectedDay);

            if (temp) {
                CalendarActivity.setTab(2);
            }
        }
    };

    private OnClickListener eventAddListener = new OnClickListener() {
        @Override
        public void onClick(View v) {
            addEventDialog = new AddEventDialog(context, weekActivity);
            addEventDialog.show();
        }
    };

    private OnTouchListener disableScrollListener = new OnTouchListener() {
        @Override
        public boolean onTouch(View v, MotionEvent event) {
            return event.getAction() == MotionEvent.ACTION_MOVE;
        }
    };

    private OnClickListener todayListener = new OnClickListener() {
        @Override
        public void onClick(View v) {
            globalCalendar = Calendar.getInstance();
            selectedDay = Calendar.getInstance();

            MonthActivity.currentYear = globalCalendar.get(Calendar.YEAR);
            MonthActivity.selectedDay = selectedDay.get(Calendar.DAY_OF_MONTH);
            MonthActivity.currentMonth = globalCalendar.get(Calendar.MONTH);
            if (globalCalendar.get(Calendar.DAY_OF_WEEK) != 1) {
                globalCalendar.set(Calendar.DAY_OF_WEEK, 1);
            }

            firstDayOfWeek = globalCalendar.get(Calendar.DAY_OF_MONTH);

            monthInfo.setText(getWeekName());

            calendarDaysName();
        }
    };

    private OnClickListener chooseWeekListener = new OnClickListener() {
        @Override
        public void onClick(View v) {
            if (v.getId() == R.id.month_left) {
                if (currentWeek == 1) {
                    currentWeek = 52;
                } else
                    currentWeek--;

                globalCalendar.add(Calendar.DAY_OF_YEAR, -7);
                selectedDay.add(Calendar.DAY_OF_YEAR, -7);
            } else if (v.getId() == R.id.month_right) {
                if (currentWeek == 52) {
                    currentWeek = 1;
                } else
                    currentWeek++;

                globalCalendar.add(Calendar.DAY_OF_YEAR, 7);
                selectedDay.add(Calendar.DAY_OF_YEAR, 7);
            }

            MonthActivity.currentYear = globalCalendar.get(Calendar.YEAR);
            MonthActivity.selectedDay = selectedDay.get(Calendar.DAY_OF_MONTH);
            MonthActivity.currentMonth = globalCalendar.get(Calendar.MONTH);
            currentWeek = globalCalendar.get(Calendar.WEEK_OF_YEAR);

            firstDayOfWeek = globalCalendar.get(Calendar.DAY_OF_MONTH);

            monthInfo.setText(getWeekName());

            calendarDaysName();

            gridView.setSelection(0);
            weekDayHours.setSelection(0);
        }
    };

    @Override
    public void onSaveInstanceState(Bundle savedInstanceState) {
        super.onSaveInstanceState(savedInstanceState);

        if (addEventDialog != null) {
            if (addEventDialog.isShowing()) {
                savedInstanceState.putBoolean("dialogAdd", true);
                savedInstanceState.putInt("numberOfScreen", addEventDialog.getNumberOfScreen());
                savedInstanceState.putStringArrayList("data", addEventDialog.getData());
                savedInstanceState.putString("title", addEventDialog.getTitle());
            }
        }
    }
}