新增轮播图跳转web页面、轮播、推荐歌单数据存储( 简易音乐 七)

新增轮播图跳转web页面、轮播、推荐歌单数据存储( 简易音乐 七)

关于

  本篇主要使用到了腾讯x5 浏览器webview与litepal操作sqlite存储数据至本地。上一篇新增我的推荐歌单、通过ViewPager2+RadioGroup重构主界面( 简易音乐 六)

效果图

  这里表面腾讯x5内核加载成功
在这里插入图片描述
  gif图片提示违规了,可能是涉及版权之类的吧,效果可参考网易云的轮播图打开的网页链接的效果。

第一步,添加引用

  添加litepal引用:

//sqlite数据库
    implementation 'org.litepal.guolindev:core:3.2.3'

   去官网下载页面,下载sdk,然后将里面的jar包,复制到我们的项目的lib中,右键选择Add As Library然后会自动在buil中添加如下一行:

implementation files('libs/tbs_sdk_thirdapp_v4.3.0.93_43993_sharewithdownloadwithfile_withoutGame_obfs_20210220_114728.jar')

如果添加失败,在build内加上这句:

android{
 sourceSets {
        main {
            jniLibs.srcDirs = ['libs']
        }
    }
}
repositories {
    flatDir {
        dirs 'libs'
    }
}
dependencies {
......
}

  在application中初始化:

 // 在调用TBS初始化、创建WebView之前进行如下配置
        HashMap map = new HashMap();
        map.put(TbsCoreSettings.TBS_SETTINGS_USE_SPEEDY_CLASSLOADER, true);
        map.put(TbsCoreSettings.TBS_SETTINGS_USE_DEXLOADER_SERVICE, true);
        QbSdk.setDownloadWithoutWifi(true);
        QbSdk.initTbsSettings(map);
        QbSdk.PreInitCallback cb = new QbSdk.PreInitCallback() {

            @Override
            public void onViewInitFinished(boolean arg0) {
                // TODO Auto-generated method stub
                //x5內核初始化完成的回调,为true表示x5内核加载成功,否则表示x5内核加载失败,会自动切换到系统内核。
                Log.e("app", " onViewInitFinished is " + arg0);
            }

            @Override
            public void onCoreInitFinished() {
                // TODO Auto-generated method stub
            }
        };
        //x5内核初始化接口
        QbSdk.initX5Environment(getApplicationContext(),  cb);
        //litepal初始化
         LitePal.initialize(instance);

  在AndroidManifest.xml下配置x5下载服务:

 <service
            android:name="com.tencent.smtt.export.external.DexClassLoaderProviderService"
            android:label="dexopt"
            android:process=":dexopt" />

  第一次加载x5内核(wifi下会消耗部分时间),可以在android studio的logcat中看到下载进度,然后会有app: onViewInitFinished is true的提示,表示内核加载成功。

新增数据库实体类

  新增BannerSQ.classRecommendSQ.class实体类如下:

public class BannerSQ extends LitePalSupport {

    @Column(unique = true,defaultValue = "unKnow")
    private String idName;

    private String pic;

    private String titleColor;

    private String typeTitle;

    private String url;

    private Object song;

    public Object getSong() {
        return song;
    }

    public void setSong(Object song) {
        this.song = song;
    }

    public void setPic(String pic) {
        this.pic = pic;
    }

    public void setTitleColor(String titleColor) {
        this.titleColor = titleColor;
    }

    public void setTypeTitle(String typeTitle) {
        this.typeTitle = typeTitle;
    }

    public void setUrl(String url) {
        this.url = url;
    }

    public String getPic() {
        return pic;
    }

    public String getIdName() {
        return idName;
    }

    public void setIdName(String idName) {
        this.idName = idName;
    }

    public String getTitleColor() {
        return titleColor;
    }

    public String getTypeTitle() {
        return typeTitle;
    }

    public String getUrl() {
        return url;
    }
}

public class RecommendSQ extends LitePalSupport {
    private String picUrl;
    private long playcount;
    private String name;

    public String getPicUrl() {
        return picUrl;
    }

    public void setPicUrl(String picUrl) {
        this.picUrl = picUrl;
    }

    public long getPlaycount() {
        return playcount;
    }

