public static bool RecurseWindowlessControls(IWindowlessControl control, WindowlessControlRecursionHandler pre, WindowlessControlRecursionHandler post)
        {
            if (pre != null)
            {
                if (!pre(control))
                {
                    return(false);
                }
            }

            if (control.Controls != null)
            {
                foreach (IWindowlessControl child in control.Controls)
                {
                    if (!RecurseWindowlessControls(child, pre, post))
                    {
                        return(false);
                    }
                }
            }

            if (post != null)
            {
                if (!post(control))
                {
                    return(false);
                }
            }

            return(true);
        }
Пример #2
0
        public void Connect(IWindowlessControl control)
        {
            Type type = GetType();

            WindowlessControlHost.RecurseWindowlessControls(control, (current) =>
            {
                if (string.IsNullOrEmpty(current.Name))
                {
                    return(true);
                }

                PropertyInfo prop = type.GetProperty(current.Name, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);
                if (prop != null)
                {
                    if (prop.GetValue(this, null) != null)
                    {
                        throw new InvalidOperationException(string.Format("Unable to connect to property {0}. The value is non-null", current.Name));
                    }
                    prop.SetValue(this, current, null);
                    return(true);
                }

                FieldInfo field = type.GetField(current.Name, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);
                if (field != null)
                {
                    if (field.GetValue(this) != null)
                    {
                        throw new InvalidOperationException(string.Format("Unable to connect to field {0}. The value is non-null", current.Name));
                    }
                    field.SetValue(this, current);
                }
                return(true);
            },
                                                            null);
        }
Пример #3
0
        protected void LayoutControl(IWindowlessControl control, Rectangle rect)
        {
            switch (control.HorizontalAlignment)
            {
            case HorizontalAlignment.Stretch:
            case HorizontalAlignment.Left:
                control.Left = rect.Left;
                break;

            case HorizontalAlignment.Center:
                control.Left = (rect.Left + rect.Right - control.Width) / 2;
                break;

            case HorizontalAlignment.Right:
                control.Left = rect.Right - control.Width;
                break;
            }
            switch (control.VerticalAlignment)
            {
            case VerticalAlignment.Stretch:
            case VerticalAlignment.Top:
                control.Top = rect.Top;
                break;

            case VerticalAlignment.Center:
                control.Top = (rect.Top + rect.Bottom - control.Height) / 2;
                break;

            case VerticalAlignment.Bottom:
                control.Top = rect.Bottom - control.Height;
                break;
            }
        }
        public void Connect(IWindowlessControl control)
        {
            Type type = GetType();
            WindowlessControlHost.RecurseWindowlessControls(control, (current) =>
            {
                if (string.IsNullOrEmpty(current.Name))
                    return true;

                PropertyInfo prop = type.GetProperty(current.Name, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);
                if (prop != null)
                {
                    if (prop.GetValue(this, null) != null)
                        throw new InvalidOperationException(string.Format("Unable to connect to property {0}. The value is non-null", current.Name));
                    prop.SetValue(this, current, null);
                    return true;
                }

                FieldInfo field = type.GetField(current.Name, BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);
                if (field != null)
                {
                    if (field.GetValue(this) != null)
                        throw new InvalidOperationException(string.Format("Unable to connect to field {0}. The value is non-null", current.Name));
                    field.SetValue(this, current);
                }
                return true;
            },
                null);
        }
Пример #5
0
 public RelativeLayout(IWindowlessControl relative, float x, float y, float width, float height)
 {
     myWidth    = width;
     myHeight   = height;
     myX        = x;
     myY        = y;
     myRelative = relative;
 }
Пример #6
0
 public RelativeLayout(IWindowlessControl relative, float x, float y, float width, float height)
 {
     myWidth = width;
     myHeight = height;
     myX = x;
     myY = y;
     myRelative = relative;
 }
 public static WindowlessControlHost GetHost(IWindowlessControl control)
 {
     control = control.Parent;
     while (control != null && !(control is WindowlessControlHost))
     {
         control = control.Parent;
     }
     return(control as WindowlessControlHost);
 }
Пример #8
0
        protected override void OnWindowlessMouseDown(WindowlessControlHost sender, WindowlessMouseEventArgs e)
        {
            base.OnWindowlessMouseDown(sender, e);
            IWindowlessControl control = FindControlAtPoint(new Point(e.X, e.Y));

            if (control == null && control != myCurrentSelection)
            {
                return;
            }
            e.Handled = true;
            ChangeSelection(control as IInteractiveContentPresenter);
            OnClickDown();
        }
