
首届流应用开发大赛名单揭晓,大众点评、京东、有道等获奖
由DCloud、36氪、CSDN联合举办的首届中国流应用开发大赛,经过一个月的选拨和评选,获奖名单正式揭晓。活动期间,数百人报名参赛,无论是一线互联网公司如大众点评、京东、网易,还是创业公司,如挑食火锅、艺人捧场,都积极开发流应用,流应用在营销、用户和订单获取、开发成本节约等方面的价值成功的吸引了App厂商。
本次大赛的中奖名单如下:
一、优秀应用奖
获奖名单(4名):
大众点评外卖、大众点评爱美丽、有道词典、京东秒杀
奖励:应用商店价值5万元的推广资源
二、优秀创业奖
获奖名单(4名):
挑食火锅、宝贝租车、艺人捧场,弈客围棋
奖励:知名创业媒体36氪提供的融资平台三天banner展示位广告资源,知名投资人约见机会。
提示:体验获奖流应用的方式:使用安装360手机助手的安卓手机,点击下面的图片链接,根据提示在外部浏览器中打开,即可体验。
1.大众点评外卖

流应用体验二维码
2.大众点评爱美丽
流应用体验二维码
3.有道词典
流应用体验二维码
4.京东秒杀
流应用体验二维码
5.挑食火锅
流应用体验二维码
6.宝贝租车
流应用体验二维码
7.艺人捧场
流应用体验二维码
8.弈客围棋
除了上述获奖的App,还有很多创业者开发了体验优质的流应用,如HiMall、枫桥居花卉等。
优秀创业者获得36Kr融资频道Banner宣传:
关于流应用:流应用是DCloud公司开发的一种可以让手机App安装包实现边用边下的技术。利用js的动态语言特点,把手机端App的安装包拆解,流式下载到手机端。类似流媒体边看边下一样,流应用也可以边用边下。再辅以特殊的压缩解码技术,使得流应用可以在5秒内完成App的下载-安装-启动全过程。流应用使用的js经过了强化,可以调用原生40多万API,使得流应用的功能和体验都达到了原生水准。
本次流应用大赛之所以受到众多开发者如此关注,主要得益于流应用具有的开发者优势和用户优势。
在开发者优势方面:
1.降低App的开发成本和人员数量,原来App厂商需要iOS、Android、前端等三个开发团队,流应用只需要1个前端开发即可完成,并且还能打包成原生App以及发布为wap网站和公众号。高效率本就是世界进步发展趋势,在资本寒冬的今天,尤其需要这种高效率开发方案。
2.降低推广成本提高转化率,推广成本降低50-80%。原生App由于安装包比较大,从下载、到安装、到启动,使得推广成本非常高,而流应用从下载到安装启动一步到位,5秒内即可完成,使得App的推广成本降低,转化率提升50%-80%。
3.多端发布,方便测试。流应用基于mui开发App,生成流应用的同时,iOS、Android原生版、浏览器版、微信App和百度直达号版也随之生成,开发一次,多端发布,效率大幅提升,成本大幅下降。
在用户优势方面,流应用具有如下五大特点:
1.秒装秒开:流应用具有秒装秒开的功能,使得用户在下载安装的时候,5秒内即可安装启动,速度非常快。
2.差量实时更新:流应用采用自动差量更新技术,每次更新只需要2-3K流量,使得用户永远使用的都是最新版本的流应用,和原生应用更新相比,每次更新都需要重新下载安装包,启动一次来说,用户体验非常好。
3.省流量:流应用具有很多缩小应用包的专利技术,能大幅减少应用包体积,但毫不影响应用功能体验。。
- 省空间:流应用的安装包只有几百K,和原生App几十M,几百M的App相比,非常小,装一个原生App的空间可以装几十个流应用,流应用更加节省空间。
5.省电更流畅:流应用采用了包体压缩技术、差量更新技术,使得流应用对手机的内存、空间占用率非常少,非常省电,同时也更加流畅。
虽然本次大赛结束了,但流应用发展还在继续。后续提交流应用的开发者还有机会获得由DCloud提供的应用商店推广资源和机械键盘等奖励礼品,欢迎大家继续提交流应用。流应用交流QQ群:471285299。
由DCloud、36氪、CSDN联合举办的首届中国流应用开发大赛,经过一个月的选拨和评选,获奖名单正式揭晓。活动期间,数百人报名参赛,无论是一线互联网公司如大众点评、京东、网易,还是创业公司,如挑食火锅、艺人捧场,都积极开发流应用,流应用在营销、用户和订单获取、开发成本节约等方面的价值成功的吸引了App厂商。
本次大赛的中奖名单如下:
一、优秀应用奖
获奖名单(4名):
大众点评外卖、大众点评爱美丽、有道词典、京东秒杀
奖励:应用商店价值5万元的推广资源
二、优秀创业奖
获奖名单(4名):
挑食火锅、宝贝租车、艺人捧场,弈客围棋
奖励:知名创业媒体36氪提供的融资平台三天banner展示位广告资源,知名投资人约见机会。
提示:体验获奖流应用的方式:使用安装360手机助手的安卓手机,点击下面的图片链接,根据提示在外部浏览器中打开,即可体验。
1.大众点评外卖
流应用体验二维码
2.大众点评爱美丽
流应用体验二维码
3.有道词典
流应用体验二维码
4.京东秒杀
流应用体验二维码
5.挑食火锅
流应用体验二维码
6.宝贝租车
流应用体验二维码
7.艺人捧场
流应用体验二维码
8.弈客围棋
除了上述获奖的App,还有很多创业者开发了体验优质的流应用,如HiMall、枫桥居花卉等。
优秀创业者获得36Kr融资频道Banner宣传:
关于流应用:流应用是DCloud公司开发的一种可以让手机App安装包实现边用边下的技术。利用js的动态语言特点,把手机端App的安装包拆解,流式下载到手机端。类似流媒体边看边下一样,流应用也可以边用边下。再辅以特殊的压缩解码技术,使得流应用可以在5秒内完成App的下载-安装-启动全过程。流应用使用的js经过了强化,可以调用原生40多万API,使得流应用的功能和体验都达到了原生水准。
本次流应用大赛之所以受到众多开发者如此关注,主要得益于流应用具有的开发者优势和用户优势。
在开发者优势方面:
1.降低App的开发成本和人员数量,原来App厂商需要iOS、Android、前端等三个开发团队,流应用只需要1个前端开发即可完成,并且还能打包成原生App以及发布为wap网站和公众号。高效率本就是世界进步发展趋势,在资本寒冬的今天,尤其需要这种高效率开发方案。
2.降低推广成本提高转化率,推广成本降低50-80%。原生App由于安装包比较大,从下载、到安装、到启动,使得推广成本非常高,而流应用从下载到安装启动一步到位,5秒内即可完成,使得App的推广成本降低,转化率提升50%-80%。
3.多端发布,方便测试。流应用基于mui开发App,生成流应用的同时,iOS、Android原生版、浏览器版、微信App和百度直达号版也随之生成,开发一次,多端发布,效率大幅提升,成本大幅下降。
在用户优势方面,流应用具有如下五大特点:
1.秒装秒开:流应用具有秒装秒开的功能,使得用户在下载安装的时候,5秒内即可安装启动,速度非常快。
2.差量实时更新:流应用采用自动差量更新技术,每次更新只需要2-3K流量,使得用户永远使用的都是最新版本的流应用,和原生应用更新相比,每次更新都需要重新下载安装包,启动一次来说,用户体验非常好。
3.省流量:流应用具有很多缩小应用包的专利技术,能大幅减少应用包体积,但毫不影响应用功能体验。。
- 省空间:流应用的安装包只有几百K,和原生App几十M,几百M的App相比,非常小,装一个原生App的空间可以装几十个流应用,流应用更加节省空间。
5.省电更流畅:流应用采用了包体压缩技术、差量更新技术,使得流应用对手机的内存、空间占用率非常少,非常省电,同时也更加流畅。
虽然本次大赛结束了,但流应用发展还在继续。后续提交流应用的开发者还有机会获得由DCloud提供的应用商店推广资源和机械键盘等奖励礼品,欢迎大家继续提交流应用。流应用交流QQ群:471285299。
收起阅读 »
Android 平台5+SDK接口说明
初始化SDK
initSDK(ICore core)
说明:
初始化SDK, SDK所有接口必须在初始化之后才可以调用
参数:
- core(ICore ) 5+内核对象
示例
@Override
public void onCoreReady(ICore coreHandler) {
try {
SDK.initSDK(coreHandler);
SDK.requestAllFeature();
} catch (Exception e) {
e.printStackTrace();
}
}
SDK集成使用方法
IApp startWebApp(Activity activity,String appBasePath,String startArgs,IWebviewStateListener listener,IOnCreateSplashView ocs)
说明:
创建并启动5+WebApp对象
参数:
- activity(Activity) Activity对象
- appBasePath(String) 移动应用所在的目录
- startArgs(String) 应用启动时传递的参数
- listener(IWebviewStateListener) Webview事件监听对象,用来监听应用的首页面加载状态
- ocs(IOnCreateSplashView) Splash事件监听对象,用来监听splash页面的加载和关闭事件
示例
public void onCoreInitEnd(ICore coreHandler) {
//创建默认webapp,
String appBasePath = "/apps/HelloH5";//表示 file:///android_asset/apps/HBuilder
String args = "{url:'http://www.baidu.com'}";//设置启动参数
app = SDK.startWebApp(activity,appBasePath, args, new IWebviewStateListener() {
@Override
public Object onCallBack(int pType, Object pArgs) {
switch (pType) {
case IWebviewStateListener.ON_WEBVIEW_READY:
//准备完毕之后添加webview到显示父View中,设置排版不显示状态,避免显示webview时,html内容排版错乱问题
View view = ((IWebview)pArgs).obtainApp().obtainWebAppRootView().obtainMainView();
view.setVisibility(View.INVISIBLE);
rootView.addView(view, 0);
break;
case IWebviewStateListener.ON_PAGE_STARTED:
break;
case IWebviewStateListener.ON_PROGRESS_CHANGED:
break;
case IWebviewStateListener.ON_PAGE_FINISHED:
//页面加载完毕,设置显示webview
app.obtainWebAppRootView().obtainMainView().setVisibility(View.VISIBLE);
break;
}
return null;
}
},this);
}
IWebview createWebview(Activity activity,String pagePath,String basePath,String docPath,String appid, String appName,IWebviewStateListener listener)
说明:
创建一个支持5+API的Webview对象
参数:
- activity(Activity) Activity对象
- pagePath(String) 页面路径
- basePath(String) 应用的默认路径
- docPath(String) 应用的doc目录路径
- appid(String) 应用的appid
- appName(String) 应用名称
- listener(IWebviewStateListener) 加载事件监听器
示例:
public void onCoreInitEnd(ICore coreHandler) {
//设置单页面集成的appid
String appid = "test1";
// 单页面集成时要加载页面的路径,可以是本地文件路径也可以是网络路径
String url = "file:///android_asset/apps/H5Plugin/www/index.html";
webview = SDK.createWebview(activity, url, appid, new IWebviewStateListener() {
@Override
public Object onCallBack(int pType, Object pArgs) {
switch (pType) {
case IWebviewStateListener.ON_WEBVIEW_READY:
// 准备完毕之后添加webview到显示父View中,设置排版不显示状态,避免显示webview时,html内容排版错乱问题
((IWebview) pArgs).obtainFrameView().obtainMainView().setVisibility(View.INVISIBLE);
SDK.attach(mRootView, ((IWebview) pArgs));
break;
case IWebviewStateListener.ON_PAGE_STARTED:
break;
case IWebviewStateListener.ON_PROGRESS_CHANGED:
break;
case IWebviewStateListener.ON_PAGE_FINISHED:
// 页面加载完毕,设置显示webview
webview.obtainFrameView().obtainMainView().setVisibility(View.VISIBLE);
break;
}
return null;
}
});
}
IWebview createWebview(Activity activity,String pagePath,String appid,IWebviewStateListener listener)
说明:
创建一个支持5+API的Webview对象
参数:
- activity(Activity) Activity对象
- pagePath(String) HTML页面的路径
- appid(String) 默认应用的APPID
- listener(IWebviewStateListener) 页面加载事件监听器
WebApp相关方法
void stopWebApp(IApp app)
说明:
停止一个正在运行的5+WebApp
参数:
app(IApp) 正在运行的WebAPP对象
String obtainCurrentRunnbingAppId()
说明:
获取当前正在运行的5+WebApp的APPID
IApp obtainCurrentApp ()
说明:
获取到当前在前台运行的5+Webapp对象
页面相关方法
ArrayList<IWebview> obtainAllIWebview()
说明:
获取运行应用的Webview对象的集合
IWebview obtainWebview(String appid,String webviewId)
说明:
根据APPID和WebviewID获取到指定的Webview对象
参数:
- appid(String) 要获取应用的APPID
- webviewId(String) 获取应用内页面的ID
IWebview obatinFirstPage(IApp app,IWebviewStateListener listener)
说明:
获取指定应用app的首页面Iwebview对象
参数:
- app(IApp) IApp对象
- listener(IWebviewStateListener) 应用首页面的加载状态的监听
void closeWebView(IWebview webview)
说明:
关闭指定IWebview页面
参数:
- webview(IWebview)
设置可使用的5+API权限
void requestAllFeature()
说明:
向5+基座申请全部扩展API调用能力
示例
public void onCoreReady(ICore coreHandler) {
try {
SDK.initSDK(coreHandler);
SDK.requestAllFeature();
} catch (Exception e) {
e.printStackTrace();
}
}
void requestFeature(String mainFeatureName,String subFeatrureName,boolean autoBoot)
说明
单独设置可以使用的API特征名
参数
- mainFeatureName(String) JS 特征名称
- subFeatrureName(String) JS特征二级名称
- autoBoot(boolean) 是否基座自动启动
示例
requestFeature("Share","share-weixin",false);
注册新扩展插件
void registerJsApi(String featureName,String className,String jsContent)
说明:
向5+SDK注册一个新的扩展API
参数:
- featureName(String) 扩展插件的JS功能名称
- className(String) 扩展插件的原生类名
- jsContent(String) 扩展插件的JS代码
示例
// 注册新的5+扩展API
private void regNewJsAPI() {
// 扩展插件的JS特征名称
String featureName = "T";
// 为处理扩展Feature的接收类全名称
String className = "com.HBuilder.integrate.webview.WebViewMode_FeatureImpl";
// content 为扩展Feature而创建的js代码
String content = "(function(plus){function test(){return plus.bridge.execSync('T','test',[arguments]);}plus.T = {test:test};})(window.plus);";
// 注册新的扩展方法
SDK.registerJsApi(featureName, className, content);
}
初始化SDK
initSDK(ICore core)
说明:
初始化SDK, SDK所有接口必须在初始化之后才可以调用
参数:
- core(ICore ) 5+内核对象
示例
@Override
public void onCoreReady(ICore coreHandler) {
try {
SDK.initSDK(coreHandler);
SDK.requestAllFeature();
} catch (Exception e) {
e.printStackTrace();
}
}
SDK集成使用方法
IApp startWebApp(Activity activity,String appBasePath,String startArgs,IWebviewStateListener listener,IOnCreateSplashView ocs)
说明:
创建并启动5+WebApp对象
参数:
- activity(Activity) Activity对象
- appBasePath(String) 移动应用所在的目录
- startArgs(String) 应用启动时传递的参数
- listener(IWebviewStateListener) Webview事件监听对象,用来监听应用的首页面加载状态
- ocs(IOnCreateSplashView) Splash事件监听对象,用来监听splash页面的加载和关闭事件
示例
public void onCoreInitEnd(ICore coreHandler) {
//创建默认webapp,
String appBasePath = "/apps/HelloH5";//表示 file:///android_asset/apps/HBuilder
String args = "{url:'http://www.baidu.com'}";//设置启动参数
app = SDK.startWebApp(activity,appBasePath, args, new IWebviewStateListener() {
@Override
public Object onCallBack(int pType, Object pArgs) {
switch (pType) {
case IWebviewStateListener.ON_WEBVIEW_READY:
//准备完毕之后添加webview到显示父View中,设置排版不显示状态,避免显示webview时,html内容排版错乱问题
View view = ((IWebview)pArgs).obtainApp().obtainWebAppRootView().obtainMainView();
view.setVisibility(View.INVISIBLE);
rootView.addView(view, 0);
break;
case IWebviewStateListener.ON_PAGE_STARTED:
break;
case IWebviewStateListener.ON_PROGRESS_CHANGED:
break;
case IWebviewStateListener.ON_PAGE_FINISHED:
//页面加载完毕,设置显示webview
app.obtainWebAppRootView().obtainMainView().setVisibility(View.VISIBLE);
break;
}
return null;
}
},this);
}
IWebview createWebview(Activity activity,String pagePath,String basePath,String docPath,String appid, String appName,IWebviewStateListener listener)
说明:
创建一个支持5+API的Webview对象
参数:
- activity(Activity) Activity对象
- pagePath(String) 页面路径
- basePath(String) 应用的默认路径
- docPath(String) 应用的doc目录路径
- appid(String) 应用的appid
- appName(String) 应用名称
- listener(IWebviewStateListener) 加载事件监听器
示例:
public void onCoreInitEnd(ICore coreHandler) {
//设置单页面集成的appid
String appid = "test1";
// 单页面集成时要加载页面的路径,可以是本地文件路径也可以是网络路径
String url = "file:///android_asset/apps/H5Plugin/www/index.html";
webview = SDK.createWebview(activity, url, appid, new IWebviewStateListener() {
@Override
public Object onCallBack(int pType, Object pArgs) {
switch (pType) {
case IWebviewStateListener.ON_WEBVIEW_READY:
// 准备完毕之后添加webview到显示父View中,设置排版不显示状态,避免显示webview时,html内容排版错乱问题
((IWebview) pArgs).obtainFrameView().obtainMainView().setVisibility(View.INVISIBLE);
SDK.attach(mRootView, ((IWebview) pArgs));
break;
case IWebviewStateListener.ON_PAGE_STARTED:
break;
case IWebviewStateListener.ON_PROGRESS_CHANGED:
break;
case IWebviewStateListener.ON_PAGE_FINISHED:
// 页面加载完毕,设置显示webview
webview.obtainFrameView().obtainMainView().setVisibility(View.VISIBLE);
break;
}
return null;
}
});
}
IWebview createWebview(Activity activity,String pagePath,String appid,IWebviewStateListener listener)
说明:
创建一个支持5+API的Webview对象
参数:
- activity(Activity) Activity对象
- pagePath(String) HTML页面的路径
- appid(String) 默认应用的APPID
- listener(IWebviewStateListener) 页面加载事件监听器
WebApp相关方法
void stopWebApp(IApp app)
说明:
停止一个正在运行的5+WebApp
参数:
app(IApp) 正在运行的WebAPP对象
String obtainCurrentRunnbingAppId()
说明:
获取当前正在运行的5+WebApp的APPID
IApp obtainCurrentApp ()
说明:
获取到当前在前台运行的5+Webapp对象
页面相关方法
ArrayList<IWebview> obtainAllIWebview()
说明:
获取运行应用的Webview对象的集合
IWebview obtainWebview(String appid,String webviewId)
说明:
根据APPID和WebviewID获取到指定的Webview对象
参数:
- appid(String) 要获取应用的APPID
- webviewId(String) 获取应用内页面的ID
IWebview obatinFirstPage(IApp app,IWebviewStateListener listener)
说明:
获取指定应用app的首页面Iwebview对象
参数:
- app(IApp) IApp对象
- listener(IWebviewStateListener) 应用首页面的加载状态的监听
void closeWebView(IWebview webview)
说明:
关闭指定IWebview页面
参数:
- webview(IWebview)
设置可使用的5+API权限
void requestAllFeature()
说明:
向5+基座申请全部扩展API调用能力
示例
public void onCoreReady(ICore coreHandler) {
try {
SDK.initSDK(coreHandler);
SDK.requestAllFeature();
} catch (Exception e) {
e.printStackTrace();
}
}
void requestFeature(String mainFeatureName,String subFeatrureName,boolean autoBoot)
说明
单独设置可以使用的API特征名
参数
- mainFeatureName(String) JS 特征名称
- subFeatrureName(String) JS特征二级名称
- autoBoot(boolean) 是否基座自动启动
示例
requestFeature("Share","share-weixin",false);
注册新扩展插件
void registerJsApi(String featureName,String className,String jsContent)
说明:
向5+SDK注册一个新的扩展API
参数:
- featureName(String) 扩展插件的JS功能名称
- className(String) 扩展插件的原生类名
- jsContent(String) 扩展插件的JS代码
示例
// 注册新的5+扩展API
private void regNewJsAPI() {
// 扩展插件的JS特征名称
String featureName = "T";
// 为处理扩展Feature的接收类全名称
String className = "com.HBuilder.integrate.webview.WebViewMode_FeatureImpl";
// content 为扩展Feature而创建的js代码
String content = "(function(plus){function test(){return plus.bridge.execSync('T','test',[arguments]);}plus.T = {test:test};})(window.plus);";
// 注册新的扩展方法
SDK.registerJsApi(featureName, className, content);
}
收起阅读 »

