public void DrawComponentCurve(FlowWindow from, ref UnityEngine.UI.Windows.Plugins.Flow.FlowWindow.ComponentLink link, FlowWindow to)
        {
            if (from.IsEnabled() == false || to.IsEnabled() == false)
            {
                return;
            }

            var component = from.GetLayoutComponent(link.sourceComponentTag);

            if (component != null)
            {
                var rect = component.tempEditorRect;

                var start = new Rect(from.rect.x + rect.x, from.rect.y + rect.y, rect.width, rect.height);
                var end   = to.rect;

                var zOffset = -4f;

                var offset   = Vector2.zero;
                var startPos = new Vector3(start.center.x + offset.x, start.center.y + offset.y, zOffset);
                var endPos   = new Vector3(end.center.x + offset.x, end.center.y + offset.y, zOffset);

                var scale = FlowSystem.GetData().flowWindowWithLayoutScaleFactor;

                var side1        = from.rect.size.x * 0.5f;
                var side2        = from.rect.size.y * 0.5f;
                var stopDistance = Mathf.Sqrt(side1 * side1 + side2 * side2);

                var color = Color.white;
                if (from.GetContainer() != to.GetContainer())
                {
                    color = Color.gray;
                    if (to.GetContainer() != null)
                    {
                        color = to.GetContainer().randomColor;
                    }
                }
                var comment = this.DrawComponentCurve(startPos, endPos, color, stopDistance + 50f * scale, link.comment);
                if (link.comment != comment)
                {
                    link.comment = comment;
                    FlowSystem.SetDirty();
                }
            }
        }
        public void DrawNodeCurve(FlowWindow from, FlowWindow to, bool doubleSide)
        {
            if (from.IsEnabled() == false || to.IsEnabled() == false)
            {
                return;
            }

            var  fromRect    = from.rect;
            Rect centerStart = fromRect;

            var  toRect    = to.rect;
            Rect centerEnd = toRect;

            var fromComponent = false;
            var toComponent   = false;

            if (from.IsFunction() == true &&
                from.IsContainer() == false)
            {
                var func = FlowSystem.GetWindow(from.GetFunctionId());
                if (func != null)
                {
                    var selected   = FlowSystem.GetSelected();
                    var isSelected = selected.Contains(from.id) || (selected.Count == 0 && this.editor.focusedGUIWindow == from.id);
                    if (isSelected == true)
                    {
                        var color     = new Color(0f, 0f, 0f, 0.1f);
                        var backColor = new Color(0.5f, 0.5f, 0.5f, 0.1f);

                        this.DrawPolygon(new Vector3(from.rect.xMin, from.rect.yMin, 0f),
                                         new Vector3(func.rect.xMin, func.rect.yMin, 0f),
                                         new Vector3(func.rect.xMin, func.rect.yMax, 0f),
                                         new Vector3(from.rect.xMin, from.rect.yMax, 0f),
                                         backColor);

                        this.DrawPolygon(new Vector3(from.rect.xMin, from.rect.yMin, 0f),
                                         new Vector3(func.rect.xMin, func.rect.yMin, 0f),
                                         new Vector3(func.rect.xMax, func.rect.yMin, 0f),
                                         new Vector3(from.rect.xMax, from.rect.yMin, 0f),
                                         backColor);

                        this.DrawPolygon(new Vector3(from.rect.xMax, from.rect.yMin, 0f),
                                         new Vector3(func.rect.xMax, func.rect.yMin, 0f),
                                         new Vector3(func.rect.xMax, func.rect.yMax, 0f),
                                         new Vector3(from.rect.xMax, from.rect.yMax, 0f),
                                         backColor);

                        this.DrawPolygon(new Vector3(from.rect.xMax, from.rect.yMax, 0f),
                                         new Vector3(func.rect.xMax, func.rect.yMax, 0f),
                                         new Vector3(func.rect.xMin, func.rect.yMax, 0f),
                                         new Vector3(from.rect.xMin, from.rect.yMax, 0f),
                                         backColor);

                        this.DrawNodeCurveDotted(new Vector3(from.rect.xMin, from.rect.yMin, 0f),
                                                 new Vector3(func.rect.xMin, func.rect.yMin, 0f),
                                                 color
                                                 );

                        this.DrawNodeCurveDotted(new Vector3(from.rect.xMin, from.rect.yMax, 0f),
                                                 new Vector3(func.rect.xMin, func.rect.yMax, 0f),
                                                 color
                                                 );

                        this.DrawNodeCurveDotted(new Vector3(from.rect.xMax, from.rect.yMin, 0f),
                                                 new Vector3(func.rect.xMax, func.rect.yMin, 0f),
                                                 color
                                                 );

                        this.DrawNodeCurveDotted(new Vector3(from.rect.xMax, from.rect.yMax, 0f),
                                                 new Vector3(func.rect.xMax, func.rect.yMax, 0f),
                                                 color
                                                 );
                    }
                }
            }

            if (FlowSystem.GetData().flowWindowWithLayout == true)
            {
                var comps = from.attachedComponents.Where((c) => c.targetWindowId == to.id && c.sourceComponentTag != LayoutTag.None);
                foreach (var comp in comps)
                {
                    var component = from.GetLayoutComponent(comp.sourceComponentTag);
                    if (component != null)
                    {
                        fromRect = centerStart;

                        var rect = component.tempEditorRect;
                        fromRect = new Rect(fromRect.x + rect.x, fromRect.y + rect.y, rect.width, rect.height);

                        this.DrawNodeCurve(from.GetContainer(), to.GetContainer(), centerStart, centerEnd, fromRect, toRect, doubleSide, 0f);

                        fromComponent = true;
                    }
                }

                if (doubleSide == true)
                {
                    comps = to.attachedComponents.Where((c) => c.targetWindowId == from.id && c.sourceComponentTag != LayoutTag.None);
                    foreach (var comp in comps)
                    {
                        var component = to.GetLayoutComponent(comp.sourceComponentTag);
                        if (component != null)
                        {
                            toRect = centerEnd;

                            var rect = component.tempEditorRect;
                            toRect = new Rect(toRect.x + rect.x, toRect.y + rect.y, rect.width, rect.height);

                            this.DrawNodeCurve(from.GetContainer(), to.GetContainer(), centerStart, centerEnd, fromRect, toRect, doubleSide, 0f);

                            toComponent = true;
                        }
                    }
                }
            }

            if (fromComponent == false && toComponent == false)
            {
                this.DrawNodeCurve(from.GetContainer(), to.GetContainer(), centerStart, centerEnd, fromRect, toRect, doubleSide);
            }
        }