Пример #9
0
        protected override void OnWindowlessMouseFocus(WindowlessControlHost sender, MouseEventArgs e)
        {
            base.OnWindowlessMouseFocus(sender, e);
            if (sender != this)
            {
                return;
            }
            IWindowlessControl control = FindControlAtPoint(new Point(e.X, e.Y));

            if (control == null && control != myCurrentSelection)
            {
                return;
            }
            ChangeSelection(control as IInteractiveContentPresenter);
        }
Пример #10
0
        void HorizontalLayoutControls(int top, int maxWidth, int maxHeight, int start, int end)
        {
            int offset = 0;

            for (int i = start; i < end; i++)
            {
                IWindowlessControl control = Controls[i];
                if (!control.Visible)
                {
                    continue;
                }
                int controlWidth = WrapStyle == WrapStyle.Greedy ? control.Width : maxWidth;
                LayoutControl(control, new Rectangle(Margin.Left + offset, top, controlWidth, maxHeight));
                offset += controlWidth;
            }
        }
Пример #11
0
        public static void WindowlessInvalidate(IWindowlessControl sender)
        {
            Point origin = Point.Empty;
            IWindowlessControl parent = sender;

            while (!(parent is WindowlessControlHost) && parent != null)
            {
                origin.X += parent.Left;
                origin.Y += parent.Top;
                parent    = parent.Parent;
            }
            WindowlessControlHost host = parent as WindowlessControlHost;

            if (host != null)
            {
                host.WindowlessInvalidate(new Rectangle(origin.X, origin.Y, sender.Width, sender.Height));
            }
        }
        public static Point WindowlessPointToHost(IWindowlessControl control, Point point)
        {
            Point ret = point;

            if (control.Parent == null)
            {
                return(point);
            }
            IWindowlessControl host = WindowlessControlHost.GetHost(control);

            while (control != host)
            {
                ret.X  += control.Left;
                ret.Y  += control.Top;
                control = control.Parent;
            }
            return(ret);
        }
Пример #13
0
        IWindowlessControl Load(Stream stream)
        {
            List <Type> additionalControls = new List <Type>();

            AddAssemblyControlsToList(Assembly.GetExecutingAssembly(), additionalControls);

            XmlAttributeOverrides overrides     = new XmlAttributeOverrides();
            XmlAttributes         xmlArrayItems = new XmlAttributes();

            xmlArrayItems.XmlArray = new XmlArrayAttribute("Controls");
            overrides.Add(typeof(WindowlessControlHost), "SerializableControls", xmlArrayItems);
            overrides.Add(typeof(WindowlessControl), "Controls", xmlArrayItems);

            XmlIgnoreAttributeOverrides(overrides, typeof(WindowlessControlHost).BaseType);

            List <Type> additionalTypes = new List <Type>();

            additionalTypes.Add(typeof(SmartColor));

            OnCreateXmlSerializer(overrides, additionalTypes, additionalControls);
            foreach (Type type in additionalControls)
            {
                xmlArrayItems.XmlArrayItems.Add(new XmlArrayItemAttribute(type));
            }

            XmlSerializer ser = new XmlSerializer(typeof(WindowlessControlHost), overrides, additionalTypes.ToArray(), null, null);

            //{
            //    WindowlessControlHost test = new WindowlessControlHost();
            //    test.Orientation = WindowlessControls.Orientation.Vertical;
            //    test.Control = new StackPanel();
            //    test.Control.Controls.Add(new WindowlessLabel("hello world"));

            //    MemoryStream mem = new MemoryStream();
            //    ser.Serialize(mem, test);
            //    mem.Seek(0, SeekOrigin.Begin);
            //    string text = new StreamReader(mem).ReadToEnd();
            //}

            IWindowlessControl ret = ser.Deserialize(stream) as IWindowlessControl;

            Connect(ret);
            return(ret);
        }
Пример #14
0
        public static void WindowlessBringIntoView(IWindowlessControl control)
        {
            WindowlessControlHost host = GetHost(control);

            host.SyncWindows();
            Point     p    = WindowlessPointToHost(control, Point.Empty);
            Rectangle rect = new Rectangle(p.X, p.Y, control.Width, control.Height);

            while (host != null)
            {
                if (host.AutoScroll)
                {
                    Point newScroll = host.AutoScrollPosition;
                    // we favor top and left over bottom and right
                    if (rect.Top < 0)
                    {
                        newScroll.Y -= rect.Top;
                    }
                    else if (rect.Bottom > host.Height && rect.Height <= host.Height)
                    {
                        newScroll.Y += (host.Height - rect.Bottom);
                    }
                    if (rect.Left < 0)
                    {
                        newScroll.X -= rect.Left;
                    }
                    else if (rect.Right > host.Width && rect.Width <= host.Width)
                    {
                        newScroll.Y += (host.Width - rect.Right);
                    }
                    // for some reason you need to pass in positive values to autoscroll, and it converts them to negative values...
                    if (newScroll != host.AutoScrollPosition)
                    {
                        host.AutoScrollPosition = new Point(Math.Abs(newScroll.X), Math.Abs(newScroll.Y));
                        host.SyncWindows();
                    }
                }

                rect.X += host.Left;
                rect.Y += host.Top;
                host    = host.Parent as WindowlessControlHost;
            }
        }