chrome://inspect调试html页面空白,DOM无法加载的解决方案
chrome://inspect调试html页面空白,DOM无法加载的解决方案
先描述一下问题
有一段时间没碰huilder hybird app 开发了,今天调试的时候
chrome://inspect/#devices
可以发现页面,但是打开后空白
解决方案
翻墙后就可以了,下次就不需要翻墙了
估计原因
1.chrome升级后原有配置失效
2.浏览器缓存被软件管家清掉了
chrome://inspect调试html页面空白,DOM无法加载的解决方案
先描述一下问题
有一段时间没碰huilder hybird app 开发了,今天调试的时候
chrome://inspect/#devices
可以发现页面,但是打开后空白
解决方案
翻墙后就可以了,下次就不需要翻墙了
估计原因
1.chrome升级后原有配置失效
2.浏览器缓存被软件管家清掉了
收起阅读 »

android studio 的离线打包指南在哪里?不会只有 eclipse ADT 吧?
能不能请官方出个 android studio 的离线打包指南?
android studio 都已经出几年了,也是 google 官方指定的使用的 IDE
没道理只有 eclipse ADT bundle 离线打包 的指南吧?
能不能请官方出个 android studio 的离线打包指南?
android studio 都已经出几年了,也是 google 官方指定的使用的 IDE
没道理只有 eclipse ADT bundle 离线打包 的指南吧?

