HBuilderX

HBuilderX

极客开发工具
uni-app

uni-app

开发一次,多端覆盖
uniCloud

uniCloud

云开发平台
HTML5+

HTML5+

增强HTML5的功能体验
MUI

MUI

上万Star的前端框架

获取本机所有安装程序的包名和应用名(含解决JSBObject方案)

因为项目需要启动本机第三方应用,但由于管控软件已经启用,无法再随意安装程序获取本机所有安装程序的包名和应用名,于是就想到使用Nativejs或Java原生获取,下面是网上我查找到的获取包名和应用名的方法,我进行了整合

//Java实现代码  
//获取PackageManager  
PackageManager packageManager = context.getPackageManager();  
//获取所有已安装程序的包信息  
List <PackageInfo> packageInfos = packageManager.getInstalledPackages(0);  
// 遍历所有安装程序的包信息和应用程序名  
ApplicationInfo applicationInfo = null;  
if (packageInfos != null) {  
    for (int i = 0; i < packageInfos.size(); i++) {  
        String packName = packageInfos.get(i).packageName;  
        applicationInfo = packageManager.getApplicationInfo(packName, 0);  
        String appName=(String)((applicationInfo != null) ? packageManager.getApplicationLabel(applicationInfo) : "???");  
        Log.e(TAG, "PackageName:" + packName+",ApplicationName:"+appName);  
    }  
 }

那么如何转换为NJS代码呢了,我认真拜读了DCloud_App_Array老大写的入门教程https://ask.dcloud.net.cn/article/88,Nativejs示例https://ask.dcloud.net.cn/article/114和在插件市场的Nativejs的代码(重点是DCloud_App_Array写的),还有最推荐实践项目就是HbuilderX自带的Hello 5+的HTML5Plus规范演示,它基本演示绝大部分应用。但是对于简单的不需要类相互调用的还好实现,但遇到上面相互调用首先想到的是plus.android.importClass,然后通过类的.来调用,这点和https://ask.dcloud.net.cn/question/65208非常类似,但Java对象毕竟是非JS对象,所以经常出现JSBObject的问题,无法获取真实内容,该文章作者在回复中提到了invoke解决的,但没有实际代码,我和后面回复中一样急切需要解决方案,不过还好通过自己测试还是实现,同时对Nativejsy调用原生能力的认识也真正算是入门了,现在只要有java代码,而且Nativejs能实现的,就可以完成Java转NJS了。为了给自己留下记录,同时也帮助还在NativeJS迷茫路上的人们一点方向。

先看我实现上面功能的NJS代码,看你是否理解:

const main = plus.android.runtimeMainActivity();  
let pManager = plus.android.invoke(main, 'getPackageManager');  
let pInfo = plus.android.invoke(pManager, 'getInstalledPackages', 0);  
let total = plus.android.invoke(pInfo, 'size');  
let packName = '';  
let appName = '';  
let obj = null;  
// 遍历获取包名和应用名称  
for (let i = 0; i < total; i++) {  
    // 获取包名  
    packName = plus.android.getAttribute(plus.android.invoke(pInfo, 'get', i), 'packageName');  
    // 获取包名对应的应用名  
    obj = plus.android.invoke(pManager, 'getApplicationInfo', packName, 0);  
    appName = plus.android.invoke(pManager, 'getApplicationLabel', obj);  
    console.log(packName, appName);  
}