Пример #15
0
        public DropdownControl(WindowlessControlHost dropdownSource, IWindowlessControl dropdownContent)
        {
            AutoScroll = true;
            Orientation = Orientation.Vertical;
            myDropdownSource = dropdownSource;

            OverlayPanel overlay = new OverlayPanel();
            WindowlessRectangle rectangle = new WindowlessRectangle();
            rectangle.Color = SystemColors.ControlDarkDark;
            rectangle.Filled = false;
            overlay.Controls.Add(rectangle);

            OverlayPanel inner = new OverlayPanel();
            inner.Margin = new Thickness(1, 1, 1, 1);
            inner.Controls.Add(dropdownContent);
            overlay.Controls.Add(inner);
            overlay.FitHeightControl = overlay.FitWidthControl = inner;
            Control = overlay;
        }
        public static void WindowlessBringIntoView(IWindowlessControl control)
        {
            WindowlessControlHost host = GetHost(control);
            host.SyncWindows();
            Point p = WindowlessPointToHost(control, Point.Empty);
            Rectangle rect = new Rectangle(p.X, p.Y, control.Width, control.Height);
            while (host != null)
            {
                if (host.AutoScroll)
                {
                    Point newScroll = host.AutoScrollPosition;
                    // we favor top and left over bottom and right
                    if (rect.Top < 0)
                    {
                        newScroll.Y -= rect.Top;
                    }
                    else if (rect.Bottom > host.Height && rect.Height <= host.Height)
                    {
                        newScroll.Y += (host.Height - rect.Bottom);
                    }
                    if (rect.Left < 0)
                    {
                        newScroll.X -= rect.Left;
                    }
                    else if (rect.Right > host.Width && rect.Width <= host.Width)
                    {
                        newScroll.Y += (host.Width - rect.Right);
                    }
                    // for some reason you need to pass in positive values to autoscroll, and it converts them to negative values...
                    if (newScroll != host.AutoScrollPosition)
                    {
                        host.AutoScrollPosition = new Point(Math.Abs(newScroll.X), Math.Abs(newScroll.Y));
                        host.SyncWindows();
                    }
                }

                rect.X += host.Left;
                rect.Y += host.Top;
                host = host.Parent as WindowlessControlHost;
            }
        }
Пример #17
0
        public DropdownControl(WindowlessControlHost dropdownSource, IWindowlessControl dropdownContent)
        {
            AutoScroll       = true;
            Orientation      = Orientation.Vertical;
            myDropdownSource = dropdownSource;

            OverlayPanel        overlay   = new OverlayPanel();
            WindowlessRectangle rectangle = new WindowlessRectangle();

            rectangle.Color  = SystemColors.ControlDarkDark;
            rectangle.Filled = false;
            overlay.Controls.Add(rectangle);

            OverlayPanel inner = new OverlayPanel();

            inner.Margin = new Thickness(1, 1, 1, 1);
            inner.Controls.Add(dropdownContent);
            overlay.Controls.Add(inner);
            overlay.FitHeightControl = overlay.FitWidthControl = inner;
            Control = overlay;
        }
Пример #18
0
        int FindOrInsertAncestor(IWindowlessControl control, List <IWindowlessControl> hierarchySorted)
        {
            int index = hierarchySorted.IndexOf(control);

            if (index != -1)
            {
                return(index);
            }

            RelativeLayout layout = control.Layout as RelativeLayout;

            // if this is a root, just insert it at the head and go
            if (layout.Relative == null)
            {
                hierarchySorted.Insert(0, control);
                return(0);
            }

            index = FindOrInsertAncestor(layout.Relative, hierarchySorted) + 1;
            hierarchySorted.Insert(index, control);
            return(index);
        }