【分享】一个Notification 进度条插件(android,NJS实现,直接就可使用)
如题,分享一个Notification 进度条插件(android,用js调用原生api实现,直接就可以使用).
参考1: http://ask.dcloud.net.cn/article/155
参考2:http://ask.dcloud.net.cn/question/2464
详细介绍: 最近有一个需求是,android更新资源包时,需要在通知栏里显示下载进度条,于是就搜索了下已有的解决方案
发现并没有现成的解决方案,于是参考了以上两个解决方案,结合了下,实现了直接能调用的js插件.
第一步(分析以上两种方案的缺陷):
第一种:功能上能实现需求,但是使用起来太麻烦,而且也不方便调试(需要离线打包后才能看到效果),
而且,我这里还遇到了一个问题,在 hbuild 6.9.2 中,我明明已经添加了自定义模块权限,但是却一直提示我 ***权限没有添加, 真的是把我弄的吐血了, 所以没办法,只能另谋他路.
第二种:使用起来很方便,但是却没有完全达到功能要求(只显示了普通通知,但没有显示进度条),而且在api <16 的机子上会报错.
于是在这个基础上,结合第一种方法.写了一个 工具类,实现android的通知栏控制(兼容了api11-16的通知显示)
源码:
/**
* @description njs实现android原生功能
* 1.通知栏消息
* @see http://ask.dcloud.net.cn/article/503
*
* @author dailc
* @version 1.0
* @time 2016-01-08 08:38:20
*/
(function(obj) {
var defaultTitle = '通知栏标题';
var defaultContent = '通知内容';
var defaultTicker = '通知提示';
var defaultNotifyId = 1000;
var defaultNumber = 1;
/**
* plusReady
* @param {type} callback
* @returns {Window}
*/
obj.plusReady = function(callback) {
if (window.plus) {
setTimeout(function() { //解决callback与plusready事件的执行时机问题(典型案例:showWaiting,closeWaiting)
callback();
}, 0);
} else {
document.addEventListener("plusready", function() {
callback();
}, false);
}
return this;
};
/**
* @description 比较两个版本大小
* 比较版本大小,如果新版本nowVersion大于旧版本OldResourceVersion则返回true,否则返回false
*/
function compareVersion(OldVersion, nowVersion) {
if (!OldVersion || !nowVersion || OldVersion == '' || nowVersion == '') {
return false;
}
//第二份参数 是 数组的最大长度
var OldVersionA = OldVersion.split(".", 4);
var nowVersionA = nowVersion.split(".", 4);
for (var i = 0; i < OldVersionA.length && i < nowVersionA.length; i++) {
var strOld = OldVersionA[i];
var numOld = parseInt(strOld);
var strNow = nowVersionA[i];
var numNow = parseInt(strNow);
//小版本到高版本
if (numNow > numOld
//||strNow.length>strOld.length
) {
return true;
} else if (numNow < numOld) {
return false;
}
}
//如果是版本 如 1.6 - 1.6.1
if (nowVersionA.length > OldVersionA.length && 0 == nowVersion.indexOf(OldVersion)) {
return true;
}
};
/**
* @description 通过push功能来推送消息
*/
obj.sendNotificationByPush = function() {
var options = {
cover: false
};
var str = ": 欢迎使用Html5 Plus创建本地消息!";
plus.push.createMessage(str, "LocalMSG", options);
};
(function() {
/**
* @constructor 创建通知栏进度条构造函数
*/
function NotificationCustom() {
if (plus.os.name != 'Android') {
return;
}
//当前版本号
var SystemVersion = plus.os.version;
var Context = plus.android.importClass("android.content.Context");
var main = plus.android.runtimeMainActivity();
var NotificationManager = plus.android.importClass("android.app.NotificationManager");
var nm = main.getSystemService(Context.NOTIFICATION_SERVICE)
// Notification build 要android api16以上才能使用(4.1.2以上)
var Notification = null;
if (compareVersion('4.1.1', SystemVersion) == true) {
Notification = plus.android.importClass("android.app.Notification");
} else {
Notification = plus.android.importClass("android.support.v4.app.NotificationCompat");
}
if (Notification) {
this.notifyManager = nm;
this.mNotificationBuild = new Notification.Builder(main);
//设为true代表常驻状态栏
this.mNotificationBuild.setOngoing(false);
this.mNotificationBuild.setContentTitle(defaultTitle);
this.mNotificationBuild.setContentText(defaultContent);
this.mNotificationBuild.setTicker(defaultTicker);
//默认的push图标
this.mNotificationBuild.setSmallIcon(17301620);
//设置默认声音
//console.log('默认:'+plus.android.importClass("android.app.Notification").DEFAULT_SOUND);
this.mNotificationBuild.setDefaults(plus.android.importClass("android.app.Notification").DEFAULT_SOUND);
//this.mNotificationBuild.setNumber(defaultNumber)
}
};
/**
* @description 给android通知栏发送通知
* @param {String} title 标题
* @param {String} content 内容
* @param {String} tickerTips 提示
* @param {Number} notifyId id,默认为1000
*/
NotificationCustom.prototype.setNotification = function(title, content, tickerTips,notifyId) {
if (this.mNotificationBuild == null ||
this.notifyManager == null) {
return;
}
notifyId = (typeof(notifyId)=='number')?notifyId:defaultNotifyId;
title = title || defaultTitle;
content = content || defaultContent;
tickerTips = tickerTips || defaultTicker;
this.mNotificationBuild.setContentTitle(title);
this.mNotificationBuild.setContentText(content);
this.mNotificationBuild.setTicker(tickerTips);
//默认有声音
this.mNotificationBuild.setDefaults(plus.android.importClass("android.app.Notification").DEFAULT_SOUND);
this.notifyManager.notify(notifyId, this.mNotificationBuild.build());
};
/**
* @description 设置进度条
* @param {Number} progress
* @param {String} title 标题
* @param {String} content 内容
* @param {String} tickerTips 提示
* @param {Number} notifyId id,默认为1000
*/
NotificationCustom.prototype.setProgress = function(progress, title, content, tickerTips,notifyId) {
if (this.mNotificationBuild == null ||
this.notifyManager == null) {
return;
}
notifyId = (typeof(notifyId)=='number')?notifyId:defaultNotifyId;
title = title || '正在下载';
content = content || '正在下载';
tickerTips = tickerTips || '进度提示';
// tickerTips = tickerTips || defaultTicker;
this.mNotificationBuild.setContentTitle(title);
this.mNotificationBuild.setContentText(content);
this.mNotificationBuild.setTicker(tickerTips);
//进度条显示时,默认无声音
this.mNotificationBuild.setDefaults(0);
this.mNotificationBuild.setProgress(100, progress, false);
this.notifyManager.notify(notifyId, this.mNotificationBuild.build());
};
/**
* @description 完成进度条
* @param {String} title 标题
* @param {String} content 内容
* @param {String} tickerTips 提示
* @param {Number} notifyId id,默认为1000
*/
NotificationCustom.prototype.compProgressNotification = function(title, content, tickerTips,notifyId) {
if (this.mNotificationBuild == null ||
this.notifyManager == null) {
return;
}
notifyId = (typeof(notifyId)=='number')?notifyId:defaultNotifyId;
title = title || '进度条显示完毕';
content = content || '进度条显示完毕';
tickerTips = tickerTips || '进度提示';
this.mNotificationBuild.setContentTitle(title);
this.mNotificationBuild.setContentText(content);
this.mNotificationBuild.setTicker(tickerTips);
this.mNotificationBuild.setProgress(0, 0, false);
//默认有声音
this.mNotificationBuild.setDefaults(plus.android.importClass("android.app.Notification").DEFAULT_SOUND);
this.notifyManager.notify(notifyId, this.mNotificationBuild.build());
};
/**
* @description 清除通知栏信息
* @param {Number} notifyId id,默认为1000
*/
NotificationCustom.prototype.clearNotification = function(notifyId) {
notifyId = (typeof(notifyId)=='number')?notifyId:defaultNotifyId;
if(this.notifyManager){
this.notifyManager.cancel(notifyId);
}
};
/**
* @description 清除所有通知栏信息
*/
NotificationCustom.prototype.clearAllNotification = function() {
if(this.notifyManager){
this.notifyManager.cancelAll();
}
};
obj.plusReady(function() {
obj.NotificationUtil = new NotificationCustom();
});
})();
})(window.NjsPhoneApi = {});
调用方法示例:
显示普通通知:
NjsPhoneApi.NotificationUtil.setNotification('测试标题'+staticI,'测试内容');
显示进度条代码:
function testProgress() {
//插件调用
NjsPhoneApi.NotificationUtil.setNotification("新版下载", "开始下载");
var current = 0;
NjsPhoneApi.NotificationUtil.setProgress(current); //插件调用
function progress() {
setTimeout(function() {
current += 1;
NjsPhoneApi.NotificationUtil.setProgress(current);
if(current>=100){
NjsPhoneApi.NotificationUtil.compProgressNotification("下载完成");
}else{
progress();
}
}, 100);
};
progress();
};
testProgress();//调用显示进度条
取消单条通知:(传入参数为id,不传采用默认id)
NjsPhoneApi.NotificationUtil.clearNotification();
取消所有通知:
NjsPhoneApi.NotificationUtil.clearAllNotification();
另外: 支持自定义id的通知,也就是说可以通过传入不同的id,同时显示不同的通知
效果图1:
效果图2:
示例源码:鉴于有一些朋友会有各式各样的奇怪错误,所以这里单独写了一个示例,测试了android机型(华为,联想)都是可以正常使用的.
示例源码中采用的是默认id
如题,分享一个Notification 进度条插件(android,用js调用原生api实现,直接就可以使用).
参考1: http://ask.dcloud.net.cn/article/155
参考2:http://ask.dcloud.net.cn/question/2464
详细介绍: 最近有一个需求是,android更新资源包时,需要在通知栏里显示下载进度条,于是就搜索了下已有的解决方案
发现并没有现成的解决方案,于是参考了以上两个解决方案,结合了下,实现了直接能调用的js插件.
第一步(分析以上两种方案的缺陷):
第一种:功能上能实现需求,但是使用起来太麻烦,而且也不方便调试(需要离线打包后才能看到效果),
而且,我这里还遇到了一个问题,在 hbuild 6.9.2 中,我明明已经添加了自定义模块权限,但是却一直提示我 ***权限没有添加, 真的是把我弄的吐血了, 所以没办法,只能另谋他路.
第二种:使用起来很方便,但是却没有完全达到功能要求(只显示了普通通知,但没有显示进度条),而且在api <16 的机子上会报错.
于是在这个基础上,结合第一种方法.写了一个 工具类,实现android的通知栏控制(兼容了api11-16的通知显示)
源码:
/**
* @description njs实现android原生功能
* 1.通知栏消息
* @see http://ask.dcloud.net.cn/article/503
*
* @author dailc
* @version 1.0
* @time 2016-01-08 08:38:20
*/
(function(obj) {
var defaultTitle = '通知栏标题';
var defaultContent = '通知内容';
var defaultTicker = '通知提示';
var defaultNotifyId = 1000;
var defaultNumber = 1;
/**
* plusReady
* @param {type} callback
* @returns {Window}
*/
obj.plusReady = function(callback) {
if (window.plus) {
setTimeout(function() { //解决callback与plusready事件的执行时机问题(典型案例:showWaiting,closeWaiting)
callback();
}, 0);
} else {
document.addEventListener("plusready", function() {
callback();
}, false);
}
return this;
};
/**
* @description 比较两个版本大小
* 比较版本大小,如果新版本nowVersion大于旧版本OldResourceVersion则返回true,否则返回false
*/
function compareVersion(OldVersion, nowVersion) {
if (!OldVersion || !nowVersion || OldVersion == '' || nowVersion == '') {
return false;
}
//第二份参数 是 数组的最大长度
var OldVersionA = OldVersion.split(".", 4);
var nowVersionA = nowVersion.split(".", 4);
for (var i = 0; i < OldVersionA.length && i < nowVersionA.length; i++) {
var strOld = OldVersionA[i];
var numOld = parseInt(strOld);
var strNow = nowVersionA[i];
var numNow = parseInt(strNow);
//小版本到高版本
if (numNow > numOld
//||strNow.length>strOld.length
) {
return true;
} else if (numNow < numOld) {
return false;
}
}
//如果是版本 如 1.6 - 1.6.1
if (nowVersionA.length > OldVersionA.length && 0 == nowVersion.indexOf(OldVersion)) {
return true;
}
};
/**
* @description 通过push功能来推送消息
*/
obj.sendNotificationByPush = function() {
var options = {
cover: false
};
var str = ": 欢迎使用Html5 Plus创建本地消息!";
plus.push.createMessage(str, "LocalMSG", options);
};
(function() {
/**
* @constructor 创建通知栏进度条构造函数
*/
function NotificationCustom() {
if (plus.os.name != 'Android') {
return;
}
//当前版本号
var SystemVersion = plus.os.version;
var Context = plus.android.importClass("android.content.Context");
var main = plus.android.runtimeMainActivity();
var NotificationManager = plus.android.importClass("android.app.NotificationManager");
var nm = main.getSystemService(Context.NOTIFICATION_SERVICE)
// Notification build 要android api16以上才能使用(4.1.2以上)
var Notification = null;
if (compareVersion('4.1.1', SystemVersion) == true) {
Notification = plus.android.importClass("android.app.Notification");
} else {
Notification = plus.android.importClass("android.support.v4.app.NotificationCompat");
}
if (Notification) {
this.notifyManager = nm;
this.mNotificationBuild = new Notification.Builder(main);
//设为true代表常驻状态栏
this.mNotificationBuild.setOngoing(false);
this.mNotificationBuild.setContentTitle(defaultTitle);
this.mNotificationBuild.setContentText(defaultContent);
this.mNotificationBuild.setTicker(defaultTicker);
//默认的push图标
this.mNotificationBuild.setSmallIcon(17301620);
//设置默认声音
//console.log('默认:'+plus.android.importClass("android.app.Notification").DEFAULT_SOUND);
this.mNotificationBuild.setDefaults(plus.android.importClass("android.app.Notification").DEFAULT_SOUND);
//this.mNotificationBuild.setNumber(defaultNumber)
}
};
/**
* @description 给android通知栏发送通知
* @param {String} title 标题
* @param {String} content 内容
* @param {String} tickerTips 提示
* @param {Number} notifyId id,默认为1000
*/
NotificationCustom.prototype.setNotification = function(title, content, tickerTips,notifyId) {
if (this.mNotificationBuild == null ||
this.notifyManager == null) {
return;
}
notifyId = (typeof(notifyId)=='number')?notifyId:defaultNotifyId;
title = title || defaultTitle;
content = content || defaultContent;
tickerTips = tickerTips || defaultTicker;
this.mNotificationBuild.setContentTitle(title);
this.mNotificationBuild.setContentText(content);
this.mNotificationBuild.setTicker(tickerTips);
//默认有声音
this.mNotificationBuild.setDefaults(plus.android.importClass("android.app.Notification").DEFAULT_SOUND);
this.notifyManager.notify(notifyId, this.mNotificationBuild.build());
};
/**
* @description 设置进度条
* @param {Number} progress
* @param {String} title 标题
* @param {String} content 内容
* @param {String} tickerTips 提示
* @param {Number} notifyId id,默认为1000
*/
NotificationCustom.prototype.setProgress = function(progress, title, content, tickerTips,notifyId) {
if (this.mNotificationBuild == null ||
this.notifyManager == null) {
return;
}
notifyId = (typeof(notifyId)=='number')?notifyId:defaultNotifyId;
title = title || '正在下载';
content = content || '正在下载';
tickerTips = tickerTips || '进度提示';
// tickerTips = tickerTips || defaultTicker;
this.mNotificationBuild.setContentTitle(title);
this.mNotificationBuild.setContentText(content);
this.mNotificationBuild.setTicker(tickerTips);
//进度条显示时,默认无声音
this.mNotificationBuild.setDefaults(0);
this.mNotificationBuild.setProgress(100, progress, false);
this.notifyManager.notify(notifyId, this.mNotificationBuild.build());
};
/**
* @description 完成进度条
* @param {String} title 标题
* @param {String} content 内容
* @param {String} tickerTips 提示
* @param {Number} notifyId id,默认为1000
*/
NotificationCustom.prototype.compProgressNotification = function(title, content, tickerTips,notifyId) {
if (this.mNotificationBuild == null ||
this.notifyManager == null) {
return;
}
notifyId = (typeof(notifyId)=='number')?notifyId:defaultNotifyId;
title = title || '进度条显示完毕';
content = content || '进度条显示完毕';
tickerTips = tickerTips || '进度提示';
this.mNotificationBuild.setContentTitle(title);
this.mNotificationBuild.setContentText(content);
this.mNotificationBuild.setTicker(tickerTips);
this.mNotificationBuild.setProgress(0, 0, false);
//默认有声音
this.mNotificationBuild.setDefaults(plus.android.importClass("android.app.Notification").DEFAULT_SOUND);
this.notifyManager.notify(notifyId, this.mNotificationBuild.build());
};
/**
* @description 清除通知栏信息
* @param {Number} notifyId id,默认为1000
*/
NotificationCustom.prototype.clearNotification = function(notifyId) {
notifyId = (typeof(notifyId)=='number')?notifyId:defaultNotifyId;
if(this.notifyManager){
this.notifyManager.cancel(notifyId);
}
};
/**
* @description 清除所有通知栏信息
*/
NotificationCustom.prototype.clearAllNotification = function() {
if(this.notifyManager){
this.notifyManager.cancelAll();
}
};
obj.plusReady(function() {
obj.NotificationUtil = new NotificationCustom();
});
})();
})(window.NjsPhoneApi = {});
调用方法示例:
显示普通通知:
NjsPhoneApi.NotificationUtil.setNotification('测试标题'+staticI,'测试内容');
显示进度条代码:
function testProgress() {
//插件调用
NjsPhoneApi.NotificationUtil.setNotification("新版下载", "开始下载");
var current = 0;
NjsPhoneApi.NotificationUtil.setProgress(current); //插件调用
function progress() {
setTimeout(function() {
current += 1;
NjsPhoneApi.NotificationUtil.setProgress(current);
if(current>=100){
NjsPhoneApi.NotificationUtil.compProgressNotification("下载完成");
}else{
progress();
}
}, 100);
};
progress();
};
testProgress();//调用显示进度条
取消单条通知:(传入参数为id,不传采用默认id)
NjsPhoneApi.NotificationUtil.clearNotification();
取消所有通知:
NjsPhoneApi.NotificationUtil.clearAllNotification();
另外: 支持自定义id的通知,也就是说可以通过传入不同的id,同时显示不同的通知
效果图1:
效果图2:
示例源码:鉴于有一些朋友会有各式各样的奇怪错误,所以这里单独写了一个示例,测试了android机型(华为,联想)都是可以正常使用的.
示例源码中采用的是默认id

