public void PlaceLeft()
    {
        TrackSection section = null;

        if (trackLayer.CurrentSection != null)
        {
            section = trackLayer.PlaceTrack(length, -angle);
        }
        else
        {
            RaycastHit hit;
            if (FirstPersonController.Main.RaycastCameraForward(out hit, 1000.0f, terrainMask))
            {
                section = trackLayer.StartTrack(hit.point + Vector3.up * 0.01f, GetNewTrackRotation(hit),
                                                length, -angle);
            }
        }
        if (section != null)
        {
            TrackFactory.Instance.PlaceAndRegisterSection(section, true);
            DeselectIfConnected();
        }
    }
Esempio n. 2
0
    private bool TryPlaceTrack(TrackSection from, bool fromEnd, TrackSection to, bool toEnd)
    {
        Vector3 intersection;

        fromPoint    = fromEnd ? from.EndPosition : from.Position;
        toPoint      = toEnd ? to.EndPosition : to.Position;
        fromRotation = fromEnd ? from.EndRotation : Helper.InvertTrackRotation(from.Rotation);
        // Note that this is pointing towards the section being build
        toRotation = toEnd ? to.EndRotation : Helper.InvertTrackRotation(to.Rotation);

        if (Helper.LineLineIntersection(out intersection,
                                        fromPoint,
                                        fromRotation * Vector3.forward,
                                        toPoint,
                                        toRotation * Vector3.forward))
        {
            float d1, d2, shortestDistance;
            d1 = shortestDistance = Vector3.Distance(intersection, fromPoint);
            d2 = Vector3.Distance(intersection, toPoint);
            if (d2 < shortestDistance)
            {
                shortestDistance = d2;
            }

            // Calculate curvature
            float curve = 180.0f - Quaternion.Angle(fromRotation, toRotation);

            // Check if the curve should go left or right
            var cross = Vector3.Cross(fromRotation * Vector3.forward, (toPoint - fromPoint));
            if (cross.y < 0)
            {
                // Go left
                curve = -curve;
            }


            // Calculate straight length
            var straightLength = Mathf.Max(d1, d2) - shortestDistance;

            trackLayer.Reposition(from, !fromEnd);
            if (d1 == d2)
            {
                // Place only curve
                trackLayer.PlaceTrack(CalculateCurveLength(curve, 0, 0), curve);
                TrackFactory.Instance.PlaceAndRegisterSection(trackLayer.CurrentSection, true);
            }
            else if (shortestDistance == d1)
            {
                // Place curve first, then straight
                trackLayer.PlaceTrack(CalculateCurveLength(curve, 0, straightLength), curve);
                TrackFactory.Instance.PlaceAndRegisterSection(trackLayer.CurrentSection);
                trackLayer.PlaceTrack(straightLength);
                TrackFactory.Instance.PlaceAndRegisterSection(trackLayer.CurrentSection, true);
            }
            else if (shortestDistance == d2)
            {
                // Place straight first, then curve
                trackLayer.PlaceTrack(straightLength);
                TrackFactory.Instance.PlaceAndRegisterSection(trackLayer.CurrentSection);
                trackLayer.PlaceTrack(CalculateCurveLength(curve, straightLength, 0), curve);
                TrackFactory.Instance.PlaceAndRegisterSection(trackLayer.CurrentSection, true);
            }

            trackLayer.Reposition(null, false);
            return(true);
        }
        // TODO: Add in-line check
        else if (Quaternion.Angle(fromRotation, Helper.InvertTrackRotation(toRotation)) < 0.5f)
        {
            trackLayer.Reposition(fromSection, !fromEnd);
            trackLayer.PlaceTrack(Vector3.Distance(fromPoint, toPoint));
            TrackFactory.Instance.PlaceAndRegisterSection(trackLayer.CurrentSection, true);
            return(true);
        }
        return(false);
    }