Пример #19
0
        protected override void OnWindowlessKeyDown(Control sender, System.Windows.Forms.KeyEventArgs e)
        {
            if (e.Handled)
            {
                return;
            }
            switch (e.KeyCode)
            {
            case Keys.Enter:
                OnClickDown();
                break;

            case Keys.F19:
            case Keys.F20:
            {
                int  firstIndex = -1;
                int  prevIndex  = -1;
                int  nextIndex  = -1;
                int  lastIndex  = -1;
                bool found      = false;
                for (int i = 0; i < Control.Controls.Count; i++)
                {
                    IWindowlessControl current = Control.Controls[i];
                    if (current == myCurrentSelection)
                    {
                        found = true;
                        continue;
                    }

                    if (!current.Visible)
                    {
                        continue;
                    }

                    if (firstIndex != -1)
                    {
                        firstIndex = i;
                    }

                    if (!found)
                    {
                        prevIndex = i;
                    }
                    if (found && nextIndex == -1)
                    {
                        nextIndex = i;
                    }
                    lastIndex = i;
                }

                int newIndex = -1;
                if (e.KeyCode == Keys.F19)
                {
                    newIndex = prevIndex;
                }
                else
                {
                    newIndex = nextIndex;
                }

                if (newIndex >= 0 && newIndex < Items.Count && newIndex != SelectedIndex)
                {
                    e.Handled     = true;
                    SelectedIndex = newIndex;
                }
            }
            break;

            case Keys.Up:
            case Keys.Down:
            case Keys.Right:
            case Keys.Left:
                if (CurrentSelection != null)
                {
                    IWindowlessControl control = Control.Controls[Items.IndexOf(CurrentSelection)];
                    Rectangle          rect    = new Rectangle(control.Left, control.Top, control.Width, control.Height);
                    e.Handled = NavigateSelection(rect, e.KeyCode);
                }
                else if (Items.Count != 0)
                {
                    SelectedIndex = 0;
                }
                break;
            }
            base.OnWindowlessKeyDown(sender, e);
        }
Пример #20
0
        void WindowlessPaintHost(IWindowlessControl control, Graphics graphics, Point origin, Rectangle destRect)
        {
            if (!control.Visible)
            {
                return;
            }
            // paint everything in a clip rectangle belonging to a host tree

            IWindowlessPaintControl paintControl = control as IWindowlessPaintControl;

            if (paintControl != null)
            {
                if (paintControl.PaintSelf)
                {
                    WindowlessPaintEventArgs we = myPaintEventArgs;
                    we.Graphics      = graphics;
                    we.ClipRectangle = destRect;
                    we.Origin        = origin;
                    Rectangle clip = we.ClipRectangle;
                    clip.X += we.Origin.X;
                    clip.Y += we.Origin.Y;

                    if (paintControl.ClipToBounds)
                    {
                        myDummyRegion.MakeEmpty();
                        myDummyRegion.Union(clip);
                        myDummyRegion.Intersect(graphics.Clip);
                    }
                    else
                    {
                        myDummyRegion.MakeInfinite();
                    }
                    Region oldClip = we.Graphics.Clip;
                    we.Graphics.Clip = myDummyRegion;

                    paintControl.OnWindowlessPaint(we);

                    we.Graphics.Clip = oldClip;
                }
                if (!paintControl.PaintChildren)
                {
                    return;
                }
            }

            if (control.Controls == null)
            {
                return;
            }
            foreach (IWindowlessControl child in control.Controls)
            {
                if (child is WindowlessControlHost)
                {
                    continue;
                }
                Point     childOrigin = new Point(origin.X + child.Left, origin.Y + child.Top);
                Rectangle childRect   = new Rectangle(child.Left, child.Top, child.Width, child.Height);
                Rectangle clipRect    = childRect;
                clipRect.Location = childOrigin;
                if (!graphics.Clip.IsVisible(clipRect))
                {
                    continue;
                }
                childRect.Intersect(destRect);
                if (childRect.Width <= 0 || childRect.Height <= 0)
                {
                    continue;
                }
                childRect.X -= child.Left;
                childRect.Y -= child.Top;
                WindowlessPaintHost(child, graphics, childOrigin, childRect);
            }
        }