判断手机已安装某APP的方法(Android,Native.js)
原生实现
private boolean isInstalledApp(Context context, String packageName){
//获取packagemanager
final PackageManager packageManager = context.getPackageManager();
//获取所有已安装程序的包信息
List< packageInfo> pinfo = packageManager.getInstalledPackages(0);
//用于存储所有已安装程序的包名
List<String> pName = new ArrayList<String>();
//从pinfo中将包名字逐一取出,压入pName list中
if(pinfo != null){
for(int i = 0; i < pinfo.size(); i++){
String pn = pinfo.get(i).packageName;
pName.add(pn);
}
}
//判断pName中是否有目标程序的包名,有TRUE,没有FALSE
return pName.contains(packageName);
}
Native.js
var isInstalledApp = function(pkgname) {
plus.android.importClass('java.util.ArrayList');
plus.android.importClass('android.content.pm.PackageInfo');
plus.android.importClass('android.content.pm.PackageManager');
var MainActivity = plus.android.runtimeMainActivity();
var PackageManager = MainActivity.getPackageManager();
var pinfo = plus.android.invoke(PackageManager, 'getInstalledPackages', 0)
if (pinfo != null) {
for (i = 0; i < pinfo.size(); i++) {
//PackageInfo{4b45699f9d com.tencent.mobileqq}
if (pinfo.get(i).toString().indexOf(pkgname) !== -1) {
return true;
}
}
}
return false;
}
## 使用 isInstalledApp('com.tencent.mm')
注意个别手机如华为有权限问题,如果不给权限,无法获取本机应用列表。
方式二:
var getIntentByPackageName = function(pkgname) {
plus.android.importClass('android.content.pm.PackageManager');
var MainActivity = plus.android.runtimeMainActivity();
var PackageManager = MainActivity.getPackageManager();
return plus.android.invoke(PackageManager, 'getLaunchIntentForPackage', pkgname);
}
var isInstalledApp = function(pkgname) {
return getIntentByPackageName(pkgname) != null;
}
## 使用 isInstalledApp('com.tencent.mm')
原生实现
private boolean isInstalledApp(Context context, String packageName){
//获取packagemanager
final PackageManager packageManager = context.getPackageManager();
//获取所有已安装程序的包信息
List< packageInfo> pinfo = packageManager.getInstalledPackages(0);
//用于存储所有已安装程序的包名
List<String> pName = new ArrayList<String>();
//从pinfo中将包名字逐一取出,压入pName list中
if(pinfo != null){
for(int i = 0; i < pinfo.size(); i++){
String pn = pinfo.get(i).packageName;
pName.add(pn);
}
}
//判断pName中是否有目标程序的包名,有TRUE,没有FALSE
return pName.contains(packageName);
}
Native.js
var isInstalledApp = function(pkgname) {
plus.android.importClass('java.util.ArrayList');
plus.android.importClass('android.content.pm.PackageInfo');
plus.android.importClass('android.content.pm.PackageManager');
var MainActivity = plus.android.runtimeMainActivity();
var PackageManager = MainActivity.getPackageManager();
var pinfo = plus.android.invoke(PackageManager, 'getInstalledPackages', 0)
if (pinfo != null) {
for (i = 0; i < pinfo.size(); i++) {
//PackageInfo{4b45699f9d com.tencent.mobileqq}
if (pinfo.get(i).toString().indexOf(pkgname) !== -1) {
return true;
}
}
}
return false;
}
## 使用 isInstalledApp('com.tencent.mm')
注意个别手机如华为有权限问题,如果不给权限,无法获取本机应用列表。
方式二:
var getIntentByPackageName = function(pkgname) {
plus.android.importClass('android.content.pm.PackageManager');
var MainActivity = plus.android.runtimeMainActivity();
var PackageManager = MainActivity.getPackageManager();
return plus.android.invoke(PackageManager, 'getLaunchIntentForPackage', pkgname);
}
var isInstalledApp = function(pkgname) {
return getIntentByPackageName(pkgname) != null;
}
## 使用 isInstalledApp('com.tencent.mm')
收起阅读 »

