询问者
实现IScrollInfo接口时遇到的问题

问题
-
各位好,最近有个需求,需要实现Virtulizing WrapPanel 参照msdn blog上的这篇教程以及MSDN的官方例子, 写了个自定义的Warp Panel, Wrap的功能到时能正常实现,可是就是不能滑动了,调试的时候将断点设置在IScrollInfo里的接口函数里,但是断点怎么也进不去了,所以在此请教一下是哪出问题了,谢谢!
public class VTWrapPanel : VirtualizingPanel, IScrollInfo { private TranslateTransform _trans = new TranslateTransform(); public VTWrapPanel() { this.RenderTransform = _trans; } #region VirtualizingPanel #region 私有字段 private Size _extent = new Size(0, 0); private Size _viewport = new Size(0, 0); #endregion #region 重载方法 /// <summary> /// 计算布局 /// </summary> /// <param name="availableSize"></param> /// <returns></returns> protected override Size MeasureOverride(Size availableSize) { Size childSize = new Size( availableSize.Width, (availableSize.Height * 2) / this.Children.Count); Size extent = new Size( availableSize.Width, childSize.Height * this.Children.Count); if (extent != _extent) { _extent = extent; if (_owner != null) _owner.InvalidateScrollInfo(); } if (availableSize != _viewport) { _viewport = availableSize; if (_owner != null) _owner.InvalidateScrollInfo(); } foreach (UIElement child in this.Children) { child.Measure(childSize); } return availableSize; } protected override Size ArrangeOverride(Size finalSize) { Size childSize = new Size( finalSize.Width, (finalSize.Height * 2) / this.Children.Count); Size extent = new Size( finalSize.Width, childSize.Height * this.Children.Count); if (extent != _extent) { _extent = extent; if (_owner != null) _owner.InvalidateScrollInfo(); } if (finalSize != _viewport) { _viewport = finalSize; if (_owner != null) _owner.InvalidateScrollInfo(); } for (int i = 0; i < this.Children.Count; i++) { this.Children[i].Arrange(new Rect(0, childSize.Height * i, childSize.Width, childSize.Height)); } return finalSize; } #endregion #endregion #region IScrollInfo #region 私有字段 private ScrollViewer _owner; private bool _canHScroll = false; private bool _canVScroll = false; private Point _offset; #endregion #region 公共属性 public ScrollViewer ScrollOwner { get { return _owner; } set { _owner = value; } } public bool CanHorizontallyScroll { get { return _canHScroll; } set { _canHScroll = value; } } public bool CanVerticallyScroll { get { return _canVScroll; } set { _canVScroll = value; } } public double HorizontalOffset { get { return _offset.X; } } public double VerticalOffset { get { return _offset.Y; } } public double ExtentHeight { get { return _extent.Height; } } public double ExtentWidth { get { return _extent.Width; } } public double ViewportHeight { get { return _viewport.Height; } } public double ViewportWidth { get { return _viewport.Width; } } #endregion #region Scroll commands public void LineUp() { SetVerticalOffset(this.VerticalOffset - 1); } public void LineDown() { SetVerticalOffset(this.VerticalOffset + 1); } public void LineLeft() { SetHorizontalOffset(this.HorizontalOffset - 1); } public void LineRight() { SetHorizontalOffset(this.HorizontalOffset + 1); } /// <summary> /// ensure the visiblity of one of the children in the Panel /// REF:http://blogs.msdn.com/b/bencon/archive/2006/12/09/iscrollinfo-tutorial-part-iv.aspx /// </summary> /// <param name="visual"> the thing that we need to make visible - it will be one of the children of the Panel</param> /// <param name="rectangle">the rectangle of the Visual that needs to be visible</param> /// <returns>the rectangle of the Visual that you managed to make visible</returns> public Rect MakeVisible(UIElement visual, Rect rectangle) { for (int i = 0; i < this.Children.Count; i++) { if ((UIElement)this.Children[i] == visual) { // we found the visual! Let's scroll it into view. First we need to know how big each child is. Size finalSize = this.RenderSize; Size childSize = new Size( finalSize.Width, (finalSize.Height * 2) / this.Children.Count); // now we can calculate the vertical offset that we need and set it SetVerticalOffset(childSize.Height * i); // child size is always smaller than viewport, because that is what makes the Panel return rectangle; } } throw new ArgumentException("Given visual is not in this Panel"); } public void MouseWheelDown() { throw new NotImplementedException(); } public void MouseWheelLeft() { throw new NotImplementedException(); } public void MouseWheelRight() { throw new NotImplementedException(); } public void MouseWheelUp() { throw new NotImplementedException(); } public void PageDown() { throw new NotImplementedException(); } public void PageLeft() { throw new NotImplementedException(); } public void PageRight() { throw new NotImplementedException(); } public void PageUp() { throw new NotImplementedException(); } #endregion public void SetHorizontalOffset(double offset) { //首先检查offset是不是小于0,或者是否大于比当前的宽度,如果是的话,将其置为0 if (offset < 0 || _viewport.Width >= _extent.Width) { offset = 0; } else { if (offset + _viewport.Width >= _extent.Width) { offset = _extent.Width - _viewport.Width; } } _offset.X = offset; if (_owner != null) _owner.InvalidateScrollInfo(); _trans.X = -offset; } public void SetVerticalOffset(double offset) { if (offset < 0 || _viewport.Height >= _extent.Height) { offset = 0; } else { if (offset + _viewport.Height >= _extent.Height) { offset = _extent.Height - _viewport.Height; } } _offset.Y = offset; if (_owner != null) _owner.InvalidateScrollInfo(); _trans.Y = -offset; } #endregion }
2012年9月19日 5:31