Пример #21
0
        public override bool MeasureUnpadded(Size bounds, bool boundsChange)
        {
            // todo: this method is f****n huge.
            // can refactor by using reflection so the width/height crap can be done in a single spot.
            if (!(bounds.Width != Int32.MaxValue ^ bounds.Height != Int32.MaxValue))
            {
                throw new Exception("WrapPanel needs to have one infinite dimension.");
            }

            bool layoutChange = false;
            int  maxWidth     = 0;
            int  maxHeight    = 0;

            foreach (IWindowlessControl control in Controls)
            {
                if (!control.Visible)
                {
                    continue;
                }
                Rectangle oldRect = new Rectangle(control.Left, control.Top, control.Width, control.Height);
                if (control.NeedsMeasure || boundsChange)
                {
                    control.Measure(bounds);
                }
                maxWidth  = Math.Max(maxWidth, control.Width);
                maxHeight = Math.Max(maxHeight, control.Height);

                layoutChange |= oldRect != new Rectangle(control.Left, control.Top, control.Width, control.Height);
            }

            int newWidth  = 0;
            int newHeight = 0;

            if (bounds.Width == Int32.MaxValue)
            {
                // vertical wrapping
                int left           = 0;
                int top            = 0;
                int maxColumnWidth = 0;

                //if (WrapStyle == WrapStyle.UniformGrid)
                //{
                //    maxHeight = bounds.Height / (bounds.Height / maxHeight);
                //}

                foreach (IWindowlessControl control in Controls)
                {
                    if (!control.Visible)
                    {
                        continue;
                    }
                    int controlHeight = WrapStyle == WrapStyle.Greedy ? control.Height : maxHeight;

                    // start a new column if necessary
                    if (controlHeight + top > bounds.Height)
                    {
                        top            = 0;
                        left          += WrapStyle == WrapStyle.UniformGrid ? maxWidth : maxColumnWidth;
                        maxColumnWidth = 0;
                        newHeight      = Math.Max(newHeight, top);
                    }

                    control.Top  = top + Margin.Top;
                    control.Left = left + Margin.Left;
                    top         += controlHeight;

                    maxColumnWidth = Math.Max(maxColumnWidth, control.Width);
                }

                newWidth  = left + maxColumnWidth;
                newHeight = Math.Max(newHeight, top);
            }
            else
            {
                // horizontal wrapping
                int left         = 0;
                int top          = 0;
                int maxRowHeight = 0;

                if (WrapStyle == WrapStyle.UniformGrid && HorizontalAlignment == HorizontalAlignment.Stretch)
                {
                    maxWidth = bounds.Width / (bounds.Width / maxWidth);
                }

                //foreach (IWindowlessControl control in Controls)
                int start = 0;
                int end   = 0;
                for (int i = 0; i < Controls.Count; i++)
                {
                    IWindowlessControl control = Controls[i];
                    if (!control.Visible)
                    {
                        continue;
                    }
                    int controlWidth = WrapStyle == WrapStyle.Greedy ? control.Width : maxWidth;

                    // start a new column if necessary
                    if (controlWidth + left > bounds.Width)
                    {
                        HorizontalLayoutControls(top + Margin.Top, maxWidth, WrapStyle == WrapStyle.Greedy ? maxHeight : maxRowHeight, start, end);
                        start        = end;
                        end          = i;
                        newWidth     = Math.Max(newWidth, left);
                        left         = 0;
                        top         += WrapStyle == WrapStyle.UniformGrid ? maxHeight : maxRowHeight;
                        maxRowHeight = 0;
                    }
                    end++;

                    //control.Top = top + Margin.Top;
                    //control.Left = left + Margin.Left;
                    left += controlWidth;

                    maxRowHeight = Math.Max(maxRowHeight, control.Height);
                }
                if (end <= Controls.Count)
                {
                    HorizontalLayoutControls(top + Margin.Top, maxWidth, WrapStyle == WrapStyle.Greedy ? maxHeight : maxRowHeight, start, Controls.Count);
                }

                newHeight = top + maxRowHeight;
                newWidth  = Math.Max(newWidth, left);
            }

            if (HorizontalAlignment == HorizontalAlignment.Stretch && bounds.Width != Int32.MaxValue)
            {
                ClientWidth = bounds.Width;
            }
            else
            {
                ClientWidth = newWidth;
            }
            if (VerticalAlignment == VerticalAlignment.Stretch && bounds.Height != Int32.MaxValue)
            {
                ClientHeight = bounds.Height;
            }
            else
            {
                ClientHeight = newHeight;
            }

            return(layoutChange);
        }
        void SyncWindows()
        {
            if (Control != null)
            {
                if (AutoScrollPosition.Y != Control.Top || AutoScrollPosition.X != Control.Left)
                {
                    Control.Left = AutoScrollPosition.X;
                    Control.Top  = AutoScrollPosition.Y;
                    WindowlessInvalidate();
                }
            }

            foreach (Control control in Controls)
            {
                IWindowlessControl wc = control as IWindowlessControl;
                if (wc == null)
                {
                    continue;
                }
                Point p = WindowlessControlHost.WindowlessPointToHost(wc, Point.Empty);
                if (control.Left != p.X)
                {
                    control.Left = p.X;
                }
                if (control.Top != p.Y)
                {
                    control.Top = p.Y;
                }
            }

            if (myAutoScroll)
            {
                if (Control.Width <= ClientSize.Width && Control.Height <= ClientSize.Height)
                {
                    if (base.AutoScroll)
                    {
                        base.AutoScroll = false;
                    }
                }
                else
                {
                    if (!base.AutoScroll)
                    {
                        base.AutoScroll = true;
                    }
                }
            }

            // note: this code causes infinite loop
            // note: this code no longer seems necessary, no wierd scrollbars as of late...
            // see if we got scroll bars
            // fix a bug with windows being horrible at making scrollbars disappear.
            //if (AutoScroll)
            //{
            //    SuspendRemeasure();
            //    foreach (Control control in Controls)
            //    {
            //        if (control.Bottom > ClientSize.Height || control.Right > ClientSize.Width || control.Left < 0 || control.Top < 0 && control.Visible)
            //        {
            //            control.Visible = false;
            //            control.Visible = true;
            //            break;
            //        }
            //    }
            //    ResumeRemeasure();
            //}
        }
        void WindowlessPaintHost(IWindowlessControl control, Graphics graphics, Point origin, Rectangle destRect)
        {
            if (!control.Visible)
                return;
            // paint everything in a clip rectangle belonging to a host tree

            IWindowlessPaintControl paintControl = control as IWindowlessPaintControl;
            if (paintControl != null)
            {
                if (paintControl.PaintSelf)
                {
                    WindowlessPaintEventArgs we = myPaintEventArgs;
                    we.Graphics = graphics;
                    we.ClipRectangle = destRect;
                    we.Origin = origin;
                    Rectangle clip = we.ClipRectangle;
                    clip.X += we.Origin.X;
                    clip.Y += we.Origin.Y;

                    if (paintControl.ClipToBounds)
                    {
                        myDummyRegion.MakeEmpty();
                        myDummyRegion.Union(clip);
                        myDummyRegion.Intersect(graphics.Clip);
                    }
                    else
                    {
                        myDummyRegion.MakeInfinite();
                    }
                    Region oldClip = we.Graphics.Clip;
                    we.Graphics.Clip = myDummyRegion;

                    paintControl.OnWindowlessPaint(we);

                    we.Graphics.Clip = oldClip;
                }
                if (!paintControl.PaintChildren)
                    return;
            }

            if (control.Controls == null)
                return;
            foreach (IWindowlessControl child in control.Controls)
            {
                if (child is WindowlessControlHost)
                    continue;
                Point childOrigin = new Point(origin.X + child.Left, origin.Y + child.Top);
                Rectangle childRect = new Rectangle(child.Left, child.Top, child.Width, child.Height);
                Rectangle clipRect = childRect;
                clipRect.Location = childOrigin;
                if (!graphics.Clip.IsVisible(clipRect))
                    continue;
                childRect.Intersect(destRect);
                if (childRect.Width <= 0 || childRect.Height <= 0)
                    continue;
                childRect.X -= child.Left;
                childRect.Y -= child.Top;
                WindowlessPaintHost(child, graphics, childOrigin, childRect);
            }
        }
