예제 #1
0
        public static int BentConnections(bool ignoreAnnos)
        {
            return(Project.Current.Elements.OfType <Connection>().Count(p =>
            {
                var port1 = (Room.CompassPort)p.VertexList[0].Port;
                var port2 = (Room.CompassPort)p.VertexList[1].Port;

                if (port1 == null || port2 == null)
                {
                    return false;
                }

                var firstRoomConnectionDir = port1.CompassPoint;
                var secondRoomConnectionDir = port2.CompassPoint;

                if (ignoreAnnos)
                {
                    return !Project.Current.Canvas.EqualEnough(firstRoomConnectionDir, CompassPointHelper.GetOpposite(secondRoomConnectionDir));
                }
                if (p.VertexList[0].Connection.StartText != "" || p.VertexList[1].Connection.EndText != "")
                {
                    return false;
                }

                // if the port directions are not (roughly) opposite, then we have a bent connection. Note NN(EW) = N, WW(NS) = W, etc.
                return !Project.Current.Canvas.EqualEnough(firstRoomConnectionDir, CompassPointHelper.GetOpposite(secondRoomConnectionDir));
            }
                                                                        ));
        }
예제 #2
0
        Room IAutomapCanvas.CreateRoom(Room existing, AutomapDirection directionFromExisting, string name)
        {
            if (!Project.Current.Elements.Contains(existing))
            {
                // avoid issues if the user has just deleted the existing room
                return(null);
            }

            var room = new Room(Project.Current);

            room.Name = name;

            Vector delta;

            PositionRelativeTo(room, existing, CompassPointHelper.GetCompassDirection(directionFromExisting), out delta);

            if (AnyRoomsIntersect(room))
            {
                ShiftMap(room.InnerBounds, delta);
                Debug.WriteLine("Shift map.");
            }

            Project.Current.Elements.Add(room);

            return(room);
        }
예제 #3
0
        public void Element(string localName, CompassPoint value)
        {
            string name;

            if (CompassPointHelper.ToName(value, out name))
            {
                Writer.WriteElementString(localName, name);
            }
        }
예제 #4
0
        public void Value(CompassPoint value)
        {
            string name;

            if (CompassPointHelper.ToName(value, out name))
            {
                Writer.WriteValue(name);
            }
        }
예제 #5
0
        public void Attribute(string localName, CompassPoint value)
        {
            string name;

            if (CompassPointHelper.ToName(value, out name))
            {
                Writer.WriteAttributeString(localName, name);
            }
        }
예제 #6
0
        void PositionRelativeTo(Room room, Room existing, CompassPoint existingCompassPoint, out Vector delta)
        {
            delta    = CompassPointHelper.GetAutomapDirectionVector(existingCompassPoint);
            delta.X *= Settings.PreferredDistanceBetweenRooms + room.Width;
            delta.Y *= Settings.PreferredDistanceBetweenRooms + room.Height;

            var newRoomCenter = existing.InnerBounds.Center + delta;

            room.Position = Settings.Snap(new Vector(newRoomCenter.X - room.Width / 2, newRoomCenter.Y - room.Height / 2));
        }
예제 #7
0
        public CompassPoint ToCompassPoint(CompassPoint defaultValue)
        {
            CompassPoint point;

            if (CompassPointHelper.FromName(Text, out point))
            {
                return(point);
            }
            return(defaultValue);
        }
예제 #8
0
        void IAutomapCanvas.RemoveExitStub(Room room, AutomapDirection direction)
        {
            if (!Project.Current.Elements.Contains(room))
            {
                // avoid issues if the user has just deleted one of these rooms
                return;
            }

            var compassPoint = CompassPointHelper.GetCompassDirection(direction);

            foreach (var connection in room.GetConnections(compassPoint))
            {
                CompassPoint sourceCompassPoint, targetCompassPoint;
                var          source = connection.GetSourceRoom(out sourceCompassPoint);
                var          target = connection.GetTargetRoom(out targetCompassPoint);
                if (source == room && target == room && sourceCompassPoint == compassPoint && targetCompassPoint == compassPoint)
                {
                    Project.Current.Elements.Remove(connection);
                }
            }
        }
예제 #9
0
        void IAutomapCanvas.AddExitStub(Room room, AutomapDirection direction)
        {
            if (!Project.Current.Elements.Contains(room))
            {
                // avoid issues if the user has just deleted one of these rooms
                return;
            }

            var sourceCompassPoint = CompassPointHelper.GetCompassDirection(direction);
            var connection         = addConnection(room, sourceCompassPoint, room, sourceCompassPoint);

            switch (direction)
            {
            case AutomapDirection.Up:
                connection.StartText = Connection.Up;
                break;

            case AutomapDirection.Down:
                connection.StartText = Connection.Down;
                break;
            }
        }