Mac版HBuilder使用SVN连接https地址报错的解决办法
Mac版HBuilder安装svn插件后,连接https的svn地址可能会报
svn: E175002: Connection has been shutdown: javax.net.ssl.SSLProtocolException: handshake alert: unrecognized_name
svn: E175002: OPTIONS request failed on '/svn/ifeedback_web'
svn: E175002: Connection has been shutdown: javax.net.ssl.SSLProtocolException: handshake alert: unrecognized_name
svn: E175002: OPTIONS request failed on '/svn/ifeedback_web'
Connection has been shutdown: javax.net.ssl.SSLProtocolException: handshake alert: unrecognized_name
handshake alert: unrecognized_name
的错误,解决办法如下
打开HBuilder.app/Contents/MacOS/HBuilder.ini文件,在最后添加如下三行代码重启HBuilder即可
-Dsvnkit.http.sslProtocols="SSLv3"
-Djsse.enableSNIExtension=false
-Dhudson.spool-svn=true
参考附件HBuilder.ini.zip中的HBuilder.ini(可备份下原来的覆盖本地的)
Mac版HBuilder安装svn插件后,连接https的svn地址可能会报
svn: E175002: Connection has been shutdown: javax.net.ssl.SSLProtocolException: handshake alert: unrecognized_name
svn: E175002: OPTIONS request failed on '/svn/ifeedback_web'
svn: E175002: Connection has been shutdown: javax.net.ssl.SSLProtocolException: handshake alert: unrecognized_name
svn: E175002: OPTIONS request failed on '/svn/ifeedback_web'
Connection has been shutdown: javax.net.ssl.SSLProtocolException: handshake alert: unrecognized_name
handshake alert: unrecognized_name
的错误,解决办法如下
打开HBuilder.app/Contents/MacOS/HBuilder.ini文件,在最后添加如下三行代码重启HBuilder即可
-Dsvnkit.http.sslProtocols="SSLv3"
-Djsse.enableSNIExtension=false
-Dhudson.spool-svn=true
参考附件HBuilder.ini.zip中的HBuilder.ini(可备份下原来的覆盖本地的)
收起阅读 »
DCloud-BeeCloud Pay 无后端开发的支付服务
DCloud-BeeCloud Pay
==============
DCloud和BeeCloud合作的支付业务,与普通的三方支付不同。
它仅需要工程师写前端App的js代码,调用Plus的原生支付接口进行支付宝和微信的原生支付,不需要服务器编写代码,即可收款到开发商自己的微信或支付宝的账户里。
需要注意钱并不流经DCloud或beecloud的服务器,开发商向微信和支付宝申请账户,最终用户支付的钱直接到达开发商在微信或支付宝里申请的账户。
BeeCloud同样支持银联在线支付渠道,银联在线在WAP及流应用环境下同样可用。
体验DEMO的方式:HBuilder 7.0版本后新建的Hello mui项目含有cloud pay模板。
准备工作
注册
- 在BeeCloud官网注册,并完成企业认证。
创建APP
- 在BeeCloud控制台创建你的第一个APP。
配置支付参数
- 配置您所需的支付渠道的支付参数,具体请参考BeeCloud-渠道参数配置,如图:
开始支付
manifest.json配置
模块权限配置
- 勾选
payment
模块
SDK配置
-
需要在
plus.payment-支付
中配置scheme-
支付宝支付
自定义填写,推荐使用小写字符串,不能填写alipay,AliPay等关键字 -
微信支付
固定填写,微信开放平台创建应用的APPID
-
这些配置都是云打包之后生效,所以测试微信支付,必须云打包之后,在手机上运行,才能正常调起微信客户端支付。否则在数据正常的情况下,调起微信客户端后,会出现异常(只显示一个确定按钮)
真机运行使用的是DCloud公司的支付配置信息,此时付款会付给DCloud。
代码实现
-
在页面中引入
beecloud.js
( 在Hello mui里含有本文件)<script src="beecloud.js"></script>
-
构建支付参数发起支付
<script src="beecloud.js"></script>
<script type="text/javascript">
function beecloudPay(bcChannel) {
/*
* 构建支付参数
*
* app_id: BeeCloud控制台上创建的APP的appid,必填
* title: 订单标题,32个字节,最长支持16个汉字;必填
* total_fee: 支付金额,以分为单位,大于0的整数,必填
* bill_no: 订单号,8~32位数字和/或字母组合,确保在商户系统中唯一,必填
* optional: 扩展参数,可以传入任意数量的key/value对来补充对业务逻辑的需求;此参数会在webhook回调中返回; 选填
* bill_timeout: 订单失效时间,必须为非零正整数,单位为秒,必须大于360。选填
*/
var payData = {
app_id: "c37d661d-7e61-49ea-96a5-68c34e83db3b",
channel: bcChannel,
title: "DCloud",
total_fee: 1,
bill_no: beecloud.genBillNo(),
optional: {'uerId':'beecloud','phone':'4006280728'},
bill_timeout: 360
};
/*
* 发起支付
* payData: 支付参数
* cbsuccess: 支付成功回调
* cberror: 支付失败回调
*/
beecloud.payReq(payData, function(result) {
mui.alert("----- 支付成功 -----" + str);
}, function(e) {
mui.alert("----- 支付失败 -----\n" +"错误码:"+ e.code + '\n' + e.message);
});
}
</script>
</br>
联系Beecloud
如果您遇到问题,有以下方式可以联系到Beecloud:
① 请致电 4006280728 转 1
② 加入我们的开发者交流群:429506653
③ 在我们的FAQ页寻找答案
DCloud-BeeCloud Pay
==============
DCloud和BeeCloud合作的支付业务,与普通的三方支付不同。
它仅需要工程师写前端App的js代码,调用Plus的原生支付接口进行支付宝和微信的原生支付,不需要服务器编写代码,即可收款到开发商自己的微信或支付宝的账户里。
需要注意钱并不流经DCloud或beecloud的服务器,开发商向微信和支付宝申请账户,最终用户支付的钱直接到达开发商在微信或支付宝里申请的账户。
BeeCloud同样支持银联在线支付渠道,银联在线在WAP及流应用环境下同样可用。
体验DEMO的方式:HBuilder 7.0版本后新建的Hello mui项目含有cloud pay模板。
准备工作
注册
- 在BeeCloud官网注册,并完成企业认证。
创建APP
- 在BeeCloud控制台创建你的第一个APP。
配置支付参数
- 配置您所需的支付渠道的支付参数,具体请参考BeeCloud-渠道参数配置,如图:
开始支付
manifest.json配置
模块权限配置
- 勾选
payment
模块
SDK配置
-
需要在
plus.payment-支付
中配置scheme-
支付宝支付
自定义填写,推荐使用小写字符串,不能填写alipay,AliPay等关键字 -
微信支付
固定填写,微信开放平台创建应用的APPID
-
这些配置都是云打包之后生效,所以测试微信支付,必须云打包之后,在手机上运行,才能正常调起微信客户端支付。否则在数据正常的情况下,调起微信客户端后,会出现异常(只显示一个确定按钮)
真机运行使用的是DCloud公司的支付配置信息,此时付款会付给DCloud。
代码实现
-
在页面中引入
beecloud.js
( 在Hello mui里含有本文件)<script src="beecloud.js"></script>
-
构建支付参数发起支付
<script src="beecloud.js"></script>
<script type="text/javascript">
function beecloudPay(bcChannel) {
/*
* 构建支付参数
*
* app_id: BeeCloud控制台上创建的APP的appid,必填
* title: 订单标题,32个字节,最长支持16个汉字;必填
* total_fee: 支付金额,以分为单位,大于0的整数,必填
* bill_no: 订单号,8~32位数字和/或字母组合,确保在商户系统中唯一,必填
* optional: 扩展参数,可以传入任意数量的key/value对来补充对业务逻辑的需求;此参数会在webhook回调中返回; 选填
* bill_timeout: 订单失效时间,必须为非零正整数,单位为秒,必须大于360。选填
*/
var payData = {
app_id: "c37d661d-7e61-49ea-96a5-68c34e83db3b",
channel: bcChannel,
title: "DCloud",
total_fee: 1,
bill_no: beecloud.genBillNo(),
optional: {'uerId':'beecloud','phone':'4006280728'},
bill_timeout: 360
};
/*
* 发起支付
* payData: 支付参数
* cbsuccess: 支付成功回调
* cberror: 支付失败回调
*/
beecloud.payReq(payData, function(result) {
mui.alert("----- 支付成功 -----" + str);
}, function(e) {
mui.alert("----- 支付失败 -----\n" +"错误码:"+ e.code + '\n' + e.message);
});
}
</script>
</br>
联系Beecloud
如果您遇到问题,有以下方式可以联系到Beecloud:
① 请致电 4006280728 转 1
② 加入我们的开发者交流群:429506653
③ 在我们的FAQ页寻找答案

