NOTE: See bottom of the question as I have managed to use a workaround which works to press the two buttons at once on Android (thanks to Douglas Potestas help)
Ive struggled with this in the past and got it working. But its been a long time since I have used Raycasts and I have mostly forgotten. Quick summary before people tell me to use OnPointerEnter etc is that on all of my Android games using OnPointer events you cannot press the two buttons (eg. imaging a NES gamepad pressing A and B with the same thumb like when you play Mario or something). You cannot slide the thumb to press both it only registers the first button hit, and this is not adequate for most of my game ideas.
Basically, I want to check if the thumb is over any amount of buttons at every frame of the game loop.
So I have this very basic code which I hoped would work, but the hit only returns anything if it hits a physical game object such as Cube or Capsule.
I want it to return if it hits a UI Image/Panel/Button (it matters not which one really).
I've tried adding 2d box collider and a 3d cube collider both as trigger and not trigger and made sure its big enough. I've tagged the image/button. I've checked the Raycast Target box. Here is update loop of my OnScreenControlManager.cs
void Update () {
Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
RaycastHit hit;
float rayLength = Mathf.Infinity;
if (Physics.Raycast(ray, out hit, rayLength))
{
Debug.Log("hit coll = " + hit.collider.tag);
if (hit.collider.tag == "LeftButton")
{
Debug.Log("hit coll = " + hit.collider.tag);
}
}
}
I definitely had this working about a year ago in Unity 5. I'm now using Unity 2017, hope that isn't anything to do with it.
Have also tried Physics2d.Raycast:
private void Update()
{
RaycastHit2D hit = Physics2D.Raycast(Camera.main.ScreenToWorldPoint(Input.mousePosition), Vector2.zero);
if (hit.collider != null)
{
Debug.Log("Target tag: " + hit.collider.tag);
}
}
Solution which works using new Rects and the Overlaps method. (Note , you cannot use this if the buttons are small and close together
public class OnScreenController : MonoBehaviour
{
Rect touchRect;
public float touchRectExtents;
Bounds buttonLeftBounds;
public GameObject buttonLeft;
Rect buttonLeftRect;
Bounds buttonABounds;
public GameObject buttonA;
Rect buttonARect;
Bounds buttonBBounds;
public GameObject buttonB;
Rect buttonBRect;
public Text aPressed, bPressed;
private void Start()
{
buttonLeftBounds = buttonLeft.GetComponent<Collider2D>().bounds;
buttonABounds = buttonA.GetComponent<Collider2D>().bounds;
buttonBBounds = buttonB.GetComponent<Collider2D>().bounds;
}
private void Update()
{
touchRect = new Rect(Input.mousePosition.x - touchRectExtents, Input.mousePosition.y - touchRectExtents, touchRectExtents * 2, touchRectExtents * 2);
buttonLeftRect = new Rect(buttonLeftBounds.center.x - buttonLeftBounds.extents.x, buttonLeftBounds.center.y + buttonLeftBounds.extents.y, buttonLeftBounds.size.x, buttonLeftBounds.size.y);
buttonARect = new Rect(buttonABounds.center.x - buttonABounds.extents.x, buttonABounds.center.y + buttonABounds.extents.y, buttonABounds.size.x, buttonABounds.size.y);
buttonBRect = new Rect(buttonBBounds.center.x - buttonBBounds.extents.x, buttonBBounds.center.y + buttonBBounds.extents.y, buttonBBounds.size.x, buttonBBounds.size.y);
if (touchRect.Overlaps(buttonLeftRect))
{
Debug.Log(" LEFT PRESSED");
}
if (touchRect.Overlaps(buttonARect))
{
aPressed.text = "A PRESSED";
}
else
{
aPressed.text = "A NOT PRESSED";
}
if (touchRect.Overlaps(buttonBRect))
{
bPressed.text = "B PRESSED";
}
else
{
bPressed.text = "B NOT PRESSED";
}
}
}
EDIT: Still doesnt work :[ although i can now press the two buttons at once with the same touch, i need to add a way to check for other touches. For example if I am using the D-Pad with left thumb, this code doesnt even detect the hit on the buttons because Mouse.inputposition is still over at the D-Pad.