How to place a 3D Model in AR at center of screen and move it near or far with respect to camera angle on axis?

Viewed 1674

Below is the code which I have tried. It gives me the desired result but it is not optimized like camToPlan or MagicPlan app. In CamToPlan app center node moves very eficiently as per camera movement. If the camera is tilt the anchornode distance changes. How to achive the same in below code?

Camera camera = arSceneView.getScene().getCamera();
            Vector3 distance = Vector3.subtract(camera.getWorldPosition(), vector3CirclePosition);
            float abs = Math.abs(distance.y);
            float newAngleInRadian = (float) (Math.toRadians(90f) - (float) camera.getLocalRotation().x);
            float zCoordinate = (float) (abs / Math.cos(newAngleInRadian));
            Log.i("1", "zCoordinate::" + zCoordinate + "::" + abs);
            Vector3 cameraPos = arFragment.getArSceneView().getScene().getCamera().getWorldPosition();
            Vector3 cameraForward = arFragment.getArSceneView().getScene().getCamera().getForward();
            Vector3 position = Vector3.add(cameraPos, cameraForward.scaled(zCoordinate));
            redNodeCenter.setWorldPosition(position);
1 Answers

Step1: Create addWaterMark() method in your class

 private var oldWaterMark : Node? = null
 
 private fun addWaterMark() {
    ModelRenderable.builder()

            .setSource(context, R.raw.step1)
            .build()
            .thenAccept {
                addNode(it)
            }
            .exceptionally {
                Toast.makeText(context, "Error", Toast.LENGTH_SHORT).show()
                return@exceptionally null
            }

}

private fun addNode(model: ModelRenderable?) {
    if(oldWaterMark!=null){
        arSceneView().scene.removeChild(oldWaterMark)
    }
    model?.let {
        val node = Node().apply {
            setParent(arSceneView().scene)
            var camera = arSceneView().scene.camera

            var ray = camera.screenPointToRay(200f,500f)

           // var local=arSceneView.getScene().getCamera().localPosition

            localPosition = ray.getPoint(1f)
            localRotation = arSceneView().scene.camera.localRotation
            localScale = Vector3(0.3f, 0.3f, 0.3f)


            renderable = it
        }

        arSceneView().scene.addChild(node)
        oldWaterMark = node
    }
}

Step 2: Call the addWaterMark() inside addOnUpdateListener

  arSceneView.scene.addOnUpdateListener { addWaterMark() }

Note: I created oldWaterMark object for remove the old watermark

If you want to change the position change this line

  camera.screenPointToRay(200f,500f)//200f -> X position, 500f -> Y position
Related