微信支付 苹果 只有一个按钮
帮论坛里面的同学解决问题的时候遇到这个,然后这位同学最后发现是自己的SDK配置里面微信支付和微信分享的APPid配置不相同造成的
换句话说就是微信支付的APPid配置错了,到上图这一步其实微信支付已经走到最后一步了,支付字符串基本没问题了,已经吊起支付了,
但是跟微信app的交互出现了问题,验证失败,导致各种奇葩BUG出现,基本都是appid和签名的问题,另外我又去翻了下微信开放平台的
创建应用,发现苹果的支付校验是通过bundleID来校验的,也就是app打包的包名,如果苹果出现了上图的问题也可以去查下开放平台配置
是否有问题,目前我遇到的问题基本就这些了,希望对大家开发有点帮助吧!
帮论坛里面的同学解决问题的时候遇到这个,然后这位同学最后发现是自己的SDK配置里面微信支付和微信分享的APPid配置不相同造成的
换句话说就是微信支付的APPid配置错了,到上图这一步其实微信支付已经走到最后一步了,支付字符串基本没问题了,已经吊起支付了,
但是跟微信app的交互出现了问题,验证失败,导致各种奇葩BUG出现,基本都是appid和签名的问题,另外我又去翻了下微信开放平台的
创建应用,发现苹果的支付校验是通过bundleID来校验的,也就是app打包的包名,如果苹果出现了上图的问题也可以去查下开放平台配置
是否有问题,目前我遇到的问题基本就这些了,希望对大家开发有点帮助吧!

