BluetoothMapContentObserver.java revision 725c70cfb004690027ded41f080bfe1bb17d2285
1fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie/* 25a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Copyright (C) 2014 Samsung System LSI 35a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Licensed under the Apache License, Version 2.0 (the "License"); 45a60e47497f21f64e6d79420dc4c56c1907df22akschulz * you may not use this file except in compliance with the License. 55a60e47497f21f64e6d79420dc4c56c1907df22akschulz * You may obtain a copy of the License at 65a60e47497f21f64e6d79420dc4c56c1907df22akschulz * 75a60e47497f21f64e6d79420dc4c56c1907df22akschulz * http://www.apache.org/licenses/LICENSE-2.0 85a60e47497f21f64e6d79420dc4c56c1907df22akschulz * 95a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Unless required by applicable law or agreed to in writing, software 105a60e47497f21f64e6d79420dc4c56c1907df22akschulz * distributed under the License is distributed on an "AS IS" BASIS, 115a60e47497f21f64e6d79420dc4c56c1907df22akschulz * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 125a60e47497f21f64e6d79420dc4c56c1907df22akschulz * See the License for the specific language governing permissions and 135a60e47497f21f64e6d79420dc4c56c1907df22akschulz * limitations under the License. 145a60e47497f21f64e6d79420dc4c56c1907df22akschulz */ 15fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xiepackage com.android.bluetooth.map; 16fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 175a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport android.annotation.TargetApi; 18fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.app.Activity; 19fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.app.PendingIntent; 20fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.content.BroadcastReceiver; 21326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bondeimport android.content.ContentProviderClient; 22fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.content.ContentResolver; 23fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.content.ContentUris; 24fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.content.ContentValues; 25fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.content.Context; 26fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.content.Intent; 27fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.content.IntentFilter; 28326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bondeimport android.content.IntentFilter.MalformedMimeTypeException; 29edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chouimport android.content.pm.PackageManager; 30fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.database.ContentObserver; 31fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.database.Cursor; 32fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.net.Uri; 33edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chouimport android.os.Binder; 34fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.os.Handler; 355a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport android.os.Looper; 36326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bondeimport android.os.Message; 37326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bondeimport android.os.ParcelFileDescriptor; 38edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chouimport android.os.Process; 39326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bondeimport android.os.RemoteException; 4089de413eba69b0c5e128a82e0ad179cec9152578Ajay Panickerimport android.os.UserManager; 41fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.provider.Telephony; 42fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.provider.Telephony.Mms; 43fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.provider.Telephony.MmsSms; 44fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.provider.Telephony.Sms; 45fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.provider.Telephony.Sms.Inbox; 46fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.telephony.PhoneStateListener; 47fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.telephony.ServiceState; 48fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.telephony.SmsManager; 49fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.telephony.SmsMessage; 50fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.telephony.TelephonyManager; 51326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bondeimport android.text.format.DateUtils; 52eb7b90f5b93db1230a5b64caa3d8d05a642e33a6Marie Janssenimport android.text.TextUtils; 53fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.util.Log; 54fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport android.util.Xml; 555a60e47497f21f64e6d79420dc4c56c1907df22akschulz 565a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport org.xmlpull.v1.XmlSerializer; 57fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 58fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport com.android.bluetooth.map.BluetoothMapUtils.TYPE; 595a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport com.android.bluetooth.map.BluetoothMapbMessageMime.MimePart; 605a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport com.android.bluetooth.mapapi.BluetoothMapContract; 615a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport com.android.bluetooth.mapapi.BluetoothMapContract.MessageColumns; 62fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xieimport com.google.android.mms.pdu.PduHeaders; 63fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 645a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.io.FileNotFoundException; 655a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.io.FileOutputStream; 665a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.io.IOException; 675a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.io.OutputStream; 685a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.io.StringWriter; 695a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.io.UnsupportedEncodingException; 705a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.util.ArrayList; 715a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.util.Arrays; 725a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.util.Calendar; 735a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.util.Collections; 745a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.util.HashMap; 755a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.util.HashSet; 765a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.util.Map; 775a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport java.util.Set; 785a60e47497f21f64e6d79420dc4c56c1907df22akschulz 795a60e47497f21f64e6d79420dc4c56c1907df22akschulzimport javax.obex.ResponseCodes; 805a60e47497f21f64e6d79420dc4c56c1907df22akschulz 815a60e47497f21f64e6d79420dc4c56c1907df22akschulz@TargetApi(19) 82fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xiepublic class BluetoothMapContentObserver { 83fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private static final String TAG = "BluetoothMapContentObserver"; 84fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 85326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private static final boolean D = BluetoothMapService.DEBUG; 86326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private static final boolean V = BluetoothMapService.VERBOSE; 87326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 885a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final String EVENT_TYPE_NEW = "NewMessage"; 895a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final String EVENT_TYPE_DELETE = "MessageDeleted"; 905a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final String EVENT_TYPE_REMOVED = "MessageRemoved"; 915a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final String EVENT_TYPE_SHIFT = "MessageShift"; 92326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private static final String EVENT_TYPE_DELEVERY_SUCCESS = "DeliverySuccess"; 93326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private static final String EVENT_TYPE_SENDING_SUCCESS = "SendingSuccess"; 94326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private static final String EVENT_TYPE_SENDING_FAILURE = "SendingFailure"; 95326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private static final String EVENT_TYPE_DELIVERY_FAILURE = "DeliveryFailure"; 965a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final String EVENT_TYPE_READ_STATUS = "ReadStatusChanged"; 975a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final String EVENT_TYPE_CONVERSATION = "ConversationChanged"; 985a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final String EVENT_TYPE_PRESENCE = "ParticipantPresenceChanged"; 995a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final String EVENT_TYPE_CHAT_STATE = "ParticipantChatStateChanged"; 1005a60e47497f21f64e6d79420dc4c56c1907df22akschulz 1015a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_NEW_MESSAGE = 1L; 1025a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_MESSAGE_DELETED = 1L<<1; 1035a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_MESSAGE_SHIFT = 1L<<2; 1045a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_SENDING_SUCCESS = 1L<<3; 1055a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_SENDING_FAILED = 1L<<4; 1065a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_DELIVERY_SUCCESS = 1L<<5; 1075a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_DELIVERY_FAILED = 1L<<6; 1085a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_MEMORY_FULL = 1L<<7; // Unused 1095a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_MEMORY_AVAILABLE = 1L<<8; // Unused 1105a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_READ_STATUS_CHANGED = 1L<<9; 1115a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_CONVERSATION_CHANGED = 1L<<10; 1125a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_PARTICIPANT_PRESENCE_CHANGED = 1L<<11; 1135a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_PARTICIPANT_CHATSTATE_CHANGED= 1L<<12; 1145a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final long EVENT_FILTER_MESSAGE_REMOVED = 1L<<13; 1155a60e47497f21f64e6d79420dc4c56c1907df22akschulz 1165a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: If we are requesting a large message from the network, on a slow connection 1175a60e47497f21f64e6d79420dc4c56c1907df22akschulz // 20 seconds might not be enough... But then again 20 seconds is long for other 1185a60e47497f21f64e6d79420dc4c56c1907df22akschulz // cases. 119326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private static final long PROVIDER_ANR_TIMEOUT = 20 * DateUtils.SECOND_IN_MILLIS; 120fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 121fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private Context mContext; 122fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private ContentResolver mResolver; 123326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private ContentProviderClient mProviderClient = null; 124fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private BluetoothMnsObexClient mMnsClient; 125326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private BluetoothMapMasInstance mMasInstance = null; 126fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private int mMasId; 127326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private boolean mEnableSmsMms = false; 128326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private boolean mObserverRegistered = false; 1295a60e47497f21f64e6d79420dc4c56c1907df22akschulz private BluetoothMapAccountItem mAccount; 130326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private String mAuthority = null; 131326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 1325a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Default supported feature bit mask is 0x1f 1335a60e47497f21f64e6d79420dc4c56c1907df22akschulz private int mMapSupportedFeatures = BluetoothMapUtils.MAP_FEATURE_DEFAULT_BITMASK; 1345a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Default event report version is 1.0 1355a60e47497f21f64e6d79420dc4c56c1907df22akschulz private int mMapEventReportVersion = BluetoothMapUtils.MAP_EVENT_REPORT_V10; 1365a60e47497f21f64e6d79420dc4c56c1907df22akschulz 137326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private BluetoothMapFolderElement mFolders = 138326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde new BluetoothMapFolderElement("DUMMY", null); // Will be set by the MAS when generated. 139326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private Uri mMessageUri = null; 1405a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Uri mContactUri = null; 1415a60e47497f21f64e6d79420dc4c56c1907df22akschulz 1425a60e47497f21f64e6d79420dc4c56c1907df22akschulz private boolean mTransmitEvents = true; 1435a60e47497f21f64e6d79420dc4c56c1907df22akschulz 1445a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* To make the filter update atomic, we declare it volatile. 1455a60e47497f21f64e6d79420dc4c56c1907df22akschulz * To avoid a penalty when using it, copy the value to a local 1465a60e47497f21f64e6d79420dc4c56c1907df22akschulz * non-volatile variable when used more than once. 1475a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Actually we only ever use the lower 4 bytes of this variable, 1485a60e47497f21f64e6d79420dc4c56c1907df22akschulz * hence we could manage without the volatile keyword, but as 1495a60e47497f21f64e6d79420dc4c56c1907df22akschulz * we tend to copy ways of doing things, we better do it right:-) */ 1505a60e47497f21f64e6d79420dc4c56c1907df22akschulz private volatile long mEventFilter = 0xFFFFFFFFL; 151fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 152fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public static final int DELETED_THREAD_ID = -1; 153fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 154326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // X-Mms-Message-Type field types. These are from PduHeaders.java 155fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public static final int MESSAGE_TYPE_RETRIEVE_CONF = 0x84; 156fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 157326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // Text only MMS converted to SMS if sms parts less than or equal to defined count 158326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private static final int CONVERT_MMS_TO_SMS_PART_COUNT = 10; 159326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 160fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private TYPE mSmsType; 161fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 162ed70219e41ba68196798dcbf75b782d13fb88603kschulz private static final String ACTION_MESSAGE_DELIVERY = 163ed70219e41ba68196798dcbf75b782d13fb88603kschulz "com.android.bluetooth.BluetoothMapContentObserver.action.MESSAGE_DELIVERY"; 164ed70219e41ba68196798dcbf75b782d13fb88603kschulz /*package*/ static final String ACTION_MESSAGE_SENT = 165ed70219e41ba68196798dcbf75b782d13fb88603kschulz "com.android.bluetooth.BluetoothMapContentObserver.action.MESSAGE_SENT"; 166ed70219e41ba68196798dcbf75b782d13fb88603kschulz 167ed70219e41ba68196798dcbf75b782d13fb88603kschulz public static final String EXTRA_MESSAGE_SENT_HANDLE = "HANDLE"; 168ed70219e41ba68196798dcbf75b782d13fb88603kschulz public static final String EXTRA_MESSAGE_SENT_RESULT = "result"; 169ed70219e41ba68196798dcbf75b782d13fb88603kschulz public static final String EXTRA_MESSAGE_SENT_MSG_TYPE = "type"; 170ed70219e41ba68196798dcbf75b782d13fb88603kschulz public static final String EXTRA_MESSAGE_SENT_URI = "uri"; 171ed70219e41ba68196798dcbf75b782d13fb88603kschulz public static final String EXTRA_MESSAGE_SENT_RETRY = "retry"; 172ed70219e41ba68196798dcbf75b782d13fb88603kschulz public static final String EXTRA_MESSAGE_SENT_TRANSPARENT = "transparent"; 173ed70219e41ba68196798dcbf75b782d13fb88603kschulz public static final String EXTRA_MESSAGE_SENT_TIMESTAMP = "timestamp"; 174ed70219e41ba68196798dcbf75b782d13fb88603kschulz 175ed70219e41ba68196798dcbf75b782d13fb88603kschulz private SmsBroadcastReceiver mSmsBroadcastReceiver = new SmsBroadcastReceiver(); 176725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker private CeBroadcastReceiver mCeBroadcastReceiver = new CeBroadcastReceiver(); 177ed70219e41ba68196798dcbf75b782d13fb88603kschulz 178725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker private boolean mStorageUnlocked = false; 179ed70219e41ba68196798dcbf75b782d13fb88603kschulz private boolean mInitialized = false; 180ed70219e41ba68196798dcbf75b782d13fb88603kschulz 181ed70219e41ba68196798dcbf75b782d13fb88603kschulz 182fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie static final String[] SMS_PROJECTION = new String[] { 183326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Sms._ID, 184fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Sms.THREAD_ID, 185fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Sms.ADDRESS, 186fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Sms.BODY, 187fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Sms.DATE, 188fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Sms.READ, 189fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Sms.TYPE, 190fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Sms.STATUS, 191fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Sms.LOCKED, 192326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Sms.ERROR_CODE 193fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie }; 194fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 195326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde static final String[] SMS_PROJECTION_SHORT = new String[] { 196326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Sms._ID, 197326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Sms.THREAD_ID, 1985a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.TYPE, 1995a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.READ 2005a60e47497f21f64e6d79420dc4c56c1907df22akschulz }; 2015a60e47497f21f64e6d79420dc4c56c1907df22akschulz 2025a60e47497f21f64e6d79420dc4c56c1907df22akschulz static final String[] SMS_PROJECTION_SHORT_EXT = new String[] { 2035a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms._ID, 2045a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.THREAD_ID, 2055a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.ADDRESS, 2065a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.BODY, 2075a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.DATE, 2085a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.READ, 2095a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.TYPE, 210326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde }; 211326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 212326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde static final String[] MMS_PROJECTION_SHORT = new String[] { 213326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Mms._ID, 214fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Mms.THREAD_ID, 215fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Mms.MESSAGE_TYPE, 2165a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.MESSAGE_BOX, 2175a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.READ 2185a60e47497f21f64e6d79420dc4c56c1907df22akschulz }; 2195a60e47497f21f64e6d79420dc4c56c1907df22akschulz 2205a60e47497f21f64e6d79420dc4c56c1907df22akschulz static final String[] MMS_PROJECTION_SHORT_EXT = new String[] { 2215a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms._ID, 2225a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.THREAD_ID, 2235a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.MESSAGE_TYPE, 2245a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.MESSAGE_BOX, 2255a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.READ, 2265a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.DATE, 2275a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.SUBJECT, 2285a60e47497f21f64e6d79420dc4c56c1907df22akschulz Mms.PRIORITY 229fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie }; 230fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2315a60e47497f21f64e6d79420dc4c56c1907df22akschulz static final String[] MSG_PROJECTION_SHORT = new String[] { 232326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde BluetoothMapContract.MessageColumns._ID, 233326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde BluetoothMapContract.MessageColumns.FOLDER_ID, 234326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde BluetoothMapContract.MessageColumns.FLAG_READ 235326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde }; 236326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2375a60e47497f21f64e6d79420dc4c56c1907df22akschulz static final String[] MSG_PROJECTION_SHORT_EXT = new String[] { 2385a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns._ID, 2395a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FOLDER_ID, 2405a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FLAG_READ, 2415a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.DATE, 2425a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.SUBJECT, 2435a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FROM_LIST, 2445a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FLAG_HIGH_PRIORITY 2455a60e47497f21f64e6d79420dc4c56c1907df22akschulz }; 2465a60e47497f21f64e6d79420dc4c56c1907df22akschulz 2475a60e47497f21f64e6d79420dc4c56c1907df22akschulz static final String[] MSG_PROJECTION_SHORT_EXT2 = new String[] { 2485a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns._ID, 2495a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FOLDER_ID, 2505a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FLAG_READ, 2515a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.DATE, 2525a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.SUBJECT, 2535a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FROM_LIST, 2545a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FLAG_HIGH_PRIORITY, 2555a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.THREAD_ID, 2565a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.THREAD_NAME 2575a60e47497f21f64e6d79420dc4c56c1907df22akschulz }; 258326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 259326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde public BluetoothMapContentObserver(final Context context, 2605a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMnsObexClient mnsClient, 2615a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapMasInstance masInstance, 2625a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapAccountItem account, 2635a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean enableSmsMms) throws RemoteException { 264fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie mContext = context; 265fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie mResolver = mContext.getContentResolver(); 266326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mAccount = account; 267326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mMasInstance = masInstance; 268326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mMasId = mMasInstance.getMasId(); 2695a60e47497f21f64e6d79420dc4c56c1907df22akschulz 2705a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMapSupportedFeatures = mMasInstance.getRemoteFeatureMask(); 2715a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (D) Log.d(TAG, "BluetoothMapContentObserver: Supported features " + 2725a60e47497f21f64e6d79420dc4c56c1907df22akschulz Integer.toHexString(mMapSupportedFeatures) ) ; 2735a60e47497f21f64e6d79420dc4c56c1907df22akschulz 2745a60e47497f21f64e6d79420dc4c56c1907df22akschulz if((BluetoothMapUtils.MAP_FEATURE_EXTENDED_EVENT_REPORT_11_BIT 2755a60e47497f21f64e6d79420dc4c56c1907df22akschulz & mMapSupportedFeatures) != 0){ 2765a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMapEventReportVersion = BluetoothMapUtils.MAP_EVENT_REPORT_V11; 2775a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 2785a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Make sure support for all formats result in latest version returned 2795a60e47497f21f64e6d79420dc4c56c1907df22akschulz if((BluetoothMapUtils.MAP_FEATURE_EVENT_REPORT_V12_BIT 2805a60e47497f21f64e6d79420dc4c56c1907df22akschulz & mMapSupportedFeatures) != 0){ 2815a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMapEventReportVersion = BluetoothMapUtils.MAP_EVENT_REPORT_V12; 2825a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 2835a60e47497f21f64e6d79420dc4c56c1907df22akschulz 284326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(account != null) { 285326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mAuthority = Uri.parse(account.mBase_uri).getAuthority(); 286326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mMessageUri = Uri.parse(account.mBase_uri + "/" + BluetoothMapContract.TABLE_MESSAGE); 2875a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mAccount.getType() == TYPE.IM) { 2885a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactUri = Uri.parse(account.mBase_uri + "/" 2895a60e47497f21f64e6d79420dc4c56c1907df22akschulz + BluetoothMapContract.TABLE_CONVOCONTACT); 2905a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 2915a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: We need to release this again! 292326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mProviderClient = mResolver.acquireUnstableContentProviderClient(mAuthority); 293326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (mProviderClient == null) { 294326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde throw new RemoteException("Failed to acquire provider for " + mAuthority); 295326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 296326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mProviderClient.setDetectNotResponding(PROVIDER_ANR_TIMEOUT); 2975a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactList = mMasInstance.getContactList(); 2985a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mContactList == null) { 2995a60e47497f21f64e6d79420dc4c56c1907df22akschulz setContactList(new HashMap<String, BluetoothMapConvoContactElement>(), false); 3005a60e47497f21f64e6d79420dc4c56c1907df22akschulz initContactsList(); 3015a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 302326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 303326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mEnableSmsMms = enableSmsMms; 304fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie mSmsType = getSmsType(); 305326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mMnsClient = mnsClient; 3065a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Get the cached list - if any, else create */ 3075a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMsgListSms = mMasInstance.getMsgListSms(); 3085a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean doInit = false; 3095a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mEnableSmsMms) { 3105a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mMsgListSms == null) { 3115a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListSms(new HashMap<Long, Msg>(), false); 3125a60e47497f21f64e6d79420dc4c56c1907df22akschulz doInit = true; 3135a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3145a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMsgListMms = mMasInstance.getMsgListMms(); 3155a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mMsgListMms == null) { 3165a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListMms(new HashMap<Long, Msg>(), false); 3175a60e47497f21f64e6d79420dc4c56c1907df22akschulz doInit = true; 3185a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3195a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3205a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mAccount != null) { 3215a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMsgListMsg = mMasInstance.getMsgListMsg(); 3225a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mMsgListMsg == null) { 3235a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListMsg(new HashMap<Long, Msg>(), false); 3245a60e47497f21f64e6d79420dc4c56c1907df22akschulz doInit = true; 3255a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3265a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3275a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(doInit) { 3285a60e47497f21f64e6d79420dc4c56c1907df22akschulz initMsgList(); 3295a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3305a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3315a60e47497f21f64e6d79420dc4c56c1907df22akschulz 332e6564029f132077c8a4877431a95899db201e506Ashwini Munigala public int getObserverRemoteFeatureMask() { 333e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if (V) Log.v(TAG, "getObserverRemoteFeatureMask : " + mMapEventReportVersion 334e6564029f132077c8a4877431a95899db201e506Ashwini Munigala + " mMapSupportedFeatures: " + mMapSupportedFeatures); 335e6564029f132077c8a4877431a95899db201e506Ashwini Munigala return mMapSupportedFeatures; 336e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } 337e6564029f132077c8a4877431a95899db201e506Ashwini Munigala 338e6564029f132077c8a4877431a95899db201e506Ashwini Munigala public void setObserverRemoteFeatureMask(int remoteSupportedFeatures) { 339e6564029f132077c8a4877431a95899db201e506Ashwini Munigala mMapSupportedFeatures = remoteSupportedFeatures; 340e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if ((BluetoothMapUtils.MAP_FEATURE_EXTENDED_EVENT_REPORT_11_BIT 341e6564029f132077c8a4877431a95899db201e506Ashwini Munigala & mMapSupportedFeatures) != 0) { 342e6564029f132077c8a4877431a95899db201e506Ashwini Munigala mMapEventReportVersion = BluetoothMapUtils.MAP_EVENT_REPORT_V11; 343e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } 344e6564029f132077c8a4877431a95899db201e506Ashwini Munigala // Make sure support for all formats result in latest version returned 345e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if ((BluetoothMapUtils.MAP_FEATURE_EVENT_REPORT_V12_BIT 346e6564029f132077c8a4877431a95899db201e506Ashwini Munigala & mMapSupportedFeatures) != 0) { 347e6564029f132077c8a4877431a95899db201e506Ashwini Munigala mMapEventReportVersion = BluetoothMapUtils.MAP_EVENT_REPORT_V12; 348e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } 349e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if (V) Log.d(TAG, "setObserverRemoteFeatureMask : " + mMapEventReportVersion 350e6564029f132077c8a4877431a95899db201e506Ashwini Munigala + " mMapSupportedFeatures : " + mMapSupportedFeatures); 351e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } 3525a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3535a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Map<Long, Msg> getMsgListSms() { 3545a60e47497f21f64e6d79420dc4c56c1907df22akschulz return mMsgListSms; 3555a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3565a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3575a60e47497f21f64e6d79420dc4c56c1907df22akschulz private void setMsgListSms(Map<Long, Msg> msgListSms, boolean changesDetected) { 3585a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMsgListSms = msgListSms; 3595a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(changesDetected) { 3605a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.updateFolderVersionCounter(); 3615a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3625a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.setMsgListSms(msgListSms); 3635a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3645a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3655a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3665a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Map<Long, Msg> getMsgListMms() { 3675a60e47497f21f64e6d79420dc4c56c1907df22akschulz return mMsgListMms; 3685a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3695a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3705a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3715a60e47497f21f64e6d79420dc4c56c1907df22akschulz private void setMsgListMms(Map<Long, Msg> msgListMms, boolean changesDetected) { 3725a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMsgListMms = msgListMms; 3735a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(changesDetected) { 3745a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.updateFolderVersionCounter(); 3755a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3765a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.setMsgListMms(msgListMms); 377326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 378326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 3795a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3805a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Map<Long, Msg> getMsgListMsg() { 3815a60e47497f21f64e6d79420dc4c56c1907df22akschulz return mMsgListMsg; 3825a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3835a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3845a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3855a60e47497f21f64e6d79420dc4c56c1907df22akschulz private void setMsgListMsg(Map<Long, Msg> msgListMsg, boolean changesDetected) { 3865a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMsgListMsg = msgListMsg; 3875a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(changesDetected) { 3885a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.updateFolderVersionCounter(); 3895a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3905a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.setMsgListMsg(msgListMsg); 3915a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3925a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3935a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Map<String, BluetoothMapConvoContactElement> getContactList() { 3945a60e47497f21f64e6d79420dc4c56c1907df22akschulz return mContactList; 3955a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 3965a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3975a60e47497f21f64e6d79420dc4c56c1907df22akschulz 398326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /** 3995a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Currently we only have data for IM / email contacts 4005a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @param contactList 4015a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @param changesDetected that is not chat state changed nor presence state changed. 402326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde */ 4035a60e47497f21f64e6d79420dc4c56c1907df22akschulz private void setContactList(Map<String, BluetoothMapConvoContactElement> contactList, 4045a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean changesDetected) { 4055a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactList = contactList; 4065a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(changesDetected) { 4075a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.updateImEmailConvoListVersionCounter(); 4085a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4095a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.setContactList(contactList); 4105a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4115a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4125a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventNewMessage(long eventFilter) { 4135a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_NEW_MESSAGE) > 0); 4145a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4155a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4165a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventMessageDeleted(long eventFilter) { 4175a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_MESSAGE_DELETED) > 0); 4185a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4195a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4205a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventMessageShift(long eventFilter) { 4215a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_MESSAGE_SHIFT) > 0); 4225a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4235a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4245a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventSendingSuccess(long eventFilter) { 4255a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_SENDING_SUCCESS) > 0); 4265a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4275a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4285a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventSendingFailed(long eventFilter) { 4295a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_SENDING_FAILED) > 0); 4305a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4315a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4325a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventDeliverySuccess(long eventFilter) { 4335a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_DELIVERY_SUCCESS) > 0); 4345a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4355a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4365a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventDeliveryFailed(long eventFilter) { 4375a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_DELIVERY_FAILED) > 0); 4385a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4395a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4405a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventReadStatusChanged(long eventFilter) { 4415a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_READ_STATUS_CHANGED) > 0); 4425a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4435a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4445a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventConversationChanged(long eventFilter) { 4455a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_CONVERSATION_CHANGED) > 0); 4465a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4475a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4485a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventParticipantPresenceChanged(long eventFilter) { 4495a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_PARTICIPANT_PRESENCE_CHANGED) > 0); 4505a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4515a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4525a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventParticipantChatstateChanged(long eventFilter) { 4535a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_PARTICIPANT_CHATSTATE_CHANGED) > 0); 4545a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 4555a60e47497f21f64e6d79420dc4c56c1907df22akschulz 4565a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static boolean sendEventMessageRemoved(long eventFilter) { 4575a60e47497f21f64e6d79420dc4c56c1907df22akschulz return ((eventFilter & EVENT_FILTER_MESSAGE_REMOVED) > 0); 458fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 459fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 460fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private TYPE getSmsType() { 461fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie TYPE smsType = null; 4625a60e47497f21f64e6d79420dc4c56c1907df22akschulz TelephonyManager tm = (TelephonyManager) mContext.getSystemService( 4635a60e47497f21f64e6d79420dc4c56c1907df22akschulz Context.TELEPHONY_SERVICE); 464fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 4652e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta if (tm.getPhoneType() == TelephonyManager.PHONE_TYPE_CDMA) { 466fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie smsType = TYPE.SMS_CDMA; 4672e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta } else { 4682e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta smsType = TYPE.SMS_GSM; 469fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 470fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 471fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return smsType; 472fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 473fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 474b6fdf260e28b4eb6b5cdb19f53710c0470ffcad2Hemant Gupta private final ContentObserver mObserver = new ContentObserver(new Handler()) { 475fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie @Override 476fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void onChange(boolean selfChange) { 477fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie onChange(selfChange, null); 478fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 479fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 480fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie @Override 481fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void onChange(boolean selfChange, Uri uri) { 4825a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(uri == null) { 4835a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.w(TAG, "onChange() with URI == null - not handled."); 4845a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 4855a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 486725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 487725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker if (!mStorageUnlocked) { 488725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker Log.v(TAG, "Ignore events until storage is completely unlocked"); 489725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker return; 490725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 491725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 492fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (V) Log.d(TAG, "onChange on thread: " + Thread.currentThread().getId() 4935a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " Uri: " + uri.toString() + " selfchange: " + selfChange); 494fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 4955a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(uri.toString().contains(BluetoothMapContract.TABLE_CONVOCONTACT)) 4965a60e47497f21f64e6d79420dc4c56c1907df22akschulz handleContactListChanges(uri); 4975a60e47497f21f64e6d79420dc4c56c1907df22akschulz else 4985a60e47497f21f64e6d79420dc4c56c1907df22akschulz handleMsgListChanges(uri); 499fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 500fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie }; 501fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 5025a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final HashMap<Integer, String> FOLDER_SMS_MAP; 5035a60e47497f21f64e6d79420dc4c56c1907df22akschulz static { 5045a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_SMS_MAP = new HashMap<Integer, String>(); 5055a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_SMS_MAP.put(Sms.MESSAGE_TYPE_INBOX, BluetoothMapContract.FOLDER_NAME_INBOX); 5065a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_SMS_MAP.put(Sms.MESSAGE_TYPE_SENT, BluetoothMapContract.FOLDER_NAME_SENT); 5075a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_SMS_MAP.put(Sms.MESSAGE_TYPE_DRAFT, BluetoothMapContract.FOLDER_NAME_DRAFT); 5085a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_SMS_MAP.put(Sms.MESSAGE_TYPE_OUTBOX, BluetoothMapContract.FOLDER_NAME_OUTBOX); 5095a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_SMS_MAP.put(Sms.MESSAGE_TYPE_FAILED, BluetoothMapContract.FOLDER_NAME_OUTBOX); 5105a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_SMS_MAP.put(Sms.MESSAGE_TYPE_QUEUED, BluetoothMapContract.FOLDER_NAME_OUTBOX); 5115a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 512fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 5135a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static String getSmsFolderName(int type) { 5145a60e47497f21f64e6d79420dc4c56c1907df22akschulz String name = FOLDER_SMS_MAP.get(type); 5155a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(name != null) { 5165a60e47497f21f64e6d79420dc4c56c1907df22akschulz return name; 5175a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 5185a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.e(TAG, "New SMS mailbox types have been introduced, without an update in BT..."); 5195a60e47497f21f64e6d79420dc4c56c1907df22akschulz return "Unknown"; 5205a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 5215a60e47497f21f64e6d79420dc4c56c1907df22akschulz 5225a60e47497f21f64e6d79420dc4c56c1907df22akschulz 5235a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static final HashMap<Integer, String> FOLDER_MMS_MAP; 5245a60e47497f21f64e6d79420dc4c56c1907df22akschulz static { 5255a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_MMS_MAP = new HashMap<Integer, String>(); 5265a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_MMS_MAP.put(Mms.MESSAGE_BOX_INBOX, BluetoothMapContract.FOLDER_NAME_INBOX); 5275a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_MMS_MAP.put(Mms.MESSAGE_BOX_SENT, BluetoothMapContract.FOLDER_NAME_SENT); 5285a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_MMS_MAP.put(Mms.MESSAGE_BOX_DRAFTS, BluetoothMapContract.FOLDER_NAME_DRAFT); 5295a60e47497f21f64e6d79420dc4c56c1907df22akschulz FOLDER_MMS_MAP.put(Mms.MESSAGE_BOX_OUTBOX, BluetoothMapContract.FOLDER_NAME_OUTBOX); 5305a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 5315a60e47497f21f64e6d79420dc4c56c1907df22akschulz 5325a60e47497f21f64e6d79420dc4c56c1907df22akschulz private static String getMmsFolderName(int mailbox) { 5335a60e47497f21f64e6d79420dc4c56c1907df22akschulz String name = FOLDER_MMS_MAP.get(mailbox); 5345a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(name != null) { 5355a60e47497f21f64e6d79420dc4c56c1907df22akschulz return name; 5365a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 5375a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.e(TAG, "New MMS mailboxes have been introduced, without an update in BT..."); 5385a60e47497f21f64e6d79420dc4c56c1907df22akschulz return "Unknown"; 5395a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 5405a60e47497f21f64e6d79420dc4c56c1907df22akschulz 5415a60e47497f21f64e6d79420dc4c56c1907df22akschulz /** 5425a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Set the folder structure to be used for this instance. 5435a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @param folderStructure 5445a60e47497f21f64e6d79420dc4c56c1907df22akschulz */ 5455a60e47497f21f64e6d79420dc4c56c1907df22akschulz public void setFolderStructure(BluetoothMapFolderElement folderStructure) { 5465a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.mFolders = folderStructure; 5475a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 5485a60e47497f21f64e6d79420dc4c56c1907df22akschulz 5495a60e47497f21f64e6d79420dc4c56c1907df22akschulz private class ConvoContactInfo { 5505a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mConvoColConvoId = -1; 5515a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mConvoColLastActivity = -1; 5525a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mConvoColName = -1; 5535a60e47497f21f64e6d79420dc4c56c1907df22akschulz // public int mConvoColRead = -1; 5545a60e47497f21f64e6d79420dc4c56c1907df22akschulz // public int mConvoColVersionCounter = -1; 5555a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColUci = -1; 5565a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColConvoId = -1; 5575a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColName = -1; 5585a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColNickname = -1; 5595a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColBtUid = -1; 5605a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColChatState = -1; 5615a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColContactId = -1; 5625a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColLastActive = -1; 5635a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColPresenceState = -1; 5645a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColPresenceText = -1; 5655a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColPriority = -1; 5665a60e47497f21f64e6d79420dc4c56c1907df22akschulz public int mContactColLastOnline = -1; 5675a60e47497f21f64e6d79420dc4c56c1907df22akschulz 5685a60e47497f21f64e6d79420dc4c56c1907df22akschulz public void setConvoColunms(Cursor c) { 5695a60e47497f21f64e6d79420dc4c56c1907df22akschulz // mConvoColConvoId = c.getColumnIndex( 5705a60e47497f21f64e6d79420dc4c56c1907df22akschulz // BluetoothMapContract.ConversationColumns.THREAD_ID); 5715a60e47497f21f64e6d79420dc4c56c1907df22akschulz // mConvoColLastActivity = c.getColumnIndex( 5725a60e47497f21f64e6d79420dc4c56c1907df22akschulz // BluetoothMapContract.ConversationColumns.LAST_THREAD_ACTIVITY); 5735a60e47497f21f64e6d79420dc4c56c1907df22akschulz // mConvoColName = c.getColumnIndex( 5745a60e47497f21f64e6d79420dc4c56c1907df22akschulz // BluetoothMapContract.ConversationColumns.THREAD_NAME); 5755a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColConvoId = c.getColumnIndex( 5765a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.CONVO_ID); 5775a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColName = c.getColumnIndex( 5785a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.NAME); 5795a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColNickname = c.getColumnIndex( 5805a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.NICKNAME); 5815a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColBtUid = c.getColumnIndex( 5825a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.X_BT_UID); 5835a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColChatState = c.getColumnIndex( 5845a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.CHAT_STATE); 5855a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColUci = c.getColumnIndex( 5865a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.UCI); 5875a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColNickname = c.getColumnIndex( 5885a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.NICKNAME); 5895a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColLastActive = c.getColumnIndex( 5905a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.LAST_ACTIVE); 5915a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColName = c.getColumnIndex( 5925a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.NAME); 5935a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColPresenceState = c.getColumnIndex( 5945a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.PRESENCE_STATE); 5955a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColPresenceText = c.getColumnIndex( 5965a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.STATUS_TEXT); 5975a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColPriority = c.getColumnIndex( 5985a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.PRIORITY); 5995a60e47497f21f64e6d79420dc4c56c1907df22akschulz mContactColLastOnline = c.getColumnIndex( 6005a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.ConvoContactColumns.LAST_ONLINE); 6015a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6025a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 603fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 604fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private class Event { 605fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie String eventType; 606fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie long handle; 6075a60e47497f21f64e6d79420dc4c56c1907df22akschulz String folder = null; 6085a60e47497f21f64e6d79420dc4c56c1907df22akschulz String oldFolder = null; 609fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie TYPE msgType; 6105a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Extended event parameters in MAP Event version 1.1 */ 6115a60e47497f21f64e6d79420dc4c56c1907df22akschulz String datetime = null; // OBEX time "YYYYMMDDTHHMMSS" 6125a60e47497f21f64e6d79420dc4c56c1907df22akschulz String uci = null; 6135a60e47497f21f64e6d79420dc4c56c1907df22akschulz String subject = null; 6145a60e47497f21f64e6d79420dc4c56c1907df22akschulz String senderName = null; 6155a60e47497f21f64e6d79420dc4c56c1907df22akschulz String priority = null; 6165a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Event parameters in MAP Event version 1.2 */ 6175a60e47497f21f64e6d79420dc4c56c1907df22akschulz String conversationName = null; 6185a60e47497f21f64e6d79420dc4c56c1907df22akschulz long conversationID = -1; 6195a60e47497f21f64e6d79420dc4c56c1907df22akschulz int presenceState = BluetoothMapContract.PresenceState.UNKNOWN; 6205a60e47497f21f64e6d79420dc4c56c1907df22akschulz String presenceStatus = null; 6215a60e47497f21f64e6d79420dc4c56c1907df22akschulz int chatState = BluetoothMapContract.ChatState.UNKNOWN; 622fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 623326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde final static String PATH = "telecom/msg/"; 624326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 6255a60e47497f21f64e6d79420dc4c56c1907df22akschulz private void setFolderPath(String name, TYPE type) { 6265a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (name != null) { 6275a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(type == TYPE.EMAIL || type == TYPE.IM) { 6285a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.folder = name; 629326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 6305a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.folder = PATH + name; 631326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 632fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } else { 633fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.folder = null; 634fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 6355a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6365a60e47497f21f64e6d79420dc4c56c1907df22akschulz 6375a60e47497f21f64e6d79420dc4c56c1907df22akschulz public Event(String eventType, long handle, String folder, 6385a60e47497f21f64e6d79420dc4c56c1907df22akschulz String oldFolder, TYPE msgType) { 6395a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.eventType = eventType; 6405a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.handle = handle; 6415a60e47497f21f64e6d79420dc4c56c1907df22akschulz setFolderPath(folder, msgType); 642fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (oldFolder != null) { 6435a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(msgType == TYPE.EMAIL || msgType == TYPE.IM) { 644326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.oldFolder = oldFolder; 645326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 646326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.oldFolder = PATH + oldFolder; 647326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 648fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } else { 649fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.oldFolder = null; 650fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 651fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.msgType = msgType; 652fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 653fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 6545a60e47497f21f64e6d79420dc4c56c1907df22akschulz public Event(String eventType, long handle, String folder, TYPE msgType) { 6555a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.eventType = eventType; 6565a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.handle = handle; 6575a60e47497f21f64e6d79420dc4c56c1907df22akschulz setFolderPath(folder, msgType); 6585a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.msgType = msgType; 6595a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6605a60e47497f21f64e6d79420dc4c56c1907df22akschulz 6615a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* extended event type 1.1 */ 6625a60e47497f21f64e6d79420dc4c56c1907df22akschulz public Event(String eventType, long handle, String folder, TYPE msgType, 6635a60e47497f21f64e6d79420dc4c56c1907df22akschulz String datetime, String subject, String senderName, String priority) { 6645a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.eventType = eventType; 6655a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.handle = handle; 6665a60e47497f21f64e6d79420dc4c56c1907df22akschulz setFolderPath(folder, msgType); 6675a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.msgType = msgType; 6685a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.datetime = datetime; 6695a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (subject != null) { 6705a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.subject = BluetoothMapUtils.stripInvalidChars(subject); 6715a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6725a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (senderName != null) { 6735a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.senderName = BluetoothMapUtils.stripInvalidChars(senderName); 6745a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6755a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.priority = priority; 6765a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6775a60e47497f21f64e6d79420dc4c56c1907df22akschulz 6785a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* extended event type 1.2 message events */ 6795a60e47497f21f64e6d79420dc4c56c1907df22akschulz public Event(String eventType, long handle, String folder, TYPE msgType, 6805a60e47497f21f64e6d79420dc4c56c1907df22akschulz String datetime, String subject, String senderName, String priority, 6815a60e47497f21f64e6d79420dc4c56c1907df22akschulz long conversationID, String conversationName) { 6825a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.eventType = eventType; 6835a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.handle = handle; 6845a60e47497f21f64e6d79420dc4c56c1907df22akschulz setFolderPath(folder, msgType); 6855a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.msgType = msgType; 6865a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.datetime = datetime; 6875a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (subject != null) { 6885a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.subject = BluetoothMapUtils.stripInvalidChars(subject); 6895a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6905a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (senderName != null) { 6915a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.senderName = BluetoothMapUtils.stripInvalidChars(senderName); 6925a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6935a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (conversationID != 0) { 6945a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.conversationID = conversationID; 6955a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6965a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (conversationName != null) { 6975a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.conversationName = BluetoothMapUtils.stripInvalidChars(conversationName); 6985a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 6995a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.priority = priority; 7005a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7015a60e47497f21f64e6d79420dc4c56c1907df22akschulz 7025a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* extended event type 1.2 for conversation, presence or chat state changed events */ 7035a60e47497f21f64e6d79420dc4c56c1907df22akschulz public Event(String eventType, String uci, TYPE msgType, String name, String priority, 7045a60e47497f21f64e6d79420dc4c56c1907df22akschulz String lastActivity, long conversationID, String conversationName, 7055a60e47497f21f64e6d79420dc4c56c1907df22akschulz int presenceState, String presenceStatus, int chatState) { 7065a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.eventType = eventType; 7075a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.uci = uci; 7085a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.msgType = msgType; 7095a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (name != null) { 7105a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.senderName = BluetoothMapUtils.stripInvalidChars(name); 7115a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7125a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.priority = priority; 7135a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.datetime = lastActivity; 7145a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (conversationID != 0) { 7155a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.conversationID = conversationID; 7165a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7175a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (conversationName != null) { 7185a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.conversationName = BluetoothMapUtils.stripInvalidChars(conversationName); 7195a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7205a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (presenceState != BluetoothMapContract.PresenceState.UNKNOWN) { 7215a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.presenceState = presenceState; 7225a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7235a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (presenceStatus != null) { 7245a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.presenceStatus = BluetoothMapUtils.stripInvalidChars(presenceStatus); 7255a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7265a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (chatState != BluetoothMapContract.ChatState.UNKNOWN) { 7275a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.chatState = chatState; 7285a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7295a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7305a60e47497f21f64e6d79420dc4c56c1907df22akschulz 731fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public byte[] encode() throws UnsupportedEncodingException { 732fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie StringWriter sw = new StringWriter(); 733fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie XmlSerializer xmlEvtReport = Xml.newSerializer(); 7345a60e47497f21f64e6d79420dc4c56c1907df22akschulz 735fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie try { 736fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie xmlEvtReport.setOutput(sw); 7375a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.startDocument("UTF-8", true); 738326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde xmlEvtReport.text("\r\n"); 73970be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz xmlEvtReport.startTag("", "MAP-event-report"); 7405a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion == BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 7415a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "version", BluetoothMapUtils.MAP_V10_STR); 7425a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if (mMapEventReportVersion == BluetoothMapUtils.MAP_EVENT_REPORT_V11) { 7435a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "version", BluetoothMapUtils.MAP_V11_STR); 7445a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 7455a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "version", BluetoothMapUtils.MAP_V12_STR); 7465a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 747fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie xmlEvtReport.startTag("", "event"); 748fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie xmlEvtReport.attribute("", "type", eventType); 7495a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (eventType.equals(EVENT_TYPE_CONVERSATION) || 7505a60e47497f21f64e6d79420dc4c56c1907df22akschulz eventType.equals(EVENT_TYPE_PRESENCE) || 7515a60e47497f21f64e6d79420dc4c56c1907df22akschulz eventType.equals(EVENT_TYPE_CHAT_STATE)) { 7525a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "participant_uci", uci); 7535a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 7545a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "handle", 7555a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.getMapHandle(handle, msgType)); 7565a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7575a60e47497f21f64e6d79420dc4c56c1907df22akschulz 758fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (folder != null) { 759fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie xmlEvtReport.attribute("", "folder", folder); 760fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 761fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (oldFolder != null) { 762fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie xmlEvtReport.attribute("", "old_folder", oldFolder); 763fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 7642e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta /* Avoid possible NPE for "msgType" "null" value. "msgType" 7652e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta * is a implied attribute and will be set "null" for events 7662e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta * like "memory full" or "memory available" */ 7672e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta if (msgType != null) { 7682e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta xmlEvtReport.attribute("", "msg_type", msgType.name()); 7692e7dd83a6b3b4bf15e0dec6aad9ab826e6e2531bHemant Gupta } 7705a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* If MAP event report version is above 1.0 send 7715a60e47497f21f64e6d79420dc4c56c1907df22akschulz * extended event report parameters */ 7725a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (datetime != null) { 7735a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "datetime", datetime); 7745a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7755a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (subject != null) { 7765a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "subject", 7775a60e47497f21f64e6d79420dc4c56c1907df22akschulz subject.substring(0,subject.length() < 256 ? subject.length() : 256)); 7785a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7795a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (senderName != null) { 7809a18a9fc4349f90e49d036ccafc91d8b5befe973Ajay Panicker xmlEvtReport.attribute("", "sender_name", senderName); 7815a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7825a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (priority != null) { 7835a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "priority", priority); 7845a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7855a60e47497f21f64e6d79420dc4c56c1907df22akschulz 7865a60e47497f21f64e6d79420dc4c56c1907df22akschulz //} 7875a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Include conversation information from event version 1.2 */ 7885a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion > BluetoothMapUtils.MAP_EVENT_REPORT_V11 ) { 7895a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (conversationName != null) { 7905a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "conversation_name", conversationName); 7915a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7925a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (conversationID != -1) { 7935a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Convert provider conversation handle to string incl type 7945a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "conversation_id", 7955a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.getMapConvoHandle(conversationID, msgType)); 7965a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 7975a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (eventType.equals(EVENT_TYPE_PRESENCE)) { 7985a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (presenceState != 0) { 7995a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Convert provider conversation handle to string incl type 8005a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "presence_availability", 8015a60e47497f21f64e6d79420dc4c56c1907df22akschulz String.valueOf(presenceState)); 8025a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 8035a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (presenceStatus != null) { 8045a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Convert provider conversation handle to string incl type 8055a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "presence_status", 8065a60e47497f21f64e6d79420dc4c56c1907df22akschulz presenceStatus.substring( 8075a60e47497f21f64e6d79420dc4c56c1907df22akschulz 0,presenceStatus.length() < 256 ? subject.length() : 256)); 8085a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 8095a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 8105a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (eventType.equals(EVENT_TYPE_PRESENCE)) { 8115a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (chatState != 0) { 8125a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Convert provider conversation handle to string incl type 8135a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.attribute("", "chat_state", String.valueOf(chatState)); 8145a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 8155a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 8165a60e47497f21f64e6d79420dc4c56c1907df22akschulz 8175a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 8185a60e47497f21f64e6d79420dc4c56c1907df22akschulz xmlEvtReport.endTag("", "event"); 81970be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz xmlEvtReport.endTag("", "MAP-event-report"); 820fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie xmlEvtReport.endDocument(); 821fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } catch (IllegalArgumentException e) { 822326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(D) Log.w(TAG,e); 823fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } catch (IllegalStateException e) { 824326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(D) Log.w(TAG,e); 825fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } catch (IOException e) { 826326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(D) Log.w(TAG,e); 827fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 828fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 829326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (V) Log.d(TAG, sw.toString()); 830fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 831fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return sw.toString().getBytes("UTF-8"); 832fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 833fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 834fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 8355a60e47497f21f64e6d79420dc4c56c1907df22akschulz /*package*/ class Msg { 836fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie long id; 837326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int type; // Used as folder for SMS/MMS 838326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int threadId; // Used for SMS/MMS at delete 839326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long folderId = -1; // Email folder ID 840326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long oldFolderId = -1; // Used for email undelete 841326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde boolean localInitiatedSend = false; // Used for MMS to filter out events 842326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde boolean transparent = false; // Used for EMAIL to delete message sent with transparency 8435a60e47497f21f64e6d79420dc4c56c1907df22akschulz int flagRead = -1; // Message status read/unread 844326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 8455a60e47497f21f64e6d79420dc4c56c1907df22akschulz public Msg(long id, int type, int threadId, int readFlag) { 846fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.id = id; 847fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.type = type; 848326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.threadId = threadId; 8495a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.flagRead = readFlag; 850326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 8515a60e47497f21f64e6d79420dc4c56c1907df22akschulz public Msg(long id, long folderId, int readFlag) { 852326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.id = id; 853326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.folderId = folderId; 8545a60e47497f21f64e6d79420dc4c56c1907df22akschulz this.flagRead = readFlag; 855326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 856326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 857326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Eclipse generated hashCode() and equals() to make 858326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * hashMap lookup work independent of whether the obj 859326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * is used for email or SMS/MMS and whether or not the 860326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * oldFolder is set. */ 861326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde @Override 862326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde public int hashCode() { 863326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde final int prime = 31; 864326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int result = 1; 865326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde result = prime * result + (int) (id ^ (id >>> 32)); 866326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return result; 867fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 868fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 869326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde @Override 870326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde public boolean equals(Object obj) { 871326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (this == obj) 872326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return true; 873326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (obj == null) 874326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return false; 875326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (getClass() != obj.getClass()) 876326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return false; 877326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Msg other = (Msg) obj; 878326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (id != other.id) 879326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return false; 880326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return true; 881326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 882326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 883fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 8845a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Map<Long, Msg> mMsgListSms = null; 8855a60e47497f21f64e6d79420dc4c56c1907df22akschulz 8865a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Map<Long, Msg> mMsgListMms = null; 887326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 8885a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Map<Long, Msg> mMsgListMsg = null; 889326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 8905a60e47497f21f64e6d79420dc4c56c1907df22akschulz private Map<String, BluetoothMapConvoContactElement> mContactList = null; 891326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 892326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde public int setNotificationRegistration(int notificationStatus) throws RemoteException { 893326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // Forward the request to the MNS thread as a message - including the MAS instance ID. 894326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(D) Log.d(TAG,"setNotificationRegistration() enter"); 895e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if (mMnsClient == null) { 896e6564029f132077c8a4877431a95899db201e506Ashwini Munigala return ResponseCodes.OBEX_HTTP_UNAVAILABLE; 897e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } 898326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Handler mns = mMnsClient.getMessageHandler(); 899e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if (mns != null) { 900326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Message msg = mns.obtainMessage(); 901e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if (mMnsClient.isValidMnsRecord()) { 902e6564029f132077c8a4877431a95899db201e506Ashwini Munigala msg.what = BluetoothMnsObexClient.MSG_MNS_NOTIFICATION_REGISTRATION; 903e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } else { 904e6564029f132077c8a4877431a95899db201e506Ashwini Munigala //Trigger SDP Search and notificaiton registration , if SDP record not found. 905e6564029f132077c8a4877431a95899db201e506Ashwini Munigala msg.what = BluetoothMnsObexClient.MSG_MNS_SDP_SEARCH_REGISTRATION; 906e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if (mMnsClient.mMnsLstRegRqst != null && 907e6564029f132077c8a4877431a95899db201e506Ashwini Munigala (mMnsClient.mMnsLstRegRqst.isSearchInProgress())) { 908e6564029f132077c8a4877431a95899db201e506Ashwini Munigala /* 1. Disallow next Notification ON Request : 909e6564029f132077c8a4877431a95899db201e506Ashwini Munigala * - Respond "Service Unavailable" as SDP Search and last notification 910e6564029f132077c8a4877431a95899db201e506Ashwini Munigala * registration ON request is already InProgress. 911e6564029f132077c8a4877431a95899db201e506Ashwini Munigala * - Next notification ON Request will be allowed ONLY after search 912e6564029f132077c8a4877431a95899db201e506Ashwini Munigala * and connect for last saved request [Replied with OK ] is processed. 913e6564029f132077c8a4877431a95899db201e506Ashwini Munigala */ 914e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if (notificationStatus == BluetoothMapAppParams.NOTIFICATION_STATUS_YES) { 915e6564029f132077c8a4877431a95899db201e506Ashwini Munigala return ResponseCodes.OBEX_HTTP_UNAVAILABLE; 916e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } else { 917e6564029f132077c8a4877431a95899db201e506Ashwini Munigala /* 2. Allow next Notification OFF Request: 918e6564029f132077c8a4877431a95899db201e506Ashwini Munigala * - Keep the SDP search still in progress. 919e6564029f132077c8a4877431a95899db201e506Ashwini Munigala * - Disconnect and Deregister the contentObserver. 920e6564029f132077c8a4877431a95899db201e506Ashwini Munigala */ 921e6564029f132077c8a4877431a95899db201e506Ashwini Munigala msg.what = BluetoothMnsObexClient.MSG_MNS_NOTIFICATION_REGISTRATION; 922e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } 923e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } 924e6564029f132077c8a4877431a95899db201e506Ashwini Munigala } 925326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msg.arg1 = mMasId; 926326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msg.arg2 = notificationStatus; 927326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mns.sendMessageDelayed(msg, 10); // Send message without forcing a context switch 928326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Some devices - e.g. PTS needs to get the unregister confirm before we actually 929326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * disconnect the MNS. */ 930e6564029f132077c8a4877431a95899db201e506Ashwini Munigala if(D) Log.d(TAG,"setNotificationRegistration() send : " + msg.what + " to MNS "); 931e6564029f132077c8a4877431a95899db201e506Ashwini Munigala return ResponseCodes.OBEX_HTTP_OK; 932326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 933326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // This should not happen except at shutdown. 934326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(D) Log.d(TAG,"setNotificationRegistration() Unable to send registration request"); 935326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return ResponseCodes.OBEX_HTTP_UNAVAILABLE; 936326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 937326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 938fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 9395a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean eventMaskContainsContacts(long mask) { 9405a60e47497f21f64e6d79420dc4c56c1907df22akschulz return sendEventParticipantPresenceChanged(mask); 9415a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 9425a60e47497f21f64e6d79420dc4c56c1907df22akschulz 9435a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean eventMaskContainsCovo(long mask) { 9445a60e47497f21f64e6d79420dc4c56c1907df22akschulz return (sendEventConversationChanged(mask) 9455a60e47497f21f64e6d79420dc4c56c1907df22akschulz || sendEventParticipantChatstateChanged(mask)); 9465a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 9475a60e47497f21f64e6d79420dc4c56c1907df22akschulz 9485a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Overwrite the existing notification filter. Will register/deregister observers for 9495a60e47497f21f64e6d79420dc4c56c1907df22akschulz * the Contacts and Conversation table as needed. We keep the message observer 9505a60e47497f21f64e6d79420dc4c56c1907df22akschulz * at all times. */ 9515a60e47497f21f64e6d79420dc4c56c1907df22akschulz /*package*/ synchronized void setNotificationFilter(long newFilter) { 9525a60e47497f21f64e6d79420dc4c56c1907df22akschulz long oldFilter = mEventFilter; 9535a60e47497f21f64e6d79420dc4c56c1907df22akschulz mEventFilter = newFilter; 9545a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Contacts */ 9555a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!eventMaskContainsContacts(oldFilter) && 9565a60e47497f21f64e6d79420dc4c56c1907df22akschulz eventMaskContainsContacts(newFilter)) { 9575a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: 9585a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Enable the observer 9595a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Reset the contacts list 9605a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 9615a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Conversations */ 9625a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!eventMaskContainsCovo(oldFilter) && 9635a60e47497f21f64e6d79420dc4c56c1907df22akschulz eventMaskContainsCovo(newFilter)) { 9645a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: 9655a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Enable the observer 9665a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Reset the conversations list 9675a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 9685a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 9695a60e47497f21f64e6d79420dc4c56c1907df22akschulz 970326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde public void registerObserver() throws RemoteException{ 971fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (V) Log.d(TAG, "registerObserver"); 972326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 973326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (mObserverRegistered) 974326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return; 975326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 976326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(mAccount != null) { 977326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 978326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mProviderClient = mResolver.acquireUnstableContentProviderClient(mAuthority); 979326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (mProviderClient == null) { 980326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde throw new RemoteException("Failed to acquire provider for " + mAuthority); 981326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 982326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mProviderClient.setDetectNotResponding(PROVIDER_ANR_TIMEOUT); 983326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 9845a60e47497f21f64e6d79420dc4c56c1907df22akschulz // If there is a change in the database before we init the lists we will be sending 9855a60e47497f21f64e6d79420dc4c56c1907df22akschulz // loads of events - hence init before register. 9865a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mAccount.getType() == TYPE.IM) { 9875a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Further add contact list tracking 9885a60e47497f21f64e6d79420dc4c56c1907df22akschulz initContactsList(); 9895a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 9905a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 9915a60e47497f21f64e6d79420dc4c56c1907df22akschulz // If there is a change in the database before we init the lists we will be sending 9925a60e47497f21f64e6d79420dc4c56c1907df22akschulz // loads of events - hence init before register. 9935a60e47497f21f64e6d79420dc4c56c1907df22akschulz initMsgList(); 9945a60e47497f21f64e6d79420dc4c56c1907df22akschulz 9955a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Use MmsSms Uri since the Sms Uri is not notified on deletes */ 9965a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mEnableSmsMms){ 9975a60e47497f21f64e6d79420dc4c56c1907df22akschulz //this is sms/mms 9985a60e47497f21f64e6d79420dc4c56c1907df22akschulz mResolver.registerContentObserver(MmsSms.CONTENT_URI, false, mObserver); 9995a60e47497f21f64e6d79420dc4c56c1907df22akschulz mObserverRegistered = true; 10005a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10015a60e47497f21f64e6d79420dc4c56c1907df22akschulz 10025a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mAccount != null) { 1003326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* For URI's without account ID */ 10045a60e47497f21f64e6d79420dc4c56c1907df22akschulz Uri uri = Uri.parse(mAccount.mBase_uri_no_account + "/" 10055a60e47497f21f64e6d79420dc4c56c1907df22akschulz + BluetoothMapContract.TABLE_MESSAGE); 1006326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(D) Log.d(TAG, "Registering observer for: " + uri); 1007326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mResolver.registerContentObserver(uri, true, mObserver); 1008326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 1009326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* For URI's with account ID - is handled the same way as without ID, but is 1010326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * only triggered for MAS instances with matching account ID. */ 1011326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = Uri.parse(mAccount.mBase_uri + "/" + BluetoothMapContract.TABLE_MESSAGE); 1012326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(D) Log.d(TAG, "Registering observer for: " + uri); 1013326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mResolver.registerContentObserver(uri, true, mObserver); 10145a60e47497f21f64e6d79420dc4c56c1907df22akschulz 10155a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mAccount.getType() == TYPE.IM) { 10165a60e47497f21f64e6d79420dc4c56c1907df22akschulz 10175a60e47497f21f64e6d79420dc4c56c1907df22akschulz uri = Uri.parse(mAccount.mBase_uri_no_account + "/" 10185a60e47497f21f64e6d79420dc4c56c1907df22akschulz + BluetoothMapContract.TABLE_CONVOCONTACT); 10195a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D) Log.d(TAG, "Registering observer for: " + uri); 10205a60e47497f21f64e6d79420dc4c56c1907df22akschulz mResolver.registerContentObserver(uri, true, mObserver); 10215a60e47497f21f64e6d79420dc4c56c1907df22akschulz 10225a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* For URI's with account ID - is handled the same way as without ID, but is 10235a60e47497f21f64e6d79420dc4c56c1907df22akschulz * only triggered for MAS instances with matching account ID. */ 10245a60e47497f21f64e6d79420dc4c56c1907df22akschulz uri = Uri.parse(mAccount.mBase_uri + "/" + BluetoothMapContract.TABLE_CONVOCONTACT); 10255a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D) Log.d(TAG, "Registering observer for: " + uri); 10265a60e47497f21f64e6d79420dc4c56c1907df22akschulz mResolver.registerContentObserver(uri, true, mObserver); 10275a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10285a60e47497f21f64e6d79420dc4c56c1907df22akschulz 1029326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mObserverRegistered = true; 1030326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1031fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1032fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 10335a60e47497f21f64e6d79420dc4c56c1907df22akschulz public void unregisterObserver() { 10345a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (V) Log.d(TAG, "unregisterObserver"); 10355a60e47497f21f64e6d79420dc4c56c1907df22akschulz mResolver.unregisterContentObserver(mObserver); 10365a60e47497f21f64e6d79420dc4c56c1907df22akschulz mObserverRegistered = false; 10375a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mProviderClient != null){ 10385a60e47497f21f64e6d79420dc4c56c1907df22akschulz mProviderClient.release(); 10395a60e47497f21f64e6d79420dc4c56c1907df22akschulz mProviderClient = null; 10405a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10415a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10425a60e47497f21f64e6d79420dc4c56c1907df22akschulz 10435a60e47497f21f64e6d79420dc4c56c1907df22akschulz /** 10445a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Per design it is only possible to call the refreshXxxx functions sequentially, hence it 10455a60e47497f21f64e6d79420dc4c56c1907df22akschulz * is safe to modify mTransmitEvents without synchronization. 10465a60e47497f21f64e6d79420dc4c56c1907df22akschulz */ 10475a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* package */ void refreshFolderVersionCounter() { 10485a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mObserverRegistered) { 10495a60e47497f21f64e6d79420dc4c56c1907df22akschulz // As we have observers, we already keep the counter up-to-date. 10505a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 10515a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10525a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* We need to perform the same functionality, as when we receive a notification change, 10535a60e47497f21f64e6d79420dc4c56c1907df22akschulz hence we: 10545a60e47497f21f64e6d79420dc4c56c1907df22akschulz - disable the event transmission 10555a60e47497f21f64e6d79420dc4c56c1907df22akschulz - triggers the code for updates 10565a60e47497f21f64e6d79420dc4c56c1907df22akschulz - enable the event transmission */ 10575a60e47497f21f64e6d79420dc4c56c1907df22akschulz mTransmitEvents = false; 10585a60e47497f21f64e6d79420dc4c56c1907df22akschulz try { 10595a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mEnableSmsMms) { 10605a60e47497f21f64e6d79420dc4c56c1907df22akschulz handleMsgListChangesSms(); 10615a60e47497f21f64e6d79420dc4c56c1907df22akschulz handleMsgListChangesMms(); 10625a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10635a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mAccount != null) { 10645a60e47497f21f64e6d79420dc4c56c1907df22akschulz try { 10655a60e47497f21f64e6d79420dc4c56c1907df22akschulz handleMsgListChangesMsg(mMessageUri); 10665a60e47497f21f64e6d79420dc4c56c1907df22akschulz } catch (RemoteException e) { 10675a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.e(TAG, "Unable to update FolderVersionCounter. - Not fatal, but can cause" + 10685a60e47497f21f64e6d79420dc4c56c1907df22akschulz " undesirable user experience!", e); 10695a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10705a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10715a60e47497f21f64e6d79420dc4c56c1907df22akschulz } finally { 10725a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Ensure we always enable events again 10735a60e47497f21f64e6d79420dc4c56c1907df22akschulz mTransmitEvents = true; 10745a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10755a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10765a60e47497f21f64e6d79420dc4c56c1907df22akschulz 10775a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* package */ void refreshConvoListVersionCounter() { 10785a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mObserverRegistered) { 10795a60e47497f21f64e6d79420dc4c56c1907df22akschulz // As we have observers, we already keep the counter up-to-date. 10805a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 10815a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10825a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* We need to perform the same functionality, as when we receive a notification change, 10835a60e47497f21f64e6d79420dc4c56c1907df22akschulz hence we: 10845a60e47497f21f64e6d79420dc4c56c1907df22akschulz - disable event transmission 10855a60e47497f21f64e6d79420dc4c56c1907df22akschulz - triggers the code for updates 10865a60e47497f21f64e6d79420dc4c56c1907df22akschulz - enable event transmission */ 10875a60e47497f21f64e6d79420dc4c56c1907df22akschulz mTransmitEvents = false; 10885a60e47497f21f64e6d79420dc4c56c1907df22akschulz try { 10895a60e47497f21f64e6d79420dc4c56c1907df22akschulz if((mAccount != null) && (mContactUri != null)) { 10905a60e47497f21f64e6d79420dc4c56c1907df22akschulz handleContactListChanges(mContactUri); 10915a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 10925a60e47497f21f64e6d79420dc4c56c1907df22akschulz } finally { 10935a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Ensure we always enable events again 10945a60e47497f21f64e6d79420dc4c56c1907df22akschulz mTransmitEvents = true; 1095326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1096fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1097fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1098fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void sendEvent(Event evt) { 10995a60e47497f21f64e6d79420dc4c56c1907df22akschulz 11005a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mTransmitEvents == false) { 11015a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(V) Log.v(TAG, "mTransmitEvents == false - don't send event."); 11025a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11035a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11045a60e47497f21f64e6d79420dc4c56c1907df22akschulz 11055a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "sendEvent: " + evt.eventType + " " + evt.handle + " " + evt.folder + " " 11065a60e47497f21f64e6d79420dc4c56c1907df22akschulz + evt.oldFolder + " " + evt.msgType.name() + " " + evt.datetime + " " 11075a60e47497f21f64e6d79420dc4c56c1907df22akschulz + evt.subject + " " + evt.senderName + " " + evt.priority ); 1108fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 11090e7e149687b0b5e340991b20c9d8e5232e8d3e39Hemant Gupta if (mMnsClient == null || mMnsClient.isConnected() == false) { 11100e7e149687b0b5e340991b20c9d8e5232e8d3e39Hemant Gupta Log.d(TAG, "sendEvent: No MNS client registered or connected- don't send event"); 1111fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return; 1112fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1113fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 11145a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Enable use of the cache for checking the filter */ 11155a60e47497f21f64e6d79420dc4c56c1907df22akschulz long eventFilter = mEventFilter; 11165a60e47497f21f64e6d79420dc4c56c1907df22akschulz 11175a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* This should have been a switch on the string, but it is not allowed in Java 1.6 */ 11185a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* WARNING: Here we do pointer compare for the string to speed up things, that is. 11195a60e47497f21f64e6d79420dc4c56c1907df22akschulz * HENCE: always use the EVENT_TYPE_"defines" */ 11205a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(evt.eventType == EVENT_TYPE_NEW) { 11215a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventNewMessage(eventFilter)) { 11225a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11235a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11245a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11255a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_DELETE) { 11265a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventMessageDeleted(eventFilter)) { 11275a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11285a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11295a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11305a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_REMOVED) { 11315a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventMessageRemoved(eventFilter)) { 11325a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11335a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11345a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11355a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_SHIFT) { 11365a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventMessageShift(eventFilter)) { 11375a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11385a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11395a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11405a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_DELEVERY_SUCCESS) { 11415a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventDeliverySuccess(eventFilter)) { 11425a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11435a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11445a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11455a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_SENDING_SUCCESS) { 11465a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventSendingSuccess(eventFilter)) { 11475a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11485a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11495a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11505a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_SENDING_FAILURE) { 11515a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventSendingFailed(eventFilter)) { 11525a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11535a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11545a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11555a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_DELIVERY_FAILURE) { 11565a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventDeliveryFailed(eventFilter)) { 11575a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11585a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11595a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11605a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_READ_STATUS) { 11615a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventReadStatusChanged(eventFilter)) { 11625a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11635a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11645a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11655a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_CONVERSATION) { 11665a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventConversationChanged(eventFilter)) { 11675a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11685a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11695a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11705a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_PRESENCE) { 11715a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventParticipantPresenceChanged(eventFilter)) { 11725a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11735a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11745a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11755a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(evt.eventType == EVENT_TYPE_CHAT_STATE) { 11765a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!sendEventParticipantChatstateChanged(eventFilter)) { 11775a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG, "Skip sending event of type: " + evt.eventType); 11785a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 11795a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11805a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 11815a60e47497f21f64e6d79420dc4c56c1907df22akschulz 1182fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie try { 1183fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie mMnsClient.sendEvent(evt.encode(), mMasId); 1184fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } catch (UnsupportedEncodingException ex) { 1185fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /* do nothing */ 11865a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (D) Log.e(TAG, "Exception - should not happen: ",ex); 1187fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1188fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1189fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1190326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private void initMsgList() throws RemoteException { 1191fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (V) Log.d(TAG, "initMsgList"); 119289de413eba69b0c5e128a82e0ad179cec9152578Ajay Panicker UserManager manager = UserManager.get(mContext); 1193725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker if (manager == null || !manager.isUserUnlocked()) return; 1194fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 119589de413eba69b0c5e128a82e0ad179cec9152578Ajay Panicker if (mEnableSmsMms) { 1196326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde HashMap<Long, Msg> msgListSms = new HashMap<Long, Msg>(); 1197fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1198326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Cursor c = mResolver.query(Sms.CONTENT_URI, 11995a60e47497f21f64e6d79420dc4c56c1907df22akschulz SMS_PROJECTION_SHORT, null, null, null); 120028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 12015a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 12025a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 12035a60e47497f21f64e6d79420dc4c56c1907df22akschulz long id = c.getLong(c.getColumnIndex(Sms._ID)); 12045a60e47497f21f64e6d79420dc4c56c1907df22akschulz int type = c.getInt(c.getColumnIndex(Sms.TYPE)); 12055a60e47497f21f64e6d79420dc4c56c1907df22akschulz int threadId = c.getInt(c.getColumnIndex(Sms.THREAD_ID)); 12065a60e47497f21f64e6d79420dc4c56c1907df22akschulz int read = c.getInt(c.getColumnIndex(Sms.READ)); 1207fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 12085a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = new Msg(id, type, threadId, read); 12095a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgListSms.put(id, msg); 12105a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 121128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 121228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 12135a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 1214326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 121528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz 12165a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListSms()) { 12175a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMsgListSms().clear(); 12185a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListSms(msgListSms, true); // Set initial folder version counter 1219326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1220fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1221326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde HashMap<Long, Msg> msgListMms = new HashMap<Long, Msg>(); 1222fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1223326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde c = mResolver.query(Mms.CONTENT_URI, MMS_PROJECTION_SHORT, null, null, null); 122428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 12255a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 12265a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 12275a60e47497f21f64e6d79420dc4c56c1907df22akschulz long id = c.getLong(c.getColumnIndex(Mms._ID)); 12285a60e47497f21f64e6d79420dc4c56c1907df22akschulz int type = c.getInt(c.getColumnIndex(Mms.MESSAGE_BOX)); 12295a60e47497f21f64e6d79420dc4c56c1907df22akschulz int threadId = c.getInt(c.getColumnIndex(Mms.THREAD_ID)); 12305a60e47497f21f64e6d79420dc4c56c1907df22akschulz int read = c.getInt(c.getColumnIndex(Mms.READ)); 1231fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 12325a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = new Msg(id, type, threadId, read); 12335a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgListMms.put(id, msg); 12345a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 123528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 123628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 12375a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 1238326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 123928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz 12405a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMms()) { 12415a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMsgListMms().clear(); 12425a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListMms(msgListMms, true); // Set initial folder version counter 1243326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1244fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1245fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1246326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(mAccount != null) { 12475a60e47497f21f64e6d79420dc4c56c1907df22akschulz HashMap<Long, Msg> msgList = new HashMap<Long, Msg>(); 1248326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri uri = mMessageUri; 12495a60e47497f21f64e6d79420dc4c56c1907df22akschulz Cursor c = mProviderClient.query(uri, MSG_PROJECTION_SHORT, null, null, null); 1250326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 125128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 12525a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 12535a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 12545a60e47497f21f64e6d79420dc4c56c1907df22akschulz long id = c.getLong(c.getColumnIndex(MessageColumns._ID)); 12555a60e47497f21f64e6d79420dc4c56c1907df22akschulz long folderId = c.getInt(c.getColumnIndex( 12565a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FOLDER_ID)); 12575a60e47497f21f64e6d79420dc4c56c1907df22akschulz int readFlag = c.getInt(c.getColumnIndex( 12585a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FLAG_READ)); 12595a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = new Msg(id, folderId, readFlag); 12605a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgList.put(id, msg); 12615a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 126228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 126328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 12645a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 12655a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 12665a60e47497f21f64e6d79420dc4c56c1907df22akschulz 12675a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMsg()) { 12685a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMsgListMsg().clear(); 12695a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListMsg(msgList, true); 1270326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 12715a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 12725a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 127328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz 12745a60e47497f21f64e6d79420dc4c56c1907df22akschulz private void initContactsList() throws RemoteException { 12755a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (V) Log.d(TAG, "initContactsList"); 12765a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(mContactUri == null) { 12775a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (D) Log.d(TAG, "initContactsList() no mContactUri - nothing to init"); 12785a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 12795a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 12805a60e47497f21f64e6d79420dc4c56c1907df22akschulz Uri uri = mContactUri; 12815a60e47497f21f64e6d79420dc4c56c1907df22akschulz Cursor c = mProviderClient.query(uri, 12825a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.BT_CONTACT_CHATSTATE_PRESENCE_PROJECTION, 12835a60e47497f21f64e6d79420dc4c56c1907df22akschulz null, null, null); 12845a60e47497f21f64e6d79420dc4c56c1907df22akschulz Map<String, BluetoothMapConvoContactElement> contactList = 12855a60e47497f21f64e6d79420dc4c56c1907df22akschulz new HashMap<String, BluetoothMapConvoContactElement>(); 12865a60e47497f21f64e6d79420dc4c56c1907df22akschulz try { 12875a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 12885a60e47497f21f64e6d79420dc4c56c1907df22akschulz ConvoContactInfo cInfo = new ConvoContactInfo(); 12895a60e47497f21f64e6d79420dc4c56c1907df22akschulz cInfo.setConvoColunms(c); 12905a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 12915a60e47497f21f64e6d79420dc4c56c1907df22akschulz long convoId = c.getLong(cInfo.mContactColConvoId); 12925a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (convoId == 0) 12935a60e47497f21f64e6d79420dc4c56c1907df22akschulz continue; 12945a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (V) BluetoothMapUtils.printCursor(c); 12955a60e47497f21f64e6d79420dc4c56c1907df22akschulz String uci = c.getString(cInfo.mContactColUci); 12965a60e47497f21f64e6d79420dc4c56c1907df22akschulz String name = c.getString(cInfo.mContactColName); 12975a60e47497f21f64e6d79420dc4c56c1907df22akschulz String displayName = c.getString(cInfo.mContactColNickname); 12985a60e47497f21f64e6d79420dc4c56c1907df22akschulz String presenceStatus = c.getString(cInfo.mContactColPresenceText); 12995a60e47497f21f64e6d79420dc4c56c1907df22akschulz int presenceState = c.getInt(cInfo.mContactColPresenceState); 13005a60e47497f21f64e6d79420dc4c56c1907df22akschulz long lastActivity = c.getLong(cInfo.mContactColLastActive); 13015a60e47497f21f64e6d79420dc4c56c1907df22akschulz int chatState = c.getInt(cInfo.mContactColChatState); 13025a60e47497f21f64e6d79420dc4c56c1907df22akschulz int priority = c.getInt(cInfo.mContactColPriority); 13035a60e47497f21f64e6d79420dc4c56c1907df22akschulz String btUid = c.getString(cInfo.mContactColBtUid); 13045a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapConvoContactElement contact = 13055a60e47497f21f64e6d79420dc4c56c1907df22akschulz new BluetoothMapConvoContactElement(uci, name, displayName, 13065a60e47497f21f64e6d79420dc4c56c1907df22akschulz presenceStatus, presenceState, lastActivity, chatState, 13075a60e47497f21f64e6d79420dc4c56c1907df22akschulz priority, btUid); 13085a60e47497f21f64e6d79420dc4c56c1907df22akschulz contactList.put(uci, contact); 13095a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 1310326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 13115a60e47497f21f64e6d79420dc4c56c1907df22akschulz } finally { 13125a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 13135a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 13145a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getContactList()) { 13155a60e47497f21f64e6d79420dc4c56c1907df22akschulz getContactList().clear(); 13165a60e47497f21f64e6d79420dc4c56c1907df22akschulz setContactList(contactList, true); 1317326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1318fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1319fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1320fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void handleMsgListChangesSms() { 1321fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (V) Log.d(TAG, "handleMsgListChangesSms"); 1322fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1323fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie HashMap<Long, Msg> msgListSms = new HashMap<Long, Msg>(); 13245a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean listChanged = false; 1325fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 13265a60e47497f21f64e6d79420dc4c56c1907df22akschulz Cursor c; 13275a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListSms()) { 1328ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta if (mMapEventReportVersion == BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 1329ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta c = mResolver.query(Sms.CONTENT_URI, 1330ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta SMS_PROJECTION_SHORT, null, null, null); 1331ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta } else { 1332ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta c = mResolver.query(Sms.CONTENT_URI, 1333ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta SMS_PROJECTION_SHORT_EXT, null, null, null); 1334ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta } 133528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 13365a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 13375a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 13385a60e47497f21f64e6d79420dc4c56c1907df22akschulz long id = c.getLong(c.getColumnIndex(Sms._ID)); 13395a60e47497f21f64e6d79420dc4c56c1907df22akschulz int type = c.getInt(c.getColumnIndex(Sms.TYPE)); 13405a60e47497f21f64e6d79420dc4c56c1907df22akschulz int threadId = c.getInt(c.getColumnIndex(Sms.THREAD_ID)); 13415a60e47497f21f64e6d79420dc4c56c1907df22akschulz int read = c.getInt(c.getColumnIndex(Sms.READ)); 13425a60e47497f21f64e6d79420dc4c56c1907df22akschulz 13435a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListSms().remove(id); 13445a60e47497f21f64e6d79420dc4c56c1907df22akschulz 13455a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* We must filter out any actions made by the MCE, hence do not send e.g. 13465a60e47497f21f64e6d79420dc4c56c1907df22akschulz * a message deleted and/or MessageShift for messages deleted by the MCE. */ 13475a60e47497f21f64e6d79420dc4c56c1907df22akschulz 13485a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (msg == null) { 13495a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* New message */ 13505a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg = new Msg(id, type, threadId, read); 13515a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgListSms.put(id, msg); 13525a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 13535a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt; 13545a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mTransmitEvents == true && // extract contact details only if needed 13555a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMapEventReportVersion > 13565a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 13575a60e47497f21f64e6d79420dc4c56c1907df22akschulz String date = BluetoothMapUtils.getDateTimeString( 13585a60e47497f21f64e6d79420dc4c56c1907df22akschulz c.getLong(c.getColumnIndex(Sms.DATE))); 13595a60e47497f21f64e6d79420dc4c56c1907df22akschulz String subject = c.getString(c.getColumnIndex(Sms.BODY)); 13605a60e47497f21f64e6d79420dc4c56c1907df22akschulz String name = ""; 13615a60e47497f21f64e6d79420dc4c56c1907df22akschulz String phone = ""; 13625a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (type == 1) { //inbox 13635a60e47497f21f64e6d79420dc4c56c1907df22akschulz phone = c.getString(c.getColumnIndex(Sms.ADDRESS)); 13645a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (phone != null && !phone.isEmpty()) { 13655a60e47497f21f64e6d79420dc4c56c1907df22akschulz name = BluetoothMapContent.getContactNameFromPhone(phone, 13665a60e47497f21f64e6d79420dc4c56c1907df22akschulz mResolver); 13675a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(name == null || name.isEmpty()){ 13685a60e47497f21f64e6d79420dc4c56c1907df22akschulz name = phone; 13695a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 13705a60e47497f21f64e6d79420dc4c56c1907df22akschulz }else{ 13715a60e47497f21f64e6d79420dc4c56c1907df22akschulz name = phone; 13725a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 13735a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 13745a60e47497f21f64e6d79420dc4c56c1907df22akschulz TelephonyManager tm = 13755a60e47497f21f64e6d79420dc4c56c1907df22akschulz (TelephonyManager)mContext.getSystemService( 13765a60e47497f21f64e6d79420dc4c56c1907df22akschulz Context.TELEPHONY_SERVICE); 13775a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (tm != null) { 13785a60e47497f21f64e6d79420dc4c56c1907df22akschulz phone = tm.getLine1Number(); 13795a60e47497f21f64e6d79420dc4c56c1907df22akschulz name = tm.getLine1AlphaTag(); 13805a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(name == null || name.isEmpty()){ 13815a60e47497f21f64e6d79420dc4c56c1907df22akschulz name = phone; 13825a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 13835a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 13845a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 13855a60e47497f21f64e6d79420dc4c56c1907df22akschulz String priority = "no";// no priority for sms 13865a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Incoming message from the network */ 13875a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion == 13885a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.MAP_EVENT_REPORT_V11) { 13895a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, getSmsFolderName(type), 13905a60e47497f21f64e6d79420dc4c56c1907df22akschulz mSmsType, date, subject, name, priority); 13915a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 13925a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, getSmsFolderName(type), 13935a60e47497f21f64e6d79420dc4c56c1907df22akschulz mSmsType, date, subject, name, priority, 13945a60e47497f21f64e6d79420dc4c56c1907df22akschulz (long)threadId, null); 13955a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 13965a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 13975a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Incoming message from the network */ 13985a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, getSmsFolderName(type), 13995a60e47497f21f64e6d79420dc4c56c1907df22akschulz null, mSmsType); 14005a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 14015a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 14025a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 14035a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Existing message */ 14045a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (type != msg.type) { 14055a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 14065a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.d(TAG, "new type: " + type + " old type: " + msg.type); 14075a60e47497f21f64e6d79420dc4c56c1907df22akschulz String oldFolder = getSmsFolderName(msg.type); 14085a60e47497f21f64e6d79420dc4c56c1907df22akschulz String newFolder = getSmsFolderName(type); 14095a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Filter out the intermediate outbox steps 14105a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(!oldFolder.equalsIgnoreCase(newFolder)) { 14115a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_SHIFT, id, 14125a60e47497f21f64e6d79420dc4c56c1907df22akschulz getSmsFolderName(type), oldFolder, mSmsType); 14135a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 14145a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 14155a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.type = type; 14165a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(threadId != msg.threadId) { 14175a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 14185a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.d(TAG, "Message delete change: type: " + type 14195a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " old type: " + msg.type 14205a60e47497f21f64e6d79420dc4c56c1907df22akschulz + "\n threadId: " + threadId 14215a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " old threadId: " + msg.threadId); 14225a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(threadId == DELETED_THREAD_ID) { // Message deleted 14235a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: 14245a60e47497f21f64e6d79420dc4c56c1907df22akschulz // We shall only use the folder attribute, but can't remember 14255a60e47497f21f64e6d79420dc4c56c1907df22akschulz // wether to set it to "deleted" or the name of the folder 14265a60e47497f21f64e6d79420dc4c56c1907df22akschulz // from which the message have been deleted. 1427cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta // "old_folder" used only for MessageShift event 14285a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_DELETE, id, 1429cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta getSmsFolderName(msg.type), null, mSmsType); 14305a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 14315a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.threadId = threadId; 14325a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { // Undelete 14335a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_SHIFT, id, 14345a60e47497f21f64e6d79420dc4c56c1907df22akschulz getSmsFolderName(msg.type), 14355a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.FOLDER_NAME_DELETED, mSmsType); 14365a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 14375a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.threadId = threadId; 14385a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 1439326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 14405a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(read != msg.flagRead) { 14415a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 14425a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.flagRead = read; 14435a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion > 14445a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 14455a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_READ_STATUS, id, 14465a60e47497f21f64e6d79420dc4c56c1907df22akschulz getSmsFolderName(msg.type), mSmsType); 14475a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 14485a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 1449326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 14505a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgListSms.put(id, msg); 1451fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 14525a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 145328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 145428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 14555a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 1456fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1457fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 14585a60e47497f21f64e6d79420dc4c56c1907df22akschulz for (Msg msg : getMsgListSms().values()) { 1459cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta // "old_folder" used only for MessageShift event 1460326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Event evt = new Event(EVENT_TYPE_DELETE, msg.id, 1461cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta getSmsFolderName(msg.type), null, mSmsType); 1462fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie sendEvent(evt); 14635a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 1464fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1465fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 14665a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListSms(msgListSms, listChanged); 1467fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1468fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1469fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1470fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void handleMsgListChangesMms() { 1471fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (V) Log.d(TAG, "handleMsgListChangesMms"); 1472fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 1473fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie HashMap<Long, Msg> msgListMms = new HashMap<Long, Msg>(); 14745a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean listChanged = false; 14755a60e47497f21f64e6d79420dc4c56c1907df22akschulz Cursor c; 14765a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMms()) { 1477ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta if (mMapEventReportVersion == BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 1478ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta c = mResolver.query(Mms.CONTENT_URI, 1479ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta MMS_PROJECTION_SHORT, null, null, null); 1480ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta } else { 1481ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta c = mResolver.query(Mms.CONTENT_URI, 1482ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta MMS_PROJECTION_SHORT_EXT, null, null, null); 1483ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta } 1484ea6b2c977e8a621f160f37ef0d36db91d5c29834Hemant Gupta 14855a60e47497f21f64e6d79420dc4c56c1907df22akschulz try{ 14865a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 14875a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 14885a60e47497f21f64e6d79420dc4c56c1907df22akschulz long id = c.getLong(c.getColumnIndex(Mms._ID)); 14895a60e47497f21f64e6d79420dc4c56c1907df22akschulz int type = c.getInt(c.getColumnIndex(Mms.MESSAGE_BOX)); 14905a60e47497f21f64e6d79420dc4c56c1907df22akschulz int mtype = c.getInt(c.getColumnIndex(Mms.MESSAGE_TYPE)); 14915a60e47497f21f64e6d79420dc4c56c1907df22akschulz int threadId = c.getInt(c.getColumnIndex(Mms.THREAD_ID)); 14925a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: Go through code to see if we have an issue with mismatch in types 14935a60e47497f21f64e6d79420dc4c56c1907df22akschulz // for threadId. Seems to be a long in DB?? 14945a60e47497f21f64e6d79420dc4c56c1907df22akschulz int read = c.getInt(c.getColumnIndex(Mms.READ)); 14955a60e47497f21f64e6d79420dc4c56c1907df22akschulz 14965a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListMms().remove(id); 14975a60e47497f21f64e6d79420dc4c56c1907df22akschulz 14985a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* We must filter out any actions made by the MCE, hence do not send 14995a60e47497f21f64e6d79420dc4c56c1907df22akschulz * e.g. a message deleted and/or MessageShift for messages deleted by the 15005a60e47497f21f64e6d79420dc4c56c1907df22akschulz * MCE.*/ 15015a60e47497f21f64e6d79420dc4c56c1907df22akschulz 15025a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (msg == null) { 15035a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* New message - only notify on retrieve conf */ 15045a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 15055a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (getMmsFolderName(type).equalsIgnoreCase( 15065a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.FOLDER_NAME_INBOX) && 15075a60e47497f21f64e6d79420dc4c56c1907df22akschulz mtype != MESSAGE_TYPE_RETRIEVE_CONF) { 1508fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie continue; 15095a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 15105a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg = new Msg(id, type, threadId, read); 15115a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgListMms.put(id, msg); 1512326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Event evt; 15135a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mTransmitEvents == true && // extract contact details only if needed 15145a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMapEventReportVersion != 15155a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 15165a60e47497f21f64e6d79420dc4c56c1907df22akschulz String date = BluetoothMapUtils.getDateTimeString( 15175a60e47497f21f64e6d79420dc4c56c1907df22akschulz c.getLong(c.getColumnIndex(Mms.DATE))); 15185a60e47497f21f64e6d79420dc4c56c1907df22akschulz String subject = c.getString(c.getColumnIndex(Mms.SUBJECT)); 15195a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (subject == null || subject.length() == 0) { 15205a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Get subject from mms text body parts - if any exists */ 15215a60e47497f21f64e6d79420dc4c56c1907df22akschulz subject = BluetoothMapContent.getTextPartsMms(mResolver, id); 15225a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 15235a60e47497f21f64e6d79420dc4c56c1907df22akschulz int tmpPri = c.getInt(c.getColumnIndex(Mms.PRIORITY)); 15245a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.d(TAG, "TEMP handleMsgListChangesMms, " + 15255a60e47497f21f64e6d79420dc4c56c1907df22akschulz "newMessage 'read' state: " + read + 15265a60e47497f21f64e6d79420dc4c56c1907df22akschulz "priority: " + tmpPri); 15275a60e47497f21f64e6d79420dc4c56c1907df22akschulz 15285a60e47497f21f64e6d79420dc4c56c1907df22akschulz String address = BluetoothMapContent.getAddressMms( 15295a60e47497f21f64e6d79420dc4c56c1907df22akschulz mResolver,id,BluetoothMapContent.MMS_FROM); 15305a60e47497f21f64e6d79420dc4c56c1907df22akschulz String priority = "no"; 15315a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(tmpPri == PduHeaders.PRIORITY_HIGH) 15325a60e47497f21f64e6d79420dc4c56c1907df22akschulz priority = "yes"; 15335a60e47497f21f64e6d79420dc4c56c1907df22akschulz 15345a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Incoming message from the network */ 15355a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion == 15365a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.MAP_EVENT_REPORT_V11) { 15375a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, getMmsFolderName(type), 15385a60e47497f21f64e6d79420dc4c56c1907df22akschulz TYPE.MMS, date, subject, address, priority); 15395a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 15405a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, getMmsFolderName(type), 15415a60e47497f21f64e6d79420dc4c56c1907df22akschulz TYPE.MMS, date, subject, address, priority, 15425a60e47497f21f64e6d79420dc4c56c1907df22akschulz (long)threadId, null); 15435a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 15445a60e47497f21f64e6d79420dc4c56c1907df22akschulz 15455a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 15465a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Incoming message from the network */ 15475a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, getMmsFolderName(type), 15485a60e47497f21f64e6d79420dc4c56c1907df22akschulz null, TYPE.MMS); 1549326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 15505a60e47497f21f64e6d79420dc4c56c1907df22akschulz 15515a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 15525a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 15535a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Existing message */ 15545a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (type != msg.type) { 15555a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.d(TAG, "new type: " + type + " old type: " + msg.type); 15565a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt; 15575a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 15585a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(msg.localInitiatedSend == false) { 15595a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Only send events about local initiated changes 15605a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_SHIFT, id, getMmsFolderName(type), 15615a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMmsFolderName(msg.type), TYPE.MMS); 15625a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 15635a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 15645a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.type = type; 15655a60e47497f21f64e6d79420dc4c56c1907df22akschulz 15665a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (getMmsFolderName(type).equalsIgnoreCase( 15675a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.FOLDER_NAME_SENT) 15685a60e47497f21f64e6d79420dc4c56c1907df22akschulz && msg.localInitiatedSend == true) { 15695a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Stop tracking changes for this message 15705a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.localInitiatedSend = false; 15715a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_SENDING_SUCCESS, id, 15725a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMmsFolderName(type), null, TYPE.MMS); 15735a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 15745a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 15755a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(threadId != msg.threadId) { 15765a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.d(TAG, "Message delete change: type: " + type + " old type: " 15775a60e47497f21f64e6d79420dc4c56c1907df22akschulz + msg.type 15785a60e47497f21f64e6d79420dc4c56c1907df22akschulz + "\n threadId: " + threadId + " old threadId: " 15795a60e47497f21f64e6d79420dc4c56c1907df22akschulz + msg.threadId); 15805a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 15815a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(threadId == DELETED_THREAD_ID) { // Message deleted 1582cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta // "old_folder" used only for MessageShift event 15835a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_DELETE, id, 1584cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta getMmsFolderName(msg.type), null, TYPE.MMS); 15855a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 15865a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.threadId = threadId; 15875a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { // Undelete 15885a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_SHIFT, id, 15895a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMmsFolderName(msg.type), 15905a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.FOLDER_NAME_DELETED, TYPE.MMS); 15915a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 15925a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.threadId = threadId; 15935a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 1594fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 15955a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(read != msg.flagRead) { 15965a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 15975a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.flagRead = read; 15985a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion > 15995a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 16005a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_READ_STATUS, id, 16015a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMmsFolderName(msg.type), TYPE.MMS); 16025a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 16035a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 1604326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 16055a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgListMms.put(id, msg); 1606fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 16075a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 16085a60e47497f21f64e6d79420dc4c56c1907df22akschulz 160928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 161028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 16115a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 1612fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 16135a60e47497f21f64e6d79420dc4c56c1907df22akschulz for (Msg msg : getMsgListMms().values()) { 1614cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta // "old_folder" used only for MessageShift event 1615326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Event evt = new Event(EVENT_TYPE_DELETE, msg.id, 1616cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta getMmsFolderName(msg.type), null, TYPE.MMS); 1617fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie sendEvent(evt); 16185a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 1619fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 16205a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListMms(msgListMms, listChanged); 1621fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1622fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 1623fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 16245a60e47497f21f64e6d79420dc4c56c1907df22akschulz private void handleMsgListChangesMsg(Uri uri) throws RemoteException{ 16255a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (V) Log.v(TAG, "handleMsgListChangesMsg uri: " + uri.toString()); 1626326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 1627326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // TODO: Change observer to handle accountId and message ID if present 1628326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 16295a60e47497f21f64e6d79420dc4c56c1907df22akschulz HashMap<Long, Msg> msgList = new HashMap<Long, Msg>(); 16305a60e47497f21f64e6d79420dc4c56c1907df22akschulz Cursor c; 16315a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean listChanged = false; 16325a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion == BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 16335a60e47497f21f64e6d79420dc4c56c1907df22akschulz c = mProviderClient.query(mMessageUri, MSG_PROJECTION_SHORT, null, null, null); 16345a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if (mMapEventReportVersion == BluetoothMapUtils.MAP_EVENT_REPORT_V11) { 16355a60e47497f21f64e6d79420dc4c56c1907df22akschulz c = mProviderClient.query(mMessageUri, MSG_PROJECTION_SHORT_EXT, null, null, null); 16365a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 16375a60e47497f21f64e6d79420dc4c56c1907df22akschulz c = mProviderClient.query(mMessageUri, MSG_PROJECTION_SHORT_EXT2, null, null, null); 16385a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 16395a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMsg()) { 164028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 16415a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 16425a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 16435a60e47497f21f64e6d79420dc4c56c1907df22akschulz long id = c.getLong(c.getColumnIndex( 16445a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns._ID)); 16455a60e47497f21f64e6d79420dc4c56c1907df22akschulz int folderId = c.getInt(c.getColumnIndex( 16465a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FOLDER_ID)); 16475a60e47497f21f64e6d79420dc4c56c1907df22akschulz int readFlag = c.getInt(c.getColumnIndex( 16485a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FLAG_READ)); 16495a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListMsg().remove(id); 16505a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapFolderElement folderElement = mFolders.getFolderById(folderId); 16515a60e47497f21f64e6d79420dc4c56c1907df22akschulz String newFolder; 16525a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(folderElement != null) { 16535a60e47497f21f64e6d79420dc4c56c1907df22akschulz newFolder = folderElement.getFullPath(); 16545a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 16555a60e47497f21f64e6d79420dc4c56c1907df22akschulz // This can happen if a new folder is created while connected 16565a60e47497f21f64e6d79420dc4c56c1907df22akschulz newFolder = "unknown"; 16575a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 16585a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* We must filter out any actions made by the MCE, hence do not send e.g. 16595a60e47497f21f64e6d79420dc4c56c1907df22akschulz * a message deleted and/or MessageShift for messages deleted by the MCE. */ 16605a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (msg == null) { 16615a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 16625a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* New message - created with message unread */ 16635a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg = new Msg(id, folderId, 0, readFlag); 16645a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgList.put(id, msg); 16655a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt; 16665a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Incoming message from the network */ 16675a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion != BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 16685a60e47497f21f64e6d79420dc4c56c1907df22akschulz String date = BluetoothMapUtils.getDateTimeString( 16695a60e47497f21f64e6d79420dc4c56c1907df22akschulz c.getLong(c.getColumnIndex( 16705a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.DATE))); 16715a60e47497f21f64e6d79420dc4c56c1907df22akschulz String subject = c.getString(c.getColumnIndex( 16725a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.SUBJECT)); 16735a60e47497f21f64e6d79420dc4c56c1907df22akschulz String address = c.getString(c.getColumnIndex( 16745a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FROM_LIST)); 16755a60e47497f21f64e6d79420dc4c56c1907df22akschulz String priority = "no"; 16765a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(c.getInt(c.getColumnIndex( 16775a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.FLAG_HIGH_PRIORITY)) 16785a60e47497f21f64e6d79420dc4c56c1907df22akschulz == 1) 16795a60e47497f21f64e6d79420dc4c56c1907df22akschulz priority = "yes"; 16805a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion == 16815a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.MAP_EVENT_REPORT_V11) { 16825a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, newFolder, 16835a60e47497f21f64e6d79420dc4c56c1907df22akschulz mAccount.getType(), date, subject, address, priority); 16845a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 16855a60e47497f21f64e6d79420dc4c56c1907df22akschulz long thread_id = c.getLong(c.getColumnIndex( 16865a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.THREAD_ID)); 16875a60e47497f21f64e6d79420dc4c56c1907df22akschulz String thread_name = c.getString(c.getColumnIndex( 16885a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.MessageColumns.THREAD_NAME)); 16895a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, newFolder, 16905a60e47497f21f64e6d79420dc4c56c1907df22akschulz mAccount.getType(), date, subject, address, priority, 16915a60e47497f21f64e6d79420dc4c56c1907df22akschulz thread_id, thread_name); 16925a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 1693326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 16945a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event(EVENT_TYPE_NEW, id, newFolder, null, TYPE.EMAIL); 1695326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 16965a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 16975a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 16985a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Existing message */ 16995a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (folderId != msg.folderId && msg.folderId != -1) { 17005a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (D) Log.d(TAG, "new folderId: " + folderId + " old folderId: " 17015a60e47497f21f64e6d79420dc4c56c1907df22akschulz + msg.folderId); 17025a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapFolderElement oldFolderElement = 17035a60e47497f21f64e6d79420dc4c56c1907df22akschulz mFolders.getFolderById(msg.folderId); 17045a60e47497f21f64e6d79420dc4c56c1907df22akschulz String oldFolder; 17055a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 17065a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(oldFolderElement != null) { 17075a60e47497f21f64e6d79420dc4c56c1907df22akschulz oldFolder = oldFolderElement.getFullPath(); 1708326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 17095a60e47497f21f64e6d79420dc4c56c1907df22akschulz // This can happen if a new folder is created while connected 17105a60e47497f21f64e6d79420dc4c56c1907df22akschulz oldFolder = "unknown"; 17115a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 17125a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapFolderElement deletedFolder = 17135a60e47497f21f64e6d79420dc4c56c1907df22akschulz mFolders.getFolderByName( 17145a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.FOLDER_NAME_DELETED); 17155a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapFolderElement sentFolder = 17165a60e47497f21f64e6d79420dc4c56c1907df22akschulz mFolders.getFolderByName( 17175a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.FOLDER_NAME_SENT); 17185a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* 17195a60e47497f21f64e6d79420dc4c56c1907df22akschulz * If the folder is now 'deleted', send a deleted-event in stead of 17205a60e47497f21f64e6d79420dc4c56c1907df22akschulz * a shift or if message is sent initiated by MAP Client, then send 17215a60e47497f21f64e6d79420dc4c56c1907df22akschulz * sending-success otherwise send folderShift 17225a60e47497f21f64e6d79420dc4c56c1907df22akschulz */ 17235a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(deletedFolder != null && deletedFolder.getFolderId() 17245a60e47497f21f64e6d79420dc4c56c1907df22akschulz == folderId) { 1725cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta // "old_folder" used only for MessageShift event 1726cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta Event evt = new Event(EVENT_TYPE_DELETE, msg.id, oldFolder, 1727cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta null, mAccount.getType()); 17285a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 17295a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if(sentFolder != null 17305a60e47497f21f64e6d79420dc4c56c1907df22akschulz && sentFolder.getFolderId() == folderId 17315a60e47497f21f64e6d79420dc4c56c1907df22akschulz && msg.localInitiatedSend == true) { 17325a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(msg.transparent) { 17335a60e47497f21f64e6d79420dc4c56c1907df22akschulz mResolver.delete( 17345a60e47497f21f64e6d79420dc4c56c1907df22akschulz ContentUris.withAppendedId(mMessageUri, id), 17355a60e47497f21f64e6d79420dc4c56c1907df22akschulz null, null); 17365a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 17375a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.localInitiatedSend = false; 17385a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_SENDING_SUCCESS, msg.id, 17395a60e47497f21f64e6d79420dc4c56c1907df22akschulz oldFolder, null, mAccount.getType()); 17405a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 17415a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 17425a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 17435a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (!oldFolder.equalsIgnoreCase("root")) { 17445a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_SHIFT, id, newFolder, 17455a60e47497f21f64e6d79420dc4c56c1907df22akschulz oldFolder, mAccount.getType()); 17465a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 17475a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 17485a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 17495a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.folderId = folderId; 17505a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 17515a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(readFlag != msg.flagRead) { 17525a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 17535a60e47497f21f64e6d79420dc4c56c1907df22akschulz 17545a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion > 17555a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils.MAP_EVENT_REPORT_V10) { 17565a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_READ_STATUS, id, newFolder, 17575a60e47497f21f64e6d79420dc4c56c1907df22akschulz mAccount.getType()); 1758326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde sendEvent(evt); 17595a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.flagRead = readFlag; 1760326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1761326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 17625a60e47497f21f64e6d79420dc4c56c1907df22akschulz 17635a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgList.put(id, msg); 1764326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 17655a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 176628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 176728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 17685a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 1769326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1770326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // For all messages no longer in the database send a delete notification 17715a60e47497f21f64e6d79420dc4c56c1907df22akschulz for (Msg msg : getMsgListMsg().values()) { 17725a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapFolderElement oldFolderElement = mFolders.getFolderById(msg.folderId); 1773326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String oldFolder; 17745a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 1775326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(oldFolderElement != null) { 1776326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde oldFolder = oldFolderElement.getFullPath(); 1777326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 1778326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde oldFolder = "unknown"; 1779326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 17805a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Some e-mail clients delete the message after sending, and creates a 17815a60e47497f21f64e6d79420dc4c56c1907df22akschulz * new message in sent. We cannot track the message anymore, hence send both a 17825a60e47497f21f64e6d79420dc4c56c1907df22akschulz * send success and delete message. 1783326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde */ 1784326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(msg.localInitiatedSend == true) { 1785326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msg.localInitiatedSend = false; 1786326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // If message is send with transparency don't set folder as message is deleted 1787326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (msg.transparent) 1788326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde oldFolder = null; 17895a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_SENDING_SUCCESS, msg.id, oldFolder, null, 17905a60e47497f21f64e6d79420dc4c56c1907df22akschulz mAccount.getType()); 1791326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde sendEvent(evt); 1792326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1793326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* As this message deleted is only send on a real delete - don't set folder. 1794326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * - only send delete event if message is not sent with transparency 1795326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde */ 1796326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (!msg.transparent) { 1797326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 1798cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta // "old_folder" used only for MessageShift event 1799cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta Event evt = new Event(EVENT_TYPE_DELETE, msg.id, oldFolder, 1800cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta null, mAccount.getType()); 1801326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde sendEvent(evt); 1802326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1803326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 18045a60e47497f21f64e6d79420dc4c56c1907df22akschulz setMsgListMsg(msgList, listChanged); 1805326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1806326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1807326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 1808326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private void handleMsgListChanges(Uri uri) { 1809326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(uri.getAuthority().equals(mAuthority)) { 1810326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde try { 18115a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D) Log.d(TAG, "handleMsgListChanges: account type = " 18125a60e47497f21f64e6d79420dc4c56c1907df22akschulz + mAccount.getType().toString()); 18135a60e47497f21f64e6d79420dc4c56c1907df22akschulz handleMsgListChangesMsg(uri); 18145a60e47497f21f64e6d79420dc4c56c1907df22akschulz } catch(RemoteException e) { 1815326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mMasInstance.restartObexServerSession(); 18165a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.w(TAG, "Problems contacting the ContentProvider in mas Instance " 18175a60e47497f21f64e6d79420dc4c56c1907df22akschulz + mMasId + " restaring ObexServerSession"); 1818326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1819326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 18205a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 18215a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: check to see if there could be problem with IM and SMS in one instance 18225a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mEnableSmsMms) { 1823326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde handleMsgListChangesSms(); 1824326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde handleMsgListChangesMms(); 1825326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1826326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 1827326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 18285a60e47497f21f64e6d79420dc4c56c1907df22akschulz private void handleContactListChanges(Uri uri) { 18295a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (uri.getAuthority().equals(mAuthority)) { 18305a60e47497f21f64e6d79420dc4c56c1907df22akschulz try { 18315a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (V) Log.v(TAG,"handleContactListChanges uri: " + uri.toString()); 18325a60e47497f21f64e6d79420dc4c56c1907df22akschulz Cursor c = null; 18335a60e47497f21f64e6d79420dc4c56c1907df22akschulz boolean listChanged = false; 18345a60e47497f21f64e6d79420dc4c56c1907df22akschulz try { 18355a60e47497f21f64e6d79420dc4c56c1907df22akschulz ConvoContactInfo cInfo = new ConvoContactInfo(); 18365a60e47497f21f64e6d79420dc4c56c1907df22akschulz 18375a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion != BluetoothMapUtils.MAP_EVENT_REPORT_V10 18385a60e47497f21f64e6d79420dc4c56c1907df22akschulz && mMapEventReportVersion != BluetoothMapUtils.MAP_EVENT_REPORT_V11) { 18395a60e47497f21f64e6d79420dc4c56c1907df22akschulz c = mProviderClient 18405a60e47497f21f64e6d79420dc4c56c1907df22akschulz .query(mContactUri, 18415a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract. 18425a60e47497f21f64e6d79420dc4c56c1907df22akschulz BT_CONTACT_CHATSTATE_PRESENCE_PROJECTION, 18435a60e47497f21f64e6d79420dc4c56c1907df22akschulz null, null, null); 18445a60e47497f21f64e6d79420dc4c56c1907df22akschulz cInfo.setConvoColunms(c); 18455a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 18465a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (V) Log.v(TAG,"handleContactListChanges MAP version does not" + 18475a60e47497f21f64e6d79420dc4c56c1907df22akschulz "support convocontact notifications"); 18485a60e47497f21f64e6d79420dc4c56c1907df22akschulz return; 18495a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 18505a60e47497f21f64e6d79420dc4c56c1907df22akschulz 18515a60e47497f21f64e6d79420dc4c56c1907df22akschulz HashMap<String, BluetoothMapConvoContactElement> contactList = 18525a60e47497f21f64e6d79420dc4c56c1907df22akschulz new HashMap<String, 18535a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapConvoContactElement>(getContactList().size()); 18545a60e47497f21f64e6d79420dc4c56c1907df22akschulz 18555a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized (getContactList()) { 18565a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 18575a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 18585a60e47497f21f64e6d79420dc4c56c1907df22akschulz String uci = c.getString(cInfo.mContactColUci); 18595a60e47497f21f64e6d79420dc4c56c1907df22akschulz long convoId = c.getLong(cInfo.mContactColConvoId); 18605a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (convoId == 0) 18615a60e47497f21f64e6d79420dc4c56c1907df22akschulz continue; 18625a60e47497f21f64e6d79420dc4c56c1907df22akschulz 18635a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (V) BluetoothMapUtils.printCursor(c); 18645a60e47497f21f64e6d79420dc4c56c1907df22akschulz 18655a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapConvoContactElement contact = 18665a60e47497f21f64e6d79420dc4c56c1907df22akschulz getContactList().remove(uci); 18675a60e47497f21f64e6d79420dc4c56c1907df22akschulz 18685a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* 18695a60e47497f21f64e6d79420dc4c56c1907df22akschulz * We must filter out any actions made by the 18705a60e47497f21f64e6d79420dc4c56c1907df22akschulz * MCE, hence do not send e.g. a message deleted 18715a60e47497f21f64e6d79420dc4c56c1907df22akschulz * and/or MessageShift for messages deleted by 18725a60e47497f21f64e6d79420dc4c56c1907df22akschulz * the MCE. 18735a60e47497f21f64e6d79420dc4c56c1907df22akschulz */ 18745a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (contact == null) { 18755a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 18765a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* 18775a60e47497f21f64e6d79420dc4c56c1907df22akschulz * New contact - added to conversation and 18785a60e47497f21f64e6d79420dc4c56c1907df22akschulz * tracked here 18795a60e47497f21f64e6d79420dc4c56c1907df22akschulz */ 18805a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (mMapEventReportVersion 18815a60e47497f21f64e6d79420dc4c56c1907df22akschulz != BluetoothMapUtils.MAP_EVENT_REPORT_V10 18825a60e47497f21f64e6d79420dc4c56c1907df22akschulz && mMapEventReportVersion 18835a60e47497f21f64e6d79420dc4c56c1907df22akschulz != BluetoothMapUtils.MAP_EVENT_REPORT_V11) { 18845a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt; 18855a60e47497f21f64e6d79420dc4c56c1907df22akschulz String name = c 18865a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getString(cInfo.mContactColName); 18875a60e47497f21f64e6d79420dc4c56c1907df22akschulz String displayName = c 18885a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getString(cInfo.mContactColNickname); 18895a60e47497f21f64e6d79420dc4c56c1907df22akschulz String presenceStatus = c 18905a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getString(cInfo.mContactColPresenceText); 18915a60e47497f21f64e6d79420dc4c56c1907df22akschulz int presenceState = c 18925a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getInt(cInfo.mContactColPresenceState); 18935a60e47497f21f64e6d79420dc4c56c1907df22akschulz long lastActivity = c 18945a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getLong(cInfo.mContactColLastActive); 18955a60e47497f21f64e6d79420dc4c56c1907df22akschulz int chatState = c 18965a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getInt(cInfo.mContactColChatState); 18975a60e47497f21f64e6d79420dc4c56c1907df22akschulz int priority = c 18985a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getInt(cInfo.mContactColPriority); 18995a60e47497f21f64e6d79420dc4c56c1907df22akschulz String btUid = c 19005a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getString(cInfo.mContactColBtUid); 19015a60e47497f21f64e6d79420dc4c56c1907df22akschulz 19025a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Get Conversation information for 19035a60e47497f21f64e6d79420dc4c56c1907df22akschulz // event 19045a60e47497f21f64e6d79420dc4c56c1907df22akschulz// Uri convoUri = Uri 19055a60e47497f21f64e6d79420dc4c56c1907df22akschulz// .parse(mAccount.mBase_uri 19065a60e47497f21f64e6d79420dc4c56c1907df22akschulz// + "/" 19075a60e47497f21f64e6d79420dc4c56c1907df22akschulz// + BluetoothMapContract.TABLE_CONVERSATION); 19085a60e47497f21f64e6d79420dc4c56c1907df22akschulz// String whereClause = "contacts._id = " 19095a60e47497f21f64e6d79420dc4c56c1907df22akschulz// + convoId; 19105a60e47497f21f64e6d79420dc4c56c1907df22akschulz// Cursor cConvo = mProviderClient 19115a60e47497f21f64e6d79420dc4c56c1907df22akschulz// .query(convoUri, 19125a60e47497f21f64e6d79420dc4c56c1907df22akschulz// BluetoothMapContract.BT_CONVERSATION_PROJECTION, 19135a60e47497f21f64e6d79420dc4c56c1907df22akschulz// whereClause, null, null); 19145a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: will move out of the loop when merged with CB's 19155a60e47497f21f64e6d79420dc4c56c1907df22akschulz // changes make sure to look up col index out side loop 19165a60e47497f21f64e6d79420dc4c56c1907df22akschulz String convoName = null; 19175a60e47497f21f64e6d79420dc4c56c1907df22akschulz// if (cConvo != null 19185a60e47497f21f64e6d79420dc4c56c1907df22akschulz// && cConvo.moveToFirst()) { 19195a60e47497f21f64e6d79420dc4c56c1907df22akschulz// convoName = cConvo 19205a60e47497f21f64e6d79420dc4c56c1907df22akschulz// .getString(cConvo 19215a60e47497f21f64e6d79420dc4c56c1907df22akschulz// .getColumnIndex(BluetoothMapContract.ConvoContactColumns.NAME)); 19225a60e47497f21f64e6d79420dc4c56c1907df22akschulz// } 19235a60e47497f21f64e6d79420dc4c56c1907df22akschulz 19245a60e47497f21f64e6d79420dc4c56c1907df22akschulz contact = new BluetoothMapConvoContactElement( 19255a60e47497f21f64e6d79420dc4c56c1907df22akschulz uci, name, displayName, 19265a60e47497f21f64e6d79420dc4c56c1907df22akschulz presenceStatus, presenceState, 19275a60e47497f21f64e6d79420dc4c56c1907df22akschulz lastActivity, chatState, 19285a60e47497f21f64e6d79420dc4c56c1907df22akschulz priority, btUid); 19295a60e47497f21f64e6d79420dc4c56c1907df22akschulz 19305a60e47497f21f64e6d79420dc4c56c1907df22akschulz contactList.put(uci, contact); 19315a60e47497f21f64e6d79420dc4c56c1907df22akschulz 19325a60e47497f21f64e6d79420dc4c56c1907df22akschulz evt = new Event( 19335a60e47497f21f64e6d79420dc4c56c1907df22akschulz EVENT_TYPE_CONVERSATION, 19345a60e47497f21f64e6d79420dc4c56c1907df22akschulz uci, 19355a60e47497f21f64e6d79420dc4c56c1907df22akschulz mAccount.getType(), 19365a60e47497f21f64e6d79420dc4c56c1907df22akschulz name, 19375a60e47497f21f64e6d79420dc4c56c1907df22akschulz String.valueOf(priority), 19385a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils 19395a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getDateTimeString(lastActivity), 19405a60e47497f21f64e6d79420dc4c56c1907df22akschulz convoId, convoName, 19415a60e47497f21f64e6d79420dc4c56c1907df22akschulz presenceState, presenceStatus, 19425a60e47497f21f64e6d79420dc4c56c1907df22akschulz chatState); 19435a60e47497f21f64e6d79420dc4c56c1907df22akschulz 19445a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 19455a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 19465a60e47497f21f64e6d79420dc4c56c1907df22akschulz 19475a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 19485a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Not new - compare updated content 19495a60e47497f21f64e6d79420dc4c56c1907df22akschulz// Uri convoUri = Uri 19505a60e47497f21f64e6d79420dc4c56c1907df22akschulz// .parse(mAccount.mBase_uri 19515a60e47497f21f64e6d79420dc4c56c1907df22akschulz// + "/" 19525a60e47497f21f64e6d79420dc4c56c1907df22akschulz// + BluetoothMapContract.TABLE_CONVERSATION); 19535a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: Should be changed to own provider interface name 19545a60e47497f21f64e6d79420dc4c56c1907df22akschulz// String whereClause = "contacts._id = " 19555a60e47497f21f64e6d79420dc4c56c1907df22akschulz// + convoId; 19565a60e47497f21f64e6d79420dc4c56c1907df22akschulz// Cursor cConvo = mProviderClient 19575a60e47497f21f64e6d79420dc4c56c1907df22akschulz// .query(convoUri, 19585a60e47497f21f64e6d79420dc4c56c1907df22akschulz// BluetoothMapContract.BT_CONVERSATION_PROJECTION, 19595a60e47497f21f64e6d79420dc4c56c1907df22akschulz// whereClause, null, null); 19605a60e47497f21f64e6d79420dc4c56c1907df22akschulz// // TODO: will move out of the loop when merged with CB's 19615a60e47497f21f64e6d79420dc4c56c1907df22akschulz// // changes make sure to look up col index out side loop 19625a60e47497f21f64e6d79420dc4c56c1907df22akschulz String convoName = null; 19635a60e47497f21f64e6d79420dc4c56c1907df22akschulz// if (cConvo != null && cConvo.moveToFirst()) { 19645a60e47497f21f64e6d79420dc4c56c1907df22akschulz// convoName = cConvo 19655a60e47497f21f64e6d79420dc4c56c1907df22akschulz// .getString(cConvo 19665a60e47497f21f64e6d79420dc4c56c1907df22akschulz// .getColumnIndex(BluetoothMapContract.ConvoContactColumns.NAME)); 19675a60e47497f21f64e6d79420dc4c56c1907df22akschulz// } 19685a60e47497f21f64e6d79420dc4c56c1907df22akschulz 19695a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Check if presence is updated 19705a60e47497f21f64e6d79420dc4c56c1907df22akschulz int presenceState = c.getInt(cInfo.mContactColPresenceState); 19715a60e47497f21f64e6d79420dc4c56c1907df22akschulz String presenceStatus = c.getString( 19725a60e47497f21f64e6d79420dc4c56c1907df22akschulz cInfo.mContactColPresenceText); 19735a60e47497f21f64e6d79420dc4c56c1907df22akschulz String currentPresenceStatus = contact 19745a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getPresenceStatus(); 19755a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (contact.getPresenceAvailability() != presenceState 19765a60e47497f21f64e6d79420dc4c56c1907df22akschulz || currentPresenceStatus != presenceStatus) { 19775a60e47497f21f64e6d79420dc4c56c1907df22akschulz long lastOnline = c 19785a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getLong(cInfo.mContactColLastOnline); 19795a60e47497f21f64e6d79420dc4c56c1907df22akschulz contact.setPresenceAvailability(presenceState); 19805a60e47497f21f64e6d79420dc4c56c1907df22akschulz contact.setLastActivity(lastOnline); 19815a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (currentPresenceStatus != null 19825a60e47497f21f64e6d79420dc4c56c1907df22akschulz && !currentPresenceStatus 19835a60e47497f21f64e6d79420dc4c56c1907df22akschulz .equals(presenceStatus)) { 19845a60e47497f21f64e6d79420dc4c56c1907df22akschulz contact.setPresenceStatus(presenceStatus); 19855a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 19865a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event( 19875a60e47497f21f64e6d79420dc4c56c1907df22akschulz EVENT_TYPE_PRESENCE, 19885a60e47497f21f64e6d79420dc4c56c1907df22akschulz uci, 19895a60e47497f21f64e6d79420dc4c56c1907df22akschulz mAccount.getType(), 19905a60e47497f21f64e6d79420dc4c56c1907df22akschulz contact.getName(), 19915a60e47497f21f64e6d79420dc4c56c1907df22akschulz String.valueOf(contact 19925a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getPriority()), 19935a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils 19945a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getDateTimeString(lastOnline), 19955a60e47497f21f64e6d79420dc4c56c1907df22akschulz convoId, convoName, 19965a60e47497f21f64e6d79420dc4c56c1907df22akschulz presenceState, presenceStatus, 19975a60e47497f21f64e6d79420dc4c56c1907df22akschulz 0); 19985a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 19995a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20005a60e47497f21f64e6d79420dc4c56c1907df22akschulz 20015a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Check if chat state is updated 20025a60e47497f21f64e6d79420dc4c56c1907df22akschulz int chatState = c.getInt(cInfo.mContactColChatState); 20035a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (contact.getChatState() != chatState) { 20045a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Get DB timestamp 20055a60e47497f21f64e6d79420dc4c56c1907df22akschulz long lastActivity = c.getLong(cInfo.mContactColLastActive); 20065a60e47497f21f64e6d79420dc4c56c1907df22akschulz contact.setLastActivity(lastActivity); 20075a60e47497f21f64e6d79420dc4c56c1907df22akschulz contact.setChatState(chatState); 20085a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event( 20095a60e47497f21f64e6d79420dc4c56c1907df22akschulz EVENT_TYPE_CHAT_STATE, 20105a60e47497f21f64e6d79420dc4c56c1907df22akschulz uci, 20115a60e47497f21f64e6d79420dc4c56c1907df22akschulz mAccount.getType(), 20125a60e47497f21f64e6d79420dc4c56c1907df22akschulz contact.getName(), 20135a60e47497f21f64e6d79420dc4c56c1907df22akschulz String.valueOf(contact 20145a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getPriority()), 20155a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapUtils 20165a60e47497f21f64e6d79420dc4c56c1907df22akschulz .getDateTimeString(lastActivity), 20175a60e47497f21f64e6d79420dc4c56c1907df22akschulz convoId, convoName, 0, null, 20185a60e47497f21f64e6d79420dc4c56c1907df22akschulz chatState); 20195a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendEvent(evt); 20205a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20215a60e47497f21f64e6d79420dc4c56c1907df22akschulz contactList.put(uci, contact); 20225a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20235a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 20245a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20255a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(getContactList().size() > 0) { 20265a60e47497f21f64e6d79420dc4c56c1907df22akschulz // one or more contacts were deleted, hence the conversation listing 20275a60e47497f21f64e6d79420dc4c56c1907df22akschulz // version counter should change. 20285a60e47497f21f64e6d79420dc4c56c1907df22akschulz listChanged = true; 20295a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20305a60e47497f21f64e6d79420dc4c56c1907df22akschulz setContactList(contactList, listChanged); 20315a60e47497f21f64e6d79420dc4c56c1907df22akschulz } // end synchronized 20325a60e47497f21f64e6d79420dc4c56c1907df22akschulz } finally { 20335a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 20345a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20355a60e47497f21f64e6d79420dc4c56c1907df22akschulz } catch (RemoteException e) { 20365a60e47497f21f64e6d79420dc4c56c1907df22akschulz mMasInstance.restartObexServerSession(); 20375a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.w(TAG, 20385a60e47497f21f64e6d79420dc4c56c1907df22akschulz "Problems contacting the ContentProvider in mas Instance " 20395a60e47497f21f64e6d79420dc4c56c1907df22akschulz + mMasId + " restaring ObexServerSession"); 20405a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20415a60e47497f21f64e6d79420dc4c56c1907df22akschulz 20425a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20435a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: conversation contact updates if IM and SMS(MMS in one instance 20445a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 20455a60e47497f21f64e6d79420dc4c56c1907df22akschulz 2046326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private boolean setEmailMessageStatusDelete(BluetoothMapFolderElement mCurrentFolder, 2047326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String uriStr, long handle, int status) { 2048326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde boolean res = false; 2049326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri uri = Uri.parse(uriStr + BluetoothMapContract.TABLE_MESSAGE); 2050326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2051326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int updateCount = 0; 2052326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde ContentValues contentValues = new ContentValues(); 2053326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde BluetoothMapFolderElement deleteFolder = mFolders. 20545a60e47497f21f64e6d79420dc4c56c1907df22akschulz getFolderByName(BluetoothMapContract.FOLDER_NAME_DELETED); 2055326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde contentValues.put(BluetoothMapContract.MessageColumns._ID, handle); 20565a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMsg()) { 20575a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListMsg().get(handle); 2058326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (status == BluetoothMapAppParams.STATUS_VALUE_YES) { 2059326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Set deleted folder id */ 2060326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long folderId = -1; 2061326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(deleteFolder != null) { 20625a60e47497f21f64e6d79420dc4c56c1907df22akschulz folderId = deleteFolder.getFolderId(); 2063326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2064326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde contentValues.put(BluetoothMapContract.MessageColumns.FOLDER_ID,folderId); 2065326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde updateCount = mResolver.update(uri, contentValues, null, null); 2066326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* The race between updating the value in our cached values and the database 2067326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * is handled by the synchronized statement. */ 2068326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(updateCount > 0) { 2069326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde res = true; 2070326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (msg != null) { 2071326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msg.oldFolderId = msg.folderId; 20725a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Update the folder ID to avoid triggering an event for MCE 20735a60e47497f21f64e6d79420dc4c56c1907df22akschulz * initiated actions. */ 2074326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msg.folderId = folderId; 2075326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2076326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(D) Log.d(TAG, "Deleted MSG: " + handle + " from folderId: " + folderId); 2077326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2078326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.w(TAG, "Msg: " + handle + " - Set delete status " + status 2079326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde + " failed for folderId " + folderId); 2080326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2081326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else if (status == BluetoothMapAppParams.STATUS_VALUE_NO) { 2082326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Undelete message. move to old folder if we know it, 2083326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * else move to inbox - as dictated by the spec. */ 2084326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(msg != null && deleteFolder != null && 20855a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.folderId == deleteFolder.getFolderId()) { 2086326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Only modify messages in the 'Deleted' folder */ 2087326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long folderId = -1; 20885a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapFolderElement inboxFolder = mCurrentFolder. 20895a60e47497f21f64e6d79420dc4c56c1907df22akschulz getFolderByName(BluetoothMapContract.FOLDER_NAME_INBOX); 2090326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (msg != null && msg.oldFolderId != -1) { 2091326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde folderId = msg.oldFolderId; 2092326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2093326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(inboxFolder != null) { 20945a60e47497f21f64e6d79420dc4c56c1907df22akschulz folderId = inboxFolder.getFolderId(); 2095326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 20965a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG,"We did not delete the message, hence the old folder " + 20975a60e47497f21f64e6d79420dc4c56c1907df22akschulz "is unknown. Moving to inbox."); 2098326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2099326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde contentValues.put(BluetoothMapContract.MessageColumns.FOLDER_ID, folderId); 2100326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde updateCount = mResolver.update(uri, contentValues, null, null); 2101326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(updateCount > 0) { 2102326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde res = true; 21035a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Update the folder ID to avoid triggering an event for MCE 21045a60e47497f21f64e6d79420dc4c56c1907df22akschulz * initiated actions. */ 21055a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* UPDATE: Actually the BT-Spec. states that an undelete is a move of the 21065a60e47497f21f64e6d79420dc4c56c1907df22akschulz * message to INBOX - clearified in errata 5591. 21075a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Therefore we update the cache to INBOX-folderId - to trigger a message 21085a60e47497f21f64e6d79420dc4c56c1907df22akschulz * shift event to the old-folder. */ 21095a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(inboxFolder != null) { 21105a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.folderId = inboxFolder.getFolderId(); 21115a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 21125a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.folderId = folderId; 21135a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 2114326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 21155a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D)Log.d(TAG,"We did not delete the message, hence the old folder " + 21165a60e47497f21f64e6d79420dc4c56c1907df22akschulz "is unknown. Moving to inbox."); 2117326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2118326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2119326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2120326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(V) { 2121326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde BluetoothMapFolderElement folderElement; 2122326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String folderName = "unknown"; 2123326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (msg != null) { 21245a60e47497f21f64e6d79420dc4c56c1907df22akschulz folderElement = mCurrentFolder.getFolderById(msg.folderId); 2125326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(folderElement != null) { 2126326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde folderName = folderElement.getName(); 2127326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2128326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2129326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.d(TAG,"setEmailMessageStatusDelete: " + handle + " from " + folderName 2130326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde + " status: " + status); 2131326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2132326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2133326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(res == false) { 2134326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.w(TAG, "Set delete status " + status + " failed."); 2135326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2136326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return res; 2137326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2138326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2139326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private void updateThreadId(Uri uri, String valueString, long threadId) { 2140326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde ContentValues contentValues = new ContentValues(); 2141326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde contentValues.put(valueString, threadId); 2142326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mResolver.update(uri, contentValues, null, null); 2143fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2144fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2145fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private boolean deleteMessageMms(long handle) { 2146fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie boolean res = false; 2147fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri uri = ContentUris.withAppendedId(Mms.CONTENT_URI, handle); 2148fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Cursor c = mResolver.query(uri, null, null, null, null); 214928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 215028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (c != null && c.moveToFirst()) { 215128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Move to deleted folder, or delete if already in deleted folder */ 215228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int threadId = c.getInt(c.getColumnIndex(Mms.THREAD_ID)); 215328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (threadId != DELETED_THREAD_ID) { 215428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Set deleted thread id */ 21555a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMms()) { 21565a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListMms().get(handle); 215728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if(msg != null) { // This will always be the case 215828446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz msg.threadId = DELETED_THREAD_ID; 215928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 2160326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 216128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz updateThreadId(uri, Mms.THREAD_ID, DELETED_THREAD_ID); 216228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } else { 216328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Delete from observer message list to avoid delete notifications */ 21645a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMms()) { 21655a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMsgListMms().remove(handle); 216628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 216728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Delete message */ 216828446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz mResolver.delete(uri, null, null); 2169326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 217028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz res = true; 2171fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 217228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 21735a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 2174fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 217528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz 2176fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return res; 2177fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2178fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2179fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private boolean unDeleteMessageMms(long handle) { 2180fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie boolean res = false; 2181fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri uri = ContentUris.withAppendedId(Mms.CONTENT_URI, handle); 2182fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Cursor c = mResolver.query(uri, null, null, null, null); 218328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 218428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (c != null && c.moveToFirst()) { 218528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int threadId = c.getInt(c.getColumnIndex(Mms.THREAD_ID)); 218628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (threadId == DELETED_THREAD_ID) { 218728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Restore thread id from address, or if no thread for address 21885a60e47497f21f64e6d79420dc4c56c1907df22akschulz * create new thread by insert and remove of fake message */ 218928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz String address; 219028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz long id = c.getLong(c.getColumnIndex(Mms._ID)); 219128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int msgBox = c.getInt(c.getColumnIndex(Mms.MESSAGE_BOX)); 219228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (msgBox == Mms.MESSAGE_BOX_INBOX) { 219328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz address = BluetoothMapContent.getAddressMms(mResolver, id, 21945a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContent.MMS_FROM); 219528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } else { 219628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz address = BluetoothMapContent.getAddressMms(mResolver, id, 21975a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContent.MMS_TO); 219828446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 219928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz Set<String> recipients = new HashSet<String>(); 220028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz recipients.addAll(Arrays.asList(address)); 220128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz Long oldThreadId = Telephony.Threads.getOrCreateThreadId(mContext, recipients); 22025a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMms()) { 22035a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListMms().get(handle); 220428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if(msg != null) { // This will always be the case 220528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz msg.threadId = oldThreadId.intValue(); 22065a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Spec. states that undelete shall shift the message to Inbox. 22075a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Hence we need to trigger a message shift from INBOX to old-folder 22085a60e47497f21f64e6d79420dc4c56c1907df22akschulz // after undelete. 22095a60e47497f21f64e6d79420dc4c56c1907df22akschulz // We do this by changing the cached folder value to being inbox - hence 22105a60e47497f21f64e6d79420dc4c56c1907df22akschulz // the event handler will se the update as the message have been shifted 22115a60e47497f21f64e6d79420dc4c56c1907df22akschulz // from INBOX to old-folder. (Errata 5591 clearifies this) 22125a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.type = Mms.MESSAGE_BOX_INBOX; 221328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 2214326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 221528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz updateThreadId(uri, Mms.THREAD_ID, oldThreadId); 221628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } else { 221728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz Log.d(TAG, "Message not in deleted folder: handle " + handle 22185a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " threadId " + threadId); 2219326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 222028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz res = true; 2221fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 222228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 22235a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 2224fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2225fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return res; 2226fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2227fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2228fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private boolean deleteMessageSms(long handle) { 2229fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie boolean res = false; 2230fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri uri = ContentUris.withAppendedId(Sms.CONTENT_URI, handle); 2231fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Cursor c = mResolver.query(uri, null, null, null, null); 223228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 223328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (c != null && c.moveToFirst()) { 223428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Move to deleted folder, or delete if already in deleted folder */ 223528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int threadId = c.getInt(c.getColumnIndex(Sms.THREAD_ID)); 223628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (threadId != DELETED_THREAD_ID) { 22375a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListSms()) { 22385a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListSms().get(handle); 223928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if(msg != null) { // This will always be the case 224028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz msg.threadId = DELETED_THREAD_ID; 224128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 2242326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 224328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Set deleted thread id */ 224428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz updateThreadId(uri, Sms.THREAD_ID, DELETED_THREAD_ID); 224528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } else { 224628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Delete from observer message list to avoid delete notifications */ 22475a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListSms()) { 22485a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMsgListSms().remove(handle); 224928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 225028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* Delete message */ 225128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz mResolver.delete(uri, null, null); 2252326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 225328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz res = true; 2254fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 225528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 22565a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 2257fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2258fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return res; 2259fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2260fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2261fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private boolean unDeleteMessageSms(long handle) { 2262fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie boolean res = false; 2263fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri uri = ContentUris.withAppendedId(Sms.CONTENT_URI, handle); 2264fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Cursor c = mResolver.query(uri, null, null, null, null); 226528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 226628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (c != null && c.moveToFirst()) { 226728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int threadId = c.getInt(c.getColumnIndex(Sms.THREAD_ID)); 226828446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (threadId == DELETED_THREAD_ID) { 226928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz String address = c.getString(c.getColumnIndex(Sms.ADDRESS)); 227028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz Set<String> recipients = new HashSet<String>(); 227128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz recipients.addAll(Arrays.asList(address)); 227228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz Long oldThreadId = Telephony.Threads.getOrCreateThreadId(mContext, recipients); 22735a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListSms()) { 22745a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListSms().get(handle); 22755a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(msg != null) { 22765a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.threadId = oldThreadId.intValue(); 22775a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* This will always be the case 22785a60e47497f21f64e6d79420dc4c56c1907df22akschulz * The threadId is specified as an int, so it is safe to truncate 22795a60e47497f21f64e6d79420dc4c56c1907df22akschulz * TODO: Test that this will trigger a message-shift from Inbox 22805a60e47497f21f64e6d79420dc4c56c1907df22akschulz * to old-folder 22815a60e47497f21f64e6d79420dc4c56c1907df22akschulz **/ 22825a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Spec. states that undelete shall shift the message to Inbox. 22835a60e47497f21f64e6d79420dc4c56c1907df22akschulz * Hence we need to trigger a message shift from INBOX to old-folder 22845a60e47497f21f64e6d79420dc4c56c1907df22akschulz * after undelete. 22855a60e47497f21f64e6d79420dc4c56c1907df22akschulz * We do this by changing the cached folder value to being inbox - hence 22865a60e47497f21f64e6d79420dc4c56c1907df22akschulz * the event handler will se the update as the message have been shifted 22875a60e47497f21f64e6d79420dc4c56c1907df22akschulz * from INBOX to old-folder. (Errata 5591 clearifies this) 22885a60e47497f21f64e6d79420dc4c56c1907df22akschulz * */ 22895a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.type = Sms.MESSAGE_TYPE_INBOX; 229028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 2291326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 229228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz updateThreadId(uri, Sms.THREAD_ID, oldThreadId); 229328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } else { 229428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz Log.d(TAG, "Message not in deleted folder: handle " + handle 22955a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " threadId " + threadId); 2296326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 229728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz res = true; 2298fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 229928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 23005a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 2301fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2302fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return res; 2303fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2304fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 23055a60e47497f21f64e6d79420dc4c56c1907df22akschulz /** 23065a60e47497f21f64e6d79420dc4c56c1907df22akschulz * 23075a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @param handle 23085a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @param type 23095a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @param mCurrentFolder 23105a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @param uriStr 23115a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @param statusValue 23125a60e47497f21f64e6d79420dc4c56c1907df22akschulz * @return true is success 23135a60e47497f21f64e6d79420dc4c56c1907df22akschulz */ 2314326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde public boolean setMessageStatusDeleted(long handle, TYPE type, 2315326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde BluetoothMapFolderElement mCurrentFolder, String uriStr, int statusValue) { 2316fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie boolean res = false; 2317fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (D) Log.d(TAG, "setMessageStatusDeleted: handle " + handle 23185a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " type " + type + " value " + statusValue); 2319fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2320326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (type == TYPE.EMAIL) { 2321326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde res = setEmailMessageStatusDelete(mCurrentFolder, uriStr, handle, statusValue); 23225a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if (type == TYPE.IM) { 23235a60e47497f21f64e6d79420dc4c56c1907df22akschulz // TODO: to do when deleting IM message 23245a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (D) Log.d(TAG, "setMessageStatusDeleted: IM not handled" ); 2325326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2326326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (statusValue == BluetoothMapAppParams.STATUS_VALUE_YES) { 2327326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (type == TYPE.SMS_GSM || type == TYPE.SMS_CDMA) { 2328326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde res = deleteMessageSms(handle); 2329326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else if (type == TYPE.MMS) { 2330326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde res = deleteMessageMms(handle); 2331326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2332326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else if (statusValue == BluetoothMapAppParams.STATUS_VALUE_NO) { 2333326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (type == TYPE.SMS_GSM || type == TYPE.SMS_CDMA) { 2334326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde res = unDeleteMessageSms(handle); 2335326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else if (type == TYPE.MMS) { 2336326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde res = unDeleteMessageMms(handle); 2337326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2338fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2339fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2340fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return res; 2341fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2342fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2343326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /** 2344326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * 2345326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * @param handle 2346326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * @param type 2347326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * @param uriStr 2348326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * @param statusValue 2349326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * @return true at success 2350326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde */ 23515a60e47497f21f64e6d79420dc4c56c1907df22akschulz public boolean setMessageStatusRead(long handle, TYPE type, String uriStr, int statusValue) 23525a60e47497f21f64e6d79420dc4c56c1907df22akschulz throws RemoteException{ 2353326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int count = 0; 2354fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2355fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (D) Log.d(TAG, "setMessageStatusRead: handle " + handle 23565a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " type " + type + " value " + statusValue); 2357fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 23585a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Approved MAP spec errata 3445 states that read status initiated 23595a60e47497f21f64e6d79420dc4c56c1907df22akschulz * by the MCE shall change the MSE read status. */ 2360fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (type == TYPE.SMS_GSM || type == TYPE.SMS_CDMA) { 23619944703186475606478594cab832b1a3ee2d8098Ajay Panicker Uri uri = ContentUris.withAppendedId(Sms.CONTENT_URI, handle); 2362fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ContentValues contentValues = new ContentValues(); 2363fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie contentValues.put(Sms.READ, statusValue); 2364326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde contentValues.put(Sms.SEEN, statusValue); 2365326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String values = contentValues.toString(); 23669944703186475606478594cab832b1a3ee2d8098Ajay Panicker if (D) Log.d(TAG, " -> SMS Uri: " + uri.toString() + " values " + values); 23675a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListSms()) { 23685a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListSms().get(handle); 23695a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(msg != null) { // This will always be the case 23705a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.flagRead = statusValue; 23715a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 23725a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 23739944703186475606478594cab832b1a3ee2d8098Ajay Panicker count = mResolver.update(uri, contentValues, null, null); 2374326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (D) Log.d(TAG, " -> "+count +" rows updated!"); 237528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz 2376fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } else if (type == TYPE.MMS) { 2377fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri uri = ContentUris.withAppendedId(Mms.CONTENT_URI, handle); 2378326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (D) Log.d(TAG, " -> MMS Uri: " + uri.toString()); 2379fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ContentValues contentValues = new ContentValues(); 2380fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie contentValues.put(Mms.READ, statusValue); 23815a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMms()) { 23825a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListMms().get(handle); 23835a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(msg != null) { // This will always be the case 23845a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.flagRead = statusValue; 23855a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 23865a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 2387326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde count = mResolver.update(uri, contentValues, null, null); 2388326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (D) Log.d(TAG, " -> "+count +" rows updated!"); 23895a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if (type == TYPE.EMAIL || 23905a60e47497f21f64e6d79420dc4c56c1907df22akschulz type == TYPE.IM) { 2391326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri uri = mMessageUri; 2392326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde ContentValues contentValues = new ContentValues(); 2393326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde contentValues.put(BluetoothMapContract.MessageColumns.FLAG_READ, statusValue); 2394326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde contentValues.put(BluetoothMapContract.MessageColumns._ID, handle); 23955a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMsg()) { 23965a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg msg = getMsgListMsg().get(handle); 23975a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(msg != null) { // This will always be the case 23985a60e47497f21f64e6d79420dc4c56c1907df22akschulz msg.flagRead = statusValue; 23995a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 24005a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 2401326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde count = mProviderClient.update(uri, contentValues, null, null); 2402326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 240328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz 240428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz return (count > 0); 2405fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2406fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2407fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private class PushMsgInfo { 2408fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie long id; 2409fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int transparent; 2410fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int retry; 2411fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie String phone; 2412fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri uri; 2413326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long timestamp; 2414fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int parts; 2415fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int partsSent; 2416fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int partsDelivered; 2417fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie boolean resend; 2418326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde boolean sendInProgress; 2419326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde boolean failedSent; // Set to true if a single part sent fail is received. 2420326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int statusDelivered; // Set to != 0 if a single part deliver fail is received. 2421fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2422fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public PushMsgInfo(long id, int transparent, 24235a60e47497f21f64e6d79420dc4c56c1907df22akschulz int retry, String phone, Uri uri) { 2424fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.id = id; 2425fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.transparent = transparent; 2426fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.retry = retry; 2427fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.phone = phone; 2428fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.uri = uri; 2429fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie this.resend = false; 2430326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.sendInProgress = false; 2431326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.failedSent = false; 2432326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.statusDelivered = 0; /* Assume success */ 2433326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde this.timestamp = 0; 2434fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie }; 2435fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2436fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2437fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private Map<Long, PushMsgInfo> mPushMsgList = 24385a60e47497f21f64e6d79420dc4c56c1907df22akschulz Collections.synchronizedMap(new HashMap<Long, PushMsgInfo>()); 2439fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2440326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde public long pushMessage(BluetoothMapbMessage msg, BluetoothMapFolderElement folderElement, 2441326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde BluetoothMapAppParams ap, String emailBaseUri) 2442326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde throws IllegalArgumentException, RemoteException, IOException { 2443fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (D) Log.d(TAG, "pushMessage"); 2444fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ArrayList<BluetoothMapbMessage.vCard> recipientList = msg.getRecipients(); 2445fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int transparent = (ap.getTransparent() == BluetoothMapAppParams.INVALID_VALUE_PARAMETER) ? 2446fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 0 : ap.getTransparent(); 2447fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int retry = ap.getRetry(); 2448fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int charset = ap.getCharset(); 2449fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie long handle = -1; 2450326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long folderId = -1; 2451fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2452fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (recipientList == null) { 2453326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (D) Log.d(TAG, "empty recipient list"); 2454fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return -1; 2455fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2456fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2457326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if ( msg.getType().equals(TYPE.EMAIL) ) { 2458326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Write the message to the database */ 2459326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String msgBody = ((BluetoothMapbMessageEmail) msg).getEmailBody(); 2460326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (V) { 2461326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int length = msgBody.length(); 2462326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.v(TAG, "pushMessage: message string length = " + length); 2463326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String messages[] = msgBody.split("\r\n"); 2464326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.v(TAG, "pushMessage: messages count=" + messages.length); 2465326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde for(int i = 0; i < messages.length; i++) { 2466326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.v(TAG, "part " + i + ":" + messages[i]); 2467326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2468326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2469326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde FileOutputStream os = null; 2470326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde ParcelFileDescriptor fdOut = null; 2471326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri uriInsert = Uri.parse(emailBaseUri + BluetoothMapContract.TABLE_MESSAGE); 2472326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (D) Log.d(TAG, "pushMessage - uriInsert= " + uriInsert.toString() + 24735a60e47497f21f64e6d79420dc4c56c1907df22akschulz ", intoFolder id=" + folderElement.getFolderId()); 2474326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 24755a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListMsg()) { 2476326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // Now insert the empty message into folder 2477326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde ContentValues values = new ContentValues(); 24785a60e47497f21f64e6d79420dc4c56c1907df22akschulz folderId = folderElement.getFolderId(); 2479326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(BluetoothMapContract.MessageColumns.FOLDER_ID, folderId); 2480326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri uriNew = mProviderClient.insert(uriInsert, values); 2481326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (D) Log.d(TAG, "pushMessage - uriNew= " + uriNew.toString()); 2482326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde handle = Long.parseLong(uriNew.getLastPathSegment()); 2483326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2484326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde try { 2485326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde fdOut = mProviderClient.openFile(uriNew, "w"); 2486326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde os = new FileOutputStream(fdOut.getFileDescriptor()); 2487326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // Write Email to DB 2488326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde os.write(msgBody.getBytes(), 0, msgBody.getBytes().length); 2489326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } catch (FileNotFoundException e) { 2490326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.w(TAG, e); 2491326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde throw(new IOException("Unable to open file stream")); 2492326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } catch (NullPointerException e) { 2493326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.w(TAG, e); 2494326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde throw(new IllegalArgumentException("Unable to parse message.")); 2495326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } finally { 2496326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde try { 2497326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(os != null) 2498326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde os.close(); 2499326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } catch (IOException e) {Log.w(TAG, e);} 2500326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde try { 2501326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(fdOut != null) 25025a60e47497f21f64e6d79420dc4c56c1907df22akschulz fdOut.close(); 2503326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } catch (IOException e) {Log.w(TAG, e);} 2504326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2505326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2506326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Extract the data for the inserted message, and store in local mirror, to 2507326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * avoid sending a NewMessage Event. */ 25085a60e47497f21f64e6d79420dc4c56c1907df22akschulz /*TODO: We need to add the new 1.1 parameter as well:-) e.g. read*/ 25095a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg newMsg = new Msg(handle, folderId, 1); // TODO: Create define for read-state 2510326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde newMsg.transparent = (transparent == 1) ? true : false; 25115a60e47497f21f64e6d79420dc4c56c1907df22akschulz if ( folderId == folderElement.getFolderByName( 25125a60e47497f21f64e6d79420dc4c56c1907df22akschulz BluetoothMapContract.FOLDER_NAME_OUTBOX).getFolderId() ) { 2513326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde newMsg.localInitiatedSend = true; 2514326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 25155a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMsgListMsg().put(handle, newMsg); 2516326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2517326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { // type SMS_* of MMS 2518326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde for (BluetoothMapbMessage.vCard recipient : recipientList) { 25195a60e47497f21f64e6d79420dc4c56c1907df22akschulz // Only send the message to the top level recipient 25205a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(recipient.getEnvLevel() == 0) 2521326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde { 2522326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Only send to first address */ 2523326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String phone = recipient.getFirstPhoneNumber(); 2524326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String email = recipient.getFirstEmail(); 2525326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String folder = folderElement.getName(); 2526326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde boolean read = false; 2527326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde boolean deliveryReport = true; 2528326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String msgBody = null; 2529326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2530326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* If MMS contains text only and the size is less than ten SMS's 2531326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * then convert the MMS to type SMS and then proceed 2532326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde */ 2533326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (msg.getType().equals(TYPE.MMS) && 25345a60e47497f21f64e6d79420dc4c56c1907df22akschulz (((BluetoothMapbMessageMime) msg).getTextOnly() == true)) { 25355a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgBody = ((BluetoothMapbMessageMime) msg).getMessageAsText(); 2536326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde SmsManager smsMng = SmsManager.getDefault(); 2537326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde ArrayList<String> parts = smsMng.divideMessage(msgBody); 2538326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int smsParts = parts.size(); 2539326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (smsParts <= CONVERT_MMS_TO_SMS_PART_COUNT ) { 25405a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (D) Log.d(TAG, "pushMessage - converting MMS to SMS, sms parts=" 25415a60e47497f21f64e6d79420dc4c56c1907df22akschulz + smsParts ); 2542326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msg.setType(mSmsType); 2543326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 25445a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (D) Log.d(TAG, "pushMessage - MMS text only but to big to " + 25455a60e47497f21f64e6d79420dc4c56c1907df22akschulz "convert to SMS"); 2546326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msgBody = null; 2547326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2548326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2549fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2550326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2551326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (msg.getType().equals(TYPE.MMS)) { 2552326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Send message if folder is outbox else just store in draft*/ 2553ed70219e41ba68196798dcbf75b782d13fb88603kschulz handle = sendMmsMessage(folder, phone, (BluetoothMapbMessageMime)msg, 2554ed70219e41ba68196798dcbf75b782d13fb88603kschulz transparent, retry); 2555326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else if (msg.getType().equals(TYPE.SMS_GSM) || 2556326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msg.getType().equals(TYPE.SMS_CDMA) ) { 2557fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /* Add the message to the database */ 2558326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(msgBody == null) 2559326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msgBody = ((BluetoothMapbMessageSms) msg).getSmsBody(); 2560326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2561cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta if (TextUtils.isEmpty(msgBody)) { 2562cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta Log.d(TAG, "PushMsg: Empty msgBody "); 2563cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta /* not allowed to push empty message */ 2564cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta throw new IllegalArgumentException("push EMPTY message: Invalid Body"); 2565cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta } 25665a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* We need to lock the SMS list while updating the database, 25675a60e47497f21f64e6d79420dc4c56c1907df22akschulz * to avoid sending events on MCE initiated operation. */ 2568326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri contentUri = Uri.parse(Sms.CONTENT_URI+ "/" + folder); 2569326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri uri; 25705a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized(getMsgListSms()) { 2571326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = Sms.addMessageToUri(mResolver, contentUri, phone, msgBody, 25725a60e47497f21f64e6d79420dc4c56c1907df22akschulz "", System.currentTimeMillis(), read, deliveryReport); 2573326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2574326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(V) Log.v(TAG, "Sms.addMessageToUri() returned: " + uri); 2575326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (uri == null) { 25765a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (D) Log.d(TAG, "pushMessage - failure on add to uri " 25775a60e47497f21f64e6d79420dc4c56c1907df22akschulz + contentUri); 2578326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return -1; 2579326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2580326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Cursor c = mResolver.query(uri, SMS_PROJECTION_SHORT, null, null, null); 25815a60e47497f21f64e6d79420dc4c56c1907df22akschulz 25825a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Extract the data for the inserted message, and store in local mirror, 25835a60e47497f21f64e6d79420dc4c56c1907df22akschulz * to avoid sending a NewMessage Event. */ 258428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 258528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (c != null && c.moveToFirst()) { 258628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz long id = c.getLong(c.getColumnIndex(Sms._ID)); 258728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int type = c.getInt(c.getColumnIndex(Sms.TYPE)); 258828446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int threadId = c.getInt(c.getColumnIndex(Sms.THREAD_ID)); 25895a60e47497f21f64e6d79420dc4c56c1907df22akschulz int readFlag = c.getInt(c.getColumnIndex(Sms.READ)); 25905a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(V) Log.v(TAG, "add message with id=" + id + 25915a60e47497f21f64e6d79420dc4c56c1907df22akschulz " type=" + type + " threadId=" + threadId + 25925a60e47497f21f64e6d79420dc4c56c1907df22akschulz " readFlag=" + readFlag + "to mMsgListSms"); 25935a60e47497f21f64e6d79420dc4c56c1907df22akschulz Msg newMsg = new Msg(id, type, threadId, readFlag); 25945a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMsgListSms().put(id, newMsg); 25955a60e47497f21f64e6d79420dc4c56c1907df22akschulz c.close(); 259628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } else { 25975a60e47497f21f64e6d79420dc4c56c1907df22akschulz Log.w(TAG,"Message: " + uri + " no longer exist!"); 25985a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* This can only happen, if the message is deleted 25995a60e47497f21f64e6d79420dc4c56c1907df22akschulz * just as it is added */ 26005a60e47497f21f64e6d79420dc4c56c1907df22akschulz return -1; 260128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 260228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 26035a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 2604326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2605fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2606326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde handle = Long.parseLong(uri.getLastPathSegment()); 2607fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2608326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Send message if folder is outbox */ 26095a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (folder.equalsIgnoreCase(BluetoothMapContract.FOLDER_NAME_OUTBOX)) { 2610326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde PushMsgInfo msgInfo = new PushMsgInfo(handle, transparent, 26115a60e47497f21f64e6d79420dc4c56c1907df22akschulz retry, phone, uri); 2612326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mPushMsgList.put(handle, msgInfo); 2613326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde sendMessage(msgInfo, msgBody); 2614326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(V) Log.v(TAG, "sendMessage returned..."); 26155a60e47497f21f64e6d79420dc4c56c1907df22akschulz } /* else just added to draft */ 26165a60e47497f21f64e6d79420dc4c56c1907df22akschulz 26175a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* sendMessage causes the message to be deleted and reinserted, 26185a60e47497f21f64e6d79420dc4c56c1907df22akschulz * hence we need to lock the list while this is happening. */ 2619fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2620326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2621326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (D) Log.d(TAG, "pushMessage - failure on type " ); 2622326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return -1; 2623fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2624fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2625fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2626fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2627fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2628fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /* If multiple recipients return handle of last */ 2629fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return handle; 2630fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2631fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2632ed70219e41ba68196798dcbf75b782d13fb88603kschulz public long sendMmsMessage(String folder, String to_address, BluetoothMapbMessageMime msg, 2633ed70219e41ba68196798dcbf75b782d13fb88603kschulz int transparent, int retry) { 2634fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /* 2635fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *strategy: 2636fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *1) parse message into parts 2637fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *if folder is outbox/drafts: 2638fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *2) push message to draft 2639fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *if folder is outbox: 2640fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *3) move message to outbox (to trigger the mms app to add msg to pending_messages list) 2641fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *4) send intent to mms app in order to wake it up. 2642fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *else if folder !outbox: 2643fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie *1) push message to folder 2644fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie * */ 2645326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (folder != null && (folder.equalsIgnoreCase(BluetoothMapContract.FOLDER_NAME_OUTBOX) 2646326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde || folder.equalsIgnoreCase(BluetoothMapContract.FOLDER_NAME_DRAFT))) { 2647326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long handle = pushMmsToFolder(Mms.MESSAGE_BOX_DRAFTS, to_address, msg); 26485a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* if invalid handle (-1) then just return the handle 26495a60e47497f21f64e6d79420dc4c56c1907df22akschulz * - else continue sending (if folder is outbox) */ 26505a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (BluetoothMapAppParams.INVALID_VALUE_PARAMETER != handle && 26515a60e47497f21f64e6d79420dc4c56c1907df22akschulz folder.equalsIgnoreCase(BluetoothMapContract.FOLDER_NAME_OUTBOX)) { 2652ed70219e41ba68196798dcbf75b782d13fb88603kschulz Uri btMmsUri = MmsFileProvider.CONTENT_URI.buildUpon() 2653ed70219e41ba68196798dcbf75b782d13fb88603kschulz .appendPath(Long.toString(handle)).build(); 2654ed70219e41ba68196798dcbf75b782d13fb88603kschulz Intent sentIntent = new Intent(ACTION_MESSAGE_SENT); 2655ed70219e41ba68196798dcbf75b782d13fb88603kschulz // TODO: update the mmsMsgList <- done in pushMmsToFolder() but check 2656ed70219e41ba68196798dcbf75b782d13fb88603kschulz sentIntent.setType("message/" + Long.toString(handle)); 2657ed70219e41ba68196798dcbf75b782d13fb88603kschulz sentIntent.putExtra(EXTRA_MESSAGE_SENT_MSG_TYPE, TYPE.MMS.ordinal()); 2658ed70219e41ba68196798dcbf75b782d13fb88603kschulz sentIntent.putExtra(EXTRA_MESSAGE_SENT_HANDLE, handle); // needed for notification 2659ed70219e41ba68196798dcbf75b782d13fb88603kschulz sentIntent.putExtra(EXTRA_MESSAGE_SENT_TRANSPARENT, transparent); 2660ed70219e41ba68196798dcbf75b782d13fb88603kschulz sentIntent.putExtra(EXTRA_MESSAGE_SENT_RETRY, retry); 2661ed70219e41ba68196798dcbf75b782d13fb88603kschulz //sentIntent.setDataAndNormalize(btMmsUri); 2662ed70219e41ba68196798dcbf75b782d13fb88603kschulz PendingIntent pendingSendIntent = PendingIntent.getBroadcast(mContext, 0, 2663ed70219e41ba68196798dcbf75b782d13fb88603kschulz sentIntent, 0); 2664ed70219e41ba68196798dcbf75b782d13fb88603kschulz SmsManager.getDefault().sendMultimediaMessage(mContext, 2665ed70219e41ba68196798dcbf75b782d13fb88603kschulz btMmsUri, null/*locationUrl*/, null/*configOverrides*/, 2666ed70219e41ba68196798dcbf75b782d13fb88603kschulz pendingSendIntent); 2667326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2668326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return handle; 2669326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2670326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* not allowed to push mms to anything but outbox/draft */ 26715a60e47497f21f64e6d79420dc4c56c1907df22akschulz throw new IllegalArgumentException("Cannot push message to other " + 26725a60e47497f21f64e6d79420dc4c56c1907df22akschulz "folders than outbox/draft"); 2673fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2674fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2675fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2676fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void moveDraftToOutbox(long handle) { 2677ed70219e41ba68196798dcbf75b782d13fb88603kschulz moveMmsToFolder(handle, mResolver, Mms.MESSAGE_BOX_OUTBOX); 2678ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 2679ed70219e41ba68196798dcbf75b782d13fb88603kschulz 2680ed70219e41ba68196798dcbf75b782d13fb88603kschulz /** 2681ed70219e41ba68196798dcbf75b782d13fb88603kschulz * Move a MMS to another folder. 2682ed70219e41ba68196798dcbf75b782d13fb88603kschulz * @param handle the CP handle of the message to move 2683ed70219e41ba68196798dcbf75b782d13fb88603kschulz * @param resolver the ContentResolver to use 2684ed70219e41ba68196798dcbf75b782d13fb88603kschulz * @param folder the destination folder - use Mms.MESSAGE_BOX_xxx 2685ed70219e41ba68196798dcbf75b782d13fb88603kschulz */ 2686ed70219e41ba68196798dcbf75b782d13fb88603kschulz private static void moveMmsToFolder(long handle, ContentResolver resolver, int folder) { 2687fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /*Move message by changing the msg_box value in the content provider database */ 26885a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (handle != -1) { 26895a60e47497f21f64e6d79420dc4c56c1907df22akschulz String whereClause = " _id= " + handle; 26905a60e47497f21f64e6d79420dc4c56c1907df22akschulz Uri uri = Mms.CONTENT_URI; 2691ed70219e41ba68196798dcbf75b782d13fb88603kschulz Cursor queryResult = resolver.query(uri, null, whereClause, null, null); 26925a60e47497f21f64e6d79420dc4c56c1907df22akschulz try { 26935a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (queryResult != null) { 26945a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (queryResult.getCount() > 0) { 26955a60e47497f21f64e6d79420dc4c56c1907df22akschulz queryResult.moveToFirst(); 26965a60e47497f21f64e6d79420dc4c56c1907df22akschulz ContentValues data = new ContentValues(); 26975a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* set folder to be outbox */ 2698ed70219e41ba68196798dcbf75b782d13fb88603kschulz data.put(Mms.MESSAGE_BOX, folder); 2699ed70219e41ba68196798dcbf75b782d13fb88603kschulz resolver.update(uri, data, whereClause, null); 2700ed70219e41ba68196798dcbf75b782d13fb88603kschulz if (D) Log.d(TAG, "moved MMS message to " + getMmsFolderName(folder)); 27015a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 27025a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else { 2703ed70219e41ba68196798dcbf75b782d13fb88603kschulz Log.w(TAG, "Could not move MMS message to " + getMmsFolderName(folder)); 27045a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 27055a60e47497f21f64e6d79420dc4c56c1907df22akschulz } finally { 27065a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (queryResult != null) queryResult.close(); 2707fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2708fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2709fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 27105a60e47497f21f64e6d79420dc4c56c1907df22akschulz private long pushMmsToFolder(int folder, String to_address, BluetoothMapbMessageMime msg) { 2711fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /** 2712fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie * strategy: 2713fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie * 1) parse msg into parts + header 2714fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie * 2) create thread id (abuse the ease of adding an SMS to get id for thread) 2715fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie * 3) push parts into content://mms/parts/ table 2716fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie * 3) 2717fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie */ 2718fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2719fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ContentValues values = new ContentValues(); 2720326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.MESSAGE_BOX, folder); 2721326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.READ, 0); 2722326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.SEEN, 0); 2723326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(msg.getSubject() != null) { 2724326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.SUBJECT, msg.getSubject()); 2725326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2726326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.SUBJECT, ""); 2727326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 272870be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz 2729326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(msg.getSubject() != null && msg.getSubject().length() > 0) { 2730326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.SUBJECT_CHARSET, 106); 2731326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2732326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.CONTENT_TYPE, "application/vnd.wap.multipart.related"); 2733326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.EXPIRY, 604800); 2734326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.MESSAGE_CLASS, PduHeaders.MESSAGE_CLASS_PERSONAL_STR); 2735326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.MESSAGE_TYPE, PduHeaders.MESSAGE_TYPE_SEND_REQ); 2736326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.MMS_VERSION, PduHeaders.CURRENT_MMS_VERSION); 2737326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.PRIORITY, PduHeaders.PRIORITY_NORMAL); 2738326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.READ_REPORT, PduHeaders.VALUE_NO); 2739326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.TRANSACTION_ID, "T"+ Long.toHexString(System.currentTimeMillis())); 2740326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.DELIVERY_REPORT, PduHeaders.VALUE_NO); 2741326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.LOCKED, 0); 2742326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(msg.getTextOnly() == true) 2743326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.TEXT_ONLY, true); 2744326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.MESSAGE_SIZE, msg.getSize()); 274570be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz 2746326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // Get thread id 2747fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Set<String> recipients = new HashSet<String>(); 2748fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie recipients.addAll(Arrays.asList(to_address)); 2749326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.THREAD_ID, Telephony.Threads.getOrCreateThreadId(mContext, recipients)); 2750326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri uri = Mms.CONTENT_URI; 2751fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 27525a60e47497f21f64e6d79420dc4c56c1907df22akschulz synchronized (getMsgListMms()) { 27535a60e47497f21f64e6d79420dc4c56c1907df22akschulz 2754326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = mResolver.insert(uri, values); 2755326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2756326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (uri == null) { 2757326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // unable to insert MMS 2758326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.e(TAG, "Unabled to insert MMS " + values + "Uri: " + uri); 2759326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return -1; 2760326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2761326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* As we already have all the values we need, we could skip the query, but 2762326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde doing the query ensures we get any changes made by the content provider 2763326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde at insert. */ 2764326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Cursor c = mResolver.query(uri, MMS_PROJECTION_SHORT, null, null, null); 276528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 276628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz if (c != null && c.moveToFirst()) { 276728446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz long id = c.getLong(c.getColumnIndex(Mms._ID)); 276828446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int type = c.getInt(c.getColumnIndex(Mms.MESSAGE_BOX)); 276928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz int threadId = c.getInt(c.getColumnIndex(Mms.THREAD_ID)); 2770ed70219e41ba68196798dcbf75b782d13fb88603kschulz int readStatus = c.getInt(c.getColumnIndex(Mms.READ)); 2771326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 277228446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz /* We must filter out any actions made by the MCE. Add the new message to 277328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz * the list of known messages. */ 2774326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2775ed70219e41ba68196798dcbf75b782d13fb88603kschulz Msg newMsg = new Msg(id, type, threadId, readStatus); 277628446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz newMsg.localInitiatedSend = true; 27775a60e47497f21f64e6d79420dc4c56c1907df22akschulz getMsgListMms().put(id, newMsg); 27785a60e47497f21f64e6d79420dc4c56c1907df22akschulz c.close(); 277928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 278028446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 27815a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 2782326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2783326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } // Done adding changes, unlock access to mMsgListMms to allow sending MMS events again 2784fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2785fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie long handle = Long.parseLong(uri.getLastPathSegment()); 2786326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (V) Log.v(TAG, " NEW URI " + uri.toString()); 2787326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2788fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie try { 2789326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(msg.getMimeParts() == null) { 27905a60e47497f21f64e6d79420dc4c56c1907df22akschulz /* Perhaps this message have been deleted, and no longer have any content, 27915a60e47497f21f64e6d79420dc4c56c1907df22akschulz * but only headers */ 2792326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.w(TAG, "No MMS parts present..."); 2793326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 27945a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(V) Log.v(TAG, "Adding " + msg.getMimeParts().size() 27955a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " parts to the data base."); 2796326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde for(MimePart part : msg.getMimeParts()) { 27975a60e47497f21f64e6d79420dc4c56c1907df22akschulz int count = 0; 27985a60e47497f21f64e6d79420dc4c56c1907df22akschulz count++; 2799326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.clear(); 28005a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(part.mContentType != null && 28015a60e47497f21f64e6d79420dc4c56c1907df22akschulz part.mContentType.toUpperCase().contains("TEXT")) { 2802326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_TYPE, "text/plain"); 2803326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CHARSET, 106); 2804326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mPartName != null) { 2805326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.FILENAME, part.mPartName); 2806326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.NAME, part.mPartName); 2807326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2808326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.FILENAME, "text_" + count +".txt"); 2809326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.NAME, "text_" + count +".txt"); 2810326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2811326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // Ensure we have "ci" set 2812326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentId != null) { 2813326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_ID, part.mContentId); 2814326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2815326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mPartName != null) { 2816326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_ID, "<" + part.mPartName + ">"); 2817326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2818326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_ID, "<text_" + count + ">"); 2819326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2820326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2821326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // Ensure we have "cl" set 2822326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentLocation != null) { 2823326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_LOCATION, part.mContentLocation); 2824326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2825326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mPartName != null) { 2826326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_LOCATION, part.mPartName + ".txt"); 2827326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2828326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_LOCATION, "text_" + count + ".txt"); 2829326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2830326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2831326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2832326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentDisposition != null) { 2833326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_DISPOSITION, part.mContentDisposition); 2834326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2835326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.TEXT, part.getDataAsString()); 2836326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = Uri.parse(Mms.CONTENT_URI + "/" + handle + "/part"); 2837326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = mResolver.insert(uri, values); 2838326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(V) Log.v(TAG, "Added TEXT part"); 2839326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 28405a60e47497f21f64e6d79420dc4c56c1907df22akschulz } else if (part.mContentType != null && 28415a60e47497f21f64e6d79420dc4c56c1907df22akschulz part.mContentType.toUpperCase().contains("SMIL")){ 2842326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.SEQ, -1); 2843326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_TYPE, "application/smil"); 2844326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentId != null) { 2845326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_ID, part.mContentId); 2846326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2847326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_ID, "<smil_" + count + ">"); 2848326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2849326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentLocation != null) { 2850326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_LOCATION, part.mContentLocation); 2851326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2852326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_LOCATION, "smil_" + count + ".xml"); 2853326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2854326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2855326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentDisposition != null) 2856326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_DISPOSITION, part.mContentDisposition); 2857326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.FILENAME, "smil.xml"); 2858326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.NAME, "smil.xml"); 2859326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.TEXT, new String(part.mData, "UTF-8")); 2860326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2861326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = Uri.parse(Mms.CONTENT_URI+ "/" + handle + "/part"); 2862326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = mResolver.insert(uri, values); 2863326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (V) Log.v(TAG, "Added SMIL part"); 2864326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2865326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde }else /*VIDEO/AUDIO/IMAGE*/ { 2866326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde writeMmsDataPart(handle, part, count); 2867326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (V) Log.v(TAG, "Added OTHER part"); 2868326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2869326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (uri != null){ 28705a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (V) Log.v(TAG, "Added part with content-type: " + part.mContentType 28715a60e47497f21f64e6d79420dc4c56c1907df22akschulz + " to Uri: " + uri.toString()); 2872326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 287370be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz } 2874fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2875fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } catch (UnsupportedEncodingException e) { 287670be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz Log.w(TAG, e); 2877fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } catch (IOException e) { 287870be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz Log.w(TAG, e); 2879fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2880fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2881fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie values.clear(); 2882326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Addr.CONTACT_ID, "null"); 2883326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Addr.ADDRESS, "insert-address-token"); 2884326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Addr.TYPE, BluetoothMapContent.MMS_FROM); 2885326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Addr.CHARSET, 106); 2886fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2887326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = Uri.parse(Mms.CONTENT_URI + "/" + handle + "/addr"); 2888326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = mResolver.insert(uri, values); 2889fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (uri != null && V){ 2890fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Log.v(TAG, " NEW URI " + uri.toString()); 2891fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2892fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2893fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie values.clear(); 2894326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Addr.CONTACT_ID, "null"); 2895326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Addr.ADDRESS, to_address); 2896326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Addr.TYPE, BluetoothMapContent.MMS_TO); 2897326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Addr.CHARSET, 106); 2898fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2899326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = Uri.parse(Mms.CONTENT_URI + "/" + handle + "/addr"); 2900326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde uri = mResolver.insert(uri, values); 2901fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (uri != null && V){ 2902fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Log.v(TAG, " NEW URI " + uri.toString()); 2903fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2904fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return handle; 2905fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2906fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2907fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 290870be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz private void writeMmsDataPart(long handle, MimePart part, int count) throws IOException{ 2909fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ContentValues values = new ContentValues(); 2910326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.MSG_ID, handle); 2911326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentType != null) { 2912326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_TYPE, part.mContentType); 2913326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2914326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.w(TAG, "MMS has no CONTENT_TYPE for part " + count); 2915326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2916326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentId != null) { 2917326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_ID, part.mContentId); 2918326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2919326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mPartName != null) { 2920326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_ID, "<" + part.mPartName + ">"); 2921326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2922326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_ID, "<part_" + count + ">"); 2923ed0c6ae1773ad1f4249fe3cf7447d7033195f222Ashwini Munigala } 2924ed0c6ae1773ad1f4249fe3cf7447d7033195f222Ashwini Munigala } 2925326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2926326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentLocation != null) { 2927326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_LOCATION, part.mContentLocation); 2928326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2929326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mPartName != null) { 2930326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_LOCATION, part.mPartName + ".dat"); 2931326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 2932326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_LOCATION, "part_" + count + ".dat"); 2933326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2934326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 2935326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mContentDisposition != null) 2936326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.CONTENT_DISPOSITION, part.mContentDisposition); 2937326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(part.mPartName != null) { 2938326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.FILENAME, part.mPartName); 2939326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.NAME, part.mPartName); 2940326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 294170be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz /* We must set at least one part identifier */ 2942326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.FILENAME, "part_" + count + ".dat"); 2943326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde values.put(Mms.Part.NAME, "part_" + count + ".dat"); 294470be005a18a35ec5fcb46152f0dfbe82156efa3aKim Schulz } 2945326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri partUri = Uri.parse(Mms.CONTENT_URI + "/" + handle + "/part"); 2946fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri res = mResolver.insert(partUri, values); 2947fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2948fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie // Add data to part 2949fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie OutputStream os = mResolver.openOutputStream(res); 2950326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde os.write(part.mData); 2951fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie os.close(); 2952fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 2953fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2954fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2955fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void sendMessage(PushMsgInfo msgInfo, String msgBody) { 2956fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2957fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie SmsManager smsMng = SmsManager.getDefault(); 2958fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ArrayList<String> parts = smsMng.divideMessage(msgBody); 2959fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie msgInfo.parts = parts.size(); 2960326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // We add a time stamp to differentiate delivery reports from each other for resent messages 2961326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msgInfo.timestamp = Calendar.getInstance().getTime().getTime(); 2962326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msgInfo.partsDelivered = 0; 2963326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msgInfo.partsSent = 0; 2964fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2965fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ArrayList<PendingIntent> deliveryIntents = new ArrayList<PendingIntent>(msgInfo.parts); 2966fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ArrayList<PendingIntent> sentIntents = new ArrayList<PendingIntent>(msgInfo.parts); 2967fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 2968326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* We handle the SENT intent in the MAP service, as this object 2969326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * is destroyed at disconnect, hence if a disconnect occur while sending 2970326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * a message, there is no intent handler to move the message from outbox 2971326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * to the correct folder. 2972326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * The correct solution would be to create a service that will start based on 2973326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde * the intent, if BT is turned off. */ 2974326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 2975cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta if (parts != null && parts.size() > 0) { 2976cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta for (int i = 0; i < msgInfo.parts; i++) { 2977cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta Intent intentDelivery, intentSent; 2978cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta 2979cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentDelivery = new Intent(ACTION_MESSAGE_DELIVERY, null); 2980cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta /* Add msgId and part number to ensure the intents are different, and we 2981cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta * thereby get an intent for each msg part. 2982cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta * setType is needed to create different intents for each message id/ time stamp, 2983cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta * as the extras are not used when comparing. */ 2984cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentDelivery.setType("message/" + Long.toString(msgInfo.id) + 2985cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta msgInfo.timestamp + i); 2986cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentDelivery.putExtra(EXTRA_MESSAGE_SENT_HANDLE, msgInfo.id); 2987cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentDelivery.putExtra(EXTRA_MESSAGE_SENT_TIMESTAMP, msgInfo.timestamp); 2988cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta PendingIntent pendingIntentDelivery = PendingIntent.getBroadcast(mContext, 0, 2989cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentDelivery, PendingIntent.FLAG_UPDATE_CURRENT); 2990cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta 2991cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentSent = new Intent(ACTION_MESSAGE_SENT, null); 2992cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta /* Add msgId and part number to ensure the intents are different, and we 2993cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta * thereby get an intent for each msg part. 2994cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta * setType is needed to create different intents for each message id/ time stamp, 2995cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta * as the extras are not used when comparing. */ 2996cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentSent.setType("message/" + Long.toString(msgInfo.id) + msgInfo.timestamp + i); 2997cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentSent.putExtra(EXTRA_MESSAGE_SENT_HANDLE, msgInfo.id); 2998cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentSent.putExtra(EXTRA_MESSAGE_SENT_URI, msgInfo.uri.toString()); 2999cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentSent.putExtra(EXTRA_MESSAGE_SENT_RETRY, msgInfo.retry); 3000cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentSent.putExtra(EXTRA_MESSAGE_SENT_TRANSPARENT, msgInfo.transparent); 3001cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta 3002cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta PendingIntent pendingIntentSent = PendingIntent.getBroadcast(mContext, 0, 3003cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta intentSent, PendingIntent.FLAG_UPDATE_CURRENT); 3004cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta 3005cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta // We use the same pending intent for all parts, but do not set the one shot flag. 3006cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta deliveryIntents.add(pendingIntentDelivery); 3007cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta sentIntents.add(pendingIntentSent); 3008cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta } 3009cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta 3010cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta Log.d(TAG, "sendMessage to " + msgInfo.phone); 3011cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta 3012cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta smsMng.sendMultipartTextMessage(msgInfo.phone, null, parts, sentIntents, 3013cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta deliveryIntents); 3014cd72c4dfe4db77c6df24db94f8d9a04efff7ab1dHemant Gupta } 3015fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3016fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3017fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private class SmsBroadcastReceiver extends BroadcastReceiver { 3018fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private final String[] ID_PROJECTION = new String[] { Sms._ID }; 3019326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private final Uri UPDATE_STATUS_URI = Uri.withAppendedPath(Sms.CONTENT_URI, "/status"); 3020fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3021fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void register() { 3022400eaf8761223196a18b84247b066f0201226c3bHemant Gupta Handler handler = new Handler(Looper.getMainLooper()); 3023fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3024fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie IntentFilter intentFilter = new IntentFilter(); 3025fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie intentFilter.addAction(ACTION_MESSAGE_DELIVERY); 3026326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde try{ 3027326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde intentFilter.addDataType("message/*"); 3028326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } catch (MalformedMimeTypeException e) { 3029326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.e(TAG, "Wrong mime type!!!", e); 3030326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3031326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 3032fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie mContext.registerReceiver(this, intentFilter, null, handler); 3033fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3034fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3035fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void unregister() { 3036fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie try { 3037fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie mContext.unregisterReceiver(this); 3038fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } catch (IllegalArgumentException e) { 3039fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /* do nothing */ 3040fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3041fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3042fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3043fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie @Override 3044fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void onReceive(Context context, Intent intent) { 3045fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie String action = intent.getAction(); 3046326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long handle = intent.getLongExtra(EXTRA_MESSAGE_SENT_HANDLE, -1); 3047fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie PushMsgInfo msgInfo = mPushMsgList.get(handle); 3048fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3049fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Log.d(TAG, "onReceive: action" + action); 3050fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3051fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (msgInfo == null) { 3052fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Log.d(TAG, "onReceive: no msgInfo found for handle " + handle); 3053fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie return; 3054fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3055fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 30564f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (action.equals(ACTION_MESSAGE_SENT)) { 30574f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala int result = intent.getIntExtra(EXTRA_MESSAGE_SENT_RESULT, 30584f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala Activity.RESULT_CANCELED); 30594f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala msgInfo.partsSent++; 30604f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if(result != Activity.RESULT_OK) { 30614f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala /* If just one of the parts in the message fails, we need to send the 30624f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala * entire message again 30634f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala */ 30644f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala msgInfo.failedSent = true; 30654f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 30664f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if(D) Log.d(TAG, "onReceive: msgInfo.partsSent = " + msgInfo.partsSent 30674f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala + ", msgInfo.parts = " + msgInfo.parts + " result = " + result); 30684f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 30694f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (msgInfo.partsSent == msgInfo.parts) { 30704f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala actionMessageSent(context, intent, msgInfo); 30714f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 30724f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } else if (action.equals(ACTION_MESSAGE_DELIVERY)) { 3073326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde long timestamp = intent.getLongExtra(EXTRA_MESSAGE_SENT_TIMESTAMP, 0); 3074326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int status = -1; 3075326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(msgInfo.timestamp == timestamp) { 3076326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msgInfo.partsDelivered++; 3077326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde byte[] pdu = intent.getByteArrayExtra("pdu"); 3078326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String format = intent.getStringExtra("format"); 3079326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 3080326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde SmsMessage message = SmsMessage.createFromPdu(pdu, format); 3081326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (message == null) { 3082326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.d(TAG, "actionMessageDelivery: Can't get message from pdu"); 3083326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return; 3084326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3085326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde status = message.getStatus(); 3086326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(status != 0/*0 is success*/) { 3087326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msgInfo.statusDelivered = status; 30885a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D) Log.d(TAG, "msgInfo.statusDelivered = " + status); 30890ebd4e58920add6114b1f345b7d95e0709096fe3Ajay Panicker Sms.moveMessageToFolder(mContext, msgInfo.uri, Sms.MESSAGE_TYPE_FAILED, 0); 30900ebd4e58920add6114b1f345b7d95e0709096fe3Ajay Panicker } else { 30910ebd4e58920add6114b1f345b7d95e0709096fe3Ajay Panicker Sms.moveMessageToFolder(mContext, msgInfo.uri, Sms.MESSAGE_TYPE_SENT, 0); 3092326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3093326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3094fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (msgInfo.partsDelivered == msgInfo.parts) { 3095fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie actionMessageDelivery(context, intent, msgInfo); 3096fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3097fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } else { 3098fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Log.d(TAG, "onReceive: Unknown action " + action); 3099fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3100fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3101fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 31024f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala private void actionMessageSent(Context context, Intent intent, PushMsgInfo msgInfo) { 31034f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala /* As the MESSAGE_SENT intent is forwarded from the MAP service, we use the intent 31044f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala * to carry the result, as getResult() will not return the correct value. 31054f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala */ 31064f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala boolean delete = false; 31074f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 31084f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if(D) Log.d(TAG,"actionMessageSent(): msgInfo.failedSent = " + msgInfo.failedSent); 31094f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 31104f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala msgInfo.sendInProgress = false; 31114f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 31124f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (msgInfo.failedSent == false) { 31134f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if(D) Log.d(TAG, "actionMessageSent: result OK"); 31144f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (msgInfo.transparent == 0) { 31154f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (!Sms.moveMessageToFolder(context, msgInfo.uri, 31164f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala Sms.MESSAGE_TYPE_SENT, 0)) { 31174f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala Log.w(TAG, "Failed to move " + msgInfo.uri + " to SENT"); 31184f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31194f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } else { 31204f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala delete = true; 31214f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31224f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 31234f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala Event evt = new Event(EVENT_TYPE_SENDING_SUCCESS, msgInfo.id, 31244f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala getSmsFolderName(Sms.MESSAGE_TYPE_SENT), null, mSmsType); 31254f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala sendEvent(evt); 31264f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 31274f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } else { 31284f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (msgInfo.retry == 1) { 31294f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala /* Notify failure, but keep message in outbox for resending */ 31304f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala msgInfo.resend = true; 31314f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala msgInfo.partsSent = 0; // Reset counter for the retry 31324f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala msgInfo.failedSent = false; 31334f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala Event evt = new Event(EVENT_TYPE_SENDING_FAILURE, msgInfo.id, 31344f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala getSmsFolderName(Sms.MESSAGE_TYPE_OUTBOX), null, mSmsType); 31354f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala sendEvent(evt); 31364f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } else { 31374f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (msgInfo.transparent == 0) { 31384f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (!Sms.moveMessageToFolder(context, msgInfo.uri, 31394f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala Sms.MESSAGE_TYPE_FAILED, 0)) { 31404f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala Log.w(TAG, "Failed to move " + msgInfo.uri + " to FAILED"); 31414f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31424f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } else { 31434f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala delete = true; 31444f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31454f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 31464f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala Event evt = new Event(EVENT_TYPE_SENDING_FAILURE, msgInfo.id, 31474f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala getSmsFolderName(Sms.MESSAGE_TYPE_FAILED), null, mSmsType); 31484f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala sendEvent(evt); 31494f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31504f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31514f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 31524f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala if (delete == true) { 31534f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala /* Delete from Observer message list to avoid delete notifications */ 31544f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala synchronized(getMsgListSms()) { 31554f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala getMsgListSms().remove(msgInfo.id); 31564f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31574f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 31584f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala /* Delete from DB */ 31594f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala mResolver.delete(msgInfo.uri, null, null); 31604f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31614f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala } 31624f341a3ac7cdfd7c976a9eb59117542d50458398Ashwini Munigala 3163326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde private void actionMessageDelivery(Context context, Intent intent, PushMsgInfo msgInfo) { 3164fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri messageUri = intent.getData(); 3165326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde msgInfo.sendInProgress = false; 3166fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3167fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Cursor cursor = mResolver.query(msgInfo.uri, ID_PROJECTION, null, null, null); 3168fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3169fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie try { 3170fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (cursor.moveToFirst()) { 3171fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie int messageId = cursor.getInt(0); 3172fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3173fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Uri updateUri = ContentUris.withAppendedId(UPDATE_STATUS_URI, messageId); 3174fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 31755a60e47497f21f64e6d79420dc4c56c1907df22akschulz if(D) Log.d(TAG, "actionMessageDelivery: uri=" + messageUri + ", status=" 31765a60e47497f21f64e6d79420dc4c56c1907df22akschulz + msgInfo.statusDelivered); 3177fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3178fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie ContentValues contentValues = new ContentValues(2); 3179fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3180326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde contentValues.put(Sms.STATUS, msgInfo.statusDelivered); 3181fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie contentValues.put(Inbox.DATE_SENT, System.currentTimeMillis()); 3182fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie mResolver.update(updateUri, contentValues, null, null); 3183fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } else { 3184fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Log.d(TAG, "Can't find message for status update: " + messageUri); 3185fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3186fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } finally { 31875a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (cursor != null) cursor.close(); 3188fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3189fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3190326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (msgInfo.statusDelivered == 0) { 3191326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Event evt = new Event(EVENT_TYPE_DELEVERY_SUCCESS, msgInfo.id, 31925a60e47497f21f64e6d79420dc4c56c1907df22akschulz getSmsFolderName(Sms.MESSAGE_TYPE_SENT), null, mSmsType); 3193fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie sendEvent(evt); 3194fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } else { 31955a60e47497f21f64e6d79420dc4c56c1907df22akschulz Event evt = new Event(EVENT_TYPE_DELIVERY_FAILURE, msgInfo.id, 31965a60e47497f21f64e6d79420dc4c56c1907df22akschulz getSmsFolderName(Sms.MESSAGE_TYPE_SENT), null, mSmsType); 3197fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie sendEvent(evt); 3198fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3199fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3200fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie mPushMsgList.remove(msgInfo.id); 3201fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3202fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3203fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3204725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker private class CeBroadcastReceiver extends BroadcastReceiver { 3205725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker public void register() { 3206725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker UserManager manager = UserManager.get(mContext); 3207725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker if (manager == null || manager.isUserUnlocked()) { 3208725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker mStorageUnlocked = true; 3209725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker return; 3210725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3211725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 3212725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker Handler handler = new Handler(Looper.getMainLooper()); 3213725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker IntentFilter intentFilter = new IntentFilter(); 3214725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker intentFilter.addAction(Intent.ACTION_BOOT_COMPLETED); 3215725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker mContext.registerReceiver(this, intentFilter, null, handler); 3216725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3217725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 3218725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker public void unregister() { 3219725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker try { 3220725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker mContext.unregisterReceiver(this); 3221725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } catch (IllegalArgumentException e) { 3222725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker /* do nothing */ 3223725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3224725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3225725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 3226725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker public void onReceive(Context context, Intent intent) { 3227725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker String action = intent.getAction(); 3228725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker Log.d(TAG, "onReceive: action" + action); 3229725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 3230725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker if (action.equals(Intent.ACTION_BOOT_COMPLETED)) { 3231725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker try { 3232725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker initMsgList(); 3233725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } catch (RemoteException e) { 3234725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker Log.e(TAG, "Error initializing SMS/MMS message lists."); 3235725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3236725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 3237725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker for (String folder : FOLDER_SMS_MAP.values()) { 3238725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker Event evt = new Event(EVENT_TYPE_NEW, -1, folder, mSmsType); 3239725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker sendEvent(evt); 3240725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3241725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker mStorageUnlocked = true; 3242725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker /* After unlock this BroadcastReceiver is never needed */ 3243725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker unregister(); 3244725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } else { 3245725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker Log.d(TAG, "onReceive: Unknown action " + action); 3246725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3247725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3248725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3249725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 3250ed70219e41ba68196798dcbf75b782d13fb88603kschulz /** 3251ed70219e41ba68196798dcbf75b782d13fb88603kschulz * Handle MMS sent intents in disconnected(MNS) state, where we do not need to send any 3252ed70219e41ba68196798dcbf75b782d13fb88603kschulz * notifications. 3253ed70219e41ba68196798dcbf75b782d13fb88603kschulz * @param context The context to use for provider operations 3254ed70219e41ba68196798dcbf75b782d13fb88603kschulz * @param intent The intent received 3255ed70219e41ba68196798dcbf75b782d13fb88603kschulz * @param result The result 3256ed70219e41ba68196798dcbf75b782d13fb88603kschulz */ 3257ed70219e41ba68196798dcbf75b782d13fb88603kschulz static public void actionMmsSent(Context context, Intent intent, int result, 3258ed70219e41ba68196798dcbf75b782d13fb88603kschulz Map<Long, Msg> mmsMsgList) { 3259ed70219e41ba68196798dcbf75b782d13fb88603kschulz /* 3260ed70219e41ba68196798dcbf75b782d13fb88603kschulz * if transparent: 3261ed70219e41ba68196798dcbf75b782d13fb88603kschulz * delete message and send notification(regardless of result) 3262ed70219e41ba68196798dcbf75b782d13fb88603kschulz * else 3263ed70219e41ba68196798dcbf75b782d13fb88603kschulz * Result == Success: 3264ed70219e41ba68196798dcbf75b782d13fb88603kschulz * move to sent folder (will trigger notification) 3265ed70219e41ba68196798dcbf75b782d13fb88603kschulz * Result == Fail: 3266ed70219e41ba68196798dcbf75b782d13fb88603kschulz * move to outbox (send delivery fail notification) 3267ed70219e41ba68196798dcbf75b782d13fb88603kschulz */ 3268ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(D) Log.d(TAG,"actionMmsSent()"); 3269ed70219e41ba68196798dcbf75b782d13fb88603kschulz int transparent = intent.getIntExtra(EXTRA_MESSAGE_SENT_TRANSPARENT, 0); 3270ed70219e41ba68196798dcbf75b782d13fb88603kschulz long handle = intent.getLongExtra(EXTRA_MESSAGE_SENT_HANDLE, -1); 3271ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(handle < 0) { 3272ed70219e41ba68196798dcbf75b782d13fb88603kschulz Log.w(TAG, "Intent received for an invalid handle"); 3273ed70219e41ba68196798dcbf75b782d13fb88603kschulz return; 3274ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3275ed70219e41ba68196798dcbf75b782d13fb88603kschulz ContentResolver resolver = context.getContentResolver(); 3276ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(transparent == 1) { 3277ed70219e41ba68196798dcbf75b782d13fb88603kschulz /* The specification is a bit unclear about the transparent flag. If it is set 3278ed70219e41ba68196798dcbf75b782d13fb88603kschulz * no copy of the message shall be kept in the send folder after the message 3279ed70219e41ba68196798dcbf75b782d13fb88603kschulz * was send, but in the case of a send error, it is unclear what to do. 3280ed70219e41ba68196798dcbf75b782d13fb88603kschulz * As it will not be transparent if we keep the message in any folder, 3281ed70219e41ba68196798dcbf75b782d13fb88603kschulz * we delete the message regardless of the result. 3282ed70219e41ba68196798dcbf75b782d13fb88603kschulz * If we however do have a MNS connection we need to send a notification. */ 3283ed70219e41ba68196798dcbf75b782d13fb88603kschulz Uri uri = ContentUris.withAppendedId(Mms.CONTENT_URI, handle); 3284ed70219e41ba68196798dcbf75b782d13fb88603kschulz /* Delete from observer message list to avoid delete notifications */ 3285ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(mmsMsgList != null) { 3286ed70219e41ba68196798dcbf75b782d13fb88603kschulz synchronized(mmsMsgList) { 3287ed70219e41ba68196798dcbf75b782d13fb88603kschulz mmsMsgList.remove(handle); 3288ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3289ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3290ed70219e41ba68196798dcbf75b782d13fb88603kschulz /* Delete message */ 3291ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(D) Log.d(TAG,"Transparent in use - delete"); 3292ed70219e41ba68196798dcbf75b782d13fb88603kschulz resolver.delete(uri, null, null); 3293ed70219e41ba68196798dcbf75b782d13fb88603kschulz } else if (result == Activity.RESULT_OK) { 3294ed70219e41ba68196798dcbf75b782d13fb88603kschulz /* This will trigger a notification */ 3295ed70219e41ba68196798dcbf75b782d13fb88603kschulz moveMmsToFolder(handle, resolver, Mms.MESSAGE_BOX_SENT); 3296ed70219e41ba68196798dcbf75b782d13fb88603kschulz } else { 3297ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(mmsMsgList != null) { 3298ed70219e41ba68196798dcbf75b782d13fb88603kschulz synchronized(mmsMsgList) { 3299ed70219e41ba68196798dcbf75b782d13fb88603kschulz Msg msg = mmsMsgList.get(handle); 3300ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(msg != null) { 3301ed70219e41ba68196798dcbf75b782d13fb88603kschulz msg.type=Mms.MESSAGE_BOX_OUTBOX; 3302ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3303ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3304ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3305ed70219e41ba68196798dcbf75b782d13fb88603kschulz /* Hand further retries over to the MMS application */ 3306ed70219e41ba68196798dcbf75b782d13fb88603kschulz moveMmsToFolder(handle, resolver, Mms.MESSAGE_BOX_OUTBOX); 3307ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3308ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3309ed70219e41ba68196798dcbf75b782d13fb88603kschulz 3310326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde static public void actionMessageSentDisconnected(Context context, Intent intent, int result) { 3311ed70219e41ba68196798dcbf75b782d13fb88603kschulz TYPE type = TYPE.fromOrdinal( 3312ed70219e41ba68196798dcbf75b782d13fb88603kschulz intent.getIntExtra(EXTRA_MESSAGE_SENT_MSG_TYPE, TYPE.NONE.ordinal())); 3313ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(type == TYPE.MMS) { 3314edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou actionMmsSent(context, intent, result, null); 3315ed70219e41ba68196798dcbf75b782d13fb88603kschulz } else { 3316edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou actionSmsSentDisconnected(context, intent, result); 3317ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3318ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3319ed70219e41ba68196798dcbf75b782d13fb88603kschulz 3320ed70219e41ba68196798dcbf75b782d13fb88603kschulz static public void actionSmsSentDisconnected(Context context, Intent intent, int result) { 3321edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou /* Check permission for message deletion. */ 3322edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou if ((Binder.getCallingPid() != Process.myPid()) || 3323edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou (context.checkCallingOrSelfPermission("android.Manifest.permission.WRITE_SMS") 3324edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou != PackageManager.PERMISSION_GRANTED)) { 3325edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou Log.w(TAG, "actionSmsSentDisconnected: Not allowed to delete SMS/MMS messages"); 3326edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou return; 3327edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou } 3328edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou 3329326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde boolean delete = false; 3330326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde //int retry = intent.getIntExtra(EXTRA_MESSAGE_SENT_RETRY, 0); 3331326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde int transparent = intent.getIntExtra(EXTRA_MESSAGE_SENT_TRANSPARENT, 0); 3332326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde String uriString = intent.getStringExtra(EXTRA_MESSAGE_SENT_URI); 3333326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if(uriString == null) { 3334326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde // Nothing we can do about it, just bail out 3335326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return; 3336326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3337326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Uri uri = Uri.parse(uriString); 3338326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 3339326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (result == Activity.RESULT_OK) { 3340326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.d(TAG, "actionMessageSentDisconnected: result OK"); 3341326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (transparent == 0) { 3342326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (!Sms.moveMessageToFolder(context, uri, 3343326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Sms.MESSAGE_TYPE_SENT, 0)) { 3344326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.d(TAG, "Failed to move " + uri + " to SENT"); 3345326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3346326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 3347326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde delete = true; 3348326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3349326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 3350326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /*if (retry == 1) { 3351326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde The retry feature only works while connected, else we fail the send, 33525a60e47497f21f64e6d79420dc4c56c1907df22akschulz * and move the message to failed, to let the user/app resend manually later. 3353326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else */{ 3354326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (transparent == 0) { 3355326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde if (!Sms.moveMessageToFolder(context, uri, 3356326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Sms.MESSAGE_TYPE_FAILED, 0)) { 3357326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.d(TAG, "Failed to move " + uri + " to FAILED"); 3358326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3359326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 3360326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde delete = true; 3361326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3362326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3363326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3364326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 3365edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou if (delete) { 3366326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde /* Delete from DB */ 3367326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde ContentResolver resolver = context.getContentResolver(); 3368edb6da171b8b7a6f9d4aa5a773d734a464f1ec66Miao Chou if (resolver != null) { 3369326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde resolver.delete(uri, null, null); 3370326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } else { 3371326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde Log.w(TAG, "Unable to get resolver"); 3372326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3373326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3374326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3375326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 3376fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void registerPhoneServiceStateListener() { 33775a60e47497f21f64e6d79420dc4c56c1907df22akschulz TelephonyManager tm = (TelephonyManager)mContext.getSystemService( 33785a60e47497f21f64e6d79420dc4c56c1907df22akschulz Context.TELEPHONY_SERVICE); 3379fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie tm.listen(mPhoneListener, PhoneStateListener.LISTEN_SERVICE_STATE); 3380fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3381fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3382fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void unRegisterPhoneServiceStateListener() { 33835a60e47497f21f64e6d79420dc4c56c1907df22akschulz TelephonyManager tm = (TelephonyManager)mContext.getSystemService( 33845a60e47497f21f64e6d79420dc4c56c1907df22akschulz Context.TELEPHONY_SERVICE); 3385fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie tm.listen(mPhoneListener, PhoneStateListener.LISTEN_NONE); 3386fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3387fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3388fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void resendPendingMessages() { 3389fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /* Send pending messages in outbox */ 3390fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie String where = "type = " + Sms.MESSAGE_TYPE_OUTBOX; 339189de413eba69b0c5e128a82e0ad179cec9152578Ajay Panicker UserManager manager = UserManager.get(mContext); 339289de413eba69b0c5e128a82e0ad179cec9152578Ajay Panicker if (manager == null || !manager.isUserUnlocked()) return; 33935a60e47497f21f64e6d79420dc4c56c1907df22akschulz Cursor c = mResolver.query(Sms.CONTENT_URI, SMS_PROJECTION, where, null, 33945a60e47497f21f64e6d79420dc4c56c1907df22akschulz null); 339528446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 33965a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 33975a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 33985a60e47497f21f64e6d79420dc4c56c1907df22akschulz long id = c.getLong(c.getColumnIndex(Sms._ID)); 33995a60e47497f21f64e6d79420dc4c56c1907df22akschulz String msgBody = c.getString(c.getColumnIndex(Sms.BODY)); 34005a60e47497f21f64e6d79420dc4c56c1907df22akschulz PushMsgInfo msgInfo = mPushMsgList.get(id); 34015a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (msgInfo == null || msgInfo.resend == false || 34025a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgInfo.sendInProgress == true) { 34035a60e47497f21f64e6d79420dc4c56c1907df22akschulz continue; 34045a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 34055a60e47497f21f64e6d79420dc4c56c1907df22akschulz msgInfo.sendInProgress = true; 34065a60e47497f21f64e6d79420dc4c56c1907df22akschulz sendMessage(msgInfo, msgBody); 34075a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 340828446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 340928446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 34105a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 3411fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 34125a60e47497f21f64e6d79420dc4c56c1907df22akschulz 34135a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3414fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3415fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3416fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void failPendingMessages() { 3417fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /* Move pending messages from outbox to failed */ 3418fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie String where = "type = " + Sms.MESSAGE_TYPE_OUTBOX; 34195a60e47497f21f64e6d79420dc4c56c1907df22akschulz Cursor c = mResolver.query(Sms.CONTENT_URI, SMS_PROJECTION, where, null, 34205a60e47497f21f64e6d79420dc4c56c1907df22akschulz null); 342128446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz try { 34225a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null && c.moveToFirst()) { 34235a60e47497f21f64e6d79420dc4c56c1907df22akschulz do { 34245a60e47497f21f64e6d79420dc4c56c1907df22akschulz long id = c.getLong(c.getColumnIndex(Sms._ID)); 34255a60e47497f21f64e6d79420dc4c56c1907df22akschulz String msgBody = c.getString(c.getColumnIndex(Sms.BODY)); 34265a60e47497f21f64e6d79420dc4c56c1907df22akschulz PushMsgInfo msgInfo = mPushMsgList.get(id); 34275a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (msgInfo == null || msgInfo.resend == false) { 34285a60e47497f21f64e6d79420dc4c56c1907df22akschulz continue; 34295a60e47497f21f64e6d79420dc4c56c1907df22akschulz } 34305a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.moveMessageToFolder(mContext, msgInfo.uri, 34315a60e47497f21f64e6d79420dc4c56c1907df22akschulz Sms.MESSAGE_TYPE_FAILED, 0); 34325a60e47497f21f64e6d79420dc4c56c1907df22akschulz } while (c.moveToNext()); 343328446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } 343428446a56718e80574ba7b81901fc5a1368bf5839Kim Schulz } finally { 34355a60e47497f21f64e6d79420dc4c56c1907df22akschulz if (c != null) c.close(); 3436fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 34375a60e47497f21f64e6d79420dc4c56c1907df22akschulz 3438fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3439fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3440fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private void removeDeletedMessages() { 3441fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie /* Remove messages from virtual "deleted" folder (thread_id -1) */ 3442326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mResolver.delete(Sms.CONTENT_URI, 3443fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie "thread_id = " + DELETED_THREAD_ID, null); 3444fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3445fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3446fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie private PhoneStateListener mPhoneListener = new PhoneStateListener() { 3447fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie @Override 3448fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void onServiceStateChanged(ServiceState serviceState) { 3449fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie Log.d(TAG, "Phone service state change: " + serviceState.getState()); 3450fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie if (serviceState.getState() == ServiceState.STATE_IN_SERVICE) { 3451fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie resendPendingMessages(); 3452fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3453fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3454fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie }; 3455fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3456fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void init() { 3457b6fdf260e28b4eb6b5cdb19f53710c0470ffcad2Hemant Gupta if (mSmsBroadcastReceiver != null) { 3458b6fdf260e28b4eb6b5cdb19f53710c0470ffcad2Hemant Gupta mSmsBroadcastReceiver.register(); 3459b6fdf260e28b4eb6b5cdb19f53710c0470ffcad2Hemant Gupta } 3460725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 3461725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker if (mCeBroadcastReceiver != null) { 3462725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker mCeBroadcastReceiver.register(); 3463725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker } 3464725c70cfb004690027ded41f080bfe1bb17d2285Ajay Panicker 3465fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie registerPhoneServiceStateListener(); 3466326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mInitialized = true; 3467fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3468fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie 3469fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie public void deinit() { 3470326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde mInitialized = false; 3471326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde unregisterObserver(); 3472b6fdf260e28b4eb6b5cdb19f53710c0470ffcad2Hemant Gupta if (mSmsBroadcastReceiver != null) { 3473b6fdf260e28b4eb6b5cdb19f53710c0470ffcad2Hemant Gupta mSmsBroadcastReceiver.unregister(); 3474b6fdf260e28b4eb6b5cdb19f53710c0470ffcad2Hemant Gupta } 3475fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie unRegisterPhoneServiceStateListener(); 3476fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie failPendingMessages(); 3477fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie removeDeletedMessages(); 3478fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie } 3479326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde 3480326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde public boolean handleSmsSendIntent(Context context, Intent intent){ 3481ed70219e41ba68196798dcbf75b782d13fb88603kschulz TYPE type = TYPE.fromOrdinal( 3482ed70219e41ba68196798dcbf75b782d13fb88603kschulz intent.getIntExtra(EXTRA_MESSAGE_SENT_MSG_TYPE, TYPE.NONE.ordinal())); 3483ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(type == TYPE.MMS) { 3484ed70219e41ba68196798dcbf75b782d13fb88603kschulz return handleMmsSendIntent(context, intent); 3485ed70219e41ba68196798dcbf75b782d13fb88603kschulz } else { 3486ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(mInitialized) { 3487ed70219e41ba68196798dcbf75b782d13fb88603kschulz mSmsBroadcastReceiver.onReceive(context, intent); 3488ed70219e41ba68196798dcbf75b782d13fb88603kschulz return true; 3489ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3490326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3491326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde return false; 3492326b5e610063ac24c0ba467ac585bd4c7f618a67Casper Bonde } 3493ed70219e41ba68196798dcbf75b782d13fb88603kschulz 3494ed70219e41ba68196798dcbf75b782d13fb88603kschulz public boolean handleMmsSendIntent(Context context, Intent intent){ 3495ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(D) Log.w(TAG, "handleMmsSendIntent()"); 3496ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(mMnsClient.isConnected() == false) { 3497ed70219e41ba68196798dcbf75b782d13fb88603kschulz // No need to handle notifications, just use default handling 3498ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(D) Log.w(TAG, "MNS not connected - use static handling"); 3499ed70219e41ba68196798dcbf75b782d13fb88603kschulz return false; 3500ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3501ed70219e41ba68196798dcbf75b782d13fb88603kschulz long handle = intent.getLongExtra(EXTRA_MESSAGE_SENT_HANDLE, -1); 3502ed70219e41ba68196798dcbf75b782d13fb88603kschulz int result = intent.getIntExtra(EXTRA_MESSAGE_SENT_RESULT, Activity.RESULT_CANCELED); 3503ed70219e41ba68196798dcbf75b782d13fb88603kschulz actionMmsSent(context, intent, result, getMsgListMms()); 3504ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(handle < 0) { 3505ed70219e41ba68196798dcbf75b782d13fb88603kschulz Log.w(TAG, "Intent received for an invalid handle"); 3506ed70219e41ba68196798dcbf75b782d13fb88603kschulz return true; 3507ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3508ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(result != Activity.RESULT_OK) { 3509ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(mObserverRegistered) { 3510ed70219e41ba68196798dcbf75b782d13fb88603kschulz Event evt = new Event(EVENT_TYPE_SENDING_FAILURE, handle, 3511ed70219e41ba68196798dcbf75b782d13fb88603kschulz getMmsFolderName(Mms.MESSAGE_BOX_OUTBOX), null, TYPE.MMS); 3512ed70219e41ba68196798dcbf75b782d13fb88603kschulz sendEvent(evt); 3513ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3514ed70219e41ba68196798dcbf75b782d13fb88603kschulz } else { 3515ed70219e41ba68196798dcbf75b782d13fb88603kschulz int transparent = intent.getIntExtra(EXTRA_MESSAGE_SENT_TRANSPARENT, 0); 3516ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(transparent != 0) { 3517ed70219e41ba68196798dcbf75b782d13fb88603kschulz if(mObserverRegistered) { 3518ed70219e41ba68196798dcbf75b782d13fb88603kschulz Event evt = new Event(EVENT_TYPE_SENDING_SUCCESS, handle, 3519ed70219e41ba68196798dcbf75b782d13fb88603kschulz getMmsFolderName(Mms.MESSAGE_BOX_OUTBOX), null, TYPE.MMS); 3520ed70219e41ba68196798dcbf75b782d13fb88603kschulz sendEvent(evt); 3521ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3522ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3523ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3524ed70219e41ba68196798dcbf75b782d13fb88603kschulz return true; 3525ed70219e41ba68196798dcbf75b782d13fb88603kschulz } 3526ed70219e41ba68196798dcbf75b782d13fb88603kschulz 3527fd6603b8bf9ed72dcc8bd59aaef3209251b6e17cMatthew Xie} 3528