arcore 示例_Android增强现实– Android ARCore示例

本文介绍了如何使用Google的ARCore库和Sceneform框架在Android应用中开发增强现实。通过示例代码展示了如何加载3D模型、进行运动追踪并在屏幕上定位虚拟物体。
摘要由CSDN通过智能技术生成

arcore 示例

In this tutorial, we’ll be discussing Augmented Reality and implement a hello world sample in our android application using Sceneform.

在本教程中,我们将讨论增强现实,并使用Sceneform在我们的android应用程序中实现一个hello world示例。

增强现实 (Augmented Reality)

Augmented Reality is gaining more popularity day by day. It’s used to show you virtual 3d models/graphics in a real world through your mobile’s camera. It’s useful in demonstrating simulated stuff in the real world such as paints/decoration you’d like to see on your wall.

增强现实正在日益普及。 它用于通过手机的相机向您展示真实世界中的虚拟3D模型/图形。 在演示现实世界中模拟的东西(例如您想在墙上看到的油漆/装饰)时非常有用。

Augmented Reality lies somewhere between Virtual Reality and Real environment.

增强现实位于虚拟现实和现实环境之间。

Android ARCore (Android ARCore)

Google has come up with ARCore library to enhance AR development.

Google提出了ARCore库来增强AR开发。

ARCore does motion tracking in the real world through the camera to create paths on planes/surfaces over which we can place our 3D Models and graphics.

ARCore通过摄像头在现实世界中进行运动跟踪,以在平面/表面上创建路径,我们可以在上面放置3D模型和图形。

SceneForm is a 3D framework that’s come up recently and is a better alternative to OpenGL. OpenGL looks intimidating to code.

SceneForm是最近出现的3D框架,是OpenGL的更好替代方案。 OpenGL看起来令人胆怯。

SceneForm allows us to quickly render 3d objects without the need to learn graphics or OpenGL.

SceneForm使我们能够快速渲染3d对象,而无需学习图形或OpenGL。

We can download the Google Sceneform Tools plugin in our Android Studio to view and render the 3d models.

我们可以在Android Studio中下载Google Sceneform Tools插件,以查看和渲染3D模型。

You can go to https://poly.google.com/ and download a sample model. Don’t forget to credit the creator!

您可以访问https://poly.google.com/并下载示例模型。 不要忘记相信创作者!

Typically, the OBJ and GLTX formats are used for rendering augmented images.

通常,OBJ和GLTX格式用于渲染增强图像。

Now let’s build our first AR application where we’ll use the above 3D model as our AR image.

现在,让我们构建第一个AR应用程序,在该应用程序中,我们将上述3D模型用作AR图像。

增强现实Android示例项目结构 (Augmented Reality Android Example Project Structure)

In the above project, we’ve created a sampledata directory, where we add the obj and mtl file downloaded earlier.

在上面的项目中,我们创建了一个sampledata目录,在其中添加了先前下载的obj和mtl文件。

Add the following dependency in your project’s build.gradle:

在项目的build.gradle中添加以下依赖项:

classpath 'com.google.ar.sceneform:plugin:1.0.1'

Add the following in your app’s build.gradle :

在您应用的build.gradle中添加以下内容:

implementation 'com.google.ar.sceneform.ux:sceneform-ux:1.0.0'

You need to set the ar plugin in your app’s Gradle file as well.
Add the following below the dependencies:

您还需要在应用程序的Gradle文件中设置ar插件。
在依赖项下面添加以下内容:

apply plugin: 'com.google.ar.sceneform.plugin'

We have used the following image, you can download it from this link and put it in the sampledata directory:

android poly google image

我们使用了以下图像,您可以从此链接下载它并将其放在sampledata目录中:

Now right click on the obj file and choose import sceneform assets:

android sceneform import path

现在,右键单击obj文件,然后选择导入sceneform资产:

This would automatically create the Renderable AR sceneform assets. It would automatically add the following lines at the end of the app’s build.gradle:

这将自动创建Renderable AR Sceneform资源。 它将自动在应用程序的build.gradle末尾添加以下行:

sceneform.asset('sampledata/Coffee Cup_final.obj',
        'default',
        'sampledata/Coffee Cup_final.sfa',
        'src/main/assets/Coffee Cup_final')

The build.gradle of the app looks like this finally:

android ARCore app build gradle

该应用程序的build.gradle最终看起来像这样:

Android ARCore Sceneform requires Java 8 or higher version.

Android ARCore Sceneform需要Java 8或更高版本。

The sja and sjb are the Sceneform Asset Description and Sceneform Binary files.

sja和sjb是Sceneform Asset DescriptionSceneform Binary文件。

The sjb file is visible in the 3D viewer. It is shipped with the APK.

sjb文件在3D查看器中可见。 它与APK一起提供。

The sja file is used to set properties for the sjb file.

SJA文件用于为SJB文件的属性集。

scale of the model in the sja file. scale

Android增强现实示例代码 (Android Augmented Reality Example Code)

To configure ARCore in your application add the following permission and metadata to your AndroidManifest.xml file.

要在您的应用程序中配置ARCore,请在您的AndroidManifest.xml文件中添加以下权限和元数据。

<uses-permission android:name="android.permission.CAMERA" />
    <uses-feature
        android:name="android.hardware.camera.ar"
        android:required="true" />

metadata goes inside the application tag.

元数据位于应用程序标记内。

<meta-data
            android:name="com.google.ar.core"
            android:value="required" />

The code for the activity_main.xml class is given below:

下面给出了activity_main.xml类的代码:

<?xml version="1.0" encoding="utf-8"?>
<android.support.design.widget.CoordinatorLayout xmlns:android="https://schemas.android.com/apk/res/android"
    xmlns:app="https://schemas.android.com/apk/res-auto"
    xmlns:tools="https://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <android.support.design.widget.AppBarLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:theme="@style/AppTheme.AppBarOverlay">

        <android.support.v7.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="?android:attr/actionBarSize"
            android:background="?android:attr/colorPrimary"
            app:popupTheme="@style/AppTheme.PopupOverlay" />

    </android.support.design.widget.AppBarLayout>

    <include layout="@layout/content_main" />

    <android.support.design.widget.FloatingActionButton
        android:id="@+id/fab"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="bottom|end"
        android:layout_margin="@dimen/fab_margin"
        app:srcCompat="@android:drawable/ic_input_add" />

</android.support.design.widget.CoordinatorLayout>

The code for the content_main.xml is given below:

下面给出了content_main.xml的代码:

<?xml version="1.0" encoding="utf-8"?>
<android.support.constraint.ConstraintLayout xmlns:android="https://schemas.android.com/apk/res/android"
    xmlns:app="https://schemas.android.com/apk/res-auto"
    xmlns:tools="https://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    app:layout_behavior="@string/appbar_scrolling_view_behavior"
    tools:context=".MainActivity"
    tools:showIn="@layout/activity_main">

    <fragment
        android:id="@+id/sceneForm"
        android:name="com.google.ar.sceneform.ux.ArFragment"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

</android.support.constraint.ConstraintLayout>

We’ve set the fragment as ArFragment. The ArFragment checks if the phone is compatible with ARCore.

我们将片段设置为ArFragment。 ArFragment检查手机是否与ARCore兼容。

Also, it checks if the camera permission is granted. If it isn’t, it’ll ask for it automatically.

此外,它还会检查是否授予了相机许可。 如果不是,它将自动要求它。

Also, it’ll ask you to download the ARCore by Google Application.

另外,它还会要求您通过Google Application下载ARCore。

list of devices. 设备列表当前支持ARCore。

The code for MainActivity.java class is given below:

MainActivity.java类的代码如下:

package com.journaldev.androidarsceneform;

import android.graphics.Point;
import android.net.Uri;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.design.widget.FloatingActionButton;
import android.support.v7.app.AlertDialog;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.Toolbar;
import android.view.View;
import android.view.Menu;
import android.view.MenuItem;

