Input operate
The OnMouse events for MonoBehaviour work efficiently and are often useful when you need to
detect and respond to mouse clicks. But they have some important limitations, as we’ll see here.
That’s why it’s necessary to have alternative methods and work-flows in your coding toolbox. One
limitation is that OnMouseDown takes Z-Order (depth) into consideration. This means: if you have two
overlapping objects in the scene, one in front of the other, then OnMouseDown will only fire for clicks on
the front object, and not on the back object. In many situations (such as for GUIs) this may be what
you want, but (for example) if your click is supposed to represent gun fire at a target object, then
you may want your weapon to shoot two enemies at once. Another limitation of these events is that
they won’t fire for mobile devices. In Unity, touch and tapping events don’t implicitly map to mouse
events. Therefore, a mobile touch event will not trigger a mouse down event, and vice versa. The
second issue we’ll examine later in this chapter. For now, let’s address the first issue. Specifically,
let’s see how to detect the cursor position manually and then convert its screen space position into
world space to see which objects have been clicked.
This code starts by detecting for a mouse click with Input.GetMouseButton. Once a click is detected,
it calls the ScreenPointToRay function of the Camera object to generate a ray structure, based on the
camera view and the mouse position. It should be mentioned here that for this functionality to work
correctly you should call ScreenPointToRay on the active camera (the camera you’re using for the
player view). Next, the function casts the ray into the scene with Physics.Raycast, and the nearest
intersection is returned in the HitInfo structure. Figure 9-4 shows this function at work.
if (Input.GetMouseButton(0)) { Debug.Log("left button pressed"); //Generate ray from main camera and mouse position Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition); //Will store info about nearest object hit RaycastHit hitinfo; //Test to see if ray intersects with any colliders if (Physics.Raycast(ray,out hitinfo)) { //Object was hit, get game object was hit GameObject hitGameObject = hitinfo.collider.gameObject; //Print gameobject name to console Debug.Log(hitGameObject.name); } }
Notice also that I’ve used Input.GetMouseButtonDown instead of Input.GetMouseButton. What is
the difference between these two? The latter function (GetMouseButton) returns true on every frame
for as long as the mouse button is being held down. The former (GetMouseButtonDown) returns true
only once for each button press. GetMouseButton is useful for executed repeated behavior while
the button is depressed, and GetMouseButtonDown is useful for executing on-off behavior on each
independent mouse click.

浙公网安备 33010602011771号