blob: c855d45f519ebbeab69f864fc3d871c7a8081f8f [file] [log] [blame]
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001/*
2 * Copyright (C) 2006 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.content.res;
18
Alan Viverette45c4bbb2015-01-05 14:59:19 -080019import android.animation.Animator;
20import android.animation.StateListAnimator;
Tor Norbye7b9c9122013-05-30 16:48:33 -070021import android.annotation.AnimRes;
ztenghuib5292562017-07-11 16:03:36 -070022import android.annotation.AnimatorRes;
Tor Norbye7b9c9122013-05-30 16:48:33 -070023import android.annotation.AnyRes;
24import android.annotation.ArrayRes;
Roozbeh Pournader47571c72015-09-01 14:07:04 -070025import android.annotation.AttrRes;
Tor Norbye7b9c9122013-05-30 16:48:33 -070026import android.annotation.BoolRes;
Roozbeh Pournader47571c72015-09-01 14:07:04 -070027import android.annotation.ColorInt;
Tor Norbye7b9c9122013-05-30 16:48:33 -070028import android.annotation.ColorRes;
29import android.annotation.DimenRes;
30import android.annotation.DrawableRes;
Clara Bayarried00bfd2017-01-20 14:58:21 +000031import android.annotation.FontRes;
Tor Norbye7b9c9122013-05-30 16:48:33 -070032import android.annotation.FractionRes;
33import android.annotation.IntegerRes;
34import android.annotation.LayoutRes;
Alan Viverette45c4bbb2015-01-05 14:59:19 -080035import android.annotation.NonNull;
Alan Viverette3b5c4272014-05-20 13:20:42 -070036import android.annotation.Nullable;
Tor Norbye7b9c9122013-05-30 16:48:33 -070037import android.annotation.PluralsRes;
38import android.annotation.RawRes;
39import android.annotation.StringRes;
Roozbeh Pournader47571c72015-09-01 14:07:04 -070040import android.annotation.StyleRes;
41import android.annotation.StyleableRes;
Mathew Inwood5c0d3542018-08-14 13:54:31 +010042import android.annotation.UnsupportedAppUsage;
Tor Norbye7b9c9122013-05-30 16:48:33 -070043import android.annotation.XmlRes;
Dianne Hackbornebff8f92011-05-12 18:07:47 -070044import android.content.pm.ActivityInfo;
Alan Viverette9ad386b2017-01-26 14:00:20 -050045import android.content.pm.ActivityInfo.Config;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080046import android.graphics.Movie;
Clara Bayarri18e9f9f2016-12-19 16:20:29 +000047import android.graphics.Typeface;
Alan Viverette45c4bbb2015-01-05 14:59:19 -080048import android.graphics.drawable.Drawable;
Masanori Oginoc7d9d272010-07-10 12:10:41 +090049import android.graphics.drawable.Drawable.ConstantState;
Roozbeh Pournader47571c72015-09-01 14:07:04 -070050import android.graphics.drawable.DrawableInflater;
Dianne Hackborn3b3e1452009-09-24 19:22:12 -070051import android.os.Build;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080052import android.os.Bundle;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080053import android.util.AttributeSet;
54import android.util.DisplayMetrics;
55import android.util.Log;
Alan Viverette45c4bbb2015-01-05 14:59:19 -080056import android.util.LongSparseArray;
57import android.util.Pools.SynchronizedPool;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080058import android.util.TypedValue;
Adam Lesinski4ece3d62016-06-16 18:05:41 -070059import android.view.DisplayAdjustments;
Alan Viverette45c4bbb2015-01-05 14:59:19 -080060import android.view.ViewDebug;
Siva Velusamy0d857b92015-04-22 10:23:56 -070061import android.view.ViewHierarchyEncoder;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080062
Adam Lesinski082614c2016-03-04 14:33:47 -080063import com.android.internal.annotations.VisibleForTesting;
Roozbeh Pournader47571c72015-09-01 14:07:04 -070064import com.android.internal.util.GrowingArrayUtils;
65import com.android.internal.util.XmlUtils;
66
67import org.xmlpull.v1.XmlPullParser;
68import org.xmlpull.v1.XmlPullParserException;
69
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080070import java.io.IOException;
71import java.io.InputStream;
Adam Lesinski082614c2016-03-04 14:33:47 -080072import java.lang.ref.WeakReference;
73import java.util.ArrayList;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080074
75/**
76 * Class for accessing an application's resources. This sits on top of the
Scott Mainf4f05b82011-01-07 14:38:23 -080077 * asset manager of the application (accessible through {@link #getAssets}) and
78 * provides a high-level API for getting typed data from the assets.
79 *
80 * <p>The Android resource system keeps track of all non-code assets associated with an
81 * application. You can use this class to access your application's resources. You can generally
82 * acquire the {@link android.content.res.Resources} instance associated with your application
83 * with {@link android.content.Context#getResources getResources()}.</p>
84 *
85 * <p>The Android SDK tools compile your application's resources into the application binary
86 * at build time. To use a resource, you must install it correctly in the source tree (inside
87 * your project's {@code res/} directory) and build your application. As part of the build
88 * process, the SDK tools generate symbols for each resource, which you can use in your application
89 * code to access the resources.</p>
90 *
91 * <p>Using application resources makes it easy to update various characteristics of your
92 * application without modifying code, and&mdash;by providing sets of alternative
93 * resources&mdash;enables you to optimize your application for a variety of device configurations
94 * (such as for different languages and screen sizes). This is an important aspect of developing
95 * Android applications that are compatible on different types of devices.</p>
96 *
97 * <p>For more information about using resources, see the documentation about <a
98 * href="{@docRoot}guide/topics/resources/index.html">Application Resources</a>.</p>
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080099 */
100public class Resources {
Aurimas Liutikas83386232019-01-16 12:46:42 -0800101 /**
102 * The {@code null} resource ID. This denotes an invalid resource ID that is returned by the
103 * system when a resource is not found or the value is set to {@code @null} in XML.
104 */
105 public static final @AnyRes int ID_NULL = 0;
106
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800107 static final String TAG = "Resources";
Alan Viverette562a6a82014-01-31 11:07:29 -0800108
Dianne Hackborn50707cc2013-02-08 15:32:05 -0800109 private static final Object sSync = new Object();
Fabrice Di Megliob9a13b82013-04-15 14:05:30 -0700110
Alan Viveretteedc46642014-02-01 01:43:16 -0800111 // Used by BridgeResources in layoutlib
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100112 @UnsupportedAppUsage
Alan Viveretteedc46642014-02-01 01:43:16 -0800113 static Resources mSystem = null;
114
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100115 @UnsupportedAppUsage
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800116 private ResourcesImpl mResourcesImpl;
Alan Viverette4d07bc92015-11-16 10:19:12 -0500117
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800118 // Pool of TypedArrays targeted to this Resources object.
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100119 @UnsupportedAppUsage
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800120 final SynchronizedPool<TypedArray> mTypedArrayPool = new SynchronizedPool<>(5);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800121
Alan Viverette02fc5fe2015-08-27 13:16:09 -0400122 /** Used to inflate drawable objects from XML. */
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100123 @UnsupportedAppUsage
Alan Viverette02fc5fe2015-08-27 13:16:09 -0400124 private DrawableInflater mDrawableInflater;
125
Alan Viverette4d07bc92015-11-16 10:19:12 -0500126 /** Lock object used to protect access to {@link #mTmpValue}. */
127 private final Object mTmpValueLock = new Object();
128
129 /** Single-item pool used to minimize TypedValue allocations. */
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100130 @UnsupportedAppUsage
Alan Viverette562a6a82014-01-31 11:07:29 -0800131 private TypedValue mTmpValue = new TypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -0500132
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100133 @UnsupportedAppUsage
Alan Viverette02fc5fe2015-08-27 13:16:09 -0400134 final ClassLoader mClassLoader;
Fabrice Di Megliob9a13b82013-04-15 14:05:30 -0700135
Alan Viverette62599332014-04-01 14:57:39 -0700136 /**
Adam Lesinski082614c2016-03-04 14:33:47 -0800137 * WeakReferences to Themes that were constructed from this Resources object.
138 * We keep track of these in case our underlying implementation is changed, in which case
139 * the Themes must also get updated ThemeImpls.
140 */
141 private final ArrayList<WeakReference<Theme>> mThemeRefs = new ArrayList<>();
142
143 /**
Richard Uhlerdd6a0db2018-04-26 15:09:30 +0100144 * To avoid leaking WeakReferences to garbage collected Themes on the
145 * mThemeRefs list, we flush the list of stale references any time the
146 * mThemeRefNextFlushSize is reached.
147 */
148 private static final int MIN_THEME_REFS_FLUSH_SIZE = 32;
149 private int mThemeRefsNextFlushSize = MIN_THEME_REFS_FLUSH_SIZE;
150
151 /**
Alan Viverette62599332014-04-01 14:57:39 -0700152 * Returns the most appropriate default theme for the specified target SDK version.
Alan Viverette5effd7e2014-05-05 12:25:33 -0700153 * <ul>
154 * <li>Below API 11: Gingerbread
Alan Viverette4b2b6152016-06-08 11:45:15 -0400155 * <li>APIs 12 thru 14: Holo
156 * <li>APIs 15 thru 23: Device default dark
157 * <li>APIs 24 and above: Device default light with dark action bar
Alan Viverette5effd7e2014-05-05 12:25:33 -0700158 * </ul>
Alan Viverette62599332014-04-01 14:57:39 -0700159 *
160 * @param curTheme The current theme, or 0 if not specified.
161 * @param targetSdkVersion The target SDK version.
162 * @return A theme resource identifier
163 * @hide
164 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100165 @UnsupportedAppUsage
Alan Viverette5effd7e2014-05-05 12:25:33 -0700166 public static int selectDefaultTheme(int curTheme, int targetSdkVersion) {
Dianne Hackbornd922ae02011-01-14 11:43:24 -0800167 return selectSystemTheme(curTheme, targetSdkVersion,
Alan Viverette5effd7e2014-05-05 12:25:33 -0700168 com.android.internal.R.style.Theme,
169 com.android.internal.R.style.Theme_Holo,
170 com.android.internal.R.style.Theme_DeviceDefault,
171 com.android.internal.R.style.Theme_DeviceDefault_Light_DarkActionBar);
Dianne Hackbornd922ae02011-01-14 11:43:24 -0800172 }
Alan Viverette62599332014-04-01 14:57:39 -0700173
Alan Viverette5effd7e2014-05-05 12:25:33 -0700174 /** @hide */
175 public static int selectSystemTheme(int curTheme, int targetSdkVersion, int orig, int holo,
176 int dark, int deviceDefault) {
Aurimas Liutikasd8ebfef2019-01-16 12:46:42 -0800177 if (curTheme != ID_NULL) {
Dianne Hackbornd922ae02011-01-14 11:43:24 -0800178 return curTheme;
179 }
Alan Viverette5effd7e2014-05-05 12:25:33 -0700180 if (targetSdkVersion < Build.VERSION_CODES.HONEYCOMB) {
181 return orig;
Dianne Hackbornd922ae02011-01-14 11:43:24 -0800182 }
Alan Viverette5effd7e2014-05-05 12:25:33 -0700183 if (targetSdkVersion < Build.VERSION_CODES.ICE_CREAM_SANDWICH) {
184 return holo;
185 }
Alan Viverette4b2b6152016-06-08 11:45:15 -0400186 if (targetSdkVersion < Build.VERSION_CODES.N) {
Alan Viverette5effd7e2014-05-05 12:25:33 -0700187 return dark;
188 }
189 return deviceDefault;
Dianne Hackbornd922ae02011-01-14 11:43:24 -0800190 }
Alan Viverette62599332014-04-01 14:57:39 -0700191
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800192 /**
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800193 * Return a global shared Resources object that provides access to only
194 * system resources (no application resources), and is not configured for
195 * the current screen (can not use dimension units, does not change based
196 * on orientation, etc).
Alan Viverette02fc5fe2015-08-27 13:16:09 -0400197 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800198 public static Resources getSystem() {
199 synchronized (sSync) {
200 Resources ret = mSystem;
201 if (ret == null) {
202 ret = new Resources();
203 mSystem = ret;
204 }
205 return ret;
Alan Viverette02fc5fe2015-08-27 13:16:09 -0400206 }
Yigit Boyard422dc32014-09-25 12:23:35 -0700207 }
208
209 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800210 * This exception is thrown by the resource APIs when a requested resource
211 * can not be found.
212 */
213 public static class NotFoundException extends RuntimeException {
214 public NotFoundException() {
215 }
216
217 public NotFoundException(String name) {
218 super(name);
219 }
Alan Viverette4d07bc92015-11-16 10:19:12 -0500220
221 public NotFoundException(String name, Exception cause) {
222 super(name, cause);
223 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800224 }
225
226 /**
227 * Create a new Resources object on top of an existing set of assets in an
228 * AssetManager.
Wale Ogunwale60454db2015-01-23 16:05:07 -0800229 *
Adam Lesinskiaa19d5e2016-07-15 17:49:49 -0700230 * @deprecated Resources should not be constructed by apps.
231 * See {@link android.content.Context#createConfigurationContext(Configuration)}.
232 *
Wale Ogunwale60454db2015-01-23 16:05:07 -0800233 * @param assets Previously created AssetManager.
234 * @param metrics Current display metrics to consider when
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800235 * selecting/computing resource values.
Wale Ogunwale60454db2015-01-23 16:05:07 -0800236 * @param config Desired device configuration to consider when
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800237 * selecting/computing resource values (optional).
238 */
Adam Lesinskiaa19d5e2016-07-15 17:49:49 -0700239 @Deprecated
Romain Guy5d911c32012-04-12 16:25:17 -0700240 public Resources(AssetManager assets, DisplayMetrics metrics, Configuration config) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800241 this(null);
Adam Lesinski8e8d2322016-06-24 12:29:16 -0700242 mResourcesImpl = new ResourcesImpl(assets, metrics, config, new DisplayAdjustments());
Mitsuru Oshima8169dae2009-04-28 18:12:09 -0700243 }
244
245 /**
Mitsuru Oshimaba3ba572009-07-08 18:49:26 -0700246 * Creates a new Resources object with CompatibilityInfo.
Wale Ogunwale60454db2015-01-23 16:05:07 -0800247 *
Alan Viverette02fc5fe2015-08-27 13:16:09 -0400248 * @param classLoader class loader for the package used to load custom
249 * resource classes, may be {@code null} to use system
250 * class loader
Mitsuru Oshima8169dae2009-04-28 18:12:09 -0700251 * @hide
252 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100253 @UnsupportedAppUsage
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800254 public Resources(@Nullable ClassLoader classLoader) {
Alan Viverette02fc5fe2015-08-27 13:16:09 -0400255 mClassLoader = classLoader == null ? ClassLoader.getSystemClassLoader() : classLoader;
Mitsuru Oshima569076c2009-07-02 20:06:08 -0700256 }
257
258 /**
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800259 * Only for creating the System resources.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800260 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100261 @UnsupportedAppUsage
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800262 private Resources() {
263 this(null);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800264
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800265 final DisplayMetrics metrics = new DisplayMetrics();
266 metrics.setToDefaults();
267
268 final Configuration config = new Configuration();
269 config.setToDefaults();
270
271 mResourcesImpl = new ResourcesImpl(AssetManager.getSystem(), metrics, config,
Adam Lesinski8e8d2322016-06-24 12:29:16 -0700272 new DisplayAdjustments());
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800273 }
274
275 /**
Adam Lesinski082614c2016-03-04 14:33:47 -0800276 * Set the underlying implementation (containing all the resources and caches)
277 * and updates all Theme references to new implementations as well.
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800278 * @hide
279 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100280 @UnsupportedAppUsage
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800281 public void setImpl(ResourcesImpl impl) {
Adam Lesinski082614c2016-03-04 14:33:47 -0800282 if (impl == mResourcesImpl) {
283 return;
284 }
285
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800286 mResourcesImpl = impl;
Adam Lesinski082614c2016-03-04 14:33:47 -0800287
288 // Create new ThemeImpls that are identical to the ones we have.
289 synchronized (mThemeRefs) {
290 final int count = mThemeRefs.size();
291 for (int i = 0; i < count; i++) {
292 WeakReference<Theme> weakThemeRef = mThemeRefs.get(i);
293 Theme theme = weakThemeRef != null ? weakThemeRef.get() : null;
294 if (theme != null) {
295 theme.setImpl(mResourcesImpl.newThemeImpl(theme.getKey()));
296 }
297 }
298 }
299 }
300
301 /**
302 * @hide
303 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100304 @UnsupportedAppUsage
Adam Lesinski082614c2016-03-04 14:33:47 -0800305 public ResourcesImpl getImpl() {
306 return mResourcesImpl;
307 }
308
309 /**
310 * @hide
311 */
312 public ClassLoader getClassLoader() {
313 return mClassLoader;
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800314 }
315
316 /**
317 * @return the inflater used to create drawable objects
318 * @hide Pending API finalization.
319 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100320 @UnsupportedAppUsage
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800321 public final DrawableInflater getDrawableInflater() {
322 if (mDrawableInflater == null) {
323 mDrawableInflater = new DrawableInflater(this, mClassLoader);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800324 }
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800325 return mDrawableInflater;
326 }
327
328 /**
329 * Used by AnimatorInflater.
330 *
331 * @hide
332 */
333 public ConfigurationBoundResourceCache<Animator> getAnimatorCache() {
334 return mResourcesImpl.getAnimatorCache();
335 }
336
337 /**
338 * Used by AnimatorInflater.
339 *
340 * @hide
341 */
342 public ConfigurationBoundResourceCache<StateListAnimator> getStateListAnimatorCache() {
343 return mResourcesImpl.getStateListAnimatorCache();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800344 }
345
346 /**
347 * Return the string value associated with a particular resource ID. The
348 * returned object will be a String if this is a plain string; it will be
349 * some other type of CharSequence if it is styled.
350 * {@more}
351 *
352 * @param id The desired resource identifier, as generated by the aapt
353 * tool. This integer encodes the package, type, and resource
354 * entry. The value 0 is an invalid identifier.
355 *
356 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
357 *
358 * @return CharSequence The string data associated with the resource, plus
359 * possibly styled text information.
360 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800361 @NonNull public CharSequence getText(@StringRes int id) throws NotFoundException {
362 CharSequence res = mResourcesImpl.getAssets().getResourceText(id);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800363 if (res != null) {
364 return res;
365 }
366 throw new NotFoundException("String resource ID #0x"
Clara Bayarri18e9f9f2016-12-19 16:20:29 +0000367 + Integer.toHexString(id));
368 }
369
370 /**
371 * Return the Typeface value associated with a particular resource ID.
372 * {@more}
373 *
374 * @param id The desired resource identifier, as generated by the aapt
375 * tool. This integer encodes the package, type, and resource
376 * entry. The value 0 is an invalid identifier.
377 *
378 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
379 *
380 * @return Typeface The Typeface data associated with the resource.
381 */
Clara Bayarried00bfd2017-01-20 14:58:21 +0000382 @NonNull public Typeface getFont(@FontRes int id) throws NotFoundException {
Clara Bayarri18e9f9f2016-12-19 16:20:29 +0000383 final TypedValue value = obtainTempTypedValue();
384 try {
385 final ResourcesImpl impl = mResourcesImpl;
386 impl.getValue(id, value, true);
Clara Bayarried00bfd2017-01-20 14:58:21 +0000387 Typeface typeface = impl.loadFont(this, value, id);
Clara Bayarri18e9f9f2016-12-19 16:20:29 +0000388 if (typeface != null) {
389 return typeface;
390 }
391 } finally {
392 releaseTempTypedValue(value);
393 }
394 throw new NotFoundException("Font resource ID #0x"
395 + Integer.toHexString(id));
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800396 }
397
Clara Bayarried00bfd2017-01-20 14:58:21 +0000398 @NonNull
399 Typeface getFont(@NonNull TypedValue value, @FontRes int id) throws NotFoundException {
400 return mResourcesImpl.loadFont(this, value, id);
401 }
402
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800403 /**
Clara Bayarri4b5a4d22017-01-27 20:15:45 +0000404 * @hide
405 */
Clara Bayarri2821eea2017-03-17 17:38:50 +0000406 public void preloadFonts(@ArrayRes int id) {
407 final TypedArray array = obtainTypedArray(id);
Clara Bayarri4b5a4d22017-01-27 20:15:45 +0000408 try {
Clara Bayarri2821eea2017-03-17 17:38:50 +0000409 final int size = array.length();
410 for (int i = 0; i < size; i++) {
411 array.getFont(i);
412 }
Clara Bayarri4b5a4d22017-01-27 20:15:45 +0000413 } finally {
Clara Bayarri2821eea2017-03-17 17:38:50 +0000414 array.recycle();
Clara Bayarri4b5a4d22017-01-27 20:15:45 +0000415 }
416 }
417
418 /**
Elliott Hughes95d5ab32013-03-08 11:26:57 -0800419 * Returns the character sequence necessary for grammatically correct pluralization
420 * of the given resource ID for the given quantity.
421 * Note that the character sequence is selected based solely on grammatical necessity,
422 * and that such rules differ between languages. Do not assume you know which string
423 * will be returned for a given quantity. See
424 * <a href="{@docRoot}guide/topics/resources/string-resource.html#Plurals">String Resources</a>
425 * for more detail.
Elliott Hughes1ad636c2010-07-01 16:51:48 -0700426 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800427 * @param id The desired resource identifier, as generated by the aapt
428 * tool. This integer encodes the package, type, and resource
429 * entry. The value 0 is an invalid identifier.
Elliott Hughes1ad636c2010-07-01 16:51:48 -0700430 * @param quantity The number used to get the correct string for the current language's
431 * plural rules.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800432 *
433 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
434 *
435 * @return CharSequence The string data associated with the resource, plus
436 * possibly styled text information.
437 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800438 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -0700439 public CharSequence getQuantityText(@PluralsRes int id, int quantity)
440 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800441 return mResourcesImpl.getQuantityText(id, quantity);
Elliott Hughes1ad636c2010-07-01 16:51:48 -0700442 }
443
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800444 /**
445 * Return the string value associated with a particular resource ID. It
446 * will be stripped of any styled text information.
447 * {@more}
448 *
449 * @param id The desired resource identifier, as generated by the aapt
450 * tool. This integer encodes the package, type, and resource
451 * entry. The value 0 is an invalid identifier.
452 *
453 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
454 *
455 * @return String The string data associated with the resource,
Alan Viveretteb4004df2015-04-29 16:55:42 -0700456 * stripped of styled text information.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800457 */
Alan Viveretteb4004df2015-04-29 16:55:42 -0700458 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -0700459 public String getString(@StringRes int id) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800460 return getText(id).toString();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800461 }
462
463
464 /**
465 * Return the string value associated with a particular resource ID,
466 * substituting the format arguments as defined in {@link java.util.Formatter}
467 * and {@link java.lang.String#format}. It will be stripped of any styled text
468 * information.
469 * {@more}
470 *
471 * @param id The desired resource identifier, as generated by the aapt
472 * tool. This integer encodes the package, type, and resource
473 * entry. The value 0 is an invalid identifier.
474 *
475 * @param formatArgs The format arguments that will be used for substitution.
476 *
477 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
478 *
479 * @return String The string data associated with the resource,
Alan Viveretteb4004df2015-04-29 16:55:42 -0700480 * stripped of styled text information.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800481 */
Alan Viveretteb4004df2015-04-29 16:55:42 -0700482 @NonNull
483 public String getString(@StringRes int id, Object... formatArgs) throws NotFoundException {
484 final String raw = getString(id);
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800485 return String.format(mResourcesImpl.getConfiguration().getLocales().get(0), raw,
486 formatArgs);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800487 }
488
489 /**
Elliott Hughes95d5ab32013-03-08 11:26:57 -0800490 * Formats the string necessary for grammatically correct pluralization
491 * of the given resource ID for the given quantity, using the given arguments.
492 * Note that the string is selected based solely on grammatical necessity,
493 * and that such rules differ between languages. Do not assume you know which string
494 * will be returned for a given quantity. See
495 * <a href="{@docRoot}guide/topics/resources/string-resource.html#Plurals">String Resources</a>
496 * for more detail.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800497 *
Elliott Hughes95d5ab32013-03-08 11:26:57 -0800498 * <p>Substitution of format arguments works as if using
499 * {@link java.util.Formatter} and {@link java.lang.String#format}.
500 * The resulting string will be stripped of any styled text information.
Elliott Hughes1ad636c2010-07-01 16:51:48 -0700501 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800502 * @param id The desired resource identifier, as generated by the aapt
503 * tool. This integer encodes the package, type, and resource
504 * entry. The value 0 is an invalid identifier.
505 * @param quantity The number used to get the correct string for the current language's
506 * plural rules.
507 * @param formatArgs The format arguments that will be used for substitution.
508 *
509 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
510 *
511 * @return String The string data associated with the resource,
512 * stripped of styled text information.
513 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800514 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -0700515 public String getQuantityString(@PluralsRes int id, int quantity, Object... formatArgs)
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800516 throws NotFoundException {
517 String raw = getQuantityText(id, quantity).toString();
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800518 return String.format(mResourcesImpl.getConfiguration().getLocales().get(0), raw,
519 formatArgs);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800520 }
521
522 /**
Elliott Hughes95d5ab32013-03-08 11:26:57 -0800523 * Returns the string necessary for grammatically correct pluralization
524 * of the given resource ID for the given quantity.
525 * Note that the string is selected based solely on grammatical necessity,
526 * and that such rules differ between languages. Do not assume you know which string
527 * will be returned for a given quantity. See
528 * <a href="{@docRoot}guide/topics/resources/string-resource.html#Plurals">String Resources</a>
529 * for more detail.
Elliott Hughes1ad636c2010-07-01 16:51:48 -0700530 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800531 * @param id The desired resource identifier, as generated by the aapt
532 * tool. This integer encodes the package, type, and resource
533 * entry. The value 0 is an invalid identifier.
534 * @param quantity The number used to get the correct string for the current language's
535 * plural rules.
536 *
537 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
538 *
539 * @return String The string data associated with the resource,
540 * stripped of styled text information.
541 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800542 @NonNull
543 public String getQuantityString(@PluralsRes int id, int quantity) throws NotFoundException {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800544 return getQuantityText(id, quantity).toString();
545 }
546
547 /**
548 * Return the string value associated with a particular resource ID. The
549 * returned object will be a String if this is a plain string; it will be
550 * some other type of CharSequence if it is styled.
551 *
552 * @param id The desired resource identifier, as generated by the aapt
553 * tool. This integer encodes the package, type, and resource
554 * entry. The value 0 is an invalid identifier.
555 *
556 * @param def The default CharSequence to return.
557 *
558 * @return CharSequence The string data associated with the resource, plus
559 * possibly styled text information, or def if id is 0 or not found.
560 */
Tor Norbye7b9c9122013-05-30 16:48:33 -0700561 public CharSequence getText(@StringRes int id, CharSequence def) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800562 CharSequence res = id != 0 ? mResourcesImpl.getAssets().getResourceText(id) : null;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800563 return res != null ? res : def;
564 }
565
566 /**
567 * Return the styled text array associated with a particular resource ID.
568 *
569 * @param id The desired resource identifier, as generated by the aapt
570 * tool. This integer encodes the package, type, and resource
571 * entry. The value 0 is an invalid identifier.
572 *
573 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
574 *
575 * @return The styled text array associated with the resource.
576 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800577 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -0700578 public CharSequence[] getTextArray(@ArrayRes int id) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800579 CharSequence[] res = mResourcesImpl.getAssets().getResourceTextArray(id);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800580 if (res != null) {
581 return res;
582 }
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800583 throw new NotFoundException("Text array resource ID #0x" + Integer.toHexString(id));
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800584 }
585
586 /**
587 * Return the string array associated with a particular resource ID.
588 *
589 * @param id The desired resource identifier, as generated by the aapt
590 * tool. This integer encodes the package, type, and resource
591 * entry. The value 0 is an invalid identifier.
592 *
593 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
594 *
595 * @return The string array associated with the resource.
596 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800597 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -0700598 public String[] getStringArray(@ArrayRes int id)
599 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800600 String[] res = mResourcesImpl.getAssets().getResourceStringArray(id);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800601 if (res != null) {
602 return res;
603 }
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800604 throw new NotFoundException("String array resource ID #0x" + Integer.toHexString(id));
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800605 }
606
607 /**
608 * Return the int array associated with a particular resource ID.
609 *
610 * @param id The desired resource identifier, as generated by the aapt
611 * tool. This integer encodes the package, type, and resource
612 * entry. The value 0 is an invalid identifier.
613 *
614 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
615 *
616 * @return The int array associated with the resource.
617 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800618 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -0700619 public int[] getIntArray(@ArrayRes int id) throws NotFoundException {
Adam Lesinskibebfcc42018-02-12 14:27:46 -0800620 int[] res = mResourcesImpl.getAssets().getResourceIntArray(id);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800621 if (res != null) {
622 return res;
623 }
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800624 throw new NotFoundException("Int array resource ID #0x" + Integer.toHexString(id));
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800625 }
626
627 /**
628 * Return an array of heterogeneous values.
629 *
630 * @param id The desired resource identifier, as generated by the aapt
631 * tool. This integer encodes the package, type, and resource
632 * entry. The value 0 is an invalid identifier.
633 *
634 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
635 *
636 * @return Returns a TypedArray holding an array of the array values.
637 * Be sure to call {@link TypedArray#recycle() TypedArray.recycle()}
638 * when done with it.
639 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800640 @NonNull
641 public TypedArray obtainTypedArray(@ArrayRes int id) throws NotFoundException {
642 final ResourcesImpl impl = mResourcesImpl;
Adam Lesinskibebfcc42018-02-12 14:27:46 -0800643 int len = impl.getAssets().getResourceArraySize(id);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800644 if (len < 0) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800645 throw new NotFoundException("Array resource ID #0x" + Integer.toHexString(id));
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800646 }
647
Alan Viverette52b999f2014-03-24 18:00:26 -0700648 TypedArray array = TypedArray.obtain(this, len);
Adam Lesinskibebfcc42018-02-12 14:27:46 -0800649 array.mLength = impl.getAssets().getResourceArray(id, array.mData);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800650 array.mIndices[0] = 0;
651
652 return array;
653 }
654
655 /**
656 * Retrieve a dimensional for a particular resource ID. Unit
657 * conversions are based on the current {@link DisplayMetrics} associated
658 * with the resources.
659 *
660 * @param id The desired resource identifier, as generated by the aapt
661 * tool. This integer encodes the package, type, and resource
662 * entry. The value 0 is an invalid identifier.
663 *
Danny Epstein4ffbd472018-06-29 16:21:03 -0700664 * @return Resource dimension value multiplied by the appropriate metric to convert to pixels.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800665 *
666 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
667 *
668 * @see #getDimensionPixelOffset
669 * @see #getDimensionPixelSize
670 */
Tor Norbye7b9c9122013-05-30 16:48:33 -0700671 public float getDimension(@DimenRes int id) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800672 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -0500673 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800674 final ResourcesImpl impl = mResourcesImpl;
675 impl.getValue(id, value, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800676 if (value.type == TypedValue.TYPE_DIMENSION) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800677 return TypedValue.complexToDimension(value.data, impl.getDisplayMetrics());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800678 }
Alan Viverette4d07bc92015-11-16 10:19:12 -0500679 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
680 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
681 } finally {
682 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800683 }
684 }
685
686 /**
687 * Retrieve a dimensional for a particular resource ID for use
688 * as an offset in raw pixels. This is the same as
689 * {@link #getDimension}, except the returned value is converted to
690 * integer pixels for you. An offset conversion involves simply
691 * truncating the base value to an integer.
692 *
693 * @param id The desired resource identifier, as generated by the aapt
694 * tool. This integer encodes the package, type, and resource
695 * entry. The value 0 is an invalid identifier.
696 *
697 * @return Resource dimension value multiplied by the appropriate
698 * metric and truncated to integer pixels.
699 *
700 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
701 *
702 * @see #getDimension
703 * @see #getDimensionPixelSize
704 */
Tor Norbye7b9c9122013-05-30 16:48:33 -0700705 public int getDimensionPixelOffset(@DimenRes int id) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800706 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -0500707 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800708 final ResourcesImpl impl = mResourcesImpl;
709 impl.getValue(id, value, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800710 if (value.type == TypedValue.TYPE_DIMENSION) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800711 return TypedValue.complexToDimensionPixelOffset(value.data,
712 impl.getDisplayMetrics());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800713 }
Alan Viverette4d07bc92015-11-16 10:19:12 -0500714 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
715 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
716 } finally {
717 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800718 }
719 }
720
721 /**
722 * Retrieve a dimensional for a particular resource ID for use
723 * as a size in raw pixels. This is the same as
724 * {@link #getDimension}, except the returned value is converted to
725 * integer pixels for use as a size. A size conversion involves
726 * rounding the base value, and ensuring that a non-zero base value
727 * is at least one pixel in size.
728 *
729 * @param id The desired resource identifier, as generated by the aapt
730 * tool. This integer encodes the package, type, and resource
731 * entry. The value 0 is an invalid identifier.
732 *
733 * @return Resource dimension value multiplied by the appropriate
734 * metric and truncated to integer pixels.
735 *
736 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
737 *
738 * @see #getDimension
739 * @see #getDimensionPixelOffset
740 */
Tor Norbye7b9c9122013-05-30 16:48:33 -0700741 public int getDimensionPixelSize(@DimenRes int id) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800742 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -0500743 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800744 final ResourcesImpl impl = mResourcesImpl;
745 impl.getValue(id, value, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800746 if (value.type == TypedValue.TYPE_DIMENSION) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800747 return TypedValue.complexToDimensionPixelSize(value.data, impl.getDisplayMetrics());
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800748 }
Alan Viverette4d07bc92015-11-16 10:19:12 -0500749 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
750 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
751 } finally {
752 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800753 }
754 }
755
756 /**
757 * Retrieve a fractional unit for a particular resource ID.
758 *
759 * @param id The desired resource identifier, as generated by the aapt
760 * tool. This integer encodes the package, type, and resource
761 * entry. The value 0 is an invalid identifier.
762 * @param base The base value of this fraction. In other words, a
763 * standard fraction is multiplied by this value.
764 * @param pbase The parent base value of this fraction. In other
765 * words, a parent fraction (nn%p) is multiplied by this
766 * value.
767 *
768 * @return Attribute fractional value multiplied by the appropriate
769 * base value.
770 *
771 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
772 */
Tor Norbye7b9c9122013-05-30 16:48:33 -0700773 public float getFraction(@FractionRes int id, int base, int pbase) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800774 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -0500775 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800776 mResourcesImpl.getValue(id, value, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800777 if (value.type == TypedValue.TYPE_FRACTION) {
778 return TypedValue.complexToFraction(value.data, base, pbase);
779 }
Alan Viverette4d07bc92015-11-16 10:19:12 -0500780 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
781 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
782 } finally {
783 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800784 }
785 }
786
787 /**
788 * Return a drawable object associated with a particular resource ID.
789 * Various types of objects will be returned depending on the underlying
790 * resource -- for example, a solid color, PNG image, scalable image, etc.
791 * The Drawable API hides these implementation details.
Dianne Hackbornfb5c3db2012-05-18 15:24:24 -0700792 *
793 * <p class="note"><strong>Note:</strong> Prior to
794 * {@link android.os.Build.VERSION_CODES#JELLY_BEAN}, this function
795 * would not correctly retrieve the final configuration density when
796 * the resource ID passed here is an alias to another Drawable resource.
797 * This means that if the density configuration of the alias resource
798 * is different than the actual resource, the density of the returned
Alan Viverette952802e2016-04-04 15:33:41 -0400799 * Drawable would be incorrect, resulting in bad scaling. To work
800 * around this, you can instead manually resolve the aliased reference
801 * by using {@link #getValue(int, TypedValue, boolean)} and passing
802 * {@code true} for {@code resolveRefs}. The resulting
803 * {@link TypedValue#resourceId} value may be passed to this method.</p>
Dianne Hackbornfb5c3db2012-05-18 15:24:24 -0700804 *
Alan Viverette6dbe51b2014-06-02 16:39:04 -0700805 * <p class="note"><strong>Note:</strong> To obtain a themed drawable, use
806 * {@link android.content.Context#getDrawable(int) Context.getDrawable(int)}
807 * or {@link #getDrawable(int, Theme)} passing the desired theme.</p>
808 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800809 * @param id The desired resource identifier, as generated by the aapt
810 * tool. This integer encodes the package, type, and resource
811 * entry. The value 0 is an invalid identifier.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800812 * @return Drawable An object that can be used to draw this resource.
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800813 * @throws NotFoundException Throws NotFoundException if the given ID does
814 * not exist.
Alan Viverette6dbe51b2014-06-02 16:39:04 -0700815 * @see #getDrawable(int, Theme)
Alan Viverettec10e3962014-12-02 14:58:08 -0800816 * @deprecated Use {@link #getDrawable(int, Theme)} instead.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800817 */
Alan Viverettec10e3962014-12-02 14:58:08 -0800818 @Deprecated
Tor Norbye7b9c9122013-05-30 16:48:33 -0700819 public Drawable getDrawable(@DrawableRes int id) throws NotFoundException {
Alan Viverette34a14f962014-08-15 16:13:15 -0700820 final Drawable d = getDrawable(id, null);
Alan Viverette7e0aaae2014-11-24 11:27:09 -0800821 if (d != null && d.canApplyTheme()) {
Alan Viverette34a14f962014-08-15 16:13:15 -0700822 Log.w(TAG, "Drawable " + getResourceName(id) + " has unresolved theme "
823 + "attributes! Consider using Resources.getDrawable(int, Theme) or "
824 + "Context.getDrawable(int).", new RuntimeException());
825 }
826 return d;
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800827 }
828
829 /**
830 * Return a drawable object associated with a particular resource ID and
Alan Viverette6dbe51b2014-06-02 16:39:04 -0700831 * styled for the specified theme. Various types of objects will be
832 * returned depending on the underlying resource -- for example, a solid
833 * color, PNG image, scalable image, etc.
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800834 *
835 * @param id The desired resource identifier, as generated by the aapt
836 * tool. This integer encodes the package, type, and resource
837 * entry. The value 0 is an invalid identifier.
Alan Viverette3b5c4272014-05-20 13:20:42 -0700838 * @param theme The theme used to style the drawable attributes, may be {@code null}.
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800839 * @return Drawable An object that can be used to draw this resource.
840 * @throws NotFoundException Throws NotFoundException if the given ID does
841 * not exist.
842 */
Alan Viverette4d07bc92015-11-16 10:19:12 -0500843 public Drawable getDrawable(@DrawableRes int id, @Nullable Theme theme)
844 throws NotFoundException {
Adam Lesinski50954d22017-04-14 18:41:52 -0700845 return getDrawableForDensity(id, 0, theme);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800846 }
847
848 /**
Kenny Root55fc8502010-10-28 14:47:01 -0700849 * Return a drawable object associated with a particular resource ID for the
850 * given screen density in DPI. This will set the drawable's density to be
851 * the device's density multiplied by the ratio of actual drawable density
852 * to requested density. This allows the drawable to be scaled up to the
853 * correct size if needed. Various types of objects will be returned
854 * depending on the underlying resource -- for example, a solid color, PNG
855 * image, scalable image, etc. The Drawable API hides these implementation
856 * details.
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800857 *
Alan Viverette6dbe51b2014-06-02 16:39:04 -0700858 * <p class="note"><strong>Note:</strong> To obtain a themed drawable, use
859 * {@link android.content.Context#getDrawable(int) Context.getDrawable(int)}
860 * or {@link #getDrawableForDensity(int, int, Theme)} passing the desired
861 * theme.</p>
862 *
Kenny Root55fc8502010-10-28 14:47:01 -0700863 * @param id The desired resource identifier, as generated by the aapt tool.
864 * This integer encodes the package, type, and resource entry.
865 * The value 0 is an invalid identifier.
866 * @param density the desired screen density indicated by the resource as
Adam Lesinski50954d22017-04-14 18:41:52 -0700867 * found in {@link DisplayMetrics}. A value of 0 means to use the
868 * density returned from {@link #getConfiguration()}.
869 * This is equivalent to calling {@link #getDrawable(int)}.
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800870 * @return Drawable An object that can be used to draw this resource.
Kenny Root55fc8502010-10-28 14:47:01 -0700871 * @throws NotFoundException Throws NotFoundException if the given ID does
872 * not exist.
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800873 * @see #getDrawableForDensity(int, int, Theme)
Alan Viverettea6f8b2c2014-12-02 15:26:33 -0800874 * @deprecated Use {@link #getDrawableForDensity(int, int, Theme)} instead.
Kenny Root55fc8502010-10-28 14:47:01 -0700875 */
Chris Craik1194b0b2018-03-23 13:36:24 -0700876 @Nullable
Alan Viverettea6f8b2c2014-12-02 15:26:33 -0800877 @Deprecated
Alan Viverette4d07bc92015-11-16 10:19:12 -0500878 public Drawable getDrawableForDensity(@DrawableRes int id, int density)
879 throws NotFoundException {
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800880 return getDrawableForDensity(id, density, null);
881 }
882
883 /**
884 * Return a drawable object associated with a particular resource ID for the
885 * given screen density in DPI and styled for the specified theme.
886 *
887 * @param id The desired resource identifier, as generated by the aapt tool.
888 * This integer encodes the package, type, and resource entry.
889 * The value 0 is an invalid identifier.
890 * @param density The desired screen density indicated by the resource as
Adam Lesinski50954d22017-04-14 18:41:52 -0700891 * found in {@link DisplayMetrics}. A value of 0 means to use the
892 * density returned from {@link #getConfiguration()}.
893 * This is equivalent to calling {@link #getDrawable(int, Theme)}.
Chris Craik1194b0b2018-03-23 13:36:24 -0700894 * @param theme The theme used to style the drawable attributes, may be {@code null} if the
895 * drawable cannot be decoded.
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800896 * @return Drawable An object that can be used to draw this resource.
897 * @throws NotFoundException Throws NotFoundException if the given ID does
Chris Craik1194b0b2018-03-23 13:36:24 -0700898 * not exist.
Alan Viverette8eea3ea2014-02-03 18:40:20 -0800899 */
Chris Craik1194b0b2018-03-23 13:36:24 -0700900 @Nullable
Tor Norbye7b9c9122013-05-30 16:48:33 -0700901 public Drawable getDrawableForDensity(@DrawableRes int id, int density, @Nullable Theme theme) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800902 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -0500903 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800904 final ResourcesImpl impl = mResourcesImpl;
905 impl.getValueForDensity(id, density, value, true);
Adam Lesinski50954d22017-04-14 18:41:52 -0700906 return impl.loadDrawable(this, value, id, density, theme);
Alan Viverette4d07bc92015-11-16 10:19:12 -0500907 } finally {
908 releaseTempTypedValue(value);
Dianne Hackborn50707cc2013-02-08 15:32:05 -0800909 }
Kenny Root55fc8502010-10-28 14:47:01 -0700910 }
911
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800912 @NonNull
Mathew Inwood5c0d3542018-08-14 13:54:31 +0100913 @UnsupportedAppUsage
Adam Lesinski50954d22017-04-14 18:41:52 -0700914 Drawable loadDrawable(@NonNull TypedValue value, int id, int density, @Nullable Theme theme)
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800915 throws NotFoundException {
Adam Lesinski50954d22017-04-14 18:41:52 -0700916 return mResourcesImpl.loadDrawable(this, value, id, density, theme);
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800917 }
918
Kenny Root55fc8502010-10-28 14:47:01 -0700919 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800920 * Return a movie object associated with the particular resource ID.
921 * @param id The desired resource identifier, as generated by the aapt
922 * tool. This integer encodes the package, type, and resource
923 * entry. The value 0 is an invalid identifier.
924 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
Aurimas Liutikasf0764b52018-08-22 12:55:04 -0700925 *
926 * @deprecated Prefer {@link android.graphics.drawable.AnimatedImageDrawable}.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800927 */
Aurimas Liutikasf0764b52018-08-22 12:55:04 -0700928 @Deprecated
Tor Norbye7b9c9122013-05-30 16:48:33 -0700929 public Movie getMovie(@RawRes int id) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800930 final InputStream is = openRawResource(id);
931 final Movie movie = Movie.decodeStream(is);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800932 try {
933 is.close();
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800934 } catch (IOException e) {
935 // No one cares.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800936 }
937 return movie;
938 }
939
940 /**
Alan Viverette45c4bbb2015-01-05 14:59:19 -0800941 * Returns a color integer associated with a particular resource ID. If the
942 * resource holds a complex {@link ColorStateList}, then the default color
943 * from the set is returned.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800944 *
945 * @param id The desired resource identifier, as generated by the aapt
946 * tool. This integer encodes the package, type, and resource
947 * entry. The value 0 is an invalid identifier.
948 *
Alan Viverette45c4bbb2015-01-05 14:59:19 -0800949 * @throws NotFoundException Throws NotFoundException if the given ID does
950 * not exist.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800951 *
Alan Viverette45c4bbb2015-01-05 14:59:19 -0800952 * @return A single color value in the form 0xAARRGGBB.
953 * @deprecated Use {@link #getColor(int, Theme)} instead.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800954 */
Tor Norbye80756e32015-03-02 09:39:27 -0800955 @ColorInt
Alan Viverette4a357cd2015-03-18 18:37:18 -0700956 @Deprecated
Tor Norbye7b9c9122013-05-30 16:48:33 -0700957 public int getColor(@ColorRes int id) throws NotFoundException {
Alan Viverette45c4bbb2015-01-05 14:59:19 -0800958 return getColor(id, null);
959 }
960
961 /**
962 * Returns a themed color integer associated with a particular resource ID.
963 * If the resource holds a complex {@link ColorStateList}, then the default
964 * color from the set is returned.
965 *
966 * @param id The desired resource identifier, as generated by the aapt
967 * tool. This integer encodes the package, type, and resource
968 * entry. The value 0 is an invalid identifier.
969 * @param theme The theme used to style the color attributes, may be
970 * {@code null}.
971 *
972 * @throws NotFoundException Throws NotFoundException if the given ID does
973 * not exist.
974 *
975 * @return A single color value in the form 0xAARRGGBB.
976 */
Tor Norbye80756e32015-03-02 09:39:27 -0800977 @ColorInt
Tor Norbye7b9c9122013-05-30 16:48:33 -0700978 public int getColor(@ColorRes int id, @Nullable Theme theme) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800979 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -0500980 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800981 final ResourcesImpl impl = mResourcesImpl;
982 impl.getValue(id, value, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800983 if (value.type >= TypedValue.TYPE_FIRST_INT
Alan Viverette45c4bbb2015-01-05 14:59:19 -0800984 && value.type <= TypedValue.TYPE_LAST_INT) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800985 return value.data;
Dianne Hackborn50707cc2013-02-08 15:32:05 -0800986 } else if (value.type != TypedValue.TYPE_STRING) {
Alan Viverette4d07bc92015-11-16 10:19:12 -0500987 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
988 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800989 }
Alan Viverette45c4bbb2015-01-05 14:59:19 -0800990
Adam Lesinskifb302cc2016-02-29 16:50:38 -0800991 final ColorStateList csl = impl.loadColorStateList(this, value, id, theme);
Alan Viverette4d07bc92015-11-16 10:19:12 -0500992 return csl.getDefaultColor();
993 } finally {
994 releaseTempTypedValue(value);
Dianne Hackborn50707cc2013-02-08 15:32:05 -0800995 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800996 }
997
998 /**
Alan Viverette45c4bbb2015-01-05 14:59:19 -0800999 * Returns a color state list associated with a particular resource ID. The
1000 * resource may contain either a single raw color value or a complex
1001 * {@link ColorStateList} holding multiple possible colors.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001002 *
1003 * @param id The desired resource identifier of a {@link ColorStateList},
Alan Viverette45c4bbb2015-01-05 14:59:19 -08001004 * as generated by the aapt tool. This integer encodes the
1005 * package, type, and resource entry. The value 0 is an invalid
1006 * identifier.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001007 *
Alan Viverette45c4bbb2015-01-05 14:59:19 -08001008 * @throws NotFoundException Throws NotFoundException if the given ID does
1009 * not exist.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001010 *
Alan Viverette45c4bbb2015-01-05 14:59:19 -08001011 * @return A ColorStateList object containing either a single solid color
1012 * or multiple colors that can be selected based on a state.
1013 * @deprecated Use {@link #getColorStateList(int, Theme)} instead.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001014 */
Chris Craikceb26932018-02-01 15:51:34 -08001015 @NonNull
Alan Viverette4a357cd2015-03-18 18:37:18 -07001016 @Deprecated
Tor Norbye7b9c9122013-05-30 16:48:33 -07001017 public ColorStateList getColorStateList(@ColorRes int id) throws NotFoundException {
Alan Viverette45c4bbb2015-01-05 14:59:19 -08001018 final ColorStateList csl = getColorStateList(id, null);
1019 if (csl != null && csl.canApplyTheme()) {
1020 Log.w(TAG, "ColorStateList " + getResourceName(id) + " has "
1021 + "unresolved theme attributes! Consider using "
1022 + "Resources.getColorStateList(int, Theme) or "
1023 + "Context.getColorStateList(int).", new RuntimeException());
1024 }
1025 return csl;
1026 }
1027
1028 /**
1029 * Returns a themed color state list associated with a particular resource
1030 * ID. The resource may contain either a single raw color value or a
1031 * complex {@link ColorStateList} holding multiple possible colors.
1032 *
1033 * @param id The desired resource identifier of a {@link ColorStateList},
1034 * as generated by the aapt tool. This integer encodes the
1035 * package, type, and resource entry. The value 0 is an invalid
1036 * identifier.
1037 * @param theme The theme used to style the color attributes, may be
1038 * {@code null}.
1039 *
1040 * @throws NotFoundException Throws NotFoundException if the given ID does
1041 * not exist.
1042 *
1043 * @return A themed ColorStateList object containing either a single solid
1044 * color or multiple colors that can be selected based on a state.
1045 */
Chris Craikceb26932018-02-01 15:51:34 -08001046 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -07001047 public ColorStateList getColorStateList(@ColorRes int id, @Nullable Theme theme)
Alan Viverette45c4bbb2015-01-05 14:59:19 -08001048 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001049 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -05001050 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001051 final ResourcesImpl impl = mResourcesImpl;
1052 impl.getValue(id, value, true);
1053 return impl.loadColorStateList(this, value, id, theme);
Alan Viverette4d07bc92015-11-16 10:19:12 -05001054 } finally {
1055 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001056 }
1057 }
1058
Chris Craikceb26932018-02-01 15:51:34 -08001059 @NonNull
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001060 ColorStateList loadColorStateList(@NonNull TypedValue value, int id, @Nullable Theme theme)
1061 throws NotFoundException {
1062 return mResourcesImpl.loadColorStateList(this, value, id, theme);
1063 }
1064
Teng-Hui Zhue03c4692016-03-17 10:38:43 -07001065 /**
1066 * @hide
1067 */
Chris Craikceb26932018-02-01 15:51:34 -08001068 @NonNull
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001069 public ComplexColor loadComplexColor(@NonNull TypedValue value, int id, @Nullable Theme theme) {
1070 return mResourcesImpl.loadComplexColor(this, value, id, theme);
1071 }
1072
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001073 /**
1074 * Return a boolean associated with a particular resource ID. This can be
1075 * used with any integral resource value, and will return true if it is
1076 * non-zero.
1077 *
1078 * @param id The desired resource identifier, as generated by the aapt
1079 * tool. This integer encodes the package, type, and resource
1080 * entry. The value 0 is an invalid identifier.
1081 *
1082 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1083 *
1084 * @return Returns the boolean value contained in the resource.
1085 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07001086 public boolean getBoolean(@BoolRes int id) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001087 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -05001088 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001089 mResourcesImpl.getValue(id, value, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001090 if (value.type >= TypedValue.TYPE_FIRST_INT
Alan Viverette4d07bc92015-11-16 10:19:12 -05001091 && value.type <= TypedValue.TYPE_LAST_INT) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001092 return value.data != 0;
1093 }
Alan Viverette4d07bc92015-11-16 10:19:12 -05001094 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
1095 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
1096 } finally {
1097 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001098 }
1099 }
1100
1101 /**
1102 * Return an integer associated with a particular resource ID.
1103 *
1104 * @param id The desired resource identifier, as generated by the aapt
1105 * tool. This integer encodes the package, type, and resource
1106 * entry. The value 0 is an invalid identifier.
1107 *
1108 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1109 *
1110 * @return Returns the integer value contained in the resource.
1111 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07001112 public int getInteger(@IntegerRes int id) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001113 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -05001114 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001115 mResourcesImpl.getValue(id, value, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001116 if (value.type >= TypedValue.TYPE_FIRST_INT
Alan Viverette4d07bc92015-11-16 10:19:12 -05001117 && value.type <= TypedValue.TYPE_LAST_INT) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001118 return value.data;
1119 }
Alan Viverette4d07bc92015-11-16 10:19:12 -05001120 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
1121 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
1122 } finally {
1123 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001124 }
1125 }
1126
1127 /**
Alan Viveretteb1e1dbf2014-08-07 17:17:43 -07001128 * Retrieve a floating-point value for a particular resource ID.
1129 *
1130 * @param id The desired resource identifier, as generated by the aapt
1131 * tool. This integer encodes the package, type, and resource
1132 * entry. The value 0 is an invalid identifier.
1133 *
1134 * @return Returns the floating-point value contained in the resource.
1135 *
1136 * @throws NotFoundException Throws NotFoundException if the given ID does
1137 * not exist or is not a floating-point value.
Alan Viveretteb1e1dbf2014-08-07 17:17:43 -07001138 */
Jake Wharton32365b92018-09-07 16:09:21 -04001139 public float getFloat(@DimenRes int id) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001140 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -05001141 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001142 mResourcesImpl.getValue(id, value, true);
Alan Viveretteb1e1dbf2014-08-07 17:17:43 -07001143 if (value.type == TypedValue.TYPE_FLOAT) {
1144 return value.getFloat();
1145 }
Alan Viverette4d07bc92015-11-16 10:19:12 -05001146 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
1147 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
1148 } finally {
1149 releaseTempTypedValue(value);
Alan Viveretteb1e1dbf2014-08-07 17:17:43 -07001150 }
1151 }
1152
1153 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001154 * Return an XmlResourceParser through which you can read a view layout
1155 * description for the given resource ID. This parser has limited
1156 * functionality -- in particular, you can't change its input, and only
1157 * the high-level events are available.
1158 *
1159 * <p>This function is really a simple wrapper for calling
1160 * {@link #getXml} with a layout resource.
1161 *
1162 * @param id The desired resource identifier, as generated by the aapt
1163 * tool. This integer encodes the package, type, and resource
1164 * entry. The value 0 is an invalid identifier.
1165 *
1166 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1167 *
1168 * @return A new parser object through which you can read
1169 * the XML data.
1170 *
1171 * @see #getXml
1172 */
Chris Craikceb26932018-02-01 15:51:34 -08001173 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -07001174 public XmlResourceParser getLayout(@LayoutRes int id) throws NotFoundException {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001175 return loadXmlResourceParser(id, "layout");
1176 }
1177
1178 /**
1179 * Return an XmlResourceParser through which you can read an animation
1180 * description for the given resource ID. This parser has limited
1181 * functionality -- in particular, you can't change its input, and only
1182 * the high-level events are available.
1183 *
1184 * <p>This function is really a simple wrapper for calling
1185 * {@link #getXml} with an animation resource.
1186 *
1187 * @param id The desired resource identifier, as generated by the aapt
1188 * tool. This integer encodes the package, type, and resource
1189 * entry. The value 0 is an invalid identifier.
1190 *
1191 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1192 *
1193 * @return A new parser object through which you can read
1194 * the XML data.
1195 *
1196 * @see #getXml
1197 */
Chris Craikceb26932018-02-01 15:51:34 -08001198 @NonNull
ztenghuib5292562017-07-11 16:03:36 -07001199 public XmlResourceParser getAnimation(@AnimatorRes @AnimRes int id) throws NotFoundException {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001200 return loadXmlResourceParser(id, "anim");
1201 }
1202
1203 /**
1204 * Return an XmlResourceParser through which you can read a generic XML
1205 * resource for the given resource ID.
1206 *
1207 * <p>The XmlPullParser implementation returned here has some limited
1208 * functionality. In particular, you can't change its input, and only
1209 * high-level parsing events are available (since the document was
1210 * pre-parsed for you at build time, which involved merging text and
1211 * stripping comments).
1212 *
1213 * @param id The desired resource identifier, as generated by the aapt
1214 * tool. This integer encodes the package, type, and resource
1215 * entry. The value 0 is an invalid identifier.
1216 *
1217 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1218 *
1219 * @return A new parser object through which you can read
1220 * the XML data.
1221 *
1222 * @see android.util.AttributeSet
1223 */
Chris Craikceb26932018-02-01 15:51:34 -08001224 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -07001225 public XmlResourceParser getXml(@XmlRes int id) throws NotFoundException {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001226 return loadXmlResourceParser(id, "xml");
1227 }
1228
1229 /**
1230 * Open a data stream for reading a raw resource. This can only be used
1231 * with resources whose value is the name of an asset files -- that is, it can be
1232 * used to open drawable, sound, and raw resources; it will fail on string
1233 * and color resources.
1234 *
Adam Lesinski50954d22017-04-14 18:41:52 -07001235 * @param id The resource identifier to open, as generated by the aapt tool.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001236 *
1237 * @return InputStream Access to the resource data.
1238 *
1239 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001240 */
Chris Craikceb26932018-02-01 15:51:34 -08001241 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -07001242 public InputStream openRawResource(@RawRes int id) throws NotFoundException {
Alan Viverette4d07bc92015-11-16 10:19:12 -05001243 final TypedValue value = obtainTempTypedValue();
1244 try {
1245 return openRawResource(id, value);
1246 } finally {
1247 releaseTempTypedValue(value);
1248 }
1249 }
1250
1251 /**
Alan Viverette4d07bc92015-11-16 10:19:12 -05001252 * Returns a TypedValue suitable for temporary use. The obtained TypedValue
1253 * should be released using {@link #releaseTempTypedValue(TypedValue)}.
1254 *
1255 * @return a typed value suitable for temporary use
1256 */
1257 private TypedValue obtainTempTypedValue() {
1258 TypedValue tmpValue = null;
1259 synchronized (mTmpValueLock) {
1260 if (mTmpValue != null) {
1261 tmpValue = mTmpValue;
Dianne Hackborn50707cc2013-02-08 15:32:05 -08001262 mTmpValue = null;
1263 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001264 }
Alan Viverette4d07bc92015-11-16 10:19:12 -05001265 if (tmpValue == null) {
1266 return new TypedValue();
1267 }
1268 return tmpValue;
1269 }
1270
1271 /**
1272 * Returns a TypedValue to the pool. After calling this method, the
1273 * specified TypedValue should no longer be accessed.
1274 *
1275 * @param value the typed value to return to the pool
1276 */
1277 private void releaseTempTypedValue(TypedValue value) {
1278 synchronized (mTmpValueLock) {
Dianne Hackborn50707cc2013-02-08 15:32:05 -08001279 if (mTmpValue == null) {
1280 mTmpValue = value;
1281 }
1282 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001283 }
1284
1285 /**
1286 * Open a data stream for reading a raw resource. This can only be used
Andy Stadlerf8a7cea2009-04-10 16:24:47 -07001287 * with resources whose value is the name of an asset file -- that is, it can be
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001288 * used to open drawable, sound, and raw resources; it will fail on string
1289 * and color resources.
1290 *
Adam Lesinski50954d22017-04-14 18:41:52 -07001291 * @param id The resource identifier to open, as generated by the aapt tool.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001292 * @param value The TypedValue object to hold the resource information.
1293 *
1294 * @return InputStream Access to the resource data.
1295 *
1296 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001297 */
Chris Craikceb26932018-02-01 15:51:34 -08001298 @NonNull
Tor Norbye7b9c9122013-05-30 16:48:33 -07001299 public InputStream openRawResource(@RawRes int id, TypedValue value)
1300 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001301 return mResourcesImpl.openRawResource(id, value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001302 }
1303
1304 /**
1305 * Open a file descriptor for reading a raw resource. This can only be used
1306 * with resources whose value is the name of an asset files -- that is, it can be
1307 * used to open drawable, sound, and raw resources; it will fail on string
1308 * and color resources.
1309 *
1310 * <p>This function only works for resources that are stored in the package
1311 * as uncompressed data, which typically includes things like mp3 files
1312 * and png images.
1313 *
Adam Lesinski50954d22017-04-14 18:41:52 -07001314 * @param id The resource identifier to open, as generated by the aapt tool.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001315 *
1316 * @return AssetFileDescriptor A new file descriptor you can use to read
1317 * the resource. This includes the file descriptor itself, as well as the
1318 * offset and length of data where the resource appears in the file. A
1319 * null is returned if the file exists but is compressed.
1320 *
1321 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1322 *
1323 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07001324 public AssetFileDescriptor openRawResourceFd(@RawRes int id)
1325 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001326 final TypedValue value = obtainTempTypedValue();
Dianne Hackborn50707cc2013-02-08 15:32:05 -08001327 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001328 return mResourcesImpl.openRawResourceFd(id, value);
Dianne Hackborn50707cc2013-02-08 15:32:05 -08001329 } finally {
Alan Viverette4d07bc92015-11-16 10:19:12 -05001330 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001331 }
1332 }
1333
1334 /**
1335 * Return the raw data associated with a particular resource ID.
1336 *
1337 * @param id The desired resource identifier, as generated by the aapt
1338 * tool. This integer encodes the package, type, and resource
1339 * entry. The value 0 is an invalid identifier.
1340 * @param outValue Object in which to place the resource data.
1341 * @param resolveRefs If true, a resource that is a reference to another
1342 * resource will be followed so that you receive the
1343 * actual final resource data. If false, the TypedValue
1344 * will be filled in with the reference itself.
1345 *
1346 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1347 *
1348 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07001349 public void getValue(@AnyRes int id, TypedValue outValue, boolean resolveRefs)
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001350 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001351 mResourcesImpl.getValue(id, outValue, resolveRefs);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001352 }
1353
1354 /**
Kenny Root55fc8502010-10-28 14:47:01 -07001355 * Get the raw value associated with a resource with associated density.
1356 *
1357 * @param id resource identifier
1358 * @param density density in DPI
1359 * @param resolveRefs If true, a resource that is a reference to another
1360 * resource will be followed so that you receive the actual final
1361 * resource data. If false, the TypedValue will be filled in with
1362 * the reference itself.
1363 * @throws NotFoundException Throws NotFoundException if the given ID does
1364 * not exist.
1365 * @see #getValue(String, TypedValue, boolean)
Kenny Root55fc8502010-10-28 14:47:01 -07001366 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07001367 public void getValueForDensity(@AnyRes int id, int density, TypedValue outValue,
1368 boolean resolveRefs) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001369 mResourcesImpl.getValueForDensity(id, density, outValue, resolveRefs);
Kenny Root55fc8502010-10-28 14:47:01 -07001370 }
1371
1372 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001373 * Return the raw data associated with a particular resource ID.
1374 * See getIdentifier() for information on how names are mapped to resource
1375 * IDs, and getString(int) for information on how string resources are
1376 * retrieved.
1377 *
1378 * <p>Note: use of this function is discouraged. It is much more
1379 * efficient to retrieve resources by identifier than by name.
1380 *
1381 * @param name The name of the desired resource. This is passed to
1382 * getIdentifier() with a default type of "string".
1383 * @param outValue Object in which to place the resource data.
1384 * @param resolveRefs If true, a resource that is a reference to another
1385 * resource will be followed so that you receive the
1386 * actual final resource data. If false, the TypedValue
1387 * will be filled in with the reference itself.
1388 *
1389 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1390 *
1391 */
1392 public void getValue(String name, TypedValue outValue, boolean resolveRefs)
1393 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001394 mResourcesImpl.getValue(name, outValue, resolveRefs);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001395 }
1396
Aurimas Liutikasaae06632019-01-30 13:16:27 -08001397
1398 /**
1399 * @param set AttributeSet for which we want to find the source.
1400 * @return The resource id for the source that is backing the given AttributeSet
1401 * @hide
1402 */
1403 @AnyRes
1404 public static int getAttributeSetSourceResId(@Nullable AttributeSet set) {
1405 return ResourcesImpl.getAttributeSetSourceResId(set);
1406 }
1407
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001408 /**
1409 * This class holds the current attribute values for a particular theme.
1410 * In other words, a Theme is a set of values for resource attributes;
1411 * these are used in conjunction with {@link TypedArray}
1412 * to resolve the final value for an attribute.
1413 *
1414 * <p>The Theme's attributes come into play in two ways: (1) a styled
1415 * attribute can explicit reference a value in the theme through the
1416 * "?themeAttribute" syntax; (2) if no value has been defined for a
1417 * particular styled attribute, as a last resort we will try to find that
1418 * attribute's value in the Theme.
1419 *
1420 * <p>You will normally use the {@link #obtainStyledAttributes} APIs to
1421 * retrieve XML attributes with style and theme information applied.
1422 */
1423 public final class Theme {
Mathew Inwood5c0d3542018-08-14 13:54:31 +01001424 @UnsupportedAppUsage
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001425 private ResourcesImpl.ThemeImpl mThemeImpl;
1426
1427 private Theme() {
1428 }
1429
1430 void setImpl(ResourcesImpl.ThemeImpl impl) {
1431 mThemeImpl = impl;
1432 }
1433
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001434 /**
1435 * Place new attribute values into the theme. The style resource
1436 * specified by <var>resid</var> will be retrieved from this Theme's
1437 * resources, its values placed into the Theme object.
1438 *
1439 * <p>The semantics of this function depends on the <var>force</var>
1440 * argument: If false, only values that are not already defined in
1441 * the theme will be copied from the system resource; otherwise, if
1442 * any of the style's attributes are already defined in the theme, the
1443 * current values in the theme will be overwritten.
1444 *
Alan Viverette75257ce2014-05-22 19:31:38 -07001445 * @param resId The resource ID of a style resource from which to
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001446 * obtain attribute values.
1447 * @param force If true, values in the style resource will always be
1448 * used in the theme; otherwise, they will only be used
1449 * if not already defined in the theme.
1450 */
Alan Viverette75257ce2014-05-22 19:31:38 -07001451 public void applyStyle(int resId, boolean force) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001452 mThemeImpl.applyStyle(resId, force);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001453 }
1454
1455 /**
1456 * Set this theme to hold the same contents as the theme
1457 * <var>other</var>. If both of these themes are from the same
1458 * Resources object, they will be identical after this function
1459 * returns. If they are from different Resources, only the resources
1460 * they have in common will be set in this theme.
1461 *
1462 * @param other The existing Theme to copy from.
1463 */
1464 public void setTo(Theme other) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001465 mThemeImpl.setTo(other.mThemeImpl);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001466 }
1467
1468 /**
John Spurlock330dd532012-12-18 12:03:11 -05001469 * Return a TypedArray holding the values defined by
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001470 * <var>Theme</var> which are listed in <var>attrs</var>.
1471 *
Scott Main183bf112012-08-13 19:12:13 -07001472 * <p>Be sure to call {@link TypedArray#recycle() TypedArray.recycle()} when you are done
1473 * with the array.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001474 *
Adam Lesinski5ec88752017-04-12 14:45:14 -07001475 * @param attrs The desired attributes. These attribute IDs must be sorted in ascending
1476 * order.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001477 *
1478 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1479 *
1480 * @return Returns a TypedArray holding an array of the attribute values.
1481 * Be sure to call {@link TypedArray#recycle() TypedArray.recycle()}
1482 * when done with it.
1483 *
1484 * @see Resources#obtainAttributes
1485 * @see #obtainStyledAttributes(int, int[])
1486 * @see #obtainStyledAttributes(AttributeSet, int[], int, int)
1487 */
Aurimas Liutikas77acf4b2018-12-19 17:31:03 -08001488 @NonNull
1489 public TypedArray obtainStyledAttributes(@NonNull @StyleableRes int[] attrs) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001490 return mThemeImpl.obtainStyledAttributes(this, null, attrs, 0, 0);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001491 }
1492
1493 /**
John Spurlock330dd532012-12-18 12:03:11 -05001494 * Return a TypedArray holding the values defined by the style
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001495 * resource <var>resid</var> which are listed in <var>attrs</var>.
1496 *
Scott Main183bf112012-08-13 19:12:13 -07001497 * <p>Be sure to call {@link TypedArray#recycle() TypedArray.recycle()} when you are done
1498 * with the array.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001499 *
Alan Viverette395cd012015-08-11 17:27:04 -04001500 * @param resId The desired style resource.
Adam Lesinski5ec88752017-04-12 14:45:14 -07001501 * @param attrs The desired attributes in the style. These attribute IDs must be sorted in
1502 * ascending order.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001503 *
1504 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
1505 *
1506 * @return Returns a TypedArray holding an array of the attribute values.
1507 * Be sure to call {@link TypedArray#recycle() TypedArray.recycle()}
1508 * when done with it.
1509 *
1510 * @see Resources#obtainAttributes
1511 * @see #obtainStyledAttributes(int[])
1512 * @see #obtainStyledAttributes(AttributeSet, int[], int, int)
1513 */
Aurimas Liutikas77acf4b2018-12-19 17:31:03 -08001514 @NonNull
1515 public TypedArray obtainStyledAttributes(@StyleRes int resId,
1516 @NonNull @StyleableRes int[] attrs)
Tor Norbyec91531a2015-04-01 17:41:55 -07001517 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001518 return mThemeImpl.obtainStyledAttributes(this, null, attrs, 0, resId);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001519 }
1520
1521 /**
John Spurlock330dd532012-12-18 12:03:11 -05001522 * Return a TypedArray holding the attribute values in
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001523 * <var>set</var>
1524 * that are listed in <var>attrs</var>. In addition, if the given
1525 * AttributeSet specifies a style class (through the "style" attribute),
1526 * that style will be applied on top of the base attributes it defines.
1527 *
Scott Main183bf112012-08-13 19:12:13 -07001528 * <p>Be sure to call {@link TypedArray#recycle() TypedArray.recycle()} when you are done
1529 * with the array.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001530 *
1531 * <p>When determining the final value of a particular attribute, there
1532 * are four inputs that come into play:</p>
1533 *
1534 * <ol>
1535 * <li> Any attribute values in the given AttributeSet.
1536 * <li> The style resource specified in the AttributeSet (named
1537 * "style").
1538 * <li> The default style specified by <var>defStyleAttr</var> and
1539 * <var>defStyleRes</var>
1540 * <li> The base values in this theme.
1541 * </ol>
1542 *
1543 * <p>Each of these inputs is considered in-order, with the first listed
1544 * taking precedence over the following ones. In other words, if in the
1545 * AttributeSet you have supplied <code>&lt;Button
1546 * textColor="#ff000000"&gt;</code>, then the button's text will
1547 * <em>always</em> be black, regardless of what is specified in any of
1548 * the styles.
1549 *
1550 * @param set The base set of attribute values. May be null.
Adam Lesinski5ec88752017-04-12 14:45:14 -07001551 * @param attrs The desired attributes to be retrieved. These attribute IDs must be sorted
1552 * in ascending order.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001553 * @param defStyleAttr An attribute in the current theme that contains a
1554 * reference to a style resource that supplies
John Spurlock330dd532012-12-18 12:03:11 -05001555 * defaults values for the TypedArray. Can be
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001556 * 0 to not look for defaults.
1557 * @param defStyleRes A resource identifier of a style resource that
John Spurlock330dd532012-12-18 12:03:11 -05001558 * supplies default values for the TypedArray,
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001559 * used only if defStyleAttr is 0 or can not be found
1560 * in the theme. Can be 0 to not look for defaults.
1561 *
1562 * @return Returns a TypedArray holding an array of the attribute values.
1563 * Be sure to call {@link TypedArray#recycle() TypedArray.recycle()}
1564 * when done with it.
1565 *
1566 * @see Resources#obtainAttributes
1567 * @see #obtainStyledAttributes(int[])
1568 * @see #obtainStyledAttributes(int, int[])
1569 */
Aurimas Liutikas77acf4b2018-12-19 17:31:03 -08001570 @NonNull
1571 public TypedArray obtainStyledAttributes(@Nullable AttributeSet set,
1572 @NonNull @StyleableRes int[] attrs, @AttrRes int defStyleAttr,
1573 @StyleRes int defStyleRes) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001574 return mThemeImpl.obtainStyledAttributes(this, set, attrs, defStyleAttr, defStyleRes);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001575 }
1576
1577 /**
Alan Viverette52b999f2014-03-24 18:00:26 -07001578 * Retrieve the values for a set of attributes in the Theme. The
1579 * contents of the typed array are ultimately filled in by
1580 * {@link Resources#getValue}.
1581 *
Alan Viverette7f4a63d2014-10-30 10:29:03 -07001582 * @param values The base set of attribute values, must be equal in
1583 * length to {@code attrs}. All values must be of type
1584 * {@link TypedValue#TYPE_ATTRIBUTE}.
Adam Lesinski5ec88752017-04-12 14:45:14 -07001585 * @param attrs The desired attributes to be retrieved. These attribute IDs must be sorted
1586 * in ascending order.
Alan Viverette52b999f2014-03-24 18:00:26 -07001587 * @return Returns a TypedArray holding an array of the attribute
1588 * values. Be sure to call {@link TypedArray#recycle()}
1589 * when done with it.
1590 * @hide
1591 */
Alan Viverette7f4a63d2014-10-30 10:29:03 -07001592 @NonNull
Mathew Inwood5c0d3542018-08-14 13:54:31 +01001593 @UnsupportedAppUsage
Alan Viverette7f4a63d2014-10-30 10:29:03 -07001594 public TypedArray resolveAttributes(@NonNull int[] values, @NonNull int[] attrs) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001595 return mThemeImpl.resolveAttributes(this, values, attrs);
Alan Viverette52b999f2014-03-24 18:00:26 -07001596 }
1597
1598 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001599 * Retrieve the value of an attribute in the Theme. The contents of
1600 * <var>outValue</var> are ultimately filled in by
1601 * {@link Resources#getValue}.
1602 *
1603 * @param resid The resource identifier of the desired theme
1604 * attribute.
1605 * @param outValue Filled in with the ultimate resource value supplied
1606 * by the attribute.
1607 * @param resolveRefs If true, resource references will be walked; if
1608 * false, <var>outValue</var> may be a
1609 * TYPE_REFERENCE. In either case, it will never
1610 * be a TYPE_ATTRIBUTE.
1611 *
1612 * @return boolean Returns true if the attribute was found and
1613 * <var>outValue</var> is valid, else false.
1614 */
Alan Viverette52b999f2014-03-24 18:00:26 -07001615 public boolean resolveAttribute(int resid, TypedValue outValue, boolean resolveRefs) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001616 return mThemeImpl.resolveAttribute(resid, outValue, resolveRefs);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001617 }
1618
1619 /**
Jon Miranda042ad632014-09-03 17:57:35 -07001620 * Gets all of the attribute ids associated with this {@link Theme}. For debugging only.
1621 *
1622 * @return The int array containing attribute ids associated with this {@link Theme}.
1623 * @hide
1624 */
1625 public int[] getAllAttributes() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001626 return mThemeImpl.getAllAttributes();
Jon Miranda042ad632014-09-03 17:57:35 -07001627 }
1628
1629 /**
Alan Viverette52b999f2014-03-24 18:00:26 -07001630 * Returns the resources to which this theme belongs.
1631 *
1632 * @return Resources to which this theme belongs.
1633 */
1634 public Resources getResources() {
1635 return Resources.this;
1636 }
1637
1638 /**
Alan Viverette8eea3ea2014-02-03 18:40:20 -08001639 * Return a drawable object associated with a particular resource ID
1640 * and styled for the Theme.
1641 *
1642 * @param id The desired resource identifier, as generated by the aapt
1643 * tool. This integer encodes the package, type, and resource
1644 * entry. The value 0 is an invalid identifier.
1645 * @return Drawable An object that can be used to draw this resource.
1646 * @throws NotFoundException Throws NotFoundException if the given ID
1647 * does not exist.
1648 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07001649 public Drawable getDrawable(@DrawableRes int id) throws NotFoundException {
Alan Viverette8eea3ea2014-02-03 18:40:20 -08001650 return Resources.this.getDrawable(id, this);
1651 }
1652
1653 /**
Alan Viverettec1d52792015-05-05 09:49:03 -07001654 * Returns a bit mask of configuration changes that will impact this
1655 * theme (and thus require completely reloading it).
1656 *
1657 * @return a bit mask of configuration changes, as defined by
1658 * {@link ActivityInfo}
1659 * @see ActivityInfo
1660 */
Alan Viverette9ad386b2017-01-26 14:00:20 -05001661 public @Config int getChangingConfigurations() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001662 return mThemeImpl.getChangingConfigurations();
Alan Viverettec1d52792015-05-05 09:49:03 -07001663 }
1664
1665 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001666 * Print contents of this theme out to the log. For debugging only.
1667 *
1668 * @param priority The log priority to use.
1669 * @param tag The log tag to use.
1670 * @param prefix Text to prefix each line printed.
1671 */
1672 public void dump(int priority, String tag, String prefix) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001673 mThemeImpl.dump(priority, tag, prefix);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001674 }
Alan Viverette8eea3ea2014-02-03 18:40:20 -08001675
Deepanshu Guptabfec73c2014-03-11 18:02:44 -07001676 // Needed by layoutlib.
1677 /*package*/ long getNativeTheme() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001678 return mThemeImpl.getNativeTheme();
Deepanshu Guptabfec73c2014-03-11 18:02:44 -07001679 }
1680
1681 /*package*/ int getAppliedStyleResId() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001682 return mThemeImpl.getAppliedStyleResId();
Deepanshu Guptabfec73c2014-03-11 18:02:44 -07001683 }
Alan Viverette75257ce2014-05-22 19:31:38 -07001684
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001685 /**
1686 * @hide
1687 */
1688 public ThemeKey getKey() {
1689 return mThemeImpl.getKey();
Alan Viverette75257ce2014-05-22 19:31:38 -07001690 }
Jon Miranda836c0a82014-08-11 12:32:26 -07001691
1692 private String getResourceNameFromHexString(String hexString) {
1693 return getResourceName(Integer.parseInt(hexString, 16));
1694 }
1695
1696 /**
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001697 * Parses {@link #getKey()} and returns a String array that holds pairs of
Alan Viverettee54d2452015-05-06 10:41:43 -07001698 * adjacent Theme data: resource name followed by whether or not it was
1699 * forced, as specified by {@link #applyStyle(int, boolean)}.
Jon Miranda836c0a82014-08-11 12:32:26 -07001700 *
1701 * @hide
1702 */
1703 @ViewDebug.ExportedProperty(category = "theme", hasAdjacentMapping = true)
1704 public String[] getTheme() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001705 return mThemeImpl.getTheme();
Jon Miranda836c0a82014-08-11 12:32:26 -07001706 }
Alan Viverettee54d2452015-05-06 10:41:43 -07001707
Siva Velusamy0d857b92015-04-22 10:23:56 -07001708 /** @hide */
1709 public void encode(@NonNull ViewHierarchyEncoder encoder) {
1710 encoder.beginObject(this);
Alan Viveretteac674092015-05-08 11:04:47 -07001711 final String[] properties = getTheme();
Siva Velusamy0d857b92015-04-22 10:23:56 -07001712 for (int i = 0; i < properties.length; i += 2) {
1713 encoder.addProperty(properties[i], properties[i+1]);
1714 }
1715 encoder.endObject();
1716 }
1717
Alan Viverettee54d2452015-05-06 10:41:43 -07001718 /**
1719 * Rebases the theme against the parent Resource object's current
1720 * configuration by re-applying the styles passed to
1721 * {@link #applyStyle(int, boolean)}.
1722 *
1723 * @hide
1724 */
1725 public void rebase() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001726 mThemeImpl.rebase();
Alan Viverettee54d2452015-05-06 10:41:43 -07001727 }
Aurimas Liutikas8f004c82019-01-17 17:20:10 -08001728
1729 /**
1730 * Returns the resource ID for the style specified using {@code style="..."} in the
1731 * {@link AttributeSet}'s backing XML element or {@link Resources#ID_NULL} otherwise if not
1732 * specified or otherwise not applicable.
1733 * <p>
1734 * Each {@link android.view.View} can have an explicit style specified in the layout file.
1735 * This style is used first during the {@link android.view.View} attribute resolution, then
1736 * if an attribute is not defined there the resource system looks at default style and theme
1737 * as fallbacks.
1738 *
1739 * @param set The base set of attribute values.
1740 *
1741 * @return The resource ID for the style specified using {@code style="..."} in the
1742 * {@link AttributeSet}'s backing XML element or {@link Resources#ID_NULL} otherwise
1743 * if not specified or otherwise not applicable.
1744 */
1745 @StyleRes
1746 public int getExplicitStyle(@Nullable AttributeSet set) {
1747 if (set == null) {
1748 return ID_NULL;
1749 }
1750 int styleAttr = set.getStyleAttribute();
1751 if (styleAttr == ID_NULL) {
1752 return ID_NULL;
1753 }
1754 String styleAttrType = getResources().getResourceTypeName(styleAttr);
1755 if ("attr".equals(styleAttrType)) {
1756 TypedValue explicitStyle = new TypedValue();
1757 boolean resolved = resolveAttribute(styleAttr, explicitStyle, true);
1758 if (resolved) {
1759 return explicitStyle.resourceId;
1760 }
1761 } else if ("style".equals(styleAttrType)) {
1762 return styleAttr;
1763 }
1764 return ID_NULL;
1765 }
1766
1767 /**
1768 * Returns the ordered list of resource ID that are considered when resolving attribute
1769 * values when making an equivalent call to
1770 * {@link #obtainStyledAttributes(AttributeSet, int[], int, int)} . The list will include
1771 * a set of explicit styles ({@code explicitStyleRes} and it will include the default styles
1772 * ({@code defStyleAttr} and {@code defStyleRes}).
1773 *
1774 * @param defStyleAttr An attribute in the current theme that contains a
1775 * reference to a style resource that supplies
1776 * defaults values for the TypedArray. Can be
1777 * 0 to not look for defaults.
1778 * @param defStyleRes A resource identifier of a style resource that
1779 * supplies default values for the TypedArray,
1780 * used only if defStyleAttr is 0 or can not be found
1781 * in the theme. Can be 0 to not look for defaults.
1782 * @param explicitStyleRes A resource identifier of an explicit style resource.
1783 * @return ordered list of resource ID that are considered when resolving attribute values.
1784 */
Aurimas Liutikas6c15bc02019-02-28 11:16:06 -08001785 @NonNull
Aurimas Liutikas8f004c82019-01-17 17:20:10 -08001786 public int[] getAttributeResolutionStack(@AttrRes int defStyleAttr,
1787 @StyleRes int defStyleRes, @StyleRes int explicitStyleRes) {
Aurimas Liutikas6c15bc02019-02-28 11:16:06 -08001788 int[] stack = mThemeImpl.getAttributeResolutionStack(
Aurimas Liutikas8f004c82019-01-17 17:20:10 -08001789 defStyleAttr, defStyleRes, explicitStyleRes);
Aurimas Liutikas6c15bc02019-02-28 11:16:06 -08001790 if (stack == null) {
1791 return new int[0];
1792 } else {
1793 return stack;
1794 }
Aurimas Liutikas8f004c82019-01-17 17:20:10 -08001795 }
Alan Viverettee54d2452015-05-06 10:41:43 -07001796 }
1797
1798 static class ThemeKey implements Cloneable {
1799 int[] mResId;
1800 boolean[] mForce;
1801 int mCount;
1802
1803 private int mHashCode = 0;
1804
1805 public void append(int resId, boolean force) {
1806 if (mResId == null) {
1807 mResId = new int[4];
1808 }
1809
1810 if (mForce == null) {
1811 mForce = new boolean[4];
1812 }
1813
1814 mResId = GrowingArrayUtils.append(mResId, mCount, resId);
1815 mForce = GrowingArrayUtils.append(mForce, mCount, force);
1816 mCount++;
1817
1818 mHashCode = 31 * (31 * mHashCode + resId) + (force ? 1 : 0);
1819 }
1820
1821 /**
1822 * Sets up this key as a deep copy of another key.
1823 *
1824 * @param other the key to deep copy into this key
1825 */
1826 public void setTo(ThemeKey other) {
1827 mResId = other.mResId == null ? null : other.mResId.clone();
1828 mForce = other.mForce == null ? null : other.mForce.clone();
1829 mCount = other.mCount;
1830 }
1831
1832 @Override
1833 public int hashCode() {
1834 return mHashCode;
1835 }
1836
1837 @Override
1838 public boolean equals(Object o) {
1839 if (this == o) {
1840 return true;
1841 }
1842
1843 if (o == null || getClass() != o.getClass() || hashCode() != o.hashCode()) {
1844 return false;
1845 }
1846
1847 final ThemeKey t = (ThemeKey) o;
1848 if (mCount != t.mCount) {
1849 return false;
1850 }
1851
1852 final int N = mCount;
1853 for (int i = 0; i < N; i++) {
1854 if (mResId[i] != t.mResId[i] || mForce[i] != t.mForce[i]) {
1855 return false;
1856 }
1857 }
1858
1859 return true;
1860 }
1861
1862 /**
1863 * @return a shallow copy of this key
1864 */
1865 @Override
1866 public ThemeKey clone() {
1867 final ThemeKey other = new ThemeKey();
1868 other.mResId = mResId;
1869 other.mForce = mForce;
1870 other.mCount = mCount;
John Reck4feb3262015-07-13 14:42:43 -07001871 other.mHashCode = mHashCode;
Alan Viverettee54d2452015-05-06 10:41:43 -07001872 return other;
1873 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001874 }
1875
1876 /**
1877 * Generate a new Theme object for this set of Resources. It initially
1878 * starts out empty.
Jon Miranda836c0a82014-08-11 12:32:26 -07001879 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001880 * @return Theme The newly created Theme container.
1881 */
1882 public final Theme newTheme() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001883 Theme theme = new Theme();
1884 theme.setImpl(mResourcesImpl.newThemeImpl());
Adam Lesinski4fed9712017-05-23 13:14:54 -07001885 synchronized (mThemeRefs) {
1886 mThemeRefs.add(new WeakReference<>(theme));
Richard Uhlerdd6a0db2018-04-26 15:09:30 +01001887
1888 // Clean up references to garbage collected themes
1889 if (mThemeRefs.size() > mThemeRefsNextFlushSize) {
1890 mThemeRefs.removeIf(ref -> ref.get() == null);
1891 mThemeRefsNextFlushSize = Math.max(MIN_THEME_REFS_FLUSH_SIZE,
1892 2 * mThemeRefs.size());
1893 }
Adam Lesinski4fed9712017-05-23 13:14:54 -07001894 }
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001895 return theme;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001896 }
1897
1898 /**
1899 * Retrieve a set of basic attribute values from an AttributeSet, not
1900 * performing styling of them using a theme and/or style resources.
Jon Miranda836c0a82014-08-11 12:32:26 -07001901 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001902 * @param set The current attribute values to retrieve.
Adam Lesinski5ec88752017-04-12 14:45:14 -07001903 * @param attrs The specific attributes to be retrieved. These attribute IDs must be sorted in
1904 * ascending order.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001905 * @return Returns a TypedArray holding an array of the attribute values.
1906 * Be sure to call {@link TypedArray#recycle() TypedArray.recycle()}
1907 * when done with it.
1908 *
1909 * @see Theme#obtainStyledAttributes(AttributeSet, int[], int, int)
1910 */
Adam Lesinski5ec88752017-04-12 14:45:14 -07001911 public TypedArray obtainAttributes(AttributeSet set, @StyleableRes int[] attrs) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001912 int len = attrs.length;
Alan Viverette52b999f2014-03-24 18:00:26 -07001913 TypedArray array = TypedArray.obtain(this, len);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001914
1915 // XXX note that for now we only work with compiled XML files.
1916 // To support generic XML files we will need to manually parse
1917 // out the attributes from the XML file (applying type information
1918 // contained in the resources and such).
1919 XmlBlock.Parser parser = (XmlBlock.Parser)set;
Adam Lesinskibebfcc42018-02-12 14:27:46 -08001920 mResourcesImpl.getAssets().retrieveAttributes(parser, attrs, array.mData, array.mIndices);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001921
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001922 array.mXml = parser;
1923
1924 return array;
1925 }
Mitsuru Oshimae5fb3282009-06-09 21:16:08 -07001926
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001927 /**
1928 * Store the newly updated configuration.
Adam Lesinskiaa19d5e2016-07-15 17:49:49 -07001929 *
1930 * @deprecated See {@link android.content.Context#createConfigurationContext(Configuration)}.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001931 */
Adam Lesinskiaa19d5e2016-07-15 17:49:49 -07001932 @Deprecated
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001933 public void updateConfiguration(Configuration config, DisplayMetrics metrics) {
Dianne Hackborne2515ee2011-04-27 18:52:56 -04001934 updateConfiguration(config, metrics, null);
1935 }
1936
1937 /**
1938 * @hide
1939 */
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001940 public void updateConfiguration(Configuration config, DisplayMetrics metrics,
1941 CompatibilityInfo compat) {
1942 mResourcesImpl.updateConfiguration(config, metrics, compat);
Narayan Kamath21fc8ba2014-03-05 18:42:23 +00001943 }
1944
1945 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001946 * Update the system resources configuration if they have previously
1947 * been initialized.
1948 *
1949 * @hide
1950 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +01001951 @UnsupportedAppUsage
Dianne Hackborne2515ee2011-04-27 18:52:56 -04001952 public static void updateSystemConfiguration(Configuration config, DisplayMetrics metrics,
1953 CompatibilityInfo compat) {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001954 if (mSystem != null) {
Dianne Hackborne2515ee2011-04-27 18:52:56 -04001955 mSystem.updateConfiguration(config, metrics, compat);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001956 //Log.i(TAG, "Updated system resources " + mSystem
1957 // + ": " + mSystem.getConfiguration());
1958 }
1959 }
1960
1961 /**
1962 * Return the current display metrics that are in effect for this resource
1963 * object. The returned object should be treated as read-only.
1964 *
1965 * @return The resource's current display metrics.
1966 */
1967 public DisplayMetrics getDisplayMetrics() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001968 return mResourcesImpl.getDisplayMetrics();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001969 }
1970
Adam Lesinski4ece3d62016-06-16 18:05:41 -07001971 /** @hide */
Mathew Inwood5c0d3542018-08-14 13:54:31 +01001972 @UnsupportedAppUsage
Adam Lesinski4ece3d62016-06-16 18:05:41 -07001973 public DisplayAdjustments getDisplayAdjustments() {
1974 return mResourcesImpl.getDisplayAdjustments();
1975 }
1976
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001977 /**
1978 * Return the current configuration that is in effect for this resource
1979 * object. The returned object should be treated as read-only.
1980 *
1981 * @return The resource's current configuration.
1982 */
1983 public Configuration getConfiguration() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001984 return mResourcesImpl.getConfiguration();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001985 }
Filip Gruszczynski23493322015-07-29 17:02:59 -07001986
1987 /** @hide */
1988 public Configuration[] getSizeConfigurations() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08001989 return mResourcesImpl.getSizeConfigurations();
1990 }
Filip Gruszczynski23493322015-07-29 17:02:59 -07001991
Mitsuru Oshima9189cab2009-06-03 11:19:12 -07001992 /**
1993 * Return the compatibility mode information for the application.
1994 * The returned object should be treated as read-only.
1995 *
Dianne Hackborn3904d032011-05-27 12:09:11 -07001996 * @return compatibility info.
Mitsuru Oshima9189cab2009-06-03 11:19:12 -07001997 * @hide
1998 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +01001999 @UnsupportedAppUsage
Mitsuru Oshima9189cab2009-06-03 11:19:12 -07002000 public CompatibilityInfo getCompatibilityInfo() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002001 return mResourcesImpl.getCompatibilityInfo();
Mitsuru Oshima9189cab2009-06-03 11:19:12 -07002002 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002003
2004 /**
Dianne Hackborna53b8282009-07-17 11:13:48 -07002005 * This is just for testing.
2006 * @hide
2007 */
Adam Lesinski082614c2016-03-04 14:33:47 -08002008 @VisibleForTesting
Mathew Inwood5c0d3542018-08-14 13:54:31 +01002009 @UnsupportedAppUsage
Dianne Hackborna53b8282009-07-17 11:13:48 -07002010 public void setCompatibilityInfo(CompatibilityInfo ci) {
Adam Lesinski79a8ffe2013-09-19 20:33:15 -07002011 if (ci != null) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002012 mResourcesImpl.updateConfiguration(null, null, ci);
Adam Lesinski79a8ffe2013-09-19 20:33:15 -07002013 }
Dianne Hackborna53b8282009-07-17 11:13:48 -07002014 }
2015
2016 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002017 * Return a resource identifier for the given resource name. A fully
2018 * qualified resource name is of the form "package:type/entry". The first
2019 * two components (package and type) are optional if defType and
2020 * defPackage, respectively, are specified here.
2021 *
2022 * <p>Note: use of this function is discouraged. It is much more
2023 * efficient to retrieve resources by identifier than by name.
2024 *
2025 * @param name The name of the desired resource.
2026 * @param defType Optional default resource type to find, if "type/" is
2027 * not included in the name. Can be null to require an
2028 * explicit type.
2029 * @param defPackage Optional default package to find, if "package:" is
2030 * not included in the name. Can be null to require an
2031 * explicit package.
2032 *
2033 * @return int The associated resource identifier. Returns 0 if no such
2034 * resource was found. (0 is not a valid resource ID.)
2035 */
2036 public int getIdentifier(String name, String defType, String defPackage) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002037 return mResourcesImpl.getIdentifier(name, defType, defPackage);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002038 }
2039
2040 /**
Jeff Sharkey47b50332013-03-15 14:46:46 -07002041 * Return true if given resource identifier includes a package.
2042 *
2043 * @hide
2044 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07002045 public static boolean resourceHasPackage(@AnyRes int resid) {
Jeff Sharkey47b50332013-03-15 14:46:46 -07002046 return (resid >>> 24) != 0;
2047 }
2048
2049 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002050 * Return the full name for a given resource identifier. This name is
2051 * a single string of the form "package:type/entry".
2052 *
2053 * @param resid The resource identifier whose name is to be retrieved.
2054 *
2055 * @return A string holding the name of the resource.
2056 *
2057 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
2058 *
2059 * @see #getResourcePackageName
2060 * @see #getResourceTypeName
2061 * @see #getResourceEntryName
2062 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07002063 public String getResourceName(@AnyRes int resid) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002064 return mResourcesImpl.getResourceName(resid);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002065 }
2066
2067 /**
2068 * Return the package name for a given resource identifier.
2069 *
2070 * @param resid The resource identifier whose package name is to be
2071 * retrieved.
2072 *
2073 * @return A string holding the package name of the resource.
2074 *
2075 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
2076 *
2077 * @see #getResourceName
2078 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07002079 public String getResourcePackageName(@AnyRes int resid) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002080 return mResourcesImpl.getResourcePackageName(resid);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002081 }
2082
2083 /**
2084 * Return the type name for a given resource identifier.
2085 *
2086 * @param resid The resource identifier whose type name is to be
2087 * retrieved.
2088 *
2089 * @return A string holding the type name of the resource.
2090 *
2091 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
2092 *
2093 * @see #getResourceName
2094 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07002095 public String getResourceTypeName(@AnyRes int resid) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002096 return mResourcesImpl.getResourceTypeName(resid);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002097 }
Winson2f3669b2019-01-11 11:28:34 -08002098
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002099 /**
2100 * Return the entry name for a given resource identifier.
Winson2f3669b2019-01-11 11:28:34 -08002101 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002102 * @param resid The resource identifier whose entry name is to be
2103 * retrieved.
Winson2f3669b2019-01-11 11:28:34 -08002104 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002105 * @return A string holding the entry name of the resource.
Winson2f3669b2019-01-11 11:28:34 -08002106 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002107 * @throws NotFoundException Throws NotFoundException if the given ID does not exist.
Winson2f3669b2019-01-11 11:28:34 -08002108 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002109 * @see #getResourceName
2110 */
Tor Norbye7b9c9122013-05-30 16:48:33 -07002111 public String getResourceEntryName(@AnyRes int resid) throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002112 return mResourcesImpl.getResourceEntryName(resid);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002113 }
Winson2f3669b2019-01-11 11:28:34 -08002114
2115 /**
2116 * Return formatted log of the last retrieved resource's resolution path.
2117 *
2118 * @return A string holding a formatted log of the steps taken to resolve the last resource.
2119 *
2120 * @throws NotFoundException Throws NotFoundException if there hasn't been a resource
2121 * resolved yet.
2122 *
2123 * @hide
2124 */
2125 public String getLastResourceResolution() throws NotFoundException {
2126 return mResourcesImpl.getLastResourceResolution();
2127 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002128
2129 /**
2130 * Parse a series of {@link android.R.styleable#Extra &lt;extra&gt;} tags from
2131 * an XML file. You call this when you are at the parent tag of the
Dianne Hackborndef15372010-08-15 12:43:52 -07002132 * extra tags, and it will return once all of the child tags have been parsed.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002133 * This will call {@link #parseBundleExtra} for each extra tag encountered.
2134 *
2135 * @param parser The parser from which to retrieve the extras.
2136 * @param outBundle A Bundle in which to place all parsed extras.
2137 * @throws XmlPullParserException
2138 * @throws IOException
2139 */
2140 public void parseBundleExtras(XmlResourceParser parser, Bundle outBundle)
2141 throws XmlPullParserException, IOException {
2142 int outerDepth = parser.getDepth();
2143 int type;
2144 while ((type=parser.next()) != XmlPullParser.END_DOCUMENT
2145 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) {
2146 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) {
2147 continue;
2148 }
2149
2150 String nodeName = parser.getName();
2151 if (nodeName.equals("extra")) {
2152 parseBundleExtra("extra", parser, outBundle);
2153 XmlUtils.skipCurrentTag(parser);
2154
2155 } else {
2156 XmlUtils.skipCurrentTag(parser);
2157 }
2158 }
2159 }
2160
2161 /**
2162 * Parse a name/value pair out of an XML tag holding that data. The
2163 * AttributeSet must be holding the data defined by
2164 * {@link android.R.styleable#Extra}. The following value types are supported:
2165 * <ul>
2166 * <li> {@link TypedValue#TYPE_STRING}:
2167 * {@link Bundle#putCharSequence Bundle.putCharSequence()}
2168 * <li> {@link TypedValue#TYPE_INT_BOOLEAN}:
2169 * {@link Bundle#putCharSequence Bundle.putBoolean()}
2170 * <li> {@link TypedValue#TYPE_FIRST_INT}-{@link TypedValue#TYPE_LAST_INT}:
2171 * {@link Bundle#putCharSequence Bundle.putBoolean()}
2172 * <li> {@link TypedValue#TYPE_FLOAT}:
2173 * {@link Bundle#putCharSequence Bundle.putFloat()}
2174 * </ul>
2175 *
2176 * @param tagName The name of the tag these attributes come from; this is
2177 * only used for reporting error messages.
2178 * @param attrs The attributes from which to retrieve the name/value pair.
2179 * @param outBundle The Bundle in which to place the parsed value.
2180 * @throws XmlPullParserException If the attributes are not valid.
2181 */
2182 public void parseBundleExtra(String tagName, AttributeSet attrs,
2183 Bundle outBundle) throws XmlPullParserException {
2184 TypedArray sa = obtainAttributes(attrs,
2185 com.android.internal.R.styleable.Extra);
2186
2187 String name = sa.getString(
2188 com.android.internal.R.styleable.Extra_name);
2189 if (name == null) {
2190 sa.recycle();
2191 throw new XmlPullParserException("<" + tagName
2192 + "> requires an android:name attribute at "
2193 + attrs.getPositionDescription());
2194 }
2195
2196 TypedValue v = sa.peekValue(
2197 com.android.internal.R.styleable.Extra_value);
2198 if (v != null) {
2199 if (v.type == TypedValue.TYPE_STRING) {
2200 CharSequence cs = v.coerceToString();
2201 outBundle.putCharSequence(name, cs);
2202 } else if (v.type == TypedValue.TYPE_INT_BOOLEAN) {
2203 outBundle.putBoolean(name, v.data != 0);
2204 } else if (v.type >= TypedValue.TYPE_FIRST_INT
2205 && v.type <= TypedValue.TYPE_LAST_INT) {
2206 outBundle.putInt(name, v.data);
2207 } else if (v.type == TypedValue.TYPE_FLOAT) {
2208 outBundle.putFloat(name, v.getFloat());
2209 } else {
2210 sa.recycle();
2211 throw new XmlPullParserException("<" + tagName
2212 + "> only supports string, integer, float, color, and boolean at "
2213 + attrs.getPositionDescription());
2214 }
2215 } else {
2216 sa.recycle();
2217 throw new XmlPullParserException("<" + tagName
2218 + "> requires an android:value or android:resource attribute at "
2219 + attrs.getPositionDescription());
2220 }
2221
2222 sa.recycle();
2223 }
2224
2225 /**
2226 * Retrieve underlying AssetManager storage for these resources.
2227 */
2228 public final AssetManager getAssets() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002229 return mResourcesImpl.getAssets();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002230 }
2231
2232 /**
2233 * Call this to remove all cached loaded layout resources from the
2234 * Resources object. Only intended for use with performance testing
2235 * tools.
2236 */
2237 public final void flushLayoutCache() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002238 mResourcesImpl.flushLayoutCache();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002239 }
2240
2241 /**
2242 * Start preloading of resource data using this Resources object. Only
2243 * for use by the zygote process for loading common system resources.
2244 * {@hide}
2245 */
2246 public final void startPreloading() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002247 mResourcesImpl.startPreloading();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002248 }
2249
2250 /**
2251 * Called by zygote when it is done preloading resources, to change back
2252 * to normal Resources operation.
2253 */
2254 public final void finishPreloading() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002255 mResourcesImpl.finishPreloading();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002256 }
Dianne Hackborndde331c2012-08-03 14:01:57 -07002257
Romain Guy3b748a42013-04-17 18:54:38 -07002258 /**
2259 * @hide
2260 */
Mathew Inwood5c0d3542018-08-14 13:54:31 +01002261 @UnsupportedAppUsage
Alan Viverette52b999f2014-03-24 18:00:26 -07002262 public LongSparseArray<ConstantState> getPreloadedDrawables() {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002263 return mResourcesImpl.getPreloadedDrawables();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002264 }
2265
Alan Viverette10979612016-01-06 15:27:35 -05002266 /**
2267 * Loads an XML parser for the specified file.
2268 *
2269 * @param id the resource identifier for the file
2270 * @param type the type of resource (used for logging)
2271 * @return a parser for the specified XML file
2272 * @throws NotFoundException if the file could not be loaded
2273 */
2274 @NonNull
Mathew Inwood5c0d3542018-08-14 13:54:31 +01002275 @UnsupportedAppUsage
Alan Viverette10979612016-01-06 15:27:35 -05002276 XmlResourceParser loadXmlResourceParser(@AnyRes int id, @NonNull String type)
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002277 throws NotFoundException {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002278 final TypedValue value = obtainTempTypedValue();
Alan Viverette4d07bc92015-11-16 10:19:12 -05002279 try {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002280 final ResourcesImpl impl = mResourcesImpl;
2281 impl.getValue(id, value, true);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002282 if (value.type == TypedValue.TYPE_STRING) {
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002283 return impl.loadXmlResourceParser(value.string.toString(), id,
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002284 value.assetCookie, type);
2285 }
Alan Viverette4d07bc92015-11-16 10:19:12 -05002286 throw new NotFoundException("Resource ID #0x" + Integer.toHexString(id)
2287 + " type #0x" + Integer.toHexString(value.type) + " is not valid");
2288 } finally {
2289 releaseTempTypedValue(value);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002290 }
2291 }
Alan Viverette10979612016-01-06 15:27:35 -05002292
2293 /**
2294 * Loads an XML parser for the specified file.
2295 *
2296 * @param file the path for the XML file to parse
2297 * @param id the resource identifier for the file
2298 * @param assetCookie the asset cookie for the file
2299 * @param type the type of resource (used for logging)
2300 * @return a parser for the specified XML file
2301 * @throws NotFoundException if the file could not be loaded
2302 */
2303 @NonNull
Mathew Inwood5c0d3542018-08-14 13:54:31 +01002304 @UnsupportedAppUsage
Adam Lesinskifb302cc2016-02-29 16:50:38 -08002305 XmlResourceParser loadXmlResourceParser(String file, int id, int assetCookie,
2306 String type) throws NotFoundException {
2307 return mResourcesImpl.loadXmlResourceParser(file, id, assetCookie, type);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002308 }
2309
Alan Viverette45c4bbb2015-01-05 14:59:19 -08002310 /**
Adam Lesinski082614c2016-03-04 14:33:47 -08002311 * Called by ConfigurationBoundResourceCacheTest.
2312 * @hide
2313 */
2314 @VisibleForTesting
2315 public int calcConfigChanges(Configuration config) {
2316 return mResourcesImpl.calcConfigChanges(config);
2317 }
2318
2319 /**
Alan Viverette45c4bbb2015-01-05 14:59:19 -08002320 * Obtains styled attributes from the theme, if available, or unstyled
2321 * resources if the theme is null.
2322 *
2323 * @hide
2324 */
2325 public static TypedArray obtainAttributes(
2326 Resources res, Theme theme, AttributeSet set, int[] attrs) {
2327 if (theme == null) {
2328 return res.obtainAttributes(set, attrs);
2329 }
2330 return theme.obtainStyledAttributes(set, attrs, 0, 0);
2331 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002332}