前言
Ionic是目前较为流行的Hybird App解决方案,在Ionic开发过程当中会遇到不少常见的开发问题,本文尝试对这些问题给出解决方案。javascript
一些常识与技巧
list
有延迟,能够在ion-content
处使用overflow-scroll="true"
尝试- 在
<i>
上用ng-click
上是没效果的 <label>
标签内的事件会在整个label
内被触发,点哪都触发- 快捷修改背景色
style=""
- 能用
ng-if
就用ng-if
,ng-if
的效率比ng-show
和ng-hide
高 - 直接在
ion-list
中的ion-item
中并不能触发ng-click
事件,能够在item中的元素上再套一层div - 能够用
ng-class="{'important': post.important}"
配合css 根据列表元素显示不一样的效果 - 获取日期用
$filter
,var postdate = $filter('date')(date, 'yyyy-MM-dd HH:mm:ss');
- 列表中的元素不能写成
id : 4
,应写成id : "4"
,注意在建立id变量的时候也须要转成string,如var id = InfoListService.getListLength()+1+"";
- 使用
$log
进行log输出,为何用$log
而不是console.log呢?能够看看这个 - 在安卓上的体验比较差,动画有延迟?能够试试ionic集成的crosswalk
controllers
和services
的文件名可能会重合,可是他们意义差很少,能够将controllers
中的文件名小写,对应的services
中的文件名大写进行区分,或者加后缀xxxControler
,xxxService
问题列表
- 如何在某个界面中去掉导航栏?
- 如何在ionic中加载本地图片?
- 如何在ionic中嵌入网页代码?
- 如何将template加载到某个tab或某个sidemenu项目下?
- 运行serve命令时ionic报错?
- 用docker跑ionic的时候,不能把地址绑定到0.0.0.0怎么处理?
- 加载页面的时候会看到双括号一闪而过?
- 更新了数据,如何让界面更新呢?
- 如何实现IonicView中card上面有一列分割线的效果?
- controller.js和service.js文件愈来愈大怎么办?
- 如何寻找优秀的范例代码?
- 如何显示相对时间?
- 发布应用的时候若是遇到翻译错误即MissingTranslation怎么办?
- 如何在列表右下方添加时间等信息?
- 如何回到上一页面?
- 如何关闭应用?
- 在安卓设备上如何让title居中?
- 如何让在sidemenu中的headerbar可以显示头像等其余信息?
- ionic的subheader挡住了内容区域怎么办?
- 对于须要添加数据的list,在添加数据后页面不能及时刷新形成卡顿怎么办?
- ionic如何处理回退按钮?例如询问用户是否真的要退出应用
- ionic如何实现对每一个请求都添加认证信息或认证失败自动从新登陆?
- ionic如何实现搜索框内的所有清除按钮?
如何在某个界面中去掉导航栏?
若是某个界面上不想要导航栏,能够简单地在最顶端的标签中添加hide-nav-bar="true"
css
如何在ionic中加载本地图片?
对于css文件夹中的样式文件中若是要调用本地的图片的话,从该css文件所在的文件夹开始算,例如www/css/style.css
要加../
,不然在浏览器中能够正常显示,在设备上不行,结构以下所示:html
.login-page { background:url(../img/signup_bg.png); background-size: cover; background-repeat: no-repeat; }
可是对于在页面中定义的图片路径,从www
路径开始算,不然浏览器中可显示,但设备上不行,img文件夹和index.html在一级,如:java
<img src="img/commander.jpg">
如何在ionic中嵌入网页代码?
使用ng-bind-html
这个类,不过它会过滤原始html的标签,咱们能够引入$sce
模块,用$sce.trustAsHtml()
方法信任咱们获取的网页android
如何将template加载到某个tab或某个sidemenu项目下?
<ion-nav-view name="menuContent">
能够指定name
,而后在子状态中使用该name
,ionic就知道该把该状态的template渲染到哪边了。例如:ios
// signup page .state('auth.signup', { url: '/signup', views: { 'auth-signup': { templateUrl: 'templates/auth-signup.html', controller: 'SignUpCtrl' } } }) 另有一个tabs中声明该auth-signup: <ion-tab title="Sign Up" icon-on="ion-ios-personadd" icon-off="ion-ios-personadd-outline" href="#/auth/signup"> <ion-nav-view name="auth-signup"></ion-nav-view> </ion-tab>
运行serve命令时ionic报错?
ionic $ An uncaught exception occured and has been reported to Ionic
看看你是不还有一个终端在运行着serve呢?
用docker跑ionic的时候,不能把地址绑定到0.0.0.0怎么处理?
能够用ionic serve -all
的方法解决git
加载页面的时候会看到双括号一闪而过?
angularjs
在使用双括号的时候,第一个加载的页面,也就是应用中的index.html
,其未被渲染好的模版可能会被用户看到。用ng-bind
就不会遇到这个问题。形成这种现象的缘由是,浏览器须要首先加载HTML页面,渲染它,而后Angular
才有机会把它解释成你指望看到的内容。不过好消息是,在大多数的模版中你依然可使用双括号.可是对于index.html页面中的数据绑定操做,建议使用ng-bind
。angularjs
ng-bind
使用方式以下: <p ng-bind="greeting"></p>
github
更新了数据,如何让界面更新呢?
能够用广播,注意$broadcast 和 $emit的区别docker
如何实现IonicView中card上面有一列分割线的效果?
在css里定义
#info-up { border-top: 4px solid #f06336; }
controller.js和service.js文件愈来愈大怎么办?
全部的控制器没必要都放在controllers.js这一个文件中,能够新建controllers文件夹,
而后把每一个controller都建一个.js文件,同理services和utils等都是.但注意要在index.html中head部分声明.可是为了不他们相互覆盖,第一个加载的js中模块中要加[…],其余都不须要。如:
// File : /js/directives/mainDirective.js angular.module('app.directives',[]); // File : /js/directives/myGreatDirective.js angular.module('app.directives') .directive('myGreatDirective', function(){ return { //... } }); // File : /js/directives/myBetterDirective.js angular.module('app.directives') .directive('myBetterDirective', function(){ return { //... } }); ...
看angularjs-code-organization了解更多,嗯这篇文章写的还不是best practice,由于你还得记着本身把[]写到那个模块里了,统一地写在app.js中便可,在app.js最下面加上相似:
angular.module('fcws.controllers',['ionic', 'fcws.services']); angular.module('fcws.services', []);
能够达到和上面同样的效果,并且能够统一管理.
如何寻找优秀的范例代码?
目前有些ionic 的app没有进行代码混淆,至少ionic官方的ionic view没有进行代码混淆,下载他们的app,文件名改为zip,解压,全部的 www文件都在assets文件夹中,至关于开源了有木有,看看那些最优秀的practice。看中哪些优秀的app,下下来,如何在googleplay上下载?把googleplay应用的地址贴到apps.evozi中。
如何显示相对时间?
如几分钟前,几天前等,能够用momentjs,看这篇教程
发布应用的时候若是遇到翻译错误即MissingTranslation怎么办?
暂时的解决方法是,不进行翻译校订, 在 /platforms/android/build.gradle 中的android {}节中加入:
lintOptions { disable 'MissingTranslation' disable 'ExtraTranslation' }
如何在列表右下方添加时间等信息?
span
能够用来将时间之类的附加信息显示到列表右边,以下面会将建立时间显示在name的右边:
<ion-item class="item item-avatar-left " ng-repeat="message in messages"> <img src="../../img/commander.jpg"> <span class="item-note">{{message.create_at}}</span> <h2 >{{message.name}}</h2> <p > {{message.content}}</p> </ion-item >
如何回到上一页面?
用$ionicHistory
这个模块,引入该模块后使用goBack([backCount])
,backCount指定回去多少个页面(-1表明回去一个页面),默认为-1
如何关闭应用?
ionic.Platform.exitApp();
在安卓设备上如何让title居中?
在headerbar中添加align-title="center"
,如:
<ion-header-bar class="bar-positive" align-title="center"> <h1 class="title">{{username}}</h1> </ion-header-bar>
不过这个设置对ion-view无效,亲测,若是要统一让全部navbar上的title居中(包括上面的headerbar),能够在config里设置,如:
.config(function($stateProvider, $urlRouterProvider,$ionicConfigProvider) { $ionicConfigProvider.navBar.alignTitle('center'); ...
若是要让某一个view title居中,能够用$ionicNavBarDelegate
,参考ionic官方文档
如何让在sidemenu中的headerbar可以显示头像等其余信息?
解决方案是去掉headerbar,添加一个avatar到sidemenu content中,如:
<ion-side-menu side="left"> <ion-content class="bar-positive"> <ion-list> <ion-item class="item item-avatar item-positive" href="#"> <img src="img/commander.jpg"> <h2 class=" light"> <i class="icon ion-ios-star"></i>{{title}} </h2> <a>{{username}}</a> </ion-item>
ionic的subheader挡住了内容区域怎么办?
解决方案是给<ion-content>
加类has-subheader
,同理也能够加has-header
。以下:
<ion-content class="has-header has-subheader">
对于须要添加数据的list,在添加数据后页面不能及时刷新形成卡顿怎么办?
可使用$ionicScrollDelegate.resize();
在添加数据后手动进行从新刷新,记得添加依赖
ionic如何处理回退按钮?例如询问用户是否真的要退出应用
能够在app.js的.run方法中增长对硬件回退按钮的注册处理,这里我在大部分页面都想注册该事件,除去有二级历史页面的我单独判断了下,注意增长依赖。
$ionicPlatform.registerBackButtonAction(function(e) { var current_state_name = $state.current.name; if(current_state_name !== 'sidemenu.post' && current_state_name !== 'sidemenu.contact_town' && current_state_name !== 'sidemenu.contact_people'){ $ionicPopup.confirm({ title: '退出应用', template: '您肯定要退出xxxx吗?' }).then(function (res) { if (res) { //ionic.Platform.exitApp(); navigator.app.exitApp(); } else { console.log('You are not sure'); } }); e.preventDefault(); return false; }else{ navigator.app.backHistory(); } },100);
ionic如何实现对每一个请求都添加认证信息或认证失败自动从新登陆?
在应用的注册或者登陆部分,不记名token
响应了这个请求而且这个token
被存储到本地存储中。当你向后端请求一个服务时,你须要把这个token
放在头部中。你能够在app.js
的.config
方法中使用AngularJS
的拦截器实现这个。每次请求都会被拦截而且会把认证头部和值放到头部中,同理若是服务器端响应401
或403
,跳转到从新登陆页面.
$httpProvider.interceptors.push(function ($q, $location, User, $rootScope) { return { 'request': function (config) { config.headers = config.headers || {}; if (User.getToken()) { config.headers.Authorization = 'Bearer ' + User.getToken(); } return config; }, 'responseError': function (response) { if (response.status === 401 || response.status === 403) { //若是以前登录过 if (User.getToken()) { $rootScope.$broadcast('unAuthenticed'); } } return $q.reject(response); } }; });
ionic如何实现搜索框内的所有清除按钮?
在label中的input不能嵌入按钮,由于ionic对于label中的tap事件会进行重定向到input上。解决方案是将label替换成span或div。以下面的搜索框,注意ng-model须要是一个对象才能置空,变量不行:
<span class="item-input-wrapper"> <i class="icon ion-ios-search placeholder-icon"></i> <input type="search" placeholder="请输入姓名前缀" ng-model="search.key"> <i class="icon ion-close-circled placeholder-icon" style="vertical-align: middle;" on-tap="clearSearch()" ng-if="search.key.length"></i> </span>
ps: 附上博客的原文地址