1 /* 2 * Copyright (C) 2014 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.telephony; 18 19 import android.content.Context; 20 import android.graphics.Bitmap; 21 import android.graphics.Canvas; 22 import android.graphics.Color; 23 import android.graphics.Paint; 24 import android.graphics.PorterDuff; 25 import android.graphics.PorterDuffColorFilter; 26 import android.graphics.Rect; 27 import android.graphics.Typeface; 28 import android.os.Build; 29 import android.os.Parcel; 30 import android.os.Parcelable; 31 import android.util.DisplayMetrics; 32 33 /** 34 * A Parcelable class for Subscription Information. 35 */ 36 public class SubscriptionInfo implements Parcelable { 37 38 /** 39 * Size of text to render on the icon. 40 */ 41 private static final int TEXT_SIZE = 16; 42 43 /** 44 * Subscription Identifier, this is a device unique number 45 * and not an index into an array 46 */ 47 private int mId; 48 49 /** 50 * The GID for a SIM that maybe associated with this subscription, empty if unknown 51 */ 52 private String mIccId; 53 54 /** 55 * The index of the slot that currently contains the subscription 56 * and not necessarily unique and maybe INVALID_SLOT_ID if unknown 57 */ 58 private int mSimSlotIndex; 59 60 /** 61 * The name displayed to the user that identifies this subscription 62 */ 63 private CharSequence mDisplayName; 64 65 /** 66 * String that identifies SPN/PLMN 67 * TODO : Add a new field that identifies only SPN for a sim 68 */ 69 private CharSequence mCarrierName; 70 71 /** 72 * The source of the name, NAME_SOURCE_UNDEFINED, NAME_SOURCE_DEFAULT_SOURCE, 73 * NAME_SOURCE_SIM_SOURCE or NAME_SOURCE_USER_INPUT. 74 */ 75 private int mNameSource; 76 77 /** 78 * The color to be used for tinting the icon when displaying to the user 79 */ 80 private int mIconTint; 81 82 /** 83 * A number presented to the user identify this subscription 84 */ 85 private String mNumber; 86 87 /** 88 * Data roaming state, DATA_RAOMING_ENABLE, DATA_RAOMING_DISABLE 89 */ 90 private int mDataRoaming; 91 92 /** 93 * SIM Icon bitmap 94 */ 95 private Bitmap mIconBitmap; 96 97 /** 98 * Mobile Country Code 99 */ 100 private int mMcc; 101 102 /** 103 * Mobile Network Code 104 */ 105 private int mMnc; 106 107 /** 108 * ISO Country code for the subscription's provider 109 */ 110 private String mCountryIso; 111 112 /** 113 * @hide 114 */ 115 public SubscriptionInfo(int id, String iccId, int simSlotIndex, CharSequence displayName, 116 CharSequence carrierName, int nameSource, int iconTint, String number, int roaming, 117 Bitmap icon, int mcc, int mnc, String countryIso) { 118 this.mId = id; 119 this.mIccId = iccId; 120 this.mSimSlotIndex = simSlotIndex; 121 this.mDisplayName = displayName; 122 this.mCarrierName = carrierName; 123 this.mNameSource = nameSource; 124 this.mIconTint = iconTint; 125 this.mNumber = number; 126 this.mDataRoaming = roaming; 127 this.mIconBitmap = icon; 128 this.mMcc = mcc; 129 this.mMnc = mnc; 130 this.mCountryIso = countryIso; 131 } 132 133 /** 134 * @return the subscription ID. 135 */ 136 public int getSubscriptionId() { 137 return this.mId; 138 } 139 140 /** 141 * @return the ICC ID. 142 */ 143 public String getIccId() { 144 return this.mIccId; 145 } 146 147 /** 148 * @return the slot index of this Subscription's SIM card. 149 */ 150 public int getSimSlotIndex() { 151 return this.mSimSlotIndex; 152 } 153 154 /** 155 * @return the name displayed to the user that identifies this subscription 156 */ 157 public CharSequence getDisplayName() { 158 return this.mDisplayName; 159 } 160 161 /** 162 * Sets the name displayed to the user that identifies this subscription 163 * @hide 164 */ 165 public void setDisplayName(CharSequence name) { 166 this.mDisplayName = name; 167 } 168 169 /** 170 * @return the name displayed to the user that identifies Subscription provider name 171 */ 172 public CharSequence getCarrierName() { 173 return this.mCarrierName; 174 } 175 176 /** 177 * Sets the name displayed to the user that identifies Subscription provider name 178 * @hide 179 */ 180 public void setCarrierName(CharSequence name) { 181 this.mCarrierName = name; 182 } 183 184 /** 185 * @return the source of the name, eg NAME_SOURCE_UNDEFINED, NAME_SOURCE_DEFAULT_SOURCE, 186 * NAME_SOURCE_SIM_SOURCE or NAME_SOURCE_USER_INPUT. 187 * @hide 188 */ 189 public int getNameSource() { 190 return this.mNameSource; 191 } 192 193 /** 194 * Creates and returns an icon {@code Bitmap} to represent this {@code SubscriptionInfo} in a user 195 * interface. 196 * 197 * @param context A {@code Context} to get the {@code DisplayMetrics}s from. 198 * 199 * @return A bitmap icon for this {@code SubscriptionInfo}. 200 */ 201 public Bitmap createIconBitmap(Context context) { 202 int width = mIconBitmap.getWidth(); 203 int height = mIconBitmap.getHeight(); 204 DisplayMetrics metrics = context.getResources().getDisplayMetrics(); 205 206 // Create a new bitmap of the same size because it will be modified. 207 Bitmap workingBitmap = Bitmap.createBitmap(metrics, width, height, mIconBitmap.getConfig()); 208 209 Canvas canvas = new Canvas(workingBitmap); 210 Paint paint = new Paint(); 211 212 // Tint the icon with the color. 213 paint.setColorFilter(new PorterDuffColorFilter(mIconTint, PorterDuff.Mode.SRC_ATOP)); 214 canvas.drawBitmap(mIconBitmap, 0, 0, paint); 215 paint.setColorFilter(null); 216 217 // Write the sim slot index. 218 paint.setAntiAlias(true); 219 paint.setTypeface(Typeface.create("sans-serif", Typeface.NORMAL)); 220 paint.setColor(Color.WHITE); 221 // Set text size scaled by density 222 paint.setTextSize(TEXT_SIZE * metrics.density); 223 // Convert sim slot index to localized string 224 final String index = String.format("%d", mSimSlotIndex + 1); 225 final Rect textBound = new Rect(); 226 paint.getTextBounds(index, 0, 1, textBound); 227 final float xOffset = (width / 2.f) - textBound.centerX(); 228 final float yOffset = (height / 2.f) - textBound.centerY(); 229 canvas.drawText(index, xOffset, yOffset, paint); 230 231 return workingBitmap; 232 } 233 234 /** 235 * A highlight color to use in displaying information about this {@code PhoneAccount}. 236 * 237 * @return A hexadecimal color value. 238 */ 239 public int getIconTint() { 240 return mIconTint; 241 } 242 243 /** 244 * Sets the color displayed to the user that identifies this subscription 245 * @hide 246 */ 247 public void setIconTint(int iconTint) { 248 this.mIconTint = iconTint; 249 } 250 251 /** 252 * @return the number of this subscription. 253 */ 254 public String getNumber() { 255 return mNumber; 256 } 257 258 /** 259 * @return the data roaming state for this subscription, either 260 * {@link SubscriptionManager#DATA_ROAMING_ENABLE} or {@link SubscriptionManager#DATA_ROAMING_DISABLE}. 261 */ 262 public int getDataRoaming() { 263 return this.mDataRoaming; 264 } 265 266 /** 267 * @return the MCC. 268 */ 269 public int getMcc() { 270 return this.mMcc; 271 } 272 273 /** 274 * @return the MNC. 275 */ 276 public int getMnc() { 277 return this.mMnc; 278 } 279 280 /** 281 * @return the ISO country code 282 */ 283 public String getCountryIso() { 284 return this.mCountryIso; 285 } 286 287 public static final Parcelable.Creator<SubscriptionInfo> CREATOR = new Parcelable.Creator<SubscriptionInfo>() { 288 @Override 289 public SubscriptionInfo createFromParcel(Parcel source) { 290 int id = source.readInt(); 291 String iccId = source.readString(); 292 int simSlotIndex = source.readInt(); 293 CharSequence displayName = source.readCharSequence(); 294 CharSequence carrierName = source.readCharSequence(); 295 int nameSource = source.readInt(); 296 int iconTint = source.readInt(); 297 String number = source.readString(); 298 int dataRoaming = source.readInt(); 299 int mcc = source.readInt(); 300 int mnc = source.readInt(); 301 String countryIso = source.readString(); 302 Bitmap iconBitmap = Bitmap.CREATOR.createFromParcel(source); 303 304 return new SubscriptionInfo(id, iccId, simSlotIndex, displayName, carrierName, 305 nameSource, iconTint, number, dataRoaming, iconBitmap, mcc, mnc, countryIso); 306 } 307 308 @Override 309 public SubscriptionInfo[] newArray(int size) { 310 return new SubscriptionInfo[size]; 311 } 312 }; 313 314 @Override 315 public void writeToParcel(Parcel dest, int flags) { 316 dest.writeInt(mId); 317 dest.writeString(mIccId); 318 dest.writeInt(mSimSlotIndex); 319 dest.writeCharSequence(mDisplayName); 320 dest.writeCharSequence(mCarrierName); 321 dest.writeInt(mNameSource); 322 dest.writeInt(mIconTint); 323 dest.writeString(mNumber); 324 dest.writeInt(mDataRoaming); 325 dest.writeInt(mMcc); 326 dest.writeInt(mMnc); 327 dest.writeString(mCountryIso); 328 mIconBitmap.writeToParcel(dest, flags); 329 } 330 331 @Override 332 public int describeContents() { 333 return 0; 334 } 335 336 /** 337 * @hide 338 */ 339 public static String givePrintableIccid(String iccId) { 340 String iccIdToPrint = null; 341 if (iccId != null) { 342 if (iccId.length() > 9 && !Build.IS_DEBUGGABLE) { 343 iccIdToPrint = iccId.substring(0, 9) + Rlog.pii(false, iccId.substring(9)); 344 } else { 345 iccIdToPrint = iccId; 346 } 347 } 348 return iccIdToPrint; 349 } 350 351 @Override 352 public String toString() { 353 String iccIdToPrint = givePrintableIccid(mIccId); 354 return "{id=" + mId + ", iccId=" + iccIdToPrint + " simSlotIndex=" + mSimSlotIndex 355 + " displayName=" + mDisplayName + " carrierName=" + mCarrierName 356 + " nameSource=" + mNameSource + " iconTint=" + mIconTint 357 + " dataRoaming=" + mDataRoaming + " iconBitmap=" + mIconBitmap + " mcc " + mMcc 358 + " mnc " + mMnc + "}"; 359 } 360 } 361