    public void setPlaycount(long playcount) {
        this.playcount = playcount;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

  在src/main/下新增一个assets文件夹,并新增文件litepal/xml,写法格式固定:

<?xml version="1.0" encoding="UTF-8" ?>
<litepal>
    <dbname value="musicHome" ></dbname>
    <!--没修过一次或是新增数据库实体类这里都要+1-->
    <version value="7"></version>
    <list>
        <mapping class="com.tobey.jianyimusic.data.database.BannerSQ"/>
        <mapping class="com.tobey.jianyimusic.data.database.RecommendSQ"/>
    </list>
</litepal>

修改fragment代码

  修改轮播图、推荐歌单的存储类,新增跳转web页面

public class Fragment_main extends BaseFragment {

    @BindView(R.id.banner)
    Banner banner;
    @BindView(R.id.text_fm)
    TextView textView_fm;
    @BindView(R.id.recommend_recycle)
    RecyclerView recyclerRecommend;

    //修改为数据库实体类,方便数据库存储
    List<BannerSQ> list_banner_sq;
    List<RecommendSQ> list_recommend_sq;

    private static int potsition = 0;
     //适配器也要修改,将RecommendListBean替换成RecommendSQ
    private RecommdListAdapter adapter;



    @Override
    protected int getLayout() {
        return R.layout.fragment_main;
    }

    @Override
    protected void initView(View view) {
        String date = Calendar.getInstance().get(Calendar.DAY_OF_MONTH) + "";
        textView_fm.setText(date);
        initData();
    }

    private void initData() {
        RetrofitUtils.getmApi().getBanner(1)
                .compose(RXHelper.observableIO2Main(getContext()))
                .subscribe(new StaticMethodUtils.OnCallback<banner_bean>(){

                    @Override
                    public void onNext(banner_bean banner_bean) {
                        if (banner_bean.getCode() == 200){

                            updateBanner(banner_bean.getBanners());

                        }
                    }

                    @Override
                    public void onError(Throwable e) {
                        super.onError(e);
                        //网络异常则查询数据库来充当banner轮播图数据                   
                        queryDb();
                    }
                });
        LinearLayoutManager manager = new LinearLayoutManager(getContext());
        manager.setOrientation(LinearLayoutManager.HORIZONTAL);
        recyclerRecommend.setLayoutManager(manager);

        RetrofitUtils.getmApi().getRecommendPlayList()
                .compose(RXHelper.observableIO2Main(getContext()))
                .subscribe(new StaticMethodUtils.OnCallback<RecommendListBean>(){
                    @Override
                    public void onNext(RecommendListBean recommendListBean) {
                        if (recommendListBean.getCode() == 200){
                            list_recommend_sq = new ArrayList<>();
                            int size = recommendListBean.getRecommend().size();
                            for (int i=0;i<size;i++){
                                RecommendSQ recommendSQ = new RecommendSQ();
                                recommendSQ.setName(recommendListBean.getRecommend().get(i).getName());
                                recommendSQ.setPicUrl(recommendListBean.getRecommend().get(i).getPicUrl());
                                recommendSQ.setPlaycount(recommendListBean.getRecommend().get(i).getPlaycount());
                                list_recommend_sq.add(recommendSQ);
                            }

                            adapter = new RecommdListAdapter(list_recommend_sq);
                            adapter.notifyDataSetChanged();
                            recyclerRecommend.setAdapter(adapter);
                            //sqlite在使用前要调用LitePal.getDatabase();建议数据库表,但是我们待会会修改SplashActivity.java,所以此处不用添加
                            //通过这个方法可以判断数据是否存储成功 
                            boolean result =  LitePal.saveAll(list_recommend_sq);
                          if (!result){
                                Log.e("数据库内容","数据收藏存储失败");
                            }
                        }
                    }

                    @Override
                    public void onError(Throwable e) {
                        super.onError(e);
                       //查询推荐歌单数据库表
                        queryRecommendDb();
                    }
                });


    }


    private void queryRecommendDb() {
        //查询RecommendSQ表中第一条数据是否存在用于判空
        if (LitePal.findFirst(RecommendSQ.class) != null){
            list_recommend_sq = LitePal.findAll(RecommendSQ.class);
            adapter = new RecommdListAdapter(list_recommend_sq);
            adapter.notifyDataSetChanged();
            recyclerRecommend.setAdapter(adapter);
        }
    }

    private void queryDb() {
        if (LitePal.findFirst(BannerSQ.class) != null){
            list_banner_sq = LitePal.findAll(BannerSQ.class);
            int s = list_banner_sq.size();
            banner.setIndicator(new RectangleIndicator(getActivity()))
                    .setIndicatorHeight(5)
                    .setIndicatorWidth(6,6)
                    .setIndicatorGravity(IndicatorConfig.Direction.CENTER)
                    .setAdapter(new ImageTitleAdapter(list_banner_sq,this))
                    .addBannerLifecycleObserver(getActivity())//添加生命周期观察者
                    .setIntercept(true)
                    .setOnBannerListener(new OnBannerListener() {
                        @Override
                        public void OnBannerClick(Object data, int position) {
                        }
                    })
                    .setBannerRound(10f);
        }
    }

    private void updateBanner(List<banner_bean.BannersBean> banners) {
        if (banners !=null && banners.size() >0){
            int i = banners.size();
            list_banner_sq = new ArrayList<>();
            for (int j=0;j<i;j++){
                BannerSQ bannerSQ = new BannerSQ();
                bannerSQ.setPic(banners.get(j).getPic());
                bannerSQ.setTitleColor(banners.get(j).getTitleColor());
                bannerSQ.setUrl(banners.get(j).getUrl());
                bannerSQ.setTypeTitle(banners.get(j).getTypeTitle());
                bannerSQ.setIdName(j+1+"");
                bannerSQ.setSong(banners.get(j).getSong());
                list_banner_sq.add(bannerSQ);

            }
   
            banner.setIndicator(new RectangleIndicator(getActivity()))
                    .setIndicatorHeight(5)
                    .setIndicatorWidth(6,6)
                    .setIndicatorGravity(IndicatorConfig.Direction.CENTER)
                    .setAdapter(new ImageTitleAdapter(list_banner_sq,this))
                    .addBannerLifecycleObserver(getActivity())//添加生命周期观察者
                    .setIntercept(true)
                    .setOnBannerListener(new OnBannerListener() {
                        @Override
                        public void OnBannerClick(Object data, int position) {
                           //只有url不为空才表示有web网页可以加载    
                           if (list_banner_sq.get(position).getUrl() !=null){
                               ARouter.getInstance()
                                       .build(Config.ROUTE_WEB)
                                       .withString("url",list_banner_sq.get(position).getUrl())
                                       .navigation(getActivity());
                           }
                          
                        }
                    })
                    .setBannerRound(10f);
            insertBannerDb();
        }
    }

    private void insertBannerDb() {
        boolean result =  LitePal.saveAll(list_banner_sq);
        if (result){
            Log.e("数据库内容","数据存储成功");
            // ToastUtils.show("数据存储成功");
        }else {
            Log.e("数据库内容","数据存储失败");
            //  ToastUtils.show("数据存储失败");
        }
    }

    @Override
    protected void setListener() {

    }



    @Override
    public void onDestroy() {
        super.onDestroy();
        if (list_banner_sq !=null){
            list_banner_sq.clear();
            list_banner_sq = null;
        }
    }

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

        if (list_recommend_sq !=null){
            list_recommend_sq.clear();
            list_recommend_sq = null;
        }
    }
}