我现在归纳总结Java转NJS代码几个要点:
1、plus.android.runtimeMainActivity(),起初我认识它就是普通Activity,其实它是Context,它是Html5+运行期环境主组件,用于处理与用户交互的各种事件,也是应用程序全局环境android.app.Activity的实现对象,是唯一的,生命周期是应用程序生命周期,可以完成所有有关程序的操作,至于Context重要可以百度.
2、plus.android.getAttribute和plus.android.setAttribute,获取或设置类或对象的属性,不再建议使用.来操作了,对于属性就建议使用它两个都可以完成了,毕竟android中java类还是比较复杂的,一个不好就访问了非静态常量,它两者则不存在这样问吧
3、plus.android.invoke调用类或对象的方法,支持静态或非静态,同样不建议使用.来操作了,原因同上。无论是importClass获取类对象(ClassObject)还是newObject获取的实例对象(InstanceObject)使用这种方法调用方法则没问题
4、遇到上面这种不断调用类的方法获取下一步操作的对象,甚至是能完.连续调用的,一定要使用我上面介绍的一个对象和三个函数来转换,其它都会非常容易出现失败的。同时要牢记为了思路清晰, 连续调用可分解为一个一个invoke调用,返回的对象就用let申明即可 ,这里有个 最大误区就是以为要和Java一样,先导入类再定义返回的对象,我开始也是在这里迷茫的,JS中不存在让它种写法啊,就是使用构造函数传递返回值相当于this来获取,结果经常返回null或JSBObject 后来想明白了,在JS中只有对象概念,才不管你是A类的对象还是B类的对象,只要是对象就是由属性和方法组成,上面转换代码你引入类就是多此一举了。
5、plus.android.importClass和plus.android.newObject什么时候使用呢?Java代码中调用类的静态方法或new获得的对象的代码就需要使用它们了,前者使用importClass,后者使用newObject。
总结:如果你理解我的代码,也掌握我提的五个要点,尤其是前面四个要点,任何Java代码转NJS都不再算复杂了

最后,还要是提供NativeJS还在入门的同学们,看完入门教程后,重点可参考Hello 5+的HTML5Plus规范来学习,它的示例代码非常多,毕竟是官方的模板,写法和技巧都值得学习。

继续阅读 »

因为项目需要启动本机第三方应用,但由于管控软件已经启用,无法再随意安装程序获取本机所有安装程序的包名和应用名,于是就想到使用Nativejs或Java原生获取,下面是网上我查找到的获取包名和应用名的方法,我进行了整合

//Java实现代码  
//获取PackageManager  
PackageManager packageManager = context.getPackageManager();  
//获取所有已安装程序的包信息  
List <PackageInfo> packageInfos = packageManager.getInstalledPackages(0);  
// 遍历所有安装程序的包信息和应用程序名  
ApplicationInfo applicationInfo = null;  
if (packageInfos != null) {  
    for (int i = 0; i < packageInfos.size(); i++) {  
        String packName = packageInfos.get(i).packageName;  
        applicationInfo = packageManager.getApplicationInfo(packName, 0);  
        String appName=(String)((applicationInfo != null) ? packageManager.getApplicationLabel(applicationInfo) : "???");  
        Log.e(TAG, "PackageName:" + packName+",ApplicationName:"+appName);  
    }  
 }

那么如何转换为NJS代码呢了,我认真拜读了DCloud_App_Array老大写的入门教程https://ask.dcloud.net.cn/article/88,Nativejs示例https://ask.dcloud.net.cn/article/114和在插件市场的Nativejs的代码(重点是DCloud_App_Array写的),还有最推荐实践项目就是HbuilderX自带的Hello 5+的HTML5Plus规范演示,它基本演示绝大部分应用。但是对于简单的不需要类相互调用的还好实现,但遇到上面相互调用首先想到的是plus.android.importClass,然后通过类的.来调用,这点和https://ask.dcloud.net.cn/question/65208非常类似,但Java对象毕竟是非JS对象,所以经常出现JSBObject的问题,无法获取真实内容,该文章作者在回复中提到了invoke解决的,但没有实际代码,我和后面回复中一样急切需要解决方案,不过还好通过自己测试还是实现,同时对Nativejsy调用原生能力的认识也真正算是入门了,现在只要有java代码,而且Nativejs能实现的,就可以完成Java转NJS了。为了给自己留下记录,同时也帮助还在NativeJS迷茫路上的人们一点方向。

先看我实现上面功能的NJS代码,看你是否理解:

