com.nbplus.vbroadlauncher.fragment.LoadIoTDevicesDialogFragmentStatus.java Source code

Java tutorial

Introduction

Here is the source code for com.nbplus.vbroadlauncher.fragment.LoadIoTDevicesDialogFragmentStatus.java

Source

/*
 * Copyright (c) 2015. NB Plus (www.nbplus.co.kr)
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 */

package com.nbplus.vbroadlauncher.fragment;

import android.app.Activity;
import android.app.AlertDialog;
import android.app.Dialog;
import android.bluetooth.BluetoothAdapter;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.graphics.Color;
import android.graphics.Point;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.os.Handler;
import android.support.v4.app.DialogFragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentTransaction;
import android.support.v4.content.ContextCompat;
import android.support.v4.content.LocalBroadcastManager;
import android.util.Log;
import android.view.KeyEvent;
import android.view.View;
import android.view.ViewGroup;
import android.view.Window;
import android.view.WindowManager;
import android.widget.AdapterView;
import android.widget.Button;
import android.widget.GridView;
import android.widget.ImageButton;

import com.nbplus.iotlib.IoTInterface;
import com.nbplus.iotlib.callback.IoTServiceStatusNotification;
import com.nbplus.iotlib.data.DeviceTypes;
import com.nbplus.iotlib.data.IoTDevice;
import com.nbplus.iotlib.data.IoTResultCodes;
import com.nbplus.iotlib.data.IoTServiceCommand;
import com.nbplus.iotlib.data.IoTServiceStatus;
import com.nbplus.vbroadlauncher.BaseActivity;
import com.nbplus.vbroadlauncher.BroadcastWebViewActivity;
import com.nbplus.vbroadlauncher.R;
import com.nbplus.vbroadlauncher.adapter.StickyGridHeadersIoTDevicesAdapter;
import com.nbplus.vbroadlauncher.data.Constants;

import org.basdroid.common.DisplayUtils;

import java.util.ArrayList;

/**
 * Created by basagee on 2015. 6. 23..
 */