  修改config.java,添加WebActivity的标签:

String ROUTE_WEB = "/app/web";

  修改SplashActivity.java,在初始化的地方添加如下判断方法,用于数据库清理,因为litepal暂时未做list数据的判重更新操作,之后插入,所以我在启动动画页面对数据库在有网络情况下进行数据删除。

  //建立数据库
                LitePal.getDatabase();
                if (LitePal.findFirst(BannerSQ.class) != null&& StaticMethodUtils.isNetWorkActive(SplashActivity.this)){
                    LitePal.deleteAll(BannerSQ.class);
                    LitePal.deleteAll(RecommendSQ.class);
                    Log.e("数据库内容","删除功能");
                }

新增WebActivity页面加载网页

  webview布局页面如下:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".home.WebActivity">
    <include layout="@layout/common_title" android:id="@+id/title"/>
    <com.tencent.smtt.sdk.WebView
        android:id="@+id/web"
        android:layout_below="@+id/title"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>
    <ProgressBar
        android:id="@+id/progressBar"
        style="?android:attr/progressBarStyleHorizontal"
        android:layout_width="match_parent"
        android:layout_height="3dip"
        android:layout_below="@+id/title"
        android:progressDrawable="@drawable/pg"
        />
</RelativeLayout>

  设置ProgressBar的透明背景pg.xml,使网页加载完成展示的不会突兀:

<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >

    <item android:id="@android:id/background">
        <shape>
            <corners android:radius="2dp" />
            <gradient
                android:angle="270"
                android:centerColor="@android:color/transparent"
                android:endColor="@android:color/transparent"
                android:startColor="@android:color/transparent" />
        </shape>
    </item>
    <item android:id="@android:id/progress">
        <clip>
            <shape>
                <corners android:radius="2dp" />
                <gradient
                    android:centerColor="#1C66B6"
                    android:endColor="#1C66B6"
                    android:startColor="#1C66B6" />

            </shape>
        </clip>
    </item>

</layer-list>

  修改WebActivity.java

@Route(path = Config.ROUTE_WEB)
public class WebActivity extends BaseActivity {

    @BindView(R.id.web)
    WebView webView;
    @BindView(R.id.progressBar)
    ProgressBar pg;

