BluetoothMapConvoContactElement.java revision eb7b90f5b93db1230a5b64caa3d8d05a642e33a6
1/*
2* Copyright (C) 2015 Samsung System LSI
3* Licensed under the Apache License, Version 2.0 (the "License");
4* you may not use this file except in compliance with the License.
5* You may obtain a copy of the License at
6*
7*      http://www.apache.org/licenses/LICENSE-2.0
8*
9* Unless required by applicable law or agreed to in writing, software
10* distributed under the License is distributed on an "AS IS" BASIS,
11* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12* See the License for the specific language governing permissions and
13* limitations under the License.
14*/
15package com.android.bluetooth.map;
16
17import java.io.IOException;
18import java.io.UnsupportedEncodingException;
19import java.text.ParseException;
20import java.text.SimpleDateFormat;
21import java.util.Date;
22
23import org.xmlpull.v1.XmlPullParser;
24import org.xmlpull.v1.XmlPullParserException;
25import org.xmlpull.v1.XmlSerializer;
26
27import android.util.Log;
28
29import com.android.bluetooth.SignedLongLong;
30
31public class BluetoothMapConvoContactElement
32    implements Comparable<BluetoothMapConvoContactElement> {
33
34    public static final long CONTACT_ID_TYPE_SMS_MMS = 1;
35    public static final long CONTACT_ID_TYPE_EMAIL   = 2;
36    public static final long CONTACT_ID_TYPE_IM      = 3;
37
38    private static final String XML_ATT_PRIORITY = "priority";
39    private static final String XML_ATT_PRESENCE_STATUS = "presence_status";
40    private static final String XML_ATT_PRESENCE_AVAILABILITY = "presence_availability";
41    private static final String XML_ATT_X_BT_UID = "x_bt_uid";
42    private static final String XML_ATT_LAST_ACTIVITY = "last_activity";
43    private static final String XML_ATT_CHAT_STATE = "chat_state";
44    private static final String XML_ATT_NAME = "name";
45    private static final String XML_ATT_DISPLAY_NAME = "display_name";
46    private static final String XML_ATT_UCI = "x_bt_uci";
47    protected static final String XML_TAG_CONVOCONTACT = "convocontact";
48    private static final String TAG = "BluetoothMapConvoContactElement";
49    private static final boolean D = false;
50    private static final boolean V = false;
51
52    private String mUci = null;
53    private String mName = null;
54    private String mDisplayName = null;
55    private String mPresenceStatus = null;
56    private int mPresenceAvailability = -1;
57    private int mPriority = -1;
58    private long mLastActivity = -1;
59    private SignedLongLong mBtUid = null;
60    private int mChatState = -1;
61
62    public static BluetoothMapConvoContactElement createFromMapContact(MapContact contact,
63            String address) {
64        BluetoothMapConvoContactElement newElement = new BluetoothMapConvoContactElement();
65        newElement.mUci = address;
66        // TODO: For now we use the ID as BT-UID
67        newElement.mBtUid = new SignedLongLong(contact.getId(),0);
68        newElement.mDisplayName = contact.getName();
69        return newElement;
70    }
71
72    public BluetoothMapConvoContactElement(String uci, String name, String displayName,
73            String presenceStatus, int presenceAvailability, long lastActivity, int chatState,
74            int priority, String btUid) {
75        this.mUci = uci;
76        this.mName = name;
77        this.mDisplayName = displayName;
78        this.mPresenceStatus = presenceStatus;
79        this.mPresenceAvailability = presenceAvailability;
80        this.mLastActivity = lastActivity;
81        this.mChatState = chatState;
82        this.mPresenceStatus = presenceStatus;
83        this.mPriority = priority;
84        if(btUid != null) {
85            try {
86                this.mBtUid = SignedLongLong.fromString(btUid);
87            } catch (UnsupportedEncodingException e) {
88                Log.w(TAG,e);
89            }
90        }
91    }
92
93    public BluetoothMapConvoContactElement() {
94        // TODO Auto-generated constructor stub
95    }
96
97    public String getPresenceStatus() {
98        return mPresenceStatus;
99    }
100
101    public String getDisplayName() {
102        return mDisplayName;
103    }
104
105    public void setDisplayName(String displayName) {
106        this.mDisplayName = displayName;
107    }
108
109    public void setPresenceStatus(String presenceStatus) {
110        this.mPresenceStatus = presenceStatus;
111    }
112
113    public int getPresenceAvailability() {
114        return mPresenceAvailability;
115    }
116
117    public void setPresenceAvailability(int presenceAvailability) {
118        this.mPresenceAvailability = presenceAvailability;
119    }
120
121    public int getPriority() {
122        return mPriority;
123    }
124
125    public void setPriority(int priority) {
126        this.mPriority = priority;
127    }
128
129    public String getName() {
130        return mName;
131    }
132
133    public void setName(String name) {
134        this.mName = name;
135    }
136
137    public String getBtUid() {
138        return mBtUid.toHexString();
139    }
140
141    public void setBtUid(SignedLongLong btUid) {
142        this.mBtUid = btUid;
143    }
144
145    public int getChatState() {
146        return mChatState;
147    }
148
149    public void setChatState(int chatState) {
150        this.mChatState = chatState;
151    }
152
153    public void setChatState(String chatState) {
154        this.mChatState = Integer.valueOf(chatState);
155    }
156
157
158    public String getLastActivityString() {
159        SimpleDateFormat format = new SimpleDateFormat("yyyyMMdd'T'HHmmss");
160        Date date = new Date(mLastActivity);
161        return format.format(date); // Format to YYYYMMDDTHHMMSS local time
162    }
163
164    public void setLastActivity(long dateTime) {
165        this.mLastActivity = dateTime;
166    }
167
168    public void setLastActivity(String lastActivity) throws ParseException {
169        SimpleDateFormat format = new SimpleDateFormat("yyyyMMdd'T'HHmmss");
170        Date date = format.parse(lastActivity);
171        this.mLastActivity = date.getTime();
172    }
173
174    public void setContactId(String uci) {
175        this.mUci = uci;
176    }
177
178    public String getContactId(){
179        return mUci;
180    }
181
182    public int compareTo(BluetoothMapConvoContactElement e) {
183        if (this.mLastActivity < e.mLastActivity) {
184            return 1;
185        } else if (this.mLastActivity > e.mLastActivity) {
186            return -1;
187        } else {
188            return 0;
189        }
190    }
191
192    /* Encode the MapConvoContactElement into the StringBuilder reference.
193     * Here we have taken the choice not to report empty attributes, to reduce the
194     * amount of data to be transfered over BT. */
195    public void encode(XmlSerializer xmlConvoElement)
196            throws IllegalArgumentException, IllegalStateException, IOException
197    {
198            // construct the XML tag for a single contact in the convolisting element.
199            xmlConvoElement.startTag(null, XML_TAG_CONVOCONTACT);
200            if(mUci != null) {
201                xmlConvoElement.attribute(null, XML_ATT_UCI, mUci);
202            }
203            if(mDisplayName != null) {
204                xmlConvoElement.attribute(null, XML_ATT_DISPLAY_NAME,
205                            BluetoothMapUtils.stripInvalidChars(mDisplayName));
206            }
207            if(mName != null) {
208                xmlConvoElement.attribute(null, XML_ATT_NAME,
209                        BluetoothMapUtils.stripInvalidChars(mName));
210            }
211            if(mChatState != -1) {
212                xmlConvoElement.attribute(null, XML_ATT_CHAT_STATE, String.valueOf(mChatState));
213            }
214            if(mLastActivity != -1) {
215                xmlConvoElement.attribute(null, XML_ATT_LAST_ACTIVITY,
216                        this.getLastActivityString());
217            }
218            if(mBtUid != null) {
219                xmlConvoElement.attribute(null, XML_ATT_X_BT_UID, mBtUid.toHexString());
220            }
221            if(mPresenceAvailability != -1) {
222                xmlConvoElement.attribute(null,  XML_ATT_PRESENCE_AVAILABILITY,
223                        String.valueOf(mPresenceAvailability));
224            }
225            if(mPresenceStatus != null) {
226                xmlConvoElement.attribute(null,  XML_ATT_PRESENCE_STATUS, mPresenceStatus);
227            }
228            if(mPriority != -1) {
229                xmlConvoElement.attribute(null, XML_ATT_PRIORITY, String.valueOf(mPriority));
230            }
231
232            xmlConvoElement.endTag(null, XML_TAG_CONVOCONTACT);
233    }
234
235
236    /**
237     * Call this function to create a BluetoothMapConvoContactElement. Will consume the end-tag.
238     * @param parser must point into XML_TAG_CONVERSATION tag, hence attributes can be read.
239     * @return
240     * @throws IOException
241     * @throws XmlPullParserException
242     */
243    public static BluetoothMapConvoContactElement createFromXml(XmlPullParser parser)
244            throws ParseException, XmlPullParserException, IOException {
245        int count = parser.getAttributeCount();
246        BluetoothMapConvoContactElement newElement;
247        if(count<1) {
248            throw new IllegalArgumentException(XML_TAG_CONVOCONTACT +
249                    " is not decorated with attributes");
250        }
251        newElement = new BluetoothMapConvoContactElement();
252        for (int i = 0; i<count; i++) {
253            String attributeName = parser.getAttributeName(i).trim();
254            String attributeValue = parser.getAttributeValue(i);
255            if(attributeName.equalsIgnoreCase(XML_ATT_UCI)) {
256                newElement.mUci = attributeValue;
257            } else if(attributeName.equalsIgnoreCase(XML_ATT_NAME)) {
258                newElement.mName = attributeValue;
259            } else if(attributeName.equalsIgnoreCase(XML_ATT_DISPLAY_NAME)) {
260                newElement.mDisplayName = attributeValue;
261            } else if(attributeName.equalsIgnoreCase(XML_ATT_CHAT_STATE)) {
262                newElement.setChatState(attributeValue);
263            } else if(attributeName.equalsIgnoreCase(XML_ATT_LAST_ACTIVITY)) {
264                newElement.setLastActivity(attributeValue);
265            } else if(attributeName.equalsIgnoreCase(XML_ATT_X_BT_UID)) {
266                newElement.setBtUid(SignedLongLong.fromString(attributeValue));
267            } else if(attributeName.equalsIgnoreCase(XML_ATT_PRESENCE_AVAILABILITY)) {
268                newElement.mPresenceAvailability = Integer.parseInt(attributeValue);
269            } else if(attributeName.equalsIgnoreCase(XML_ATT_PRESENCE_STATUS)) {
270                newElement.setPresenceStatus(attributeValue);
271            } else if(attributeName.equalsIgnoreCase(XML_ATT_PRIORITY)) {
272                newElement.setPriority(Integer.parseInt(attributeValue));
273            } else {
274                if(D) Log.i(TAG,"Unknown XML attribute: " + parser.getAttributeName(i));
275            }
276        }
277        parser.nextTag(); // Consume the end-tag
278        return newElement;
279    }
280
281    @Override
282    public boolean equals(Object obj) {
283        if (this == obj) {
284            return true;
285        }
286        if (obj == null) {
287            return false;
288        }
289        if (getClass() != obj.getClass()) {
290            return false;
291        }
292        BluetoothMapConvoContactElement other = (BluetoothMapConvoContactElement) obj;
293/*      As we use equals only for test, we don't compare auto assigned values
294 *      if (mBtUid == null) {
295            if (other.mBtUid != null) {
296                return false;
297            }
298        } else if (!mBtUid.equals(other.mBtUid)) {
299            return false;
300        }*/
301        if (mChatState != other.mChatState) {
302            return false;
303        }
304        if (mDisplayName == null) {
305            if (other.mDisplayName != null) {
306                return false;
307            }
308        } else if (!mDisplayName.equals(other.mDisplayName)) {
309            return false;
310        }
311/*      As we use equals only for test, we don't compare auto assigned values
312 *      if (mId == null) {
313            if (other.mId != null) {
314                return false;
315            }
316        } else if (!mId.equals(other.mId)) {
317            return false;
318        }*/
319        if (mLastActivity != other.mLastActivity) {
320            return false;
321        }
322        if (mName == null) {
323            if (other.mName != null) {
324                return false;
325            }
326        } else if (!mName.equals(other.mName)) {
327            return false;
328        }
329        if (mPresenceAvailability != other.mPresenceAvailability) {
330            return false;
331        }
332        if (mPresenceStatus == null) {
333            if (other.mPresenceStatus != null) {
334                return false;
335            }
336        } else if (!mPresenceStatus.equals(other.mPresenceStatus)) {
337            return false;
338        }
339        if (mPriority != other.mPriority) {
340            return false;
341        }
342        return true;
343    }
344
345}
346
347
348