ARKit touch object to interact with it, is it possible?

Now, I am working on a project which allow users to interact with the 3D object when it is detected. After they interact with the 3D object, it would show another 3D object. Thank you so much if you could help 🙂

Replies

Hey,


So I'm just getting started with ARKit myself, but I've finished a game (almost), so I might be able to provide some insight.


(Please keep this in mind as all my methods may not be completely kosher)


Anyway, YES, you can interact with AR objects.


What's important to keep in mind is because you're still dealing with SK or SC Nodes, many of their methods work in the context of AR.


For Example:


touchesBegan: still tracks finger placements on the screen, allowing you to detect if a node is touched in the exact same way as you normally would in Spritekit or Scenekit.


You can also use a line like this to see if the node as at any particular point, area, or even off screen:


(In this particular case I'm testing if a node is dead center on screen (Typical Shooting Game Crosshair Situation))



SKNode *node = [self nodeAtPoint:CGPointZero];







The problem is, the context is a little different.


You may have noticed in the AR example that you basically have to ask for an ARAnchor in your Scene, but the ViewController actually defines the sprite.


This makes certain things like assigning actions awkward, because any selectors used would have to be in the view controller. (or you'd have to get them to execute selectors differently, but I honestly don't know how to do that correctly (perfectly) in this context (yet).




Garbage Collection gets a little trickier because ARAnchors have to be dealt with along with the SKNodes we add to them.



A simple method I used to get familiar with the situation was to simply pass along the name of the ARANchor identifier to the Sprite with the following line:



sprite.name = [anchor.identifier UUIDString];


Then, I'd assign it a runAction to FadeToAlpha:0 (This basically makes it fade away, and sets the alpha to 0, which we can test for)


Afterwards, in the Scene, you can run a loop like this:



    for(SKSpriteNode *sate in self.children) {

       if(sate.alpha == 0) {
      
            //NSLog(@"Removing Transparent Satellite");
          
            [self removeExplosionAnchorsByName:sate.name];
          
            [self loadSatellite];
       }
    }



And then the final function does the actual cleanup:



- (void)removeExplosionAnchorsByName:(NSString *)name {

    ARSKView *sceneView = (ARSKView *)self.view;
    ARFrame *currentFrame = [sceneView.session currentFrame];
   
    //[sceneView.session removeAnchor:anchor];
   
    //[self loadSatellite];
   
    for(ARAnchor *tempAnchor in currentFrame.anchors) {
   
        //NSLog(@"Lingering:%@", [tempAnchor.identifier UUIDString]);
       
        if([[tempAnchor.identifier UUIDString] isEqualToString:name]) {
       
            [sceneView.session removeAnchor:tempAnchor];
        }
   
    }
}



This keeps your Scene clean, but the more robust thing would be to define the Sprites userData Dictionary in the nodeForAnchor method of the View Controller (ARSKScene Delegate) according to whatever complexity you require.


Note: The current builds of ARKit (Beta) also adds a name property to the ARAnchor itself, so it seems even Apple is still shifting around how these should work.


My guess is the Anchors will end up becoming a property of the node itself (Instead of the current Anchor > Node Parent/Child Relationship),

much like the current position object normally used in Spritekit. This however remains to be seen.



All the Best!


P.S


It doesn't seem possible to MOVE an ARAnchor yet, which I would love to be able to animate.


(I haven't tried running an SKAction against a ARAnchor but my guess is 99.999999999999999999 % of a horrible crash anyway)