1
\$\begingroup\$

In this scene, the object becomes invisible and then comes back

Crate flies off the top of the screen, then falls back into view

In this scene, the object becomes invisible but does not come back

Wheel bounces off the right side of the screen and is never seen again

Is there any way I can tell if an object will come back when it becomes invisible?

Edit: Thank you to S. Tarık Çetin for the solution

     private void Update()
     {
         if (isInvisible)
             if (IsNotComingBack())
                 OnInvisible?.Invoke();
     }

     private void OnBecameInvisible()
     {
         isInvisible = true;
     }

     private bool IsNotComingBack()
     {
         var screenLeft = _cam.ScreenToWorldPoint(_cam.transform.position).x;
         var screenRight = _cam.ScreenToWorldPoint(Vector3.right * Screen.width).x;
         var objectWidth = _spriteRenderer.bounds.extents.x;
         var isNotComingBack = transform.position.x - objectWidth < screenLeft ||
                          transform.position.x + objectWidth > screenRight;
         return isNotComingBack;
     }
\$\endgroup\$
4
  • \$\begingroup\$ Hi, I'm not sure if I understand the question really... What do you mean by "Invisible", that it goes outside the camera? If so, the box becomes visible again because it is going up and down in an arch because of gravity/physics (shoot it makes it go up and outside of view, gravity makes it fall back down). The wheel on the other hand is moving to the right with physics and will not bounce back into view unless you program something to do that.. You would know if an object comes back, by thinking about it's trajectory. \$\endgroup\$
    – D.Kallan
    Commented Feb 23, 2021 at 3:59
  • \$\begingroup\$ @D.Kallan Yes, I'm talking about when it goes outside the camera. I know that the objects go out of view because of physics. Is there a formula that will take into account the position and velocity and tell me if the object will return to the scene? \$\endgroup\$
    – Sean Carey
    Commented Feb 23, 2021 at 4:21
  • \$\begingroup\$ Why you need to know that? \$\endgroup\$
    – Nikaas
    Commented Feb 23, 2021 at 8:46
  • 1
    \$\begingroup\$ @Nikaas Most likely they want to quickly end the turn if there are no actions left to do. \$\endgroup\$ Commented Feb 23, 2021 at 13:19

4 Answers 4

1
\$\begingroup\$

You know (x, y) of the object, you also know the (width, height). You know xMin, which is left of your screen, and xMax, which is right of your screen. If at any time either of these two conditions happens, it is not coming back:

  1. (x + width/2) < xMin
  2. (x - width/2) > xMax

Otherwise it is still within xMin and xMax, it will come down in the visible area.

You might need some other solution if the objects are not uniform scale, but this should give you the basic idea.

\$\endgroup\$
2
  • \$\begingroup\$ Doesn't this still leave a period of doubt, if the object is off the top of the screen but has not yet crossed xMin or xMax? In that case, it might be coming back (if its x velocity is low enough), or it might not (if its x velocity is high enough). \$\endgroup\$
    – DMGregory
    Commented Feb 23, 2021 at 13:23
  • 1
    \$\begingroup\$ It's actually a valid answer. Once the object becomes invisible, it's position tracking might be started to check if X position is out of viewport range. It might be a coroutine, it might be done in Update(). However, just because precision here doesn't change anything, running Coroutine once per second might do it just enough. \$\endgroup\$
    – eLTomis
    Commented Feb 23, 2021 at 17:52
2
\$\begingroup\$

The equation of motion for an object accelerating under constant gravity is:

$$\vec p(t) = \vec p_0 + \vec v_0 t + \frac 1 2 \vec a t^2$$

...where \$t\$ is the number of seconds since you started tracking the object in this particular ballistic arc (eg. since the time it was launched, or time in the future from this frame), and \$\vec p_0\$ and \$\vec v_0\$ are the position and velocity of the object at that start time \$t = 0\$

If you're using a physics engine with a symplectic Euler integrator like Box2D, it will have a slight integration error compared to the real physics equation above, but we can correct for that by nudging our \$\vec v_0\$ term forward in time:

$$ \vec v_{0\text{ for solving}} = \vec v_{0 \text{ reported}} + \frac 1 2 \vec a \Delta t$$

We take whatever velocity the object has according to Box2D, and add one half a time step's worth of acceleration to it, to get the term we'll use in the equation at the top. Here \$\Delta t\$ is the number of seconds per simulation step.

Now we can use the quadratic formula to solve this equation to find the times \$t^*\$ when the object crosses a particular height \$y^*\$ - say, the height at the top of your screen (or slightly below, if you want to make sure you see more that just the most fleeting glimpse of the object as it crosses the screen corner).

Or \$y^*\$ could be the height of your ground, if you want to predict where the object will land (and neglect objects that will briefly cross the corner of the screen again before landing out of view).

$$p_y(t^*) = y^*\\ p_0{_y} + v_0{_y}t^* + \frac 1 2 a_y {t^*}^2 = y^*\\ t^* = \frac {-v_0{_y} \pm \sqrt{v_0{_y}^2 - 4(\frac 1 2 a_y)(p_0{_y} - y^*)}}{a_y} $$

If you have no real solutions, then the object never goes off the top of the screen.

If you do have two real solutions for \$t\$, take the greatest one. This is the time in the future when the object falls back into the screen vertically.

Now substitute that \$t^*\$ into the equation at the top, and you'll get the full position of the object at that time. Now you can measure its x coordinate to see if it's still within the screen, or too far left/right to be visible.

Be sure to take the object's dimensions, or offset from its local origin point into account when picking your \$y^*\$ and left/right thresholds - they can be tighter for small objects and looser for large objects.

\$\endgroup\$
0
\$\begingroup\$

One generic way to handle this is to run the entire physics simulation in advance or rendering any of it and store the results for each frame in an array. You can then go through those results frame by frame to render them. If you do that you then know all of the positions for every object in the future, and can therefore work out which ones won't be coming back on screen.

This works even if things can collide with objects that are off screen and bounce back onto the screen, which I think would be possible from a bounce off the floor if the object was spinning in the right way.

Unfortunately it appears that Unity doesn't make it simple to do that. You'll probably need two copies of the scene, one of them without graphics. See https://answers.unity.com/questions/1114401/simulate-physics-without-rendering.html

\$\endgroup\$
-2
\$\begingroup\$

If there is no need to go back to same position then an easy way is adding colliders around the scene to make a bounce back when it goes off camera

\$\endgroup\$
4
  • \$\begingroup\$ But that doesn't seem to be what the question author wants. They don't want objects to bounce back from invisible walls just outside the camera. They want to know if they can safely remove the object because it's not coming back or not because its on a trajectory which will cause it to come back into the field of view of the camera. \$\endgroup\$
    – Philipp
    Commented Feb 23, 2021 at 17:44
  • \$\begingroup\$ I think a small tweak to this answer could bring it back on track. Instead of solid colliders that bounce the object back, you could use trigger colliders on the left and right, with a script that destroys the object on contact, and signals back to the gameplay logic that the item is gone forever now. \$\endgroup\$
    – DMGregory
    Commented Feb 23, 2021 at 18:07
  • \$\begingroup\$ Though the destroyer collider needs to be far enough away from the side to no destroy the object when the moving part is big and only 1/2 off screen. \$\endgroup\$
    – Zibelas
    Commented Feb 24, 2021 at 6:31
  • \$\begingroup\$ You guys are right. If he use a trigger collider to trigger when object goes off camera might solve cause he will know it's safe to destroy \$\endgroup\$ Commented Feb 24, 2021 at 14:49

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .