android 集成TBS X5内核WebView(首次安装不需要kill掉程序就可以加载)

0x00. 为何不直接使用内置的WebView组件?

Android中的WebView组件,在4.4以前的版本是WebKit的内核,4.4以后才换成chromium的内核。而且不同版本之间运行的效率也参差不齐,适配问题很让人头疼。因此考虑用第三方webview是个不错的选择。

0x01、有哪些第三方WebView可供选择呢?

方案1:Crosswalk

Home · crosswalk-project/crosswalk-website Wiki · GitHub
优点:各种流畅、强大,静态集成
缺点:体积过大,打包后的APK要48M左右,这个问题有点致命
解决思路:使用Crosswalk的精简版 crosswalk-lite(此版本不是官方主推,更新也不频繁)
Crosswalk Lite

《android 集成TBS X5内核WebView(首次安装不需要kill掉程序就可以加载)》 1533270141(1).png

可以看到,体积确实小了很多,但是,请注意这段话:

《android 集成TBS X5内核WebView(首次安装不需要kill掉程序就可以加载)》 1533270261(1).png

Lite仅支持x86和ARM的32位版本。 尚不支持x86_64和ARM64。所以,如果想适配64位的Android机,此方案只能舍弃。
接下来我们再看看方案2

方案2:腾讯TBS X5内核webview

腾讯TBS官网

优点:体积小,可以动态集成,静态集成,而且APP接入TBS后可以共享使用微信,或者手机QQ,QQ浏览器的X5内核
缺点:首次安装APP后第一次启动时X5内核总是加载失败(手机中已经安装了微信和QQ也不行,直接运行官网的demo也是首次加载失败),kill掉程序后再次启动就好了(这个问题有人已经在官网反馈了,但是官方没有给出解决方案)

集成可以动态集成(启动APP后再开始下载X5内核)和静态集成(X5内核一起打包进APK,不需再次下载)

0x02. 动态集成TBS(studio)

A. 获取TBS

TBS官网APK下载地址

去官网下载TBS的SDK文件,选择第一个(完整版)即可,目前是v3.6.0.1315版本,下载后解压文件如下:

《android 集成TBS X5内核WebView(首次安装不需要kill掉程序就可以加载)》 1533273651(1).png

其中,studio版的demo是module, 不能直接运行,如果想跑起来,需要以module添加进某个项目中再运行这个module

B. 新建项目

新建一个studio的空项目,把解压SDK后的jar包文件放在libs目录下,并导入,如图:

《android 集成TBS X5内核WebView(首次安装不需要kill掉程序就可以加载)》 1533274296(1).png

C. 集成TBS

把 SDK接入示例-Android Studio.zip 解压,把main目录下的jniLibs文件夹整个复制到自己的项目的main目录下,如图:

《android 集成TBS X5内核WebView(首次安装不需要kill掉程序就可以加载)》 1533275152(1).png

x5暂时不提供64位so文件,为了保证64位手机能正常加载x5内核,需如下配置:

1)打开app的build.gradle,在defaultConfig标签内加入

 ndk{abiFilters"armeabi","armeabi-v7a","x86","mips"}

完整如下:

    defaultConfig {
        applicationId "your applicationId"
        minSdkVersion 15
        targetSdkVersion 28
        versionCode 1
        versionName "1.0"
        testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"

        ndk{abiFilters "armeabi", "armeabi-v7a", "x86", "mips"}
    }

2)如果配置后编译报错,打开项目的gradle.properties文件,在最后加上

android.useDeprecatedNdk=true    

至此,动态集成TBS X5内核webview介绍完毕,总结一下动态集成的特点,就是先集成,后加载(当手机中没有X5内核时TBS底层会自动下载X5内核)。可是,如果用户第一次安装就没有网络,手机中也没有X5内核,这种场景怎么办呢?总不能用系统的webview吧,如果那样,很多功能将不可使用。所以,接下来介绍一下静态集成,集成完成后不需任何网络就可以使用

0x03. 静态集成TBS(studio)

静态集成TBS官网地址

动态集成和静态集成大同小异,具体步骤:
1:打开连接后,下载压缩包,解压后,是如下文件:

《android 集成TBS X5内核WebView(首次安装不需要kill掉程序就可以加载)》 1533281420(1).png

2:和动态集成一样,把jar包放在项目的libs目录下面,导入