    @Autowired(name = "url")
    String url;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_web);

    }

    @Override
    protected BasePresenter onCreatePresenter() {
        return null;
    }

    @Override
    protected void initData() {
       Log.e("网址",url);
        webView.loadUrl(url);
        webView.getSettings().setGeolocationEnabled(false);//定位
        webView.getSettings().setJavaScriptEnabled(true);
        webView.getSettings().setUseWideViewPort(true);
        webView.getSettings().setJavaScriptCanOpenWindowsAutomatically(true);

        savaData(webView);
        if (webView.getX5WebViewExtension() !=null){
            webView.getX5WebViewExtension().setVerticalScrollBarEnabled(false);
            Log.e("内部",webView.getX5WebViewExtension().toString());
            Log.e("内核版本", QbSdk.getTbsVersion(this)+"");
            webView.getSettingsExtension().setDisplayCutoutEnable(true); //适配刘海屏

        }
        webView.setWebViewClient(client);
        webView.setWebChromeClient(webChromeClient);

        Log.e("当前",webView.getSettings().getUserAgentString());
    }

    private void savaData(WebView webView) {
        webView.getSettings().setDomStorageEnabled(true);
        webView.getSettings().setDatabaseEnabled(true);
        webView.getSettings().setAppCacheEnabled(true);
        String appCach = getApplicationContext().getCacheDir().getAbsolutePath();
        webView.getSettings().setAppCachePath(appCach);
    }

    WebViewClient client = new WebViewClient(){
        @Override
        public boolean shouldOverrideUrlLoading(WebView webView, String s) {
           //拦截url调整系统浏览器
            webView.loadUrl(s);
           return true;
        }


    };

    WebChromeClient webChromeClient = new WebChromeClient(){
        @Override
        public void onProgressChanged(WebView webView, int i) {
            super.onProgressChanged(webView, i);
            pg.setProgress(i);
            if (i == 100){
                pg.setVisibility(View.GONE);
            }
        }

        @Override
        public void onReceivedTitle(WebView webView, String s) {
            super.onReceivedTitle(webView, s);
            Log.e("标题",s);
            /*MarqueeTextView textView = findViewById(R.id.tv_title);

            textView.setUrl(s,textView);
            textView.setScrollMode(SCROLL_FOREVER);
            textView.setVisibility(View.VISIBLE);*/
            //这里是设置标题的
            setTitleText(s);
        }
    };

    @Override
    protected void initModule() {
        //获取传值的地方需要绑定
        ARouter.getInstance().inject(this);
       //页面返回功能
        setBackBtn();
    }

    @Override
    protected void onResume() {
        super.onResume();
        webView.onResume();
    }

    @Override
    protected void onPause() {
        super.onPause();
        webView.onPause();
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        if (webView != null){
            webView.clearHistory();
            webView.loadUrl("about:blank");
            webView.stopLoading();
            webView.setWebViewClient(null);
            webView.destroy();
            webView = null;
        }
    }
}

好了,本篇到此结束了,有问题欢迎批评指正!,觉得不错的也请点个赞奥

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
以下是一个简单的实现方式: 1. 在轮组件中添加一个点击事件,可以使用 @click 或者 v-on:click 来绑定事件。 2. 在点击事件中使用 $router.push() 方法进行页面,该方法接受一个路由路径作为参数。 3. 可以为每个轮设置对应的路由路径,在点击事件中获取当前轮的路由路径,并将其作为参数传递给 $router.push() 方法。 示例代码如下: ``` <template> <div class="carousel"> <div class="carousel-item" v-for="item in items" :key="item.id" @click="goToPage(item)"> <img :src="item.imgSrc" alt=""> </div> </div> </template> <script> export default { data() { return { items: [ { id: 1, imgSrc: 'path/to/image1.jpg', route: '/page1' }, { id: 2, imgSrc: 'path/to/image2.jpg', route: '/page2' }, { id: 3, imgSrc: 'path/to/image3.jpg', route: '/page3' } ] } }, methods: { goToPage(item) { this.$router.push(item.route) } } } </script> ``` 需要注意的是,要使用 $router.push() 方法进行页面,需要先在组件中注入 router 对象。可以在 main.js 中引入 vue-router,然后在 Vue 实例中注入 router 对象。示例代码如下: ``` import Vue from 'vue' import VueRouter from 'vue-router' import App from './App.vue' import Page1 from './components/Page1.vue' import Page2 from './components/Page2.vue' import Page3 from './components/Page3.vue' Vue.use(VueRouter) const routes = [ { path: '/page1', component: Page1 }, { path: '/page2', component: Page2 }, { path: '/page3', component: Page3 } ] const router = new VueRouter({ routes }) new Vue({ router, render: h => h(App) }).$mount('#app') ``` 在上述代码中,我们定义了三个路由,分别对应三个组件 Page1、Page2、Page3。然后在 Vue 实例中注入 router 对象,并将其传递给组件。这样,在组件中就可以使用 $router.push() 方法进行页面了。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

雪の星空朝酱

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值