Ejemplo n.º 1
0
    void Update()
    {
        // calculate average position of each player and grappling hook reticles
        int     sources       = 0;
        Vector3 newAimOffset1 = Vector3.zero;

        if (grapple1.GetReticle(1) != null && grapple1.GetReticle(1).activeSelf)
        {
            newAimOffset1 += (grapple1.GetReticle(1).transform.position - player1.transform.position);
            sources++;
        }
        if (grapple1.GetReticle(2) != null && grapple1.GetReticle(2).activeSelf)
        {
            newAimOffset1 += (grapple1.GetReticle(2).transform.position - player1.transform.position);
            sources++;
        }
        if (sources > 0)
        {
            newAimOffset1 /= sources;
        }
        sources = 0;
        Vector3 newAimOffset2 = Vector3.zero;

        if (grapple2.GetReticle(1) != null && grapple2.GetReticle(1).activeSelf)
        {
            newAimOffset2 += (grapple2.GetReticle(1).transform.position - player2.transform.position);
            sources++;
        }
        if (grapple2.GetReticle(2) != null && grapple2.GetReticle(2).activeSelf)
        {
            newAimOffset2 += (grapple2.GetReticle(2).transform.position - player2.transform.position);
            sources++;
        }
        if (sources > 0)
        {
            newAimOffset2 /= sources;
        }
        // lerp screen centers to new screen centers
        aimOffset1    = Vector3.Lerp(aimOffset1, newAimOffset1, lerpSpeed);
        aimOffset2    = Vector3.Lerp(aimOffset2, newAimOffset2, lerpSpeed);
        screenCenter1 = player1.transform.position + (aimOffset1 / 2);
        screenCenter2 = player2.transform.position + (aimOffset2 / 2);
        // center of each split screen
        Vector3 center;
        // ratio of screen width to height
        float widthHeightRatio = 1f * Screen.width / Screen.height;
        // corners of camera
        Vector3 topLeft     = new Vector3(-widthHeightRatio, 1f, 0f);
        Vector3 topRight    = new Vector3(widthHeightRatio, 1f, 0f);
        Vector3 bottomLeft  = new Vector3(-widthHeightRatio, -1f, 0f);
        Vector3 bottomRight = new Vector3(widthHeightRatio, -1f, 0f);
        // point between players
        Vector3 centerPoint = (screenCenter1 + screenCenter2) / 2;
        // direction from one player to the other
        Vector3 splitOrthogonal = screenCenter1 - centerPoint;
        // direction of split
        Vector3 split = Vector3.Cross(splitOrthogonal, Vector3.forward).normalized;

        // if split is intersecting with left and right of screen
        if (Mathf.Abs(split.x) > Mathf.Abs(split.y) * widthHeightRatio)
        {
            // intersecting points
            Vector3 splitIntersection1 = new Vector3(widthHeightRatio, split.y * (widthHeightRatio / split.x), 0f);
            Vector3 splitIntersection2 = -splitIntersection1;
            // if player1 is on the top
            if (splitOrthogonal.y > 0)
            {
                // location in center of each screen
                center = cameraSize * Centroid4(topLeft, topRight, splitIntersection1, splitIntersection2);
            }
            // if player1 is on the bottom
            else
            {
                // location in center of each screen
                center = cameraSize * Centroid4(bottomLeft, bottomRight, splitIntersection1, splitIntersection2);
            }
        }
        // if split is intersecting with top and bottom of screen
        else
        {
            // intersecting points
            Vector3 splitIntersection1 = new Vector3(split.x * (1f / split.y), 1f, 0f);
            Vector3 splitIntersection2 = -splitIntersection1;
            // if player1 is on the right
            if (splitOrthogonal.x > 0)
            {
                // location in center of each screen
                center = cameraSize * Centroid4(bottomRight, topRight, splitIntersection1, splitIntersection2);
            }
            // if player1 is on the left
            else
            {
                // location in center of each screen
                center = cameraSize * Centroid4(bottomLeft, topLeft, splitIntersection1, splitIntersection2);
            }
        }

        // feathered location for split screen cameras
        float featherAmount = ((screenCenter1 - screenCenter2).magnitude - splitscreenDistanceMultiplier * cameraSize) / (centerCameraDistanceMultiplier * cameraSize - splitscreenDistanceMultiplier * cameraSize);

        if (featherAmount < 0)
        {
            featherAmount = 0;
        }
        if (featherAmount > 1)
        {
            featherAmount = 1;
        }
        Vector3 feather = (1 - featherAmount) * splitscreenDistanceMultiplier * cameraSize / 2 * (screenCenter2 - screenCenter1).normalized - featherAmount * center;

        // set positions of all cameras
        // main camera should be between two players
        transform.position = (screenCenter1 + screenCenter2) / 2 + offset;
        // these cameras should smoothly transition according to feather
        cam1.transform.position = screenCenter1 + feather + offset;
        cam2.transform.position = screenCenter2 - feather + offset;
        // set orientation of renderer based on orientation of players, split should be perpendicular to vector between players
        vRenderer.transform.up = screenCenter2 - screenCenter1;
        divider.transform.up   = vRenderer.transform.up;
        // scale divider according to distance between players
        float scale = dividerScaleMultiplier * (screenCenter1 - screenCenter2).magnitude;

        if (scale > maxDividerSize)
        {
            scale = maxDividerSize;
        }
        divider.transform.localScale = new Vector3(1f, scale, 1f);
        // if the screen should split, show the renderer
        if ((screenCenter1 - screenCenter2).magnitude > splitscreenDistanceMultiplier * cameraSize)
        {
            vRenderer.SetActive(true);
            divider.SetActive(true);
        }
        else
        {
            vRenderer.SetActive(false);
            divider.SetActive(false);
        }
    }