const main = plus.android.runtimeMainActivity();  
let pManager = plus.android.invoke(main, 'getPackageManager');  
let pInfo = plus.android.invoke(pManager, 'getInstalledPackages', 0);  
let total = plus.android.invoke(pInfo, 'size');  
let packName = '';  
let appName = '';  
let obj = null;  
// 遍历获取包名和应用名称  
for (let i = 0; i < total; i++) {  
    // 获取包名  
    packName = plus.android.getAttribute(plus.android.invoke(pInfo, 'get', i), 'packageName');  
    // 获取包名对应的应用名  
    obj = plus.android.invoke(pManager, 'getApplicationInfo', packName, 0);  
    appName = plus.android.invoke(pManager, 'getApplicationLabel', obj);  
    console.log(packName, appName);  
}

我现在归纳总结Java转NJS代码几个要点:
1、plus.android.runtimeMainActivity(),起初我认识它就是普通Activity,其实它是Context,它是Html5+运行期环境主组件,用于处理与用户交互的各种事件,也是应用程序全局环境android.app.Activity的实现对象,是唯一的,生命周期是应用程序生命周期,可以完成所有有关程序的操作,至于Context重要可以百度.
2、plus.android.getAttribute和plus.android.setAttribute,获取或设置类或对象的属性,不再建议使用.来操作了,对于属性就建议使用它两个都可以完成了,毕竟android中java类还是比较复杂的,一个不好就访问了非静态常量,它两者则不存在这样问吧
3、plus.android.invoke调用类或对象的方法,支持静态或非静态,同样不建议使用.来操作了,原因同上。无论是importClass获取类对象(ClassObject)还是newObject获取的实例对象(InstanceObject)使用这种方法调用方法则没问题
4、遇到上面这种不断调用类的方法获取下一步操作的对象,甚至是能完.连续调用的,一定要使用我上面介绍的一个对象和三个函数来转换,其它都会非常容易出现失败的。同时要牢记为了思路清晰, 连续调用可分解为一个一个invoke调用,返回的对象就用let申明即可 ,这里有个 最大误区就是以为要和Java一样,先导入类再定义返回的对象,我开始也是在这里迷茫的,JS中不存在让它种写法啊,就是使用构造函数传递返回值相当于this来获取,结果经常返回null或JSBObject 后来想明白了,在JS中只有对象概念,才不管你是A类的对象还是B类的对象,只要是对象就是由属性和方法组成,上面转换代码你引入类就是多此一举了。
5、plus.android.importClass和plus.android.newObject什么时候使用呢?Java代码中调用类的静态方法或new获得的对象的代码就需要使用它们了,前者使用importClass,后者使用newObject。
总结:如果你理解我的代码,也掌握我提的五个要点,尤其是前面四个要点,任何Java代码转NJS都不再算复杂了

最后,还要是提供NativeJS还在入门的同学们,看完入门教程后,重点可参考Hello 5+的HTML5Plus规范来学习,它的示例代码非常多,毕竟是官方的模板,写法和技巧都值得学习。

收起阅读 »

vue3.0版聊天室|vue3+vant3.x仿微信聊天+朋友圈

vuex vue.js

项目介绍

随着vue3越来越稳定了,加上Vite工具的推出,2021年再一次让vue.js变得很受开发者青睐。今天给大家分享的是基于vue3.0+有赞vant3技术建构开发的仿微信app界面聊天实战案例。

vue3.x mobile版聊天室|vue3仿微信聊天实战开发

img

Vue3ChatRoom项目支持发送消息/emoj表情图、图片/视频预览、网址查看、长按菜单、红包/朋友圈等功能。

Vue3+vant-ui实现下拉刷新、左滑菜单功能。
img

Vue3+Image组件实现朋友圈及图片查看功能
img

实现技术

  • 编辑器:VScode
  • MVVM框架:vue3.0
  • 状态管理:vuex4.x
  • 地址路由:vue-router@4
  • UI组件库:vant3.x (有赞移动端vue3.0组件库)
  • 弹层组件:v3popup(基于vue3自定义弹窗组件)
  • iconfont图标:阿里字体图标库
  • 自定义顶部headerBar+底部tabBar组件

img

img

img

img

img

img

img

img

img

img

img

img

img

img

项目结构

img

vue3弹层组件

v3popup基于vue3.0开发的自定义弹框组件,贯穿于整个项目应用。

img

由于之前有过一篇分享文章,这里就不过多的介绍了。
vue3.0系列之自定义全局弹框组件|vue3移动端弹层组件