Пример #24
0
        static Control GetBestNavigationHost(Rectangle rect, Keys key, Control parent, Control exclude, out ulong bestScore)
        {
            // we are in this function because the parent control does not want focus
            bestScore = ulong.MaxValue;

            if (parent.Controls == null || parent == exclude)
            {
                return(null);
            }

            Control best = null;

            foreach (Control control in parent.Controls)
            {
                // don't try to refocus onto something within self
                IWindowlessControl host = control as IWindowlessControl;
                bool visible            = host != null ? host.Visible : control.Visible;
                if (control == exclude || !visible)
                {
                    continue;
                }

                if (IsFocusable(control))
                {
                    long distance;
                    bool positiveDirection = false;

                    if (key == Keys.Up)
                    {
                        distance = GetEdgeDistance(control.Bottom, control.Left, control.Width, rect.Top, rect.Left, rect.Width, positiveDirection);
                    }
                    else if (key == Keys.Down)
                    {
                        positiveDirection = true;
                        distance          = GetEdgeDistance(control.Top, control.Left, control.Width, rect.Bottom, rect.Left, rect.Width, positiveDirection);
                    }
                    else if (key == Keys.Left)
                    {
                        distance = GetEdgeDistance(control.Right, control.Top, control.Height, rect.Left, rect.Top, rect.Height, positiveDirection);
                    }
                    else
                    {
                        positiveDirection = true;
                        distance          = GetEdgeDistance(control.Left, control.Top, control.Height, rect.Right, rect.Top, rect.Height, positiveDirection);
                    }

                    ulong score = ScoreDistance(distance, positiveDirection);

                    if (score < bestScore)
                    {
                        bestScore = score;
                        best      = control;
                    }
                }

                Rectangle childRect = rect;
                childRect.X -= control.Left;
                childRect.Y -= control.Top;

                // if the control is scrollable, the rect needs to be put into the space of the autoscroll's topleft,
                // not just the client topleft.
                ScrollableControl scrollControl = control as ScrollableControl;
                if (scrollControl != null && control != exclude.Parent)
                {
                    childRect.X += scrollControl.AutoScrollPosition.X;
                    childRect.Y += scrollControl.AutoScrollPosition.Y;
                }

                ulong   bestChildScore;
                Control bestChild = GetBestNavigationHost(childRect, key, control, exclude, out bestChildScore);
                if (bestChild != null && bestChildScore < bestScore)
                {
                    bestScore = bestChildScore;
                    best      = bestChild;
                }
            }

            // don't return this value, since it would return something in the wrong direction.
            if (bestScore >= long.MaxValue)
            {
                return(null);
            }

            return(best);
        }
