[ionic开源项目教程] - 第8讲 根据菜单分类加载数据(重要)
[ionic开源项目教程] - 第8讲 根据菜单分类加载数据(重要)
[效果图]

注意
今天遇到一个比较棘手的问题,就是左右滑动菜单的设计不合理性,所以tab1.html对应的视图层和controller层都有所改动,最关键最核心的代码在service层,可能会有点不好理解,我会尽量讲明白。
1.tab1.html的要做一些调整: 这里我把tab1.html的完整代码贴出来,有以下几点改动
- 1. ion-content:内容标签的位置放到了ion-slide内层和list外层,这样做的目的是解决多个滑动列表不相互干扰。
- 2. slide.items:对list的数据源做了一层包装,这样做的目的是多个列表的数据不相互干扰。
3. doRefresh下拉刷新和loadMore上拉加载和list的数据源items一样也做了一层包装。
<ion-view view-title="健康">
<ion-slide-box show-pager="false" on-slide-changed="slideChanged($index)">
<ion-slide ng-repeat="slide in slides">
<ion-content>
<ion-refresher pulling-text="下拉刷新" on-refresh="slide.doRefresh()"></ion-refresher>
<div class="list has-header">
<a ng-repeat="item in slide.items" class="item item-thumbnail-right item-text-wrap" href="#">
<img ng-src="{{imgUrl+item.img}}" width="30" height="30" alt="">
<h3>{{item.title}}</h3>
<p>{{item.description | substring:item.description}}</p>
</a>
</div>
<ion-infinite-scroll ng-if="!slide.isload" on-infinite="slide.loadMore()" distance="1%">
</ion-infinite-scroll>
</ion-content>
</ion-slide>
</ion-slide-box>
<ion-tabs class="tabs-striped tabs-top">
<ion-tab ng-repeat="item in tabs" on-select="selectedTab($index)" title="{{item.name}}"></ion-tab>
</ion-tabs>
</ion-view>
2.controller.js层Tab1Ctrl的实现
需要注意的地方:
1.此次controller的改动的代码比较少,下拉刷新doRefresh和上拉加载loadMore都放到了service层。
2.使用了ion-infinite-scroll标签后,controller页面初始化的时候会自动触发loadMore函数,但在android平台这个函数不会触发,所以做了判断。
.controller('Tab1Ctrl', function ($scope, $rootScope, $timeout, Tab1Service, $ionicSlideBoxDelegate, $ionicTabsDelegate) {
$rootScope.imgUrl = server.imgUrl;
var classify = Tab1Service.getClassify()
$scope.slides = classify;
$scope.tabs = classify;
var getData = function (index) {
var c = classify[index];
// 安卓平台不会自动触发加载
if (ionic.Platform.isAndroid()) {
c.doRefresh();
}
// 初始化数据,和回调函数
c.isload = false;
c.callback = function () {
$scope.$broadcast('scroll.refreshComplete');
$scope.$broadcast('scroll.infiniteScrollComplete');
}
}
getData(0);
$scope.slideChanged = function (index) {
getData(index);
//这里使用instances[1]的原因是视图中有两个tabs
$ionicTabsDelegate._instances[1].select(index);
};
$scope.$on('$ionicView.afterEnter', function () {
//等待视图加载完成的时候默认选中第一个菜单
$ionicTabsDelegate._instances[1].select($ionicSlideBoxDelegate.currentIndex());
});
$scope.selectedTab = function (index) {
//滑动的索引和速度
$ionicSlideBoxDelegate.slide(index)
}
3.最难理解的service层
service层对不同的分类做了函数封装。每个分类都有自己的数据源items[]、doRefresh(下拉加载)、loadMore(加载更多),各个分类的数据加载都互不影响。视图层是直接通过controller为载体调用的service的函数。下面介绍下各个属性的说明:
- name:菜单名
- isload:是否加载
- url:接口
- page:页数
- row:每页请求的条数(暂时没用到,这里做为备用参数),现在的页数都是用的全局配置config.js中的settings.rows
- items:数据列表
- loadMore:上拉加载更多 。
- doRefresh:下拉刷新。
callback:回掉函数,在loadMore和doRefresh操作完成都会调用该函数。
.service('Tab1Service', function ($http) {
this.getClassify = function () {
return [
{
name: '健康资讯', isload: true, url: server.domain + '/info/list',
page: 1, rows: 20,
items: [],
loadMore: function () {
$this = this;
console.log("正在加载更多数据..." + this.page);
$http.get(this.url + "?page=" + this.page + "&rows=" + settings.rows).success(function (response) {
$this.items = $this.items.concat(response.tngou);
$this.page++;
$this.callback();
});
},
doRefresh: function () {
$this = this;
console.log("正在执行refresh操作...");
$http.get(this.url + "?page=1&rows=" + settings.rows).success(function (response) {
$this.page = 2;
$this.items = response.tngou;
$this.callback();
});
},
callback: function () {
//回掉函数
}
},
{
name: '健康知识', isload: true, url: server.domain + '/lore/list',
page: 1, rows: 20,
items: [],
loadMore: function () {
$this = this;
console.log("正在加载更多数据..." + this.page);
$http.get(this.url + "?page=" + this.page + "&rows=" + settings.rows).success(function (response) {
$this.items = $this.items.concat(response.tngou);
$this.page++;
$this.callback();
});
},
doRefresh: function () {
$this = this;
console.log("正在执行refresh操作...");
$http.get(this.url + "?page=1&rows=" + settings.rows).success(function (response) {
$this.page = 2;
$this.items = response.tngou
$this.callback();
});
},
callback: function () {
//回掉函数
}
},
{
name: '健康问答', isload: true, url: server.domain + '/ask/list',
page: 1, rows: 20,
items: [],
loadMore: function () {
$this = this;
console.log("正在加载更多数据..." + this.page);
$http.get(this.url + "?page=" + this.page + "&rows=" + settings.rows).success(function (response) {
$this.items = $this.items.concat(response.tngou);
$this.page++;
$this.callback();
});
},
doRefresh: function () {
$this = this;
console.log("正在执行refresh操作...");
$http.get(this.url + "?page=1&rows=" + settings.rows).success(function (response) {
$this.page = 2;
$this.items = response.tngou
$this.callback();
});
},
callback: function () {
//回掉函数
}
}
]
}
})
4.难点
- 搞清楚视图层的包含关系
- 对service层代码的理解
有什么不理解的地方欢迎加入 [Tonge移动开发交流群] 群号:111055535。
完!
[ionic开源项目教程] - 第8讲 根据菜单分类加载数据(重要)的更多相关文章
- [ionic开源项目教程] - 第4讲 通Service层获取数据列表
第4讲:通Service层获取数据列表 上一讲中页面的基本架构已完成,这一讲介绍如何通过service层从服务器请求数据,在通过controller层为载体,显示到视图层. 1.在services.j ...
- [ionic开源项目教程] - 第11讲 封装BaseController实现controller继承
关注微信订阅号:TongeBlog,可查看[ionic开源项目]全套教程. 截止到第10讲,tab1[健康]模块的功能基本已经完成了,但这一讲中,controller层又做了较大的改动,因为下一讲中t ...
- [ionic开源项目教程] - 第10讲 新闻详情页的用户体验优化
目录 [ionic开源项目教程] 第1讲 前言,技术储备,环境搭建,常用命令 [ionic开源项目教程] 第2讲 新建项目,架构页面,配置app.js和controllers.js [ionic开源项 ...
- [ionic开源项目教程] - 第9讲 新闻详情页的实现
目录 [ionic开源项目教程] 第1讲 前言,技术储备,环境搭建,常用命令 [ionic开源项目教程] 第2讲 新建项目,架构页面,配置app.js和controllers.js [ionic开源项 ...
- [ionic开源项目教程] - 第14讲 ionic解决跨域问题
[ionic开源项目教程] 第14讲 使用jsonp解决跨域问题 相信很多朋友在开发中都会遇到以下这个问题. No 'Access-Control-Allow-Origin' header is pr ...
- [ionic开源项目教程] - 第12讲 医疗模块的实现以及Service层loadMore和doRefresh的提取封装
关注微信订阅号:TongeBlog,可查看[ionic开源项目]全套教程. 这一讲主要实现tab2[医疗]模块,[医疗]模块跟tab1[健康]模块类似. [ionic开源项目教程] - 第12讲 医疗 ...
- [ionic开源项目教程] - 第13讲 Service层优化,提取公用Service,以及生活和农业两大模块的实现
关注微信订阅号:TongeBlog,可查看[ionic开源项目]全套教程. 这一讲主要实现生活和农业两大模块的实现,在这个过程中,对service层提取出一个公用的BaseService. 这一讲分为 ...
- [ionic开源项目教程] - 第2讲 新建项目,配置app.js和controllers.js搭建基础视图
新建项目 由项目功能架构图选择合适的页面架构,这里选用Tab,ionic新建项目,默认的模板就是tab. $ ionic start TongeNews Creating Ionic app in f ...
- [ionic开源项目教程] - 第15讲 ionic用户个人中心登录注册的实现
第15讲 ionic用户个人中心登录注册的实现 这一讲包括登陆.注册.个人中心.个人资料页面的实现. 在一讲的改动有四个地方: 在config.js里配置接口地址 完善个人中心的服务层(service ...
随机推荐
- 一些实用的 jQuery 技巧
jQuery如今已经成为Web开发中最流行的JavaScript库,通过jQuery和大量的插件,你可以轻松实现各种绚丽的效果. 本文将为你介绍一些实用的技巧,希望可以帮助你更加高效地使用jQuery ...
- var 和 dynamic在实际项目中的应用
先回顾一下这两个关键词的用法. var是个语法糖,是在用var声明变量的那一刻就确定了其变量的类型. 因为需要在声明的时候就确定其类型,所以要求在用var声明隐式局部变量的时候必须初始化该变量. 编译 ...
- Sqli-labs less 30
Less-30 Less-30与less-29原理是一致的,我们可以看到less-30的sql语句为: 所以payload为: http://127.0.0.1:8080/sqli-labs/Less ...
- D3D depth buffer的预览
在使用D3D开发游戏的过程中,很多情况下都会用到depth buffer来完成特定的效果,比如DOF,Shadows,SSAO等等.在这些情况下我们就可能需要预览depth buffer来确定它是正确 ...
- IE8中能继续使用Expression的解决方案
在实际工作中,长的报表需要固定表头,比如DataGrid等控件. 过去在用IE8以前版本的时候,只需要在css中加上 position:relative ; top:expresion(this.of ...
- 服务接口API限流 Rate Limit 续
一.前言 上一篇文章中粗浅的介绍使用Redis和基于令牌桶算法进行对服务接口API限流,本文介绍另一种算法---漏桶算法的应用.Nginx想必大家都有所了解是一个高性能的 HTTP 和反向代理服务器, ...
- vc++ 获取当前用户名
#include<afxwin.h> #include <stdio.h> int main(void) { char userName[MAX_PATH]; unsigned ...
- 线性时间常数空间找到数组中数目超过n/5的所有元素
问题描述: Design an algorithm that, given a list of n elements in an array, finds all the elements that ...
- Ado.Net要知道的东西
什么是ADO.NET? ADO.NET就是一组类库,这组类库可以让我们通过程序的方式访问数据库,就像System.IO下的类用类操作文件一样,System.Data.这组类是用来操作数据库(不光是MS ...
- lintcode :最近公共祖先
题目 最近公共祖先 给定一棵二叉树,找到两个节点的最近公共父节点(LCA). 最近公共祖先是两个节点的公共的祖先节点且具有最大深度. 样例 对于下面这棵二叉树 4 / \ 3 7 / \ 5 6 LC ...