I'm trying to set the effect distance of a UI shadow based on a third person camera and the directional light in the scene to make it look like the UI has a shadow that moves depending on how the camera is rotated and the directional light, but I can't get the calculations right.
The camera is a normal third person camera that follows the player and orbits around the player.
I've been at this for a couple days, using a combination of the camera's forward, right and up values with the directional light's forward, right and up values. Multiplying and adding them together until it looks right.
This is the best I've found so far, but I still haven't found a good way to incorporate the directional light.
Vector2 effectDistance;
effectDistance.x = Camera.main.transform.right.z;
effectDistance.y = -Camera.main.transform.forward.y * Camera.main.transform.up.z;
if (Camera.main.transform.eulerAngles.x > 180)
{
effectDistance.y *= -1;
}
shadow.effectDistance = effectDistance * 100 * -directionalLight.right.y;
With this, when moving the camera up, the shadow moves up as well. But it doesn't take the directional light's eulerAngles.y into account yet, so it only follows correctly when it's set to 0.
But I've just found that this code still doesn't work fully even when the directional light's eulerAngles.y is 0...
I'm on the verge of giving up to be honest.
Here is what I came up with which seems to work more or less
My idea was mainly
So all together something like e.g.
var lightDirection = directionalLight.transform.forward;
// basically how the shadow falls on the ground
var lightOnGroundPlane = Vector3.ProjectOnPlane(lightDirection, Vector3.up);
// map the shadow direction into the camera plane
var lightDirectionOnCameraPlane = Vector3.ProjectOnPlane(lightOnGroundPlane, Camera.main.transform.forward);
// convert it to a direction in Camera local space
var lightDirectionOnCameraPlaneLocal = Camera.main.transform.InverseTransformDirection(lightDirectionOnCameraPlane);
// finally apply some multiplier (usually that would be for instance the height of the 3D object + you are in pixel space)
shadow.effectDistance = new Vector2(lightDirectionOnCameraPlaneLocal.x, lightDirectionOnCameraPlaneLocal.y) * 100;