three.ar.js_我们如何通过AR.js使产品吉祥物栩栩如生
three.ar.js
by Mateusz Tarnaski
由Mateusz Tarnaski
我们如何通过AR.js使产品吉祥物栩栩如生 (How we brought our product mascot to life with AR.js)
Short answer: using a browser-based Augmented Reality (AR) application. For the long answer, read below.
简短答案:使用基于浏览器的增强现实(AR)应用程序。 对于长答案,请阅读以下内容。
The idea of playing with AR started as a random interesting experiment. In our company, we strive to stay at the edge of the curve. We share technical novelties and new technologies with each other on a semi-regular basis. Since we are mostly dealing with web technologies, the concept of AR in the browser really took off.
玩AR的想法最初是一个有趣的随机实验。 在我们公司,我们努力保持在曲线的边缘。 我们半定期地分享技术新颖性和新技术。 由于我们主要处理Web技术,因此浏览器中AR的概念真正兴起了。
Since AR is mostly an entertainment technology, a practical application was not obvious to us from the start. Luckily, two unrelated things happened at the same time:
由于AR主要是一种娱乐技术,因此从一开始,实际应用对我们来说并不明显。 幸运的是,同时发生了两项无关的事情:
we had just created a mascot for our product — Hubert,
我们刚刚为我们的产品创建了一个吉祥物- 休伯特(Hubert) ,
we had to do a marketing booth at devoxxPL 2018
我们必须在devoxxPL 2018上做一个营销摊位
We decided to bring Hubert to life during the event, in the form of an AR app for people to play with. In our heads, users should be able to:
我们决定在活动期间通过一个可供人们玩耍的AR应用程序使Hubert栩栩如生。 在我们看来,用户应该能够:
- render Hubert on a wall background in their phones在手机中的背景墙上渲染休伯特
- take a picture of the rendered model拍摄渲染模型的照片
- tweet the photo (not the subject of this article)鸣叫照片(不是本文的主题)
The end result is available on glitch.com, scaled down and rotated to be suitable for a desktop experience (you can also take a quick look into the source code).
最终结果可在glitch.com上找到 , 并按比例缩小和旋转以适合桌面体验(您也可以快速查看源代码 )。
实时渲染休伯特 (Rendering Hubert in real time)
We used AR.js (version from this commit) as the main building block of our AR app — it packages webRTC camera access, marker recognition, and 3D scene rendering. We liked it mostly because you can have a basic demo running in around 20 lines of code.
我们使用AR.js ( 此commit的版本)作为我们的AR应用程序的主要构建块-它包装了webRTC摄像机访问,标记识别和3D场景渲染。 我们之所以喜欢它,主要是因为您可以在大约20行代码中运行一个基本演示。
Under the hood, AR.js can use either three.js or A-frame implementations to render your 3D scenes.
在后台,AR.js可以使用three.js或A-frame实现来渲染3D场景。
- three.js offers fine-grained control of 3D rendering, and is JavaScript-based. You have probably heard about it in the context of rendering 2D and 3D scenes in the browser.three.js提供了3D渲染的细粒度控制,并且基于JavaScript。 您可能在浏览器中渲染2D和3D场景时听说过它。
- A-frame is a web framework designed specifically for building VR and AR experiences. It has an HTML-like markup that is more declarative than three.js, but sacrifices some of the control in favor of ease of use.A框架是专门为构建VR和AR体验而设计的Web框架。 它具有类似HTML的标记,比three.js更具声明性,但是为了便于使用而牺牲了一些控件。
We didn’t have a VR or 3D expert (except Mrówa, who prepared the 3D model). As A-frame’s HTML-like declarative syntax looked more familiar to us, we opted for A-frame to do the rendering.
我们没有VR或3D专家(准备3D模型的Mrówa除外)。 由于A框架的类似HTML的声明性语法对我们来说更熟悉,因此我们选择了A框架进行渲染。
Here you can see the code for rendering Hubert, 30 lines on the dot. We omitted some options and A-frame tweaking for the sake of simplicity. You can refer to the repo to see it all.
在这里,您可以看到渲染点30行的Hubert的代码。 为了简单起见,我们省略了一些选项和A帧调整。 您可以参考该仓库以查看全部内容。
This gives us Hubert nicely rendered in the web browser in real time.
这使我们的Hubert可以在Web浏览器中很好地实时呈现。
拍摄照片以进行鸣叫 (Capturing a photo to tweet)
Unfortunately, we don’t have a single video feed rendering the whole scene. There is the video from your camera and a rendered 3D scene. We quickly figured out that we would have to capture a frame from both sources and put them together for a nice photo of Hubert.
不幸的是,我们没有一个视频提要呈现整个场景。 有摄像机的视频和渲染的3D场景。 我们很快就发现,我们必须从这两个来源中捕获一帧并将它们放在一起才能获得Hubert的漂亮照片。
Taking frames out of a webRTC video stream is pretty straightforward. The best material on the subject can be found here. If your browser has the appropriate API, you need two elements:
从webRTC视频流中取出帧非常简单。 有关此主题的最佳材料可以在此处找到 。 如果您的浏览器具有适当的API,则需要两个元素:
- a reference to your source <video/> tag对源<video />标签的引用
- a destination <canvas/> element in which to put your frame用于放置框架的目标<canvas />元素
Then it’s just a simple matter of drawing a 2D image from video to canvas. In our case, both of these are a bit tricky.
然后,只需将视频中的2D图像绘制到画布即可。 在我们的情况下,这两者都有些棘手。
The video take we are using is generated and embedded by AR.js. We had no idea how to get it gracefully, so we hacked our way around it with a loop and a DOM selector:
我们正在使用的视频片段由AR.js生成并嵌入。 我们不知道如何优雅地获取它,因此我们用一个循环和一个DOM选择器来破解它:
We also needed to hack some scaling. AR.js doesn’t present the raw video feed to the user, they scale it to fill the screen without losing aspect ratio. That means we need to apply the same scaling to our frame. If not, our screenshot will have “more” of the video feed than is shown on the screen. We don’t want to confuse the users here.
我们还需要破解一些扩展。 AR.js不会将原始视频提要呈现给用户,而是会对其进行缩放以填充整个屏幕,而不会丢失宽高比。 这意味着我们需要对框架应用相同的缩放比例。 如果没有,我们的屏幕快照将具有比屏幕上显示的更多的视频供稿。 我们不想在这里混淆用户。
What the user sees:
用户看到的内容:
If we take a frame without scaling and just try to copy from point (0,0) we lose margins imposed by AR.js. This is a totally different picture from what is presented to the user:
如果我们采取不缩放的框架, 而只是尝试从点(0,0)复制,则会失去AR.js施加的边距。 这是与呈现给用户的图片完全不同的图片:
Suffice it to say we just reverse-engineered the scaling and figured out the bounding box of what the user sees:
可以说我们只是对缩放比例进行了逆向工程,并弄清楚了用户看到的边界框:
To achieve this final result (the same as what is presented live to the user, give or take some camera shake):
要获得最终结果(与向用户实时展示的内容相同,请晃动或晃动照相机):
Now we just need to get Hubert in the picture. Again, the API for that is very straightforward. To capture a screenshot of a rendered A-frame scene, we need to get the scene’s canvas. The relevant part is copied to our destination canvas, on top of the previously taken video frame.
现在,我们只需要让Hubert参与其中即可。 同样, 该API非常简单。 要捕获渲染的A帧场景的屏幕截图,我们需要获取场景的画布。 在先前拍摄的视频帧之上,相关部分被复制到我们的目标画布。
Getting the relevant part is the tricky bit in our case. Thanks to the AR.js scaling, we cannot simply get the “perspective” shot of the scene and use that. It will look too wide or too short, depending on orientation.
在我们的案例中,获取相关部分是棘手的事情。 由于AR.js的缩放,我们不能简单地获得场景的“透视”镜头并使用它。 根据方向的不同,它看起来太宽或太短。
For landscape mode (width > height), the scaling method we used for video works perfectly well.
对于横向模式(宽度>高度),我们用于视频的缩放方法效果很好。
For portrait mode, it works great on a PC… However, once you enter the realm of mobile devices, the scaling breaks and the screenshot doesn’t look nice. You get this skinny Hubert…
对于纵向模式,它可以在PC上很好地工作……但是,一旦进入移动设备领域,缩放比例就会中断,并且屏幕截图看起来也不会很好。 你得到这个瘦的休伯特…
…instead of our lovely, bubbly mascot in all his glory:
…代替他所有荣耀的可爱,起泡的吉祥物:
We are still not sure why that is the case. We made the mistake of not testing it out thoroughly on actual mobile devices, thinking it would work the same as it does on the development machine. (Yes, we know how bad that sounds, but that’s the reality of it.) During the conference, we managed to figure out the formula for portrait scaling and introduced a fix:
我们仍然不确定为什么会这样。 我们犯了一个错误,即没有在实际的移动设备上进行全面测试,认为它的工作原理与在开发机上的工作原理相同。 (是的,我们知道这听起来有多糟,但这是事实。)在会议期间,我们设法找出人像缩放的公式并引入了解决方法:
It’s not pretty. It’s one of those “it’s late, it works, just leave it” fixes. The values presented above produced a satisfactory result and we left it at that.
不好看 这是“迟到了,它起作用了,随它去吧”修复程序之一。 上面给出的值产生了令人满意的结果,我们保留了该结果。
With that, we have a picture of Hubert in the real world! It can be retrieved from the destination canvas element and displayed on the page or sent to the server to tweet out.
这样,我们就可以看到真实世界中的休伯特照片! 可以从目标画布元素中检索它并将其显示在页面上,或发送到服务器以发出鸣叫。
摘要 (Summary)
AR in the browser is possible. Even more, it is possible on mid-grade mobile hardware (as of June 2018). Getting it to work on every phone and browser is still a long shot, so don’t count on it for wide, diverse userbases.
浏览器中的AR是可能的。 更重要的是,截至2018年6月,中端移动硬件也可以使用。 要使其在每部手机和浏览器上都能正常工作还很遥远,因此不要指望广泛而多样的用户群可以使用它。
However, if you have a somewhat controlled environment, augmented reality on a phone can be used to create unique experiences. These don’t require special hardware or workstations and that is a big, big plus. Just make sure to test it on actual devices ahead of time.
但是,如果您在某种程度上控制了环境,则可以使用电话上的增强现实来创建独特的体验。 这些不需要特殊的硬件或工作站,这是一大优势。 只要确保提前在实际设备上进行测试即可。
翻译自: https://www.freecodecamp.org/news/how-we-brought-our-product-mascot-to-life-87830db12ff4/
three.ar.js
相关文章:

利用tuning-primer脚本优化MySQL数据库
脚本下载网址: http://www.day32.com/MySQL/tuning-primer.sh #!/bin/sh # vim: ts8########################################################################## ## MySQL performance tuning primer script ## Writen by: Matthew Montgomery ## Report bugs t…

自定义View步骤学习笔记
用途 : 一个View内部的子控件比较多的时候可以自定义一个View,把它内部的子控件屏蔽起来(就像苹果的导航栏上面的UIBarButton,你是通过BarButtonitem来修改显示的内容) 1.重写 initWithFrame 和 awakeFromNib(一般两个都要写),然后在写一个初始化的方法,在初始化方法中添加子控…

小程序给视频加默认图片封面,点击播放视频并停止播放上一个视频
微信小程序开发交流qq群 173683895 承接微信小程序开发。扫码加微信。 实现的功能: 微信小程序视频组件添加图片封面, 点击图片播放视频, 点击下一个视频的封面图自动停止播放当前视频并播放点击的视频。 效果GIF图: 实现代码: WXML …

一天 用户旅程_439天的旅程改变了我的生活
一天 用户旅程by Daniel Lemay丹尼尔勒梅(Daniel Lemay) 439天的旅程改变了我的生活 (The 439 day Journey that Changed my Life) It was Spring of 2017. I was beyond displeased with my current work situation. I dreaded going into work every day and being a punchi…

实现音乐播放器
音乐播放器 首先声明一下,本例是直接采用课本中范例122的方法。 效果图如下: 1、activity_main.xml布局 1 //四个按钮2 <LinearLayout3 android:layout_width"fill_parent"4 android:layout_height"wrap_content"5 …

学习ASP.NET MVC系列 - 还有比这更简炼的吗?把复杂的事情变简单了,贡献啊!...
转自学习ASP.NET MVC系列: 学习ASP.NET MVC(一)——我的第一个ASP.NET MVC应用程序 学习ASP.NET MVC(二)——我的第一个ASP.NET MVC 控制器 学习ASP.NET MVC(三)——我的第一个ASP.NET MVC 视图 学习ASP.NET MVC(四)——我的第一个ASP.NET MVC 实体对象 学习ASP.NET…
微信小程序开通腾讯云开发实践流程附详细图解
微信小程序开发交流qq群 173683895 云开发流程: 1.关联账户 关联腾讯云账号与微信公众号平台账号。前往关联账号时,请选择微信公众号。错误关联账号请在腾讯云账号中心重新绑定。 已关联账号 2.安装开发者工具 下载与安装客户端微信开发者工具并使…

github组织存储库使用_为什么我不使用您的GitHub存储库
github组织存储库使用by Sam Westreich, PhD由Sam Westreich博士 为什么我不使用您的GitHub存储库 (Why I’m not using your GitHub repository) As a bioinformatician, I reside in an interesting middle ground between developers and end users. My background trainin…

PHP导入excel到mysql数据库完整代码附效果图
微信小程序开发交流qq群 173683895 承接微信小程序开发。扫码加微信。 1.新建一个数据库 ImportXlsx 并在里面添加表名 IsXlsx. 2.下载 phpExcel 插件 点击下载 3.导入文件和xlsx 。 4.获取xlsx表的对象并存入数据库 效果图: PHP 实现 demo <?phph…

黑马程序员—易混淆的知识
------- android培训、java培训、期待与您交流! ---------- String和StringBuffer类区别1.String 是定长的例如:String s1"abc";s1"egf";StringBuffer类:是变成字符串,因为它具有(buffer)缓冲区&a…

简谈 Java 中的泛型通配符
很好的一篇文章https://zhuanlan.zhihu.com/p/26681625 转载于:https://www.cnblogs.com/hihtml5/p/6978651.html

播客#47:劳伦斯·布拉德福德
On todays episode, I interview Laurence Bradford. Shes the creator of the LearnToCodeWith.me blog and podcast, and the Newbie Coder Warehouse Facebook group.在今天的一集中,我采访了劳伦斯布拉德福德。 她是LearnToCodeWith.me博客和播客以及Newbie Cod…

如何使用 DBCC MEMORYSTATUS 命令来监视 SQL Server 2005 中的内存使用情况
https://technet.microsoft.com/en-us/solutionaccelerators/dd537566.aspx 注意:这篇文章是由无人工介入的微软自动的机器翻译软件翻译完成。微软很高兴能同时提供给您由人工翻译的和由机器翻译的文章, 以使您能使用您的语言访问所有的知识库文章。然而由机器翻译的…

{code:-1,error:`QcloudSecretId`不能为空,请确保 SDK 配置已正确初始化}解决方法
微信小程序开发交流qq群 173683895 承接微信小程序开发。扫码加微信。 微信小程序云开发登录报错:{"code":-1,"error":"QcloudSecretId不能为空,请确保 SDK 配置已正确初始化"} 遇到这个错误的原因是:腾讯不…

[转载] Tmux 速成教程:技巧和调整
原文: http://blog.jobbole.com/87584/ 决定从 screen 转向 tmux 了, 非常喜欢 tmux 的窗格功能. 简介 有些开发者经常要使用终端控制台工作,导致最终打开了过多的标签页。如果你也是他们当中的一员,或者你正在实践结对编程,那么我推荐你读一…

css在兼容模式下无法引用_如何在CSS中使用深色模式
css在兼容模式下无法引用by Frank Lmmer由FrankLmmer 如何在CSS中使用深色模式 (How to get dark mode working with CSS) I have been playing around with MacOS Mojave’s dark mode lately. It’s not 100% pleasing to my eyes, yet. But it’s especially useful when n…

COJ 0995 WZJ的数据结构(负五)区间操作
WZJ的数据结构(负五)难度级别:C; 运行时间限制:1000ms; 运行空间限制:262144KB; 代码长度限制:2000000B 试题描述请你设计一个数据结构,完成以下功能…

接入网易云信IM即时通讯的微信小程序聊天室
微信小程序开发交流qq群 173683895 承接微信小程序开发。扫码加微信。 接入流程: 初次接触网易云通信IM服务,您可以通过以下产品介绍文档了解我们的产品功能、相关概念、业务限制: 产品简介主要功能帐号集成与登录接口及业务限制 1. 创建…

vue颜色选择器_如何制作? Vue的颜色选择器!
vue颜色选择器by ZAYDEK由ZAYDEK 如何制作? Vue的颜色选择器! (How to make a ? color picker with Vue!) 注意:颜色看起来可能比实际颜色更可爱! (Caution: colors may appear cuter than they are!) Before I get to the arti…

centos7中使用yum安装tomcat以及它的启动、停止、重启
centos7中使用yum安装tomcat 介绍 Apache Tomcat是用于提供Java应用程序的Web服务器和servlet容器。 Tomcat是Apache Software Foundation发布的Java Servlet和JavaServer Pages技术的开源实现。 本教程介绍在CentOS 7服务器上使用yum进行Tomcat 7的基本安装和一些配置。请注意…

JS 数组A有数组B的数据就删除
微信小程序开发交流qq群 173683895 承接微信小程序开发。扫码加微信。 创建了两个数组,并且封装了一个函数以供调用。 var arr1 [a,b,c,d],arr2 [a,c,d,f]; this.arrayWeightRemoval(arr1,arr2); //返回结果 [b] ;// 数据去重this.arrayWeightRemoval functio…

PL/SQL Developer的调试存储过程
学会使用PL/SQL Developer的调试功能,对于编写复杂的存储过程,包,funtion...非常有帮助,所以今晚学习了一下: (1)在sp里设置断点。 (2)点击TEST. (3) Debug-->Start. …

graphql_普通英语GraphQL指南
graphqlby Luis Aguilar路易斯阿吉拉尔(Luis Aguilar) 普通英语GraphQL指南 (A Guide to GraphQL in Plain English) 您需要了解的最新流行语正在席卷API开发领域。 (All you need to know about the latest buzzword that’s taking the API development scene by storm.) TL…

第1课第4.4节_Android硬件访问服务编写HAL代码
android应用如何访问C库 - 落魄影子 - 博客频道 - CSDN.NET http://blog.csdn.net/ab198604/article/details/51249303 Android硬件访问服务框架代码编写 - 落魄影子 - 博客频道 - CSDN.NET http://blog.csdn.net/ab198604/article/details/51397586 4 编写HAL代码 源码下载方…
Android新版NDK环境配置(免Cygwin)
本菜鸟在查阅了很多文章,又是去折腾cygwin之类的,虽然可以编译出so文件,但运行项目却有很多问题。当发现最新的ndk不需要cygwin的时候,跪了(orz)。 现在进入正题。 使用工具: adt-bundle-window…

小程序获取用户的操作轨迹日志
微信小程序开发交流qq群 173683895 花费了两天时间,修改过数次,终于把这个功能封装成了一个独立的工具。 任何小程序都可在不修改原代码的情况下直接镶入使用!!! 步骤: 1. 在小程序 app.js 的平级目录…

paypal提现软件_PayPal软件工程师生命中的一天
paypal提现软件Find out what a normal day is like for a PayPal software engineer.找出PayPal软件工程师的正常日子。 Shruti Kapoor shares what she does and shows off some of the PayPal campus in San Jose, California.Shruti Kapoor分享了她的工作,并展…

关于IOS的蓝牙(转)
关于IOS的蓝牙 首先,你要了解你的目的是什么,一般的IOS蓝牙开发有以下三种目的: 1. IOS设备和IOS设备之间交互 好消息是:ios6.0可以把iPhone手机当从设备了,可以两台iPhone通过蓝牙通信传数据了,有点类似sp…

JavaSE--jdom解析之bom
参考:http://www.cnblogs.com/findumars/p/3620078.html 1 org.jdom2.input.JDOMParseException: Error on line 1: Content is not allowed in prolog. 2 13:15:55,821 [main] ERROR SajtSvrImpl:182 - 未知:org.jdom2.input.JDOMParseException: Error…

JS数组去重,JS根据数组里面的对象属性值去重
微信小程序开发交流qq群 173683895 承接微信小程序开发。扫码加微信。 微信小程序开发交流qq群 173683895 js数组简单去重 var arr1 [1, 2, 3, 4, 5, 6, 3, 4, 3];function arrayUnique1(arr) {var arr1 [], obj {};for (var i 0, elem; (elem arr[i]) ! null; i) {i…