• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2009 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.content.res.cts;
18 
19 import static org.junit.Assert.assertEquals;
20 import static org.junit.Assert.assertNotNull;
21 import static org.junit.Assert.assertNull;
22 import static org.junit.Assert.assertTrue;
23 import static org.junit.Assert.fail;
24 import static org.junit.Assume.assumeTrue;
25 
26 import android.content.Context;
27 import android.content.cts.R;
28 import android.content.pm.ApplicationInfo;
29 import android.content.pm.PackageManager;
30 import android.content.pm.PackageManager.NameNotFoundException;
31 import android.content.res.AssetManager;
32 import android.content.res.Configuration;
33 import android.content.res.Resources;
34 import android.content.res.Resources.NotFoundException;
35 import android.content.res.TypedArray;
36 import android.util.DisplayMetrics;
37 
38 import androidx.test.InstrumentationRegistry;
39 import androidx.test.runner.AndroidJUnit4;
40 
41 import org.junit.Before;
42 import org.junit.Test;
43 import org.junit.runner.RunWith;
44 
45 import java.util.ArrayList;
46 import java.util.List;
47 import java.util.Locale;
48 
49 @RunWith(AndroidJUnit4.class)
50 public class ConfigTest {
51     private static final String TEST_PACKAGE = "android.content.cts";
52 
53     private Context mContext;
54     private int mTargetSdkVersion;
55 
56     enum Properties {
57         LANGUAGE,
58         COUNTRY,
59         SCRIPT,
60         VARIANT,
61         GRAMMATICAL_GENDER,
62         MCC,
63         MNC,
64         TOUCHSCREEN,
65         KEYBOARD,
66         KEYBOARDHIDDEN,
67         NAVIGATION,
68         ORIENTATION,
69         COLOR_MODE,
70         WIDTH,
71         HEIGHT,
72         DENSITY,
73         SCREENLAYOUT,
74         SWIDTH_DP,
75         WIDTH_DP,
76         HEIGHT_DP
77     }
78 
checkValue(final Resources res, final int resId, final String expectedValue)79     private static void checkValue(final Resources res, final int resId,
80             final String expectedValue) {
81         try {
82             final String actual = res.getString(resId);
83             assertNotNull("Returned wrong configuration-based simple value: expected <nothing>, "
84                     + "got '" + actual + "' from resource 0x" + Integer.toHexString(resId),
85                     expectedValue);
86             assertEquals("Returned wrong configuration-based simple value: expected '"
87                     + expectedValue + "', got '" + actual + "' from resource 0x"
88                     + Integer.toHexString(resId), expectedValue, actual);
89         } catch (NotFoundException e) {
90             assertNull("Resource not found for configuration-based simple value: expecting \""
91                     + expectedValue + "\"", expectedValue);
92         }
93     }
94 
checkValue(final Resources res, final int resId, final int[] styleable, final String[] expectedValues)95     private static void checkValue(final Resources res, final int resId,
96             final int[] styleable, final String[] expectedValues) {
97         final Resources.Theme theme = res.newTheme();
98         final TypedArray sa = theme.obtainStyledAttributes(resId, styleable);
99         for (int i = 0; i < styleable.length; i++) {
100             final String actual = sa.getString(i);
101             assertEquals("Returned wrong configuration-based style value: expected '"
102                     + expectedValues[i] + "', got '" + actual + "' from attr "
103                     + i + " of resource 0x" + Integer.toHexString(resId),
104                     actual, expectedValues[i]);
105         }
106         sa.recycle();
107     }
108 
109     private class TotalConfig {
110         final Configuration mConfig;
111         final DisplayMetrics mMetrics;
112 
TotalConfig()113         public TotalConfig() {
114             mConfig = new Configuration();
115             mMetrics = new DisplayMetrics();
116             mConfig.locale = Locale.ROOT;
117         }
118 
setProperty(final Properties p, final int value)119         public void setProperty(final Properties p, final int value) {
120             switch(p) {
121                 case GRAMMATICAL_GENDER:
122                     mConfig.setGrammaticalGender(value);
123                     break;
124                 case MCC:
125                     mConfig.mcc = value;
126                     break;
127                 case MNC:
128                     mConfig.mnc = value;
129                     break;
130                 case TOUCHSCREEN:
131                     mConfig.touchscreen = value;
132                     break;
133                 case KEYBOARD:
134                     mConfig.keyboard = value;
135                     break;
136                 case KEYBOARDHIDDEN:
137                     mConfig.keyboardHidden = value;
138                     break;
139                 case NAVIGATION:
140                     mConfig.navigation = value;
141                     break;
142                 case ORIENTATION:
143                     mConfig.orientation = value;
144                     break;
145                 case COLOR_MODE:
146                     mConfig.colorMode = value;
147                     break;
148                 case WIDTH:
149                     mMetrics.widthPixels = value;
150                     mMetrics.noncompatWidthPixels = value;
151                     break;
152                 case HEIGHT:
153                     mMetrics.heightPixels = value;
154                     mMetrics.noncompatHeightPixels = value;
155                     break;
156                 case DENSITY:
157                     // this is the ratio from the standard
158                     mMetrics.density = (((float)value)/((float)DisplayMetrics.DENSITY_DEFAULT));
159                     mMetrics.noncompatDensity = mMetrics.density;
160                     mConfig.densityDpi = value;
161                     break;
162                 case SCREENLAYOUT:
163                     mConfig.screenLayout = value;
164                     break;
165                 case SWIDTH_DP:
166                     mConfig.smallestScreenWidthDp = value;
167                     break;
168                 case WIDTH_DP:
169                     mConfig.screenWidthDp = value;
170                     break;
171                 case HEIGHT_DP:
172                     mConfig.screenHeightDp = value;
173                     break;
174                 default:
175                     assert(false);
176                     break;
177             }
178         }
179 
setProperty(final Properties p, final String value)180         public void setProperty(final Properties p, final String value) {
181             switch(p) {
182                 case LANGUAGE:
183                     mConfig.locale = new Locale.Builder()
184                             .setLocale(mConfig.locale)
185                             .setLanguage(value)
186                             .build();
187                     break;
188                 case COUNTRY:
189                     mConfig.locale = new Locale.Builder()
190                             .setLocale(mConfig.locale)
191                             .setRegion(value)
192                             .build();
193                     break;
194                 case SCRIPT:
195                     mConfig.locale = new Locale.Builder()
196                             .setLocale(mConfig.locale)
197                             .setScript(value)
198                             .build();
199                     break;
200                 case VARIANT:
201                     mConfig.locale = new Locale.Builder()
202                             .setLocale(mConfig.locale)
203                             .setVariant(value)
204                             .build();
205                     break;
206                 default:
207                     assert(false);
208                     break;
209             }
210         }
211 
getResources()212         public Resources getResources() {
213             final AssetManager assmgr = new AssetManager();
214             assmgr.addAssetPath(mContext.getPackageResourcePath());
215             return new Resources(assmgr, mMetrics, mConfig);
216         }
217     }
218 
makeEmptyConfig()219     public TotalConfig makeEmptyConfig() {
220         return new TotalConfig();
221     }
222 
makeClassicConfig()223     public TotalConfig makeClassicConfig() {
224         TotalConfig config = new TotalConfig();
225         config.setProperty(Properties.LANGUAGE, "en");
226         config.setProperty(Properties.COUNTRY, "US");
227         config.setProperty(Properties.MCC, 310);
228         config.setProperty(Properties.MNC, 001); // unused
229         config.setProperty(Properties.TOUCHSCREEN, Configuration.TOUCHSCREEN_FINGER);
230         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_QWERTY);
231         config.setProperty(Properties.KEYBOARDHIDDEN, Configuration.KEYBOARDHIDDEN_YES);
232         config.setProperty(Properties.NAVIGATION, Configuration.NAVIGATION_TRACKBALL);
233         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_PORTRAIT);
234         config.setProperty(Properties.SWIDTH_DP, 320);
235         config.setProperty(Properties.WIDTH_DP, 320);
236         config.setProperty(Properties.HEIGHT_DP, 480);
237         config.setProperty(Properties.DENSITY, 160);
238         config.setProperty(Properties.WIDTH, 200);
239         config.setProperty(Properties.HEIGHT, 320);
240         return config;
241     }
242 
checkPair(Resources res, int[] notResIds, int simpleRes, String simpleString, int bagRes, String bagString)243     private static void checkPair(Resources res, int[] notResIds,
244             int simpleRes, String simpleString,
245             int bagRes, String bagString) {
246         boolean willHave = true;
247         if (notResIds != null) {
248             for (int i : notResIds) {
249                 if (i == simpleRes) {
250                     willHave = false;
251                     break;
252                 }
253             }
254         }
255         checkValue(res, simpleRes, willHave ? simpleString : null);
256         checkValue(res, bagRes, R.styleable.TestConfig,
257                 new String[]{willHave ? bagString : null});
258     }
259 
260     @Before
setUp()261     public void setUp() {
262         mContext = InstrumentationRegistry.getContext();
263         final PackageManager pm = mContext.getPackageManager();
264         try {
265             ApplicationInfo appInfo = pm.getApplicationInfo(TEST_PACKAGE,
266                     PackageManager.ApplicationInfoFlags.of(0));
267             mTargetSdkVersion = appInfo.targetSdkVersion;
268         } catch (NameNotFoundException e) {
269             fail("Should be able to find application info for this package");
270         }
271     }
272 
273     @Test
testAllEmptyConfigs()274     public void testAllEmptyConfigs() {
275         /**
276          * Test a resource that contains a value for each possible single
277          * configuration value.
278          */
279         TotalConfig config = makeEmptyConfig();
280         Resources res = config.getResources();
281         checkValue(res, R.configVarying.simple, "simple default");
282         checkValue(res, R.configVarying.bag,
283                 R.styleable.TestConfig, new String[]{"bag default"});
284 
285         config = makeEmptyConfig();
286         config.setProperty(Properties.LANGUAGE, "xx");
287         res = config.getResources();
288         checkValue(res, R.configVarying.simple, "simple xx");
289         checkValue(res, R.configVarying.bag,
290                 R.styleable.TestConfig, new String[]{"bag xx"});
291 
292         config = makeEmptyConfig();
293         config.setProperty(Properties.LANGUAGE, "xx");
294         config.setProperty(Properties.COUNTRY, "YY");
295         res = config.getResources();
296         checkValue(res, R.configVarying.simple, "simple xx-rYY");
297         checkValue(res, R.configVarying.bag,
298                 R.styleable.TestConfig, new String[]{"bag xx-rYY"});
299 
300         config = makeEmptyConfig();
301         config.setProperty(Properties.MCC, 111);
302         res = config.getResources();
303         checkValue(res, R.configVarying.simple, "simple mcc111");
304         checkValue(res, R.configVarying.bag,
305                 R.styleable.TestConfig, new String[]{"bag mcc111"});
306 
307         config = makeEmptyConfig();
308         config.setProperty(Properties.MNC, 222);
309         res = config.getResources();
310         checkValue(res, R.configVarying.simple, "simple mnc222");
311         checkValue(res, R.configVarying.bag,
312                 R.styleable.TestConfig, new String[]{"bag mnc222"});
313 
314         config = makeEmptyConfig();
315         config.setProperty(Properties.TOUCHSCREEN, Configuration.TOUCHSCREEN_NOTOUCH);
316         res = config.getResources();
317         checkValue(res, R.configVarying.simple, "simple notouch");
318         checkValue(res, R.configVarying.bag,
319                 R.styleable.TestConfig, new String[]{"bag notouch"});
320 
321         config = makeEmptyConfig();
322         config.setProperty(Properties.TOUCHSCREEN, Configuration.TOUCHSCREEN_STYLUS);
323         res = config.getResources();
324         checkValue(res, R.configVarying.simple, "simple stylus");
325         checkValue(res, R.configVarying.bag,
326                 R.styleable.TestConfig, new String[]{"bag stylus"});
327 
328         config = makeEmptyConfig();
329         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_NOKEYS);
330         res = config.getResources();
331         checkValue(res, R.configVarying.simple, "simple nokeys");
332         checkValue(res, R.configVarying.bag,
333                 R.styleable.TestConfig, new String[]{"bag nokeys"});
334 
335         config = makeEmptyConfig();
336         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_12KEY);
337         res = config.getResources();
338         checkValue(res, R.configVarying.simple, "simple 12key");
339         checkValue(res, R.configVarying.bag,
340                 R.styleable.TestConfig, new String[]{"bag 12key"});
341 
342         config = makeEmptyConfig();
343         config.setProperty(Properties.KEYBOARDHIDDEN, Configuration.KEYBOARDHIDDEN_NO);
344         res = config.getResources();
345         checkValue(res, R.configVarying.simple, "simple keysexposed");
346         checkValue(res, R.configVarying.bag,
347                 R.styleable.TestConfig, new String[]{"bag keysexposed"});
348 
349         config = makeEmptyConfig();
350         config.setProperty(Properties.NAVIGATION, Configuration.NAVIGATION_NONAV);
351         res = config.getResources();
352         checkValue(res, R.configVarying.simple, "simple nonav");
353         checkValue(res, R.configVarying.bag,
354                 R.styleable.TestConfig, new String[]{"bag nonav"});
355 
356         config = makeEmptyConfig();
357         config.setProperty(Properties.NAVIGATION, Configuration.NAVIGATION_DPAD);
358         res = config.getResources();
359         checkValue(res, R.configVarying.simple, "simple dpad");
360         checkValue(res, R.configVarying.bag,
361                 R.styleable.TestConfig, new String[]{"bag dpad"});
362 
363         config = makeEmptyConfig();
364         config.setProperty(Properties.NAVIGATION, Configuration.NAVIGATION_WHEEL);
365         res = config.getResources();
366         checkValue(res, R.configVarying.simple, "simple wheel");
367         checkValue(res, R.configVarying.bag,
368                 R.styleable.TestConfig, new String[]{"bag wheel"});
369 
370         config = makeEmptyConfig();
371         config.setProperty(Properties.HEIGHT, 480);
372         config.setProperty(Properties.WIDTH, 320);
373         res = config.getResources();
374         checkValue(res, R.configVarying.simple, "simple 480x320");
375         checkValue(res, R.configVarying.bag,
376                 R.styleable.TestConfig, new String[]{"bag 480x320"});
377 
378         config = makeEmptyConfig();
379         config.setProperty(Properties.DENSITY, 240);
380         res = config.getResources();
381         checkValue(res, R.configVarying.simple, "simple 240dpi");
382         checkValue(res, R.configVarying.bag,
383                 R.styleable.TestConfig, new String[]{"bag 240dpi"});
384 
385         config = makeEmptyConfig();
386         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
387         res = config.getResources();
388         checkValue(res, R.configVarying.simple, "simple landscape");
389         checkValue(res, R.configVarying.bag,
390                 R.styleable.TestConfig, new String[]{"bag landscape"});
391 
392         config = makeEmptyConfig();
393         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_SQUARE);
394         res = config.getResources();
395         checkValue(res, R.configVarying.simple, "simple square");
396         checkValue(res, R.configVarying.bag,
397                 R.styleable.TestConfig, new String[]{"bag square"});
398 
399         config = makeEmptyConfig();
400         config.setProperty(Properties.COLOR_MODE, Configuration.COLOR_MODE_HDR_YES);
401         res = config.getResources();
402         checkValue(res, R.configVarying.simple, "simple hdr");
403         checkValue(res, R.configVarying.bag,
404                 R.styleable.TestConfig, new String[]{"bag hdr"});
405 
406         config = makeEmptyConfig();
407         config.setProperty(Properties.COLOR_MODE, Configuration.COLOR_MODE_HDR_NO);
408         res = config.getResources();
409         checkValue(res, R.configVarying.simple, "simple ldr");
410         checkValue(res, R.configVarying.bag,
411                 R.styleable.TestConfig, new String[]{"bag ldr"});
412 
413         config = makeEmptyConfig();
414         config.setProperty(Properties.COLOR_MODE, Configuration.COLOR_MODE_WIDE_COLOR_GAMUT_YES);
415         res = config.getResources();
416         checkValue(res, R.configVarying.simple, "simple widecg");
417         checkValue(res, R.configVarying.bag,
418                 R.styleable.TestConfig, new String[]{"bag widecg"});
419 
420         config = makeEmptyConfig();
421         config.setProperty(Properties.COLOR_MODE, Configuration.COLOR_MODE_WIDE_COLOR_GAMUT_NO);
422         res = config.getResources();
423         checkValue(res, R.configVarying.simple, "simple nowidecg");
424         checkValue(res, R.configVarying.bag,
425                 R.styleable.TestConfig, new String[]{"bag nowidecg"});
426 
427         config = makeEmptyConfig();
428         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_SMALL);
429         res = config.getResources();
430         checkValue(res, R.configVarying.simple, "simple small");
431         checkValue(res, R.configVarying.bag,
432                 R.styleable.TestConfig, new String[]{"bag small"});
433 
434         config = makeEmptyConfig();
435         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_NORMAL);
436         res = config.getResources();
437         checkValue(res, R.configVarying.simple, "simple normal");
438         checkValue(res, R.configVarying.bag,
439                 R.styleable.TestConfig, new String[]{"bag normal"});
440 
441         config = makeEmptyConfig();
442         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
443         res = config.getResources();
444         checkValue(res, R.configVarying.simple, "simple large");
445         checkValue(res, R.configVarying.bag,
446                 R.styleable.TestConfig, new String[]{"bag large"});
447 
448         config = makeEmptyConfig();
449         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_XLARGE);
450         res = config.getResources();
451         checkValue(res, R.configVarying.simple, "simple xlarge");
452         checkValue(res, R.configVarying.bag,
453                 R.styleable.TestConfig, new String[]{"bag xlarge"});
454 
455         config = makeEmptyConfig();
456         config.setProperty(Properties.SWIDTH_DP, 600);
457         res = config.getResources();
458         checkValue(res, R.configVarying.simple, "simple sw600");
459         checkValue(res, R.configVarying.bag,
460                 R.styleable.TestConfig, new String[]{"bag sw600"});
461 
462         config = makeEmptyConfig();
463         config.setProperty(Properties.SWIDTH_DP, 600);
464         res = config.getResources();
465         checkValue(res, R.configVarying.simple, "simple sw600");
466         checkValue(res, R.configVarying.bag,
467                 R.styleable.TestConfig, new String[]{"bag sw600"});
468 
469         config = makeEmptyConfig();
470         config.setProperty(Properties.SWIDTH_DP, 720);
471         res = config.getResources();
472         checkValue(res, R.configVarying.simple, "simple sw720");
473         checkValue(res, R.configVarying.bag,
474                 R.styleable.TestConfig, new String[]{"bag sw720"});
475 
476         config = makeEmptyConfig();
477         config.setProperty(Properties.WIDTH_DP, 600);
478         res = config.getResources();
479         checkValue(res, R.configVarying.simple, "simple w600");
480         checkValue(res, R.configVarying.bag,
481                 R.styleable.TestConfig, new String[]{"bag w600"});
482 
483         config = makeEmptyConfig();
484         config.setProperty(Properties.WIDTH_DP, 720);
485         res = config.getResources();
486         checkValue(res, R.configVarying.simple, "simple w720");
487         checkValue(res, R.configVarying.bag,
488                 R.styleable.TestConfig, new String[]{"bag w720"});
489 
490         config = makeEmptyConfig();
491         config.setProperty(Properties.HEIGHT_DP, 550);
492         res = config.getResources();
493         checkValue(res, R.configVarying.simple, "simple h550");
494         checkValue(res, R.configVarying.bag,
495                 R.styleable.TestConfig, new String[]{"bag h550"});
496 
497         config = makeEmptyConfig();
498         config.setProperty(Properties.HEIGHT_DP, 670);
499         res = config.getResources();
500         checkValue(res, R.configVarying.simple, "simple h670");
501         checkValue(res, R.configVarying.bag,
502                 R.styleable.TestConfig, new String[]{"bag h670"});
503 
504         config = makeEmptyConfig();
505         config.setProperty(Properties.GRAMMATICAL_GENDER,
506                 Configuration.GRAMMATICAL_GENDER_FEMININE);
507         res = config.getResources();
508         checkValue(res, R.configVarying.simple, "simple feminine");
509         checkValue(res, R.configVarying.bag,
510                 R.styleable.TestConfig, new String[]{"bag feminine"});
511 
512         config = makeEmptyConfig();
513         config.setProperty(Properties.GRAMMATICAL_GENDER,
514                 Configuration.GRAMMATICAL_GENDER_MASCULINE);
515         res = config.getResources();
516         checkValue(res, R.configVarying.simple, "simple masculine");
517         checkValue(res, R.configVarying.bag,
518                 R.styleable.TestConfig, new String[]{"bag masculine"});
519 
520         config = makeEmptyConfig();
521         config.setProperty(Properties.GRAMMATICAL_GENDER,
522                 Configuration.GRAMMATICAL_GENDER_NEUTRAL);
523         res = config.getResources();
524         checkValue(res, R.configVarying.simple, "simple neuter");
525         checkValue(res, R.configVarying.bag,
526                 R.styleable.TestConfig, new String[]{"bag neuter"});
527     }
528 
529     @Test
testAllClassicConfigs()530     public void testAllClassicConfigs() {
531         /**
532          * Test a resource that contains a value for each possible single
533          * configuration value.
534          */
535         TotalConfig config = makeClassicConfig();
536         Resources res = config.getResources();
537         checkValue(res, R.configVarying.simple, "simple default");
538         checkValue(res, R.configVarying.bag,
539                 R.styleable.TestConfig, new String[]{"bag default"});
540 
541         config = makeClassicConfig();
542         config.setProperty(Properties.LANGUAGE, "xx");
543         res = config.getResources();
544         checkValue(res, R.configVarying.simple, "simple xx");
545         checkValue(res, R.configVarying.bag,
546                 R.styleable.TestConfig, new String[]{"bag xx"});
547 
548         config = makeClassicConfig();
549         config.setProperty(Properties.LANGUAGE, "xx");
550         config.setProperty(Properties.COUNTRY, "YY");
551         res = config.getResources();
552         checkValue(res, R.configVarying.simple, "simple xx-rYY");
553         checkValue(res, R.configVarying.bag,
554                 R.styleable.TestConfig, new String[]{"bag xx-rYY"});
555 
556         config = makeClassicConfig();
557         config.setProperty(Properties.MCC, 111);
558         res = config.getResources();
559         checkValue(res, R.configVarying.simple, "simple mcc111");
560         checkValue(res, R.configVarying.bag,
561                 R.styleable.TestConfig, new String[]{"bag mcc111"});
562 
563         config = makeClassicConfig();
564         config.setProperty(Properties.MNC, 222);
565         res = config.getResources();
566         checkValue(res, R.configVarying.simple, "simple mnc222");
567         checkValue(res, R.configVarying.bag,
568                 R.styleable.TestConfig, new String[]{"bag mnc222"});
569 
570         config = makeClassicConfig();
571         config.setProperty(Properties.TOUCHSCREEN, Configuration.TOUCHSCREEN_NOTOUCH);
572         res = config.getResources();
573         checkValue(res, R.configVarying.simple, "simple notouch");
574         checkValue(res, R.configVarying.bag,
575                 R.styleable.TestConfig, new String[]{"bag notouch"});
576 
577         config = makeClassicConfig();
578         config.setProperty(Properties.TOUCHSCREEN, Configuration.TOUCHSCREEN_STYLUS);
579         res = config.getResources();
580         checkValue(res, R.configVarying.simple, "simple stylus");
581         checkValue(res, R.configVarying.bag,
582                 R.styleable.TestConfig, new String[]{"bag stylus"});
583 
584         config = makeClassicConfig();
585         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_NOKEYS);
586         res = config.getResources();
587         checkValue(res, R.configVarying.simple, "simple nokeys");
588         checkValue(res, R.configVarying.bag,
589                 R.styleable.TestConfig, new String[]{"bag nokeys"});
590 
591         config = makeClassicConfig();
592         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_12KEY);
593         res = config.getResources();
594         checkValue(res, R.configVarying.simple, "simple 12key 63x57");
595         checkValue(res, R.configVarying.bag,
596                 R.styleable.TestConfig, new String[]{"bag 12key 63x57"});
597 
598         config = makeClassicConfig();
599         config.setProperty(Properties.KEYBOARDHIDDEN, Configuration.KEYBOARDHIDDEN_NO);
600         res = config.getResources();
601         checkValue(res, R.configVarying.simple, "simple keysexposed");
602         checkValue(res, R.configVarying.bag,
603                 R.styleable.TestConfig, new String[]{"bag keysexposed"});
604 
605         config = makeClassicConfig();
606         config.setProperty(Properties.NAVIGATION, Configuration.NAVIGATION_NONAV);
607         res = config.getResources();
608         checkValue(res, R.configVarying.simple, "simple nonav");
609         checkValue(res, R.configVarying.bag,
610                 R.styleable.TestConfig, new String[]{"bag nonav"});
611 
612         config = makeClassicConfig();
613         config.setProperty(Properties.NAVIGATION, Configuration.NAVIGATION_DPAD);
614         res = config.getResources();
615         checkValue(res, R.configVarying.simple, "simple dpad 63x57");
616         checkValue(res, R.configVarying.bag,
617                 R.styleable.TestConfig, new String[]{"bag dpad 63x57"});
618 
619         config = makeClassicConfig();
620         config.setProperty(Properties.NAVIGATION, Configuration.NAVIGATION_WHEEL);
621         res = config.getResources();
622         checkValue(res, R.configVarying.simple, "simple wheel");
623         checkValue(res, R.configVarying.bag,
624                 R.styleable.TestConfig, new String[]{"bag wheel"});
625 
626         config = makeClassicConfig();
627         config.setProperty(Properties.HEIGHT, 480);
628         config.setProperty(Properties.WIDTH, 320);
629         res = config.getResources();
630         checkValue(res, R.configVarying.simple, "simple 480x320");
631         checkValue(res, R.configVarying.bag,
632                 R.styleable.TestConfig, new String[]{"bag 480x320"});
633 
634         config = makeClassicConfig();
635         config.setProperty(Properties.DENSITY, 240);
636         res = config.getResources();
637         checkValue(res, R.configVarying.simple, "simple 240dpi");
638         checkValue(res, R.configVarying.bag,
639                 R.styleable.TestConfig, new String[]{"bag 240dpi"});
640 
641         config = makeClassicConfig();
642         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
643         res = config.getResources();
644         checkValue(res, R.configVarying.simple, "simple landscape");
645         checkValue(res, R.configVarying.bag,
646                 R.styleable.TestConfig, new String[]{"bag landscape"});
647 
648         config = makeClassicConfig();
649         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_SQUARE);
650         res = config.getResources();
651         checkValue(res, R.configVarying.simple, "simple square");
652         checkValue(res, R.configVarying.bag,
653                 R.styleable.TestConfig, new String[]{"bag square"});
654 
655         config = makeClassicConfig();
656         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_SMALL);
657         res = config.getResources();
658         checkValue(res, R.configVarying.simple, "simple small");
659         checkValue(res, R.configVarying.bag,
660                 R.styleable.TestConfig, new String[]{"bag small"});
661 
662         config = makeClassicConfig();
663         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_NORMAL);
664         res = config.getResources();
665         checkValue(res, R.configVarying.simple, "simple normal");
666         checkValue(res, R.configVarying.bag,
667                 R.styleable.TestConfig, new String[]{"bag normal"});
668 
669         config = makeClassicConfig();
670         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
671         res = config.getResources();
672         checkValue(res, R.configVarying.simple, "simple large");
673         checkValue(res, R.configVarying.bag,
674                 R.styleable.TestConfig, new String[]{"bag large"});
675 
676         config = makeClassicConfig();
677         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_XLARGE);
678         res = config.getResources();
679         checkValue(res, R.configVarying.simple, "simple xlarge");
680         checkValue(res, R.configVarying.bag,
681                 R.styleable.TestConfig, new String[]{"bag xlarge"});
682 
683         config = makeClassicConfig();
684         config.setProperty(Properties.SWIDTH_DP, 600);
685         res = config.getResources();
686         checkValue(res, R.configVarying.simple, "simple sw600");
687         checkValue(res, R.configVarying.bag,
688                 R.styleable.TestConfig, new String[]{"bag sw600"});
689 
690         config = makeClassicConfig();
691         config.setProperty(Properties.SWIDTH_DP, 600);
692         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
693         res = config.getResources();
694         checkValue(res, R.configVarying.simple, "simple sw600 land");
695         checkValue(res, R.configVarying.bag,
696                 R.styleable.TestConfig, new String[]{"bag sw600 land"});
697 
698         config = makeClassicConfig();
699         config.setProperty(Properties.SWIDTH_DP, 720);
700         res = config.getResources();
701         checkValue(res, R.configVarying.simple, "simple sw720");
702         checkValue(res, R.configVarying.bag,
703                 R.styleable.TestConfig, new String[]{"bag sw720"});
704 
705         config = makeClassicConfig();
706         config.setProperty(Properties.WIDTH_DP, 600);
707         res = config.getResources();
708         checkValue(res, R.configVarying.simple, "simple w600");
709         checkValue(res, R.configVarying.bag,
710                 R.styleable.TestConfig, new String[]{"bag w600"});
711 
712         config = makeClassicConfig();
713         config.setProperty(Properties.WIDTH_DP, 720);
714         res = config.getResources();
715         checkValue(res, R.configVarying.simple, "simple w720");
716         checkValue(res, R.configVarying.bag,
717                 R.styleable.TestConfig, new String[]{"bag w720"});
718 
719         config = makeClassicConfig();
720         config.setProperty(Properties.HEIGHT_DP, 550);
721         res = config.getResources();
722         checkValue(res, R.configVarying.simple, "simple h550");
723         checkValue(res, R.configVarying.bag,
724                 R.styleable.TestConfig, new String[]{"bag h550"});
725 
726         config = makeClassicConfig();
727         config.setProperty(Properties.HEIGHT_DP, 670);
728         res = config.getResources();
729         checkValue(res, R.configVarying.simple, "simple h670");
730         checkValue(res, R.configVarying.bag,
731                 R.styleable.TestConfig, new String[]{"bag h670"});
732     }
733 
734     @Test
testDensity()735     public void testDensity() throws Exception {
736         // Have 32, 240 and the default 160 content.
737         // Rule is that next highest wins.
738         TotalConfig config = makeClassicConfig();
739         config.setProperty(Properties.DENSITY, 2);
740         Resources res = config.getResources();
741         checkValue(res, R.configVarying.simple, "simple 32dpi");
742         checkValue(res, R.configVarying.bag,
743                 R.styleable.TestConfig, new String[]{"bag 32dpi"});
744 
745         config = makeClassicConfig();
746         config.setProperty(Properties.DENSITY, 32);
747         res = config.getResources();
748         checkValue(res, R.configVarying.simple, "simple 32dpi");
749         checkValue(res, R.configVarying.bag,
750                 R.styleable.TestConfig, new String[]{"bag 32dpi"});
751 
752         config = makeClassicConfig();
753         config.setProperty(Properties.DENSITY, 48);
754         res = config.getResources();
755         checkValue(res, R.configVarying.simple, "simple default");
756         checkValue(res, R.configVarying.bag,
757                 R.styleable.TestConfig, new String[]{"bag default"});
758 
759         config = makeClassicConfig();
760         config.setProperty(Properties.DENSITY, 150);
761         res = config.getResources();
762         checkValue(res, R.configVarying.simple, "simple default");
763         checkValue(res, R.configVarying.bag,
764                 R.styleable.TestConfig, new String[]{"bag default"});
765 
766         config = makeClassicConfig();
767         config.setProperty(Properties.DENSITY, 181);
768         res = config.getResources();
769         checkValue(res, R.configVarying.simple, "simple 240dpi");
770         checkValue(res, R.configVarying.bag,
771                 R.styleable.TestConfig, new String[]{"bag 240dpi"});
772 
773         config = makeClassicConfig();
774         config.setProperty(Properties.DENSITY, 239);
775         res = config.getResources();
776         checkValue(res, R.configVarying.simple, "simple 240dpi");
777         checkValue(res, R.configVarying.bag,
778                 R.styleable.TestConfig, new String[]{"bag 240dpi"});
779 
780         config = makeClassicConfig();
781         config.setProperty(Properties.DENSITY, 490);
782         res = config.getResources();
783         checkValue(res, R.configVarying.simple, "simple 240dpi");
784         checkValue(res, R.configVarying.bag,
785                 R.styleable.TestConfig, new String[]{"bag 240dpi"});
786     }
787 
788     @Test
testScreenSize()789     public void testScreenSize() throws Exception {
790         // ensure that we fall back to the best available screen size
791         // for a given configuration.
792         TotalConfig config = makeClassicConfig();
793         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_SMALL);
794         Resources res = config.getResources();
795         checkValue(res, R.configVarying.simple, "simple small");
796         checkValue(res, R.configVarying.small, "small");
797         checkValue(res, R.configVarying.normal, "default");
798         checkValue(res, R.configVarying.large, "default");
799         checkValue(res, R.configVarying.xlarge, "default");
800 
801         config = makeClassicConfig();
802         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_NORMAL);
803         res = config.getResources();
804         checkValue(res, R.configVarying.simple, "simple normal");
805         checkValue(res, R.configVarying.small, "default");
806         checkValue(res, R.configVarying.normal, "normal");
807         checkValue(res, R.configVarying.large, "default");
808         checkValue(res, R.configVarying.xlarge, "default");
809 
810         config = makeClassicConfig();
811         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
812         res = config.getResources();
813         checkValue(res, R.configVarying.simple, "simple large");
814         checkValue(res, R.configVarying.small, "default");
815         checkValue(res, R.configVarying.normal, "normal");
816         checkValue(res, R.configVarying.large, "large");
817         checkValue(res, R.configVarying.xlarge, "default");
818 
819         config = makeClassicConfig();
820         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_XLARGE);
821         res = config.getResources();
822         checkValue(res, R.configVarying.simple, "simple xlarge");
823         checkValue(res, R.configVarying.small, "default");
824         checkValue(res, R.configVarying.normal, "normal");
825         checkValue(res, R.configVarying.large, "large");
826         checkValue(res, R.configVarying.xlarge, "xlarge");
827     }
828 
829     @Test
testNewScreenSize()830     public void testNewScreenSize() throws Exception {
831         // ensure that swNNNdp, wNNNdp, and hNNNdp are working correctly
832         // for various common screen configurations.
833         TotalConfig config = makeClassicConfig();
834         config.setProperty(Properties.SWIDTH_DP, 589);
835         config.setProperty(Properties.WIDTH_DP, 589);
836         config.setProperty(Properties.HEIGHT_DP, 500);
837         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
838         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
839         Resources res = config.getResources();
840         checkValue(res, R.configVarying.simple, "simple large");
841         checkValue(res, R.configVarying.sw, "default");
842         checkValue(res, R.configVarying.w, "default");
843         checkValue(res, R.configVarying.h, "default");
844         checkValue(res, R.configVarying.wh, "default");
845 
846         config = makeClassicConfig();
847         config.setProperty(Properties.SWIDTH_DP, 590);
848         config.setProperty(Properties.WIDTH_DP, 590);
849         config.setProperty(Properties.HEIGHT_DP, 500);
850         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
851         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
852         config.setProperty(Properties.DENSITY, DisplayMetrics.DENSITY_MEDIUM);
853         res = config.getResources();
854         checkValue(res, R.configVarying.simple, "simple sw590 mdpi");
855         checkValue(res, R.configVarying.sw, "590 mdpi");
856 
857         config.setProperty(Properties.DENSITY, DisplayMetrics.DENSITY_HIGH);
858         res = config.getResources();
859         checkValue(res, R.configVarying.simple, "simple sw590 hdpi");
860         checkValue(res, R.configVarying.sw, "590 hdpi");
861 
862         config.setProperty(Properties.DENSITY, DisplayMetrics.DENSITY_XHIGH);
863         res = config.getResources();
864         checkValue(res, R.configVarying.simple, "simple sw590 xhdpi");
865         checkValue(res, R.configVarying.sw, "590 xhdpi");
866 
867         config.setProperty(Properties.SWIDTH_DP, 591);
868         config.setProperty(Properties.WIDTH_DP, 591);
869         config.setProperty(Properties.DENSITY, DisplayMetrics.DENSITY_MEDIUM);
870         res = config.getResources();
871         checkValue(res, R.configVarying.simple, "simple sw591");
872         checkValue(res, R.configVarying.sw, "591");
873 
874         config.setProperty(Properties.DENSITY, DisplayMetrics.DENSITY_HIGH);
875         res = config.getResources();
876         checkValue(res, R.configVarying.simple, "simple sw591 hdpi");
877         checkValue(res, R.configVarying.sw, "591 hdpi");
878 
879         config.setProperty(Properties.DENSITY, DisplayMetrics.DENSITY_XHIGH);
880         res = config.getResources();
881         checkValue(res, R.configVarying.simple, "simple sw591 hdpi");
882         checkValue(res, R.configVarying.sw, "591 hdpi");
883 
884         config = makeClassicConfig();
885         config.setProperty(Properties.SWIDTH_DP, 480);
886         config.setProperty(Properties.WIDTH_DP, 800);
887         config.setProperty(Properties.HEIGHT_DP, 480);
888         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
889         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
890         res = config.getResources();
891         checkValue(res, R.configVarying.simple, "simple w720");
892         checkValue(res, R.configVarying.sw, "default");
893         checkValue(res, R.configVarying.w, "720");
894         checkValue(res, R.configVarying.h, "default");
895         checkValue(res, R.configVarying.wh, "600");
896 
897         config = makeClassicConfig();
898         config.setProperty(Properties.SWIDTH_DP, 600);
899         config.setProperty(Properties.WIDTH_DP, 1024);
900         config.setProperty(Properties.HEIGHT_DP, 552);
901         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
902         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
903         res = config.getResources();
904         checkValue(res, R.configVarying.simple, "simple sw600 land");
905         checkValue(res, R.configVarying.sw, "600 land");
906         checkValue(res, R.configVarying.w, "720");
907         checkValue(res, R.configVarying.h, "550");
908         checkValue(res, R.configVarying.wh, "600-550");
909 
910         config = makeClassicConfig();
911         config.setProperty(Properties.SWIDTH_DP, 600);
912         config.setProperty(Properties.WIDTH_DP, 600);
913         config.setProperty(Properties.HEIGHT_DP, 974);
914         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_PORTRAIT);
915         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
916         res = config.getResources();
917         checkValue(res, R.configVarying.simple, "simple sw600");
918         checkValue(res, R.configVarying.sw, "600");
919         checkValue(res, R.configVarying.w, "600");
920         checkValue(res, R.configVarying.h, "670");
921         checkValue(res, R.configVarying.wh, "600-550");
922 
923         config = makeClassicConfig();
924         config.setProperty(Properties.SWIDTH_DP, 719);
925         config.setProperty(Properties.WIDTH_DP, 1279);
926         config.setProperty(Properties.HEIGHT_DP, 669);
927         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
928         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_LARGE);
929         res = config.getResources();
930         checkValue(res, R.configVarying.simple, "simple sw600 land");
931         checkValue(res, R.configVarying.sw, "600 land");
932         checkValue(res, R.configVarying.w, "720");
933         checkValue(res, R.configVarying.h, "550");
934         checkValue(res, R.configVarying.wh, "600-550");
935 
936         config = makeClassicConfig();
937         config.setProperty(Properties.SWIDTH_DP, 800);
938         config.setProperty(Properties.WIDTH_DP, 1280);
939         config.setProperty(Properties.HEIGHT_DP, 672);
940         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
941         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_XLARGE);
942         res = config.getResources();
943         checkValue(res, R.configVarying.simple, "simple sw720");
944         checkValue(res, R.configVarying.sw, "720");
945         checkValue(res, R.configVarying.w, "720");
946         checkValue(res, R.configVarying.h, "670");
947         checkValue(res, R.configVarying.wh, "720-670");
948 
949         config = makeClassicConfig();
950         config.setProperty(Properties.SWIDTH_DP, 800);
951         config.setProperty(Properties.WIDTH_DP, 720);
952         config.setProperty(Properties.HEIGHT_DP, 1230);
953         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_PORTRAIT);
954         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_XLARGE);
955         res = config.getResources();
956         checkValue(res, R.configVarying.simple, "simple sw720");
957         checkValue(res, R.configVarying.sw, "720");
958         checkValue(res, R.configVarying.w, "720");
959         checkValue(res, R.configVarying.h, "670");
960         checkValue(res, R.configVarying.wh, "720-670");
961     }
962 
963 // TODO - add tests for special cases - ie, other key params seem ignored if
964 // nokeys is set
965 
966     @Test
testPrecedence()967     public void testPrecedence() {
968         /**
969          * Check for precedence of resources selected when there are multiple
970          * options matching the current config.
971          */
972         TotalConfig config = makeEmptyConfig();
973         config.setProperty(Properties.HEIGHT, 640);
974         config.setProperty(Properties.WIDTH, 400);
975         Resources res = config.getResources();
976         checkValue(res, R.configVarying.simple, "simple 640x400");
977         checkValue(res, R.configVarying.bag,
978                 R.styleable.TestConfig, new String[]{"bag 640x400"});
979 
980         config.setProperty(Properties.NAVIGATION, Configuration.NAVIGATION_NONAV);
981         res = config.getResources();
982         checkValue(res, R.configVarying.simple, "simple nonav");
983         checkValue(res, R.configVarying.bag,
984                 R.styleable.TestConfig, new String[]{"bag nonav"});
985 
986         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_NOKEYS);
987         res = config.getResources();
988         checkValue(res, R.configVarying.simple, "simple nokeys");
989         checkValue(res, R.configVarying.bag,
990                 R.styleable.TestConfig, new String[]{"bag nokeys"});
991 
992         config.setProperty(Properties.KEYBOARDHIDDEN, Configuration.KEYBOARDHIDDEN_NO);
993         res = config.getResources();
994         checkValue(res, R.configVarying.simple, "simple keysexposed");
995         checkValue(res, R.configVarying.bag,
996                 R.styleable.TestConfig, new String[]{"bag keysexposed"});
997 
998         config.setProperty(Properties.TOUCHSCREEN, Configuration.TOUCHSCREEN_NOTOUCH);
999         res = config.getResources();
1000         checkValue(res, R.configVarying.simple, "simple notouch");
1001         checkValue(res, R.configVarying.bag,
1002                 R.styleable.TestConfig, new String[]{"bag notouch"});
1003 
1004         config.setProperty(Properties.DENSITY, 240);
1005         res = config.getResources();
1006         checkValue(res, R.configVarying.simple, "simple 240dpi");
1007         checkValue(res, R.configVarying.bag,
1008                 R.styleable.TestConfig, new String[]{"bag 240dpi"});
1009 
1010         config.setProperty(Properties.ORIENTATION, Configuration.ORIENTATION_LANDSCAPE);
1011         res = config.getResources();
1012         checkValue(res, R.configVarying.simple, "simple landscape");
1013         checkValue(res, R.configVarying.bag,
1014                 R.styleable.TestConfig, new String[]{"bag landscape"});
1015 
1016         config.setProperty(Properties.COLOR_MODE, Configuration.COLOR_MODE_HDR_YES);
1017         res = config.getResources();
1018         checkValue(res, R.configVarying.simple, "simple hdr");
1019         checkValue(res, R.configVarying.bag,
1020                 R.styleable.TestConfig, new String[]{"bag hdr"});
1021 
1022         config.setProperty(Properties.COLOR_MODE, Configuration.COLOR_MODE_WIDE_COLOR_GAMUT_YES);
1023         res = config.getResources();
1024         checkValue(res, R.configVarying.simple, "simple widecg");
1025         checkValue(res, R.configVarying.bag,
1026                 R.styleable.TestConfig, new String[]{"bag widecg"});
1027 
1028         config.setProperty(Properties.SCREENLAYOUT, Configuration.SCREENLAYOUT_SIZE_XLARGE);
1029         res = config.getResources();
1030         checkValue(res, R.configVarying.simple, "simple xlarge");
1031         checkValue(res, R.configVarying.bag,
1032                 R.styleable.TestConfig, new String[]{"bag xlarge"});
1033 
1034         config.setProperty(Properties.HEIGHT_DP, 670);
1035         res = config.getResources();
1036         checkValue(res, R.configVarying.simple, "simple h670");
1037         checkValue(res, R.configVarying.bag,
1038                 R.styleable.TestConfig, new String[]{"bag h670"});
1039 
1040         config.setProperty(Properties.WIDTH_DP, 720);
1041         res = config.getResources();
1042         checkValue(res, R.configVarying.simple, "simple 720-670");
1043         checkValue(res, R.configVarying.bag,
1044                 R.styleable.TestConfig, new String[]{"bag 720-670"});
1045 
1046         config.setProperty(Properties.SWIDTH_DP, 720);
1047         res = config.getResources();
1048         checkValue(res, R.configVarying.simple, "simple sw720");
1049         checkValue(res, R.configVarying.bag,
1050                 R.styleable.TestConfig, new String[]{"bag sw720"});
1051 
1052         config.setProperty(Properties.GRAMMATICAL_GENDER,
1053                 Configuration.GRAMMATICAL_GENDER_FEMININE);
1054         res = config.getResources();
1055         checkValue(res, R.configVarying.simple, "simple feminine");
1056         checkValue(res, R.configVarying.bag,
1057                 R.styleable.TestConfig, new String[]{"bag feminine"});
1058 
1059         config.setProperty(Properties.LANGUAGE, "xx");
1060         config.setProperty(Properties.COUNTRY, "YY");
1061         res = config.getResources();
1062         checkValue(res, R.configVarying.simple, "simple xx-rYY");
1063         checkValue(res, R.configVarying.bag,
1064                 R.styleable.TestConfig, new String[]{"bag xx-rYY"});
1065 
1066         config.setProperty(Properties.MCC, 111);
1067         res = config.getResources();
1068         checkValue(res, R.configVarying.simple, "simple mcc111 xx-rYY");
1069         checkValue(res, R.configVarying.bag,
1070                 R.styleable.TestConfig, new String[]{"bag mcc111 xx-rYY"});
1071 
1072         config.setProperty(Properties.MNC, 222);
1073         res = config.getResources();
1074         checkValue(res, R.configVarying.simple, "simple mcc111 mnc222");
1075         checkValue(res, R.configVarying.bag,
1076                 R.styleable.TestConfig, new String[]{"bag mcc111 mnc222"});
1077     }
1078 
1079     @Test
testCombinations()1080     public void testCombinations() {
1081         /**
1082          * Verify that in cases of ties, the specific ordering is followed
1083          */
1084 
1085         /**
1086          * Precidence order: mcc, mnc, locale, swdp, wdp, hdp, screenlayout-size,
1087          * screenlayout-long, orientation, density,
1088          * touchscreen, hidden, keyboard, navigation, width-height
1089          */
1090 
1091         /**
1092          * verify mcc trumps mnc.  Have 110-xx, 220-xx but no 110-220
1093          * so which is selected?  Should be mcc110-xx.
1094          */
1095         TotalConfig config = makeClassicConfig();
1096         config.setProperty(Properties.MCC, 110);
1097         config.setProperty(Properties.MNC, 220);
1098         config.setProperty(Properties.LANGUAGE, "xx");
1099         Resources res = config.getResources();
1100         checkValue(res, R.configVarying.simple, "simple mcc110 xx");
1101         checkValue(res, R.configVarying.bag,
1102                 R.styleable.TestConfig, new String[]{"bag mcc110 xx"});
1103 
1104         /* full A + B + C doesn't exist.  Do we get A + C or B + C?
1105          */
1106         config = makeClassicConfig();
1107         config.setProperty(Properties.MCC, 111);
1108         config.setProperty(Properties.MNC, 222);
1109         config.setProperty(Properties.LANGUAGE, "xx");
1110         res = config.getResources();
1111         checkValue(res, R.configVarying.simple, "simple mcc111 mnc222");
1112         checkValue(res, R.configVarying.bag,
1113                 R.styleable.TestConfig, new String[]{"bag mcc111 mnc222"});
1114 
1115         config = makeClassicConfig();
1116         config.setProperty(Properties.MNC, 222);
1117         config.setProperty(Properties.LANGUAGE, "xx");
1118         config.setProperty(Properties.ORIENTATION,
1119                 Configuration.ORIENTATION_SQUARE);
1120         res = config.getResources();
1121         checkValue(res, R.configVarying.simple, "simple mnc222 xx");
1122         checkValue(res, R.configVarying.bag,
1123                 R.styleable.TestConfig, new String[]{"bag mnc222 xx"});
1124 
1125         config = makeClassicConfig();
1126         config.setProperty(Properties.LANGUAGE, "xx");
1127         config.setProperty(Properties.ORIENTATION,
1128                 Configuration.ORIENTATION_SQUARE);
1129         config.setProperty(Properties.DENSITY, 32);
1130         res = config.getResources();
1131         checkValue(res, R.configVarying.simple, "simple xx square");
1132         checkValue(res, R.configVarying.bag,
1133                 R.styleable.TestConfig, new String[]{"bag xx square"});
1134 
1135         /**
1136          * Verify that proper strings are found for multiple-selectivity case
1137          * (ie, a string set for locale and mcc is found only when both are
1138          * true).
1139          */
1140         config = makeClassicConfig();
1141         config.setProperty(Properties.LANGUAGE, "xx");
1142         config.setProperty(Properties.COUNTRY, "YY");
1143         config.setProperty(Properties.MCC, 111);
1144         res = config.getResources();
1145         checkValue(res, R.configVarying.simple, "simple mcc111 xx-rYY");
1146         checkValue(res, R.configVarying.bag, R.styleable.TestConfig,
1147                 new String[] { "bag mcc111 xx-rYY" });
1148 
1149         config = makeClassicConfig();
1150         config.setProperty(Properties.LANGUAGE, "xx");
1151         config.setProperty(Properties.COUNTRY, "YY");
1152         config.setProperty(Properties.MCC, 333);
1153         res = config.getResources();
1154         checkValue(res, R.configVarying.simple, "simple xx-rYY");
1155         checkValue(res, R.configVarying.bag,
1156                 R.styleable.TestConfig, new String[] { "bag xx-rYY" });
1157 
1158         config = makeClassicConfig();
1159         config.setProperty(Properties.MNC, 333);
1160         res = config.getResources();
1161         checkValue(res, R.configVarying.simple, "simple default");
1162         checkValue(res, R.configVarying.bag,
1163                 R.styleable.TestConfig, new String[]{"bag default"});
1164 
1165         config = makeClassicConfig();
1166         config.setProperty(Properties.ORIENTATION,
1167                 Configuration.ORIENTATION_SQUARE);
1168         config.setProperty(Properties.DENSITY, 32);
1169         config.setProperty(Properties.TOUCHSCREEN,
1170                 Configuration.TOUCHSCREEN_STYLUS);
1171         res = config.getResources();
1172         checkValue(res, R.configVarying.simple, "simple square 32dpi");
1173         checkValue(res, R.configVarying.bag,
1174                 R.styleable.TestConfig, new String[]{"bag square 32dpi"});
1175 
1176         config = makeClassicConfig();
1177         config.setProperty(Properties.DENSITY, 32);
1178         config.setProperty(Properties.TOUCHSCREEN,
1179                 Configuration.TOUCHSCREEN_STYLUS);
1180         config.setProperty(Properties.KEYBOARDHIDDEN,
1181                 Configuration.KEYBOARDHIDDEN_NO);
1182         res = config.getResources();
1183         checkValue(res, R.configVarying.simple, "simple 32dpi stylus");
1184         checkValue(res, R.configVarying.bag,
1185                 R.styleable.TestConfig, new String[]{"bag 32dpi stylus"});
1186 
1187         config = makeClassicConfig();
1188         config.setProperty(Properties.TOUCHSCREEN,
1189                 Configuration.TOUCHSCREEN_STYLUS);
1190         config.setProperty(Properties.KEYBOARDHIDDEN,
1191                 Configuration.KEYBOARDHIDDEN_NO);
1192         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_12KEY);
1193         res = config.getResources();
1194         checkValue(res, R.configVarying.simple, "simple stylus keysexposed");
1195         checkValue(res, R.configVarying.bag,
1196                 R.styleable.TestConfig, new String[]{"bag stylus keysexposed"});
1197 
1198         config = makeClassicConfig();
1199         config.setProperty(Properties.KEYBOARDHIDDEN,
1200                 Configuration.KEYBOARDHIDDEN_NO);
1201         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_12KEY);
1202         config.setProperty(Properties.NAVIGATION,
1203                 Configuration.NAVIGATION_DPAD);
1204         res = config.getResources();
1205         checkValue(res, R.configVarying.simple, "simple keysexposed 12key");
1206         checkValue(res, R.configVarying.bag,
1207                 R.styleable.TestConfig, new String[]{"bag keysexposed 12key"});
1208 
1209         config = makeClassicConfig();
1210         config.setProperty(Properties.KEYBOARD, Configuration.KEYBOARD_12KEY);
1211         config.setProperty(Properties.NAVIGATION,
1212                 Configuration.NAVIGATION_DPAD);
1213         config.setProperty(Properties.HEIGHT, 63);
1214         config.setProperty(Properties.WIDTH, 57);
1215         res = config.getResources();
1216         checkValue(res, R.configVarying.simple, "simple 12key dpad");
1217         checkValue(res, R.configVarying.bag,
1218                 R.styleable.TestConfig, new String[]{"bag 12key dpad"});
1219 
1220         config = makeClassicConfig();
1221         config.setProperty(Properties.NAVIGATION,
1222                 Configuration.NAVIGATION_DPAD);
1223         config.setProperty(Properties.HEIGHT, 640);
1224         config.setProperty(Properties.WIDTH, 400);
1225         res = config.getResources();
1226         checkValue(res, R.configVarying.simple, "simple dpad 63x57");
1227         checkValue(res, R.configVarying.bag,
1228                 R.styleable.TestConfig, new String[]{"bag dpad 63x57"});
1229     }
1230 
1231     @Test
testVersions()1232     public void testVersions() {
1233         final boolean isReleaseBuild = "REL".equals(android.os.Build.VERSION.CODENAME);
1234 
1235         // Release builds must not have a dev SDK version
1236         if (isReleaseBuild) {
1237             assertTrue("Release builds must build with a valid SDK version",
1238                     mTargetSdkVersion < 10000);
1239         }
1240 
1241         // ...and skip this test if this is a dev-SDK-version build
1242         assumeTrue("This product was built with non-release SDK level 10000",
1243                 mTargetSdkVersion < 10000);
1244 
1245         // Check that we get the most recent resources that are <= our
1246         // current version.  Note the special version adjustment, so that
1247         // during development the resource version is incremented to the
1248         // next one.
1249         int vers = android.os.Build.VERSION.SDK_INT;
1250         if (!isReleaseBuild) {
1251             vers++;
1252         }
1253         String expected = "v" + vers + "cur";
1254         assertEquals(expected, mContext.getResources().getString(R.string.version_cur));
1255         assertEquals("base",  mContext.getResources().getString(R.string.version_old));
1256         assertEquals("v3",  mContext.getResources().getString(R.string.version_v3));
1257     }
1258 
1259     @Test
testNormalLocales()1260     public void testNormalLocales() {
1261         Resources res;
1262         TotalConfig config = makeClassicConfig();
1263         // Hebrew
1264         config.setProperty(Properties.LANGUAGE, "iw");
1265         res = config.getResources();
1266         checkValue(res, R.configVarying.simple, "simple iw");
1267         checkValue(res, R.configVarying.bag,
1268                 R.styleable.TestConfig, new String[]{"bag iw"});
1269 
1270         // Hebrew for Israel
1271         config.setProperty(Properties.LANGUAGE, "iw");
1272         config.setProperty(Properties.COUNTRY, "IL");
1273         res = config.getResources();
1274         checkValue(res, R.configVarying.simple, "simple iw IL");
1275         checkValue(res, R.configVarying.bag,
1276                 R.styleable.TestConfig, new String[]{"bag iw IL"});
1277 
1278         config = makeClassicConfig();
1279         // Macedonian
1280         config.setProperty(Properties.LANGUAGE, "mk");
1281         res = config.getResources();
1282         checkValue(res, R.configVarying.simple, "simple mk");
1283         checkValue(res, R.configVarying.bag,
1284                 R.styleable.TestConfig, new String[]{"bag mk"});
1285 
1286         // Macedonian for Macedonia
1287         config.setProperty(Properties.LANGUAGE, "mk");
1288         config.setProperty(Properties.COUNTRY, "MK");
1289         res = config.getResources();
1290         checkValue(res, R.configVarying.simple, "simple mk MK");
1291         checkValue(res, R.configVarying.bag,
1292                 R.styleable.TestConfig, new String[]{"bag mk MK"});
1293     }
1294 
1295     @Test
testExtendedLocales()1296     public void testExtendedLocales() {
1297         TotalConfig config = makeClassicConfig();
1298         // BCP 47 Locale kok
1299         config.setProperty(Properties.LANGUAGE, "kok");
1300         Resources res = config.getResources();
1301         checkValue(res, R.configVarying.simple, "simple kok");
1302         checkValue(res, R.configVarying.bag,
1303                 R.styleable.TestConfig, new String[]{"bag kok"});
1304 
1305         // BCP 47 Locale kok-IN
1306         config.setProperty(Properties.COUNTRY, "IN");
1307         res = config.getResources();
1308         checkValue(res, R.configVarying.simple, "simple kok IN");
1309         checkValue(res, R.configVarying.bag,
1310                 R.styleable.TestConfig, new String[]{"bag kok IN"});
1311 
1312         // BCP 47 Locale kok-419
1313         config.setProperty(Properties.COUNTRY, "419");
1314         res = config.getResources();
1315         checkValue(res, R.configVarying.simple, "simple kok 419");
1316         checkValue(res, R.configVarying.bag,
1317                 R.styleable.TestConfig, new String[]{"bag kok 419"});
1318 
1319 
1320         // BCP 47 Locale kok-419-VARIANT
1321         config.setProperty(Properties.VARIANT, "VARIANT");
1322         res = config.getResources();
1323         checkValue(res, R.configVarying.simple, "simple kok 419 VARIANT");
1324         checkValue(res, R.configVarying.bag,
1325                 R.styleable.TestConfig, new String[]{"bag kok 419 VARIANT"});
1326 
1327         // BCP 47 Locale kok-Knda
1328         config = makeClassicConfig();
1329         config.setProperty(Properties.LANGUAGE, "kok");
1330         config.setProperty(Properties.SCRIPT, "Knda");
1331         res = config.getResources();
1332         checkValue(res, R.configVarying.simple, "simple kok Knda");
1333         checkValue(res, R.configVarying.bag,
1334                 R.styleable.TestConfig, new String[]{"bag kok Knda"});
1335 
1336         // BCP 47 Locale kok-Knda-419
1337         config.setProperty(Properties.COUNTRY, "419");
1338         res = config.getResources();
1339         checkValue(res, R.configVarying.simple, "simple kok Knda 419");
1340         checkValue(res, R.configVarying.bag,
1341                 R.styleable.TestConfig, new String[]{"bag kok Knda 419"});
1342 
1343         // BCP 47 Locale kok-Knda-419-VARIANT
1344         config.setProperty(Properties.VARIANT, "VARIANT");
1345         res = config.getResources();
1346         checkValue(res, R.configVarying.simple, "simple kok Knda 419 VARIANT");
1347         checkValue(res, R.configVarying.bag,
1348                 R.styleable.TestConfig, new String[]{"bag kok Knda 419 VARIANT"});
1349 
1350         // BCP 47 Locale kok-VARIANT
1351         config = makeClassicConfig();
1352         config.setProperty(Properties.LANGUAGE, "kok");
1353         config.setProperty(Properties.VARIANT, "VARIANT");
1354         res = config.getResources();
1355         checkValue(res, R.configVarying.simple, "simple kok VARIANT");
1356         checkValue(res, R.configVarying.bag,
1357                 R.styleable.TestConfig, new String[]{"bag kok VARIANT"});
1358     }
1359 
1360     @Test
testTlAndFilConversion()1361     public void testTlAndFilConversion() {
1362         TotalConfig config = makeClassicConfig();
1363 
1364         // Ensure that "fil" is mapped to "tl" correctly.
1365         config.setProperty(Properties.LANGUAGE, "fil");
1366         config.setProperty(Properties.COUNTRY, "US");
1367         Resources res = config.getResources();
1368         checkValue(res, R.configVarying.simple, "simple fil");  // We have this resource in 'fil'
1369         checkValue(res, R.configVarying.bag,
1370                 R.styleable.TestConfig, new String[] { "bag tl" });  // But this comes from 'tl'
1371 
1372         // Ensure that "fil-PH" is mapped to "tl-PH" correctly.
1373         config = makeClassicConfig();
1374         config.setProperty(Properties.LANGUAGE, "fil");
1375         config.setProperty(Properties.COUNTRY, "PH");
1376         res = config.getResources();
1377         checkValue(res, R.configVarying.simple, "simple tl PH");
1378         checkValue(res, R.configVarying.bag,
1379                 R.styleable.TestConfig, new String[] { "bag tl PH" });
1380 
1381         // Ensure that "fil-SA" works with no "tl" version.
1382         config = makeClassicConfig();
1383         config.setProperty(Properties.LANGUAGE, "fil");
1384         config.setProperty(Properties.COUNTRY, "SA");
1385         res = config.getResources();
1386         checkValue(res, R.configVarying.simple, "simple fil");  // This comes from 'fil'
1387         checkValue(res, R.configVarying.bag,
1388                 R.styleable.TestConfig, new String[] { "bag fil SA" });  // And this from 'fil-SA'
1389 
1390         // Ensure that "tlh" is not mistakenly treated as a "tl" variant.
1391         config = makeClassicConfig();
1392         config.setProperty(Properties.LANGUAGE, "tlh");
1393         config.setProperty(Properties.COUNTRY, "US");
1394         res = config.getResources();
1395         checkValue(res, R.configVarying.simple, "simple tlh");
1396         checkValue(res, R.configVarying.bag,
1397                 R.styleable.TestConfig, new String[] { "bag tlh" });
1398 
1399         config = makeClassicConfig();
1400         config.setProperty(Properties.LANGUAGE, "tgl");
1401         res = config.getResources();
1402         checkValue(res, R.configVarying.simple, "simple tgl");
1403         checkValue(res, R.configVarying.bag,
1404                 R.styleable.TestConfig, new String[] { "bag tgl" });
1405 
1406         config = makeClassicConfig();
1407         config.setProperty(Properties.LANGUAGE, "tgl");
1408         config.setProperty(Properties.COUNTRY, "PH");
1409         res = config.getResources();
1410         checkValue(res, R.configVarying.simple, "simple tgl PH");
1411         checkValue(res, R.configVarying.bag,
1412                 R.styleable.TestConfig, new String[] { "bag tgl PH" });
1413     }
1414 
1415     @Test
testGetLocalesConvertsTlToFil()1416     public void testGetLocalesConvertsTlToFil() {
1417         TotalConfig config = makeClassicConfig();
1418 
1419         // Check that the list of locales doesn't contain any of the
1420         // "tl" variants. They should've been converted to "fil"
1421         // locales.
1422         AssetManager am = config.getResources().getAssets();
1423         String[] locales = am.getLocales();
1424         final List<String> tlLocales = new ArrayList<String>(4);
1425         final List<String> filLocales = new ArrayList<String>(4);
1426         for (String locale : locales) {
1427             if (locale.startsWith("tl-") || locale.equals("tl")) {
1428                 tlLocales.add(locale);
1429             }
1430 
1431             if (locale.startsWith("fil-") || locale.equals("fil")) {
1432                 filLocales.add(locale);
1433             }
1434         }
1435 
1436         assertEquals(0, tlLocales.size());
1437         assertEquals(3, filLocales.size());
1438         assertTrue(filLocales.contains("fil"));
1439         assertTrue(filLocales.contains("fil-PH"));
1440         assertTrue(filLocales.contains("fil-SA"));
1441     }
1442 }
1443