vue.config.js基本配置

用来进行一些基础的项目开发配置,可自定义webpack设置路径别名。

const path = require('path')  

module.exports = {  
    // 基本路径  
    // publicPath: '/',  

    // 输出文件目录  
    // outputDir: 'dist',  

    // assetsDir: '',  

    // 环境配置  
    devServer: {  
        // host: 'localhost',  
        // port: 8080,  
        // 是否开启https  
        https: false,  
        // 编译完是否打开网页  
        open: false,  

        // 代理配置  
        // proxy: {  
        //     '^/api': {  
        //         target: '<url>',  
        //         ws: true,  
        //         changeOrigin: true  
        //     },  
        //     '^/foo': {  
        //         target: '<other_url>'  
        //     }  
        // }  
    },  

    // webpack配置  
    chainWebpack: config => {  
        // 配置路径别名  
        config.resolve.alias  
            .set('@', path.join(__dirname, 'src'))  
            .set('@assets', path.join(__dirname, 'src/assets'))  
            .set('@components', path.join(__dirname, 'src/components'))  
            .set('@views', path.join(__dirname, 'src/views'))  
    }  
}

vue3公共页面配置

在main.js中配置一些公共引入。

import { createApp } from 'vue'  
import App from './App.vue'  

// 引入vuex和路由配置  
import store from './store'  
import router from './router'  

// 引入js  
import '@assets/js/fontSize'  

// 引入公共组件  
import Plugins from './plugins'  

const app = createApp(App)  

app.use(store)  
app.use(router)  
app.use(Plugins)  

app.mount('#app')

vue3表单验证

vue3.0中通过getCurrentInstance来获得上下文,可用来操作router或store。

<script>  
import { reactive, inject, getCurrentInstance } from 'vue'  
export default {  
    components: {},  
    setup() {  
        const { ctx } = getCurrentInstance()  

        const v3popup = inject('v3popup')  
        const utils = inject('utils')  
        const formObj = reactive({})  

        // ...  

        const handleSubmit = () => {  
            if(!formObj.tel){  
                Snackbar('手机号不能为空!')  
            }else if(!utils.checkTel(formObj.tel)){  
                Snackbar('手机号格式不正确!')  
            }else if(!formObj.pwd){  
                Snackbar('密码不能为空!')  
            }else{  
                ctx.$store.commit('SET_TOKEN', utils.setToken());  
                ctx.$store.commit('SET_USER', formObj.tel);  

                // ...  
            }  
        }  

        return {  
            formObj,  
            handleSubmit  
        }  
    }  
}  
</script>

vue3.0中使用全局钩子路由来实现登录拦截。

router.beforeEach((to, from, next) => {  
    const token = store.state.token  

    // 判断当前路由地址是否需要登录权限  
    if(to.meta.requireAuth) {  
        if(token) {  
            next()  
        }else {  
            // 未登录授权  
            V3Popup({  
                content: '还未登录授权!', position: 'top', popupStyle: 'background:#fa5151;color:#fff;', time: 2,  
                onEnd: () => {  
                    next({ path: '/login' })  
                }  
            })  
        }  
    }else {  
        next()  
    }  
})

vue3聊天模块

底部聊天编辑器采用公共分离模块,使用图文混排模式,可插入文字+emoj表情。
img
使用的是div可编辑器属性实现,大家感兴趣可以自己去试一试这个功能。

img

ok,以上就是基于vue3.x开发聊天实战项目的介绍,希望大家能喜欢!

Electron+Vue.js仿微信桌面端聊天实例|electron-vue客户端开发

链接:https://juejin.cn/post/6915310758859374606/
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

继续阅读 »

项目介绍

随着vue3越来越稳定了,加上Vite工具的推出,2021年再一次让vue.js变得很受开发者青睐。今天给大家分享的是基于vue3.0+有赞vant3技术建构开发的仿微信app界面聊天实战案例。

vue3.x mobile版聊天室|vue3仿微信聊天实战开发

img

Vue3ChatRoom项目支持发送消息/emoj表情图、图片/视频预览、网址查看、长按菜单、红包/朋友圈等功能。

