微信小程序遇到AR,会擦出怎么样的火花期待激动......

通过该教程,可以从基础开始打造一个微信小程序的AR框架,所有代码开源,提供大家学习。

本课程需要一定的基础:微信开发者工具,JavaScript,Html,Css

第二章:基石-摄像头数据获取


【前情提要】

  上一章,我们了解了微信小程序与AR相遇一些前因后果,同时也,罗列出来是要实现这样的功能,我们要做的事情:

1. 实现在微信小程序中访问摄像头,并且可以实时的拿到每一帧画面的数据。
2. 实现在微信小程序中访问WebGL接口,实现绘制三维物体。该教程采用Three.js引擎
3. 实现在背景为摄像头实时画面的背景上显示WebGL的3D物体。
4. 整体框架搭建
5. 图像算法接入

【目的】

微信小程序获取摄像头数据,可以实时获得每一帧的每一个像素数据。

【准备】

  下面需要搭建环境,做一些准备工作。

  首先,需要注册微信小程序开发者。注册地址=>

  注册成功之后,需要下载微信小程序开发工具。下载地址=>

  目前笔者的开发环境是:Windows 10

  下载的微信小程序版本为:RC v1.0.2.1909111

【创建工程】 

  打开,微信开发者工具之后,会看到如下的页面。

  

  用注册好的微信扫描二维码之后,就可以登陆开发工具。下面可以选择”小程序项目“下的”小程序“选项,创建一个系的呢小程序。

  其中有几个项目可以按照下面的说明填写:

  项目名称:为该小程序的项目名称,目前我们用CameraTest

  目录:项目文件保存的本地文件目录,可以点击右侧的小箭头,选择本地的一个空目录

  AppID:这个微信小程序绑定的ID,每个需要上线的小程序都要有自己的ID。我们做测试的时候,可以用测试号来创建。当然这样创建的小程序只能用来测试,不可以发布。点击“AppID”下面的“测试号”几个字,即可以自动使用测试号。

  开发模式:我们选择“小程序”模式

  后端服务:这是微信小程序新推出的功能,可以使用微信自己的云平台开发数据库,我们目前不需要,所以选择不适用云服务器。(选择测试账号之后,就不会显示后端服务选项,测试账号不支持后端服务)

  语言:选择“JavaScript”

配置还之后可以参考下图:

  配置完成后,选择“新建”按钮,创建一个新的小程序项目。

关于小程序开发工具的使用,不是本教程的重点,所以这里不会做过多的阐述。感兴趣的同学,可以自行学习=>

  这时候可以看到,工具已经为我们创建好了一个新的预定义的工程,工程文件目录,可以在编辑器中查看到,如下图:

  当然,目前创建的工程中有很多不需要的内容,我们把不需要的文件删掉,做一个最简单的工程。删减之后的文件目录如下:

  剩下,需要删除一些不需要的代码。

  首先“app.js”文件,将不需要的代码删除,最后保留如下的代码:

//app.js
App({
onLaunch: function () { },
})

  同时,我们需要将“app.wxss”中的内容全部删除。  

  然后,我们需要删除“app.json”中不需要的内容,最后保留如下内容:

{
"pages": [
"pages/index/index"
],
"window": {
"backgroundTextStyle": "light",
"navigationBarBackgroundColor": "#fff",
"navigationBarTitleText": "WeChat",
"navigationBarTextStyle": "black"
},
"sitemapLocation": "sitemap.json"
}

  接着删除“index.js”文件中不需要的代码:

//index.js
//获取应用实例
const app = getApp() Page({
data: {
},
onLoad: function () { },
})

  最后,删除“index.wxml”中不需要的部分:

<view>

</view>

  另外,我们需要用到小程序最新的SDK,这样才可以用到获取摄像头数据的功能。该功能是从2.7.0版本之后支持的。

  打开开发工具,的“详情”按钮,然后选择“本地设置”,在调用基础库中选择大于2.7.0的版本,如下图:

  这样我们就建立了一个简单的基本工程(后面的章节中如需创建基本工程,也是按照相同的步骤)。

小知识:

微信小程序的架构类似于网页程序

wxml文件类似于Html文件,用于页面的布局

wxss文件类似于css文件,用于定义页面的样式

js文件都是用于实现业务逻辑

json文件是微信小程序特有的,用于定义该页面的权限等相关参数

【开发】

  下面我们就来实现一下,微信小程序获取摄像头每一帧数据的功能。

  首先,在index.wxml文件中,添加摄像头Camera标签,如下:

<view class="container">
<camera
mode="normal"
device-position="back"
flash="auto"
frame-size="medium"
style="position:fixed;width:100%;height:100%">
</camera>
</view>

  在camera的标签中,我们添加了几个属性

  mode:代表摄像头开启的模式,是拍照或者摄像模式

  device-position:代表我们开启的是前置的还是后置的摄像头

  flash:标记摄像头闪光灯的模式

  frame-size:就是我们在每一帧画面中获得的数据内容的大小

  style:指示页面的上camera区域的大小位置

小知识:

有关camera标签的更多设置,可以参考微信公众号的文档=>

  设置完wxml文件之后,就已经可以在模拟器中看到摄像头的画面了。其次,我们需要在代码中,获取到每一帧画面的数据。

  微信基础库2.7.0版本之后提供了camera的帧回调函数,可以通过回调函数拿到每一帧的画面数据。在“index.js”的文件中,添加代码,如下:

//index.js
//获取应用实例
const app = getApp() Page({
data: {
},
onLoad: function () {
//获取视频context
var cameraContext = wx.createCameraContext();
//注册帧回调函数
var listener = cameraContext.onCameraFrame((frame)=>{
//打印返回数据是否是一个ArrayBuffer,并且返回每一帧的大小
console.log(frame.data instanceof ArrayBuffer, frame.width, frame.height);
});
//启动监听
listener.start();
},
})

  代码首先通过createCameraContext()函数,获得当前页面上的摄像头内容,其次通过onCameraFrame函数注册一个事件监听函数,最后启动监听。

  在回调函数中,会返回一个frame的对象,该对象有三个属性:width,height和data,width与height保存了每一帧画面的宽度和高度,data属性保存了每一帧画面的像素列表。

  如果一切正常,保存代码后在输出面板,我们可以看到回调函数里的输出:

true 480 640

  这代表每一帧得到的data是一个ArryBuffer数组,并且每一帧的画面宽度是480个像素,高度是640个像素。

  其次的我们想更进一步了解data中的数据,每一个像素到底用了多少空间,包含了哪些颜色的值。

  为此,我们可以加一些代码:

//index.js
//获取应用实例
const app = getApp() Page({
data: {
},
onLoad: function () {
//获取视频context
var cameraContext = wx.createCameraContext();
//注册帧回调函数
var listener = cameraContext.onCameraFrame((frame)=>{
//获取每一帧data的长度
var data = new Uint8Array(frame.data);
console.log(data.length);
});
//启动监听
listener.start();
},
})

  用一个Uint8Array对象来保存frame中的data数据,然后我们输出data.length得到数组的长度。在笔者的环境中,获得到的输出如下:

1228800

  这样我们可以计算一下,每个像素占用了几个Uint8的空间。现在已知每帧画面的长宽为640*480,所以每一帧画面有

  640*480=307200 个像素

  每个像素占用的Uint8空间的个数为:

  1228800/307200=4 个

  由此可知,每个像素占用了4个Uint8的空间。也就是说,一个像素存储的形式是"[0-255],[0-255],[0,255],[0,255]" 4个0-255的数值。可以很容易的联想到,每个像素应该是按照RGBA的格式,即红色分量,绿色分量,蓝色分量以及透明度这四个值存储的。(事实也是如此)

  有兴趣的同学,也可以试验一下在摄像头前面放不同颜色的纸验证一下这个猜测。

  至此,我们就可以获得每一帧的数据,以及每一帧每个像素RGBA四个分量的值。这些值将有助于后面图像相关的各种算法,了解这些值在frame.data中的组成结构也可以帮助我们今后更好的实现我们的AR功能。

【总结】

  为了给后面的框架结构打好基础,这一章我们主要学习了,如何在微信公众号环境下打开摄像头并实时的获取到每一帧的数据。

  实现的方法主要是通过,createCameraContext接口获取摄像头的内容,再通过onCameraFrame注册帧回调函数从而在回调函数传回的数据中得到每一帧具体的像素内容。

  通过这样的方法,我们可以得到每一帧的大小,以及每一帧每个像素RGBA四个分量的数值。

【代码】

Github =>