3:把apk文件的后缀改为zip, 然后解压,得到多个so包,像动态集成一样,把jniLibs文件夹粘贴到main目录下, 把jniLibs里面的armeabi文件夹清空,把刚才解压APK文件得到的所有so包放在armeabi文件夹中。其实整个过程就是把动态集成中缺少的so包添加到项目中,这样就不需要再下载了。

至此,静态集成TBS完毕。下面我们再来介绍一下用法(两种集成方式使用基本相同,只有预加载X5内核的代码不同)

0x04. 使用WebView(studio)

A. 添加权限

打开app的清单文件AndroidManifest.xml,添加权限(从官方demo中复制即可) 如下:

<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>

<uses-permission android:name="android.permission.INTERNET"/>

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>

<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>

<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>

<uses-permission android:name="android.permission.READ_PHONE_STATE"/>

<uses-permission android:name="android.permission.READ_SETTINGS"/>

<uses-permission android:name="android.permission.WRITE_SETTINGS"/>

<uses-permission android:name="android.permission.INTERNET"/>

<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/>

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>

<!-- 硬件加速对X5视频播放非常重要,建议开启 -->

<uses-permission android:name="android.permission.GET_TASKS"/>
B. 加载X5内核

这一步骤静态集成和动态集成代码不同,咱们分开介绍

1)动态集成的X5内核加载代码:

因为在打开webview之前要加载X5内核,此过程比较耗时,虽然是异步的,但是如果没有加载完成或者没有加载成功,打开的webview将是Android原生的控件,而不是X5内核的WebView,所以这个动作越早做越好,因此官方建议自定义application, 在onCreate方法中调用QbSdk.initX5Environment()来预加载X5内核,该方法需要传递2个参数,第一个参数是context,第二个参数是实现QbSdk.PreInitCallback接口的实例,此接口是X5内核初始化的回调接口,有两个抽象方法,onCoreInitFinished()和 onViewInitFinished(boolean var1),其中,onCoreInitFinished()回调方法表示X5内核初始化完成(注意,不保证一定成功),onViewInitFinished(boolean var1) 回调方法回传的参数如果为true,表示X5内核加载成功,否则X5内核加载失败。如下:

public class APPAplication extends Application {
      @Override
      public void onCreate() {
            // TODO Auto-generated method stub
            super.onCreate();
            QbSdk.PreInitCallback cb = new QbSdk.PreInitCallback() {
            @Override
            public void onViewInitFinished(boolean arg0) {
                // TODO Auto-generated method stub
                //x5內核初始化完成的回调,为true表示x5内核加载成功,否则表示x5内核加载失败,会自动切换到系统内核。
                Log.d("app", " onViewInitFinished is " + arg0);
            }
            
            @Override
            public void onCoreInitFinished() {
                // TODO Auto-generated method stub
            }
        };
        //x5内核初始化接口
        QbSdk.initX5Environment(getApplicationContext(),  cb);          
      }
}
2)静态集成的X5内核加载代码:

在加载X5内核时(即application的onCreate方法里),不再调用QbSdk.initX5Environment()方法,而是调用QbSdk.preinstallStaticTbs(getApplicationContext());方法,而且要在异步线程中执行。

public class LemageApplication extends Application {

    public static boolean x5Init;

    @Override
    public void onCreate() {
        super.onCreate();

        new Thread(new Runnable() {
            @Override
            public void run() {
                QbSdk.preinstallStaticTbs(getApplicationContext());
            }
        }).start();

    }
}

最后,无论是动态集成还是静态集成,只要自定义了application, 别忘了在AndroidManifest.xml文件中更改名字 ,同时,如果需要硬件加速的话,也要加上

android:hardwareAccelerated="true"

如下代码:

    <application
        android:name="your applicationId"
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:hardwareAccelerated="true"
        android:theme="@style/AppTheme">

至此,就可以在项目中使用x5内核的webview了。如果是想通过x5来播放视频,那么请继续往下看:

0x05. 播放视频(studio)

如果需要webview播放视频,那么有两种方式,第一种,参考官方demo的FullScreenActivity类,此类中有一个webview加载的是本地的html,在html中通过标签来播放网络视频,可以调节屏幕大小,可以根据自己的需求灵活控制。第二种先要在AndroidManifest.xml中声明一个VideoActivity类,如下:

        <!--视频播放界面-->
        <activity
            android:name="com.tencent.smtt.sdk.VideoActivity"
            android:alwaysRetainTaskState="true"
            android:configChanges="orientation|screenSize|keyboardHidden"
            android:exported="false"
            android:launchMode="singleTask">
            <intent-filter>
                <action android:name="com.tencent.smtt.tbs.video.PLAY"/>
                <category android:name="android.intent.category.DEFAULT"/>
            </intent-filter>
        </activity>

然后想播放视频时,可以在自己的activity中直接调用TbsVideo.openVideo()方法,该方法需要传递两个参数,第一个是context, 第二个是播放视频的路径. 需要注意的是,在调用TbsVideo.openVideo()方法前,需要判断一下视频播放器是否初始化完成,代码如下:

   private void startVideo() {
        if ((TbsVideo.canUseTbsPlayer(this))) {
            //可以播放视频
            TbsVideo.openVideo(this, urlTest);
        } else {
            Toast.makeText(this, "视频播放器没有准备好", Toast.LENGTH_SHORT).show();
        }
    }

0x06. 使用office(studio)

X5内核的一大特色就是可以在手机不安装office的情况下,可以只需下载插件即可浏览office文档(下载插件的过程由TBS内部控制),应用层只需调用API即可。下面以浏览PDF文件举例:(注:X5内核不能浏览远程office,只能先下载到本地再浏览)

A. TbsReaderView

显示浏览PDF效果的控件不是webview,而是TbsReaderView,而且,TbsReaderView不能在XML中布局,必须要代码动态布局,否则报错。通过查看TbsReaderView的源代码发现,它只有一个构造方法,需要两个参数,第一个参数是context, 第二个参数是TbsReaderView.ReaderCallback,也就是说,如果在xml中布局,那么构造方法不会读取XML中的属性,所以只能代码生成实例后添加进父控件中显示。

B. 调用
    private void displayFile() {
        Bundle bundle = new Bundle();
        //传递文件路径
        bundle.putString("filePath", url);
        //加载插件保存的路径
        bundle.putString("tempPath", Environment.getExternalStorageDirectory().getPath());
        boolean result = mTbsReaderView.preOpen(parseFormat("测试XLSX.xlsx"), false);
        if (result) {
            mTbsReaderView.openFile(bundle);
        }
    }

首先,创建一个Bundle对象,然后,分别put目标office文件的本地路径,和pdf插件保存的路径,然后把bundle对象作为参数传递给TbsReaderView就可以了。

至此,TBS X5内核webview集成和基础使用全部介绍完毕,对比如下:

动态集成:体积小,所以启动程序后如果没有X5内核会自动下载
静态集成:体积大,但是不需要下载,使用户在没有网的情况下也可以使用
*** ******注意:

网上有很多文章说是无论是静态还是动态集成,有的机型首次安装APP时加载X5内核都失败,必须要kill掉程序后再次启动才能加载成功。这个问题我自己也遇到过。其实产生这个问题的原因是X5内核还没有加载完成就加载WebView,此时的WebView是原生的WebView,而不是X5内核的,此时如果不kill掉程序,哪怕X5内核加载完成也改变不了这个WebView的内核了。所以会造成这个问题。解决的办法就是想办法在X5内核加载完成之前不加载com.tencent.smtt.sdk.WebView就可以了,等X5内核加载成功后再加载com.tencent.smtt.sdk.WebView。如果在X5内核加载成功之前一定要用WebView,可以先用原生的代替。这样哪怕是首次安装APP也可以不用kill掉程序就可以用X5内核了。
但是,还有一个问题,官网说是X5内核共享,但是手机中明明安装了微信,QQ,可是首次安装为什么还需要加载X5内核?如果有知道的同仁请告知一下,感谢。

————————
写在最后
近来发现很多留言的读者朋友很多是想要x5静态包的, 本来一直都是通过QQ邮箱发放,但是最近工作比较繁忙,所以想了一个办法,想要x5静态包的朋友们只需要扫描下面的二维码,发送“x5静态包”, 即可获得百度网盘的下载链接。同时,有技术上需要讨论的大家也可以发送给公众号一起研究。本公众号会不定期的推送技术文章以及各种干货,欢迎大家扫描关注,感谢。

《android 集成TBS X5内核WebView(首次安装不需要kill掉程序就可以加载)》 神气小风.jpg

    原文作者:神气小风
    原文地址: https://www.jianshu.com/p/da19da46fb20
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