예제 #10
0
        public Vector GetCorner(CompassPoint point, RoomShape myRmShape = RoomShape.SquareCorners, CornerRadii corners = null)
        {
            bool   isOctagonal = (myRmShape == RoomShape.Octagonal);
            bool   isRounded   = (myRmShape == RoomShape.RoundedCorners);
            bool   isEllipse   = (myRmShape == RoomShape.Ellipse);
            double angleInRadians;

            if (myRmShape == RoomShape.Ellipse)
            {
                angleInRadians = CompassPointHelper.CalcRadianForEllipse(point, this);
                return(new Vector(Center.X + (float)((Width / 2.0) * Math.Cos(angleInRadians)), Center.Y + (float)((Height / 2.0) * Math.Sin(angleInRadians))));
            }

            if (myRmShape == RoomShape.Ellipse)
            {
                if (point == CompassPoint.NorthEast || point == CompassPoint.NorthWest || point == CompassPoint.SouthWest || point == CompassPoint.SouthEast)
                {
                    angleInRadians = CompassPointHelper.CalcRadianForEllipse(point, this);

                    if (point == CompassPoint.NorthEast)
                    {
                        var rect = new Rect(X + Width, Y, (float)corners.TopRight, (float)corners.TopRight);
                        return(new Vector((rect.Center.X - (float)(corners.TopRight / 2.0)) - (float)((corners.TopRight / 2.0) * Math.Cos(angleInRadians)), (rect.Center.Y + (float)(corners.TopLeft / 4.0)) + (float)((corners.TopRight / 2.0) * Math.Sin(angleInRadians))));
                    }

                    if (point == CompassPoint.NorthWest)
                    {
                        var rect = new Rect(X, Y, (float)corners.TopLeft, (float)corners.TopLeft);
                        return(new Vector((rect.Center.X - (float)(corners.TopLeft / 2.0)) - (float)((corners.TopLeft / 2.0) * Math.Cos(angleInRadians)), (rect.Center.Y + (float)(corners.TopLeft / 4.0)) + (float)((corners.TopLeft / 2.0) * Math.Sin(angleInRadians))));
                    }

                    if (point == CompassPoint.SouthWest)
                    {
                        var rect = new Rect(X, Y + Height, (float)corners.BottomLeft, (float)corners.BottomLeft);
                        return(new Vector((rect.Center.X - (float)(corners.BottomLeft / 2.0)) - (float)((corners.BottomLeft / 2.0) * Math.Cos(angleInRadians)), (rect.Center.Y - (float)(corners.BottomLeft / 2.0)) - (float)((corners.BottomLeft / 2.0) * Math.Sin(angleInRadians))));
                    }

                    if (point == CompassPoint.SouthEast)
                    {
                        var rect = new Rect(X + Width, Y + Height, (float)corners.BottomRight, (float)corners.BottomRight);
                        return(new Vector((rect.Center.X - (float)(corners.BottomRight / 2.0)) - (float)((corners.BottomRight / 2.0) * Math.Cos(angleInRadians)), (rect.Center.Y - (float)(corners.BottomRight / 2.0)) - (float)((corners.BottomRight / 2.0) * Math.Sin(angleInRadians))));
                    }
                }
            }

            switch (point)
            {
            case CompassPoint.North:
                return(new Vector(X + Width / 2, Y));

            case CompassPoint.NorthNorthEast:
                return(new Vector(X + Width * 3 / 4, Y));

            case CompassPoint.NorthEast:
                if (isOctagonal)
                {
                    return(new Vector(X + Width * 7 / 8, Y + Height * 1 / 8));
                }
                if (isRounded)
                {
                    return(new Vector((float)(X + Width - 0.25 * corners.TopLeft), (float)(Y + 0.25 * corners.TopLeft)));
                }
                return(new Vector(X + Width, Y));

            case CompassPoint.EastNorthEast:
                return(new Vector(X + Width, Y + Height / 4));

            case CompassPoint.East:
                return(new Vector(X + Width, Y + Height / 2));

            case CompassPoint.EastSouthEast:
                return(new Vector(X + Width, Y + Height * 3 / 4));

            case CompassPoint.SouthEast:
                if (isOctagonal)
                {
                    return(new Vector(X + Width * 7 / 8, Y + Height * 7 / 8));
                }
                if (isRounded)
                {
                    return(new Vector((float)(X + Width - 0.25 * corners.TopLeft), (float)(Y + Height - 0.25 * corners.TopLeft)));
                }
                return(new Vector(X + Width, Y + Height));

            case CompassPoint.SouthSouthEast:
                return(new Vector(X + Width * 3 / 4, Y + Height));

            case CompassPoint.South:
                return(new Vector(X + Width / 2, Y + Height));

            case CompassPoint.SouthSouthWest:
                return(new Vector(X + Width / 4, Y + Height));

            case CompassPoint.SouthWest:
                if (isOctagonal)
                {
                    return(new Vector(X + Width * 1 / 8, Y + Height * 7 / 8));
                }
                if (isRounded)
                {
                    return(new Vector((float)(X + 0.3 * corners.TopLeft), (float)(Y + Height - 0.3 * corners.TopLeft)));
                }
                return(new Vector(X, Y + Height));

            case CompassPoint.WestSouthWest:
                return(new Vector(X, Y + Height * 3 / 4));

            case CompassPoint.West:
                return(new Vector(X, Y + Height / 2));

            case CompassPoint.WestNorthWest:
                return(new Vector(X, Y + Height / 4));

            case CompassPoint.NorthWest:
                if (isOctagonal)
                {
                    return(new Vector(X + Width * 1 / 8, Y + Height * 1 / 8));
                }
                if (isRounded)
                {
                    return(new Vector((float)(X + 0.3 * corners.TopLeft), (float)(Y + 0.3 * corners.TopLeft)));
                }
                return(new Vector(X, Y));

            case CompassPoint.NorthNorthWest:
                return(new Vector(X + Width / 4, Y));

            default:
                throw new InvalidOperationException();
            }
        }