Пример #25
0
        int FindOrInsertAncestor(IWindowlessControl control, List<IWindowlessControl> hierarchySorted)
        {
            int index = hierarchySorted.IndexOf(control);
            if (index != -1)
                return index;

            RelativeLayout layout = control.Layout as RelativeLayout;
            // if this is a root, just insert it at the head and go
            if (layout.Relative == null)
            {
                hierarchySorted.Insert(0, control);
                return 0;
            }

            index = FindOrInsertAncestor(layout.Relative, hierarchySorted) + 1;
            hierarchySorted.Insert(index, control);
            return index;
        }
Пример #26
0
 public SerializableControlCollection(IWindowlessControl control)
     : base(control)
 {
 }
Пример #27
0
        bool NavigateSelection(Rectangle rect, Keys key)
        {
            int index = Items.IndexOf(CurrentSelection);
            IWindowlessControl selected = null;

            if (index != -1)
            {
                selected = Control.Controls[index];
            }
            ulong bestScore         = UInt32.MaxValue;
            IWindowlessControl best = null;

            foreach (IWindowlessControl control in Control.Controls)
            {
                if (control == selected || !control.Visible)
                {
                    continue;
                }
                long distance;
                bool positiveDirection = false;
                if (key == Keys.Up)
                {
                    distance = GetEdgeDistance(control.Top + control.Height, control.Left, control.Width, rect.Top, rect.Left, rect.Width, positiveDirection);
                }
                else if (key == Keys.Down)
                {
                    positiveDirection = true;
                    distance          = GetEdgeDistance(control.Top, control.Left, control.Width, rect.Bottom, rect.Left, rect.Width, positiveDirection);
                }
                else if (key == Keys.Left)
                {
                    distance = GetEdgeDistance(control.Left + control.Width, control.Top, control.Height, rect.Left, rect.Top, rect.Height, positiveDirection);
                }
                else
                {
                    positiveDirection = true;
                    distance          = GetEdgeDistance(control.Left, control.Top, control.Height, rect.Right, rect.Top, rect.Height, positiveDirection);
                }


                ulong score = ScoreDistance(distance, positiveDirection);
                if (score < bestScore)
                {
                    bestScore = score;
                    best      = control;
                }
            }

            if (bestScore >= Int32.MaxValue)
            {
                return(false);
            }

            if (best == null)
            {
                return(false);
            }

            CurrentSelection = Items[Control.Controls.IndexOf(best)];
            return(true);
        }
 public static void WindowlessInvalidate(IWindowlessControl sender)
 {
     Point origin = Point.Empty;
     IWindowlessControl parent = sender;
     while (!(parent is WindowlessControlHost) && parent != null)
     {
         origin.X += parent.Left;
         origin.Y += parent.Top;
         parent = parent.Parent;
     }
     WindowlessControlHost host = parent as WindowlessControlHost;
     if (host != null)
         host.WindowlessInvalidate(new Rectangle(origin.X, origin.Y, sender.Width, sender.Height));
 }