import com.google.ar.core.Anchor;
import com.google.ar.core.Frame;
import com.google.ar.core.HitResult;
import com.google.ar.core.Plane;
import com.google.ar.core.Trackable;
import com.google.ar.sceneform.AnchorNode;
import com.google.ar.sceneform.rendering.ModelRenderable;
import com.google.ar.sceneform.ux.ArFragment;
import com.google.ar.sceneform.ux.TransformableNode;

import java.util.List;
import java.util.function.Consumer;
import java.util.function.Function;

public class MainActivity extends AppCompatActivity {

    ArFragment arFragment;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);

        FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
        fab.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                addObject(Uri.parse("Coffee Cup_Final.sfb"));
            }
        });

        arFragment = (ArFragment) getSupportFragmentManager().findFragmentById(R.id.sceneForm);
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.menu_main, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();

        //noinspection SimplifiableIfStatement
        if (id == R.id.action_settings) {
            return true;
        }

        return super.onOptionsItemSelected(item);
    }

    private void addObject(Uri parse) {
        Frame frame = arFragment.getArSceneView().getArFrame();
        Point point = getScreenCenter();
        if (frame != null) {
            List<HitResult> hits = frame.hitTest((float) point.x, (float) point.y);

            for (int i = 0; i < hits.size(); i++) {
                Trackable trackable = hits.get(i).getTrackable();
                if (trackable instanceof Plane && ((Plane) trackable).isPoseInPolygon(hits.get(i).getHitPose())) {
                    placeObject(arFragment, hits.get(i).createAnchor(), parse);
                }
            }
        }
    }

    private final void placeObject(final ArFragment fragment, final Anchor createAnchor, Uri model) {
        ModelRenderable.builder().setSource(fragment.getContext(), model).build().thenAccept((new Consumer() {
            public void accept(Object var1) {
                this.accept((ModelRenderable) var1);
            }

            public final void accept(ModelRenderable it) {
                if (it != null)
                    MainActivity.this.addNode(arFragment, createAnchor, it);
            }
        })).exceptionally((new Function() {
            public Object apply(Object var1) {
                return this.apply((Throwable) var1);
            }

            @Nullable
            public final Void apply(Throwable it) {
                AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this);
                builder.setMessage(it.getMessage()).setTitle("error!");
                AlertDialog dialog = builder.create();
                dialog.show();
                return null;
            }
        }));
    }

    private void addNode(ArFragment fragment, Anchor createAnchor, ModelRenderable renderable) {

        AnchorNode anchorNode = new AnchorNode(createAnchor);
        TransformableNode transformableNode = new TransformableNode(fragment.getTransformationSystem());
        transformableNode.setRenderable(renderable);
        transformableNode.setParent(anchorNode);
        fragment.getArSceneView().getScene().addChild(anchorNode);
        transformableNode.select();
    }

    private Point getScreenCenter() {
        View vw = findViewById(android.R.id.content);
        return new Point(vw.getWidth() / 2, vw.getHeight() / 2);
    }
}

The anchor is the position where the model or the Node is placed in the screen. It’s the center of the screen here.

锚点是模型或节点在屏幕中的放置位置。 这是屏幕的中心。

In the addObject() the ARFragment gets the hit points on the plane using motion tracking.

addObject() ,ARFragment使用运动跟踪获取平面上的命中点。

placeObject() asynchronously sets the node to the center of the screen.

placeObject()异步将节点设置为屏幕的中心。

Following are the outputs when the application is launched:

以下是启动应用程序时的输出:

In the final output, the cup is positioned on the plane which consists of white dots.

在最终输出中,杯子位于由白点组成的平面上。

The above screenshot is from Samsung S8.

上面的截图来自三星S8。

Now try changing the model scale in SFA file!

现在尝试更改SFA文件中的模型比例!

This brings an end to this tutorial. You can download the final AndroidArSceneform Project from the link below.

本教程到此结束。 您可以从下面的链接下载最终的AndroidArSceneform项目

The size of the project is big, thanks to the OBJ file.

该项目的规模很大,这要归功于OBJ文件。

Github Repository. Github存储库下载android studio项目。

翻译自: https://www.journaldev.com/21479/android-augmented-reality-arcore-example

arcore 示例

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值