예제 #11
0
        void IAutomapCanvas.Connect(Room source, AutomapDirection directionFromSource, Room target)
        {
            if (!Project.Current.Elements.Contains(source) || !Project.Current.Elements.Contains(target))
            {
                // avoid issues if the user has just deleted one of these rooms
                return;
            }

            // work out the correct compass point to use for the given direction

            // look for existing connections:
            // if the given direction is up/down/in/out, any existing connection will suffice;
            // otherwise, only match an existing connection if it's pretty close to the one we want.
            var          sourceCompassPoint = CompassPointHelper.GetCompassDirection(directionFromSource);
            CompassPoint?acceptableSourceCompassPoint;

            switch (directionFromSource)
            {
            case AutomapDirection.Up:
            case AutomapDirection.Down:
            case AutomapDirection.In:
            case AutomapDirection.Out:
                acceptableSourceCompassPoint = null;     // any existing connection will do
                break;

            default:
                acceptableSourceCompassPoint = sourceCompassPoint;
                break;
            }
            bool wrongWay;
            var  connection = FindConnection(source, target, acceptableSourceCompassPoint, out wrongWay);

            if (connection == null)
            {
                // there is no suitable connection between these rooms:
                var targetCompassPoint = CompassPointHelper.GetAutomapOpposite(sourceCompassPoint);

                // check whether we can move one of the rooms to make the connection tidier;
                // we won't need this very often, but it can be useful especially if the user teleports into a room
                // and then steps out into an existing one (this can appear to happen if the user moves into a
                // dark room, turns on the light, then leaves).
                TryMoveRoomsForTidyConnection(source, sourceCompassPoint, target, targetCompassPoint);

                // add a new connection
                connection       = addConnection(source, sourceCompassPoint, target, targetCompassPoint);
                connection.Style = ConnectionStyle.Solid;
                connection.Flow  = ConnectionFlow.OneWay;
            }
            else if (wrongWay)
            {
                // there is a suitable connection between these rooms, but it goes the wrong way;
                // make it bidirectional since we can now go both ways.
                connection.Flow = ConnectionFlow.TwoWay;
            }

            // if this is an up/down/in/out connection, mark it as such;
            // but don't override any existing text.
            switch (directionFromSource)
            {
            case AutomapDirection.Up:
            case AutomapDirection.Down:
            case AutomapDirection.In:
            case AutomapDirection.Out:
                if (string.IsNullOrEmpty(connection.StartText) && string.IsNullOrEmpty(connection.EndText))
                {
                    switch (directionFromSource)
                    {
                    case AutomapDirection.Up:
                        connection.SetText(wrongWay ? ConnectionLabel.Down : ConnectionLabel.Up);
                        break;

                    case AutomapDirection.Down:
                        connection.SetText(wrongWay ? ConnectionLabel.Up : ConnectionLabel.Down);
                        break;

                    case AutomapDirection.In:
                        connection.SetText(wrongWay ? ConnectionLabel.Out : ConnectionLabel.In);
                        break;

                    case AutomapDirection.Out:
                        connection.SetText(wrongWay ? ConnectionLabel.In : ConnectionLabel.Out);
                        break;
                    }
                }
                break;
            }
        }