Пример #29
0
        public override bool MeasureUnpadded(System.Drawing.Size bounds, bool boundsChange)
        {
            // prime the root controls and make a list of the leaf controls
            List <IWindowlessControl> leaves = new List <IWindowlessControl>(Controls);
            List <IWindowlessControl> roots  = new List <IWindowlessControl>();

            foreach (IWindowlessControl control in Controls)
            {
                RelativeLayout layout = control.Layout as RelativeLayout;
                if (layout == null)
                {
                    control.Layout = layout = new RelativeLayout();
                }
                if (layout.Relative == null)
                {
                    layout.RelativeWidth = layout.RelativeHeight = 1;
                    layout.RelativeX     = layout.RelativeY = 0;
                    roots.Add(control);
                }
                else
                {
                    leaves.Remove(layout.Relative);
                }
            }

            List <IWindowlessControl> hierarchySort = HierarchySort(leaves);

            // compute the relative layouts for all but the root controls
            foreach (IWindowlessControl control in Controls)
            {
                RelativeLayout layout = control.Layout as RelativeLayout;
                if (layout.Relative == null)
                {
                    continue;
                }

                layout.RelativeWidth  = layout.Width;
                layout.RelativeHeight = layout.Height;
                layout.RelativeX      = layout.X;
                layout.RelativeY      = layout.Y;
                // climb the lineage and calculate the relative layouts
                IWindowlessControl relative       = layout.Relative;
                RelativeLayout     relativeLayout = null;
                while (relative != null)
                {
                    relativeLayout         = relative.Layout as RelativeLayout;
                    layout.RelativeX       = layout.X * relativeLayout.Width + relativeLayout.X;
                    layout.RelativeY       = layout.Y * relativeLayout.Height + relativeLayout.Y;
                    layout.RelativeWidth  *= relativeLayout.Width;
                    layout.RelativeHeight *= relativeLayout.Height;
                    relative = relativeLayout.Relative;
                }

                // the last thing we should have now is the root controls layout
                // if anything is out of bounds, make note of it in the root control
                relativeLayout.RelativeX = Math.Min(relativeLayout.RelativeX, layout.RelativeX);
                relativeLayout.RelativeY = Math.Min(relativeLayout.RelativeY, layout.RelativeY);
                // for root controls, i am using the relative width/height to record the bottom right corner
                // of the control tree
                relativeLayout.RelativeWidth  = Math.Max(layout.RelativeX + layout.RelativeWidth, relativeLayout.RelativeWidth);
                relativeLayout.RelativeHeight = Math.Max(layout.RelativeY + layout.RelativeHeight, relativeLayout.RelativeHeight);
            }

            float maxWidth     = 0;
            float maxHeight    = 0;
            bool  layoutChange = false;

            // measure all the root controls, get the max dims and use that as a reference from
            // here on out
            foreach (IWindowlessControl control in roots)
            {
                RelativeLayout layout  = control.Layout as RelativeLayout;
                Rectangle      oldRect = new Rectangle(control.Left, control.Top, control.Width, control.Height);
                // always measure, regardless of bounds change or the control needing measure
                // size is relative to other controls...
                Size treeBounds = new Size();
                if (bounds.Width == Int32.MaxValue)
                {
                    treeBounds.Width = Int32.MaxValue;
                }
                else
                {
                    treeBounds.Width = (int)Math.Round(bounds.Width / (layout.RelativeWidth - layout.RelativeX));
                }
                if (bounds.Height == Int32.MaxValue)
                {
                    treeBounds.Height = Int32.MaxValue;
                }
                else
                {
                    treeBounds.Height = (int)Math.Round(bounds.Height / (layout.RelativeHeight - layout.RelativeY));
                }

                control.Measure(treeBounds);

                float treeWidth  = (layout.RelativeWidth - layout.RelativeX) * control.Width;
                float treeHeight = (layout.RelativeHeight - layout.RelativeX) * control.Height;
                maxWidth      = Math.Max(maxWidth, treeWidth);
                maxHeight     = Math.Max(maxHeight, treeHeight);
                layoutChange |= oldRect != new Rectangle(control.Left, control.Top, control.Width, control.Height);
            }

            ClientWidth  = (int)Math.Round(maxWidth);
            ClientHeight = (int)Math.Round(maxHeight);

            // lay out the roots
            foreach (IWindowlessControl control in roots)
            {
                RelativeLayout layout   = control.Layout as RelativeLayout;
                Rectangle      rootRect = new Rectangle();
                // todo: add something to the layout class to persist this?
                float treeWidth  = layout.RelativeWidth - layout.RelativeX;
                float treeHeight = layout.RelativeHeight - layout.RelativeY;
                rootRect.Width  = (int)Math.Round(ClientWidth / treeWidth);
                rootRect.Height = (int)Math.Round(ClientHeight / treeHeight);

                rootRect.X = (int)Math.Round(-(layout.RelativeX / treeWidth) * ClientWidth) + ClientLeft;
                rootRect.Y = (int)Math.Round(-(layout.RelativeY / treeHeight) * ClientHeight) + ClientTop;
                LayoutControl(control, rootRect);
            }



            // measure out all child controls and layout all controls
            foreach (IWindowlessControl control in hierarchySort)
            {
                RelativeLayout     layout   = control.Layout as RelativeLayout;
                IWindowlessControl relative = layout.Relative;
                if (relative == null)
                {
                    continue;
                }

                Size childBounds = new Size();
                // calcuate child bounds
                childBounds.Width  = (int)Math.Round(layout.RelativeWidth * relative.Width);
                childBounds.Height = (int)Math.Round(layout.RelativeHeight * relative.Height);

                // calculate the layout rect
                Rectangle childRect = new Rectangle();
                childRect.X    = (int)Math.Round(layout.RelativeX * relative.Width + relative.Left);
                childRect.Y    = (int)Math.Round(layout.RelativeY * relative.Height + relative.Top);
                childRect.Size = childBounds;

                // lay it out
                Rectangle oldRect = new Rectangle(control.Left, control.Top, control.Width, control.Height);
                control.Measure(childBounds);
                LayoutControl(control, childRect);
                layoutChange |= oldRect != new Rectangle(control.Left, control.Top, control.Width, control.Height);
            }

            return(layoutChange);
        }