com.chess.genesis.net.GenesisNotifier.java Source code

Java tutorial

Introduction

Here is the source code for com.chess.genesis.net.GenesisNotifier.java

Source

/* GenesisChess, an Android chess application
 * Copyright 2014, Justin Madru (justin.jdm64@gmail.com)
 *
 * 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://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.chess.genesis.net;

import android.app.*;
import android.content.*;
import android.net.*;
import android.os.*;
import android.support.v4.app.NotificationCompat.Builder;
import com.chess.genesis.*;
import com.chess.genesis.activity.*;
import com.chess.genesis.data.*;
import java.util.*;
import org.json.*;

public class GenesisNotifier extends Service implements Runnable {
    public final static int DEFAULT_POLL_FREQ = 30;

    public final static int ERROR_NOTE = 1;
    public final static int YOURTURN_NOTE = 2;
    public final static int NEWMGS_NOTE = 4;

    private final static String YOURTURN_MSG = "It's your turn in a game you're in";
    private final static String NEWMSG_MSG = "A new message was posted to a game you're in";

    private NetworkClient net;
    private SocketClient socket;
    private GameDataDB db;
    private int lock;
    private boolean fromalarm;
    private boolean error;

    private final Handler handle = new Handler() {
        @Override
        public void handleMessage(final Message msg) {
            final JSONObject json = (JSONObject) msg.obj;

            try {
                if (json.getString("result").equals("error")) {
                    error = true;
                    socket.disconnect();
                    //   SendNotification(ERROR_NOTE, json.getString("reason"));
                    return;
                }
            } catch (final JSONException e) {
                throw new RuntimeException(e.getMessage(), e);
            }

            switch (msg.what) {
            case NetworkClient.SYNC_GAMES:
                NewMove(json);
                break;
            case NetworkClient.SYNC_MSGS:
                NewMsgs(json);
                break;
            case NetworkClient.GAME_STATUS:
                game_status(json);
                break;
            }
            // release lock
            lock--;
        }
    };

    public static void clearNotification(final Context context, final int id) {
        final GameDataDB db2 = new GameDataDB(context);
        final NotificationManager nm = (NotificationManager) context.getSystemService(NOTIFICATION_SERVICE);

        if ((id & YOURTURN_NOTE) != 0) {
            if (db2.getOnlineGameList(Enums.YOUR_TURN).getCount() == 0)
                nm.cancel(YOURTURN_NOTE);
        } else if ((id & NEWMGS_NOTE) != 0) {
            if (db2.getUnreadMsgCount() == 0)
                nm.cancel(NEWMGS_NOTE);
        }
        db2.close();
    }

    @Override
    public synchronized void run() {
        final Pref pref = new Pref(this);
        if (!pref.getBool(R.array.pf_isLoggedIn) || !pref.getBool(R.array.pf_noteEnabled)) {
            CancelWakup(this);
            stopSelf();
            return;
        } else if (internetIsActive() && fromalarm) {
            CheckServer();
        }
        ScheduleWakeup(this);
        stopSelf();
    }

    @Override
    public int onStartCommand(final Intent intent, final int flags, final int startid) {
        final Bundle bundle = intent.getExtras();
        fromalarm = bundle != null && bundle.getBoolean("fromAlarm", false);

        new Thread(this).start();
        return START_NOT_STICKY;
    }

    @Override
    public IBinder onBind(final Intent intent) {
        return null;
    }

    public static void ScheduleWakeup(final Context context) {
        final Calendar cal = Calendar.getInstance();
        cal.add(Calendar.MINUTE, Pref.getInt(context, R.array.pf_notifierPolling));
        final long start = cal.getTimeInMillis();
        final long interval = start - System.currentTimeMillis();

        final Intent intent = new Intent(context, GenesisAlarm.class);
        final PendingIntent pintent = PendingIntent.getBroadcast(context, 0, intent,
                PendingIntent.FLAG_UPDATE_CURRENT);

        final AlarmManager am = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
        am.setInexactRepeating(AlarmManager.RTC, start, interval, pintent);
    }

    private static void CancelWakup(final Context context) {
        final Intent intent = new Intent(context, GenesisAlarm.class);
        final PendingIntent pintent = PendingIntent.getBroadcast(context, 0, intent,
                PendingIntent.FLAG_UPDATE_CURRENT);

        final AlarmManager am = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
        am.cancel(pintent);
    }

    private boolean internetIsActive() {
        final ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
        final NetworkInfo netInfo = cm.getActiveNetworkInfo();

        return (netInfo != null && netInfo.isConnected());
    }

    private void SendNotification(final int id, final String text) {
        final Intent intent;
        if (Pref.getBool(this, R.array.pf_tabletMode)) {
            intent = new Intent(this, MainMenuTablet.class);

            final Bundle bundle = new Bundle();
            bundle.putInt("loadFrag", Enums.ONLINE_LIST);
            intent.putExtras(bundle);
        } else {
            intent = new Intent(this, GameListOnline.class);
        }

        final PendingIntent pintent = PendingIntent.getActivity(this, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
        final NotificationManager nm = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
        final Notification note = createNotification(id, text, pintent);

        nm.notify(id, note);
    }

    private Notification createNotification(final int id, final String text, final PendingIntent pintent) {
        final Builder noteBuilder = new Builder(getApplicationContext());

        noteBuilder.setContentText(text).setSmallIcon(R.drawable.icon);

        switch (id) {
        case ERROR_NOTE:
            noteBuilder.setContentTitle("Error!");
            break;
        case YOURTURN_NOTE:
            noteBuilder.setContentTitle("It's Your turn");
            break;
        case NEWMGS_NOTE:
            noteBuilder.setContentTitle("New Message");
            break;
        }

        if (id == ERROR_NOTE) {
            noteBuilder.setAutoCancel(true);
            return noteBuilder.getNotification();
        }
        noteBuilder.setOnlyAlertOnce(true).setContentIntent(pintent);

        final Pref pref = new Pref(this);
        if (pref.getBool(R.array.pf_noteRingtoneEnable))
            noteBuilder.setSound(Uri.parse(pref.getString(R.array.pf_noteRingtone)));
        if (pref.getBool(R.array.pf_noteVibrateEnable))
            noteBuilder.setVibrate(parseVibrate());

        return noteBuilder.getNotification();
    }

    private long[] parseVibrate() {
        final String str = Pref.getString(this, R.array.pf_noteVibrate);
        final String[] arr = str.trim().split(",");
        final long[] vib = new long[arr.length];

        for (int i = 0; i < arr.length; i++)
            vib[i] = Long.parseLong(arr[i]);
        return vib;
    }

    /*
     * Sync Code
     */

    private void trylock() {
        try {
            lock++;
            while (lock > 0 && !error)
                Thread.sleep(16);
            lock = 0;
        } catch (final java.lang.InterruptedException e) {
            throw new RuntimeException(e.getMessage(), e);
        }
    }

    public void CheckServer() {
        error = false;
        lock = 0;
        socket = SocketClient.getNewInstance();
        net = new NetworkClient(socket, this, handle);
        db = new GameDataDB(this);

        final Pref pref = new Pref(this);
        final long mtime = pref.getLong(R.array.pf_lastmsgsync);
        final long gtime = pref.getLong(R.array.pf_lastgamesync);

        if (db.getOnlineGameList(Enums.YOUR_TURN).getCount() > 0) {
            SendNotification(YOURTURN_NOTE, YOURTURN_MSG);
        } else {
            net.sync_games(gtime);
            net.run();
            trylock();

            if (db.getOnlineGameList(Enums.YOUR_TURN).getCount() > 0)
                SendNotification(YOURTURN_NOTE, YOURTURN_MSG);
        }

        if (db.getUnreadMsgCount() > 0) {
            SendNotification(NEWMGS_NOTE, NEWMSG_MSG);
        } else {
            net.sync_msgs(mtime);
            net.run();
            trylock();

            if (db.getUnreadMsgCount() > 0)
                SendNotification(NEWMGS_NOTE, NEWMSG_MSG);
        }
        socket.disconnect();
        db.close();
    }

    private void NewMove(final JSONObject json) {
        try {
            final JSONArray ids = json.getJSONArray("gameids");

            for (int i = 0, len = ids.length(); i < len; i++) {
                if (error)
                    return;
                net.game_status(ids.getString(i));
                net.run();

                lock++;
            }
            // Save sync time
            final PrefEdit pref = new PrefEdit(this);
            pref.putLong(R.array.pf_lastgamesync, json.getLong("time"));
            pref.commit();
        } catch (final JSONException e) {
            throw new RuntimeException(e.getMessage(), e);
        }
    }

    private void NewMsgs(final JSONObject json) {
        try {
            final JSONArray msgs = json.getJSONArray("msglist");
            final long time = json.getLong("time");

            for (int i = 0, len = msgs.length(); i < len; i++) {
                final JSONObject item = msgs.getJSONObject(i);
                db.insertMsg(item);
            }

            // Save sync time
            final PrefEdit pref = new PrefEdit(this);
            pref.putLong(R.array.pf_lastmsgsync, time);
            pref.commit();
        } catch (final JSONException e) {
            throw new RuntimeException(e.getMessage(), e);
        }
    }

    private void game_status(final JSONObject json) {
        db.updateOnlineGame(json);
    }
}