[go: nahoru, domu]

Merge "Bump all versions for March 13th Release" into androidx-master-dev
am: b83b3330d8

Change-Id: Id45dc42fe759e7a9f40818c751e4e4601f9a4b4c
diff --git a/appcompat/resources/src/main/java/androidx/appcompat/widget/DrawableUtils.java b/appcompat/resources/src/main/java/androidx/appcompat/widget/DrawableUtils.java
index 58b1d10..89bb5dc 100644
--- a/appcompat/resources/src/main/java/androidx/appcompat/widget/DrawableUtils.java
+++ b/appcompat/resources/src/main/java/androidx/appcompat/widget/DrawableUtils.java
@@ -33,6 +33,7 @@
 import androidx.annotation.RestrictTo;
 import androidx.core.graphics.drawable.DrawableCompat;
 import androidx.core.graphics.drawable.WrappedDrawable;
+import androidx.core.os.BuildCompat;
 
 import java.lang.reflect.Field;
 import java.lang.reflect.Method;
@@ -68,6 +69,15 @@
      * use reflection. Since the {@code Insets} class is hidden also, we return a Rect instead.
      */
     public static Rect getOpticalBounds(Drawable drawable) {
+        if (BuildCompat.isAtLeastQ()) {
+            final android.graphics.Insets insets = drawable.getOpticalInsets();
+            final Rect result = new Rect();
+            result.left = insets.left;
+            result.right = insets.right;
+            result.top = insets.top;
+            result.bottom = insets.bottom;
+            return result;
+        }
         if (sInsetsClazz != null) {
             try {
                 // If the Drawable is wrapped, we need to manually unwrap it and process
diff --git a/appcompat/src/androidTest/java/androidx/appcompat/widget/AppCompatTextViewTest.java b/appcompat/src/androidTest/java/androidx/appcompat/widget/AppCompatTextViewTest.java
index 9b4e2ad..4745c02 100644
--- a/appcompat/src/androidTest/java/androidx/appcompat/widget/AppCompatTextViewTest.java
+++ b/appcompat/src/androidTest/java/androidx/appcompat/widget/AppCompatTextViewTest.java
@@ -41,6 +41,7 @@
 import android.os.Build;
 import android.os.LocaleList;
 import android.text.Layout;
+import android.text.PrecomputedText;
 import android.view.View;
 import android.view.ViewGroup;
 import android.view.textclassifier.TextClassificationManager;
@@ -54,6 +55,7 @@
 import androidx.appcompat.testutils.TestUtils;
 import androidx.core.content.ContextCompat;
 import androidx.core.content.res.ResourcesCompat;
+import androidx.core.os.BuildCompat;
 import androidx.core.graphics.ColorUtils;
 import androidx.core.text.PrecomputedTextCompat;
 import androidx.core.view.ViewCompat;
@@ -576,6 +578,9 @@
                 // setText may wrap the given text with SpannedString. Check the contents by casting
                 // to String.
                 assertEquals(SAMPLE_TEXT_1, tv.getText().toString());
+                if (BuildCompat.isAtLeastQ()) {
+                    assertTrue(tv.getText() instanceof PrecomputedText);
+                }
             }
         });
     }
@@ -593,6 +598,9 @@
                 tv.measure(UNLIMITED_MEASURE_SPEC, UNLIMITED_MEASURE_SPEC);
                 assertNotEquals(0.0f, tv.getMeasuredWidth());
                 assertEquals(SAMPLE_TEXT_1, tv.getText().toString());
+                if (BuildCompat.isAtLeastQ()) {
+                    assertTrue(tv.getText() instanceof PrecomputedText);
+                }
             }
         });
         executor.doExecution(0);
@@ -622,6 +630,9 @@
                 // setText may wrap the given text with SpannedString. Check the contents by casting
                 // to String.
                 assertEquals(SAMPLE_TEXT_2, tv.getText().toString());
+                if (BuildCompat.isAtLeastQ()) {
+                    assertTrue(tv.getText() instanceof PrecomputedText);
+                }
             }
         });
         executor.doExecution(0);  // Do execution of 1st runnable.
@@ -634,6 +645,9 @@
                 // setText may wrap the given text with SpannedString. Check the contents by casting
                 // to String.
                 assertEquals(SAMPLE_TEXT_2, tv.getText().toString());
+                if (BuildCompat.isAtLeastQ()) {
+                    assertTrue(tv.getText() instanceof PrecomputedText);
+                }
             }
         });
     }
diff --git a/appcompat/src/main/java/androidx/appcompat/widget/ListPopupWindow.java b/appcompat/src/main/java/androidx/appcompat/widget/ListPopupWindow.java
index 056213e..72ef8eb 100644
--- a/appcompat/src/main/java/androidx/appcompat/widget/ListPopupWindow.java
+++ b/appcompat/src/main/java/androidx/appcompat/widget/ListPopupWindow.java
@@ -23,6 +23,7 @@
 import android.database.DataSetObserver;
 import android.graphics.Rect;
 import android.graphics.drawable.Drawable;
+import android.os.Build;
 import android.os.Handler;
 import android.util.AttributeSet;
 import android.util.Log;
@@ -75,29 +76,35 @@
      */
     static final int EXPAND_LIST_TIMEOUT = 250;
 