Vue3+vant-ui实现下拉刷新、左滑菜单功能。
img

Vue3+Image组件实现朋友圈及图片查看功能
img

实现技术

  • 编辑器:VScode
  • MVVM框架:vue3.0
  • 状态管理:vuex4.x
  • 地址路由:vue-router@4
  • UI组件库:vant3.x (有赞移动端vue3.0组件库)
  • 弹层组件:v3popup(基于vue3自定义弹窗组件)
  • iconfont图标:阿里字体图标库
  • 自定义顶部headerBar+底部tabBar组件

img

img

img

img

img

img

img

img

img

img

img

img

img

img

项目结构

img

vue3弹层组件

v3popup基于vue3.0开发的自定义弹框组件,贯穿于整个项目应用。

img

由于之前有过一篇分享文章,这里就不过多的介绍了。
vue3.0系列之自定义全局弹框组件|vue3移动端弹层组件

vue.config.js基本配置

用来进行一些基础的项目开发配置,可自定义webpack设置路径别名。

const path = require('path')  

module.exports = {  
    // 基本路径  
    // publicPath: '/',  

    // 输出文件目录  
    // outputDir: 'dist',  

    // assetsDir: '',  

    // 环境配置  
    devServer: {  
        // host: 'localhost',  
        // port: 8080,  
        // 是否开启https  
        https: false,  
        // 编译完是否打开网页  
        open: false,  

        // 代理配置  
        // proxy: {  
        //     '^/api': {  
        //         target: '<url>',  
        //         ws: true,  
        //         changeOrigin: true  
        //     },  
        //     '^/foo': {  
        //         target: '<other_url>'  
        //     }  
        // }  
    },  

    // webpack配置  
    chainWebpack: config => {  
        // 配置路径别名  
        config.resolve.alias  
            .set('@', path.join(__dirname, 'src'))  
            .set('@assets', path.join(__dirname, 'src/assets'))  
            .set('@components', path.join(__dirname, 'src/components'))  
            .set('@views', path.join(__dirname, 'src/views'))  
    }  
}

vue3公共页面配置

在main.js中配置一些公共引入。

import { createApp } from 'vue'  
import App from './App.vue'  

// 引入vuex和路由配置  
import store from './store'  
import router from './router'  

// 引入js  
import '@assets/js/fontSize'  

// 引入公共组件  
import Plugins from './plugins'  

const app = createApp(App)  

app.use(store)  
app.use(router)  
app.use(Plugins)  

app.mount('#app')

vue3表单验证

vue3.0中通过getCurrentInstance来获得上下文,可用来操作router或store。

<script>  
import { reactive, inject, getCurrentInstance } from 'vue'  
export default {  
    components: {},  
    setup() {  
        const { ctx } = getCurrentInstance()  

        const v3popup = inject('v3popup')  
        const utils = inject('utils')  
        const formObj = reactive({})  

        // ...  

        const handleSubmit = () => {  
            if(!formObj.tel){  
                Snackbar('手机号不能为空!')  
            }else if(!utils.checkTel(formObj.tel)){  
                Snackbar('手机号格式不正确!')  
            }else if(!formObj.pwd){  
                Snackbar('密码不能为空!')  
            }else{  
                ctx.$store.commit('SET_TOKEN', utils.setToken());  
                ctx.$store.commit('SET_USER', formObj.tel);  

                // ...  
            }  
        }  

        return {  
            formObj,  
            handleSubmit  
        }  
    }  
}  
</script>

vue3.0中使用全局钩子路由来实现登录拦截。

router.beforeEach((to, from, next) => {  
    const token = store.state.token  

    // 判断当前路由地址是否需要登录权限  
    if(to.meta.requireAuth) {  
        if(token) {  
            next()  
        }else {  
            // 未登录授权  
            V3Popup({  
                content: '还未登录授权!', position: 'top', popupStyle: 'background:#fa5151;color:#fff;', time: 2,  
                onEnd: () => {  
                    next({ path: '/login' })  
                }  
            })  
        }  
    }else {  
        next()  
    }  
})

vue3聊天模块