Android下打开手机GPS设置
这几天找打开GPS设置帖子,好像都没有找到,没办法只好自己写了。
手上只有两台安卓设备,一台魅族MX和一台华为,因此只能保证安卓下能用,可能还需要大家佐证。
if(plus.os.name == "Android"){
var context = plus.android.importClass("android.content.Context");
var locationManager=plus.android.importClass("android.location.LocationManager");
var main=plus.android.runtimeMainActivity();
var mainSvr=main.getSystemService(context.LOCATION_SERVICE);
var gpsProvider = mainSvr.isProviderEnabled(locationManager.GPS_PROVIDER);//检查是否开启了GPS
if(!gpsProvider) {
var message = "为了获取您的精准位置,请开启GPS设备。";
var title = "GPS未启用";
var alertCB = function () {
var Intent = plus.android.importClass("android.content.Intent");
var mIntent = new Intent('android.settings.LOCATION_SOURCE_SETTINGS');
main.startActivity(mIntent);//打开GPS设置
}
plus.nativeUI.alert( message, alertCB, title);
}
}
关于iOS下的gps设置,如果有朋友做出来了,希望能分享下,本人为这个已经愁白了头了!
这几天找打开GPS设置帖子,好像都没有找到,没办法只好自己写了。
手上只有两台安卓设备,一台魅族MX和一台华为,因此只能保证安卓下能用,可能还需要大家佐证。
if(plus.os.name == "Android"){
var context = plus.android.importClass("android.content.Context");
var locationManager=plus.android.importClass("android.location.LocationManager");
var main=plus.android.runtimeMainActivity();
var mainSvr=main.getSystemService(context.LOCATION_SERVICE);
var gpsProvider = mainSvr.isProviderEnabled(locationManager.GPS_PROVIDER);//检查是否开启了GPS
if(!gpsProvider) {
var message = "为了获取您的精准位置,请开启GPS设备。";
var title = "GPS未启用";
var alertCB = function () {
var Intent = plus.android.importClass("android.content.Intent");
var mIntent = new Intent('android.settings.LOCATION_SOURCE_SETTINGS');
main.startActivity(mIntent);//打开GPS设置
}
plus.nativeUI.alert( message, alertCB, title);
}
}
关于iOS下的gps设置,如果有朋友做出来了,希望能分享下,本人为这个已经愁白了头了!
收起阅读 »