需求
1. 做一個新聞展示頁
2. 新聞分類可以自定義
3. 每類新聞的內容,樣式不一樣
4. 上拉加載新的數據
5. 點擊進入詳情頁,再返回時,定位到原來的位置
圖片展示
采用的技術
輪播圖使用:swiper
zepto.js
vue.js
vue.resource.js
vue-router.js
滑動插件:iscroll.js
界面樣式采用的 weui
設計的思路
因為使用了vue.js 每個分類的樣式不一樣,而且分類是可以配置的。所以呢,想到了單頁面應用,所以選擇了vue-router.js的路由。也使用了vue.resource 插件用來做數據傳輸。
因為我比較菜,所以呢還是使用的原始的引入方式,沒有使用webpack之類的打包工具,就最原始的js 寫法。
難點
使用了路由,是為了返回的時候,可以回到剛才離開的地方,vue雖然有自帶的keep-alive 但是似乎必須使用路由的history模式,還要修改服務器端的東西,所以感覺不是很合適。而且我們需要Ajax加載數據,怎樣能返回路由的時候,展示ajax加載的內容呢?
我想到了記錄個數,每次進入路由再從這個數開始加載,但是呢我們沒有下拉更新,用戶再也看不到之前看的內容。
后來我想到了H5 的緩存方法。使用了sessionStorage。
sessionStorage用于本地存儲一個會話(session)中的數據,這些數據只有在同一個會話中的頁面才能訪問并且當會話結束后數據也隨之銷毀。因此sessionStorage不是一種持久化的本地存儲,僅僅是會話級別的存儲。
再離開一個路由之前,把這個路由現在狀態信息全部記錄下來(包括提示語,滑動位置,新聞內容等),等下次進入這個路由的時候,再取出來數據這樣就實現了不管加載多少數據,再次進入這個路由的時候,都可以和上一個銜接上。
下圖為存在緩存里面的內容。而且一關閉瀏覽器數據會被清空
有一個重要的地方是:sessionStorage 是有最大容量的,應該是有容量限制的,我找了找localStorage 5M左右,sessionStorage 我還沒有找到,但在項目中運行情況來看,暫時穩定。
重要代碼展示
路由的定義
重點的是每個組件里面的方法
每個組件都共用的data , create 和 methods_all
var returndata={ swipertime:swipertime, demoData: [], demoData2:[], message:'正在加載數據', iscrollaction:false, token:'{pigcms:$token}', cdn:"{pigcms::C('cdn_images')}", param:{ api_url:"{pigcms::C('api_weixin')}", local_url:"{pigcms::C('site_url')}", classid: -1, startnum: 0 , other:'' }, ajax_status:false, huadong:true, } //組件開始的時候,先注銷掉上一個組件的滑動,然后查看緩存里面有沒有數據,如果有緩存就進入緩存里面,如果沒有,就重新加載 var create=function() { var that = this; if (that.myScroll){ that.myScroll.destroy(); //把滑動注銷掉 } var session_name=this.$route.path; if(sessionStorage[session_name]){ //說明緩存里面有 that.session_data(); }else{ that.ajax_data(); } };//有緩存的處理辦法session_data:function () { var that = this; var session_name=this.$route.path; //把緩存內容取出來 var session_data= JSON.parse(sessionStorage[session_name]); for (x in session_data){ switch(x){ case 'data1': that.demoData=session_data[x]; break; case 'data2': that.demoData2=session_data[x]; break; case 'scroll_y': var scroll_y=session_data[x]; break; case 'iscrollaction': that.iscrollaction=session_data[x]; break; case 'startnum': that.param.startnum=session_data[x]; break; case 'other': that.param.other=session_data[x]; break; case 'message': that.message=session_data[x]; break; case 'classid': that.param.classid=session_data[x]; break; } } Vue.nextTick(function () { //初始化滾動插件 that.myScroll = new IScroll('#wrapper', { mouseWheel: true, wheelAction: 'zoom', click: true, scrollX: false, scrollY: true, startY:scroll_y,//滑動定位到原來的位置 }); //滾動監聽 that.myScroll.on('scrollStart',that.showbox);//滾動監聽,1000 that.myScroll.on('scrollEnd',that.scrollaction);//滾動監聽,1000 that.myScroll.refresh(); }) },//沒有緩存重新加載 ajax_data:function(){ var that = this; if (this.$route.params.id != ''){ that.param.classid=this.$route.params.id; }else{ that.param.classid=-1; } that.param.startnum=0;//初始化數據 var url = that.param.api_url + ******' + that.token + '&classid=' + that.param.classid + '&offset=' + that.param.startnum;//接口url that.$http.jsonp(url).then(function (response) { var res = response.data; //取出的數據 this._data.demoData2 = res.new; this._data.demoData = res.data; this._data.param.other = res.other ; var listdata = res.data; //數據 var code = res.code; //狀態值 if (res.other !== 1) { if (code == '20001') { if(listdata.length == 10){ that.iscrollaction = true; that.message='正在加載數據'; }else{ that.iscrollaction = false; that.message='沒有更多資訊'; } }else if (code == '20002') { that.iscrollaction=false; that.message='沒有更多資訊'; } else if (code == '40001' || code == '40002') { that.message='訪問錯誤'; that.iscrollaction=false; }else{ that.message='暫無數據'; that.iscrollaction=false; } } else { that.iscrollaction=false; } that.param.startnum = listdata.length; Vue.nextTick(function () { //初始化滾動插件 that.myScroll = new IScroll('#wrapper', { mouseWheel: true, wheelAction: 'zoom', click: true, scrollX: false, scrollY: true, }); //滾動監聽 that.myScroll.on('scrollStart',that.showbox);//滾動監聽,1000 that.myScroll.on('scrollEnd',that.scrollaction);//滾動監聽,1000 //把數據放在緩存里面 var session_name=that.$route.path; var session_all={}; session_all.name=session_name; session_all.data1=that._data.demoData; session_all.data2=that._data.demoData2; session_all.scroll_y = 0; session_all.iscrollaction=that.iscrollaction; session_all.startnum= that.param.startnum; session_all.other= that.param.other; session_all.message= that.message; session_all.classid= that.param.classid; var session_all = JSON.stringify(session_all); sessionStorage[session_name]=session_all; }) }, function (response) { //取消加載效果 loadingToast.css('display', 'none'); that.message='服務器維護,請稍后重試'; }); },
遇到的困難
最折磨我的還是iscroll的問題,我們用的vue,所以呢 我的點擊都是用v-on:click 這種方式來完成的,但是呢,剛開始用iscroll的時候,點擊不生效,后來是給 iscroll的options.click 設置為true 才可以點擊。
后來有一個難題是:在滑動過程中點擊會出發跳轉,(本意是滑動一下會再次點擊希望他停止滑動,卻發生了跳轉),造成了不好的體驗。我去看了其他的網站, 有的安卓會發生,蘋果不會,有的是蘋果發生,安卓不會。讓我不知道應該怎么辦。
總結
sessionStorage 和 localStorage的區別
而localStorage用于持久化的本地存儲,除非主動刪除數據,否則數據是永遠不會過期的。
以上所述是小編給大家介紹的vue實現新聞展示頁的步驟詳解,希望對大家有所幫助,如果大家有任何疑問請給我留言,小編會及時回復大家的。在此也非常感謝大家對武林網網站的支持!
如果你覺得本文對你有幫助,歡迎轉載,請注明出處,謝謝!
新聞熱點
疑難解答