底部聊天编辑器采用公共分离模块,使用图文混排模式,可插入文字+emoj表情。
img
使用的是div可编辑器属性实现,大家感兴趣可以自己去试一试这个功能。

img

ok,以上就是基于vue3.x开发聊天实战项目的介绍,希望大家能喜欢!

Electron+Vue.js仿微信桌面端聊天实例|electron-vue客户端开发

链接:https://juejin.cn/post/6915310758859374606/
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

收起阅读 »

hbuilder for linux还没有吗

哈哈,估计是没有

哈哈,估计是没有

关于 .sync 和 v-model 失效问题解决方案

解决方案

内容全在附件里面图片,官方提示我非法内容,但是我没搞懂哪里非法

内容全在附件里面图片,官方提示我非法内容,但是我没搞懂哪里非法

uni-app 页面顶部栏固定悬浮的 css 兼容方法

uni_app

uni-app 中 NavigationBar(导航栏 44px)以及 TabBar(底部选项卡 50px)组件的高度是固定的,不可修改,各小程序平台,包括同小程序平台的 iOS 和 Android 的高度也不一样。

泪雪博客

那么如果我们需要悬浮导航菜单则需要使用 position: sticky 来使其悬浮,然后对于 H5 平台加上 top:44px 的高度,这样 uni-app 页面顶部导航栏的固定悬浮就实现了兼容,具体的代码如下:

.menu {  
    position: sticky;  
    /* #ifdef H5 */  
    top: 44px;  
    /* #endif */  
    /* #ifndef H5 */  
    top: 0;  
    /* #endif */  
    z-index: 999;  
    flex: 1;  
    flex-direction: column;  
    overflow: hidden;  
    background-color: #ffffff;  
}

以上代码纯属子凡开发中简单的需要稍微注意的地方,仅供大家学习参考。

其中 position: fixed 虽然也可以悬浮固定,但是底部的元素就无法继承 top 的值了,可以简单说 fixed 是特殊版的 absolute,fixed 元素总是相对于 body 定位的。所以就需要使用 position: static,static(没有定位)是 position 的默认值,元素处于正常的文档流中,会忽略 left、top、right、bottom 和 z-index 属性。

除非注明,否则均为泪雪博客原创文章,禁止任何形式转载

本文链接:https://zhangzifan.com/uni-app-navigationbar-position-static.html

继续阅读 »

uni-app 中 NavigationBar(导航栏 44px)以及 TabBar(底部选项卡 50px)组件的高度是固定的,不可修改,各小程序平台,包括同小程序平台的 iOS 和 Android 的高度也不一样。

泪雪博客

那么如果我们需要悬浮导航菜单则需要使用 position: sticky 来使其悬浮,然后对于 H5 平台加上 top:44px 的高度,这样 uni-app 页面顶部导航栏的固定悬浮就实现了兼容,具体的代码如下:

.menu {  
    position: sticky;  
    /* #ifdef H5 */  
    top: 44px;  
    /* #endif */  
    /* #ifndef H5 */  
    top: 0;  
    /* #endif */  
    z-index: 999;  
    flex: 1;  
    flex-direction: column;  
    overflow: hidden;  
    background-color: #ffffff;  
}

以上代码纯属子凡开发中简单的需要稍微注意的地方,仅供大家学习参考。

其中 position: fixed 虽然也可以悬浮固定,但是底部的元素就无法继承 top 的值了,可以简单说 fixed 是特殊版的 absolute,fixed 元素总是相对于 body 定位的。所以就需要使用 position: static,static(没有定位)是 position 的默认值,元素处于正常的文档流中,会忽略 left、top、right、bottom 和 z-index 属性。

除非注明,否则均为泪雪博客原创文章,禁止任何形式转载

本文链接:https://zhangzifan.com/uni-app-navigationbar-position-static.html

收起阅读 »

uniapp离线打包apk提示当前应用运行在自定义调试基座中?

uniapp离线打包

找了半天才找到解决方案,此处记录下来方便自己和遇到同类问题的同学使用

dcloud_control.xml中的 syncDebug 改为 false 或 去掉就好了
<hbuilder debug="false" syncDebug="false">