예제 #12
0
 /// <summary>
 /// Approximately match two directions, allowing for aesthetic rearrangement by the user.
 /// </summary>
 /// <remarks>
 /// Two compass points match if they are on the same side of a box representing the room.
 /// </remarks>
 bool ApproximateDirectionMatch(CompassPoint one, CompassPoint two)
 {
     return(CompassPointHelper.GetAutomapDirectionVector(one) == CompassPointHelper.GetAutomapDirectionVector(two));
 }
예제 #13
0
파일: Rect.cs 프로젝트: taradinoc/trizbort
        public Vector GetCorner(CompassPoint point, bool ellipse = false, CornerRadii corners = null)
        {
            if (ellipse)
            {
                return(new Vector(Center.X + (float)((Width / 2.0) * Math.Cos(CompassPointHelper.GetAngleInRadians(point))), Center.Y + (float)((Height / 2.0) * Math.Sin(CompassPointHelper.GetAngleInRadians(point)))));
            }

            if (corners != null)
            {
                if (point != CompassPoint.East && point != CompassPoint.West && point != CompassPoint.North && point != CompassPoint.South)
                {
                    if (corners.TopRight > 10.0 && (point == CompassPoint.EastNorthEast || point == CompassPoint.NorthEast || point == CompassPoint.NorthNorthEast))
                    {
                        return(new Vector(Center.X + (float)((Width / 2.0) * Math.Cos(CompassPointHelper.GetAngleInRadians(point))), Center.Y + (float)((Height / 2.0) * Math.Sin(CompassPointHelper.GetAngleInRadians(point)))));
                    }

                    if (corners.TopLeft > 10.0 && (point == CompassPoint.WestNorthWest || point == CompassPoint.NorthWest || point == CompassPoint.NorthNorthWest))
                    {
                        return(new Vector(Center.X + (float)((Width / 2.0) * Math.Cos(CompassPointHelper.GetAngleInRadians(point))), Center.Y + (float)((Height / 2.0) * Math.Sin(CompassPointHelper.GetAngleInRadians(point)))));
                    }

                    if (corners.BottomLeft > 10.0 && (point == CompassPoint.WestSouthWest || point == CompassPoint.SouthWest || point == CompassPoint.SouthSouthWest))
                    {
                        return(new Vector(Center.X + (float)((Width / 2.0) * Math.Cos(CompassPointHelper.GetAngleInRadians(point))), Center.Y + (float)((Height / 2.0) * Math.Sin(CompassPointHelper.GetAngleInRadians(point)))));
                    }

                    if (corners.BottomRight > 10.0 && (point == CompassPoint.SouthSouthEast || point == CompassPoint.SouthEast || point == CompassPoint.EastSouthEast))
                    {
                        return(new Vector(Center.X + (float)((Width / 2.0) * Math.Cos(CompassPointHelper.GetAngleInRadians(point))), Center.Y + (float)((Height / 2.0) * Math.Sin(CompassPointHelper.GetAngleInRadians(point)))));
                    }
                }
            }

            switch (point)
            {
            case CompassPoint.North:
                return(new Vector(X + Width / 2, Y));

            case CompassPoint.NorthNorthEast:
                return(new Vector(X + Width * 3 / 4, Y));

            case CompassPoint.NorthEast:
                return(new Vector(X + Width, Y));

            case CompassPoint.EastNorthEast:
                return(new Vector(X + Width, Y + Height / 4));

            case CompassPoint.East:
                return(new Vector(X + Width, Y + Height / 2));

            case CompassPoint.EastSouthEast:
                return(new Vector(X + Width, Y + Height * 3 / 4));

            case CompassPoint.SouthEast:
                return(new Vector(X + Width, Y + Height));

            case CompassPoint.SouthSouthEast:
                return(new Vector(X + Width * 3 / 4, Y + Height));

            case CompassPoint.South:
                return(new Vector(X + Width / 2, Y + Height));

            case CompassPoint.SouthSouthWest:
                return(new Vector(X + Width / 4, Y + Height));

            case CompassPoint.SouthWest:
                return(new Vector(X, Y + Height));

            case CompassPoint.WestSouthWest:
                return(new Vector(X, Y + Height * 3 / 4));

            case CompassPoint.West:
                return(new Vector(X, Y + Height / 2));

            case CompassPoint.WestNorthWest:
                return(new Vector(X, Y + Height / 4));

            case CompassPoint.NorthWest:
                return(new Vector(X, Y));

            case CompassPoint.NorthNorthWest:
                return(new Vector(X + Width / 4, Y));

            default:
                throw new InvalidOperationException();
            }
        }