当微信小程序遇到AR(二)的更多相关文章

  1. 当微信小程序遇到AR(四)

    当微信小程序遇到AR,会擦出怎么样的火花?期待与激动...... 通过该教程,可以从基础开始打造一个微信小程序的AR框架,所有代码开源,提供大家学习. 本课程需要一定的基础:微信开发者工具,JavaS ...

  2. 微信小程序条码、二维码生成模块

    代码地址如下:http://www.demodashi.com/demo/13994.html 一.前期准备工作 软件环境:微信开发者工具 官方下载地址:https://mp.weixin.qq.co ...

  3. 微信小程序把玩(二十八)image组件

    原文:微信小程序把玩(二十八)image组件 image组件也是一个程序不可缺少的,可以这样说一个app中image组件随处可以看到,一般 image有两种加载方式第一种是网络图片第二种是本地图片资源 ...

  4. 微信小程序把玩(二十九)video组件

    原文:微信小程序把玩(二十九)video组件 视频播放组件与图片加载组件也没啥差别,使用起来也没啥注意的 重要属性: wxml <!--监听button点击事件--> <button ...

  5. 微信小程序把玩(二十七)audio组件

    原文:微信小程序把玩(二十七)audio组件 音频播放已经封装的很好!只需配合属性设置即可! (method和data配合使用) 主要属性: wxml <audio action="{ ...

  6. 微信小程序把玩(二十四)toast组件

    原文:微信小程序把玩(二十四)toast组件 toast消息提示框,可用在提示一些信息,比如清楚缓存给用户一个友好的提示!或操作一些请求不想让用户有什么操作,toast也可以做到因为toast显示时其 ...

  7. 微信小程序把玩(二十五)loading组件

    原文:微信小程序把玩(二十五)loading组件 loading通常使用在请求网络数据时的一种方式,通过hidden属性设置显示与否 主要属性: wxml <!----> <butt ...

  8. 微信小程序把玩(二十六)navigator组件

    原文:微信小程序把玩(二十六)navigator组件 navigator跳转分为两个状态一种是关闭当前页面一种是不关闭当前页面.用redirect属性指定. 主要属性: wxml <naviga ...

  9. 微信小程序把玩(二十二)action-sheet组件

    原文:微信小程序把玩(二十二)action-sheet组件 action-sheet组件是从底部弹出可选菜单项,估计也是借鉴IOS的设计添加的,action-sheet有两个子组件, action-s ...

随机推荐

  1. .NET Core 3时代DevExpress Winforms v19.2增强TreeList控件

    DevExpress Winforms Controls内置140多个UI控件和库,完美构建流畅.美观且易于使用的应用程序.无论是Office风格的界面,还是分析处理大批量的业务数据,DevExpre ...

  2. Jquery select 三级联动 (需要JSON数据)

    Scripts/Category.js //Jquery三级类别联动 $(function () { BindCategory(); }) function BindCategory() { var ...

  3. Appium自动化测试教程-自学网-monkey参数

    monkey 参数 参数分类 · 常规类参数 · 事件类参数 · 约束类参数 · 调试类参数 常规类参数 常规类参数包括帮助参数和日志信息参数.帮助参数用于输出Monkey命令使用指导:日志信息参数将 ...

  4. HashMap判断键是否为null

    用containsKey(),而不用get(): HashMap中,null可以作为键,这样的键只有一个:可以有一个或多个键所对应的值为null.当get()方法返回null值时,即可以表示HashM ...

  5. word如何选择图片粘贴

    自动导入Word图片,或者粘贴Word内容时自动上传所有的图片,并且最终保留Word样式,这应该是Web编辑器里面最基本的一个需求功能了.一般情况下我们将Word内容粘贴到Web编辑器(富文本编辑器) ...

  6. 51nod 1060

    反素数定义:对于任意正整数 $n$, 其约数个数记为 $f(n)$, 如果某个正整数 $n$ 满足 对于任意正整数 $i, (0 < i < n)$, 都有 $f(i) < f(n) ...

  7. 51nod 1051

    * 最大子矩阵 * sum[i][j] 表示第 i 行前 j 列的和,即每一行的前缀 * i,j 指针枚举列,k指针枚举行 * Now 记录当前枚举的子矩阵的价值 * 由于记录了前缀信息,一旦 Now ...

  8. [Poj] Roads in the North

    http://poj.org/problem?id=2631 树的直径裸题 dfs/bfs均可 /* dfs */ #include <iostream> #include <cst ...

  9. 牛客练习赛55 E-树 树形DP

    题意 你有一颗大小为\(n\)的树,点从\(1\)到\(n\)标号. 设\(dis⁡(x,y)\)表示\(x\)到\(y\)的距离. 求\(\sum_{i=1}^{n}\sum_{j=1}^{n}di ...

  10. 分页——为Mybatis配置PageHelper

    1.pom.xml追加 pagehelper : 4.1.4 2.mappers.xml中追加 <plugins> <plugin interceptor="com.git ...