继续阅读 »

找了半天才找到解决方案,此处记录下来方便自己和遇到同类问题的同学使用

dcloud_control.xml中的 syncDebug 改为 false 或 去掉就好了
<hbuilder debug="false" syncDebug="false">

收起阅读 »

hbuilderx 3.0.5 bug

版本 HTML5+ 蓝牙打印 移动APP bug已修复

基座运行

Uncaught java.lang.NullPointerException: Attempt to get length of null array;at android.bluetooth.BluetoothOutputStream.write

bug定位是在

var outputStream = bluetoothSocket.getOutputStream();
var bytes = plus.android.invoke(str, 'getBytes', 'gbk');
outputStream.write(bytes); // 这里

写入的时候报错

实测发现:
2.9.8 版本没有问题 3.0.4 和 3.0.5均有问题

继续阅读 »

基座运行

Uncaught java.lang.NullPointerException: Attempt to get length of null array;at android.bluetooth.BluetoothOutputStream.write

bug定位是在

var outputStream = bluetoothSocket.getOutputStream();
var bytes = plus.android.invoke(str, 'getBytes', 'gbk');
outputStream.write(bytes); // 这里

写入的时候报错

实测发现:
2.9.8 版本没有问题 3.0.4 和 3.0.5均有问题

收起阅读 »

修改后浏览器不自动刷新的问题经验分享

开发h5项目时,修改保存后浏览器不自动刷新的问题困扰我很久了,今天版本更新,正常了,突然想到以前每次更新后都会去做下面修改:
因为每次更新后开发调试时一直发http://localhost:8080/sockjs-node/info?t=xxx 请求,于是照网上操作:
打开node_modules/sockjs-client/dist/sockjs.js,在代码的1605行注释
// self.xhr.send(payload);

