blob: 0abc99821c1e591b47149b4ba4a37f907de6e2cc [file] [log] [blame]
Selim Cinek9acd6732018-03-23 16:39:02 -07001/*
2 * Copyright (C) 2018 The Android Open Source Project
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 android.app;
18
19import android.annotation.NonNull;
20import android.annotation.Nullable;
21import android.graphics.drawable.Icon;
22import android.os.Parcel;
23import android.os.Parcelable;
24
Beverlye98937a2018-11-15 10:18:57 -050025import java.util.Objects;
26
Selim Cinek9acd6732018-03-23 16:39:02 -070027/**
28 * Provides an immutable reference to an entity that appears repeatedly on different surfaces of the
29 * platform. For example, this could represent the sender of a message.
30 */
31public final class Person implements Parcelable {
32
33 @Nullable private CharSequence mName;
34 @Nullable private Icon mIcon;
35 @Nullable private String mUri;
36 @Nullable private String mKey;
37 private boolean mIsBot;
38 private boolean mIsImportant;
39
40 private Person(Parcel in) {
41 mName = in.readCharSequence();
42 if (in.readInt() != 0) {
43 mIcon = Icon.CREATOR.createFromParcel(in);
44 }
45 mUri = in.readString();
46 mKey = in.readString();
47 mIsImportant = in.readBoolean();
48 mIsBot = in.readBoolean();
49 }
50
51 private Person(Builder builder) {
52 mName = builder.mName;
53 mIcon = builder.mIcon;
54 mUri = builder.mUri;
55 mKey = builder.mKey;
56 mIsBot = builder.mIsBot;
57 mIsImportant = builder.mIsImportant;
58 }
59
60 /** Creates and returns a new {@link Builder} initialized with this Person's data. */
61 public Builder toBuilder() {
62 return new Builder(this);
63 }
64
65 /**
66 * @return the uri provided for this person or {@code null} if no Uri was provided.
67 */
68 @Nullable
69 public String getUri() {
70 return mUri;
71 }
72
73 /**
74 * @return the name provided for this person or {@code null} if no name was provided.
75 */
76 @Nullable
77 public CharSequence getName() {
78 return mName;
79 }
80
81 /**
82 * @return the icon provided for this person or {@code null} if no icon was provided.
83 */
84 @Nullable
85 public Icon getIcon() {
86 return mIcon;
87 }
88
89 /**
90 * @return the key provided for this person or {@code null} if no key was provided.
91 */
92 @Nullable
93 public String getKey() {
94 return mKey;
95 }
96
97 /**
98 * @return whether this Person is a machine.
99 */
100 public boolean isBot() {
101 return mIsBot;
102 }
103
104 /**
105 * @return whether this Person is important.
106 */
107 public boolean isImportant() {
108 return mIsImportant;
109 }
110
111 /**
112 * @return the URI associated with this person, or "name:mName" otherwise
113 * @hide
114 */
115 public String resolveToLegacyUri() {
116 if (mUri != null) {
117 return mUri;
118 }
119 if (mName != null) {
120 return "name:" + mName;
121 }
122 return "";
123 }
124
125 @Override
Beverlye98937a2018-11-15 10:18:57 -0500126 public boolean equals(Object obj) {
127 if (obj instanceof Person) {
128 final Person other = (Person) obj;
129 return Objects.equals(mName, other.mName)
Tony Makf99ee172018-11-23 12:14:39 +0000130 && (mIcon == null ? other.mIcon == null :
131 (other.mIcon != null && mIcon.sameAs(other.mIcon)))
Beverlye98937a2018-11-15 10:18:57 -0500132 && Objects.equals(mUri, other.mUri)
133 && Objects.equals(mKey, other.mKey)
134 && mIsBot == other.mIsBot
135 && mIsImportant == other.mIsImportant;
136 }
137 return false;
138 }
139
140 @Override
141 public int hashCode() {
142 return Objects.hash(mName, mIcon, mUri, mKey, mIsBot, mIsImportant);
143 }
144
145 @Override
Selim Cinek9acd6732018-03-23 16:39:02 -0700146 public int describeContents() {
147 return 0;
148 }
149
150 @Override
151 public void writeToParcel(Parcel dest, @WriteFlags int flags) {
152 dest.writeCharSequence(mName);
153 if (mIcon != null) {
154 dest.writeInt(1);
155 mIcon.writeToParcel(dest, 0);
156 } else {
157 dest.writeInt(0);
158 }
159 dest.writeString(mUri);
160 dest.writeString(mKey);
161 dest.writeBoolean(mIsImportant);
162 dest.writeBoolean(mIsBot);
163 }
164
165 /** Builder for the immutable {@link Person} class. */
166 public static class Builder {
167 @Nullable private CharSequence mName;
168 @Nullable private Icon mIcon;
169 @Nullable private String mUri;
170 @Nullable private String mKey;
171 private boolean mIsBot;
172 private boolean mIsImportant;
173
174 /** Creates a new, empty {@link Builder}. */
175 public Builder() {
176 }
177
178 private Builder(Person person) {
179 mName = person.mName;
180 mIcon = person.mIcon;
181 mUri = person.mUri;
182 mKey = person.mKey;
183 mIsBot = person.mIsBot;
184 mIsImportant = person.mIsImportant;
185 }
186
187 /**
188 * Give this person a name.
189 *
190 * @param name the name of this person.
191 */
192 @NonNull
193 public Person.Builder setName(@Nullable CharSequence name) {
194 this.mName = name;
195 return this;
196 }
197
198 /**
199 * Add an icon for this person.
200 * <br />
201 * The system will prefer this icon over any images that are resolved from the URI.
202 *
203 * @param icon the icon of the person.
204 */
205 @NonNull
206 public Person.Builder setIcon(@Nullable Icon icon) {
207 this.mIcon = icon;
208 return this;
209 }
210
211 /**
212 * Set a URI associated with this person.
213 *
214 * <P>
215 * The person should be specified by the {@code String} representation of a
216 * {@link android.provider.ContactsContract.Contacts#CONTENT_LOOKUP_URI}.
217 * </P>
218 *
219 * <P>The system will also attempt to resolve {@code mailto:} and {@code tel:} schema
220 * URIs. The path part of these URIs must exist in the contacts database, in the
221 * appropriate column, or the reference will be discarded as invalid. Telephone schema
222 * URIs will be resolved by {@link android.provider.ContactsContract.PhoneLookup}.
223 * </P>
224 *
225 * @param uri a URI for the person.
226 */
227 @NonNull
228 public Person.Builder setUri(@Nullable String uri) {
229 mUri = uri;
230 return this;
231 }
232
233 /**
234 * Add a key to this person in order to uniquely identify it.
235 * This is especially useful if the name doesn't uniquely identify this person or if the
236 * display name is a short handle of the actual name.
237 *
238 * <P>If no key is provided, the name serves as the key for the purpose of
239 * identification.</P>
240 *
241 * @param key the key that uniquely identifies this person.
242 */
243 @NonNull
244 public Person.Builder setKey(@Nullable String key) {
245 mKey = key;
246 return this;
247 }
248
249 /**
250 * Sets whether this is an important person. Use this method to denote users who frequently
251 * interact with the user of this device when {@link #setUri(String)} isn't provided with
252 * {@link android.provider.ContactsContract.Contacts#CONTENT_LOOKUP_URI}, and instead with
253 * the {@code mailto:} or {@code tel:} schemas.
254 *
255 * @param isImportant {@code true} if this is an important person, {@code false} otherwise.
256 */
257 @NonNull
258 public Person.Builder setImportant(boolean isImportant) {
259 mIsImportant = isImportant;
260 return this;
261 }
262
263 /**
264 * Sets whether this person is a machine rather than a human.
265 *
266 * @param isBot {@code true} if this person is a machine, {@code false} otherwise.
267 */
268 @NonNull
269 public Person.Builder setBot(boolean isBot) {
270 mIsBot = isBot;
271 return this;
272 }
273
274 /** Creates and returns the {@link Person} this builder represents. */
275 @NonNull
276 public Person build() {
277 return new Person(this);
278 }
279 }
280
281 public static final Creator<Person> CREATOR = new Creator<Person>() {
282 @Override
283 public Person createFromParcel(Parcel in) {
284 return new Person(in);
285 }
286
287 @Override
288 public Person[] newArray(int size) {
289 return new Person[size];
290 }
291 };
292}