乐趣区

初探uniapp框架-踩坑

近些天有接触到 uni-app 框架,使用 HBuilderX 软件进行编译,能生成多端项目文件,如微信、百度、支付宝小程序及 Android 和 ios 端,记录遇到的问题

1. 条件编译

  • 我觉得比较突出的一点功能,就是这个条件编译,指定对应的代码执行在对应的一端
#ifdef:if defined 仅在某平台存在
#ifndef:if not defined 除了某平台均存在
如:只在微信小程序中才执行的代码
// #ifdef MP-WEIXIN 
uni.getSystemInfo({
    success: res => {this.navHeight = `${res.statusBarHeight + 46}px`;
    }
});
// #endif

  • uni-app 条件编译
  • 在 pages.json 中也能够有这样的条件编译

2. 使用相机功能

  • 在 Android 中,能够在跳转页面后直接调用 api 来使用相机,但是 ios 上就不行,跳转后无法调用相机
/* 调用相机代码 */
uni.chooseImage({
    count: 1,
    sizeType: ['original', 'compressed'],
    sourceType: ['camera'],
    success: res => {const tempFilePaths = res.tempFilePaths[0];
    }
});

3. 对于 scroll-view 中的 scroll-into-view 定位元素

  • scroll-into-view,值应为某子元素 id(id 不能以数字开头)。设置哪个方向可滚动,则在哪个方向滚动到该元素

在使用这个滚动到对应元素时,前端的渲染需要进行一定的延迟才能够定位到对应的 id

<scroll-view class="scrollView" scroll-with-animation scroll-x :scroll-into-view="'cate_'+scrollIntoCate">
    <view :id="'cate_'+item.id"v-for="item in cateList":key="item">{{item.title}}</view>
</scroll-view>

/* 在 js 中 */
onLoad(options) {setTimeout(() => {this.scrollIntoCate = options.id;}, 400);
},
.scrollView{
    /* 若是横向滚动定位,应设置宽度 */
    width: 100%;
    /* 若是竖向滚动定位,则应设置高度 */
    height: 100%;
}

如果你是竖向的滚动定位,则你必须设置高度,横向定位的话,应该设置宽度,否则无法定位元素

4. 对于覆盖在视频上的文字

  • 小程序端能够使用 cover-view 来进行覆盖视频,但是,App 端暂不支持 cover-view、cover-image 组件之间的嵌套,使得在小程序上能够实现的布局,app 端则样式错乱
  • app 端使用了原生子窗体 subNav 来实现覆盖
  • 使用后缀名为 nvue 的文件

    • px:以 750 宽的屏幕为基准动态计算的长度单位,与 vue 页面中的 rpx 理念相同。(一定要注意 nvue 里的 px,和 vue 里的 px 逻辑不一样)
    • wx:与设备屏幕宽度无关的长度单位,与 vue 页面中的 px 理念相同
    • 使用 nvue 的注意点
  • 在 pages.json 中进行 subNav 的配置
{
    "path": "pages/video/video",
    "style": {
        "app-plus": {
            /* 子窗体定位 */
            "subNVues":[{  
                "id": "videoChild",
                "path": "pages/video/index", 
                "style": {  
                    "position": "absolute",  
                    "left": "0px",
                    "bottom": "0px",
                    "width": "750px",
                    "height": "100px",
                    "background": "transparent"
                }  
            }]  
        }  
    }
}

将要设置子窗体的页面放入同一个文件夹,在 index.nvue 中,文字的放置应该是在 text 中,在 pages.json 中也应写死宽度,不能使用百分比,支持 flex 布局,同时,在 index.nvue 中你要是想设置背景色,则应该使用 background-color

  • subNVue 子窗体与 vue/nvue 页面通信
/* list.vue 文件 */
this.$nextTick(() => {uni.$emit('children', Object);
})

/* index.nvue 文件 */
<div class="shopInfo" id="videoChild">
    <text class="shopName">@{{shopname}}</text>
</div>


created() {uni.$on('children', (data) => {this.$nextTick(() => {console.log(data);
        })
    })
},
/* 在页面销毁前移除监听事件 */
beforeDestroy(){uni.$off('children');
},

5.animation 动画

  • 设置动画形成不同效果,使用不同的动画时间
<view class="listItem" v-for="item in imageList" :key="item.id">
    <image class="itemImg" :src="item.img" :style="{animationDuration: item.index}"></image>
</view>


this.imageList.push(...res.data.result.list);
    for (let i = 0; i < this.imageList.length; i++) {if (!this.imageList[i].index) {this.imageList[i].index = parseInt(35 + Math.random() * (10 - 5)) + 's';
    }
}
.itemImg {
    width: 1000upx;
    height: 318upx;
    animation: imageMove linear infinite alternate;
}
@keyframes imageMove {
    0% {transform: translateX(0);
    }
    50% {transform: translateX(-30%);
    }
    100% {transform: translateX(0);
    }
}

6. 指定每次分割数组的长度

  • 开始的时候我想的有点多,想着每次指定分割长度后再进行操作,实际上只要直接操作就可以了
let cateList = [];
this.cateLength = cateList.length;
let temporaryList = [];
if (cateList.length > 10) {for (let i = 0; i < cateList.length; i += 10) {let list = cateList.slice(i, 10 + i);
        temporaryList.push(list);
    }
    this.cateList = temporaryList;
}

正在努力学习中,若对你的学习有帮助,留下你的印记呗(点个赞咯 ^_^)

  • 往期好文推荐:

    • 实现单行及多行文字超出后加省略号
    • 判断 iOS 和 Android 及 PC 端
    • 使用 vue 开发移动端管理后台
    • 原生 js 实现瀑布流及微信小程序中使用左右两列实现瀑布流
    • 画三角形
退出移动版