-    private static Method sClipToWindowEnabledMethod;
+    private static Method sSetClipToWindowEnabledMethod;
     private static Method sGetMaxAvailableHeightMethod;
     private static Method sSetEpicenterBoundsMethod;
 
     static {
-        try {
-            sClipToWindowEnabledMethod = PopupWindow.class.getDeclaredMethod(
-                    "setClipToScreenEnabled", boolean.class);
-        } catch (NoSuchMethodException e) {
-            Log.i(TAG, "Could not find method setClipToScreenEnabled() on PopupWindow. Oh well.");
+        if (Build.VERSION.SDK_INT <= 28) {
+            try {
+                sSetClipToWindowEnabledMethod = PopupWindow.class.getDeclaredMethod(
+                        "setClipToScreenEnabled", boolean.class);
+            } catch (NoSuchMethodException e) {
+                Log.i(TAG,
+                        "Could not find method setClipToScreenEnabled() on PopupWindow. Oh well.");
+            }
+            try {
+                sSetEpicenterBoundsMethod = PopupWindow.class.getDeclaredMethod(
+                        "setEpicenterBounds", Rect.class);
+            } catch (NoSuchMethodException e) {
+                Log.i(TAG,
+                        "Could not find method setEpicenterBounds(Rect) on PopupWindow. Oh well.");
+            }
         }
-        try {
-            sGetMaxAvailableHeightMethod = PopupWindow.class.getDeclaredMethod(
-                    "getMaxAvailableHeight", View.class, int.class, boolean.class);
-        } catch (NoSuchMethodException e) {
-            Log.i(TAG, "Could not find method getMaxAvailableHeight(View, int, boolean)"
-                    + " on PopupWindow. Oh well.");
-        }
-        try {
-            sSetEpicenterBoundsMethod = PopupWindow.class.getDeclaredMethod(
-                    "setEpicenterBounds", Rect.class);
-        } catch (NoSuchMethodException e) {
-            Log.i(TAG, "Could not find method setEpicenterBounds(Rect) on PopupWindow. Oh well.");
+        if (Build.VERSION.SDK_INT <= 23) {
+            try {
+                sGetMaxAvailableHeightMethod = PopupWindow.class.getDeclaredMethod(
+                        "getMaxAvailableHeight", View.class, int.class, boolean.class);
+            } catch (NoSuchMethodException e) {
+                Log.i(TAG, "Could not find method getMaxAvailableHeight(View, int, boolean)"
+                        + " on PopupWindow. Oh well.");
+            }
         }
     }
 
@@ -734,12 +741,16 @@
             if (mOverlapAnchorSet) {
                 PopupWindowCompat.setOverlapAnchor(mPopup, mOverlapAnchor);
             }
-            if (sSetEpicenterBoundsMethod != null) {
-                try {
-                    sSetEpicenterBoundsMethod.invoke(mPopup, mEpicenterBounds);
-                } catch (Exception e) {
-                    Log.e(TAG, "Could not invoke setEpicenterBounds on PopupWindow", e);
+            if (Build.VERSION.SDK_INT <= 28) {
+                if (sSetEpicenterBoundsMethod != null) {
+                    try {
+                        sSetEpicenterBoundsMethod.invoke(mPopup, mEpicenterBounds);
+                    } catch (Exception e) {
+                        Log.e(TAG, "Could not invoke setEpicenterBounds on PopupWindow", e);
+                    }
                 }
+            } else {
+                mPopup.setEpicenterBounds(mEpicenterBounds);
             }
             PopupWindowCompat.showAsDropDown(mPopup, getAnchorView(), mDropDownHorizontalOffset,
                     mDropDownVerticalOffset, mDropDownGravity);
@@ -1418,25 +1429,33 @@
     }
 
     private void setPopupClipToScreenEnabled(boolean clip) {
-        if (sClipToWindowEnabledMethod != null) {
-            try {
-                sClipToWindowEnabledMethod.invoke(mPopup, clip);
-            } catch (Exception e) {
-                Log.i(TAG, "Could not call setClipToScreenEnabled() on PopupWindow. Oh well.");
+        if (Build.VERSION.SDK_INT <= 28) {
+            if (sSetClipToWindowEnabledMethod != null) {
+                try {
+                    sSetClipToWindowEnabledMethod.invoke(mPopup, clip);
+                } catch (Exception e) {
+                    Log.i(TAG, "Could not call setClipToScreenEnabled() on PopupWindow. Oh well.");
+                }
             }
+        } else {
+            mPopup.setClipToScreenEnabled(clip);
         }
     }
 
     private int getMaxAvailableHeight(View anchor, int yOffset, boolean ignoreBottomDecorations) {
-        if (sGetMaxAvailableHeightMethod != null) {
-            try {
-                return (int) sGetMaxAvailableHeightMethod.invoke(mPopup, anchor, yOffset,
-                        ignoreBottomDecorations);
-            } catch (Exception e) {
-                Log.i(TAG, "Could not call getMaxAvailableHeightMethod(View, int, boolean)"
-                        + " on PopupWindow. Using the public version.");
+        if (Build.VERSION.SDK_INT <= 23) {
+            if (sGetMaxAvailableHeightMethod != null) {
+                try {
+                    return (int) sGetMaxAvailableHeightMethod.invoke(mPopup, anchor, yOffset,
+                            ignoreBottomDecorations);
+                } catch (Exception e) {
+                    Log.i(TAG, "Could not call getMaxAvailableHeightMethod(View, int, boolean)"
+                            + " on PopupWindow. Using the public version.");
+                }
             }
+            return mPopup.getMaxAvailableHeight(anchor, yOffset);
+        } else {
+            return mPopup.getMaxAvailableHeight(anchor, yOffset, ignoreBottomDecorations);
         }
-        return mPopup.getMaxAvailableHeight(anchor, yOffset);
     }
 }
diff --git a/appcompat/src/main/java/androidx/appcompat/widget/MenuPopupWindow.java b/appcompat/src/main/java/androidx/appcompat/widget/MenuPopupWindow.java
index aa8295a..8a80b87 100644
--- a/appcompat/src/main/java/androidx/appcompat/widget/MenuPopupWindow.java
+++ b/appcompat/src/main/java/androidx/appcompat/widget/MenuPopupWindow.java
@@ -57,8 +57,10 @@
 
     static {
         try {
-            sSetTouchModalMethod = PopupWindow.class.getDeclaredMethod(
-                    "setTouchModal", boolean.class);
+            if (Build.VERSION.SDK_INT <= 28) {
+                sSetTouchModalMethod = PopupWindow.class.getDeclaredMethod(
+                        "setTouchModal", boolean.class);
+            }
         } catch (NoSuchMethodException e) {
             Log.i(TAG, "Could not find method setTouchModal() on PopupWindow. Oh well.");
         }
@@ -98,12 +100,16 @@
      * other windows behind it.
      */
     public void setTouchModal(final boolean touchModal) {
-        if (sSetTouchModalMethod != null) {
-            try {
-                sSetTouchModalMethod.invoke(mPopup, touchModal);
-            } catch (Exception e) {
-                Log.i(TAG, "Could not invoke setTouchModal() on PopupWindow. Oh well.");
+        if (Build.VERSION.SDK_INT <= 28) {
+            if (sSetTouchModalMethod != null) {
+                try {
+                    sSetTouchModalMethod.invoke(mPopup, touchModal);
+                } catch (Exception e) {
+                    Log.i(TAG, "Could not invoke setTouchModal() on PopupWindow. Oh well.");
+                }
             }
+        } else {
+            mPopup.setTouchModal(touchModal);
         }
     }
 
diff --git a/biometric/api/1.0.0-alpha04.txt b/biometric/api/1.0.0-alpha04.txt
index f517f0f..576a1e5 100644
--- a/biometric/api/1.0.0-alpha04.txt
+++ b/biometric/api/1.0.0-alpha04.txt
@@ -13,6 +13,7 @@
     field public static final int ERROR_LOCKOUT_PERMANENT = 9; // 0x9
     field public static final int ERROR_NEGATIVE_BUTTON = 13; // 0xd
     field public static final int ERROR_NO_BIOMETRICS = 11; // 0xb
+    field public static final int ERROR_NO_DEVICE_CREDENTIAL = 14; // 0xe
     field public static final int ERROR_NO_SPACE = 4; // 0x4
     field public static final int ERROR_TIMEOUT = 3; // 0x3
     field public static final int ERROR_UNABLE_TO_PROCESS = 2; // 0x2
@@ -41,8 +42,10 @@
   }
 
   public static class BiometricPrompt.PromptInfo {
+    method public boolean getAllowDeviceCredential();
     method public CharSequence? getDescription();
     method public CharSequence getNegativeButtonText();
+    method public boolean getRequireConfirmation();
     method public CharSequence? getSubtitle();
     method public CharSequence getTitle();
   }
@@ -50,8 +53,10 @@
   public static class BiometricPrompt.PromptInfo.Builder {
     ctor public BiometricPrompt.PromptInfo.Builder();
     method public androidx.biometric.BiometricPrompt.PromptInfo build();
+    method @RequiresApi(29) public androidx.biometric.BiometricPrompt.PromptInfo.Builder setAllowDeviceCredential(boolean);
     method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setDescription(CharSequence?);
     method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setNegativeButtonText(CharSequence);
+    method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setRequireConfirmation(boolean);
     method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setSubtitle(CharSequence?);
     method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setTitle(CharSequence);
   }
diff --git a/biometric/api/current.txt b/biometric/api/current.txt
index f517f0f..576a1e5 100644
--- a/biometric/api/current.txt
+++ b/biometric/api/current.txt
@@ -13,6 +13,7 @@
     field public static final int ERROR_LOCKOUT_PERMANENT = 9; // 0x9
     field public static final int ERROR_NEGATIVE_BUTTON = 13; // 0xd
     field public static final int ERROR_NO_BIOMETRICS = 11; // 0xb
+    field public static final int ERROR_NO_DEVICE_CREDENTIAL = 14; // 0xe
     field public static final int ERROR_NO_SPACE = 4; // 0x4
     field public static final int ERROR_TIMEOUT = 3; // 0x3
     field public static final int ERROR_UNABLE_TO_PROCESS = 2; // 0x2
@@ -41,8 +42,10 @@
   }
 
   public static class BiometricPrompt.PromptInfo {
+    method public boolean getAllowDeviceCredential();
     method public CharSequence? getDescription();
     method public CharSequence getNegativeButtonText();
+    method public boolean getRequireConfirmation();
     method public CharSequence? getSubtitle();
     method public CharSequence getTitle();
   }
@@ -50,8 +53,10 @@
   public static class BiometricPrompt.PromptInfo.Builder {
     ctor public BiometricPrompt.PromptInfo.Builder();
     method public androidx.biometric.BiometricPrompt.PromptInfo build();
+    method @RequiresApi(29) public androidx.biometric.BiometricPrompt.PromptInfo.Builder setAllowDeviceCredential(boolean);
     method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setDescription(CharSequence?);
     method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setNegativeButtonText(CharSequence);
+    method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setRequireConfirmation(boolean);
     method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setSubtitle(CharSequence?);
     method public androidx.biometric.BiometricPrompt.PromptInfo.Builder setTitle(CharSequence);
   }
diff --git a/biometric/src/main/java/androidx/biometric/BiometricConstants.java b/biometric/src/main/java/androidx/biometric/BiometricConstants.java
index f4384b0..7824178 100644
--- a/biometric/src/main/java/androidx/biometric/BiometricConstants.java
+++ b/biometric/src/main/java/androidx/biometric/BiometricConstants.java
@@ -107,6 +107,11 @@
     int ERROR_NEGATIVE_BUTTON = 13;
 
     /**
+     * The device does not have pin, pattern, or password set up.
+     */
+    int ERROR_NO_DEVICE_CREDENTIAL = 14;
+
+    /**
      * @hide
      */
     @RestrictTo(RestrictTo.Scope.LIBRARY)
diff --git a/biometric/src/main/java/androidx/biometric/BiometricFragment.java b/biometric/src/main/java/androidx/biometric/BiometricFragment.java
index 5622c89..1d9da37 100644
--- a/biometric/src/main/java/androidx/biometric/BiometricFragment.java
+++ b/biometric/src/main/java/androidx/biometric/BiometricFragment.java
@@ -22,12 +22,14 @@
 import android.os.CancellationSignal;
 import android.os.Handler;
 import android.os.Looper;
+import android.text.TextUtils;
 import android.view.LayoutInflater;
 import android.view.View;
 import android.view.ViewGroup;
 
 import androidx.annotation.RequiresApi;
 import androidx.annotation.RestrictTo;
+import androidx.core.os.BuildCompat;
 import androidx.fragment.app.Fragment;
 
 import java.util.concurrent.Executor;
@@ -207,13 +209,25 @@
         // Start the actual authentication when the fragment is attached.
         if (!mShowing) {
             mNegativeButtonText = mBundle.getCharSequence(BiometricPrompt.KEY_NEGATIVE_TEXT);
-            mBiometricPrompt = new android.hardware.biometrics.BiometricPrompt.Builder(getContext())
-                    .setTitle(mBundle.getCharSequence(BiometricPrompt.KEY_TITLE))
+            final android.hardware.biometrics.BiometricPrompt.Builder builder =
+                    new android.hardware.biometrics.BiometricPrompt.Builder(getContext());
+            builder.setTitle(mBundle.getCharSequence(BiometricPrompt.KEY_TITLE))
                     .setSubtitle(mBundle.getCharSequence(BiometricPrompt.KEY_SUBTITLE))
-                    .setDescription(mBundle.getCharSequence(BiometricPrompt.KEY_DESCRIPTION))
-                    .setNegativeButton(mBundle.getCharSequence(BiometricPrompt.KEY_NEGATIVE_TEXT),
-                            mClientExecutor, mNegativeButtonListener)
-                    .build();
+                    .setDescription(mBundle.getCharSequence(BiometricPrompt.KEY_DESCRIPTION));
+            // The negative text could be empty if setAllowDeviceCredential is true.
+            if (!TextUtils.isEmpty(mBundle.getCharSequence(BiometricPrompt.KEY_NEGATIVE_TEXT))) {
+                builder.setNegativeButton(
+                        mBundle.getCharSequence(BiometricPrompt.KEY_NEGATIVE_TEXT),
+                        mClientExecutor, mNegativeButtonListener);
+            }
+
+            if (BuildCompat.isAtLeastQ()) {
+                builder.setRequireConfirmation(
+                        mBundle.getBoolean((BiometricPrompt.KEY_REQUIRE_CONFIRMATION), true));
+                builder.setAllowDeviceCredential(
+                        mBundle.getBoolean(BiometricPrompt.KEY_ALLOW_DEVICE_CREDENTIAL));
+            }
+            mBiometricPrompt = builder.build();
             mCancellationSignal = new CancellationSignal();
             if (mCryptoObject == null) {
                 mBiometricPrompt.authenticate(mCancellationSignal, mExecutor,
diff --git a/biometric/src/main/java/androidx/biometric/BiometricPrompt.java b/biometric/src/main/java/androidx/biometric/BiometricPrompt.java
index da6bf70..b59c10e 100644
--- a/biometric/src/main/java/androidx/biometric/BiometricPrompt.java
+++ b/biometric/src/main/java/androidx/biometric/BiometricPrompt.java
@@ -27,6 +27,7 @@
 import androidx.annotation.IntDef;
 import androidx.annotation.NonNull;
 import androidx.annotation.Nullable;
+import androidx.annotation.RequiresApi;
 import androidx.fragment.app.FragmentActivity;
 import androidx.fragment.app.FragmentManager;
 import androidx.lifecycle.Lifecycle;
@@ -60,6 +61,8 @@
     static final String KEY_SUBTITLE = "subtitle";
     static final String KEY_DESCRIPTION = "description";
     static final String KEY_NEGATIVE_TEXT = "negative_text";
+    static final String KEY_REQUIRE_CONFIRMATION = "require_confirmation";
+    static final String KEY_ALLOW_DEVICE_CREDENTIAL = "allow_device_credential";
 
     @Retention(SOURCE)
     @IntDef({BiometricConstants.ERROR_HW_UNAVAILABLE,
@@ -73,7 +76,8 @@
             BiometricConstants.ERROR_USER_CANCELED,
             BiometricConstants.ERROR_NO_BIOMETRICS,
             BiometricConstants.ERROR_HW_NOT_PRESENT,
-            BiometricConstants.ERROR_NEGATIVE_BUTTON})
+            BiometricConstants.ERROR_NEGATIVE_BUTTON,
+            BiometricConstants.ERROR_NO_DEVICE_CREDENTIAL})
     @interface BiometricError {}
 
     /**
@@ -237,6 +241,52 @@
             }
 
             /**
+             * Optional: A hint to the system to require user confirmation after a biometric has
+             * been authenticated. For example, implicit modalities like Face and
+             * Iris authentication are passive, meaning they don't require an explicit user action
+             * to complete. When set to 'false', the user action (e.g. pressing a button)
+             * will not be required. BiometricPrompt will require confirmation by default.
+             *
+             * A typical use case for not requiring confirmation would be for low-risk transactions,
+             * such as re-authenticating a recently authenticated application. A typical use case
+             * for requiring confirmation would be for authorizing a purchase.
+             *
+             * Note that this is a hint to the system. The system may choose to ignore the flag. For
+             * example, if the user disables implicit authentication in Settings, or if it does not
+             * apply to a modality (e.g. Fingerprint). When ignored, the system will default to
+             * requiring confirmation.
+             *
+             * This method only applies to Q and above.
+             */
+            @NonNull
+            public Builder setRequireConfirmation(boolean requireConfirmation) {
+                mBundle.putBoolean(KEY_REQUIRE_CONFIRMATION, requireConfirmation);
+                return this;
+            }
+
+            /**
+             * The user will first be prompted to authenticate with biometrics, but also given the
+             * option to authenticate with their device PIN, pattern, or password. Developers should
+             * first check {@link android.app.KeyguardManager#isDeviceSecure()} before enabling
+             * this. If the device is not secure, {@link BiometricPrompt#ERROR_NO_DEVICE_CREDENTIAL}
+             * will be returned in
+             * {@link AuthenticationCallback#onAuthenticationError(int, CharSequence)}}
+             *
+             * Note that {@link Builder#setNegativeButtonText(CharSequence)} should not be set
+             * if this is set to true.
+             *
+             * @param enable When true, the prompt will fall back to ask for the user's device
+             *               credentials (PIN, pattern, or password).
+             * @return
+             */
+            @RequiresApi(29)
+            @NonNull
+            public Builder setAllowDeviceCredential(boolean enable) {
+                mBundle.putBoolean(KEY_ALLOW_DEVICE_CREDENTIAL, enable);
+                return this;
+            }
+
+            /**
              * Creates a {@link BiometricPrompt}.
              * @return a {@link BiometricPrompt}
              * @throws IllegalArgumentException if any of the required fields are not set.
@@ -245,12 +295,17 @@
             public PromptInfo build() {
                 final CharSequence title = mBundle.getCharSequence(KEY_TITLE);
                 final CharSequence negative = mBundle.getCharSequence(KEY_NEGATIVE_TEXT);
+                boolean allowDeviceCredential = mBundle.getBoolean(KEY_ALLOW_DEVICE_CREDENTIAL);
 
                 if (TextUtils.isEmpty(title)) {
                     throw new IllegalArgumentException("Title must be set and non-empty");
-                } else if (TextUtils.isEmpty(negative)) {
-                    throw new IllegalArgumentException("Negative button text must be set and "
-                            + "non-empty");
+                }
+                if (TextUtils.isEmpty(negative) && !allowDeviceCredential) {
+                    throw new IllegalArgumentException("Negative text must be set and non-empty");
+                }
+                if (!TextUtils.isEmpty(negative) && allowDeviceCredential) {
+                    throw new IllegalArgumentException("Can't have both negative button behavior"
+                            + " and device credential enabled");
                 }
                 return new PromptInfo(mBundle);
             }
@@ -297,6 +352,22 @@
         public CharSequence getNegativeButtonText() {
             return mBundle.getCharSequence(KEY_NEGATIVE_TEXT);
         }
+
+        /**
+         * @return See {@link Builder#setRequireConfirmation(boolean)}.
+         */
+        @Nullable
+        public boolean getRequireConfirmation() {
+            return mBundle.getBoolean(KEY_REQUIRE_CONFIRMATION);
+        }
+
+        /**
+         * @return See {@link Builder#setAllowDeviceCredential(boolean)}.
+         */
+        @Nullable
+        public boolean getAllowDeviceCredential() {
+            return mBundle.getBoolean(KEY_ALLOW_DEVICE_CREDENTIAL);
+        }
     }
 
     // Passed in from the client.
@@ -444,6 +515,8 @@
             throw new IllegalArgumentException("PromptInfo can not be null");
         } else if (crypto == null) {
             throw new IllegalArgumentException("CryptoObject can not be null");
+        } else if (info.getBundle().getBoolean(KEY_ALLOW_DEVICE_CREDENTIAL)) {
+            throw new IllegalArgumentException("Device credential not supported with crypto");
         }
         authenticateInternal(info, crypto);
     }
diff --git a/buildSrc/src/main/kotlin/androidx/build/DiffAndDocs.kt b/buildSrc/src/main/kotlin/androidx/build/DiffAndDocs.kt
index 224130c..3573279 100644
--- a/buildSrc/src/main/kotlin/androidx/build/DiffAndDocs.kt
+++ b/buildSrc/src/main/kotlin/androidx/build/DiffAndDocs.kt
@@ -82,6 +82,12 @@
         val doclavaConfiguration = root.configurations.create("doclava")
         doclavaConfiguration.dependencies.add(root.dependencies.create(DOCLAVA_DEPENDENCY))
 
+        // Pulls in the :fakeannotations project, which provides modified annotations required to
+        // generate SDK API stubs in Doclava from Metalava-generated platform SDK stubs.
+        val annotationConfiguration = root.configurations.create("annotation")
+        annotationConfiguration.dependencies.add(root.dependencies.project(
+            mapOf("path" to ":fakeannotations")))
+
         // tools.jar required for com.sun.javadoc
         // TODO this breaks the ability to use JDK 9+ for compilation.
         doclavaConfiguration.dependencies.add(root.dependencies.create(root.files(
@@ -90,7 +96,8 @@
         rules = additionalRules + TIP_OF_TREE
         docsProject = root.findProject(":docs-fake")
         anchorTask = root.tasks.register("anchorDocsTask")
-        val generateSdkApiTask = createGenerateSdkApiTask(root, doclavaConfiguration)
+        val generateSdkApiTask = createGenerateSdkApiTask(root, doclavaConfiguration,
+            annotationConfiguration)
         val now = LocalDateTime.now()
         // The diff output assumes that each library is of the same version,
         // but our libraries may each be of different versions
@@ -560,13 +567,21 @@
  * <p>
  * This is useful for federating docs against the platform SDK when no API XML file is available.
  */
-private fun createGenerateSdkApiTask(project: Project, doclavaConfig: Configuration): DoclavaTask =
+private fun createGenerateSdkApiTask(
+    project: Project,
+    doclavaConfig: Configuration,
+    annotationConfig: Configuration
+): DoclavaTask =
         project.tasks.createWithConfig("generateSdkApi", DoclavaTask::class.java) {
             dependsOn(doclavaConfig)
+            dependsOn(annotationConfig)
             description = "Generates API files for the current SDK."
             setDocletpath(doclavaConfig.resolve())
             destinationDir = project.docsDir()
+            // Strip the androidx.annotation classes injected by Metalava. They are not accessible.
             classpath = androidJarFile(project)
+                .filter { it.path.contains("androidx/annotation") }
+                .plus(project.files(annotationConfig.resolve()))
             source(project.zipTree(androidSrcJarFile(project))
                 .matching(PatternSet().include("**/*.java")))
             exclude("**/overview.html") // TODO https://issuetracker.google.com/issues/116699307
diff --git a/buildSrc/src/main/kotlin/androidx/build/PublishDocsRules.kt b/buildSrc/src/main/kotlin/androidx/build/PublishDocsRules.kt
index 7f7d4dc..9b587e7 100644
--- a/buildSrc/src/main/kotlin/androidx/build/PublishDocsRules.kt
+++ b/buildSrc/src/main/kotlin/androidx/build/PublishDocsRules.kt
@@ -46,7 +46,7 @@
     prebuilts(LibraryGroups.CORE, "core-ktx", "1.1.0-alpha04")
     prebuilts(LibraryGroups.CURSORADAPTER, "1.0.0")
     prebuilts(LibraryGroups.CUSTOMVIEW, "1.0.0")
-    prebuilts(LibraryGroups.DOCUMENTFILE, "1.0.0")
+    ignore(LibraryGroups.DOCUMENTFILE)
     prebuilts(LibraryGroups.DRAWERLAYOUT, "1.0.0")
     prebuilts(LibraryGroups.DYNAMICANIMATION, "dynamicanimation-ktx", "1.0.0-alpha01")
     prebuilts(LibraryGroups.DYNAMICANIMATION, "1.0.0")
diff --git a/buildSrc/src/main/kotlin/androidx/build/SupportConfig.kt b/buildSrc/src/main/kotlin/androidx/build/SupportConfig.kt
index 5a45ac0..85d5382 100644
--- a/buildSrc/src/main/kotlin/androidx/build/SupportConfig.kt
+++ b/buildSrc/src/main/kotlin/androidx/build/SupportConfig.kt
@@ -27,20 +27,24 @@
 
     /**
      * The Android SDK version to use for compilation.
-     *
+     * <p>
      * Either an integer value or a pre-release platform code, prefixed with "android-" (ex.
      * "android-28" or "android-Q") as you would see within the SDK's platforms directory.
      */
-    const val COMPILE_SDK_VERSION = "android-28"
+    const val COMPILE_SDK_VERSION = "android-Q"
 
     /**
      * The Android SDK version to use for targetSdkVersion meta-data.
-     *
+     * <p>
      * Either an integer value (ex. 28), a pre-release platform code (ex. "Q") as you would see
      * within the SDK's platforms directory as android-<version>, or a released platform version
      * code as you would see within Build.VERSIONS.VERSION_CODE (ex. "HONEYCOMB" or "P").
+     * <p>
+     * <strong>Note:</strong> This must be set to an integer value or released platform version in
+     * order for tests to run on devices running released versions of the Android OS. If this is
+     * set to a pre-release version, tests will only be able to run on pre-release devices.
      */
-    const val TARGET_SDK_VERSION = "28"
+    const val TARGET_SDK_VERSION = 28
 
     fun getKeystore(project: Project): File {
         val supportRoot = (project.rootProject.property("ext") as ExtraPropertiesExtension)
diff --git a/car/core/src/main/java/androidx/car/drawer/CarDrawerAdapter.java b/car/core/src/main/java/androidx/car/drawer/CarDrawerAdapter.java
index 3bafda9..0605865 100644
--- a/car/core/src/main/java/androidx/car/drawer/CarDrawerAdapter.java
+++ b/car/core/src/main/java/androidx/car/drawer/CarDrawerAdapter.java
@@ -99,6 +99,7 @@
         void onTitleChanged(@Nullable CharSequence newTitle);
     }
 
+    @SuppressWarnings("deprecation")
     protected CarDrawerAdapter(Context context, boolean showDisabledListOnEmpty) {
         mShowDisabledListOnEmpty = showDisabledListOnEmpty;
 
diff --git a/core/api/1.1.0-alpha03.txt b/core/api/1.1.0-alpha03.txt
index cdd40ca..43c05b2 100644
--- a/core/api/1.1.0-alpha03.txt
+++ b/core/api/1.1.0-alpha03.txt
@@ -2354,6 +2354,7 @@
     method public boolean isScrollable();
     method public boolean isSelected();
     method public boolean isShowingHintText();
+    method public boolean isTextEntryKey();
     method public boolean isVisibleToUser();
     method public static androidx.core.view.accessibility.AccessibilityNodeInfoCompat! obtain(android.view.View!);
     method public static androidx.core.view.accessibility.AccessibilityNodeInfoCompat! obtain(android.view.View!, int);
@@ -2413,6 +2414,7 @@
     method public void setSource(android.view.View!);
     method public void setSource(android.view.View!, int);
     method public void setText(CharSequence!);
+    method public void setTextEntryKey(boolean);
     method public void setTextSelection(int, int);
     method public void setTooltipText(CharSequence?);
     method public void setTraversalAfter(android.view.View!);
@@ -2486,6 +2488,10 @@
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_MOVE_WINDOW;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_NEXT_AT_MOVEMENT_GRANULARITY;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_NEXT_HTML_ELEMENT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_DOWN;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_LEFT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_RIGHT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_UP;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PASTE;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PREVIOUS_AT_MOVEMENT_GRANULARITY;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PREVIOUS_HTML_ELEMENT;
diff --git a/core/api/1.1.0-alpha04.txt b/core/api/1.1.0-alpha04.txt
index e9cfd20..1852227 100644
--- a/core/api/1.1.0-alpha04.txt
+++ b/core/api/1.1.0-alpha04.txt
@@ -2337,6 +2337,7 @@
     method public int getTextSelectionEnd();
     method public int getTextSelectionStart();
     method public CharSequence? getTooltipText();
+    method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat.TouchDelegateInfoCompat? getTouchDelegateInfo();
     method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat! getTraversalAfter();
     method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat! getTraversalBefore();
     method public String! getViewIdResourceName();
@@ -2362,6 +2363,7 @@
     method public boolean isScrollable();
     method public boolean isSelected();
     method public boolean isShowingHintText();
+    method public boolean isTextEntryKey();
     method public boolean isVisibleToUser();
     method public static androidx.core.view.accessibility.AccessibilityNodeInfoCompat! obtain(android.view.View!);
     method public static androidx.core.view.accessibility.AccessibilityNodeInfoCompat! obtain(android.view.View!, int);
@@ -2421,8 +2423,10 @@
     method public void setSource(android.view.View!);
     method public void setSource(android.view.View!, int);
     method public void setText(CharSequence!);
+    method public void setTextEntryKey(boolean);
     method public void setTextSelection(int, int);
     method public void setTooltipText(CharSequence?);
+    method public void setTouchDelegateInfo(androidx.core.view.accessibility.AccessibilityNodeInfoCompat.TouchDelegateInfoCompat);
     method public void setTraversalAfter(android.view.View!);
     method public void setTraversalAfter(android.view.View!, int);
     method public void setTraversalBefore(android.view.View!);
@@ -2494,6 +2498,10 @@
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_MOVE_WINDOW;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_NEXT_AT_MOVEMENT_GRANULARITY;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_NEXT_HTML_ELEMENT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_DOWN;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_LEFT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_RIGHT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_UP;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PASTE;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PREVIOUS_AT_MOVEMENT_GRANULARITY;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PREVIOUS_HTML_ELEMENT;
@@ -2546,6 +2554,13 @@
     field public static final int RANGE_TYPE_PERCENT = 2; // 0x2
   }
 
+  public static final class AccessibilityNodeInfoCompat.TouchDelegateInfoCompat {
+    ctor public AccessibilityNodeInfoCompat.TouchDelegateInfoCompat(java.util.Map<android.graphics.Region,android.view.View>);
+    method public android.graphics.Region? getRegionAt(@IntRange(from=0) int);
+    method @IntRange(from=0) public int getRegionCount();
+    method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat? getTargetForRegion(android.graphics.Region);
+  }
+
   public class AccessibilityNodeProviderCompat {
     ctor public AccessibilityNodeProviderCompat();
     ctor public AccessibilityNodeProviderCompat(Object!);
diff --git a/core/api/1.1.0-alpha05.txt b/core/api/1.1.0-alpha05.txt
index 0ece2e3..5855002 100644
--- a/core/api/1.1.0-alpha05.txt
+++ b/core/api/1.1.0-alpha05.txt
@@ -2338,6 +2338,7 @@
     method public int getTextSelectionEnd();
     method public int getTextSelectionStart();
     method public CharSequence? getTooltipText();
+    method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat.TouchDelegateInfoCompat? getTouchDelegateInfo();
     method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat! getTraversalAfter();
     method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat! getTraversalBefore();
     method public String! getViewIdResourceName();
@@ -2363,6 +2364,7 @@
     method public boolean isScrollable();
     method public boolean isSelected();
     method public boolean isShowingHintText();
+    method public boolean isTextEntryKey();
     method public boolean isVisibleToUser();
     method public static androidx.core.view.accessibility.AccessibilityNodeInfoCompat! obtain(android.view.View!);
     method public static androidx.core.view.accessibility.AccessibilityNodeInfoCompat! obtain(android.view.View!, int);
@@ -2422,8 +2424,10 @@
     method public void setSource(android.view.View!);
     method public void setSource(android.view.View!, int);
     method public void setText(CharSequence!);
+    method public void setTextEntryKey(boolean);
     method public void setTextSelection(int, int);
     method public void setTooltipText(CharSequence?);
+    method public void setTouchDelegateInfo(androidx.core.view.accessibility.AccessibilityNodeInfoCompat.TouchDelegateInfoCompat);
     method public void setTraversalAfter(android.view.View!);
     method public void setTraversalAfter(android.view.View!, int);
     method public void setTraversalBefore(android.view.View!);
@@ -2495,6 +2499,10 @@
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_MOVE_WINDOW;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_NEXT_AT_MOVEMENT_GRANULARITY;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_NEXT_HTML_ELEMENT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_DOWN;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_LEFT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_RIGHT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_UP;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PASTE;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PREVIOUS_AT_MOVEMENT_GRANULARITY;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PREVIOUS_HTML_ELEMENT;
@@ -2547,6 +2555,13 @@
     field public static final int RANGE_TYPE_PERCENT = 2; // 0x2
   }
 
+  public static final class AccessibilityNodeInfoCompat.TouchDelegateInfoCompat {
+    ctor public AccessibilityNodeInfoCompat.TouchDelegateInfoCompat(java.util.Map<android.graphics.Region,android.view.View>);
+    method public android.graphics.Region? getRegionAt(@IntRange(from=0) int);
+    method @IntRange(from=0) public int getRegionCount();
+    method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat? getTargetForRegion(android.graphics.Region);
+  }
+
   public class AccessibilityNodeProviderCompat {
     ctor public AccessibilityNodeProviderCompat();
     ctor public AccessibilityNodeProviderCompat(Object!);
diff --git a/core/api/current.txt b/core/api/current.txt
index 0ece2e3..5855002 100644
--- a/core/api/current.txt
+++ b/core/api/current.txt
@@ -2338,6 +2338,7 @@
     method public int getTextSelectionEnd();
     method public int getTextSelectionStart();
     method public CharSequence? getTooltipText();
+    method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat.TouchDelegateInfoCompat? getTouchDelegateInfo();
     method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat! getTraversalAfter();
     method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat! getTraversalBefore();
     method public String! getViewIdResourceName();
@@ -2363,6 +2364,7 @@
     method public boolean isScrollable();
     method public boolean isSelected();
     method public boolean isShowingHintText();
+    method public boolean isTextEntryKey();
     method public boolean isVisibleToUser();
     method public static androidx.core.view.accessibility.AccessibilityNodeInfoCompat! obtain(android.view.View!);
     method public static androidx.core.view.accessibility.AccessibilityNodeInfoCompat! obtain(android.view.View!, int);
@@ -2422,8 +2424,10 @@
     method public void setSource(android.view.View!);
     method public void setSource(android.view.View!, int);
     method public void setText(CharSequence!);
+    method public void setTextEntryKey(boolean);
     method public void setTextSelection(int, int);
     method public void setTooltipText(CharSequence?);
+    method public void setTouchDelegateInfo(androidx.core.view.accessibility.AccessibilityNodeInfoCompat.TouchDelegateInfoCompat);
     method public void setTraversalAfter(android.view.View!);
     method public void setTraversalAfter(android.view.View!, int);
     method public void setTraversalBefore(android.view.View!);
@@ -2495,6 +2499,10 @@
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_MOVE_WINDOW;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_NEXT_AT_MOVEMENT_GRANULARITY;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_NEXT_HTML_ELEMENT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_DOWN;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_LEFT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_RIGHT;
+    field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat ACTION_PAGE_UP;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PASTE;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PREVIOUS_AT_MOVEMENT_GRANULARITY;
     field public static final androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat! ACTION_PREVIOUS_HTML_ELEMENT;
@@ -2547,6 +2555,13 @@
     field public static final int RANGE_TYPE_PERCENT = 2; // 0x2
   }
 
+  public static final class AccessibilityNodeInfoCompat.TouchDelegateInfoCompat {
+    ctor public AccessibilityNodeInfoCompat.TouchDelegateInfoCompat(java.util.Map<android.graphics.Region,android.view.View>);
+    method public android.graphics.Region? getRegionAt(@IntRange(from=0) int);
+    method @IntRange(from=0) public int getRegionCount();
+    method public androidx.core.view.accessibility.AccessibilityNodeInfoCompat? getTargetForRegion(android.graphics.Region);
+  }
+
   public class AccessibilityNodeProviderCompat {
     ctor public AccessibilityNodeProviderCompat();
     ctor public AccessibilityNodeProviderCompat(Object!);
diff --git a/core/api/restricted_1.1.0-alpha05.txt b/core/api/restricted_1.1.0-alpha05.txt
index 5baf105..87a5dd5 100644
--- a/core/api/restricted_1.1.0-alpha05.txt
+++ b/core/api/restricted_1.1.0-alpha05.txt
@@ -255,6 +255,15 @@
     method public android.graphics.Typeface? createFromResourcesFontFile(android.content.Context!, android.content.res.Resources!, int, String!, int);
   }
 
+  @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP) @RequiresApi(29) public class TypefaceCompatApi29Impl {
+    ctor public TypefaceCompatApi29Impl();
+    method public android.graphics.Typeface? createFromFontFamilyFilesResourceEntry(android.content.Context!, androidx.core.content.res.FontResourcesParserCompat.FontFamilyFilesResourceEntry!, android.content.res.Resources!, int);
+    method public android.graphics.Typeface? createFromFontInfo(android.content.Context!, android.os.CancellationSignal?, androidx.core.provider.FontsContractCompat.FontInfo[], int);
+    method protected android.graphics.Typeface! createFromInputStream(android.content.Context!, java.io.InputStream!);
+    method public android.graphics.Typeface? createFromResourcesFontFile(android.content.Context!, android.content.res.Resources!, int, String!, int);
+    method protected androidx.core.provider.FontsContractCompat.FontInfo! findBestInfo(androidx.core.provider.FontsContractCompat.FontInfo[]!, int);
+  }
+
   @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public class TypefaceCompatUtil {
     method public static void closeQuietly(java.io.Closeable!);
     method @RequiresApi(19) public static java.nio.ByteBuffer? copyToDirectBuffer(android.content.Context!, android.content.res.Resources!, int);
diff --git a/core/api/restricted_current.txt b/core/api/restricted_current.txt
index 5baf105..87a5dd5 100644
--- a/core/api/restricted_current.txt
+++ b/core/api/restricted_current.txt
@@ -255,6 +255,15 @@
     method public android.graphics.Typeface? createFromResourcesFontFile(android.content.Context!, android.content.res.Resources!, int, String!, int);
   }
 
+  @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP) @RequiresApi(29) public class TypefaceCompatApi29Impl {
+    ctor public TypefaceCompatApi29Impl();
+    method public android.graphics.Typeface? createFromFontFamilyFilesResourceEntry(android.content.Context!, androidx.core.content.res.FontResourcesParserCompat.FontFamilyFilesResourceEntry!, android.content.res.Resources!, int);
+    method public android.graphics.Typeface? createFromFontInfo(android.content.Context!, android.os.CancellationSignal?, androidx.core.provider.FontsContractCompat.FontInfo[], int);
+    method protected android.graphics.Typeface! createFromInputStream(android.content.Context!, java.io.InputStream!);
+    method public android.graphics.Typeface? createFromResourcesFontFile(android.content.Context!, android.content.res.Resources!, int, String!, int);
+    method protected androidx.core.provider.FontsContractCompat.FontInfo! findBestInfo(androidx.core.provider.FontsContractCompat.FontInfo[]!, int);
+  }
+
   @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public class TypefaceCompatUtil {
     method public static void closeQuietly(java.io.Closeable!);
     method @RequiresApi(19) public static java.nio.ByteBuffer? copyToDirectBuffer(android.content.Context!, android.content.res.Resources!, int);
diff --git a/core/src/androidTest/java/androidx/core/view/accessibility/AccessibilityNodeInfoCompatTest.java b/core/src/androidTest/java/androidx/core/view/accessibility/AccessibilityNodeInfoCompatTest.java
index 6b7746e..17ca4c0 100644
--- a/core/src/androidTest/java/androidx/core/view/accessibility/AccessibilityNodeInfoCompatTest.java
+++ b/core/src/androidTest/java/androidx/core/view/accessibility/AccessibilityNodeInfoCompatTest.java
@@ -17,13 +17,19 @@
 package androidx.core.view.accessibility;
 
 import static org.hamcrest.CoreMatchers.is;
+import static org.hamcrest.CoreMatchers.nullValue;
 import static org.hamcrest.core.IsEqual.equalTo;
 import static org.junit.Assert.assertThat;
 
+import android.graphics.Region;
 import android.os.Build;
+import android.view.View;
 import android.view.accessibility.AccessibilityNodeInfo;
 
+import androidx.core.os.BuildCompat;
 import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat;
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.TouchDelegateInfoCompat;
+import androidx.test.InstrumentationRegistry;
 import androidx.test.ext.junit.runners.AndroidJUnit4;
 import androidx.test.filters.SdkSuppress;
 import androidx.test.filters.SmallTest;
@@ -32,6 +38,9 @@
 import org.junit.Test;
 import org.junit.runner.RunWith;
 
+import java.util.HashMap;
+import java.util.Map;
+
 @SmallTest
 @RunWith(AndroidJUnit4.class)
 public class AccessibilityNodeInfoCompatTest {
@@ -107,6 +116,16 @@
 
     @SdkSuppress(minSdkVersion = 19)
     @Test
+    public void testGetSetTextEntryKey() {
+        AccessibilityNodeInfoCompat nodeCompat = obtainedWrappedNodeCompat();
+        nodeCompat.setTextEntryKey(true);
+        assertThat(nodeCompat.isTextEntryKey(), is(true));
+        nodeCompat.setTextEntryKey(false);
+        assertThat(nodeCompat.isTextEntryKey(), is(false));
+    }
+
+    @SdkSuppress(minSdkVersion = 19)
+    @Test
     public void testAccessibilityActionsNotNull() {
         try {
             AccessibilityActionCompat actionCompat;
@@ -148,6 +167,30 @@
         }
     }
 
+    @Test
+    public void testTouchDelegateInfo() {
+        final Map<Region, View> targetMap = new HashMap<>(1);
+        final Region region = new Region(1, 1, 10, 10);
+        targetMap.put(region, new View(InstrumentationRegistry.getContext()));
+        final TouchDelegateInfoCompat delegateInfo = new TouchDelegateInfoCompat(targetMap);
+        final AccessibilityNodeInfoCompat accessibilityNodeInfoCompat =
+                obtainedWrappedNodeCompat();
+        accessibilityNodeInfoCompat.setTouchDelegateInfo(delegateInfo);
+        final TouchDelegateInfoCompat touchDelegateInfoResult =
+                accessibilityNodeInfoCompat.getTouchDelegateInfo();
+        if (BuildCompat.isAtLeastQ()) {
+            assertThat(touchDelegateInfoResult.getRegionCount(), is(1));
+            assertThat(touchDelegateInfoResult.getRegionAt(0), is(region));
+            // getTargetForRegion return null, since we are not a11y service
+            assertThat(touchDelegateInfoResult.getTargetForRegion(region), is(nullValue()));
+        } else {
+            assertThat(touchDelegateInfoResult, is(nullValue()));
+            assertThat(delegateInfo.getRegionCount(), is(0));
+            assertThat(delegateInfo.getRegionAt(0), is(nullValue()));
+            assertThat(delegateInfo.getTargetForRegion(region), is(nullValue()));
+        }
+    }
+
     private AccessibilityNodeInfoCompat obtainedWrappedNodeCompat() {
         AccessibilityNodeInfo accessibilityNodeInfo = AccessibilityNodeInfo.obtain();
         return AccessibilityNodeInfoCompat.wrap(accessibilityNodeInfo);
diff --git a/core/src/main/java/androidx/core/graphics/TypefaceCompat.java b/core/src/main/java/androidx/core/graphics/TypefaceCompat.java
index a55a4134..d07da13 100644
--- a/core/src/main/java/androidx/core/graphics/TypefaceCompat.java
+++ b/core/src/main/java/androidx/core/graphics/TypefaceCompat.java
@@ -18,6 +18,7 @@
 
 import static androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX;
 
+import android.annotation.SuppressLint;
 import android.content.Context;
 import android.content.res.Resources;
 import android.graphics.Typeface;
@@ -34,16 +35,20 @@
 import androidx.core.content.res.FontResourcesParserCompat.FontFamilyFilesResourceEntry;
 import androidx.core.content.res.FontResourcesParserCompat.ProviderResourceEntry;
 import androidx.core.content.res.ResourcesCompat;
+import androidx.core.os.BuildCompat;
 import androidx.core.provider.FontsContractCompat;
 import androidx.core.provider.FontsContractCompat.FontInfo;
 
 /**
  * Helper for accessing features in {@link Typeface}.
  */
+@SuppressLint("NewApi")  // TODO: Remove this suppression once Q SDK is released.
 public class TypefaceCompat {
     private static final TypefaceCompatBaseImpl sTypefaceCompatImpl;
     static {
-        if (Build.VERSION.SDK_INT >= 28) {
+        if (BuildCompat.isAtLeastQ()) {
+            sTypefaceCompatImpl = new TypefaceCompatApi29Impl();
+        } else if (Build.VERSION.SDK_INT >= 28) {
             sTypefaceCompatImpl = new TypefaceCompatApi28Impl();
         } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
             sTypefaceCompatImpl = new TypefaceCompatApi26Impl();
diff --git a/core/src/main/java/androidx/core/graphics/TypefaceCompatApi29Impl.java b/core/src/main/java/androidx/core/graphics/TypefaceCompatApi29Impl.java
new file mode 100644
index 0000000..87e003bd
--- /dev/null
+++ b/core/src/main/java/androidx/core/graphics/TypefaceCompatApi29Impl.java
@@ -0,0 +1,159 @@
+/*
+ * Copyright 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package androidx.core.graphics;
+
+import static androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP;
+
+import android.content.ContentResolver;
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.Typeface;
+import android.graphics.fonts.Font;
+import android.graphics.fonts.FontFamily;
+import android.graphics.fonts.FontStyle;
+import android.os.CancellationSignal;
+import android.os.ParcelFileDescriptor;
+
+import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
+import androidx.annotation.RequiresApi;
+import androidx.annotation.RestrictTo;
+import androidx.core.content.res.FontResourcesParserCompat;
+import androidx.core.provider.FontsContractCompat;
+
+import java.io.IOException;
+import java.io.InputStream;
+
+/** @hide */
+@RestrictTo(LIBRARY_GROUP)
+@RequiresApi(29)
+public class TypefaceCompatApi29Impl extends TypefaceCompatBaseImpl {
+    @Override
+    protected FontsContractCompat.FontInfo findBestInfo(FontsContractCompat.FontInfo[] fonts,
+            int style) {
+        throw new RuntimeException("Do not use this function in API 29 or later.");
+    }
+
+    // Caller must close the stream.
+    @Override
+    protected Typeface createFromInputStream(Context context, InputStream is) {
+        throw new RuntimeException("Do not use this function in API 29 or later.");
+    }
+
+    @Nullable
+    @Override
+    public Typeface createFromFontInfo(Context context,
+            @Nullable CancellationSignal cancellationSignal,
+            @NonNull FontsContractCompat.FontInfo[] fonts, int style) {
+        FontFamily.Builder familyBuilder = null;
+        final ContentResolver resolver = context.getContentResolver();
+        for (FontsContractCompat.FontInfo font : fonts) {
+            try (ParcelFileDescriptor pfd = resolver.openFileDescriptor(font.getUri(), "r",
+                    cancellationSignal)) {
+                if (pfd == null) {
+                    continue;  // keep adding succeeded fonts.
+                }
+                final Font platformFont = new Font.Builder(pfd.getFileDescriptor())
+                        .setWeight(font.getWeight())
+                        .setSlant(font.isItalic() ? FontStyle.FONT_SLANT_ITALIC
+                                : FontStyle.FONT_SLANT_UPRIGHT)
+                        .setTtcIndex(font.getTtcIndex())
+                        .build();  // TODO: font variation settings?
+                if (familyBuilder == null) {
+                    familyBuilder = new FontFamily.Builder(platformFont);
+                } else {
+                    familyBuilder.addFont(platformFont);
+                }
+            } catch (IOException e) {
+                // keep adding succeeded fonts.
+            }
+        }
+        if (familyBuilder == null) {
+            return null;  // No font is added. Give up.
+        }
+        final FontStyle defaultStyle = new FontStyle(
+                (style & Typeface.BOLD) != 0 ? FontStyle.FONT_WEIGHT_BOLD
+                        : FontStyle.FONT_WEIGHT_NORMAL,
+                (style & Typeface.ITALIC) != 0 ? FontStyle.FONT_SLANT_ITALIC
+                        : FontStyle.FONT_SLANT_UPRIGHT
+        );
+        return new Typeface.CustomFallbackBuilder(familyBuilder.build())
+                .setStyle(defaultStyle)
+                .build();
+    }
+
+    @Nullable
+    @Override
+    public Typeface createFromFontFamilyFilesResourceEntry(Context context,
+            FontResourcesParserCompat.FontFamilyFilesResourceEntry familyEntry, Resources resources,
+            int style) {
+        FontFamily.Builder familyBuilder = null;
+        for (FontResourcesParserCompat.FontFileResourceEntry entry : familyEntry.getEntries()) {
+            try {
+                final Font platformFont = new Font.Builder(resources, entry.getResourceId())
+                        .setWeight(entry.getWeight())
+                        .setSlant(entry.isItalic() ? FontStyle.FONT_SLANT_ITALIC
+                                : FontStyle.FONT_SLANT_UPRIGHT)
+                        .setTtcIndex(entry.getTtcIndex())
+                        .setFontVariationSettings(entry.getVariationSettings())
+                        .build();
+                if (familyBuilder == null) {
+                    familyBuilder = new FontFamily.Builder(platformFont);
+                } else {
+                    familyBuilder.addFont(platformFont);
+                }
+            } catch (IOException e) {
+                // keep adding succeeded fonts
+            }
+        }
+        if (familyBuilder == null) {
+            return null;  // No font is added. Give up
+        }
+        final FontStyle defaultStyle = new FontStyle(
+                (style & Typeface.BOLD) != 0 ? FontStyle.FONT_WEIGHT_BOLD
+                        : FontStyle.FONT_WEIGHT_NORMAL,
+                (style & Typeface.ITALIC) != 0 ? FontStyle.FONT_SLANT_ITALIC
+                        : FontStyle.FONT_SLANT_UPRIGHT
+        );
+        return new Typeface.CustomFallbackBuilder(familyBuilder.build())
+                .setStyle(defaultStyle)
+                .build();
+    }
+
+    /**
+     * Used by Resources to load a font resource of type font file.
+     */
+    @Nullable
+    @Override
+    public Typeface createFromResourcesFontFile(
+            Context context, Resources resources, int id, String path, int style) {
+        FontFamily family = null;
+        try {
+            family = new FontFamily.Builder(new Font.Builder(resources, id).build()).build();
+        } catch (IOException e) {
+            return null;
+        }
+        final FontStyle defaultStyle = new FontStyle(
+                (style & Typeface.BOLD) != 0 ? FontStyle.FONT_WEIGHT_BOLD
+                        : FontStyle.FONT_WEIGHT_NORMAL,
+                (style & Typeface.ITALIC) != 0 ? FontStyle.FONT_SLANT_ITALIC
+                        : FontStyle.FONT_SLANT_UPRIGHT
+        );
+        return new Typeface.CustomFallbackBuilder(family).setStyle(defaultStyle).build();
+    }
+
+}
diff --git a/core/src/main/java/androidx/core/text/PrecomputedTextCompat.java b/core/src/main/java/androidx/core/text/PrecomputedTextCompat.java
index 66d1a3e..3ab3705 100644
--- a/core/src/main/java/androidx/core/text/PrecomputedTextCompat.java
+++ b/core/src/main/java/androidx/core/text/PrecomputedTextCompat.java
@@ -18,6 +18,7 @@
 
 import static androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX;
 
+import android.annotation.SuppressLint;
 import android.os.Build;
 import android.text.Layout;
 import android.text.PrecomputedText;
@@ -37,6 +38,7 @@
 import androidx.annotation.RequiresApi;
 import androidx.annotation.RestrictTo;
 import androidx.annotation.UiThread;
+import androidx.core.os.BuildCompat;
 import androidx.core.os.TraceCompat;
 import androidx.core.util.ObjectsCompat;
 import androidx.core.util.Preconditions;
@@ -191,9 +193,18 @@
             }
         }
 
+        @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
         Params(@NonNull TextPaint paint, @NonNull TextDirectionHeuristic textDir,
                 int strategy, int frequency) {
-            mWrapped = null;
+            if (BuildCompat.isAtLeastQ()) {
+                mWrapped = new PrecomputedText.Params.Builder(paint)
+                        .setBreakStrategy(strategy)
+                        .setHyphenationFrequency(frequency)
+                        .setTextDirection(textDir)
+                        .build();
+            } else {
+                mWrapped = null;
+            }
             mPaint = paint;
             mTextDir = textDir;
             mBreakStrategy = strategy;
@@ -206,7 +217,7 @@
             mTextDir = wrapped.getTextDirection();
             mBreakStrategy = wrapped.getBreakStrategy();
             mHyphenationFrequency = wrapped.getHyphenationFrequency();
-            mWrapped = null;
+            mWrapped = (BuildCompat.isAtLeastQ()) ? wrapped : null;
         }
 
         /**
@@ -262,11 +273,6 @@
          */
         @RestrictTo(LIBRARY_GROUP_PREFIX)
         public boolean equalsWithoutTextDirection(@NonNull Params other) {
-
-            if (mWrapped != null) {
-                return mWrapped.equals(other.mWrapped);
-            }
-
             if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
                 if (mBreakStrategy != other.getBreakStrategy()) {
                     return false;
@@ -422,6 +428,7 @@
      * @param params parameters that define how text will be precomputed
      * @return A {@link PrecomputedText}
      */
+    @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
     public static PrecomputedTextCompat create(@NonNull CharSequence text, @NonNull Params params) {
         Preconditions.checkNotNull(text);
         Preconditions.checkNotNull(params);
@@ -429,6 +436,11 @@
         try {
             TraceCompat.beginSection("PrecomputedText");
 
+            if (BuildCompat.isAtLeastQ() && params.mWrapped != null) {
+                return new PrecomputedTextCompat(
+                        PrecomputedText.create(text, params.mWrapped), params);
+            }
+
             ArrayList<Integer> ends = new ArrayList<>();
 
             int paraEnd = 0;
@@ -488,7 +500,7 @@
         mText = precomputed;
         mParams = params;
         mParagraphEnds = null;
-        mWrapped = null;
+        mWrapped = (BuildCompat.isAtLeastQ()) ? precomputed : null;
     }
 
     /**
@@ -515,24 +527,39 @@
     /**
      * Returns the count of paragraphs.
      */
+    @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
     public @IntRange(from = 0) int getParagraphCount() {
-        return mParagraphEnds.length;
+        if (BuildCompat.isAtLeastQ()) {
+            return mWrapped.getParagraphCount();
+        } else {
+            return mParagraphEnds.length;
+        }
     }
 
     /**
      * Returns the paragraph start offset of the text.
      */
+    @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
     public @IntRange(from = 0) int getParagraphStart(@IntRange(from = 0) int paraIndex) {
         Preconditions.checkArgumentInRange(paraIndex, 0, getParagraphCount(), "paraIndex");
-        return paraIndex == 0 ? 0 : mParagraphEnds[paraIndex - 1];
+        if (BuildCompat.isAtLeastQ()) {
+            return mWrapped.getParagraphStart(paraIndex);
+        } else {
+            return paraIndex == 0 ? 0 : mParagraphEnds[paraIndex - 1];
+        }
     }
 
     /**
      * Returns the paragraph end offset of the text.
      */
+    @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
     public @IntRange(from = 0) int getParagraphEnd(@IntRange(from = 0) int paraIndex) {
         Preconditions.checkArgumentInRange(paraIndex, 0, getParagraphCount(), "paraIndex");
-        return mParagraphEnds[paraIndex];
+        if (BuildCompat.isAtLeastQ()) {
+            return mWrapped.getParagraphEnd(paraIndex);
+        } else {
+            return mParagraphEnds[paraIndex];
+        }
     }
 
     /**
@@ -646,25 +673,35 @@
     /**
      * @throws IllegalArgumentException if {@link MetricAffectingSpan} is specified.
      */
+    @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
     @Override
     public void setSpan(Object what, int start, int end, int flags) {
         if (what instanceof MetricAffectingSpan) {
             throw new IllegalArgumentException(
                     "MetricAffectingSpan can not be set to PrecomputedText.");
         }
-        mText.setSpan(what, start, end, flags);
+        if (BuildCompat.isAtLeastQ()) {
+            mWrapped.setSpan(what, start, end, flags);
+        } else {
+            mText.setSpan(what, start, end, flags);
+        }
     }
 
     /**
      * @throws IllegalArgumentException if {@link MetricAffectingSpan} is specified.
      */
+    @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
     @Override
     public void removeSpan(Object what) {
         if (what instanceof MetricAffectingSpan) {
             throw new IllegalArgumentException(
                     "MetricAffectingSpan can not be removed from PrecomputedText.");
         }
-        mText.removeSpan(what);
+        if (BuildCompat.isAtLeastQ()) {
+            mWrapped.removeSpan(what);
+        } else {
+            mText.removeSpan(what);
+        }
     }
 
     ///////////////////////////////////////////////////////////////////////////////////////////////
@@ -672,9 +709,15 @@
     //
     // Just proxy for underlying mText if appropriate.
 
+    @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
     @Override
     public <T> T[] getSpans(int start, int end, Class<T> type) {
-        return mText.getSpans(start, end, type);
+        if (BuildCompat.isAtLeastQ()) {
+            return mWrapped.getSpans(start, end, type);
+        } else {
+            return mText.getSpans(start, end, type);
+        }
+
     }
 
     @Override
diff --git a/core/src/main/java/androidx/core/view/ViewCompat.java b/core/src/main/java/androidx/core/view/ViewCompat.java
index f5925bd..b6ab58b 100644
--- a/core/src/main/java/androidx/core/view/ViewCompat.java
+++ b/core/src/main/java/androidx/core/view/ViewCompat.java
@@ -60,6 +60,7 @@
 import androidx.annotation.UiThread;
 import androidx.collection.ArrayMap;
 import androidx.core.R;
+import androidx.core.os.BuildCompat;
 import androidx.core.view.AccessibilityDelegateCompat.AccessibilityDelegateAdapter;
 import androidx.core.view.accessibility.AccessibilityNodeInfoCompat;
 import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat;
@@ -906,6 +907,15 @@
 
     private static @Nullable View.AccessibilityDelegate
             getAccessibilityDelegateInternal(@NonNull View v) {
+        if (BuildCompat.isAtLeastQ()) {
+            return v.getAccessibilityDelegate();
+        } else {
+            return getAccessibilityDelegateThroughReflection(v);
+        }
+    }
+
+    private static @Nullable View.AccessibilityDelegate getAccessibilityDelegateThroughReflection(
+            @NonNull View v) {
         if (sAccessibilityDelegateCheckFailed) {
             return null; // View implementation might have changed.
         }
diff --git a/core/src/main/java/androidx/core/view/ViewPropertyAnimatorCompat.java b/core/src/main/java/androidx/core/view/ViewPropertyAnimatorCompat.java
index 8963c2b..b645fb59 100644
--- a/core/src/main/java/androidx/core/view/ViewPropertyAnimatorCompat.java
+++ b/core/src/main/java/androidx/core/view/ViewPropertyAnimatorCompat.java
@@ -18,6 +18,7 @@
 import android.animation.Animator;
 import android.animation.AnimatorListenerAdapter;
 import android.animation.ValueAnimator;
+import android.annotation.SuppressLint;
 import android.os.Build;
 import android.view.View;
 import android.view.animation.Interpolator;
@@ -69,6 +70,7 @@
         }
 
         @Override
+        @SuppressLint("WrongConstant")
         public void onAnimationEnd(View view) {
             if (mVpa.mOldLayerType > -1) {
                 view.setLayerType(mVpa.mOldLayerType, null);
@@ -672,6 +674,7 @@
      * @see View#setLayerType(int, android.graphics.Paint)
      * @return This object, allowing calls to methods in this class to be chained.
      */
+    @SuppressLint("WrongConstant")
     public ViewPropertyAnimatorCompat withLayer() {
         View view;
         if ((view = mView.get()) != null) {
diff --git a/core/src/main/java/androidx/core/view/accessibility/AccessibilityNodeInfoCompat.java b/core/src/main/java/androidx/core/view/accessibility/AccessibilityNodeInfoCompat.java
index 2f784ae..7d9d140 100644
--- a/core/src/main/java/androidx/core/view/accessibility/AccessibilityNodeInfoCompat.java
+++ b/core/src/main/java/androidx/core/view/accessibility/AccessibilityNodeInfoCompat.java
@@ -19,6 +19,7 @@
 import static androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX;
 
 import android.graphics.Rect;
+import android.graphics.Region;
 import android.os.Build;
 import android.os.Bundle;
 import android.text.InputType;
@@ -31,12 +32,15 @@
 import android.util.SparseArray;
 import android.view.View;
 import android.view.accessibility.AccessibilityNodeInfo;
+import android.view.accessibility.AccessibilityNodeInfo.TouchDelegateInfo;
 
+import androidx.annotation.IntRange;
 import androidx.annotation.NonNull;
 import androidx.annotation.Nullable;
 import androidx.annotation.RestrictTo;
 import androidx.core.R;
 import androidx.core.accessibilityservice.AccessibilityServiceInfoCompat;
+import androidx.core.os.BuildCompat;
 import androidx.core.view.ViewCompat;
 import androidx.core.view.accessibility.AccessibilityViewCommand.CommandArguments;
 import androidx.core.view.accessibility.AccessibilityViewCommand.MoveAtGranularityArguments;
@@ -51,6 +55,7 @@
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.List;
+import java.util.Map;
 
 /**
  * Helper for accessing {@link android.view.accessibility.AccessibilityNodeInfo} in a backwards
@@ -449,6 +454,42 @@
                         android.R.id.accessibilityActionScrollRight, null, null, null);
 
         /**
+         * Action to move to the page above.
+         */
+        @NonNull
+        public static final AccessibilityActionCompat ACTION_PAGE_UP =
+                new AccessibilityActionCompat(Build.VERSION.SDK_INT >= 29
+                        ?  AccessibilityNodeInfo.AccessibilityAction.ACTION_PAGE_UP : null,
+                        android.R.id.accessibilityActionPageUp, null, null, null);
+
+        /**
+         * Action to move to the page below.
+         */
+        @NonNull
+        public static final AccessibilityActionCompat ACTION_PAGE_DOWN =
+                new AccessibilityActionCompat(Build.VERSION.SDK_INT >= 29
+                        ?  AccessibilityNodeInfo.AccessibilityAction.ACTION_PAGE_DOWN : null,
+                        android.R.id.accessibilityActionPageDown, null, null, null);
+
+        /**
+         * Action to move to the page left.
+         */
+        @NonNull
+        public static final AccessibilityActionCompat ACTION_PAGE_LEFT =
+                new AccessibilityActionCompat(Build.VERSION.SDK_INT >= 29
+                        ?  AccessibilityNodeInfo.AccessibilityAction.ACTION_PAGE_LEFT : null,
+                        android.R.id.accessibilityActionPageLeft, null, null, null);
+
+        /**
+         * Action to move to the page right.
+         */
+        @NonNull
+        public static final AccessibilityActionCompat ACTION_PAGE_RIGHT =
+                new AccessibilityActionCompat(Build.VERSION.SDK_INT >= 29
+                        ?  AccessibilityNodeInfo.AccessibilityAction.ACTION_PAGE_RIGHT : null,
+                        android.R.id.accessibilityActionPageRight, null, null, null);
+
+        /**
          * Action that context clicks the node.
          */
         public static final AccessibilityActionCompat ACTION_CONTEXT_CLICK =
@@ -997,6 +1038,97 @@
         }
     }
 
+    /**
+     * Class with information of touch delegated views and regions.
+     */
+    public static final class TouchDelegateInfoCompat {
+        final TouchDelegateInfo mInfo;
+
+        /**
+         * Create a new instance of {@link TouchDelegateInfoCompat}.
+         *
+         * @param targetMap A map from regions (in view coordinates) to delegated views.
+         */
+        public TouchDelegateInfoCompat(@NonNull Map<Region, View> targetMap) {
+            if (BuildCompat.isAtLeastQ()) {
+                mInfo = new TouchDelegateInfo(targetMap);
+            } else {
+                mInfo = null;
+            }
+        }
+
+        TouchDelegateInfoCompat(@NonNull TouchDelegateInfo info) {
+            mInfo = info;
+        }
+
+        /**
+         * Returns the number of touch delegate target region.
+         * <p>
+         * Compatibility:
+         * <ul>
+         *     <li>API &lt; 29: Always returns {@code 0}</li>
+         * </ul>
+         *
+         * @return Number of touch delegate target region.
+         */
+        public @IntRange(from = 0) int getRegionCount() {
+            if (BuildCompat.isAtLeastQ()) {
+                return mInfo.getRegionCount();
+            }
+            return 0;
+        }
+
+        /**
+         * Return the {@link Region} at the given index.
+         * <p>
+         * Compatibility:
+         * <ul>
+         *     <li>API &lt; 29: Always returns {@code null}</li>
+         * </ul>
+         *
+         * @param index The desired index, must be between 0 and {@link #getRegionCount()}-1.
+         * @return Returns the {@link Region} stored at the given index.
+         */
+        @Nullable
+        public Region getRegionAt(@IntRange(from = 0) int index) {
+            if (BuildCompat.isAtLeastQ()) {
+                return mInfo.getRegionAt(index);
+            }
+            return null;
+        }
+
+        /**
+         * Return the target {@link AccessibilityNodeInfoCompat} for the given {@link Region}.
+         * <p>
+         *   <strong>Note:</strong> This api can only be called from
+         *   {@link android.accessibilityservice.AccessibilityService}.
+         * </p>
+         * <p>
+         *   <strong>Note:</strong> It is a client responsibility to recycle the
+         *     received info by calling {@link AccessibilityNodeInfo#recycle()}
+         *     to avoid creating of multiple instances.
+         * </p>
+         * <p>
+         * Compatibility:
+         * <ul>
+         *     <li>API &lt; 29: Always returns {@code null}</li>
+         * </ul>
+         *
+         * @param region The region retrieved from {@link #getRegionAt(int)}.
+         * @return The target node associates with the given region.
+         */
+        @Nullable
+        public AccessibilityNodeInfoCompat getTargetForRegion(@NonNull Region region) {
+            if (BuildCompat.isAtLeastQ()) {
+                AccessibilityNodeInfo info = mInfo.getTargetForRegion(region);
+                if (info != null) {
+                    return AccessibilityNodeInfoCompat.wrap(info);
+                }
+            }
+            return null;
+        }
+    }
+
     private static final String ROLE_DESCRIPTION_KEY =
             "AccessibilityNodeInfo.roleDescription";
 
@@ -1032,6 +1164,7 @@
     private static final int BOOLEAN_PROPERTY_SCREEN_READER_FOCUSABLE = 0x00000001;
     private static final int BOOLEAN_PROPERTY_IS_HEADING = 0x00000002;
     private static final int BOOLEAN_PROPERTY_IS_SHOWING_HINT = 0x00000004;
+    private static final int BOOLEAN_PROPERTY_IS_TEXT_ENTRY_KEY = 0x00000008;
 
     private final AccessibilityNodeInfo mInfo;
 
@@ -3673,6 +3806,37 @@
     }
 
     /**
+     * Returns whether node represents a text entry key that is part of a keyboard or keypad.
+     *
+     * @return {@code true} if the node is a text entry key, {@code false} otherwise.
+     */
+    public boolean isTextEntryKey() {
+        if (BuildCompat.isAtLeastQ()) {
+            return mInfo.isTextEntryKey();
+        }
+        return getBooleanProperty(BOOLEAN_PROPERTY_IS_TEXT_ENTRY_KEY);
+    }
+
+    /**
+     * Sets whether the node represents a text entry key that is part of a keyboard or keypad.
+     * <p>This method has no effect below API 19</p>
+     * <p>
+     *   <strong>Note:</strong> Cannot be called from an
+     *   {@link android.accessibilityservice.AccessibilityService}.
+     *   This class is made immutable before being delivered to an AccessibilityService.
+     * </p>
+     *
+     * @param isTextEntryKey {@code true} if the node is a text entry key, {@code false} otherwise.
+     */
+    public void setTextEntryKey(boolean isTextEntryKey) {
+        if (BuildCompat.isAtLeastQ()) {
+            mInfo.setTextEntryKey(isTextEntryKey);
+        } else {
+            setBooleanProperty(BOOLEAN_PROPERTY_IS_TEXT_ENTRY_KEY, isTextEntryKey);
+        }
+    }
+
+    /**
      * Refreshes this info with the latest state of the view it represents.
      * <p>
      * <strong>Note:</strong> If this method returns false this info is obsolete
@@ -3731,6 +3895,55 @@
         }
     }
 
+    /**
+     * Get the {@link TouchDelegateInfoCompat} for touch delegate behavior with the represented
+     * view. It is possible for the same node to be pointed to by several regions. Use
+     * {@link TouchDelegateInfoCompat#getRegionAt(int)} to get touch delegate target
+     * {@link Region}, and {@link TouchDelegateInfoCompat#getTargetForRegion(Region)}
+     * for {@link AccessibilityNodeInfoCompat} from the given region.
+     * <p>
+     * Compatibility:
+     * <ul>
+     *     <li>API &lt; 29: Always returns {@code null}</li>
+     * </ul>
+     *
+     * @return {@link TouchDelegateInfoCompat} or {@code null} if there are no touch delegates
+     * in this node.
+     */
+    @Nullable
+    public TouchDelegateInfoCompat getTouchDelegateInfo() {
+        if (BuildCompat.isAtLeastQ()) {
+            TouchDelegateInfo delegateInfo = mInfo.getTouchDelegateInfo();
+            if (delegateInfo != null) {
+                return new TouchDelegateInfoCompat(delegateInfo);
+            }
+        }
+        return null;
+    }
+
+    /**
+     * Set touch delegate info if the represented view has a {@link android.view.TouchDelegate}.
+     * <p>
+     *   <strong>Note:</strong> Cannot be called from an
+     *   {@link android.accessibilityservice.AccessibilityService}.
+     *   This class is made immutable before being delivered to an
+     *   AccessibilityService.
+     * </p>
+     * <p>
+     * Compatibility:
+     * <ul>
+     *     <li>API &lt; 29: No-op</li>
+     * </ul>
+     *
+     * @param delegatedInfo {@link TouchDelegateInfoCompat}
+     * @throws IllegalStateException If called from an AccessibilityService.
+     */
+    public void setTouchDelegateInfo(@NonNull TouchDelegateInfoCompat delegatedInfo) {
+        if (BuildCompat.isAtLeastQ()) {
+            mInfo.setTouchDelegateInfo(delegatedInfo.mInfo);
+        }
+    }
+
     @Override
     public int hashCode() {
         return (mInfo == null) ? 0 : mInfo.hashCode();
diff --git a/core/src/main/java/androidx/core/widget/TextViewCompat.java b/core/src/main/java/androidx/core/widget/TextViewCompat.java
index 9597110..bf5da4e 100644
--- a/core/src/main/java/androidx/core/widget/TextViewCompat.java
+++ b/core/src/main/java/androidx/core/widget/TextViewCompat.java
@@ -26,6 +26,7 @@
 
 import static androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX;
 
+import android.annotation.SuppressLint;
 import android.app.Activity;
 import android.content.Context;
 import android.content.Intent;
@@ -60,6 +61,7 @@
 import androidx.annotation.RequiresApi;
 import androidx.annotation.RestrictTo;
 import androidx.annotation.StyleRes;
+import androidx.core.os.BuildCompat;
 import androidx.core.text.PrecomputedTextCompat;
 import androidx.core.util.Preconditions;
 
@@ -878,14 +880,21 @@
      * @param precomputed the precomputed text
      * @throws IllegalArgumentException if precomputed text is not compatible with textView.
      */
+    @SuppressLint("NewApi")  // TODO: Remove once Q SDK is released
     public static void setPrecomputedText(@NonNull TextView textView,
                                           @NonNull PrecomputedTextCompat precomputed) {
 
-        PrecomputedTextCompat.Params param = TextViewCompat.getTextMetricsParams(textView);
-        if (!param.equalsWithoutTextDirection(precomputed.getParams())) {
-            throw new IllegalArgumentException("Given text can not be applied to TextView.");
+        if (BuildCompat.isAtLeastQ()) {
+            // Framework can not understand PrecomptedTextCompat. Pass underlying PrecomputedText.
+            // Parameter check is also done by framework.
+            textView.setText(precomputed.getPrecomputedText());
+        } else {
+            PrecomputedTextCompat.Params param = TextViewCompat.getTextMetricsParams(textView);
+            if (!param.equalsWithoutTextDirection(precomputed.getParams())) {
+                throw new IllegalArgumentException("Given text can not be applied to TextView.");
+            }
+            textView.setText(precomputed);
         }
-        textView.setText(precomputed);
     }
 
     /**
diff --git a/development/studio/idea.properties b/development/studio/idea.properties
index 47930b3..91a1949 100644
--- a/development/studio/idea.properties
+++ b/development/studio/idea.properties
@@ -5,12 +5,12 @@
 #---------------------------------------------------------------------
 # Uncomment this option if you want to customize path to IDE config folder. Make sure you're using forward slashes.
 #---------------------------------------------------------------------
-idea.config.path=${user.home}/.AndroidStudioAndroidX/config
+idea.config.path=${user.home}/.AndroidStudioAndroidXPlatform/config
 
 #---------------------------------------------------------------------
 # Uncomment this option if you want to customize path to IDE system folder. Make sure you're using forward slashes.
 #---------------------------------------------------------------------
-idea.system.path=${user.home}/.AndroidStudioAndroidX/system
+idea.system.path=${user.home}/.AndroidStudioAndroidXPlatform/system
 
 #---------------------------------------------------------------------
 # Uncomment this option if you want to customize path to user installed plugins folder. Make sure you're using forward slashes.
diff --git a/documentfile/src/main/java/androidx/documentfile/provider/DocumentFile.java b/documentfile/src/main/java/androidx/documentfile/provider/DocumentFile.java
index 1ad8df4..130cb5b 100644
--- a/documentfile/src/main/java/androidx/documentfile/provider/DocumentFile.java
+++ b/documentfile/src/main/java/androidx/documentfile/provider/DocumentFile.java
@@ -16,7 +16,6 @@
 
 package androidx.documentfile.provider;
 
-import android.content.ContentResolver;
 import android.content.Context;
 import android.content.Intent;
 import android.net.Uri;
diff --git a/documentfile/src/main/java/androidx/documentfile/provider/SingleDocumentFile.java b/documentfile/src/main/java/androidx/documentfile/provider/SingleDocumentFile.java
index 7cd4b8c..94545cd 100644
--- a/documentfile/src/main/java/androidx/documentfile/provider/SingleDocumentFile.java
+++ b/documentfile/src/main/java/androidx/documentfile/provider/SingleDocumentFile.java
@@ -97,6 +97,7 @@
     }
 
     @Override
+    @SuppressWarnings("deprecation")
     public boolean delete() {
         try {
             return DocumentsContract.deleteDocument(mContext.getContentResolver(), mUri);
diff --git a/documentfile/src/main/java/androidx/documentfile/provider/TreeDocumentFile.java b/documentfile/src/main/java/androidx/documentfile/provider/TreeDocumentFile.java
index 9cc20d6..65017b7 100644
--- a/documentfile/src/main/java/androidx/documentfile/provider/TreeDocumentFile.java
+++ b/documentfile/src/main/java/androidx/documentfile/provider/TreeDocumentFile.java
@@ -47,6 +47,7 @@
     }
 
     @Nullable
+    @SuppressWarnings("deprecation")
     private static Uri createFile(Context context, Uri self, String mimeType,
             String displayName) {
         try {
@@ -118,6 +119,7 @@
     }
 
     @Override
+    @SuppressWarnings("deprecation")
     public boolean delete() {
         try {
             return DocumentsContract.deleteDocument(mContext.getContentResolver(), mUri);
@@ -174,6 +176,7 @@
     }
 
     @Override
+    @SuppressWarnings("deprecation")
     public boolean renameTo(String displayName) {
         try {
             final Uri result = DocumentsContract.renameDocument(
diff --git a/drawerlayout/src/main/java/androidx/drawerlayout/widget/DrawerLayout.java b/drawerlayout/src/main/java/androidx/drawerlayout/widget/DrawerLayout.java
index 7bbaf62..bbd6ec03 100644
--- a/drawerlayout/src/main/java/androidx/drawerlayout/widget/DrawerLayout.java
+++ b/drawerlayout/src/main/java/androidx/drawerlayout/widget/DrawerLayout.java
@@ -1027,6 +1027,8 @@
     }
 
     @SuppressLint("WrongConstant")
+    // Remove deprecation suppression once b/120984242 is resolved.
+    @SuppressWarnings("deprecation")
     @Override
     protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
         int widthMode = MeasureSpec.getMode(widthMeasureSpec);
@@ -1313,6 +1315,8 @@
         }
     }
 
+    // Remove deprecation suppression once b/120984242 is resolved.
+    @SuppressWarnings("deprecation")
     private static boolean hasOpaqueBackground(View v) {
         final Drawable bg = v.getBackground();
         if (bg != null) {
diff --git a/fakeannotations/build.gradle b/fakeannotations/build.gradle
new file mode 100644
index 0000000..3302c21
--- /dev/null
+++ b/fakeannotations/build.gradle
@@ -0,0 +1,24 @@
+/*
+ * Copyright 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+apply plugin: 'java-library'
+
+dependencies {
+    implementation fileTree(dir: 'libs', include: ['*.jar'])
+}
+
+sourceCompatibility = "7"
+targetCompatibility = "7"
diff --git a/fakeannotations/src/main/java/androidx/annotation/RecentlyNonNull.java b/fakeannotations/src/main/java/androidx/annotation/RecentlyNonNull.java
new file mode 100644
index 0000000..194aab1
--- /dev/null
+++ b/fakeannotations/src/main/java/androidx/annotation/RecentlyNonNull.java
@@ -0,0 +1,32 @@
+/*
+ * Copyright 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package androidx.annotation;
+
+import static java.lang.annotation.ElementType.ANNOTATION_TYPE;
+import static java.lang.annotation.ElementType.FIELD;
+import static java.lang.annotation.ElementType.LOCAL_VARIABLE;
+import static java.lang.annotation.ElementType.METHOD;
+import static java.lang.annotation.ElementType.PACKAGE;
+import static java.lang.annotation.ElementType.PARAMETER;
+import static java.lang.annotation.RetentionPolicy.CLASS;
+
+import java.lang.annotation.Retention;
+import java.lang.annotation.Target;
+
+@Retention(CLASS)
+@Target({METHOD, PARAMETER, FIELD, LOCAL_VARIABLE, ANNOTATION_TYPE, PACKAGE})
+public @interface RecentlyNonNull {
+}
diff --git a/fakeannotations/src/main/java/androidx/annotation/RecentlyNullable.java b/fakeannotations/src/main/java/androidx/annotation/RecentlyNullable.java
new file mode 100644
index 0000000..4ccdf93
--- /dev/null
+++ b/fakeannotations/src/main/java/androidx/annotation/RecentlyNullable.java
@@ -0,0 +1,32 @@
+/*
+ * Copyright 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package androidx.annotation;
+
+import static java.lang.annotation.ElementType.ANNOTATION_TYPE;
+import static java.lang.annotation.ElementType.FIELD;
+import static java.lang.annotation.ElementType.LOCAL_VARIABLE;
+import static java.lang.annotation.ElementType.METHOD;
+import static java.lang.annotation.ElementType.PACKAGE;
+import static java.lang.annotation.ElementType.PARAMETER;
+import static java.lang.annotation.RetentionPolicy.CLASS;
+
+import java.lang.annotation.Retention;
+import java.lang.annotation.Target;
+
+@Retention(CLASS)
+@Target({METHOD, PARAMETER, FIELD, LOCAL_VARIABLE, ANNOTATION_TYPE, PACKAGE})
+public @interface RecentlyNullable {
+}
diff --git a/fragment/api/1.1.0-alpha03.txt b/fragment/api/1.1.0-alpha03.txt
index 8b5c94f..239fc9e3 100644
--- a/fragment/api/1.1.0-alpha03.txt
+++ b/fragment/api/1.1.0-alpha03.txt
@@ -163,6 +163,7 @@
     method @CallSuper public void onMultiWindowModeChanged(boolean);
     method @CallSuper public void onPictureInPictureModeChanged(boolean);
     method protected void onResumeFragments();
+    method public void onStateNotSaved();
     method public void setEnterSharedElementCallback(androidx.core.app.SharedElementCallback?);
     method public void setExitSharedElementCallback(androidx.core.app.SharedElementCallback?);
     method public void startActivityFromFragment(androidx.fragment.app.Fragment, android.content.Intent!, int);
diff --git a/fragment/api/1.1.0-alpha04.txt b/fragment/api/1.1.0-alpha04.txt
index 0883047..58f4d6e 100644
--- a/fragment/api/1.1.0-alpha04.txt
+++ b/fragment/api/1.1.0-alpha04.txt
@@ -164,6 +164,7 @@
     method @CallSuper public void onMultiWindowModeChanged(boolean);
     method @CallSuper public void onPictureInPictureModeChanged(boolean);
     method protected void onResumeFragments();
+    method public void onStateNotSaved();
     method public void setEnterSharedElementCallback(androidx.core.app.SharedElementCallback?);
     method public void setExitSharedElementCallback(androidx.core.app.SharedElementCallback?);
     method public void startActivityFromFragment(androidx.fragment.app.Fragment, android.content.Intent!, int);
diff --git a/fragment/api/1.1.0-alpha05.txt b/fragment/api/1.1.0-alpha05.txt
index e586a2f..47ba5f4 100644
--- a/fragment/api/1.1.0-alpha05.txt
+++ b/fragment/api/1.1.0-alpha05.txt
@@ -164,6 +164,7 @@
     method @CallSuper public void onMultiWindowModeChanged(boolean);
     method @CallSuper public void onPictureInPictureModeChanged(boolean);
     method protected void onResumeFragments();
+    method public void onStateNotSaved();
     method public void setEnterSharedElementCallback(androidx.core.app.SharedElementCallback?);
     method public void setExitSharedElementCallback(androidx.core.app.SharedElementCallback?);
     method public void startActivityFromFragment(androidx.fragment.app.Fragment, android.content.Intent!, int);
diff --git a/fragment/api/current.txt b/fragment/api/current.txt
index e586a2f..47ba5f4 100644
--- a/fragment/api/current.txt
+++ b/fragment/api/current.txt
@@ -164,6 +164,7 @@
     method @CallSuper public void onMultiWindowModeChanged(boolean);
     method @CallSuper public void onPictureInPictureModeChanged(boolean);
     method protected void onResumeFragments();
+    method public void onStateNotSaved();
     method public void setEnterSharedElementCallback(androidx.core.app.SharedElementCallback?);
     method public void setExitSharedElementCallback(androidx.core.app.SharedElementCallback?);
     method public void startActivityFromFragment(androidx.fragment.app.Fragment, android.content.Intent!, int);
diff --git a/gradle.properties b/gradle.properties
index c788833..5d0e134 100644
--- a/gradle.properties
+++ b/gradle.properties
@@ -1,4 +1,4 @@
-org.gradle.jvmargs=-Xmx8g
+org.gradle.jvmargs=-Xmx8g -XX:MaxPermSize=8g
 org.gradle.daemon=true
 org.gradle.configureondemand=true
 org.gradle.parallel=true
diff --git a/graphics/drawable/animated/api/1.1.0-alpha01.txt b/graphics/drawable/animated/api/1.1.0-alpha01.txt
index 7542e29..70c9c23 100644
--- a/graphics/drawable/animated/api/1.1.0-alpha01.txt
+++ b/graphics/drawable/animated/api/1.1.0-alpha01.txt
@@ -25,6 +25,7 @@
     method public static void registerAnimationCallback(android.graphics.drawable.Drawable!, androidx.vectordrawable.graphics.drawable.Animatable2Compat.AnimationCallback!);
     method public void setAlpha(int);
     method public void setColorFilter(android.graphics.ColorFilter!);
+    method public void setColorFilter(int, android.graphics.PorterDuff.Mode!);
     method public void start();
     method public void stop();
     method public boolean unregisterAnimationCallback(androidx.vectordrawable.graphics.drawable.Animatable2Compat.AnimationCallback);
diff --git a/graphics/drawable/animated/api/1.1.0-alpha02.txt b/graphics/drawable/animated/api/1.1.0-alpha02.txt
index 7542e29..70c9c23 100644
--- a/graphics/drawable/animated/api/1.1.0-alpha02.txt
+++ b/graphics/drawable/animated/api/1.1.0-alpha02.txt
@@ -25,6 +25,7 @@
     method public static void registerAnimationCallback(android.graphics.drawable.Drawable!, androidx.vectordrawable.graphics.drawable.Animatable2Compat.AnimationCallback!);
     method public void setAlpha(int);
     method public void setColorFilter(android.graphics.ColorFilter!);
+    method public void setColorFilter(int, android.graphics.PorterDuff.Mode!);
     method public void start();
     method public void stop();
     method public boolean unregisterAnimationCallback(androidx.vectordrawable.graphics.drawable.Animatable2Compat.AnimationCallback);
diff --git a/graphics/drawable/animated/api/current.txt b/graphics/drawable/animated/api/current.txt
index 7542e29..70c9c23 100644
--- a/graphics/drawable/animated/api/current.txt
+++ b/graphics/drawable/animated/api/current.txt
@@ -25,6 +25,7 @@
     method public static void registerAnimationCallback(android.graphics.drawable.Drawable!, androidx.vectordrawable.graphics.drawable.Animatable2Compat.AnimationCallback!);
     method public void setAlpha(int);
     method public void setColorFilter(android.graphics.ColorFilter!);
+    method public void setColorFilter(int, android.graphics.PorterDuff.Mode!);
     method public void start();
     method public void stop();
     method public boolean unregisterAnimationCallback(androidx.vectordrawable.graphics.drawable.Animatable2Compat.AnimationCallback);
diff --git a/graphics/drawable/animated/src/main/java/androidx/vectordrawable/graphics/drawable/AnimatedVectorDrawableCompat.java b/graphics/drawable/animated/src/main/java/androidx/vectordrawable/graphics/drawable/AnimatedVectorDrawableCompat.java
index b0c84bd..7dd9e1d 100644
--- a/graphics/drawable/animated/src/main/java/androidx/vectordrawable/graphics/drawable/AnimatedVectorDrawableCompat.java
+++ b/graphics/drawable/animated/src/main/java/androidx/vectordrawable/graphics/drawable/AnimatedVectorDrawableCompat.java
@@ -397,6 +397,8 @@
         return mAnimatedVectorState.mVectorDrawable.isStateful();
     }
 
+    // Remove deprecation suppression once b/120984759 is resolved
+    @SuppressWarnings("deprecation")
     @Override
     public int getOpacity() {
         if (mDelegateDrawable != null) {
diff --git a/graphics/drawable/static/api/1.1.0-alpha01.txt b/graphics/drawable/static/api/1.1.0-alpha01.txt
index 3fda85b..34cf297 100644
--- a/graphics/drawable/static/api/1.1.0-alpha01.txt
+++ b/graphics/drawable/static/api/1.1.0-alpha01.txt
@@ -8,6 +8,7 @@
     method public int getOpacity();
     method public void setAlpha(int);
     method public void setColorFilter(android.graphics.ColorFilter!);
+    method public void setColorFilter(int, android.graphics.PorterDuff.Mode!);
   }
 
 }
diff --git a/graphics/drawable/static/api/1.1.0-alpha02.txt b/graphics/drawable/static/api/1.1.0-alpha02.txt
index 3fda85b..34cf297 100644
--- a/graphics/drawable/static/api/1.1.0-alpha02.txt
+++ b/graphics/drawable/static/api/1.1.0-alpha02.txt
@@ -8,6 +8,7 @@
     method public int getOpacity();
     method public void setAlpha(int);
     method public void setColorFilter(android.graphics.ColorFilter!);
+    method public void setColorFilter(int, android.graphics.PorterDuff.Mode!);
   }
 
 }
diff --git a/graphics/drawable/static/api/current.txt b/graphics/drawable/static/api/current.txt
index 3fda85b..34cf297 100644
--- a/graphics/drawable/static/api/current.txt
+++ b/graphics/drawable/static/api/current.txt
@@ -8,6 +8,7 @@
     method public int getOpacity();
     method public void setAlpha(int);
     method public void setColorFilter(android.graphics.ColorFilter!);
+    method public void setColorFilter(int, android.graphics.PorterDuff.Mode!);
   }
 
 }
diff --git a/leanback-preference/api/1.1.0-alpha01.txt b/leanback-preference/api/1.1.0-alpha01.txt
index 79e53fb..2ff4b27 100644
--- a/leanback-preference/api/1.1.0-alpha01.txt
+++ b/leanback-preference/api/1.1.0-alpha01.txt
@@ -21,6 +21,8 @@
     method @Deprecated public static androidx.leanback.preference.LeanbackListPreferenceDialogFragment! newInstanceMulti(String!);
     method @Deprecated public static androidx.leanback.preference.LeanbackListPreferenceDialogFragment! newInstanceSingle(String!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView.Adapter! onCreateAdapter();
+    method @Deprecated public android.view.View? onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
   }
 
   @Deprecated public class LeanbackListPreferenceDialogFragment.AdapterMulti extends androidx.recyclerview.widget.RecyclerView.Adapter<androidx.leanback.preference.LeanbackListPreferenceDialogFragment.ViewHolder> implements androidx.leanback.preference.LeanbackListPreferenceDialogFragment.ViewHolder.OnItemClickListener {
@@ -67,6 +69,7 @@
   @Deprecated public class LeanbackPreferenceDialogFragment extends android.app.Fragment {
     ctor @Deprecated public LeanbackPreferenceDialogFragment();
     method @Deprecated public androidx.preference.DialogPreference! getPreference();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     field @Deprecated public static final String ARG_KEY = "key";
   }
 
@@ -88,8 +91,12 @@
 
   @Deprecated public abstract class LeanbackSettingsFragment extends android.app.Fragment implements androidx.preference.PreferenceFragment.OnPreferenceDisplayDialogCallback androidx.preference.PreferenceFragment.OnPreferenceStartFragmentCallback androidx.preference.PreferenceFragment.OnPreferenceStartScreenCallback {
     ctor @Deprecated public LeanbackSettingsFragment();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onPause();
     method @Deprecated public boolean onPreferenceDisplayDialog(androidx.preference.PreferenceFragment, androidx.preference.Preference!);
     method @Deprecated public abstract void onPreferenceStartInitialScreen();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onViewCreated(android.view.View!, android.os.Bundle!);
     method @Deprecated public void startImmersiveFragment(android.app.Fragment);
     method @Deprecated public void startPreferenceFragment(android.app.Fragment);
   }
diff --git a/leanback-preference/api/1.1.0-alpha02.txt b/leanback-preference/api/1.1.0-alpha02.txt
index 5d40456..7d55268 100644
--- a/leanback-preference/api/1.1.0-alpha02.txt
+++ b/leanback-preference/api/1.1.0-alpha02.txt
@@ -22,6 +22,8 @@
     method @Deprecated public static androidx.leanback.preference.LeanbackListPreferenceDialogFragment! newInstanceMulti(String!);
     method @Deprecated public static androidx.leanback.preference.LeanbackListPreferenceDialogFragment! newInstanceSingle(String!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView.Adapter! onCreateAdapter();
+    method @Deprecated public android.view.View? onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
   }
 
   @Deprecated public class LeanbackListPreferenceDialogFragment.AdapterMulti extends androidx.recyclerview.widget.RecyclerView.Adapter<androidx.leanback.preference.LeanbackListPreferenceDialogFragment.ViewHolder> implements androidx.leanback.preference.LeanbackListPreferenceDialogFragment.ViewHolder.OnItemClickListener {
@@ -68,6 +70,7 @@
   @Deprecated public class LeanbackPreferenceDialogFragment extends android.app.Fragment {
     ctor @Deprecated public LeanbackPreferenceDialogFragment();
     method @Deprecated public androidx.preference.DialogPreference! getPreference();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     field @Deprecated public static final String ARG_KEY = "key";
   }
 
@@ -89,8 +92,12 @@
 
   @Deprecated public abstract class LeanbackSettingsFragment extends android.app.Fragment implements androidx.preference.PreferenceFragment.OnPreferenceDisplayDialogCallback androidx.preference.PreferenceFragment.OnPreferenceStartFragmentCallback androidx.preference.PreferenceFragment.OnPreferenceStartScreenCallback {
     ctor @Deprecated public LeanbackSettingsFragment();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onPause();
     method @Deprecated public boolean onPreferenceDisplayDialog(androidx.preference.PreferenceFragment, androidx.preference.Preference!);
     method @Deprecated public abstract void onPreferenceStartInitialScreen();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onViewCreated(android.view.View!, android.os.Bundle!);
     method @Deprecated public void startImmersiveFragment(android.app.Fragment);
     method @Deprecated public void startPreferenceFragment(android.app.Fragment);
   }
diff --git a/leanback-preference/api/current.txt b/leanback-preference/api/current.txt
index 5d40456..7d55268 100644
--- a/leanback-preference/api/current.txt
+++ b/leanback-preference/api/current.txt
@@ -22,6 +22,8 @@
     method @Deprecated public static androidx.leanback.preference.LeanbackListPreferenceDialogFragment! newInstanceMulti(String!);
     method @Deprecated public static androidx.leanback.preference.LeanbackListPreferenceDialogFragment! newInstanceSingle(String!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView.Adapter! onCreateAdapter();
+    method @Deprecated public android.view.View? onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
   }
 
   @Deprecated public class LeanbackListPreferenceDialogFragment.AdapterMulti extends androidx.recyclerview.widget.RecyclerView.Adapter<androidx.leanback.preference.LeanbackListPreferenceDialogFragment.ViewHolder> implements androidx.leanback.preference.LeanbackListPreferenceDialogFragment.ViewHolder.OnItemClickListener {
@@ -68,6 +70,7 @@
   @Deprecated public class LeanbackPreferenceDialogFragment extends android.app.Fragment {
     ctor @Deprecated public LeanbackPreferenceDialogFragment();
     method @Deprecated public androidx.preference.DialogPreference! getPreference();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     field @Deprecated public static final String ARG_KEY = "key";
   }
 
@@ -89,8 +92,12 @@
 
   @Deprecated public abstract class LeanbackSettingsFragment extends android.app.Fragment implements androidx.preference.PreferenceFragment.OnPreferenceDisplayDialogCallback androidx.preference.PreferenceFragment.OnPreferenceStartFragmentCallback androidx.preference.PreferenceFragment.OnPreferenceStartScreenCallback {
     ctor @Deprecated public LeanbackSettingsFragment();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onPause();
     method @Deprecated public boolean onPreferenceDisplayDialog(androidx.preference.PreferenceFragment, androidx.preference.Preference!);
     method @Deprecated public abstract void onPreferenceStartInitialScreen();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onViewCreated(android.view.View!, android.os.Bundle!);
     method @Deprecated public void startImmersiveFragment(android.app.Fragment);
     method @Deprecated public void startPreferenceFragment(android.app.Fragment);
   }
diff --git a/leanback-preference/api/restricted_1.1.0-alpha02.txt b/leanback-preference/api/restricted_1.1.0-alpha02.txt
index c559029..9e56499 100644
--- a/leanback-preference/api/restricted_1.1.0-alpha02.txt
+++ b/leanback-preference/api/restricted_1.1.0-alpha02.txt
@@ -7,6 +7,7 @@
 
   @Deprecated @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public static class LeanbackSettingsFragment.DummyFragment extends android.app.Fragment {
     ctor @Deprecated public LeanbackSettingsFragment.DummyFragment();
+    method @Deprecated public android.view.View? onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
   }
 
   @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public class LeanbackSettingsRootView extends android.widget.FrameLayout {
diff --git a/leanback-preference/api/restricted_current.txt b/leanback-preference/api/restricted_current.txt
index c559029..9e56499 100644
--- a/leanback-preference/api/restricted_current.txt
+++ b/leanback-preference/api/restricted_current.txt
@@ -7,6 +7,7 @@
 
   @Deprecated @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public static class LeanbackSettingsFragment.DummyFragment extends android.app.Fragment {
     ctor @Deprecated public LeanbackSettingsFragment.DummyFragment();
+    method @Deprecated public android.view.View? onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
   }
 
   @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public class LeanbackSettingsRootView extends android.widget.FrameLayout {
diff --git a/leanback/api/1.1.0-alpha01.txt b/leanback/api/1.1.0-alpha01.txt
index 9dab078..6bf9dcc 100644
--- a/leanback/api/1.1.0-alpha01.txt
+++ b/leanback/api/1.1.0-alpha01.txt
@@ -24,6 +24,7 @@
   @Deprecated public class BaseFragment extends androidx.leanback.app.BrandedFragment {
     method @Deprecated protected Object! createEntranceTransition();
     method @Deprecated public final androidx.leanback.app.ProgressBarManager! getProgressBarManager();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated protected void onEntranceTransitionEnd();
     method @Deprecated protected void onEntranceTransitionPrepare();
     method @Deprecated protected void onEntranceTransitionStart();
@@ -53,7 +54,13 @@
     method @Deprecated public androidx.leanback.widget.TitleViewAdapter! getTitleViewAdapter();
     method @Deprecated public void installTitleView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public final boolean isShowingTitle();
+    method @Deprecated public void onDestroyView();
     method @Deprecated public android.view.View! onInflateTitleView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onPause();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setBadgeDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setOnSearchClickedListener(android.view.View.OnClickListener!);
     method @Deprecated public void setSearchAffordanceColor(int);
@@ -104,6 +111,9 @@
     method @Deprecated public boolean isInHeadersTransition();
     method @Deprecated public boolean isShowingHeaders();
     method @Deprecated public androidx.leanback.app.HeadersFragment! onCreateHeadersFragment();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onStop();
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setBrandColor(@ColorInt int);
     method @Deprecated public void setBrowseTransitionListener(androidx.leanback.app.BrowseFragment.BrowseTransitionListener!);
@@ -289,8 +299,10 @@
     method @Deprecated public androidx.leanback.widget.DetailsParallax! getParallax();
     method @Deprecated public androidx.leanback.app.RowsFragment! getRowsFragment();
     method @Deprecated protected android.view.View! inflateTitle(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated protected void onSetDetailsOverviewRowStatus(androidx.leanback.widget.FullWidthDetailsOverviewRowPresenter!, androidx.leanback.widget.FullWidthDetailsOverviewRowPresenter.ViewHolder!, int, int, int);
     method @Deprecated protected void onSetRowStatus(androidx.leanback.widget.RowPresenter!, androidx.leanback.widget.RowPresenter.ViewHolder!, int, int, int);
+    method @Deprecated public void onStop();
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.BaseOnItemViewClickedListener!);
     method @Deprecated public void setOnItemViewSelectedListener(androidx.leanback.widget.BaseOnItemViewSelectedListener!);
@@ -369,6 +381,7 @@
     method @Deprecated public android.graphics.drawable.Drawable! getImageDrawable();
     method @Deprecated public CharSequence! getMessage();
     method @Deprecated public boolean isBackgroundTranslucent();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public void setBackgroundDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setButtonClickListener(android.view.View.OnClickListener!);
     method @Deprecated public void setButtonText(String!);
@@ -425,6 +438,7 @@
     method @Deprecated public void notifyActionChanged(int);
     method @Deprecated public void notifyButtonActionChanged(int);
     method @Deprecated protected void onAddSharedElementTransition(android.app.FragmentTransaction!, androidx.leanback.app.GuidedStepFragment!);
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated public void onCreateActions(java.util.List<androidx.leanback.widget.GuidedAction>, android.os.Bundle!);
     method @Deprecated public androidx.leanback.widget.GuidedActionsStylist! onCreateActionsStylist();
     method @Deprecated public android.view.View! onCreateBackgroundView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
@@ -432,6 +446,8 @@
     method @Deprecated public androidx.leanback.widget.GuidedActionsStylist! onCreateButtonActionsStylist();
     method @Deprecated public androidx.leanback.widget.GuidanceStylist.Guidance onCreateGuidance(android.os.Bundle!);
     method @Deprecated public androidx.leanback.widget.GuidanceStylist! onCreateGuidanceStylist();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
     method @Deprecated public void onGuidedActionClicked(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void onGuidedActionEditCanceled(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void onGuidedActionEdited(androidx.leanback.widget.GuidedAction!);
@@ -439,6 +455,8 @@
     method @Deprecated public void onGuidedActionFocused(androidx.leanback.widget.GuidedAction!);
     method @Deprecated protected void onProvideFragmentTransitions();
     method @Deprecated public int onProvideTheme();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public boolean onSubGuidedActionClicked(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void openInEditMode(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void popBackStackToGuidedStepFragment(Class!, int);
@@ -525,9 +543,13 @@
     method @Deprecated public int getSelectedPosition();
     method @Deprecated public final androidx.leanback.widget.VerticalGridView! getVerticalGridView();
     method @Deprecated public boolean isScrolling();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public void onTransitionEnd();
     method @Deprecated public boolean onTransitionPrepare();
     method @Deprecated public void onTransitionStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public final void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setAlignment(int);
     method @Deprecated public void setOnHeaderClickedListener(androidx.leanback.app.HeadersFragment.OnHeaderClickedListener!);
@@ -597,10 +619,13 @@
     method @Deprecated protected abstract android.view.View? onCreateForegroundView(android.view.LayoutInflater!, android.view.ViewGroup!);
     method @Deprecated protected android.animation.Animator? onCreateLogoAnimation();
     method @Deprecated protected android.animation.Animator! onCreateTitleAnimator();
+    method @Deprecated public android.view.View? onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated protected void onFinishFragment();
     method @Deprecated protected void onLogoAnimationFinished();
     method @Deprecated protected void onPageChanged(int, int);
     method @Deprecated public int onProvideTheme();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setArrowBackgroundColor(@ColorInt int);
     method @Deprecated public void setArrowColor(@ColorInt int);
     method @Deprecated public void setDescriptionViewTextColor(@ColorInt int);
@@ -664,8 +689,17 @@
     method @Deprecated public boolean isShowOrHideControlsOverlayOnUserInteraction();
     method @Deprecated public void notifyPlaybackRowChanged();
     method @Deprecated protected void onBufferingStateChanged(boolean);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onDestroyView();
     method @Deprecated protected void onError(int, CharSequence!);
+    method @Deprecated public void onPause();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onStart();
+    method @Deprecated public void onStop();
     method @Deprecated protected void onVideoSizeChanged(int, int);
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setBackgroundType(int);
     method @Deprecated public void setControlsOverlayAutoHideEnabled(boolean);
@@ -765,9 +799,14 @@
     method @Deprecated public int getSelectedPosition();
     method @Deprecated public final androidx.leanback.widget.VerticalGridView! getVerticalGridView();
     method @Deprecated public boolean isScrolling();
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public void onTransitionEnd();
     method @Deprecated public boolean onTransitionPrepare();
     method @Deprecated public void onTransitionStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public final void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setAlignment(int);
     method @Deprecated public void setEntranceTransitionState(boolean);
@@ -838,6 +877,13 @@
     method @Deprecated public androidx.leanback.app.RowsFragment! getRowsFragment();
     method @Deprecated public String! getTitle();
     method @Deprecated public static androidx.leanback.app.SearchFragment! newInstance(String!);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onPause();
+    method @Deprecated public void onRequestPermissionsResult(int, String[]!, int[]!);
+    method @Deprecated public void onResume();
+    method @Deprecated public void onStart();
     method @Deprecated public void setBadgeDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.OnItemViewClickedListener!);
     method @Deprecated public void setOnItemViewSelectedListener(androidx.leanback.widget.OnItemViewSelectedListener!);
@@ -891,6 +937,7 @@
     method @Deprecated public androidx.leanback.widget.ObjectAdapter! getAdapter();
     method @Deprecated public androidx.leanback.widget.VerticalGridPresenter! getGridPresenter();
     method @Deprecated public androidx.leanback.widget.OnItemViewClickedListener! getOnItemViewClickedListener();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setGridPresenter(androidx.leanback.widget.VerticalGridPresenter!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.OnItemViewClickedListener!);
diff --git a/leanback/api/1.1.0-alpha02.txt b/leanback/api/1.1.0-alpha02.txt
index 9dab078..6bf9dcc 100644
--- a/leanback/api/1.1.0-alpha02.txt
+++ b/leanback/api/1.1.0-alpha02.txt
@@ -24,6 +24,7 @@
   @Deprecated public class BaseFragment extends androidx.leanback.app.BrandedFragment {
     method @Deprecated protected Object! createEntranceTransition();
     method @Deprecated public final androidx.leanback.app.ProgressBarManager! getProgressBarManager();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated protected void onEntranceTransitionEnd();
     method @Deprecated protected void onEntranceTransitionPrepare();
     method @Deprecated protected void onEntranceTransitionStart();
@@ -53,7 +54,13 @@
     method @Deprecated public androidx.leanback.widget.TitleViewAdapter! getTitleViewAdapter();
     method @Deprecated public void installTitleView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public final boolean isShowingTitle();
+    method @Deprecated public void onDestroyView();
     method @Deprecated public android.view.View! onInflateTitleView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onPause();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setBadgeDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setOnSearchClickedListener(android.view.View.OnClickListener!);
     method @Deprecated public void setSearchAffordanceColor(int);
@@ -104,6 +111,9 @@
     method @Deprecated public boolean isInHeadersTransition();
     method @Deprecated public boolean isShowingHeaders();
     method @Deprecated public androidx.leanback.app.HeadersFragment! onCreateHeadersFragment();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onStop();
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setBrandColor(@ColorInt int);
     method @Deprecated public void setBrowseTransitionListener(androidx.leanback.app.BrowseFragment.BrowseTransitionListener!);
@@ -289,8 +299,10 @@
     method @Deprecated public androidx.leanback.widget.DetailsParallax! getParallax();
     method @Deprecated public androidx.leanback.app.RowsFragment! getRowsFragment();
     method @Deprecated protected android.view.View! inflateTitle(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated protected void onSetDetailsOverviewRowStatus(androidx.leanback.widget.FullWidthDetailsOverviewRowPresenter!, androidx.leanback.widget.FullWidthDetailsOverviewRowPresenter.ViewHolder!, int, int, int);
     method @Deprecated protected void onSetRowStatus(androidx.leanback.widget.RowPresenter!, androidx.leanback.widget.RowPresenter.ViewHolder!, int, int, int);
+    method @Deprecated public void onStop();
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.BaseOnItemViewClickedListener!);
     method @Deprecated public void setOnItemViewSelectedListener(androidx.leanback.widget.BaseOnItemViewSelectedListener!);
@@ -369,6 +381,7 @@
     method @Deprecated public android.graphics.drawable.Drawable! getImageDrawable();
     method @Deprecated public CharSequence! getMessage();
     method @Deprecated public boolean isBackgroundTranslucent();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public void setBackgroundDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setButtonClickListener(android.view.View.OnClickListener!);
     method @Deprecated public void setButtonText(String!);
@@ -425,6 +438,7 @@
     method @Deprecated public void notifyActionChanged(int);
     method @Deprecated public void notifyButtonActionChanged(int);
     method @Deprecated protected void onAddSharedElementTransition(android.app.FragmentTransaction!, androidx.leanback.app.GuidedStepFragment!);
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated public void onCreateActions(java.util.List<androidx.leanback.widget.GuidedAction>, android.os.Bundle!);
     method @Deprecated public androidx.leanback.widget.GuidedActionsStylist! onCreateActionsStylist();
     method @Deprecated public android.view.View! onCreateBackgroundView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
@@ -432,6 +446,8 @@
     method @Deprecated public androidx.leanback.widget.GuidedActionsStylist! onCreateButtonActionsStylist();
     method @Deprecated public androidx.leanback.widget.GuidanceStylist.Guidance onCreateGuidance(android.os.Bundle!);
     method @Deprecated public androidx.leanback.widget.GuidanceStylist! onCreateGuidanceStylist();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
     method @Deprecated public void onGuidedActionClicked(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void onGuidedActionEditCanceled(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void onGuidedActionEdited(androidx.leanback.widget.GuidedAction!);
@@ -439,6 +455,8 @@
     method @Deprecated public void onGuidedActionFocused(androidx.leanback.widget.GuidedAction!);
     method @Deprecated protected void onProvideFragmentTransitions();
     method @Deprecated public int onProvideTheme();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public boolean onSubGuidedActionClicked(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void openInEditMode(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void popBackStackToGuidedStepFragment(Class!, int);
@@ -525,9 +543,13 @@
     method @Deprecated public int getSelectedPosition();
     method @Deprecated public final androidx.leanback.widget.VerticalGridView! getVerticalGridView();
     method @Deprecated public boolean isScrolling();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public void onTransitionEnd();
     method @Deprecated public boolean onTransitionPrepare();
     method @Deprecated public void onTransitionStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public final void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setAlignment(int);
     method @Deprecated public void setOnHeaderClickedListener(androidx.leanback.app.HeadersFragment.OnHeaderClickedListener!);
@@ -597,10 +619,13 @@
     method @Deprecated protected abstract android.view.View? onCreateForegroundView(android.view.LayoutInflater!, android.view.ViewGroup!);
     method @Deprecated protected android.animation.Animator? onCreateLogoAnimation();
     method @Deprecated protected android.animation.Animator! onCreateTitleAnimator();
+    method @Deprecated public android.view.View? onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated protected void onFinishFragment();
     method @Deprecated protected void onLogoAnimationFinished();
     method @Deprecated protected void onPageChanged(int, int);
     method @Deprecated public int onProvideTheme();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setArrowBackgroundColor(@ColorInt int);
     method @Deprecated public void setArrowColor(@ColorInt int);
     method @Deprecated public void setDescriptionViewTextColor(@ColorInt int);
@@ -664,8 +689,17 @@
     method @Deprecated public boolean isShowOrHideControlsOverlayOnUserInteraction();
     method @Deprecated public void notifyPlaybackRowChanged();
     method @Deprecated protected void onBufferingStateChanged(boolean);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onDestroyView();
     method @Deprecated protected void onError(int, CharSequence!);
+    method @Deprecated public void onPause();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onStart();
+    method @Deprecated public void onStop();
     method @Deprecated protected void onVideoSizeChanged(int, int);
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setBackgroundType(int);
     method @Deprecated public void setControlsOverlayAutoHideEnabled(boolean);
@@ -765,9 +799,14 @@
     method @Deprecated public int getSelectedPosition();
     method @Deprecated public final androidx.leanback.widget.VerticalGridView! getVerticalGridView();
     method @Deprecated public boolean isScrolling();
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public void onTransitionEnd();
     method @Deprecated public boolean onTransitionPrepare();
     method @Deprecated public void onTransitionStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public final void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setAlignment(int);
     method @Deprecated public void setEntranceTransitionState(boolean);
@@ -838,6 +877,13 @@
     method @Deprecated public androidx.leanback.app.RowsFragment! getRowsFragment();
     method @Deprecated public String! getTitle();
     method @Deprecated public static androidx.leanback.app.SearchFragment! newInstance(String!);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onPause();
+    method @Deprecated public void onRequestPermissionsResult(int, String[]!, int[]!);
+    method @Deprecated public void onResume();
+    method @Deprecated public void onStart();
     method @Deprecated public void setBadgeDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.OnItemViewClickedListener!);
     method @Deprecated public void setOnItemViewSelectedListener(androidx.leanback.widget.OnItemViewSelectedListener!);
@@ -891,6 +937,7 @@
     method @Deprecated public androidx.leanback.widget.ObjectAdapter! getAdapter();
     method @Deprecated public androidx.leanback.widget.VerticalGridPresenter! getGridPresenter();
     method @Deprecated public androidx.leanback.widget.OnItemViewClickedListener! getOnItemViewClickedListener();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setGridPresenter(androidx.leanback.widget.VerticalGridPresenter!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.OnItemViewClickedListener!);
diff --git a/leanback/api/current.txt b/leanback/api/current.txt
index 9dab078..6bf9dcc 100644
--- a/leanback/api/current.txt
+++ b/leanback/api/current.txt
@@ -24,6 +24,7 @@
   @Deprecated public class BaseFragment extends androidx.leanback.app.BrandedFragment {
     method @Deprecated protected Object! createEntranceTransition();
     method @Deprecated public final androidx.leanback.app.ProgressBarManager! getProgressBarManager();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated protected void onEntranceTransitionEnd();
     method @Deprecated protected void onEntranceTransitionPrepare();
     method @Deprecated protected void onEntranceTransitionStart();
@@ -53,7 +54,13 @@
     method @Deprecated public androidx.leanback.widget.TitleViewAdapter! getTitleViewAdapter();
     method @Deprecated public void installTitleView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public final boolean isShowingTitle();
+    method @Deprecated public void onDestroyView();
     method @Deprecated public android.view.View! onInflateTitleView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onPause();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setBadgeDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setOnSearchClickedListener(android.view.View.OnClickListener!);
     method @Deprecated public void setSearchAffordanceColor(int);
@@ -104,6 +111,9 @@
     method @Deprecated public boolean isInHeadersTransition();
     method @Deprecated public boolean isShowingHeaders();
     method @Deprecated public androidx.leanback.app.HeadersFragment! onCreateHeadersFragment();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onStop();
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setBrandColor(@ColorInt int);
     method @Deprecated public void setBrowseTransitionListener(androidx.leanback.app.BrowseFragment.BrowseTransitionListener!);
@@ -289,8 +299,10 @@
     method @Deprecated public androidx.leanback.widget.DetailsParallax! getParallax();
     method @Deprecated public androidx.leanback.app.RowsFragment! getRowsFragment();
     method @Deprecated protected android.view.View! inflateTitle(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated protected void onSetDetailsOverviewRowStatus(androidx.leanback.widget.FullWidthDetailsOverviewRowPresenter!, androidx.leanback.widget.FullWidthDetailsOverviewRowPresenter.ViewHolder!, int, int, int);
     method @Deprecated protected void onSetRowStatus(androidx.leanback.widget.RowPresenter!, androidx.leanback.widget.RowPresenter.ViewHolder!, int, int, int);
+    method @Deprecated public void onStop();
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.BaseOnItemViewClickedListener!);
     method @Deprecated public void setOnItemViewSelectedListener(androidx.leanback.widget.BaseOnItemViewSelectedListener!);
@@ -369,6 +381,7 @@
     method @Deprecated public android.graphics.drawable.Drawable! getImageDrawable();
     method @Deprecated public CharSequence! getMessage();
     method @Deprecated public boolean isBackgroundTranslucent();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public void setBackgroundDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setButtonClickListener(android.view.View.OnClickListener!);
     method @Deprecated public void setButtonText(String!);
@@ -425,6 +438,7 @@
     method @Deprecated public void notifyActionChanged(int);
     method @Deprecated public void notifyButtonActionChanged(int);
     method @Deprecated protected void onAddSharedElementTransition(android.app.FragmentTransaction!, androidx.leanback.app.GuidedStepFragment!);
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated public void onCreateActions(java.util.List<androidx.leanback.widget.GuidedAction>, android.os.Bundle!);
     method @Deprecated public androidx.leanback.widget.GuidedActionsStylist! onCreateActionsStylist();
     method @Deprecated public android.view.View! onCreateBackgroundView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
@@ -432,6 +446,8 @@
     method @Deprecated public androidx.leanback.widget.GuidedActionsStylist! onCreateButtonActionsStylist();
     method @Deprecated public androidx.leanback.widget.GuidanceStylist.Guidance onCreateGuidance(android.os.Bundle!);
     method @Deprecated public androidx.leanback.widget.GuidanceStylist! onCreateGuidanceStylist();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
     method @Deprecated public void onGuidedActionClicked(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void onGuidedActionEditCanceled(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void onGuidedActionEdited(androidx.leanback.widget.GuidedAction!);
@@ -439,6 +455,8 @@
     method @Deprecated public void onGuidedActionFocused(androidx.leanback.widget.GuidedAction!);
     method @Deprecated protected void onProvideFragmentTransitions();
     method @Deprecated public int onProvideTheme();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public boolean onSubGuidedActionClicked(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void openInEditMode(androidx.leanback.widget.GuidedAction!);
     method @Deprecated public void popBackStackToGuidedStepFragment(Class!, int);
@@ -525,9 +543,13 @@
     method @Deprecated public int getSelectedPosition();
     method @Deprecated public final androidx.leanback.widget.VerticalGridView! getVerticalGridView();
     method @Deprecated public boolean isScrolling();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public void onTransitionEnd();
     method @Deprecated public boolean onTransitionPrepare();
     method @Deprecated public void onTransitionStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public final void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setAlignment(int);
     method @Deprecated public void setOnHeaderClickedListener(androidx.leanback.app.HeadersFragment.OnHeaderClickedListener!);
@@ -597,10 +619,13 @@
     method @Deprecated protected abstract android.view.View? onCreateForegroundView(android.view.LayoutInflater!, android.view.ViewGroup!);
     method @Deprecated protected android.animation.Animator? onCreateLogoAnimation();
     method @Deprecated protected android.animation.Animator! onCreateTitleAnimator();
+    method @Deprecated public android.view.View? onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated protected void onFinishFragment();
     method @Deprecated protected void onLogoAnimationFinished();
     method @Deprecated protected void onPageChanged(int, int);
     method @Deprecated public int onProvideTheme();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setArrowBackgroundColor(@ColorInt int);
     method @Deprecated public void setArrowColor(@ColorInt int);
     method @Deprecated public void setDescriptionViewTextColor(@ColorInt int);
@@ -664,8 +689,17 @@
     method @Deprecated public boolean isShowOrHideControlsOverlayOnUserInteraction();
     method @Deprecated public void notifyPlaybackRowChanged();
     method @Deprecated protected void onBufferingStateChanged(boolean);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onDestroyView();
     method @Deprecated protected void onError(int, CharSequence!);
+    method @Deprecated public void onPause();
+    method @Deprecated public void onResume();
+    method @Deprecated public void onStart();
+    method @Deprecated public void onStop();
     method @Deprecated protected void onVideoSizeChanged(int, int);
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setBackgroundType(int);
     method @Deprecated public void setControlsOverlayAutoHideEnabled(boolean);
@@ -765,9 +799,14 @@
     method @Deprecated public int getSelectedPosition();
     method @Deprecated public final androidx.leanback.widget.VerticalGridView! getVerticalGridView();
     method @Deprecated public boolean isScrolling();
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
     method @Deprecated public void onTransitionEnd();
     method @Deprecated public boolean onTransitionPrepare();
     method @Deprecated public void onTransitionStart();
+    method @Deprecated public void onViewCreated(android.view.View, android.os.Bundle?);
     method @Deprecated public final void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setAlignment(int);
     method @Deprecated public void setEntranceTransitionState(boolean);
@@ -838,6 +877,13 @@
     method @Deprecated public androidx.leanback.app.RowsFragment! getRowsFragment();
     method @Deprecated public String! getTitle();
     method @Deprecated public static androidx.leanback.app.SearchFragment! newInstance(String!);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroy();
+    method @Deprecated public void onPause();
+    method @Deprecated public void onRequestPermissionsResult(int, String[]!, int[]!);
+    method @Deprecated public void onResume();
+    method @Deprecated public void onStart();
     method @Deprecated public void setBadgeDrawable(android.graphics.drawable.Drawable!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.OnItemViewClickedListener!);
     method @Deprecated public void setOnItemViewSelectedListener(androidx.leanback.widget.OnItemViewSelectedListener!);
@@ -891,6 +937,7 @@
     method @Deprecated public androidx.leanback.widget.ObjectAdapter! getAdapter();
     method @Deprecated public androidx.leanback.widget.VerticalGridPresenter! getGridPresenter();
     method @Deprecated public androidx.leanback.widget.OnItemViewClickedListener! getOnItemViewClickedListener();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
     method @Deprecated public void setAdapter(androidx.leanback.widget.ObjectAdapter!);
     method @Deprecated public void setGridPresenter(androidx.leanback.widget.VerticalGridPresenter!);
     method @Deprecated public void setOnItemViewClickedListener(androidx.leanback.widget.OnItemViewClickedListener!);
diff --git a/leanback/api/restricted_1.1.0-alpha02.txt b/leanback/api/restricted_1.1.0-alpha02.txt
index d54d9cd..b60f71d 100644
--- a/leanback/api/restricted_1.1.0-alpha02.txt
+++ b/leanback/api/restricted_1.1.0-alpha02.txt
@@ -17,6 +17,10 @@
 
   @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public final class BackgroundFragment extends android.app.Fragment {
     ctor public BackgroundFragment();
+    method public void onDestroy();
+    method public void onResume();
+    method public void onStart();
+    method public void onStop();
   }
 
   @Deprecated public class GuidedStepFragment extends android.app.Fragment implements androidx.leanback.widget.GuidedActionAdapter.FocusListener {
@@ -28,6 +32,7 @@
 
   @Deprecated @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public static class GuidedStepFragment.DummyFragment extends android.app.Fragment {
     ctor @Deprecated public GuidedStepFragment.DummyFragment();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
   }
 
   public class GuidedStepSupportFragment extends androidx.fragment.app.Fragment implements androidx.leanback.widget.GuidedActionAdapter.FocusListener {
diff --git a/leanback/api/restricted_current.txt b/leanback/api/restricted_current.txt
index d54d9cd..b60f71d 100644
--- a/leanback/api/restricted_current.txt
+++ b/leanback/api/restricted_current.txt
@@ -17,6 +17,10 @@
 
   @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public final class BackgroundFragment extends android.app.Fragment {
     ctor public BackgroundFragment();
+    method public void onDestroy();
+    method public void onResume();
+    method public void onStart();
+    method public void onStop();
   }
 
   @Deprecated public class GuidedStepFragment extends android.app.Fragment implements androidx.leanback.widget.GuidedActionAdapter.FocusListener {
@@ -28,6 +32,7 @@
 
   @Deprecated @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public static class GuidedStepFragment.DummyFragment extends android.app.Fragment {
     ctor @Deprecated public GuidedStepFragment.DummyFragment();
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
   }
 
   public class GuidedStepSupportFragment extends androidx.fragment.app.Fragment implements androidx.leanback.widget.GuidedActionAdapter.FocusListener {
diff --git a/lifecycle/runtime/api/restricted_2.1.0-alpha03.txt b/lifecycle/runtime/api/restricted_2.1.0-alpha03.txt
index c79f82d..49e4512 100644
--- a/lifecycle/runtime/api/restricted_2.1.0-alpha03.txt
+++ b/lifecycle/runtime/api/restricted_2.1.0-alpha03.txt
@@ -4,6 +4,12 @@
   @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public class ReportFragment extends android.app.Fragment {
     ctor public ReportFragment();
     method public static void injectIfNeededIn(android.app.Activity!);
+    method public void onActivityCreated(android.os.Bundle!);
+    method public void onDestroy();
+    method public void onPause();
+    method public void onResume();
+    method public void onStart();
+    method public void onStop();
   }
 
 }
diff --git a/lifecycle/runtime/api/restricted_current.txt b/lifecycle/runtime/api/restricted_current.txt
index c79f82d..49e4512 100644
--- a/lifecycle/runtime/api/restricted_current.txt
+++ b/lifecycle/runtime/api/restricted_current.txt
@@ -4,6 +4,12 @@
   @RestrictTo(androidx.annotation.RestrictTo.Scope.LIBRARY_GROUP_PREFIX) public class ReportFragment extends android.app.Fragment {
     ctor public ReportFragment();
     method public static void injectIfNeededIn(android.app.Activity!);
+    method public void onActivityCreated(android.os.Bundle!);
+    method public void onDestroy();
+    method public void onPause();
+    method public void onResume();
+    method public void onStart();
+    method public void onStop();
   }
 
 }
diff --git a/navigation/safe-args-gradle-plugin/build.gradle b/navigation/safe-args-gradle-plugin/build.gradle
index 67d3153..c9f08d3 100644
--- a/navigation/safe-args-gradle-plugin/build.gradle
+++ b/navigation/safe-args-gradle-plugin/build.gradle
@@ -45,7 +45,7 @@
 
 task generateSdkResource() {
     inputs.property("prebuiltsRoot", prebuiltsRoot)
-    inputs.property("compileSdkVersion", SupportConfig.TARGET_SDK_VERSION)
+    inputs.property("compileSdkVersion", SupportConfig.COMPILE_SDK_VERSION)
     inputs.property("buildToolsVersion", SupportConfig.BUILD_TOOLS_VERSION)
     inputs.property("minSdkVersion", SupportConfig.DEFAULT_MIN_SDK_VERSION)
     inputs.property("debugKeystore", debugKeystore)
@@ -57,7 +57,7 @@
         // so we don't use it and write a file manually
         new File(generatedResources, "sdk.prop").withWriter('UTF-8') { writer ->
             writer.write("prebuiltsRepo=$prebuiltsRoot\n")
-            writer.write("compileSdkVersion=$SupportConfig.TARGET_SDK_VERSION\n")
+            writer.write("compileSdkVersion=\"$SupportConfig.COMPILE_SDK_VERSION\"\n")
             writer.write("buildToolsVersion=$SupportConfig.BUILD_TOOLS_VERSION\n")
             writer.write("minSdkVersion=$SupportConfig.DEFAULT_MIN_SDK_VERSION\n")
             writer.write("debugKeystore=$debugKeystore\n")
diff --git a/preference/api/1.1.0-alpha03.txt b/preference/api/1.1.0-alpha03.txt
index d3b0755..611d611 100644
--- a/preference/api/1.1.0-alpha03.txt
+++ b/preference/api/1.1.0-alpha03.txt
@@ -290,9 +290,13 @@
     method @Deprecated public androidx.preference.DialogPreference! getPreference();
     method @Deprecated protected void onBindDialogView(android.view.View!);
     method @Deprecated public void onClick(android.content.DialogInterface!, int);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.app.Dialog onCreateDialog(android.os.Bundle!);
     method @Deprecated protected android.view.View! onCreateDialogView(android.content.Context!);
     method @Deprecated public abstract void onDialogClosed(boolean);
+    method @Deprecated public void onDismiss(android.content.DialogInterface!);
     method @Deprecated protected void onPrepareDialogBuilder(android.app.AlertDialog.Builder!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle);
     field @Deprecated protected static final String ARG_KEY = "key";
   }
 
@@ -314,13 +318,20 @@
     method @Deprecated public final androidx.recyclerview.widget.RecyclerView! getListView();
     method @Deprecated public androidx.preference.PreferenceManager! getPreferenceManager();
     method @Deprecated public androidx.preference.PreferenceScreen! getPreferenceScreen();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated protected androidx.recyclerview.widget.RecyclerView.Adapter! onCreateAdapter(androidx.preference.PreferenceScreen!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView.LayoutManager! onCreateLayoutManager();
     method @Deprecated public abstract void onCreatePreferences(android.os.Bundle!, String!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView! onCreateRecyclerView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
     method @Deprecated public void onDisplayPreferenceDialog(androidx.preference.Preference!);
     method @Deprecated public void onNavigateToScreen(androidx.preference.PreferenceScreen!);
     method @Deprecated public boolean onPreferenceTreeClick(androidx.preference.Preference!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onStart();
+    method @Deprecated public void onStop();
+    method @Deprecated public void onViewCreated(android.view.View!, android.os.Bundle!);
     method @Deprecated public void scrollToPreference(String!);
     method @Deprecated public void scrollToPreference(androidx.preference.Preference!);
     method @Deprecated public void setDivider(android.graphics.drawable.Drawable!);
diff --git a/preference/api/1.1.0-alpha04.txt b/preference/api/1.1.0-alpha04.txt
index 0edd4f7..b23276b 100644
--- a/preference/api/1.1.0-alpha04.txt
+++ b/preference/api/1.1.0-alpha04.txt
@@ -290,9 +290,13 @@
     method @Deprecated public androidx.preference.DialogPreference! getPreference();
     method @Deprecated protected void onBindDialogView(android.view.View!);
     method @Deprecated public void onClick(android.content.DialogInterface!, int);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.app.Dialog onCreateDialog(android.os.Bundle!);
     method @Deprecated protected android.view.View! onCreateDialogView(android.content.Context!);
     method @Deprecated public abstract void onDialogClosed(boolean);
+    method @Deprecated public void onDismiss(android.content.DialogInterface!);
     method @Deprecated protected void onPrepareDialogBuilder(android.app.AlertDialog.Builder!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle);
     field @Deprecated protected static final String ARG_KEY = "key";
   }
 
@@ -314,13 +318,20 @@
     method @Deprecated public final androidx.recyclerview.widget.RecyclerView! getListView();
     method @Deprecated public androidx.preference.PreferenceManager! getPreferenceManager();
     method @Deprecated public androidx.preference.PreferenceScreen! getPreferenceScreen();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated protected androidx.recyclerview.widget.RecyclerView.Adapter! onCreateAdapter(androidx.preference.PreferenceScreen!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView.LayoutManager! onCreateLayoutManager();
     method @Deprecated public abstract void onCreatePreferences(android.os.Bundle!, String!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView! onCreateRecyclerView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
     method @Deprecated public void onDisplayPreferenceDialog(androidx.preference.Preference!);
     method @Deprecated public void onNavigateToScreen(androidx.preference.PreferenceScreen!);
     method @Deprecated public boolean onPreferenceTreeClick(androidx.preference.Preference!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onStart();
+    method @Deprecated public void onStop();
+    method @Deprecated public void onViewCreated(android.view.View!, android.os.Bundle!);
     method @Deprecated public void scrollToPreference(String!);
     method @Deprecated public void scrollToPreference(androidx.preference.Preference!);
     method @Deprecated public void setDivider(android.graphics.drawable.Drawable!);
diff --git a/preference/api/current.txt b/preference/api/current.txt
index 0edd4f7..b23276b 100644
--- a/preference/api/current.txt
+++ b/preference/api/current.txt
@@ -290,9 +290,13 @@
     method @Deprecated public androidx.preference.DialogPreference! getPreference();
     method @Deprecated protected void onBindDialogView(android.view.View!);
     method @Deprecated public void onClick(android.content.DialogInterface!, int);
+    method @Deprecated public void onCreate(android.os.Bundle!);
+    method @Deprecated public android.app.Dialog onCreateDialog(android.os.Bundle!);
     method @Deprecated protected android.view.View! onCreateDialogView(android.content.Context!);
     method @Deprecated public abstract void onDialogClosed(boolean);
+    method @Deprecated public void onDismiss(android.content.DialogInterface!);
     method @Deprecated protected void onPrepareDialogBuilder(android.app.AlertDialog.Builder!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle);
     field @Deprecated protected static final String ARG_KEY = "key";
   }
 
@@ -314,13 +318,20 @@
     method @Deprecated public final androidx.recyclerview.widget.RecyclerView! getListView();
     method @Deprecated public androidx.preference.PreferenceManager! getPreferenceManager();
     method @Deprecated public androidx.preference.PreferenceScreen! getPreferenceScreen();
+    method @Deprecated public void onCreate(android.os.Bundle!);
     method @Deprecated protected androidx.recyclerview.widget.RecyclerView.Adapter! onCreateAdapter(androidx.preference.PreferenceScreen!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView.LayoutManager! onCreateLayoutManager();
     method @Deprecated public abstract void onCreatePreferences(android.os.Bundle!, String!);
     method @Deprecated public androidx.recyclerview.widget.RecyclerView! onCreateRecyclerView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public android.view.View! onCreateView(android.view.LayoutInflater!, android.view.ViewGroup!, android.os.Bundle!);
+    method @Deprecated public void onDestroyView();
     method @Deprecated public void onDisplayPreferenceDialog(androidx.preference.Preference!);
     method @Deprecated public void onNavigateToScreen(androidx.preference.PreferenceScreen!);
     method @Deprecated public boolean onPreferenceTreeClick(androidx.preference.Preference!);
+    method @Deprecated public void onSaveInstanceState(android.os.Bundle!);
+    method @Deprecated public void onStart();
+    method @Deprecated public void onStop();
+    method @Deprecated public void onViewCreated(android.view.View!, android.os.Bundle!);
     method @Deprecated public void scrollToPreference(String!);
     method @Deprecated public void scrollToPreference(androidx.preference.Preference!);
     method @Deprecated public void setDivider(android.graphics.drawable.Drawable!);
diff --git a/preference/res/values-en-rCA/strings.xml b/preference/res/values-en-rCA/strings.xml
index c8d1681..16cf6b7 100644
--- a/preference/res/values-en-rCA/strings.xml
+++ b/preference/res/values-en-rCA/strings.xml
@@ -5,4 +5,6 @@
     <string name="v7_preference_off" msgid="5138405918326871307">"OFF"</string>
     <string name="expand_button_title" msgid="1234962710353108940">"Advanced"</string>
     <string name="summary_collapsed_preference_list" msgid="5190123168583152844">"<xliff:g id="CURRENT_ITEMS">%1$s</xliff:g>, <xliff:g id="ADDED_ITEMS">%2$s</xliff:g>"</string>
+    <string name="copy" msgid="3209159573327985035">"Copy"</string>
+    <string name="preference_copied" msgid="7961817945132860002">"\'<xliff:g id="SUMMARY">%1$s</xliff:g>\' copied to clipboard."</string>
 </resources>
diff --git a/preference/res/values-en-rXC/strings.xml b/preference/res/values-en-rXC/strings.xml
index 96219e7..cb60d80 100644
--- a/preference/res/values-en-rXC/strings.xml
+++ b/preference/res/values-en-rXC/strings.xml
@@ -5,4 +5,6 @@
     <string name="v7_preference_off" msgid="5138405918326871307">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‎‎‎‏‏‏‎‏‎‎‏‏‏‏‎‏‎‎‏‎‎‎‏‏‏‏‎‏‎‏‎‏‎‏‎‎‎‏‏‎‏‎‎‎‏‏‎‏‎‏‎‏‎‏‎‎‎‎‏‎‏‏‎OFF‎‏‎‎‏‎"</string>
     <string name="expand_button_title" msgid="1234962710353108940">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‎‏‏‎‎‎‏‎‎‏‎‎‎‏‏‎‏‏‏‏‎‎‎‎‎‎‎‏‎‏‎‏‎‏‏‏‏‎‏‎‏‏‏‎‎‏‏‎‏‎‏‏‏‏‏‏‏‎‎‏‏‎‎‎Advanced‎‏‎‎‏‎"</string>
     <string name="summary_collapsed_preference_list" msgid="5190123168583152844">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‎‎‏‎‎‎‎‎‎‎‎‏‏‏‎‎‎‎‎‏‎‏‏‎‎‎‎‏‎‏‏‏‏‏‏‎‏‏‏‏‏‎‏‏‎‎‎‏‏‏‎‏‎‎‏‏‎‎‏‏‎‎‎‎‏‎‎‏‏‎<xliff:g id="CURRENT_ITEMS">%1$s</xliff:g>‎‏‎‎‏‏‏‎, ‎‏‎‎‏‏‎<xliff:g id="ADDED_ITEMS">%2$s</xliff:g>‎‏‎‎‏‏‏‎‎‏‎‎‏‎"</string>
+    <string name="copy" msgid="3209159573327985035">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‎‏‎‏‏‎‎‏‎‎‎‏‎‎‏‎‎‏‏‏‎‎‏‏‎‏‎‎‎‎‏‎‎‎‎‏‎‏‏‏‏‎‎‎‎‏‎‎‎‏‏‏‎‎‏‏‎‎‎‏‎‏‏‎Copy‎‏‎‎‏‎"</string>
+    <string name="preference_copied" msgid="7961817945132860002">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‏‎‏‏‏‎‎‏‏‏‏‏‏‎‎‎‎‎‏‏‏‏‎‎‏‏‏‏‎‎‏‏‎‏‎‎‎‏‏‏‏‏‏‎‎‏‏‎‎‎‎‎‏‎‎‏‏‎‎‎‏‎‎\"‎‏‎‎‏‏‎<xliff:g id="SUMMARY">%1$s</xliff:g>‎‏‎‎‏‏‏‎\" copied to clipboard.‎‏‎‎‏‎"</string>
 </resources>
diff --git a/samples/BiometricDemos/src/main/java/com/example/android/biometric/BiometricPromptDemo.java b/samples/BiometricDemos/src/main/java/com/example/android/biometric/BiometricPromptDemo.java
index 0a30f48..298874c 100644
--- a/samples/BiometricDemos/src/main/java/com/example/android/biometric/BiometricPromptDemo.java
+++ b/samples/BiometricDemos/src/main/java/com/example/android/biometric/BiometricPromptDemo.java
@@ -28,11 +28,13 @@
 import android.view.View;
 import android.widget.Button;
 import android.widget.CheckBox;
+import android.widget.RadioGroup;
 import android.widget.Toast;
 
 import androidx.annotation.NonNull;
 import androidx.annotation.RequiresApi;
 import androidx.biometric.BiometricPrompt;
+import androidx.core.os.BuildCompat;
 import androidx.fragment.app.FragmentActivity;
 
 import java.io.IOException;
@@ -66,9 +68,6 @@
 
     private static final String TAG = "BiometricPromptDemo";
 
-    private static final String KEY_SAVED_USE_CRYPTO = "saved_use_crypto_state";
-    private static final String KEY_SAVED_RADIO = "saved_radio_state";
-    private static final String KEY_SAVED_FAILURES = "saved_failures_state";
     private static final String KEY_COUNTER = "saved_counter";
 
     private static final String DEFAULT_KEY_NAME = "default_key";
@@ -78,13 +77,14 @@
     private static final int MODE_CANCEL_ON_CONFIGURATION_CHANGE = 2;
     private static final int MODE_CANCEL_AFTER_THREE_FAILURES = 3;
 
-    private int mMode = MODE_NONE;
-    private boolean mUseCrypto;
-
     private Handler mHandler = new Handler(Looper.getMainLooper());
     private KeyStore mKeyStore;
     private BiometricPrompt mBiometricPrompt;
 
+    private CheckBox mUseCryptoCheckbox;
+    private CheckBox mRequireConfirmationCheckbox;
+    private CheckBox mAllowDeviceCredential;
+
     private int mCounter;
     private int mNumberFailedAttempts;
 
@@ -128,7 +128,7 @@
             mNumberFailedAttempts++;
 
             // Cancel authentication after 3 failed attempts to test the cancel() method.
-            if (mMode == MODE_CANCEL_AFTER_THREE_FAILURES && mNumberFailedAttempts == 3) {
+            if (getMode() == MODE_CANCEL_AFTER_THREE_FAILURES && mNumberFailedAttempts == 3) {
                 mBiometricPrompt.cancelAuthentication();
             }
         }
@@ -139,9 +139,6 @@
         super.onCreate(savedInstanceState);
 
         if (savedInstanceState != null) {
-            mUseCrypto = savedInstanceState.getBoolean(KEY_SAVED_USE_CRYPTO);
-            mMode = savedInstanceState.getInt(KEY_SAVED_RADIO);
-            mNumberFailedAttempts = savedInstanceState.getInt(KEY_SAVED_FAILURES);
             mCounter = savedInstanceState.getInt(KEY_COUNTER);
         }
 
@@ -151,6 +148,9 @@
         buttonCreateKeys = findViewById(R.id.button_enable_biometric_with_crypto);
         final Button buttonAuthenticate;
         buttonAuthenticate = findViewById(R.id.button_authenticate);
+        mUseCryptoCheckbox = findViewById(R.id.checkbox_use_crypto);
+        mRequireConfirmationCheckbox = findViewById(R.id.checkbox_require_confirmation);
+        mAllowDeviceCredential = findViewById(R.id.checkbox_enable_fallback);
 
         try {
             mKeyStore = KeyStore.getInstance("AndroidKeyStore");
@@ -158,7 +158,7 @@
             throw new RuntimeException("Failed to get an instance of KeyStore", e);
         }
 
-        if (!mUseCrypto) {
+        if (!useCrypto()) {
             buttonCreateKeys.setVisibility(View.GONE);
         } else {
             buttonCreateKeys.setVisibility(View.VISIBLE);
@@ -168,11 +168,21 @@
             buttonCreateKeys.setOnClickListener(v -> enableBiometricWithCrypto());
         }
         buttonAuthenticate.setOnClickListener(v -> startAuthentication());
+
+        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.P) {
+            mRequireConfirmationCheckbox.setEnabled(false);
+            mRequireConfirmationCheckbox.setChecked(false);
+        }
+        if (!BuildCompat.isAtLeastQ()) {
+            mAllowDeviceCredential.setEnabled(false);
+            mAllowDeviceCredential.setChecked(false);
+        }
+
     }
 
     @Override
     protected void onPause() {
-        if (mMode == MODE_CANCEL_ON_CONFIGURATION_CHANGE) {
+        if (getMode() == MODE_CANCEL_ON_CONFIGURATION_CHANGE) {
             mBiometricPrompt.cancelAuthentication();
         }
         super.onPause();
@@ -192,53 +202,9 @@
     @Override
     public void onSaveInstanceState(Bundle outState) {
         super.onSaveInstanceState(outState);
-        outState.putBoolean(KEY_SAVED_USE_CRYPTO, mUseCrypto);
-        outState.putInt(KEY_SAVED_RADIO, mMode);
-        outState.putInt(KEY_SAVED_FAILURES, mNumberFailedAttempts);
         outState.putInt(KEY_COUNTER, mCounter);
     }
 
-    /**
-     * Callback when the radio buttons are clicked.
-     * @param view
-     */
-    public void onRadioButtonClicked(View view) {
-        mNumberFailedAttempts = 0;
-
-        switch(view.getId()) {
-            case R.id.radio_persist_across_configuration_changes:
-                mMode = MODE_PERSIST_ACROSS_CONFIGURATION_CHANGES;
-                break;
-            case R.id.radio_cancel_on_configuration_change:
-                mMode = MODE_CANCEL_ON_CONFIGURATION_CHANGE;
-                break;
-            case R.id.radio_cancel_after_three_failures:
-                mMode = MODE_CANCEL_AFTER_THREE_FAILURES;
-                break;
-        }
-    }
-
-    /**
-     * Callback when the checkbox is clicked.
-     * @param view
-     */
-    public void onCheckboxClicked(View view) {
-        boolean checked = ((CheckBox) view).isChecked();
-
-        switch(view.getId()) {
-            case R.id.checkbox_use_crypto:
-                if (checked) {
-                    findViewById(R.id.button_enable_biometric_with_crypto)
-                            .setVisibility(View.VISIBLE);
-                } else {
-                    findViewById(R.id.button_enable_biometric_with_crypto)
-                            .setVisibility(View.GONE);
-                }
-                mUseCrypto = checked;
-                break;
-        }
-    }
-
     @RequiresApi(Build.VERSION_CODES.M)
     private void enableBiometricWithCrypto() {
         // Create the key, this is usually done when the user allows Biometric
@@ -252,25 +218,34 @@
     }
 
     private void startAuthentication() {
-        if (mMode == MODE_NONE) {
+        if (getMode() == MODE_NONE) {
             Toast.makeText(getApplicationContext(), "Select a test first", Toast.LENGTH_SHORT)
                     .show();
             return;
         }
 
         // Build the biometric prompt info
-        BiometricPrompt.PromptInfo info =
-                new BiometricPrompt.PromptInfo.Builder()
-                        .setTitle("Title " + mCounter)
-                        .setSubtitle("Subtitle " + mCounter)
-                        .setDescription(
-                                "Lorem ipsum dolor sit amet, consecte etur adipisicing elit. "
-                                        + mCounter)
-                        .setNegativeButtonText("Negative Button " + mCounter)
-                        .build();
+        BiometricPrompt.PromptInfo.Builder builder = new BiometricPrompt.PromptInfo.Builder()
+                .setTitle("Title " + mCounter)
+                .setSubtitle("Subtitle " + mCounter)
+                .setDescription(
+                        "Lorem ipsum dolor sit amet, consecte etur adipisicing elit. "
+                                + mCounter)
+                .setRequireConfirmation(mRequireConfirmationCheckbox.isChecked());
+
+        if (BuildCompat.isAtLeastQ()) {
+            if (mAllowDeviceCredential.isChecked()) {
+                builder.setAllowDeviceCredential(true);
+            } else {
+                builder.setNegativeButtonText("Negative Button " + mCounter);
+            }
+        } else {
+            builder.setNegativeButtonText("Negative Button " + mCounter);
+        }
+        BiometricPrompt.PromptInfo info = builder.build();
         mCounter++;
 
-        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.M && mUseCrypto) {
+        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.M && useCrypto()) {
             try {
                 // Initialize the cipher. The cipher will be unlocked by KeyStore after the user has
                 // authenticated via biometrics.
@@ -357,4 +332,26 @@
             throw new RuntimeException(e);
         }
     }
+
+    private boolean useCrypto() {
+        return mUseCryptoCheckbox.isChecked();
+    }
+
+    /**
+     * @return The currently selected configuration.
+     */
+    private int getMode() {
+        int id = ((RadioGroup) findViewById(R.id.radio_group)).getCheckedRadioButtonId();
+        switch (id) {
+            case R.id.radio_persist_across_configuration_changes:
+                return MODE_PERSIST_ACROSS_CONFIGURATION_CHANGES;
+            case R.id.radio_cancel_on_configuration_change:
+                return MODE_CANCEL_ON_CONFIGURATION_CHANGE;
+            case R.id.radio_cancel_after_three_failures:
+                return MODE_CANCEL_AFTER_THREE_FAILURES;
+            default:
+                return MODE_NONE;
+        }
+    }
+
 }
diff --git a/samples/BiometricDemos/src/main/res/layout/fragment_activity.xml b/samples/BiometricDemos/src/main/res/layout/fragment_activity.xml
index 6d2c318..ed02990 100644
--- a/samples/BiometricDemos/src/main/res/layout/fragment_activity.xml
+++ b/samples/BiometricDemos/src/main/res/layout/fragment_activity.xml
@@ -33,14 +33,33 @@
         android:layout_height="wrap_content"
         android:text="@string/button_authenticate"/>
 
-    <CheckBox
-        android:id="@+id/checkbox_use_crypto"
-        android:layout_width="match_parent"
-        android:layout_height="wrap_content"
-        android:text="@string/checkbox_text_use_crypto"
-        android:>
+    <LinearLayout android:layout_width="match_parent"
+                  android:layout_height="wrap_content"
+                  android:orientation="vertical">
+        <CheckBox
+                android:id="@+id/checkbox_use_crypto"
+                android:layout_weight="1"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:text="@string/checkbox_text_use_crypto"/>
+        <CheckBox
+                android:id="@+id/checkbox_require_confirmation"
+                android:layout_weight="1"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:text="@string/checkbox_text_require_confirmation"
+                android:checked="true"/>
+        <CheckBox
+                android:id="@+id/checkbox_enable_fallback"
+                android:layout_weight="1"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:text="@string/checkbox_text_allow_device_credential"/>
+    </LinearLayout>
+
 
     <RadioGroup
+        android:id="@+id/radio_group"
         android:layout_width="wrap_content"
         android:layout_height="wrap_content">
 
@@ -48,22 +67,19 @@
             android:id="@+id/radio_persist_across_configuration_changes"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
-            android:text="@string/radio_text_persist_across_configuration_changes"
-            android:>
+            android:text="@string/radio_text_persist_across_configuration_changes" />
 
         <RadioButton
             android:id="@+id/radio_cancel_on_configuration_change"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
-            android:text="@string/radio_text_cancel_on_configuration_change"
-            android:>
+            android:text="@string/radio_text_cancel_on_configuration_change" />
 
         <RadioButton
             android:id="@+id/radio_cancel_after_three_failures"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
-            android:text="@string/radio_text_cancel_after_three_failures"
-            android:>
+            android:text="@string/radio_text_cancel_after_three_failures" />
 
     </RadioGroup>
 
diff --git a/samples/BiometricDemos/src/main/res/values/strings.xml b/samples/BiometricDemos/src/main/res/values/strings.xml
index e945842..d570e1b 100644
--- a/samples/BiometricDemos/src/main/res/values/strings.xml
+++ b/samples/BiometricDemos/src/main/res/values/strings.xml
@@ -22,6 +22,8 @@
     <string name="button_authenticate">Authenticate</string>
 
     <string name="checkbox_text_use_crypto">Use crypto</string>
+    <string name="checkbox_text_require_confirmation">Require confirmation</string>
+    <string name="checkbox_text_allow_device_credential">Allow Device Credential</string>
 
     <string name="radio_text_persist_across_configuration_changes">Persist across configuration changes</string>
     <string name="radio_text_cancel_on_configuration_change">Cancel when configuration changes</string>
diff --git a/settings.gradle b/settings.gradle
index 31e96e2..753208f 100644
--- a/settings.gradle
+++ b/settings.gradle
@@ -74,6 +74,7 @@
 includeProject(":fragment", "fragment")
 includeProject(":fragment-ktx", "fragment/ktx")
 includeProject(":fragment-testing", "fragment/testing")
+includeProject(":fakeannotations", "fakeannotations")
 includeProject(":gridlayout", "gridlayout")
 includeProject(":heifwriter", "heifwriter")
 includeProject(":interpolator", "interpolator")
diff --git a/slices/core/src/main/java/androidx/slice/SliceProvider.java b/slices/core/src/main/java/androidx/slice/SliceProvider.java
index 397db68..e5144cc 100644
--- a/slices/core/src/main/java/androidx/slice/SliceProvider.java
+++ b/slices/core/src/main/java/androidx/slice/SliceProvider.java
@@ -143,6 +143,7 @@
 
     private SliceProviderCompat mCompat;
 
+    private final Object mPinnedSliceUrisLock = new Object();
     private List<Uri> mPinnedSliceUris;
 
     /**
@@ -200,8 +201,6 @@
     @Override
     public final boolean onCreate() {
         if (Build.VERSION.SDK_INT < 19) return false;
-        mPinnedSliceUris = new ArrayList<>(SliceManager.getInstance(
-                getContext()).getPinnedSlices());
         if (Build.VERSION.SDK_INT < 28) {
             mCompat = new SliceProviderCompat(this,
                     onCreatePermissionManager(mAutoGrantPermissions), getContext());
@@ -361,8 +360,9 @@
     @RestrictTo(RestrictTo.Scope.LIBRARY)
     @RequiresApi(19)
     public void handleSlicePinned(Uri sliceUri) {
-        if (!mPinnedSliceUris.contains(sliceUri)) {
-            mPinnedSliceUris.add(sliceUri);
+        List<Uri> pinnedSlices = getPinnedSlices();
+        if (!pinnedSlices.contains(sliceUri)) {
+            pinnedSlices.add(sliceUri);
         }
     }
 
@@ -372,8 +372,9 @@
     @RestrictTo(RestrictTo.Scope.LIBRARY)
     @RequiresApi(19)
     public void handleSliceUnpinned(Uri sliceUri) {
-        if (mPinnedSliceUris.contains(sliceUri)) {
-            mPinnedSliceUris.remove(sliceUri);
+        List<Uri> pinnedSlices = getPinnedSlices();
+        if (pinnedSlices.contains(sliceUri)) {
+            pinnedSlices.remove(sliceUri);
         }
     }
 
@@ -413,6 +414,12 @@
      */
     @RequiresApi(19)
     @NonNull public List<Uri> getPinnedSlices() {
+        synchronized (mPinnedSliceUrisLock) {
+            if (mPinnedSliceUris == null) {
+                mPinnedSliceUris = new ArrayList<>(SliceManager.getInstance(getContext())
+                        .getPinnedSlices());
+            }
+        }
         return mPinnedSliceUris;
     }
 
diff --git a/slidingpanelayout/src/main/java/androidx/slidingpanelayout/widget/SlidingPaneLayout.java b/slidingpanelayout/src/main/java/androidx/slidingpanelayout/widget/SlidingPaneLayout.java
index 282d377..6ac1cb0 100644
--- a/slidingpanelayout/src/main/java/androidx/slidingpanelayout/widget/SlidingPaneLayout.java
+++ b/slidingpanelayout/src/main/java/androidx/slidingpanelayout/widget/SlidingPaneLayout.java
@@ -22,7 +22,6 @@
 import android.graphics.Paint;
 import android.graphics.PixelFormat;
 import android.graphics.PorterDuff;
-import android.graphics.PorterDuffColorFilter;
 import android.graphics.Rect;
 import android.graphics.drawable.Drawable;
 import android.os.Build;
@@ -400,6 +399,8 @@
         }
     }
 
+    @SuppressWarnings("deprecation")
+    // Remove suppression once b/120984816 is addressed.
     private static boolean viewIsOpaque(View v) {
         if (v.isOpaque()) {
             return true;
@@ -962,6 +963,7 @@
         dispatchOnPanelSlide(mSlideableView);
     }
 
+    @SuppressWarnings("deprecation")
     private void dimChildView(View v, float mag, int fadeColor) {
         final LayoutParams lp = (LayoutParams) v.getLayoutParams();
 
@@ -972,7 +974,8 @@
             if (lp.dimPaint == null) {
                 lp.dimPaint = new Paint();
             }
-            lp.dimPaint.setColorFilter(new PorterDuffColorFilter(color, PorterDuff.Mode.SRC_OVER));
+            lp.dimPaint.setColorFilter(new android.graphics.PorterDuffColorFilter(
+                    color, PorterDuff.Mode.SRC_OVER));
             if (v.getLayerType() != View.LAYER_TYPE_HARDWARE) {
                 v.setLayerType(View.LAYER_TYPE_HARDWARE, lp.dimPaint);
             }
diff --git a/swiperefreshlayout/src/main/java/androidx/swiperefreshlayout/widget/CircularProgressDrawable.java b/swiperefreshlayout/src/main/java/androidx/swiperefreshlayout/widget/CircularProgressDrawable.java
index d397f84..1aeeeb9 100644
--- a/swiperefreshlayout/src/main/java/androidx/swiperefreshlayout/widget/CircularProgressDrawable.java
+++ b/swiperefreshlayout/src/main/java/androidx/swiperefreshlayout/widget/CircularProgressDrawable.java
@@ -429,6 +429,8 @@
     }
 
     @Override
+    @SuppressWarnings("deprecation")
+    // Remove suppression was b/120985527 is addressed.
     public int getOpacity() {
         return PixelFormat.TRANSLUCENT;
     }
diff --git a/transition/src/main/java/androidx/transition/CanvasUtils.java b/transition/src/main/java/androidx/transition/CanvasUtils.java
index 4e6ac36..d3f872b 100644
--- a/transition/src/main/java/androidx/transition/CanvasUtils.java
+++ b/transition/src/main/java/androidx/transition/CanvasUtils.java
@@ -16,10 +16,12 @@
 
 package androidx.transition;
 
+import android.annotation.SuppressLint;
 import android.graphics.Canvas;
 import android.os.Build;
 
 import androidx.annotation.NonNull;
+import androidx.core.os.BuildCompat;
 
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
@@ -35,10 +37,18 @@
      *
      * IMPORTANT: This method doesn't work on Pie! It will thrown an exception instead
      */
+    @SuppressLint("NewApi") // TODO: Remove this suppression once Q SDK is released.
     static void enableZ(@NonNull Canvas canvas, boolean enable) {
         if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
             // no shadows yet added into a platform
-        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
+        } else if (BuildCompat.isAtLeastQ()) {
+            if (enable) {
+                canvas.enableZ();
+            } else {
+                canvas.disableZ();
+            }
+        } else if (Build.VERSION.SDK_INT == Build.VERSION_CODES.P) {
+            // not on P's greylist, can't use reflection
             throw new IllegalStateException("This method doesn't work on Pie!");
         } else {
             if (!sOrderMethodsFetched) {
diff --git a/transition/src/main/java/androidx/transition/GhostViewUtils.java b/transition/src/main/java/androidx/transition/GhostViewUtils.java
index ed202ec..422517a 100644
--- a/transition/src/main/java/androidx/transition/GhostViewUtils.java
+++ b/transition/src/main/java/androidx/transition/GhostViewUtils.java
@@ -23,13 +23,16 @@
 
 import androidx.annotation.NonNull;
 import androidx.annotation.Nullable;
+import androidx.core.os.BuildCompat;
 
 class GhostViewUtils {
 
     @Nullable
     static GhostView addGhost(@NonNull View view, @NonNull ViewGroup viewGroup,
             @Nullable Matrix matrix) {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
+        if (!BuildCompat.isAtLeastQ() && // TODO we need this check as Q has the same number as P
+                Build.VERSION.SDK_INT == Build.VERSION_CODES.P) {
+            // Use the platform implementation on P as we can't backport the shadows drawing.
             return GhostViewPlatform.addGhost(view, viewGroup, matrix);
         } else {
             return GhostViewPort.addGhost(view, viewGroup, matrix);
@@ -37,7 +40,9 @@
     }
 
     static void removeGhost(View view) {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
+        if (!BuildCompat.isAtLeastQ() && // TODO we need this check as Q has the same number as P
+                Build.VERSION.SDK_INT == Build.VERSION_CODES.P) {
+            // Use the platform implementation on P as we can't backport the shadows drawing.
             GhostViewPlatform.removeGhost(view);
         } else {
             GhostViewPort.removeGhost(view);
diff --git a/transition/src/main/java/androidx/transition/ImageViewUtils.java b/transition/src/main/java/androidx/transition/ImageViewUtils.java
index 9559c75..f21acc3 100644
--- a/transition/src/main/java/androidx/transition/ImageViewUtils.java
+++ b/transition/src/main/java/androidx/transition/ImageViewUtils.java
@@ -16,21 +16,25 @@
 
 package androidx.transition;
 
+import android.annotation.SuppressLint;
 import android.graphics.Matrix;
 import android.graphics.drawable.Drawable;
 import android.os.Build;
-import android.util.Log;
 import android.widget.ImageView;
 
+import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
+import androidx.annotation.RequiresApi;
+import androidx.core.os.BuildCompat;
+
 import java.lang.reflect.Field;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
 
 class ImageViewUtils {
-    private static final String TAG = "ImageViewUtils";
 
-    private static Method sAnimateTransformMethod;
-    private static boolean sAnimateTransformMethodFetched;
+    /**
+     * False when linking of the hidden animateTransform method has previously failed.
+     */
+    private static boolean sTryHiddenAnimateTransform = true;
 
     private static Field sDrawMatrixField;
     private static boolean sDrawMatrixFieldFetched;
@@ -38,10 +42,13 @@
     /**
      * Sets the matrix to animate the content of the image view.
      */
-    static void animateTransform(ImageView view, Matrix matrix) {
-        if (matrix == null) {
-            // There is a bug in ImageView.animateTransform() prior to the current development
-            // version of Android so paddings are ignored when matrix is null.
+    @SuppressLint("NewApi") // TODO: Remove this suppression once Q SDK is released.
+    static void animateTransform(@NonNull ImageView view, @Nullable Matrix matrix) {
+        if (BuildCompat.isAtLeastQ()) {
+            view.animateTransform(matrix);
+        } else if (matrix == null) {
+            // There is a bug in ImageView.animateTransform() prior to Q so paddings are
+            // ignored when matrix is null.
             Drawable drawable = view.getDrawable();
             if (drawable != null) {
                 int vwidth = view.getWidth() - view.getPaddingLeft() - view.getPaddingRight();
@@ -50,16 +57,7 @@
                 view.invalidate();
             }
         } else if (Build.VERSION.SDK_INT >= 21) {
-            fetchAnimateTransformMethod();
-            if (sAnimateTransformMethod != null) {
-                try {
-                    sAnimateTransformMethod.invoke(view, matrix);
-                } catch (IllegalAccessException e) {
-                    // Do nothing
-                } catch (InvocationTargetException e) {
-                    throw new RuntimeException(e.getCause());
-                }
-            }
+            hiddenAnimateTransform(view, matrix);
         } else {
             Drawable drawable = view.getDrawable();
             if (drawable != null) {
@@ -86,16 +84,17 @@
         }
     }
 
-    private static void fetchAnimateTransformMethod() {
-        if (!sAnimateTransformMethodFetched) {
+    @RequiresApi(21)
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
+    private static void hiddenAnimateTransform(@NonNull ImageView view, @Nullable Matrix matrix) {
+        if (sTryHiddenAnimateTransform) {
+            // Since this was an @hide method made public, we can link directly against it with
+            // a try/catch for its absence instead of doing the same through reflection.
             try {
-                sAnimateTransformMethod = ImageView.class.getDeclaredMethod("animateTransform",
-                        Matrix.class);
-                sAnimateTransformMethod.setAccessible(true);
-            } catch (NoSuchMethodException e) {
-                Log.i(TAG, "Failed to retrieve animateTransform method", e);
+                view.animateTransform(matrix);
+            } catch (NoSuchMethodError e) {
+                sTryHiddenAnimateTransform = false;
             }
-            sAnimateTransformMethodFetched = true;
         }
     }
 
diff --git a/transition/src/main/java/androidx/transition/ViewGroupUtils.java b/transition/src/main/java/androidx/transition/ViewGroupUtils.java
index 566c0cb..f27b1f8a 100644
--- a/transition/src/main/java/androidx/transition/ViewGroupUtils.java
+++ b/transition/src/main/java/androidx/transition/ViewGroupUtils.java
@@ -16,10 +16,13 @@
 
 package androidx.transition;
 
+import android.annotation.SuppressLint;
 import android.os.Build;
 import android.view.ViewGroup;
 
 import androidx.annotation.NonNull;
+import androidx.annotation.RequiresApi;
+import androidx.core.os.BuildCompat;
 
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
@@ -29,6 +32,11 @@
  */
 class ViewGroupUtils {
 
+    /**
+     * False when linking of the hidden suppressLayout method has previously failed.
+     */
+    private static boolean sTryHiddenSuppressLayout = true;
+
     private static Method sGetChildDrawingOrderMethod;
     private static boolean sGetChildDrawingOrderMethodFetched;
 
@@ -45,38 +53,60 @@
     /**
      * Provides access to the hidden ViewGroup#suppressLayout method.
      */
+    @SuppressLint("NewApi") // TODO: Remove this suppression once Q SDK is released.
     static void suppressLayout(@NonNull ViewGroup group, boolean suppress) {
-        if (Build.VERSION.SDK_INT >= 18) {
-            ViewGroupUtilsApi18.suppressLayout(group, suppress);
+        if (BuildCompat.isAtLeastQ()) {
+            group.suppressLayout(suppress);
+        } else if (Build.VERSION.SDK_INT >= 18) {
+            hiddenSuppressLayout(group, suppress);
         } else {
             ViewGroupUtilsApi14.suppressLayout(group, suppress);
         }
     }
 
+    @RequiresApi(18)
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
+    private static void hiddenSuppressLayout(@NonNull ViewGroup group, boolean suppress) {
+        if (sTryHiddenSuppressLayout) {
+            // Since this was an @hide method made public, we can link directly against it with
+            // a try/catch for its absence instead of doing the same through reflection.
+            try {
+                group.suppressLayout(suppress);
+            } catch (NoSuchMethodError e) {
+                sTryHiddenSuppressLayout = false;
+            }
+        }
+    }
+
     /**
      * Returns the index of the child to draw for this iteration.
      */
+    @SuppressLint("NewApi") // TODO: Remove this suppression once Q SDK is released.
     static int getChildDrawingOrder(@NonNull ViewGroup viewGroup, int i) {
-        if (!sGetChildDrawingOrderMethodFetched) {
-            try {
-                sGetChildDrawingOrderMethod = ViewGroup.class.getDeclaredMethod(
-                        "getChildDrawingOrder", int.class, int.class);
-                sGetChildDrawingOrderMethod.setAccessible(true);
-            } catch (NoSuchMethodException ignore) {
+        if (BuildCompat.isAtLeastQ()) {
+            return viewGroup.getChildDrawingOrder(i);
+        } else {
+            if (!sGetChildDrawingOrderMethodFetched) {
+                try {
+                    sGetChildDrawingOrderMethod = ViewGroup.class.getDeclaredMethod(
+                            "getChildDrawingOrder", int.class, int.class);
+                    sGetChildDrawingOrderMethod.setAccessible(true);
+                } catch (NoSuchMethodException ignore) {
 
+                }
+                sGetChildDrawingOrderMethodFetched = true;
             }
-            sGetChildDrawingOrderMethodFetched = true;
-        }
-        if (sGetChildDrawingOrderMethod != null) {
-            try {
-                return (Integer) sGetChildDrawingOrderMethod.invoke(viewGroup,
-                        viewGroup.getChildCount(), i);
-            } catch (IllegalAccessException ignore) {
-            } catch (InvocationTargetException ignore) {
+            if (sGetChildDrawingOrderMethod != null) {
+                try {
+                    return (Integer) sGetChildDrawingOrderMethod.invoke(viewGroup,
+                            viewGroup.getChildCount(), i);
+                } catch (IllegalAccessException ignore) {
+                } catch (InvocationTargetException ignore) {
+                }
             }
+            // fallback implementation
+            return i;
         }
-        // fallback implementation
-        return i;
     }
 
 
diff --git a/transition/src/main/java/androidx/transition/ViewGroupUtilsApi18.java b/transition/src/main/java/androidx/transition/ViewGroupUtilsApi18.java
deleted file mode 100644
index e4d4ffa..0000000
--- a/transition/src/main/java/androidx/transition/ViewGroupUtilsApi18.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package androidx.transition;
-
-import android.util.Log;
-import android.view.ViewGroup;
-
-import androidx.annotation.NonNull;
-import androidx.annotation.RequiresApi;
-
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-
-@RequiresApi(18)
-class ViewGroupUtilsApi18 {
-
-    private static final String TAG = "ViewUtilsApi18";
-
-    private static Method sSuppressLayoutMethod;
-    private static boolean sSuppressLayoutMethodFetched;
-
-    static void suppressLayout(@NonNull ViewGroup group, boolean suppress) {
-        fetchSuppressLayoutMethod();
-        if (sSuppressLayoutMethod != null) {
-            try {
-                sSuppressLayoutMethod.invoke(group, suppress);
-            } catch (IllegalAccessException e) {
-                Log.i(TAG, "Failed to invoke suppressLayout method", e);
-            } catch (InvocationTargetException e) {
-                Log.i(TAG, "Error invoking suppressLayout method", e);
-            }
-        }
-    }
-
-    private static void fetchSuppressLayoutMethod() {
-        if (!sSuppressLayoutMethodFetched) {
-            try {
-                sSuppressLayoutMethod = ViewGroup.class.getDeclaredMethod("suppressLayout",
-                        boolean.class);
-                sSuppressLayoutMethod.setAccessible(true);
-            } catch (NoSuchMethodException e) {
-                Log.i(TAG, "Failed to retrieve suppressLayout method", e);
-            }
-            sSuppressLayoutMethodFetched = true;
-        }
-    }
-
-    private ViewGroupUtilsApi18() {
-    }
-}
diff --git a/transition/src/main/java/androidx/transition/ViewUtils.java b/transition/src/main/java/androidx/transition/ViewUtils.java
index d770ab6..df3f919 100644
--- a/transition/src/main/java/androidx/transition/ViewUtils.java
+++ b/transition/src/main/java/androidx/transition/ViewUtils.java
@@ -16,19 +16,18 @@
 
 package androidx.transition;
 
+import android.annotation.SuppressLint;
 import android.graphics.Matrix;
 import android.graphics.Rect;
 import android.os.Build;
-import android.util.Log;
 import android.util.Property;
 import android.view.View;
 
 import androidx.annotation.NonNull;
 import androidx.annotation.Nullable;
+import androidx.core.os.BuildCompat;
 import androidx.core.view.ViewCompat;
 
-import java.lang.reflect.Field;
-
 /**
  * Compatibility utilities for platform features of {@link View}.
  */
@@ -37,16 +36,18 @@
     private static final ViewUtilsBase IMPL;
     private static final String TAG = "ViewUtils";
 
-    private static Field sViewFlagsField;
-    private static boolean sViewFlagsFieldFetched;
-    private static final int VISIBILITY_MASK = 0x0000000C;
-
     static {
-        if (Build.VERSION.SDK_INT >= 22) {
+        if (BuildCompat.isAtLeastQ()) {
+            // TODO: replace with 'new ViewUtilsApi29()' when we can use an SDK_INT check as lint
+            //       doesn't understand BuildCompat API checks
+            IMPL = createViewUtilsApi29();
+        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
+            IMPL = new ViewUtilsApi23();
+        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP_MR1) {
             IMPL = new ViewUtilsApi22();
-        } else if (Build.VERSION.SDK_INT >= 21) {
+        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
             IMPL = new ViewUtilsApi21();
-        } else if (Build.VERSION.SDK_INT >= 19) {
+        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
             IMPL = new ViewUtilsApi19();
         } else {
             IMPL = new ViewUtilsBase();
@@ -145,15 +146,7 @@
      *                   {@link View#GONE}.
      */
     static void setTransitionVisibility(@NonNull View view, int visibility) {
-        fetchViewFlagsField();
-        if (sViewFlagsField != null) {
-            try {
-                int viewFlags = sViewFlagsField.getInt(view);
-                sViewFlagsField.setInt(view, (viewFlags & ~VISIBILITY_MASK) | visibility);
-            } catch (IllegalAccessException e) {
-                // Do nothing
-            }
-        }
+        IMPL.setTransitionVisibility(view, visibility);
     }
 
     /**
@@ -210,16 +203,10 @@
         IMPL.setLeftTopRightBottom(v, left, top, right, bottom);
     }
 
-    private static void fetchViewFlagsField() {
-        if (!sViewFlagsFieldFetched) {
-            try {
-                sViewFlagsField = View.class.getDeclaredField("mViewFlags");
-                sViewFlagsField.setAccessible(true);
-            } catch (NoSuchFieldException e) {
-                Log.i(TAG, "fetchViewFlagsField: ");
-            }
-            sViewFlagsFieldFetched = true;
-        }
+    // TODO: delete when we use an SDK_INT check as lint doesn't understand BuildCompat API checks
+    @SuppressLint("NewApi")
+    private static ViewUtilsApi29 createViewUtilsApi29() {
+        return new ViewUtilsApi29();
     }
 
     private ViewUtils() {
diff --git a/transition/src/main/java/androidx/transition/ViewUtilsApi19.java b/transition/src/main/java/androidx/transition/ViewUtilsApi19.java
index ff604319..b5a2547 100644
--- a/transition/src/main/java/androidx/transition/ViewUtilsApi19.java
+++ b/transition/src/main/java/androidx/transition/ViewUtilsApi19.java
@@ -16,54 +16,49 @@
 
 package androidx.transition;
 
-import android.util.Log;
+import android.annotation.SuppressLint;
 import android.view.View;
 
 import androidx.annotation.NonNull;
 import androidx.annotation.RequiresApi;
 
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-
 @RequiresApi(19)
 class ViewUtilsApi19 extends ViewUtilsBase {
 
-    private static final String TAG = "ViewUtilsApi19";
-
-    private static Method sSetTransitionAlphaMethod;
-    private static boolean sSetTransitionAlphaMethodFetched;
-    private static Method sGetTransitionAlphaMethod;
-    private static boolean sGetTransitionAlphaMethodFetched;
+    /**
+     * False when linking of the hidden set[get]TransitionAlpha method has previously failed.
+     */
+    private static boolean sTryHiddenTransitionAlpha = true;
 
     @Override
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
     public void setTransitionAlpha(@NonNull View view, float alpha) {
-        fetchSetTransitionAlphaMethod();
-        if (sSetTransitionAlphaMethod != null) {
+        if (sTryHiddenTransitionAlpha) {
+            // Since this was an @hide method made public, we can link directly against it with
+            // a try/catch for its absence instead of doing the same through reflection.
             try {
-                sSetTransitionAlphaMethod.invoke(view, alpha);
-            } catch (IllegalAccessException e) {
-                // Do nothing
-            } catch (InvocationTargetException e) {
-                throw new RuntimeException(e.getCause());
+                view.setTransitionAlpha(alpha);
+                return;
+            } catch (NoSuchMethodError e) {
+                sTryHiddenTransitionAlpha = false;
             }
-        } else {
-            view.setAlpha(alpha);
         }
+        view.setAlpha(alpha);
     }
 
     @Override
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
     public float getTransitionAlpha(@NonNull View view) {
-        fetchGetTransitionAlphaMethod();
-        if (sGetTransitionAlphaMethod != null) {
+        if (sTryHiddenTransitionAlpha) {
+            // Since this was an @hide method made public, we can link directly against it with
+            // a try/catch for its absence instead of doing the same through reflection.
             try {
-                return (Float) sGetTransitionAlphaMethod.invoke(view);
-            } catch (IllegalAccessException e) {
-                // Do nothing
-            } catch (InvocationTargetException e) {
-                throw new RuntimeException(e.getCause());
+                return view.getTransitionAlpha();
+            } catch (NoSuchMethodError e) {
+                sTryHiddenTransitionAlpha = false;
             }
         }
-        return super.getTransitionAlpha(view);
+        return view.getAlpha();
     }
 
     @Override
@@ -76,29 +71,4 @@
         // Do nothing
     }
 
-    private void fetchSetTransitionAlphaMethod() {
-        if (!sSetTransitionAlphaMethodFetched) {
-            try {
-                sSetTransitionAlphaMethod = View.class.getDeclaredMethod("setTransitionAlpha",
-                        float.class);
-                sSetTransitionAlphaMethod.setAccessible(true);
-            } catch (NoSuchMethodException e) {
-                Log.i(TAG, "Failed to retrieve setTransitionAlpha method", e);
-            }
-            sSetTransitionAlphaMethodFetched = true;
-        }
-    }
-
-    private void fetchGetTransitionAlphaMethod() {
-        if (!sGetTransitionAlphaMethodFetched) {
-            try {
-                sGetTransitionAlphaMethod = View.class.getDeclaredMethod("getTransitionAlpha");
-                sGetTransitionAlphaMethod.setAccessible(true);
-            } catch (NoSuchMethodException e) {
-                Log.i(TAG, "Failed to retrieve getTransitionAlpha method", e);
-            }
-            sGetTransitionAlphaMethodFetched = true;
-        }
-    }
-
 }
diff --git a/transition/src/main/java/androidx/transition/ViewUtilsApi21.java b/transition/src/main/java/androidx/transition/ViewUtilsApi21.java
index 14301d2..c5a8900 100644
--- a/transition/src/main/java/androidx/transition/ViewUtilsApi21.java
+++ b/transition/src/main/java/androidx/transition/ViewUtilsApi21.java
@@ -16,107 +16,70 @@
 
 package androidx.transition;
 
+import android.annotation.SuppressLint;
 import android.graphics.Matrix;
-import android.util.Log;
 import android.view.View;
 
 import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
 import androidx.annotation.RequiresApi;
 
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-
 @RequiresApi(21)
 class ViewUtilsApi21 extends ViewUtilsApi19 {
 
-    private static final String TAG = "ViewUtilsApi21";
-
-    private static Method sTransformMatrixToGlobalMethod;
-    private static boolean sTransformMatrixToGlobalMethodFetched;
-    private static Method sTransformMatrixToLocalMethod;
-    private static boolean sTransformMatrixToLocalMethodFetched;
-    private static Method sSetAnimationMatrixMethod;
-    private static boolean sSetAnimationMatrixMethodFetched;
+    /**
+     * False when linking of the hidden setAnimationMatrix method has previously failed.
+     */
+    private static boolean sTryHiddenSetAnimationMatrix = true;
+    /**
+     * False when linking of the hidden transformMatrixToGlobal method has previously failed.
+     */
+    private static boolean sTryHiddenTransformMatrixToGlobal = true;
+    /**
+     * False when linking of the hidden transformMatrixToLocal method has previously failed.
+     */
+    private static boolean sTryHiddenTransformMatrixToLocal = true;
 
     @Override
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
     public void transformMatrixToGlobal(@NonNull View view, @NonNull Matrix matrix) {
-        fetchTransformMatrixToGlobalMethod();
-        if (sTransformMatrixToGlobalMethod != null) {
+        if (sTryHiddenTransformMatrixToGlobal) {
+            // Since this was an @hide method made public, we can link directly against it with
+            // a try/catch for its absence instead of doing the same through reflection.
             try {
-                sTransformMatrixToGlobalMethod.invoke(view, matrix);
-            } catch (IllegalAccessException e) {
-                // Do nothing
-            } catch (InvocationTargetException e) {
-                throw new RuntimeException(e.getCause());
+                view.transformMatrixToGlobal(matrix);
+            } catch (NoSuchMethodError e) {
+                sTryHiddenTransformMatrixToGlobal = false;
             }
         }
     }
 
     @Override
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
     public void transformMatrixToLocal(@NonNull View view, @NonNull Matrix matrix) {
-        fetchTransformMatrixToLocalMethod();
-        if (sTransformMatrixToLocalMethod != null) {
+        if (sTryHiddenTransformMatrixToLocal) {
+            // Since this was an @hide method made public, we can link directly against it with
+            // a try/catch for its absence instead of doing the same through reflection.
             try {
-                sTransformMatrixToLocalMethod.invoke(view, matrix);
-            } catch (IllegalAccessException e) {
-                // Do nothing
-            } catch (InvocationTargetException e) {
-                throw new RuntimeException(e.getCause());
+                view.transformMatrixToLocal(matrix);
+            } catch (NoSuchMethodError e) {
+                sTryHiddenTransformMatrixToLocal = false;
             }
         }
     }
 
     @Override
-    public void setAnimationMatrix(@NonNull View view, Matrix matrix) {
-        fetchSetAnimationMatrix();
-        if (sSetAnimationMatrixMethod != null) {
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
+    public void setAnimationMatrix(@NonNull View view, @Nullable Matrix matrix) {
+        if (sTryHiddenSetAnimationMatrix) {
+            // Since this was an @hide method made public, we can link directly against it with
+            // a try/catch for its absence instead of doing the same through reflection.
             try {
-                sSetAnimationMatrixMethod.invoke(view, matrix);
-            } catch (InvocationTargetException e) {
-                // Do nothing
-            } catch (IllegalAccessException e) {
-                throw new RuntimeException(e.getCause());
+                view.setAnimationMatrix(matrix);
+            } catch (NoSuchMethodError e) {
+                sTryHiddenSetAnimationMatrix = false;
             }
         }
     }
 
-    private void fetchTransformMatrixToGlobalMethod() {
-        if (!sTransformMatrixToGlobalMethodFetched) {
-            try {
-                sTransformMatrixToGlobalMethod = View.class.getDeclaredMethod(
-                        "transformMatrixToGlobal", Matrix.class);
-                sTransformMatrixToGlobalMethod.setAccessible(true);
-            } catch (NoSuchMethodException e) {
-                Log.i(TAG, "Failed to retrieve transformMatrixToGlobal method", e);
-            }
-            sTransformMatrixToGlobalMethodFetched = true;
-        }
-    }
-
-    private void fetchTransformMatrixToLocalMethod() {
-        if (!sTransformMatrixToLocalMethodFetched) {
-            try {
-                sTransformMatrixToLocalMethod = View.class.getDeclaredMethod(
-                        "transformMatrixToLocal", Matrix.class);
-                sTransformMatrixToLocalMethod.setAccessible(true);
-            } catch (NoSuchMethodException e) {
-                Log.i(TAG, "Failed to retrieve transformMatrixToLocal method", e);
-            }
-            sTransformMatrixToLocalMethodFetched = true;
-        }
-    }
-
-    private void fetchSetAnimationMatrix() {
-        if (!sSetAnimationMatrixMethodFetched) {
-            try {
-                sSetAnimationMatrixMethod = View.class.getDeclaredMethod(
-                        "setAnimationMatrix", Matrix.class);
-                sSetAnimationMatrixMethod.setAccessible(true);
-            } catch (NoSuchMethodException e) {
-                Log.i(TAG, "Failed to retrieve setAnimationMatrix method", e);
-            }
-            sSetAnimationMatrixMethodFetched = true;
-        }
-    }
-
 }
diff --git a/transition/src/main/java/androidx/transition/ViewUtilsApi22.java b/transition/src/main/java/androidx/transition/ViewUtilsApi22.java
index f8dd2a0..a251bbe 100644
--- a/transition/src/main/java/androidx/transition/ViewUtilsApi22.java
+++ b/transition/src/main/java/androidx/transition/ViewUtilsApi22.java
@@ -17,49 +17,31 @@
 package androidx.transition;
 
 import android.annotation.SuppressLint;
-import android.util.Log;
 import android.view.View;
 
+import androidx.annotation.NonNull;
 import androidx.annotation.RequiresApi;
 
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-
 @RequiresApi(22)
 class ViewUtilsApi22 extends ViewUtilsApi21 {
 
-    private static final String TAG = "ViewUtilsApi22";
-
-    private static Method sSetLeftTopRightBottomMethod;
-    private static boolean sSetLeftTopRightBottomMethodFetched;
+    /**
+     * False when linking of the hidden setLeftTopRightBottom method has previously failed.
+     */
+    private static boolean sTryHiddenSetLeftTopRightBottom = true;
 
     @Override
-    public void setLeftTopRightBottom(View v, int left, int top, int right, int bottom) {
-        fetchSetLeftTopRightBottomMethod();
-        if (sSetLeftTopRightBottomMethod != null) {
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
+    public void setLeftTopRightBottom(@NonNull View v, int left, int top, int right, int bottom) {
+        if (sTryHiddenSetLeftTopRightBottom) {
+            // Since this was an @hide method made public, we can link directly against it with
+            // a try/catch for its absence instead of doing the same through reflection.
             try {
-                sSetLeftTopRightBottomMethod.invoke(v, left, top, right, bottom);
-            } catch (IllegalAccessException e) {
-                // Do nothing
-            } catch (InvocationTargetException e) {
-                throw new RuntimeException(e.getCause());
+                v.setLeftTopRightBottom(left, top, right, bottom);
+            } catch (NoSuchMethodError e) {
+                sTryHiddenSetLeftTopRightBottom = false;
             }
         }
     }
-
-    @SuppressLint("PrivateApi")
-    private void fetchSetLeftTopRightBottomMethod() {
-        if (!sSetLeftTopRightBottomMethodFetched) {
-            try {
-                sSetLeftTopRightBottomMethod = View.class.getDeclaredMethod("setLeftTopRightBottom",
-                        int.class, int.class, int.class, int.class);
-                sSetLeftTopRightBottomMethod.setAccessible(true);
-            } catch (NoSuchMethodException e) {
-                Log.i(TAG, "Failed to retrieve setLeftTopRightBottom method", e);
-            }
-            sSetLeftTopRightBottomMethodFetched = true;
-        }
-    }
-
 }
 
diff --git a/transition/src/main/java/androidx/transition/ViewUtilsApi23.java b/transition/src/main/java/androidx/transition/ViewUtilsApi23.java
new file mode 100644
index 0000000..a089f2f
--- /dev/null
+++ b/transition/src/main/java/androidx/transition/ViewUtilsApi23.java
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package androidx.transition;
+
+import android.annotation.SuppressLint;
+import android.os.Build;
+import android.view.View;
+
+import androidx.annotation.NonNull;
+import androidx.annotation.RequiresApi;
+
+@RequiresApi(23)
+class ViewUtilsApi23 extends ViewUtilsApi22 {
+
+    /**
+     * False when linking of the hidden setLeftTopRightBottom method has previously failed.
+     */
+    private static boolean sTryHiddenSetTransitionVisibility = true;
+
+    @Override
+    @SuppressLint("NewApi") // Lint doesn't know about the hidden method.
+    public void setTransitionVisibility(@NonNull View view, int visibility) {
+        // on P this method is blacklisted, so we have to resort to reflecting on mViewFlags
+        if (Build.VERSION.SDK_INT == Build.VERSION_CODES.P) {
+            super.setTransitionVisibility(view, visibility);
+        } else {
+            if (sTryHiddenSetTransitionVisibility) {
+                // Since this was an @hide method made public, we can link directly against it with
+                // a try/catch for its absence instead of doing the same through reflection.
+                try {
+                    view.setTransitionVisibility(visibility);
+                } catch (NoSuchMethodError e) {
+                    sTryHiddenSetTransitionVisibility = false;
+                }
+            }
+        }
+    }
+}
+
diff --git a/transition/src/main/java/androidx/transition/ViewUtilsApi29.java b/transition/src/main/java/androidx/transition/ViewUtilsApi29.java
new file mode 100644
index 0000000..be835de5
--- /dev/null
+++ b/transition/src/main/java/androidx/transition/ViewUtilsApi29.java
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package androidx.transition;
+
+import android.graphics.Matrix;
+import android.view.View;
+
+import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
+import androidx.annotation.RequiresApi;
+
+@RequiresApi(29)
+class ViewUtilsApi29 extends ViewUtilsApi23 {
+
+    @Override
+    public void setTransitionAlpha(@NonNull View view, float alpha) {
+        view.setTransitionAlpha(alpha);
+    }
+
+    @Override
+    public float getTransitionAlpha(@NonNull View view) {
+        return view.getTransitionAlpha();
+    }
+
+    @Override
+    public void setTransitionVisibility(@NonNull View view, int visibility) {
+        view.setTransitionVisibility(visibility);
+    }
+
+    @Override
+    public void setLeftTopRightBottom(@NonNull View v, int left, int top, int right, int bottom) {
+        v.setLeftTopRightBottom(left, top, right, bottom);
+    }
+
+    @Override
+    public void transformMatrixToGlobal(@NonNull View view, @NonNull Matrix matrix) {
+        view.transformMatrixToGlobal(matrix);
+    }
+
+    @Override
+    public void transformMatrixToLocal(@NonNull View view, @NonNull Matrix matrix) {
+        view.transformMatrixToLocal(matrix);
+    }
+
+    @Override
+    public void setAnimationMatrix(@NonNull View view, @Nullable Matrix matrix) {
+        view.setAnimationMatrix(matrix);
+    }
+}
+
diff --git a/transition/src/main/java/androidx/transition/ViewUtilsBase.java b/transition/src/main/java/androidx/transition/ViewUtilsBase.java
index 87917dd..3c43422 100644
--- a/transition/src/main/java/androidx/transition/ViewUtilsBase.java
+++ b/transition/src/main/java/androidx/transition/ViewUtilsBase.java
@@ -23,7 +23,9 @@
 import android.view.ViewParent;
 
 import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
 
+import java.lang.reflect.Field;
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
 
@@ -34,6 +36,10 @@
     private static Method sSetFrameMethod;
     private static boolean sSetFrameFetched;
 
+    private static Field sViewFlagsField;
+    private static boolean sViewFlagsFieldFetched;
+    private static final int VISIBILITY_MASK = 0x0000000C;
+
     private float[] mMatrixValues;
 
     public void setTransitionAlpha(@NonNull View view, float alpha) {
@@ -99,7 +105,7 @@
         }
     }
 
-    public void setAnimationMatrix(@NonNull View view, Matrix matrix) {
+    public void setAnimationMatrix(@NonNull View view, @Nullable Matrix matrix) {
         if (matrix == null || matrix.isIdentity()) {
             view.setPivotX(view.getWidth() / 2);
             view.setPivotY(view.getHeight() / 2);
@@ -132,7 +138,7 @@
         }
     }
 
-    public void setLeftTopRightBottom(View v, int left, int top, int right, int bottom) {
+    public void setLeftTopRightBottom(@NonNull View v, int left, int top, int right, int bottom) {
         fetchSetFrame();
         if (sSetFrameMethod != null) {
             try {
@@ -145,6 +151,26 @@
         }
     }
 
+    public void setTransitionVisibility(@NonNull View view, int visibility) {
+        if (!sViewFlagsFieldFetched) {
+            try {
+                sViewFlagsField = View.class.getDeclaredField("mViewFlags");
+                sViewFlagsField.setAccessible(true);
+            } catch (NoSuchFieldException e) {
+                Log.i(TAG, "fetchViewFlagsField: ");
+            }
+            sViewFlagsFieldFetched = true;
+        }
+        if (sViewFlagsField != null) {
+            try {
+                int viewFlags = sViewFlagsField.getInt(view);
+                sViewFlagsField.setInt(view, (viewFlags & ~VISIBILITY_MASK) | visibility);
+            } catch (IllegalAccessException e) {
+                // Do nothing
+            }
+        }
+    }
+
     @SuppressLint("PrivateApi")
     private void fetchSetFrame() {
         if (!sSetFrameFetched) {
diff --git a/viewpager2/src/androidTest/java/androidx/viewpager2/widget/BaseTest.kt b/viewpager2/src/androidTest/java/androidx/viewpager2/widget/BaseTest.kt
index 9b308b1..2d6fb72 100644
--- a/viewpager2/src/androidTest/java/androidx/viewpager2/widget/BaseTest.kt
+++ b/viewpager2/src/androidTest/java/androidx/viewpager2/widget/BaseTest.kt
@@ -21,6 +21,11 @@
 import android.view.View
 import android.view.View.OVER_SCROLL_NEVER
 import androidx.core.view.ViewCompat
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_RIGHT
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_LEFT
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_UP
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_DOWN
 import androidx.recyclerview.widget.LinearLayoutManager
 import androidx.recyclerview.widget.RecyclerView
 import androidx.test.core.app.ApplicationProvider
@@ -221,6 +226,58 @@
                     )
                 )
         }
+
+        fun assertPageActions() {
+            var actions = getActionList(viewPager)
+            var currentPage = viewPager.currentItem
+            var numPages = viewPager.adapter!!.itemCount
+            var isUserInputEnabled = viewPager.isUserInputEnabled
+            var isHorizontalOrientation = viewPager.orientation == ViewPager2.ORIENTATION_HORIZONTAL
+            var isVerticalOrientation = viewPager.orientation == ViewPager2.ORIENTATION_VERTICAL
+
+            val expectPageLeftAction = isUserInputEnabled && isHorizontalOrientation &&
+                    (if (isRtl) currentPage < numPages - 1 else currentPage > 0)
+
+            val expectPageRightAction = isUserInputEnabled && isHorizontalOrientation &&
+                    (if (isRtl) currentPage > 0 else currentPage < numPages - 1)
+
+            val expectPageUpAction = isUserInputEnabled && isVerticalOrientation &&
+                    currentPage > 0
+
+            val expectPageDownAction = isUserInputEnabled && isVerticalOrientation &&
+                    currentPage < numPages - 1
+
+            assertThat("Left action expected: $expectPageLeftAction",
+                hasPageAction(actions, ACTION_PAGE_LEFT.id),
+                equalTo(expectPageLeftAction)
+            )
+
+            assertThat("Right action expected: $expectPageRightAction",
+                hasPageAction(actions, ACTION_PAGE_RIGHT.id),
+                equalTo(expectPageRightAction)
+            )
+            assertThat("Up action expected: $expectPageUpAction",
+                hasPageAction(actions, ACTION_PAGE_UP.id),
+                equalTo(expectPageUpAction)
+            )
+            assertThat("Down action expected: $expectPageDownAction",
+                hasPageAction(actions, ACTION_PAGE_DOWN.id),
+                equalTo(expectPageDownAction)
+            )
+        }
+
+        private fun hasPageAction(
+            actions: List<AccessibilityNodeInfoCompat.AccessibilityActionCompat>,
+            accessibilityActionId: Int
+        ): Boolean {
+            return actions.any { it.id == accessibilityActionId }
+        }
+
+        private fun getActionList(view: View):
+                List<AccessibilityNodeInfoCompat.AccessibilityActionCompat> {
+            return view.getTag(R.id.tag_accessibility_actions) as?
+                    ArrayList<AccessibilityNodeInfoCompat.AccessibilityActionCompat> ?: ArrayList()
+        }
     }
 
     /**
@@ -346,6 +403,7 @@
         if (viewPager.adapter is SelfChecking) {
             (viewPager.adapter as SelfChecking).selfCheck()
         }
+        assertPageActions()
     }
 
     fun ViewPager2.setCurrentItemSync(
diff --git a/viewpager2/src/androidTest/java/androidx/viewpager2/widget/PageAccessibilityActionsTest.kt b/viewpager2/src/androidTest/java/androidx/viewpager2/widget/PageAccessibilityActionsTest.kt
new file mode 100644
index 0000000..cb3115b
--- /dev/null
+++ b/viewpager2/src/androidTest/java/androidx/viewpager2/widget/PageAccessibilityActionsTest.kt
@@ -0,0 +1,136 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package androidx.viewpager2.widget
+
+import androidx.core.view.ViewCompat
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_DOWN
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_LEFT
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_RIGHT
+import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_UP
+import androidx.test.filters.LargeTest
+import androidx.viewpager2.LocaleTestUtils
+import androidx.viewpager2.widget.ViewPager2.ORIENTATION_HORIZONTAL
+import androidx.viewpager2.widget.ViewPager2.ORIENTATION_VERTICAL
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.junit.runners.Parameterized
+import java.util.concurrent.TimeUnit
+
+@RunWith(Parameterized::class)
+@LargeTest
+class PageAccessibilityActionsTest(private val config: TestConfig) : BaseTest() {
+    data class TestConfig(
+        @ViewPager2.Orientation val orientation: Int,
+        val rtl: Boolean
+    )
+
+    companion object {
+        @JvmStatic
+        @Parameterized.Parameters(name = "{0}")
+        fun spec(): List<TestConfig> = createTestSet()
+    }
+
+    override fun setUp() {
+        super.setUp()
+        if (config.rtl) {
+            localeUtil.resetLocale()
+            localeUtil.setLocale(LocaleTestUtils.RTL_LANGUAGE)
+        }
+    }
+
+    @Test
+    fun test_onPerformPageAction_onHorizontalOrientation() {
+        setUpTest(config.orientation).apply {
+            setAdapterSync(viewAdapterProvider(stringSequence(6)))
+
+            val initialPage = viewPager.currentItem
+            assertBasicState(initialPage)
+
+            listOf(1, 2, 3, 2, 3, 2, 3, 4, 5, 4, 5, 4, 3, 2, 1, 0, 1).forEach {
+                    targetPage ->
+                val currentPage = viewPager.currentItem
+                val latch = viewPager.addWaitForScrolledLatch(targetPage)
+                if (targetPage - currentPage == 1) {
+                    ViewCompat.performAccessibilityAction(viewPager,
+                        getNextPageAction(config.orientation, isRtl), null)
+                } else {
+                    ViewCompat.performAccessibilityAction(viewPager,
+                        getPreviousPageAction(config.orientation, isRtl), null)
+                }
+                latch.await(1, TimeUnit.SECONDS)
+                assertBasicState(targetPage)
+            }
+        }
+    }
+
+    @Test
+    fun test_onOrientationChange() {
+        setUpTest(config.orientation).apply {
+            setAdapterSync(viewAdapterProvider(stringSequence(2)))
+
+            val initialPage = viewPager.currentItem
+            assertBasicState(initialPage)
+
+            activityTestRule.runOnUiThread {
+                viewPager.setOrientation(getOppositeOrientation(config.orientation))
+            }
+            assertBasicState(initialPage)
+        }
+    }
+
+    private fun getNextPageAction(orientation: Int, isRtl: Boolean): Int {
+        if (orientation == ViewPager2.ORIENTATION_HORIZONTAL) {
+            if (isRtl) {
+                return ACTION_PAGE_LEFT.id
+            } else {
+                return ACTION_PAGE_RIGHT.id
+            }
+        }
+        return ACTION_PAGE_DOWN.id
+    }
+
+    private fun getPreviousPageAction(orientation: Int, isRtl: Boolean): Int {
+        if (orientation == ViewPager2.ORIENTATION_HORIZONTAL) {
+            if (isRtl) {
+                return ACTION_PAGE_RIGHT.id
+            } else {
+                return ACTION_PAGE_LEFT.id
+            }
+        }
+        return ACTION_PAGE_UP.id
+    }
+
+    private fun getOppositeOrientation(orientation: Int): Int {
+        if (orientation == ViewPager2.ORIENTATION_HORIZONTAL) {
+            return ViewPager2.ORIENTATION_VERTICAL
+        } else {
+            return ViewPager2.ORIENTATION_HORIZONTAL
+        }
+    }
+}
+
+// region Test Suite creation
+
+private fun createTestSet(): List<PageAccessibilityActionsTest.TestConfig> {
+    return listOf(ORIENTATION_HORIZONTAL, ORIENTATION_VERTICAL).flatMap { orientation ->
+        listOf(true, false).map { rtl ->
+            PageAccessibilityActionsTest.TestConfig(orientation, rtl)
+        }
+    }
+}
+
+// endregion
diff --git a/viewpager2/src/main/java/androidx/viewpager2/widget/ScrollEventAdapter.java b/viewpager2/src/main/java/androidx/viewpager2/widget/ScrollEventAdapter.java
index 5eadede..04a5d6b 100644
--- a/viewpager2/src/main/java/androidx/viewpager2/widget/ScrollEventAdapter.java
+++ b/viewpager2/src/main/java/androidx/viewpager2/widget/ScrollEventAdapter.java
@@ -271,10 +271,7 @@
      * Let the adapter know that mCurrentItem was restored in onRestoreInstanceState
      */
     void notifyRestoreCurrentItem(int currentItem) {
-        // Don't send page selected event for page 0 for consistency with ViewPager
-        if (currentItem != 0) {
-            dispatchSelected(currentItem);
-        }
+        dispatchSelected(currentItem);
     }
 
     private boolean isLayoutRTL() {
diff --git a/viewpager2/src/main/java/androidx/viewpager2/widget/ViewPager2.java b/viewpager2/src/main/java/androidx/viewpager2/widget/ViewPager2.java
index 5c7fb00..89a237f 100644
--- a/viewpager2/src/main/java/androidx/viewpager2/widget/ViewPager2.java
+++ b/viewpager2/src/main/java/androidx/viewpager2/widget/ViewPager2.java
@@ -16,6 +16,11 @@
 
 package androidx.viewpager2.widget;
 
+import static androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_DOWN;
+import static androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_LEFT;
+import static androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_RIGHT;
+import static androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat.ACTION_PAGE_UP;
+
 import static java.lang.annotation.RetentionPolicy.SOURCE;
 
 import android.annotation.SuppressLint;
@@ -23,7 +28,6 @@
 import android.content.res.TypedArray;
 import android.graphics.Rect;
 import android.os.Build;
-import android.os.Bundle;
 import android.os.Parcel;
 import android.os.Parcelable;
 import android.util.AttributeSet;
@@ -41,7 +45,7 @@
 import androidx.annotation.RequiresApi;
 import androidx.core.view.ViewCompat;
 import androidx.core.view.accessibility.AccessibilityNodeInfoCompat;
-import androidx.core.view.accessibility.AccessibilityNodeInfoCompat.AccessibilityActionCompat;
+import androidx.core.view.accessibility.AccessibilityViewCommand;
 import androidx.recyclerview.widget.LinearLayoutManager;
 import androidx.recyclerview.widget.PagerSnapHelper;
 import androidx.recyclerview.widget.RecyclerView;
@@ -76,6 +80,26 @@
     public static final int SCROLL_STATE_DRAGGING = 1;
     public static final int SCROLL_STATE_SETTLING = 2;
 
+    private static final AccessibilityViewCommand ACTION_PAGE_FORWARD =
+            new AccessibilityViewCommand() {
+        @Override
+        public boolean perform(@NonNull View view, @Nullable CommandArguments arguments) {
+            ViewPager2 viewPager = (ViewPager2) view;
+            viewPager.setCurrentItem(viewPager.getCurrentItem() + 1, true);
+            return true;
+        }
+    };
+
+    private static final AccessibilityViewCommand ACTION_PAGE_BACKWARD =
+            new AccessibilityViewCommand() {
+        @Override
+        public boolean perform(@NonNull View view, @Nullable CommandArguments arguments) {
+            ViewPager2 viewPager = (ViewPager2) view;
+            viewPager.setCurrentItem(viewPager.getCurrentItem() - 1, true);
+            return true;
+        }
+    };
+
     // reused in layout(...)
     private final Rect mTmpContainerRect = new Rect();
     private final Rect mTmpChildRect = new Rect();
@@ -90,6 +114,7 @@
     private PageTransformerAdapter mPageTransformerAdapter;
     private CompositeOnPageChangeCallback mPageChangeEventDispatcher;
     private boolean mUserInputEnabled = true;
+    private RecyclerView.AdapterDataObserver mAdapterDataObserver;
 
     public ViewPager2(@NonNull Context context) {
         super(context);
@@ -116,8 +141,10 @@
     private void initialize(Context context, AttributeSet attrs) {
         mRecyclerView = new RecyclerViewImpl(context);
         mRecyclerView.setId(ViewCompat.generateViewId());
+        ViewCompat.setImportantForAccessibility(mRecyclerView,
+                ViewCompat.IMPORTANT_FOR_ACCESSIBILITY_NO);
 
-        mLayoutManager = new LinearLayoutManagerImpl(context);
+        mLayoutManager = new LinearLayoutManager(context);
         mRecyclerView.setLayoutManager(mLayoutManager);
         setOrientation(context, attrs);
 
@@ -132,12 +159,23 @@
         mPageChangeEventDispatcher = new CompositeOnPageChangeCallback(3);
         mScrollEventAdapter.setOnPageChangeCallback(mPageChangeEventDispatcher);
 
+        mAdapterDataObserver = new RecyclerView.AdapterDataObserver() {
+            @Override
+            public void onChanged() {
+                super.onChanged();
+                updatePageAccessibilityActions();
+            }
+        };
+
         // Callback that updates mCurrentItem after swipes. Also triggered in other cases, but in
         // all those cases mCurrentItem will only be overwritten with the same value.
         final OnPageChangeCallback currentItemUpdater = new OnPageChangeCallback() {
             @Override
             public void onPageSelected(int position) {
-                mCurrentItem = position;
+                if (mCurrentItem != position) {
+                    mCurrentItem = position;
+                    updatePageAccessibilityActions();
+                }
             }
         };
 
@@ -152,6 +190,12 @@
         mPageChangeEventDispatcher.addOnPageChangeCallback(mPageTransformerAdapter);
 
         attachViewToParent(mRecyclerView, 0, mRecyclerView.getLayoutParams());
+
+        if (ViewCompat.getImportantForAccessibility(this)
+                == ViewCompat.IMPORTANT_FOR_ACCESSIBILITY_AUTO) {
+            ViewCompat.setImportantForAccessibility(this,
+                    ViewCompat.IMPORTANT_FOR_ACCESSIBILITY_YES);
+        }
     }
 
     /**
@@ -179,6 +223,65 @@
         };
     }
 
+    @Override
+    public CharSequence getAccessibilityClassName() {
+        return "androidx.viewpager.widget.ViewPager";
+    }
+
+    /**
+     * Update the ViewPager2's available page accessibility actions. These are updated in response
+     * to page, adapter, and orientation changes.
+     */
+    void updatePageAccessibilityActions() {
+        ViewCompat.removeAccessibilityAction(this, ACTION_PAGE_LEFT.getId());
+        ViewCompat.removeAccessibilityAction(this, ACTION_PAGE_RIGHT.getId());
+        ViewCompat.removeAccessibilityAction(this, ACTION_PAGE_UP.getId());
+        ViewCompat.removeAccessibilityAction(this, ACTION_PAGE_DOWN.getId());
+
+        if (getAdapter() == null) {
+            return;
+        }
+
+        int itemCount = getAdapter().getItemCount();
+        if (itemCount == 0) {
+            return;
+        }
+
+        if (!isUserInputEnabled()) {
+            return;
+        }
+
+        if (getOrientation() == ORIENTATION_HORIZONTAL) {
+            boolean isLayoutRtl = isLayoutRtl();
+            AccessibilityNodeInfoCompat.AccessibilityActionCompat actionPageForward =
+                    isLayoutRtl ? ACTION_PAGE_LEFT : ACTION_PAGE_RIGHT;
+            AccessibilityNodeInfoCompat.AccessibilityActionCompat actionPageBackward =
+                    isLayoutRtl ? ACTION_PAGE_RIGHT : ACTION_PAGE_LEFT;
+
+            if (mCurrentItem < itemCount - 1) {
+                ViewCompat.replaceAccessibilityAction(this, actionPageForward, null,
+                        ACTION_PAGE_FORWARD);
+            }
+            if (mCurrentItem > 0) {
+                ViewCompat.replaceAccessibilityAction(this, actionPageBackward, null,
+                        ACTION_PAGE_BACKWARD);
+            }
+        } else {
+            if (mCurrentItem < itemCount - 1) {
+                ViewCompat.replaceAccessibilityAction(this, ACTION_PAGE_DOWN, null,
+                        ACTION_PAGE_FORWARD);
+            }
+            if (mCurrentItem > 0) {
+                ViewCompat.replaceAccessibilityAction(this, ACTION_PAGE_UP, null,
+                        ACTION_PAGE_BACKWARD);
+            }
+        }
+    }
+
+    private boolean isLayoutRtl() {
+        return ViewCompat.getLayoutDirection(this) == ViewCompat.LAYOUT_DIRECTION_RTL;
+    }
+
     private void setOrientation(Context context, AttributeSet attrs) {
         TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.ViewPager2);
         try {
@@ -221,7 +324,7 @@
         super.onRestoreInstanceState(ss.getSuperState());
         setOrientation(ss.mOrientation);
         mCurrentItem = ss.mCurrentItem;
-        mUserInputEnabled = ss.mUserScrollable;
+        setUserInputEnabled(ss.mUserScrollable);
         if (ss.mScrollInProgress) {
             // A scroll was in progress, so the RecyclerView is not at mCurrentItem right now. Move
             // it to mCurrentItem instantly in the _next_ frame, as RecyclerView is not yet fired up
@@ -334,7 +437,14 @@
      * @see RecyclerView#setAdapter(Adapter)
      */
     public void setAdapter(@Nullable Adapter adapter) {
+        Adapter oldAdapter = mRecyclerView.getAdapter();
+        if (oldAdapter != null) {
+            oldAdapter.unregisterAdapterDataObserver(mAdapterDataObserver);
+        }
+
         mRecyclerView.setAdapter(adapter);
+        updatePageAccessibilityActions();
+        adapter.registerAdapterDataObserver(mAdapterDataObserver);
     }
 
     public @Nullable Adapter getAdapter() {
@@ -392,6 +502,7 @@
      */
     public void setOrientation(@Orientation int orientation) {
         mLayoutManager.setOrientation(orientation);
+        updatePageAccessibilityActions();
     }
 
     public @Orientation int getOrientation() {
@@ -440,6 +551,7 @@
 
         float previousItem = mCurrentItem;
         mCurrentItem = item;
+        updatePageAccessibilityActions();
 
         if (!mScrollEventAdapter.isIdle()) {
             // Scroll in progress, overwrite previousItem with actual current position
@@ -484,6 +596,7 @@
      */
     public void setUserInputEnabled(boolean enabled) {
         mUserInputEnabled = enabled;
+        updatePageAccessibilityActions();
     }
 
     /**
@@ -531,6 +644,13 @@
         mPageTransformerAdapter.setPageTransformer(transformer);
     }
 
+    @Override
+    @RequiresApi(17)
+    public void setLayoutDirection(int layoutDirection) {
+        super.setLayoutDirection(layoutDirection);
+        updatePageAccessibilityActions();
+    }
+
     /**
      * Slightly modified RecyclerView to get ViewPager behavior in accessibility and to
      * enable/disable user scrolling.
@@ -541,15 +661,12 @@
         }
 
         @Override
-        public CharSequence getAccessibilityClassName() {
-            return "androidx.viewpager.widget.ViewPager";
-        }
-
-        @Override
         public void onInitializeAccessibilityEvent(@NonNull AccessibilityEvent event) {
             super.onInitializeAccessibilityEvent(event);
             event.setFromIndex(mCurrentItem);
             event.setToIndex(mCurrentItem);
+            event.setSource(ViewPager2.this);
+            event.setClassName(ViewPager2.this.getAccessibilityClassName());
         }
 
         @SuppressLint("ClickableViewAccessibility")
@@ -564,41 +681,6 @@
         }
     }
 
-    /**
-     * Slightly modified LinearLayoutManager to adjust accessibility when user scrolling is
-     * disabled.
-     */
-    private class LinearLayoutManagerImpl extends LinearLayoutManager {
-        LinearLayoutManagerImpl(Context context) {
-            super(context);
-        }
-
-        @Override
-        public boolean performAccessibilityAction(@NonNull RecyclerView.Recycler recycler,
-                @NonNull RecyclerView.State state, int action, @Nullable Bundle args) {
-            switch (action) {
-                case AccessibilityNodeInfoCompat.ACTION_SCROLL_BACKWARD:
-                case AccessibilityNodeInfoCompat.ACTION_SCROLL_FORWARD:
-                    if (!isUserInputEnabled()) {
-                        return false;
-                    }
-                    break;
-            }
-            return super.performAccessibilityAction(recycler, state, action, args);
-        }
-
-        @Override
-        public void onInitializeAccessibilityNodeInfo(@NonNull RecyclerView.Recycler recycler,
-                @NonNull RecyclerView.State state, @NonNull AccessibilityNodeInfoCompat info) {
-            super.onInitializeAccessibilityNodeInfo(recycler, state, info);
-            if (!isUserInputEnabled()) {
-                info.removeAction(AccessibilityActionCompat.ACTION_SCROLL_BACKWARD);
-                info.removeAction(AccessibilityActionCompat.ACTION_SCROLL_FORWARD);
-                info.setScrollable(false);
-            }
-        }
-    }
-
     private static class SmoothScrollToPosition implements Runnable {
         private final int mPosition;
         private final RecyclerView mRecyclerView;
diff --git a/wear/api/1.1.0-alpha01.txt b/wear/api/1.1.0-alpha01.txt
index 6609d67..325310e 100644
--- a/wear/api/1.1.0-alpha01.txt
+++ b/wear/api/1.1.0-alpha01.txt
@@ -19,6 +19,14 @@
   @Deprecated public final class AmbientMode extends android.app.Fragment {
     ctor @Deprecated public AmbientMode();
     method @Deprecated public static <T extends android.app.Activity> androidx.wear.ambient.AmbientMode.AmbientController! attachAmbientSupport(T!);
+    method @Deprecated public void dump(String!, java.io.FileDescriptor!, java.io.PrintWriter!, String[]!);
+    method @Deprecated @CallSuper public void onAttach(android.content.Context!);
+    method @Deprecated @CallSuper public void onCreate(android.os.Bundle!);
+    method @Deprecated @CallSuper public void onDestroy();
+    method @Deprecated @CallSuper public void onDetach();
+    method @Deprecated @CallSuper public void onPause();
+    method @Deprecated @CallSuper public void onResume();
+    method @Deprecated @CallSuper public void onStop();
     field @Deprecated public static final String EXTRA_BURN_IN_PROTECTION = "com.google.android.wearable.compat.extra.BURN_IN_PROTECTION";
     field @Deprecated public static final String EXTRA_LOWBIT_AMBIENT = "com.google.android.wearable.compat.extra.LOWBIT_AMBIENT";
     field @Deprecated public static final String FRAGMENT_TAG = "android.support.wearable.ambient.AmbientMode";
diff --git a/wear/api/current.txt b/wear/api/current.txt
index 6609d67..325310e 100644
--- a/wear/api/current.txt
+++ b/wear/api/current.txt
@@ -19,6 +19,14 @@
   @Deprecated public final class AmbientMode extends android.app.Fragment {
     ctor @Deprecated public AmbientMode();
     method @Deprecated public static <T extends android.app.Activity> androidx.wear.ambient.AmbientMode.AmbientController! attachAmbientSupport(T!);
+    method @Deprecated public void dump(String!, java.io.FileDescriptor!, java.io.PrintWriter!, String[]!);
+    method @Deprecated @CallSuper public void onAttach(android.content.Context!);
+    method @Deprecated @CallSuper public void onCreate(android.os.Bundle!);
+    method @Deprecated @CallSuper public void onDestroy();
+    method @Deprecated @CallSuper public void onDetach();
+    method @Deprecated @CallSuper public void onPause();
+    method @Deprecated @CallSuper public void onResume();
+    method @Deprecated @CallSuper public void onStop();
     field @Deprecated public static final String EXTRA_BURN_IN_PROTECTION = "com.google.android.wearable.compat.extra.BURN_IN_PROTECTION";
     field @Deprecated public static final String EXTRA_LOWBIT_AMBIENT = "com.google.android.wearable.compat.extra.LOWBIT_AMBIENT";
     field @Deprecated public static final String FRAGMENT_TAG = "android.support.wearable.ambient.AmbientMode";