1package eu.siacs.conversations.services;
2
3import java.util.ArrayList;
4import java.util.LinkedHashMap;
5
6import android.app.Notification;
7import android.app.NotificationManager;
8import android.app.PendingIntent;
9import android.content.Context;
10import android.content.Intent;
11import android.content.SharedPreferences;
12import android.net.Uri;
13import android.support.v4.app.NotificationCompat;
14import android.support.v4.app.TaskStackBuilder;
15import android.text.Html;
16
17import eu.siacs.conversations.R;
18import eu.siacs.conversations.entities.Conversation;
19import eu.siacs.conversations.entities.Message;
20import eu.siacs.conversations.ui.ConversationActivity;
21
22public class NotificationService {
23
24 private XmppConnectionService mXmppConnectionService;
25 private NotificationManager mNotificationManager;
26
27 private LinkedHashMap<String, ArrayList<Message>> notifications = new LinkedHashMap<String, ArrayList<Message>>();
28
29 public int NOTIFICATION_ID = 0x2342;
30
31 public NotificationService(XmppConnectionService service) {
32 this.mXmppConnectionService = service;
33 this.mNotificationManager = (NotificationManager) service
34 .getSystemService(Context.NOTIFICATION_SERVICE);
35 }
36
37 public synchronized void push(Message message) {
38 String conversationUuid = message.getConversationUuid();
39 if (notifications.containsKey(conversationUuid)) {
40 notifications.get(conversationUuid).add(message);
41 } else {
42 ArrayList<Message> mList = new ArrayList<Message>();
43 mList.add(message);
44 notifications.put(conversationUuid, mList);
45 }
46 updateNotification(true);
47 }
48
49 public void clear() {
50 notifications.clear();
51 updateNotification(false);
52 }
53
54 public void clear(Conversation conversation) {
55 notifications.remove(conversation.getUuid());
56 updateNotification(false);
57 }
58
59 private void updateNotification(boolean notify) {
60 SharedPreferences preferences = mXmppConnectionService.getPreferences();
61
62 String ringtone = preferences.getString("notification_ringtone", null);
63 boolean vibrate = preferences.getBoolean("vibrate_on_notification",
64 true);
65
66 if (notifications.size() == 0) {
67 mNotificationManager.cancel(NOTIFICATION_ID);
68 } else {
69 NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(
70 mXmppConnectionService);
71 mBuilder.setSmallIcon(R.drawable.ic_notification);
72 if (notifications.size() == 1) {
73 ArrayList<Message> messages = notifications.values().iterator()
74 .next();
75 if (messages.size() >= 1) {
76 Conversation conversation = messages.get(0)
77 .getConversation();
78 mBuilder.setLargeIcon(conversation.getImage(
79 mXmppConnectionService, 64));
80 mBuilder.setContentTitle(conversation.getName());
81 StringBuilder text = new StringBuilder();
82 for (int i = 0; i < messages.size(); ++i) {
83 text.append(messages.get(i).getReadableBody(
84 mXmppConnectionService));
85 if (i != messages.size() - 1) {
86 text.append("\n");
87 }
88 }
89 mBuilder.setStyle(new NotificationCompat.BigTextStyle()
90 .bigText(text.toString()));
91 mBuilder.setContentText(messages.get(0).getReadableBody(
92 mXmppConnectionService));
93 mBuilder.setTicker(messages.get(messages.size() - 1)
94 .getReadableBody(mXmppConnectionService));
95 mBuilder.setContentIntent(createContentIntent(conversation
96 .getUuid()));
97 } else {
98 mNotificationManager.cancel(NOTIFICATION_ID);
99 return;
100 }
101 } else {
102 NotificationCompat.InboxStyle style = new NotificationCompat.InboxStyle();
103 style.setBigContentTitle(notifications.size()
104 + " "
105 + mXmppConnectionService
106 .getString(R.string.unread_conversations));
107 StringBuilder names = new StringBuilder();
108 for (ArrayList<Message> messages : notifications.values()) {
109 if (messages.size() > 0) {
110 String name = messages.get(0).getConversation()
111 .getName();
112 style.addLine(Html.fromHtml("<b>"
113 + name
114 + "</b> "
115 + messages.get(0).getReadableBody(
116 mXmppConnectionService)));
117 names.append(name);
118 names.append(", ");
119 }
120 }
121 if (names.length() >= 2) {
122 names.delete(names.length() - 2, names.length());
123 }
124 mBuilder.setContentTitle(notifications.size()
125 + " "
126 + mXmppConnectionService
127 .getString(R.string.unread_conversations));
128 mBuilder.setContentText(names.toString());
129 mBuilder.setStyle(style);
130 }
131 if (notify) {
132 if (vibrate) {
133 int dat = 70;
134 long[] pattern = { 0, 3 * dat, dat, dat };
135 mBuilder.setVibrate(pattern);
136 }
137 mBuilder.setLights(0xffffffff, 2000, 4000);
138 if (ringtone != null) {
139 mBuilder.setSound(Uri.parse(ringtone));
140 }
141 }
142 Notification notification = mBuilder.build();
143 mNotificationManager.notify(NOTIFICATION_ID, notification);
144 }
145 }
146
147 private PendingIntent createContentIntent(String conversationUuid) {
148 TaskStackBuilder stackBuilder = TaskStackBuilder
149 .create(mXmppConnectionService);
150 stackBuilder.addParentStack(ConversationActivity.class);
151
152 Intent viewConversationIntent = new Intent(mXmppConnectionService,
153 ConversationActivity.class);
154 viewConversationIntent.setAction(Intent.ACTION_VIEW);
155 viewConversationIntent.putExtra(ConversationActivity.CONVERSATION,
156 conversationUuid);
157 viewConversationIntent.setType(ConversationActivity.VIEW_CONVERSATION);
158
159 stackBuilder.addNextIntent(viewConversationIntent);
160
161 PendingIntent resultPendingIntent = stackBuilder.getPendingIntent(0,
162 PendingIntent.FLAG_UPDATE_CURRENT);
163 return resultPendingIntent;
164 }
165}