Conversation.java revision 440fe79194314b25ef5829702494735ce2f1e2e8
1/** 2 * Copyright (c) 2012, Google Inc. 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.android.mail.providers; 18 19import com.google.common.collect.ImmutableList; 20 21import android.database.Cursor; 22import android.net.Uri; 23import android.os.Parcel; 24import android.os.Parcelable; 25import android.text.TextUtils; 26 27import java.util.Collection; 28import java.util.Collections; 29 30public class Conversation implements Parcelable { 31 public static final int NO_POSITION = -1; 32 33 public long id; 34 public Uri uri; 35 public String subject; 36 public long dateMs; 37 public String snippet; 38 public boolean hasAttachments; 39 public Uri messageListUri; 40 public String senders; 41 public int numMessages; 42 public int numDrafts; 43 public int sendingState; 44 public int priority; 45 public boolean read; 46 public boolean starred; 47 public String folderList; 48 public String rawFolders; 49 public int convFlags; 50 public int personalLevel; 51 public boolean spam; 52 public boolean muted; 53 public int color; 54 55 // Used within the UI to indicate the adapter position of this conversation 56 public transient int position; 57 // Used within the UI to indicate that a Conversation should be removed from the 58 // ConversationCursor when executing an update, e.g. the the Conversation is no longer 59 // in the ConversationList for the current folder, that is it's now in some other folder(s) 60 public transient boolean localDeleteOnUpdate; 61 62 // Constituents of convFlags below 63 // Flag indicating that the item has been deleted, but will continue being shown in the list 64 // Delete/Archive of a mostly-dead item will NOT propagate the delete/archive, but WILL remove 65 // the item from the cursor 66 public static final int FLAG_MOSTLY_DEAD = 1 << 0; 67 68 /** An immutable, empty conversation list */ 69 public static final Collection<Conversation> EMPTY = Collections.emptyList(); 70 71 @Override 72 public int describeContents() { 73 return 0; 74 } 75 76 @Override 77 public void writeToParcel(Parcel dest, int flags) { 78 dest.writeLong(id); 79 dest.writeParcelable(uri, flags); 80 dest.writeString(subject); 81 dest.writeLong(dateMs); 82 dest.writeString(snippet); 83 dest.writeByte(hasAttachments ? (byte) 1 : 0); 84 dest.writeParcelable(messageListUri, 0); 85 dest.writeString(senders); 86 dest.writeInt(numMessages); 87 dest.writeInt(numDrafts); 88 dest.writeInt(sendingState); 89 dest.writeInt(priority); 90 dest.writeByte(read ? (byte) 1 : 0); 91 dest.writeByte(starred ? (byte) 1 : 0); 92 dest.writeString(folderList); 93 dest.writeString(rawFolders); 94 dest.writeInt(convFlags); 95 dest.writeInt(personalLevel); 96 dest.writeInt(spam ? 1 : 0); 97 dest.writeInt(muted ? 1 : 0); 98 dest.writeInt(color); 99 } 100 101 private Conversation(Parcel in) { 102 id = in.readLong(); 103 uri = in.readParcelable(null); 104 subject = in.readString(); 105 dateMs = in.readLong(); 106 snippet = in.readString(); 107 hasAttachments = (in.readByte() != 0); 108 messageListUri = in.readParcelable(null); 109 senders = in.readString(); 110 numMessages = in.readInt(); 111 numDrafts = in.readInt(); 112 sendingState = in.readInt(); 113 priority = in.readInt(); 114 read = (in.readByte() != 0); 115 starred = (in.readByte() != 0); 116 folderList = in.readString(); 117 rawFolders = in.readString(); 118 convFlags = in.readInt(); 119 personalLevel = in.readInt(); 120 spam = in.readInt() != 0; 121 muted = in.readInt() != 0; 122 color = in.readInt(); 123 position = NO_POSITION; 124 localDeleteOnUpdate = false; 125 } 126 127 @Override 128 public String toString() { 129 return "[conversation id=" + id + "]"; 130 } 131 132 public static final Creator<Conversation> CREATOR = new Creator<Conversation>() { 133 134 @Override 135 public Conversation createFromParcel(Parcel source) { 136 return new Conversation(source); 137 } 138 139 @Override 140 public Conversation[] newArray(int size) { 141 return new Conversation[size]; 142 } 143 144 }; 145 146 public static final Uri MOVE_CONVERSATIONS_URI = Uri.parse("content://moveconversations"); 147 148 public Conversation(Cursor cursor) { 149 if (cursor != null) { 150 id = cursor.getLong(UIProvider.CONVERSATION_ID_COLUMN); 151 uri = Uri.parse(cursor.getString(UIProvider.CONVERSATION_URI_COLUMN)); 152 dateMs = cursor.getLong(UIProvider.CONVERSATION_DATE_RECEIVED_MS_COLUMN); 153 subject = cursor.getString(UIProvider.CONVERSATION_SUBJECT_COLUMN); 154 // Don't allow null subject 155 if (subject == null) { 156 subject = ""; 157 } 158 snippet = cursor.getString(UIProvider.CONVERSATION_SNIPPET_COLUMN); 159 hasAttachments = cursor.getInt(UIProvider.CONVERSATION_HAS_ATTACHMENTS_COLUMN) != 0; 160 String messageList = cursor 161 .getString(UIProvider.CONVERSATION_MESSAGE_LIST_URI_COLUMN); 162 messageListUri = !TextUtils.isEmpty(messageList) ? Uri.parse(messageList) : null; 163 senders = cursor.getString(UIProvider.CONVERSATION_SENDER_INFO_COLUMN); 164 numMessages = cursor.getInt(UIProvider.CONVERSATION_NUM_MESSAGES_COLUMN); 165 numDrafts = cursor.getInt(UIProvider.CONVERSATION_NUM_DRAFTS_COLUMN); 166 sendingState = cursor.getInt(UIProvider.CONVERSATION_SENDING_STATE_COLUMN); 167 priority = cursor.getInt(UIProvider.CONVERSATION_PRIORITY_COLUMN); 168 read = cursor.getInt(UIProvider.CONVERSATION_READ_COLUMN) != 0; 169 starred = cursor.getInt(UIProvider.CONVERSATION_STARRED_COLUMN) != 0; 170 folderList = cursor.getString(UIProvider.CONVERSATION_FOLDER_LIST_COLUMN); 171 rawFolders = cursor.getString(UIProvider.CONVERSATION_RAW_FOLDERS_COLUMN); 172 convFlags = cursor.getInt(UIProvider.CONVERSATION_FLAGS_COLUMN); 173 personalLevel = cursor.getInt(UIProvider.CONVERSATION_PERSONAL_LEVEL_COLUMN); 174 spam = cursor.getInt(UIProvider.CONVERSATION_IS_SPAM_COLUMN) != 0; 175 muted = cursor.getInt(UIProvider.CONVERSATION_MUTED_COLUMN) != 0; 176 color = cursor.getInt(UIProvider.CONVERSATION_COLOR_COLUMN); 177 position = NO_POSITION; 178 localDeleteOnUpdate = false; 179 } 180 } 181 182 public Conversation() { 183 } 184 185 public static Conversation create(long id, Uri uri, String subject, long dateMs, 186 String snippet, boolean hasAttachment, Uri messageListUri, String senders, 187 int numMessages, int numDrafts, int sendingState, int priority, boolean read, 188 boolean starred, String folderList, String rawFolders, int convFlags, 189 int personalLevel, boolean spam, boolean muted) { 190 191 final Conversation conversation = new Conversation(); 192 193 conversation.id = id; 194 conversation.uri = uri; 195 conversation.subject = subject; 196 conversation.dateMs = dateMs; 197 conversation.snippet = snippet; 198 conversation.hasAttachments = hasAttachment; 199 conversation.messageListUri = messageListUri; 200 conversation.senders = senders; 201 conversation.numMessages = numMessages; 202 conversation.numDrafts = numDrafts; 203 conversation.sendingState = sendingState; 204 conversation.priority = priority; 205 conversation.read = read; 206 conversation.starred = starred; 207 conversation.folderList = folderList; 208 conversation.rawFolders = rawFolders; 209 conversation.convFlags = convFlags; 210 conversation.personalLevel = personalLevel; 211 conversation.spam = spam; 212 conversation.muted = muted; 213 conversation.color = 0; 214 return conversation; 215 } 216 217 @Override 218 public boolean equals(Object o) { 219 if (o instanceof Conversation) { 220 Conversation conv = (Conversation)o; 221 return conv.uri.equals(uri); 222 } 223 return false; 224 } 225 226 @Override 227 public int hashCode() { 228 return uri.hashCode(); 229 } 230 231 /** 232 * Get if this conversation is marked as high priority. 233 */ 234 public boolean isImportant() { 235 return priority == UIProvider.ConversationPriority.IMPORTANT; 236 } 237 238 /** 239 * Get if this conversation is mostly dead 240 */ 241 public boolean isMostlyDead() { 242 return (convFlags & FLAG_MOSTLY_DEAD) != 0; 243 } 244 245 /** 246 * Returns a collection of a single conversation. This method always returns a valid collection 247 * even if the input conversation is null. 248 * @param in a conversation, possibly null. 249 * @return a collection of the conversation. 250 */ 251 public static Collection<Conversation> listOf(Conversation in) { 252 final Collection<Conversation> target = (in == null) ? EMPTY : ImmutableList.of(in); 253 return target; 254 } 255}