预热和预提取:使用自定义标签页服务

本指南的第三部分重点介绍了 Custom Tabs 服务,以及为何在应用中使用该服务可提供更好的用户体验:

  • 立即打开外部内容:使用 warmup() 会导致浏览器进程在用户点击链接之前在后台启动,并且在打开链接时最多可节省 700 毫秒。mayLaunchUrl() 会预提取网页。将这两个 API 搭配使用可让网页立即加载,从而显著提升自定义标签页集成的用户体验。
  • 更好地处理已最小化自定义标签页:通过连接到自定义标签页服务并在启动自定义标签页时使用相同的 CustomTabSession,Chrome 将能够在启动新标签页之前移除之前最小化的自定义标签页,从而提供更一致的用户体验。

所需步骤如下:

  1. 使用 CustomTabsClient.getPackageName(...) 检查默认浏览器是否支持自定义标签页。如果是,请使用 CustomTabsClient.bindCustomTabsService() 绑定到 CustomTabsService。
  2. 连接到 CustomTabsService 后,在 CustomTabsServiceConnection.onCustomTabsServiceConnected() 回调中执行以下操作:

    a. 使用 CustomTabsClient.warmup() 预热浏览器进程。b. 使用 CustomTabsClient.newSession() 创建新的 CustomTabsSession

  3. (可选)使用 CustomTabsSession.mayLaunchUrl() 预加载用户可能会访问的网页。

  4. 启动新的自定义标签页时,请使用构造函数 new CustomTabsIntent.Builder(session)CustomTabsSession 传递给 CustomTabsIntent.Builder

如果您的应用以 Android API 级别 30 为目标平台,CustomTabsClient.getPackageName(...) 要求您向 Android 清单中添加查询部分,声明与支持自定义标签页的浏览器匹配的 intent 过滤器。

<manifest xmlns:android="http://schemas.android.com/apk/res/android"     xmlns:tools="http://schemas.android.com/tools">      <queries>         <intent>             <action android:name="android.support.customtabs.action.CustomTabsService" />         </intent>     </queries> </manifest> 

以下是有关如何连接到 Custom Tabs 服务的完整示例:

private CustomTabsClient mClient; private CustomTabsSession mSession;  private CustomTabsServiceConnection mConnection = new CustomTabsServiceConnection() {     @Override     public void onCustomTabsServiceConnected(             @NonNull ComponentName name,             @NonNull CustomTabsClient client     ) {         mClient = client;         // Warm up the browser process         mClient.warmup(0 /* placeholder for future use */);         // Create a new browser session         mSession = mClient.newSession(new CustomTabsCallback());         // Pre-render pages the user is likely to visit         // you can do this any time while the service is connected         mSession.mayLaunchUrl(Uri.parse("https://developers.android.com"), null, null);     }      @Override     public void onServiceDisconnected(ComponentName name) {         mClient = null;         mSession = null;     } };  private void bindCustomTabService(Context context) {     // Check for an existing connection     if (mClient != null) {         // Do nothing if there is an existing service connection         return;     }      // Get the default browser package name, this will be null if     // the default browser does not provide a CustomTabsService     String packageName = CustomTabsClient.getPackageName(context, null);     if (packageName == null) {         // Do nothing as service connection is not supported         return;     }     CustomTabsClient.bindCustomTabsService(context, packageName, mConnection); }  @Override protected void onCreate(Bundle savedInstanceState) {      bindCustomTabService(this);     findViewById(R.id.button).setOnClickListener(new View.OnClickListener() {         @Override         public void onClick(View view) {             String url = "https://developers.android.com";             CustomTabsIntent intent = new CustomTabsIntent.Builder(mSession)                     .build();             intent.launchUrl(MainActivity.this, Uri.parse(url));         }     }); } 

在 Android 上,网址可以由 Android 应用处理。例如,如果用户安装了 Facebook 应用,并点击了指向 Facebook 帖子的链接,他们通常更希望该链接在 Facebook 应用中打开,而不是在浏览器中打开。

默认情况下,自定义标签页会在相应的 Android 应用(如果已安装)中打开链接。不过,一旦建立了 CustomTabsServiceConnection,此行为便会停止,所有网址都将改为在自定义标签页中打开。为了提供更好的用户体验,我们建议您使用以下代码重新启用此行为:

CustomTabsIntent customTabsIntent = new CustomTabsIntent.Builder()     .setSendToExternalDefaultHandlerEnabled(true)     .build(); 

后续:了解如何调整自定义标签页体验的大小