Stop camera from moving through objects

2019-09-03 03:44发布

问题:

There is a lot of questions on this theme but i couldn't find one that is fitting me.

I have camera movement script which looks like this:

using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using System;
using UnityEngine.Networking;

[AddComponentMenu("Camera-Control/Smooth Mouse Look")]
public class SmoothMouseLook : NetworkBehaviour
{
    [Header("Character camera.")]
    private Camera myCamera;
    [Header("Location where camera will always be looking at.")]
    public Transform characterHead;

    [Header("How fast will camera zoom work")]
    public float cameraScrollSensitivity = 2f;

    [Header("Default position of camera")]
    public Vector3 cameraPos = new Vector3(0, 2, 0);

    public Vector3 minPos = new Vector3(-4, -4, -5);
    public Vector3 maxPos = new Vector3(4, 4, -1);

    [Header("How fast will camera move on Y axis")]
    public float cameraSensitivityY = 0.8f;
    [Header("How fast will camera move on X axis")]
    public float cameraSensitivityX = 0.8f;

    public enum InvertX { False = 0, True = 1 }
    public enum InvertY { False = 0, True = 1 }

    public InvertX invertX = InvertX.False;
    public InvertY invertY = InvertY.False;

    void Start()
    {
        if (!isLocalPlayer)
            return;

        Camera.main.gameObject.transform.parent = this.transform;
        Camera.main.gameObject.transform.localPosition = cameraPos;
        myCamera = Camera.main;

        myCamera.transform.LookAt(characterHead);

    }
    void Update()
    {
        if (!isLocalPlayer)
            return;

        Vector3 currPos = myCamera.transform.localPosition;

        currPos.z += Input.GetAxis("Mouse ScrollWheel") * cameraScrollSensitivity;
        if (currPos.z > maxPos.z)
            currPos.z = maxPos.z;
        if (currPos.z < minPos.z)
            currPos.z = minPos.z;

        if (Input.GetMouseButton(2))
        {

            if(invertY == 0)
                currPos.y -= Input.GetAxis("Mouse Y") * cameraSensitivityY / 10;
            else
                currPos.y += Input.GetAxis("Mouse Y") * cameraSensitivityY / 10;


            if (invertX == 0)
                currPos.x += Input.GetAxis("Mouse X") * cameraSensitivityX / 10;
            else
                currPos.x -= Input.GetAxis("Mouse X") * cameraSensitivityX / 10;


            if (currPos.y > maxPos.y)
                currPos.y = maxPos.y;
            if (currPos.y < minPos.y)
                currPos.y = minPos.y;
            if (currPos.x > maxPos.x)
                currPos.x = maxPos.x;
            if (currPos.x < minPos.x)
                currPos.x = minPos.x;
        }

        myCamera.transform.localPosition = currPos;

        myCamera.transform.LookAt(characterHead);
    }
}

This script is attached to character and camera is it's child.

Just as title says, problem is that camera can go through mesh (objects and terrain).

I tried setting Culling mask to 0.01 and 1 (default is 0.3) but nothing happens.

I tried adding collider which works BUT when i push camera to the ground it collides, doesn't let camera down but it lift character up :/

Only idea i have is coding it with raycast but since i am new to all this i wanted to check if there is any other way of doing it (like with collider but do not lift character) because it will take a lot of my time figuring it out with raycast.

回答1:

Could you try doing this things . If you mean not pass through meshes like the camera in Unreal Engine you can do it something like this

  1. Select the camera, go the inspector and set the near clipping planes to 0.1
  2. create an empty game object. Give the empty a box collider, and set it to the exact location of the camera. Finally set the empty object as the Camera's parent. Now when you move you Empty, it moves the camera, and it won't go through the walls.

Hope this helps