android 集成TBS X5内核WebView

作者: 神气小风 | 来源:发表于2018-08-03 17:41 被阅读321次

    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

    1533270141(1).png

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


    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版本,下载后解压文件如下:


    1533273651(1).png

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

    B. 新建项目

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


    1533274296(1).png
    C. 集成TBS

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


    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:打开连接后,下载压缩包,解压后,是如下文件:


    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内核共享,但是手机中明明安装了微信,QQ,可是首次安装加载还是失败。官网论坛和反馈中心已经有人提出此问题,但是官方没有给出解决方案。

    相关文章

      网友评论

      本文标题:android 集成TBS X5内核WebView

      本文链接:https://www.haomeiwen.com/subject/wtkuvftx.html