经测试,就是上面的操作导致的,修改后浏览器不自动刷新的原因终于找到了。那如何解决一直发http://localhost:8080的问题呢,查了好久,原来是端口被占用的原因,在manifest.josn中修改:
"devServer" : {
"https" : false,
"port" : 81,//这里的端口改成浏览器测试地址对应的端口就好啦

希望对有相同情况的同学有帮助。

继续阅读 »

开发h5项目时,修改保存后浏览器不自动刷新的问题困扰我很久了,今天版本更新,正常了,突然想到以前每次更新后都会去做下面修改:
因为每次更新后开发调试时一直发http://localhost:8080/sockjs-node/info?t=xxx 请求,于是照网上操作:
打开node_modules/sockjs-client/dist/sockjs.js,在代码的1605行注释
// self.xhr.send(payload);

经测试,就是上面的操作导致的,修改后浏览器不自动刷新的原因终于找到了。那如何解决一直发http://localhost:8080的问题呢,查了好久,原来是端口被占用的原因,在manifest.josn中修改:
"devServer" : {
"https" : false,
"port" : 81,//这里的端口改成浏览器测试地址对应的端口就好啦

希望对有相同情况的同学有帮助。

收起阅读 »

HBuilderX: 关于iOS安心打包、本地重签,证书安装教程

安心打包 HBuilderX

前言

MacOSX iOS安心打包、本地重签失败, 需要安装相关证书.

打开证书目录

安装证书

  1. 点击证书文件, 会自动打开钥匙串, 下拉列表钥匙串, 选择系统, 点击 添加 按钮
  2. 点击添加后, 请在弹窗中,输入电脑密码, 允许钥匙串访问.
  3. 按照上面的步骤, 依次完成其它证书的导入.

继续阅读 »

前言

MacOSX iOS安心打包、本地重签失败, 需要安装相关证书.

打开证书目录

安装证书

  1. 点击证书文件, 会自动打开钥匙串, 下拉列表钥匙串, 选择系统, 点击 添加 按钮
  2. 点击添加后, 请在弹窗中,输入电脑密码, 允许钥匙串访问.
  3. 按照上面的步骤, 依次完成其它证书的导入.

收起阅读 »

Android nvue 子页 图片闪烁;原因或是父页过多使用box-shadow

Android nvue

这几天 安卓 真机运行时 发现 两个问题

  1. nvue子页透明,显示出父页的内容
  2. nvue 图片闪烁,仿佛手机要 进化成炸弹了

经过不断排查,发现了解决方案;

1的解决 是设置子页的背景色

2的解决是删除了父页 box-shadow这个属性

继续阅读 »

这几天 安卓 真机运行时 发现 两个问题

  1. nvue子页透明,显示出父页的内容
  2. nvue 图片闪烁,仿佛手机要 进化成炸弹了

经过不断排查,发现了解决方案;

1的解决 是设置子页的背景色

2的解决是删除了父页 box-shadow这个属性

收起阅读 »

发布插件的坑(已解决)

插件市场

发布插件的坑

项目完成了,最近试着把公司一个下插件发布到插件市场玩一下,发布的过程提示都很到位,很多时候是文件放的位置不对,还有文件名起得不合要求,都一一提示了,非常友好。
但是发布后发现有些地方需要修改,要在更新一版,这时候就来劲了,明明我的文件结构和文件名都跟之前一模一样的,但就是提示我找不到这个插件的目录。
提示目录不存在](https://imgchr.com/i/se08u8)
看到这些提示我前前后后修改了不下十次,研究到底是我哪里名字写错了,还是网站的bug。。

坑的原因

郁闷了半天,问题依然没有解决,我突然灵机一动,试着从插件市场下载我的第一版插件下来,再上传上去,看看它能不能识别到。。
MD!竟然检查通过了,说明还是我的文件有问题啊!
顺着文件名和文件结构我继续再找了半天,发现还是找不出问题所在。我又灵机一动对比下我的压缩包和插件市场下载下来的压缩包
插件市场下载的](https://imgchr.com/i/se0GDS)
我压缩的](https://imgchr.com/i/se0JHg)
大小竟然相差一倍!

解决办法

不要使用mac自带的压缩,使用第三方压缩软件!
例如 解压专家Oka或者MyZip

继续阅读 »

发布插件的坑

项目完成了,最近试着把公司一个下插件发布到插件市场玩一下,发布的过程提示都很到位,很多时候是文件放的位置不对,还有文件名起得不合要求,都一一提示了,非常友好。
但是发布后发现有些地方需要修改,要在更新一版,这时候就来劲了,明明我的文件结构和文件名都跟之前一模一样的,但就是提示我找不到这个插件的目录。
提示目录不存在](https://imgchr.com/i/se08u8)
看到这些提示我前前后后修改了不下十次,研究到底是我哪里名字写错了,还是网站的bug。。

坑的原因

郁闷了半天,问题依然没有解决,我突然灵机一动,试着从插件市场下载我的第一版插件下来,再上传上去,看看它能不能识别到。。
MD!竟然检查通过了,说明还是我的文件有问题啊!
顺着文件名和文件结构我继续再找了半天,发现还是找不出问题所在。我又灵机一动对比下我的压缩包和插件市场下载下来的压缩包
插件市场下载的](https://imgchr.com/i/se0GDS)
我压缩的](https://imgchr.com/i/se0JHg)
大小竟然相差一倍!

解决办法

不要使用mac自带的压缩,使用第三方压缩软件!
例如 解压专家Oka或者MyZip

收起阅读 »

H5本地图片不显示、加载不出来的解决方案。

今天发布H5时发现不管在内置浏览器还是外部浏览器,本地图片都不能加载出来,路径是完全正确的,不管改为绝对路径还是相对路径都无法加载,后来打开manifest.json,点击源码视图找到H5配置,router下把"base" : "./",这句注释掉就能显示了,该行功能大概是发布H5时设为相对路径,能够在File协议里打开吧,但是路由会强制变为hash。

继续阅读 »

今天发布H5时发现不管在内置浏览器还是外部浏览器,本地图片都不能加载出来,路径是完全正确的,不管改为绝对路径还是相对路径都无法加载,后来打开manifest.json,点击源码视图找到H5配置,router下把"base" : "./",这句注释掉就能显示了,该行功能大概是发布H5时设为相对路径,能够在File协议里打开吧,但是路由会强制变为hash。

收起阅读 »