Exemple #1
0
        /// <summary>
        /// Removes the given dummy
        /// </summary>
        /// <param name="data">Data to remove</param>
        public static void Remove(DummyData <TSegmentType, TConnData> data)
        {
            // remove any connections using this dummy.
            for (var i = 0; i < data.Segment._connections.Count; i++)
            {
                var c = data.Segment._connections[i];
                DummyData <TSegmentType, TConnData> partner = null;
                if (c.From == data)
                {
                    partner = c.To;
                }
                else if (c.To == data)
                {
                    partner = c.From;
                }
                else
                {
                    continue;
                }
                data.Segment._connections.RemoveAtFast(i);
                i--;
                if (partner.Segment == data.Segment)
                {
                    continue;
                }
                var o = partner.Segment._connections;
                for (var j = 0; j < o.Count; j++)
                {
                    var cc = o[j];
                    if (cc.From == data || cc.To == data)
                    {
                        o.RemoveAtFast(j);
                        j--;
                    }
                }
            }

            var idx = data.Segment._path.IndexOf(data);

            if (idx != 0 && idx != data.Segment._path.Count - 1)
            {
                data.Segment.BreakAfter(idx);
            }
            data.Segment._path.Remove(data);
            data.Segment.PathUpdated?.Invoke();
            data.Segment = null;
        }
Exemple #2
0
        private void Split(DummyData <TSegmentType, TConnData> at)
        {
            var idx = _path.IndexOf(at);

            if (idx == -1)
            {
                throw new Exception(
                          $"Couldn't find {at.Dummy} in {GetHashCode():X8}: {string.Join(", ", _path.Select(x => x.Dummy))}");
            }

            var from = _path[idx - 1];
            var to   = _path[idx];

            var ns = _network.AllocateSegment();

            for (var i = idx; i < _path.Count; i++)
            {
                ns._path.Add(_path[i]);
                _path[i].Segment = ns;
                for (var j = 0; j < _connections.Count; j++)
                {
                    if (_connections[j].From == _path[i] || _connections[j].To == _path[i])
                    {
                        ns._connections.Add(_connections[j]);
                        _connections.RemoveAtFast(j);
                        j--;
                    }
                }
            }

            _path.RemoveRange(idx, _path.Count - idx);

            var conn = new Connection <TSegmentType, TConnData>(from, to, _network.DissolveableConnectionData);

            _connections.Add(conn);
            ns._connections.Add(conn);

            PathUpdated?.Invoke();
            ns.PathUpdated?.Invoke();
        }
Exemple #3
0
 public Connection(DummyData <TSegmentType, TConnData> from, DummyData <TSegmentType, TConnData> to, TConnData data)
 {
     Data = data;
     From = from;
     To   = to;
 }
Exemple #4
0
        public static void MakeLink(DummyData <TSegmentType, TConnData> from, DummyData <TSegmentType, TConnData> to,
                                    TConnData data)
        {
            {
                if (!from.Endpoint)
                {
                    from.Segment.Split(from);
                }

                if (!to.Endpoint)
                {
                    to.Segment.Split(to);
                }
            }

            if (data.CanDissolve && !from.Segment.AnyConnections(from) && !to.Segment.AnyConnections(to) &&
                from.Segment != to.Segment)
            {
                // attach via path injection
                var moveFromNode = from.Segment.Path.Count < to.Segment.Path.Count;

                var nodeToMove      = moveFromNode ? from : to;
                var nodeToPreserve  = moveFromNode ? to : from;
                var segmentToRemove = nodeToMove.Segment;
                var segmentToGrow   = nodeToPreserve.Segment;

                // Update paths
                {
                    var removeReversed = segmentToRemove._path.Last() == nodeToMove;
                    var modifyReversed = segmentToGrow._path.First() == nodeToPreserve;

                    var modCount = segmentToRemove._path.Count;
                    int modOffset;
                    if (modifyReversed)
                    {
                        modOffset = 0;
                        segmentToGrow._path.InsertRange(0, segmentToRemove._path);
                    }
                    else
                    {
                        modOffset = segmentToGrow._path.Count;
                        segmentToGrow._path.AddRange(segmentToRemove._path);
                    }

                    foreach (var n in segmentToRemove._path)
                    {
                        n.Segment = segmentToGrow;
                    }

                    if (modifyReversed != removeReversed)
                    {
                        // reverse injected items
                        for (var i = 0; i < (modCount >> 1) + (modCount & 1); i++)
                        {
                            var ii  = modOffset + i;
                            var oi  = modOffset + modCount - i - 1;
                            var tmp = segmentToGrow._path[oi];
                            segmentToGrow._path[oi] = segmentToGrow._path[ii];
                            segmentToGrow._path[ii] = tmp;
                        }
                    }

                    segmentToRemove._path.Clear();
                }
                // Update connections
                {
                    foreach (var conn in segmentToRemove._connections)
                    {
                        segmentToGrow._connections.Add(conn);
                    }
                    segmentToRemove._connections.Clear();
                }
                segmentToRemove._network.Segments.Remove(segmentToRemove);

                segmentToGrow.PathUpdated?.Invoke();
            }
            else
            {
                var conn = new Connection <TSegmentType, TConnData>(from, to, data);

                from.Segment._connections.Add(conn);
                if (to.Segment != from.Segment)
                {
                    to.Segment._connections.Add(conn);
                }
            }
        }
Exemple #5
0
 public void BreakLink(DummyData <TSegmentType, TConnData> from, DummyData <TSegmentType, TConnData> to)
 {
     Segment <TSegmentType, TConnData> .BreakLink(from, to);
 }
Exemple #6
0
 public void MakeLink(DummyData <TSegmentType, TConnData> from, DummyData <TSegmentType, TConnData> to,
                      TConnData data)
 {
     Segment <TSegmentType, TConnData> .MakeLink(from, to, data);
 }