public class LoadIoTDevicesDialogFragmentStatus extends DialogFragment
        implements DialogInterface.OnKeyListener, IoTServiceStatusNotification, AdapterView.OnItemClickListener {
    private static final String TAG = LoadIoTDevicesDialogFragmentStatus.class.getSimpleName();

    private ArrayList<IoTDevice> mIoTDevicesList = new ArrayList<>();
    private ArrayList<IoTDevice> mDisabledDeviceList = new ArrayList<>();

    // button control
    ImageButton mCloseButton;
    Button mRefreshButton;
    Button mSendButton;
    GridView mGridView;
    StickyGridHeadersIoTDevicesAdapter mGridAdapter;
    int originalOrientation = ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR;

    Handler mHandler = new Handler();

    public static LoadIoTDevicesDialogFragmentStatus newInstance(Bundle b) {
        LoadIoTDevicesDialogFragmentStatus frag = new LoadIoTDevicesDialogFragmentStatus();
        if (b != null) {
            frag.setArguments(b);
        }
        return frag;
    }

    @Override
    public Dialog onCreateDialog(Bundle savedInstanceState) {
        final Dialog dialog = new Dialog(
                getActivity()/*new ContextThemeWrapper(getActivity(), R.style.FullScreenDialog)*/);

        dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
        dialog.getWindow().setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
        setRetainInstance(true);
        originalOrientation = getActivity().getRequestedOrientation();
        getActivity().setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);

        // fullscreen without statusbar
        dialog.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
                WindowManager.LayoutParams.FLAG_FULLSCREEN);
        dialog.setCancelable(false);
        this.setCancelable(false);

        // disable back key
        dialog.setOnKeyListener(this);

        // set content view
        View v = getActivity().getLayoutInflater().inflate(R.layout.fragment_iot_devices, null, false);
        dialog.setContentView(v);

        // grid view
        mGridView = (GridView) v.findViewById(R.id.iot_devices_grid);
        mGridView.setEmptyView(v.findViewById(android.R.id.empty));

        // set button control
        mCloseButton = (ImageButton) v.findViewById(R.id.btn_close);
        mCloseButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Log.d(TAG, "onClick btnClose..");
                ((BaseActivity) getActivity()).dismissProgressDialog();
                Intent sendIntent = new Intent();
                sendIntent.setAction(Constants.ACTION_IOT_DEVICE_LIST);
                sendIntent.putExtra(Constants.EXTRA_IOT_DEVICE_CANCELED, true);
                LocalBroadcastManager.getInstance(getActivity()).sendBroadcast(sendIntent);

                dismiss();
            }
        });

        mRefreshButton = (Button) v.findViewById(R.id.btn_refresh);
        mRefreshButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Log.d(TAG, "onClick btnRefresh..");
                ((BaseActivity) getActivity()).showProgressDialog();

                IoTInterface.getInstance().getDevicesList(DeviceTypes.ALL, LoadIoTDevicesDialogFragmentStatus.this,
                        true);
                mHandler.postDelayed(new Runnable() {
                    @Override
                    public void run() {
                        ((BaseActivity) getActivity()).dismissProgressDialog();
                    }
                }, 6000);
            }
        });

        mSendButton = (Button) v.findViewById(R.id.btn_send);
        mSendButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Log.d(TAG, "onClick btnSend..");
                ((BaseActivity) getActivity()).dismissProgressDialog();
                showSyncAlertDialog();
            }
        });

        mGridView.setOnItemClickListener(this);

        return dialog;
    }

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

    @Override
    public void onActivityCreated(Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
        this.setStyle(DialogFragment.STYLE_NORMAL, R.style.FullScreenDialog);
    }

    /**
     * Called when the fragment is visible to the user and actively running.
     * This is generally
     * tied to {@link Activity#onResume() Activity.onResume} of the containing
     * Activity's lifecycle.
     */
    @Override
    public void onResume() {
        super.onResume();

        try {
            Point p = DisplayUtils.getScreenSize(getActivity());

            if (getDialog() != null && getDialog().getWindow() != null) {
                getDialog().getWindow().setLayout(p.x - 60, p.y - 30);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * Disable back button
     * implements DialogInterface.OnKeyListener
     */
    @Override
    public boolean onKey(DialogInterface dialog, int keyCode, KeyEvent event) {

        if (keyCode == KeyEvent.KEYCODE_BACK) {
            return true;
        }
        return false;
    }

    @Override
    public void onAttach(Activity activity) {
        super.onAttach(activity);
        Log.d(TAG, "dialog onAttach");
        IoTInterface.getInstance().getDevicesList(DeviceTypes.ALL, this, true);

        ((BaseActivity) getActivity()).showProgressDialog();
        mHandler.postDelayed(new Runnable() {
            @Override
            public void run() {
                ((BaseActivity) getActivity()).dismissProgressDialog();
            }
        }, 6000);
    }

    @Override
    public void onDetach() {
        super.onDetach();
        Log.d(TAG, "dialog onDetach");
        //        LocalBroadcastManager.getInstance(getActivity()).unregisterReceiver(mBroadcastReceiver);
        getActivity().setRequestedOrientation(originalOrientation);
    }

    public void showSyncAlertDialog() {
        new AlertDialog.Builder(getActivity()).setMessage(R.string.iot_devices_send_alert)
                //.setTitle(R.string.alert_network_title)
                .setCancelable(false)
                .setNegativeButton(android.R.string.cancel, new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int whichButton) {
                        dialog.dismiss();
                    }
                }).setPositiveButton(R.string.alert_ok, new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int whichButton) {
                        Intent sendIntent = new Intent();
                        sendIntent.setAction(Constants.ACTION_IOT_DEVICE_LIST);
                        sendIntent.putExtra(Constants.EXTRA_IOT_DEVICE_CANCELED, false);
                        sendIntent.putParcelableArrayListExtra(Constants.EXTRA_DATA, mIoTDevicesList);
                        LocalBroadcastManager.getInstance(getActivity()).sendBroadcast(sendIntent);

                        dialog.dismiss();
                        dismissDialogFragment();
                    }
                }).show();
    }

    private void dismissDialogFragment() {
        ((BroadcastWebViewActivity) getActivity()).dismissUpdateIoTDevicesDialog();
    }

    /**
     * ?  ...
     * => Caused by: java.lang.IllegalStateException: Can not perform this action after onSaveInstanceState
     * <p/>
     * There are two DialogFragment show() methods
     * - show(FragmentManager manager, String tag) and show(FragmentTransaction transaction, String tag).
     * <p/>
     * If you want to use the FragmentManager version of the method (as in the original question),
     * an easy solution is to override this method and use commitAllowingStateLoss:
     */
    @Override
    public void show(FragmentManager manager, String tag) {
        FragmentTransaction ft = manager.beginTransaction();
        ft.add(this, tag);
        ft.commitAllowingStateLoss();
    }

    /**
     * @param cmd
     * @param serviceStatus
     * @param serviceStatusCode
     * @param b
     */
    @Override
    public void onResult(final int cmd, final IoTServiceStatus serviceStatus,
            final IoTResultCodes serviceStatusCode, final Bundle b) {
        getActivity().runOnUiThread(new Runnable() {
            @Override
            public void run() {
                handleIoTReuslt(cmd, serviceStatus, serviceStatusCode, b);
            }
        });
    }

    private void handleIoTReuslt(int cmd, final IoTServiceStatus serviceStatus,
            final IoTResultCodes serviceStatusCode, Bundle b) {
        Log.d(TAG, "IoTServiceResponse onResult...serviceStatus = " + serviceStatus + ", statusCode = "
                + serviceStatusCode);
        switch (cmd) {
        case IoTServiceCommand.GET_DEVICE_LIST:
            if (serviceStatus == null || serviceStatusCode == null) {
                Log.e(TAG, "Unknown service status...");
                break;
            }

            if (!serviceStatus.equals(IoTServiceStatus.RUNNING)) {
                ((BaseActivity) getActivity()).dismissProgressDialog();

                if (serviceStatusCode.equals(IoTResultCodes.BLE_NOT_SUPPORTED)
                        || serviceStatusCode.equals(IoTResultCodes.BLUETOOTH_NOT_SUPPORTED)
                        || serviceStatusCode.equals(IoTResultCodes.BIND_SERVICE_FAILED)) {
                    Log.d(TAG, ">> Can't use service :: " + serviceStatusCode);
                    new AlertDialog.Builder(getActivity()).setMessage(R.string.error_bluetooth_not_supported)
                            //.setTitle(R.string.alert_network_title)
                            .setCancelable(true)
                            .setPositiveButton(R.string.alert_ok, new DialogInterface.OnClickListener() {
                                public void onClick(DialogInterface dialog, int whichButton) {
                                    Intent sendIntent = new Intent();
                                    sendIntent.setAction(Constants.ACTION_IOT_DEVICE_LIST);
                                    sendIntent.putExtra(Constants.EXTRA_IOT_DEVICE_CANCELED, true);
                                    LocalBroadcastManager.getInstance(getActivity()).sendBroadcast(sendIntent);

                                    dialog.dismiss();
                                    dismissDialogFragment();
                                }
                            }).show();
                    break;
                } else if (serviceStatusCode.equals(IoTResultCodes.BLUETOOTH_NOT_ENABLED)) {
                    Intent enableBtIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
                    getActivity().startActivityForResult(enableBtIntent,
                            Constants.START_ACTIVITY_REQUEST_ENABLE_BT);
                } else {
                    new AlertDialog.Builder(getActivity()).setMessage(R.string.error_bluetooth_not_supported)
                            //.setTitle(R.string.alert_network_title)
                            .setCancelable(true)
                            .setPositiveButton(R.string.alert_ok, new DialogInterface.OnClickListener() {
                                public void onClick(DialogInterface dialog, int whichButton) {
                                    dialog.dismiss();
                                }
                            }).show();
                }
            } else {
                if (serviceStatusCode.equals(IoTResultCodes.SUCCESS)) {
                    handleDeviceList(b);
                }
            }
            break;
        default:
            Log.d(TAG, "Unknown command ");
        }
    }

    private void handleDeviceList(Bundle b) {
        if (b == null) {
            return;
        }
        ArrayList<IoTDevice> iotDevicesList = b.getParcelableArrayList(IoTServiceCommand.KEY_DATA);
        if (iotDevicesList != null) {
            mIoTDevicesList = iotDevicesList;
        } else {
            mIoTDevicesList = new ArrayList<>();
        }
        mDisabledDeviceList.clear();

        if (mGridAdapter == null) {
            mGridAdapter = new StickyGridHeadersIoTDevicesAdapter(getActivity(), mIoTDevicesList,
                    R.layout.grid_iot_devices_header, R.layout.grid_iot_devices_item);

            mGridView.setAdapter(mGridAdapter);
        } else {
            mGridAdapter.setItems(mIoTDevicesList);
        }
        if (mGridAdapter.isEmpty()) {
            mSendButton.setEnabled(false);
            mSendButton.setClickable(false);
        } else {
            mSendButton.setEnabled(true);
            mSendButton.setClickable(true);
        }

        mHandler.postDelayed(new Runnable() {
            @Override
            public void run() {
                ((BaseActivity) getActivity()).dismissProgressDialog();
            }
        }, 500);
    }

    /**
     * Receive the result from a previous call to
     * {@link #startActivityForResult(Intent, int)}.  This follows the
     * related Activity API as described there in
     * {@link Activity#onActivityResult(int, int, Intent)}.
     *
     * @param requestCode The integer request code originally supplied to
     *                    startActivityForResult(), allowing you to identify who this
     *                    result came from.
     * @param resultCode  The integer result code returned by the child activity
     *                    through its setResult().
     * @param data        An Intent, which can return result data to the caller
     */
    @Override
    public void onActivityResult(int requestCode, int resultCode, Intent data) {
        Log.d(TAG, ">>> onActivityResult...");
        switch (requestCode) {
        case Constants.START_ACTIVITY_REQUEST_ENABLE_BT:
            // User chose not to enable Bluetooth.
            if (resultCode == Activity.RESULT_CANCELED) {
                dismissDialogFragment();

                Intent sendIntent = new Intent();
                sendIntent.setAction(Constants.ACTION_IOT_DEVICE_LIST);
                sendIntent.putExtra(Constants.EXTRA_IOT_DEVICE_CANCELED, true);
                LocalBroadcastManager.getInstance(getActivity()).sendBroadcast(sendIntent);
            } else {
                ((BaseActivity) getActivity()).showProgressDialog();
                IoTInterface.getInstance().getDevicesList(DeviceTypes.ALL, LoadIoTDevicesDialogFragmentStatus.this);
                mHandler.postDelayed(new Runnable() {
                    @Override
                    public void run() {
                        ((BaseActivity) getActivity()).dismissProgressDialog();
                    }
                }, 6000);
            }
            break;
        }
    }

    /**
     * Remove dialog.
     */
    @Override
    public void onDestroyView() {
        if (getDialog() != null && getRetainInstance()) {
            getDialog().setDismissMessage(null);
        }
        super.onDestroyView();
    }

    /**
     * Callback method to be invoked when an item in this AdapterView has
     * been clicked.
     * <p/>
     * Implementers can call getItemAtPosition(position) if they need
     * to access the data associated with the selected item.
     *
     * @param parent   The AdapterView where the click happened.
     * @param view     The view within the AdapterView that was clicked (this
     *                 will be a view provided by the adapter)
     * @param position The position of the view in the adapter.
     * @param id       The row id of the item that was clicked.
     */
    @Override
    public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
        Log.d(TAG, "onItemClick postion = " + position);
        StickyGridHeadersIoTDevicesAdapter.ViewHolder viewHolder = (StickyGridHeadersIoTDevicesAdapter.ViewHolder) view
                .getTag();
        if (viewHolder instanceof StickyGridHeadersIoTDevicesAdapter.ViewHolder) {
            if (viewHolder.isChecked) {
                viewHolder.isChecked = false;
                if (mIoTDevicesList.contains(viewHolder.device)) {
                    mIoTDevicesList.remove(viewHolder.device);
                    Log.d(TAG, "remove from mIoTDevicesList and add mDisabledDeviceList");
                }
                mDisabledDeviceList.add(viewHolder.device);
                viewHolder.textView.setBackgroundColor(getResources().getColor(R.color.iot_devices_unselected));

                if (mIoTDevicesList.size() == 0) {
                    mSendButton.setEnabled(false);
                }
            } else {
                viewHolder.isChecked = true;
                if (mDisabledDeviceList.contains(viewHolder.device)) {
                    mDisabledDeviceList.remove(viewHolder.device);
                    Log.d(TAG, "remove from mDisabledDeviceList and add mIoTDevicesList");
                }
                mIoTDevicesList.add(viewHolder.device);
                viewHolder.textView.setBackgroundColor(getResources().getColor(R.color.iot_devices_selected));

                if (mIoTDevicesList.size() > 0) {
                    mSendButton.setEnabled(true);
                }
            }
        } else {
            Log.d(TAG, "is not a view holder....");
        }
    }

}