1 /* 2 * Copyright (C) 2007 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 17 package android.location; 18 19 import java.util.HashMap; 20 import java.util.Locale; 21 import java.util.Map; 22 import java.util.Set; 23 24 import android.os.Bundle; 25 import android.os.Parcel; 26 import android.os.Parcelable; 27 28 /** 29 * A class representing an Address, i.e, a set of Strings describing a location. 30 * 31 * The address format is a simplified version of xAL (eXtensible Address Language) 32 * http://www.oasis-open.org/committees/ciq/ciq.html#6 33 */ 34 public class Address implements Parcelable { 35 36 private Locale mLocale; 37 38 private String mFeatureName; 39 private HashMap<Integer, String> mAddressLines; 40 private int mMaxAddressLineIndex = -1; 41 private String mAdminArea; 42 private String mSubAdminArea; 43 private String mLocality; 44 private String mSubLocality; 45 private String mThoroughfare; 46 private String mSubThoroughfare; 47 private String mPremises; 48 private String mPostalCode; 49 private String mCountryCode; 50 private String mCountryName; 51 private double mLatitude; 52 private double mLongitude; 53 private boolean mHasLatitude = false; 54 private boolean mHasLongitude = false; 55 private String mPhone; 56 private String mUrl; 57 private Bundle mExtras = null; 58 59 /** 60 * Constructs a new Address object set to the given Locale and with all 61 * other fields initialized to null or false. 62 */ Address(Locale locale)63 public Address(Locale locale) { 64 mLocale = locale; 65 } 66 67 /** 68 * Returns the Locale associated with this address. 69 */ getLocale()70 public Locale getLocale() { 71 return mLocale; 72 } 73 74 /** 75 * Returns the largest index currently in use to specify an address line. 76 * If no address lines are specified, -1 is returned. 77 */ getMaxAddressLineIndex()78 public int getMaxAddressLineIndex() { 79 return mMaxAddressLineIndex; 80 } 81 82 /** 83 * Returns a line of the address numbered by the given index 84 * (starting at 0), or null if no such line is present. 85 * 86 * @throws IllegalArgumentException if index < 0 87 */ getAddressLine(int index)88 public String getAddressLine(int index) { 89 if (index < 0) { 90 throw new IllegalArgumentException("index = " + index + " < 0"); 91 } 92 return mAddressLines == null? null : mAddressLines.get(index); 93 } 94 95 /** 96 * Sets the line of the address numbered by index (starting at 0) to the 97 * given String, which may be null. 98 * 99 * @throws IllegalArgumentException if index < 0 100 */ setAddressLine(int index, String line)101 public void setAddressLine(int index, String line) { 102 if (index < 0) { 103 throw new IllegalArgumentException("index = " + index + " < 0"); 104 } 105 if (mAddressLines == null) { 106 mAddressLines = new HashMap<Integer, String>(); 107 } 108 mAddressLines.put(index, line); 109 110 if (line == null) { 111 // We've eliminated a line, recompute the max index 112 mMaxAddressLineIndex = -1; 113 for (Integer i : mAddressLines.keySet()) { 114 mMaxAddressLineIndex = Math.max(mMaxAddressLineIndex, i); 115 } 116 } else { 117 mMaxAddressLineIndex = Math.max(mMaxAddressLineIndex, index); 118 } 119 } 120 121 /** 122 * Returns the feature name of the address, for example, "Golden Gate Bridge", or null 123 * if it is unknown 124 */ getFeatureName()125 public String getFeatureName() { 126 return mFeatureName; 127 } 128 129 /** 130 * Sets the feature name of the address to the given String, which may be null 131 */ setFeatureName(String featureName)132 public void setFeatureName(String featureName) { 133 mFeatureName = featureName; 134 } 135 136 /** 137 * Returns the administrative area name of the address, for example, "CA", or null if 138 * it is unknown 139 */ getAdminArea()140 public String getAdminArea() { 141 return mAdminArea; 142 } 143 144 /** 145 * Sets the administrative area name of the address to the given String, which may be null 146 */ setAdminArea(String adminArea)147 public void setAdminArea(String adminArea) { 148 this.mAdminArea = adminArea; 149 } 150 151 /** 152 * Returns the sub-administrative area name of the address, for example, "Santa Clara County", 153 * or null if it is unknown 154 */ getSubAdminArea()155 public String getSubAdminArea() { 156 return mSubAdminArea; 157 } 158 159 /** 160 * Sets the sub-administrative area name of the address to the given String, which may be null 161 */ setSubAdminArea(String subAdminArea)162 public void setSubAdminArea(String subAdminArea) { 163 this.mSubAdminArea = subAdminArea; 164 } 165 166 /** 167 * Returns the locality of the address, for example "Mountain View", or null if it is unknown. 168 */ getLocality()169 public String getLocality() { 170 return mLocality; 171 } 172 173 /** 174 * Sets the locality of the address to the given String, which may be null. 175 */ setLocality(String locality)176 public void setLocality(String locality) { 177 mLocality = locality; 178 } 179 180 /** 181 * Returns the sub-locality of the address, or null if it is unknown. 182 * For example, this may correspond to the neighborhood of the locality. 183 */ getSubLocality()184 public String getSubLocality() { 185 return mSubLocality; 186 } 187 188 /** 189 * Sets the sub-locality of the address to the given String, which may be null. 190 */ setSubLocality(String sublocality)191 public void setSubLocality(String sublocality) { 192 mSubLocality = sublocality; 193 } 194 195 /** 196 * Returns the thoroughfare name of the address, for example, "1600 Ampitheater Parkway", 197 * which may be null 198 */ getThoroughfare()199 public String getThoroughfare() { 200 return mThoroughfare; 201 } 202 203 /** 204 * Sets the thoroughfare name of the address, which may be null. 205 */ setThoroughfare(String thoroughfare)206 public void setThoroughfare(String thoroughfare) { 207 this.mThoroughfare = thoroughfare; 208 } 209 210 /** 211 * Returns the sub-thoroughfare name of the address, which may be null. 212 * This may correspond to the street number of the address. 213 */ getSubThoroughfare()214 public String getSubThoroughfare() { 215 return mSubThoroughfare; 216 } 217 218 /** 219 * Sets the sub-thoroughfare name of the address, which may be null. 220 */ setSubThoroughfare(String subthoroughfare)221 public void setSubThoroughfare(String subthoroughfare) { 222 this.mSubThoroughfare = subthoroughfare; 223 } 224 225 /** 226 * Returns the premises of the address, or null if it is unknown. 227 */ getPremises()228 public String getPremises() { 229 return mPremises; 230 } 231 232 /** 233 * Sets the premises of the address to the given String, which may be null. 234 */ setPremises(String premises)235 public void setPremises(String premises) { 236 mPremises = premises; 237 } 238 239 /** 240 * Returns the postal code of the address, for example "94110", 241 * or null if it is unknown. 242 */ getPostalCode()243 public String getPostalCode() { 244 return mPostalCode; 245 } 246 247 /** 248 * Sets the postal code of the address to the given String, which may 249 * be null. 250 */ setPostalCode(String postalCode)251 public void setPostalCode(String postalCode) { 252 mPostalCode = postalCode; 253 } 254 255 /** 256 * Returns the country code of the address, for example "US", 257 * or null if it is unknown. 258 */ getCountryCode()259 public String getCountryCode() { 260 return mCountryCode; 261 } 262 263 /** 264 * Sets the country code of the address to the given String, which may 265 * be null. 266 */ setCountryCode(String countryCode)267 public void setCountryCode(String countryCode) { 268 mCountryCode = countryCode; 269 } 270 271 /** 272 * Returns the localized country name of the address, for example "Iceland", 273 * or null if it is unknown. 274 */ getCountryName()275 public String getCountryName() { 276 return mCountryName; 277 } 278 279 /** 280 * Sets the country name of the address to the given String, which may 281 * be null. 282 */ setCountryName(String countryName)283 public void setCountryName(String countryName) { 284 mCountryName = countryName; 285 } 286 287 /** 288 * Returns true if a latitude has been assigned to this Address, 289 * false otherwise. 290 */ hasLatitude()291 public boolean hasLatitude() { 292 return mHasLatitude; 293 } 294 295 /** 296 * Returns the latitude of the address if known. 297 * 298 * @throws IllegalStateException if this Address has not been assigned 299 * a latitude. 300 */ getLatitude()301 public double getLatitude() { 302 if (mHasLatitude) { 303 return mLatitude; 304 } else { 305 throw new IllegalStateException(); 306 } 307 } 308 309 /** 310 * Sets the latitude associated with this address. 311 */ setLatitude(double latitude)312 public void setLatitude(double latitude) { 313 mLatitude = latitude; 314 mHasLatitude = true; 315 } 316 317 /** 318 * Removes any latitude associated with this address. 319 */ clearLatitude()320 public void clearLatitude() { 321 mHasLatitude = false; 322 } 323 324 /** 325 * Returns true if a longitude has been assigned to this Address, 326 * false otherwise. 327 */ hasLongitude()328 public boolean hasLongitude() { 329 return mHasLongitude; 330 } 331 332 /** 333 * Returns the longitude of the address if known. 334 * 335 * @throws IllegalStateException if this Address has not been assigned 336 * a longitude. 337 */ getLongitude()338 public double getLongitude() { 339 if (mHasLongitude) { 340 return mLongitude; 341 } else { 342 throw new IllegalStateException(); 343 } 344 } 345 346 /** 347 * Sets the longitude associated with this address. 348 */ setLongitude(double longitude)349 public void setLongitude(double longitude) { 350 mLongitude = longitude; 351 mHasLongitude = true; 352 } 353 354 /** 355 * Removes any longitude associated with this address. 356 */ clearLongitude()357 public void clearLongitude() { 358 mHasLongitude = false; 359 } 360 361 /** 362 * Returns the phone number of the address if known, 363 * or null if it is unknown. 364 * 365 * @throws IllegalStateException if this Address has not been assigned 366 * a phone number. 367 */ getPhone()368 public String getPhone() { 369 return mPhone; 370 } 371 372 /** 373 * Sets the phone number associated with this address. 374 */ setPhone(String phone)375 public void setPhone(String phone) { 376 mPhone = phone; 377 } 378 379 /** 380 * Returns the public URL for the address if known, 381 * or null if it is unknown. 382 */ getUrl()383 public String getUrl() { 384 return mUrl; 385 } 386 387 /** 388 * Sets the public URL associated with this address. 389 */ setUrl(String Url)390 public void setUrl(String Url) { 391 mUrl = Url; 392 } 393 394 /** 395 * Returns additional provider-specific information about the 396 * address as a Bundle. The keys and values are determined 397 * by the provider. If no additional information is available, 398 * null is returned. 399 * 400 * <!-- 401 * <p> A number of common key/value pairs are listed 402 * below. Providers that use any of the keys on this list must 403 * provide the corresponding value as described below. 404 * 405 * <ul> 406 * </ul> 407 * --> 408 */ getExtras()409 public Bundle getExtras() { 410 return mExtras; 411 } 412 413 /** 414 * Sets the extra information associated with this fix to the 415 * given Bundle. 416 */ setExtras(Bundle extras)417 public void setExtras(Bundle extras) { 418 mExtras = (extras == null) ? null : new Bundle(extras); 419 } 420 421 @Override toString()422 public String toString() { 423 StringBuilder sb = new StringBuilder(); 424 sb.append("Address[addressLines=["); 425 for (int i = 0; i <= mMaxAddressLineIndex; i++) { 426 if (i > 0) { 427 sb.append(','); 428 } 429 sb.append(i); 430 sb.append(':'); 431 String line = mAddressLines.get(i); 432 if (line == null) { 433 sb.append("null"); 434 } else { 435 sb.append('\"'); 436 sb.append(line); 437 sb.append('\"'); 438 } 439 } 440 sb.append(']'); 441 sb.append(",feature="); 442 sb.append(mFeatureName); 443 sb.append(",admin="); 444 sb.append(mAdminArea); 445 sb.append(",sub-admin="); 446 sb.append(mSubAdminArea); 447 sb.append(",locality="); 448 sb.append(mLocality); 449 sb.append(",thoroughfare="); 450 sb.append(mThoroughfare); 451 sb.append(",postalCode="); 452 sb.append(mPostalCode); 453 sb.append(",countryCode="); 454 sb.append(mCountryCode); 455 sb.append(",countryName="); 456 sb.append(mCountryName); 457 sb.append(",hasLatitude="); 458 sb.append(mHasLatitude); 459 sb.append(",latitude="); 460 sb.append(mLatitude); 461 sb.append(",hasLongitude="); 462 sb.append(mHasLongitude); 463 sb.append(",longitude="); 464 sb.append(mLongitude); 465 sb.append(",phone="); 466 sb.append(mPhone); 467 sb.append(",url="); 468 sb.append(mUrl); 469 sb.append(",extras="); 470 sb.append(mExtras); 471 sb.append(']'); 472 return sb.toString(); 473 } 474 475 public static final @android.annotation.NonNull Parcelable.Creator<Address> CREATOR = 476 new Parcelable.Creator<Address>() { 477 public Address createFromParcel(Parcel in) { 478 String language = in.readString(); 479 String country = in.readString(); 480 Locale locale = country.length() > 0 ? 481 new Locale(language, country) : 482 new Locale(language); 483 Address a = new Address(locale); 484 485 int N = in.readInt(); 486 if (N > 0) { 487 a.mAddressLines = new HashMap<Integer, String>(N); 488 for (int i = 0; i < N; i++) { 489 int index = in.readInt(); 490 String line = in.readString(); 491 a.mAddressLines.put(index, line); 492 a.mMaxAddressLineIndex = 493 Math.max(a.mMaxAddressLineIndex, index); 494 } 495 } else { 496 a.mAddressLines = null; 497 a.mMaxAddressLineIndex = -1; 498 } 499 a.mFeatureName = in.readString(); 500 a.mAdminArea = in.readString(); 501 a.mSubAdminArea = in.readString(); 502 a.mLocality = in.readString(); 503 a.mSubLocality = in.readString(); 504 a.mThoroughfare = in.readString(); 505 a.mSubThoroughfare = in.readString(); 506 a.mPremises = in.readString(); 507 a.mPostalCode = in.readString(); 508 a.mCountryCode = in.readString(); 509 a.mCountryName = in.readString(); 510 a.mHasLatitude = in.readInt() == 0 ? false : true; 511 if (a.mHasLatitude) { 512 a.mLatitude = in.readDouble(); 513 } 514 a.mHasLongitude = in.readInt() == 0 ? false : true; 515 if (a.mHasLongitude) { 516 a.mLongitude = in.readDouble(); 517 } 518 a.mPhone = in.readString(); 519 a.mUrl = in.readString(); 520 a.mExtras = in.readBundle(); 521 return a; 522 } 523 524 public Address[] newArray(int size) { 525 return new Address[size]; 526 } 527 }; 528 describeContents()529 public int describeContents() { 530 return (mExtras != null) ? mExtras.describeContents() : 0; 531 } 532 writeToParcel(Parcel parcel, int flags)533 public void writeToParcel(Parcel parcel, int flags) { 534 parcel.writeString(mLocale.getLanguage()); 535 parcel.writeString(mLocale.getCountry()); 536 if (mAddressLines == null) { 537 parcel.writeInt(0); 538 } else { 539 Set<Map.Entry<Integer, String>> entries = mAddressLines.entrySet(); 540 parcel.writeInt(entries.size()); 541 for (Map.Entry<Integer, String> e : entries) { 542 parcel.writeInt(e.getKey()); 543 parcel.writeString(e.getValue()); 544 } 545 } 546 parcel.writeString(mFeatureName); 547 parcel.writeString(mAdminArea); 548 parcel.writeString(mSubAdminArea); 549 parcel.writeString(mLocality); 550 parcel.writeString(mSubLocality); 551 parcel.writeString(mThoroughfare); 552 parcel.writeString(mSubThoroughfare); 553 parcel.writeString(mPremises); 554 parcel.writeString(mPostalCode); 555 parcel.writeString(mCountryCode); 556 parcel.writeString(mCountryName); 557 parcel.writeInt(mHasLatitude ? 1 : 0); 558 if (mHasLatitude) { 559 parcel.writeDouble(mLatitude); 560 } 561 parcel.writeInt(mHasLongitude ? 1 : 0); 562 if (mHasLongitude){ 563 parcel.writeDouble(mLongitude); 564 } 565 parcel.writeString(mPhone); 566 parcel.writeString(mUrl); 567 parcel.writeBundle(mExtras); 568 } 569 } 570