The root class of all boxes, that is, rectanglar screen areas that lay out data.
Example #1
0
		private Box ChildSetup(Box box, LayoutInfo transform, int maxBoxWidth, int left, int top)
		{
			var childTransform = transform.WithMaxWidthOffsetBy(maxBoxWidth, Left, Top); // todo: test
			box.Layout(childTransform);
			box.Left = left;
			box.Top = top;
			return box;
		}
Example #2
0
		// Figure out how much to adjust the top of box, which would be the input value of top
		// except for overlapping margins, if in fact margin overlaps the previous box.
		internal int AdjustTopForMargins(int top, LayoutInfo transform, Box prevBox, Box box)
		{
			if (prevBox != null)
			{
				top -= Math.Min(transform.MpToPixelsY(prevBox.Style.Margins.BottomMp),
					transform.MpToPixelsY(box.Style.Margins.TopMp));
			}
			return top;
		}
Example #3
0
		/// <summary>
		/// Add another box (to the end of the chain).
		/// </summary>
		/// <param name="box"></param>
		public void AddBox(Box box)
		{
			if (box == null)
				return;
			if (FirstBox == null)
			{
				FirstBox = box;
				FirstBox.Previous = null;
			}
			else
			{
				LastBox.Next = box;
				box.Previous = LastBox;
			}
			LastBox = box;
			box.Next = null;
			box.Container = this;
			NumBoxes++;
		}
Example #4
0
		/// <summary>
		/// Return true if this box contains the other one, that is, is one of its containers.
		/// Only group boxes can contain others.
		/// </summary>
		public virtual bool Contains(Box other)
		{
			return false;
		}
Example #5
0
		/// <summary>
		/// Answer true if this box is in the sequence of boxes chained after other.
		/// Optimize JohnT: if we assume they are usually close together but either order is likely,
		/// it would usually be more efficient to have a double loop that searches both Next chains at once
		/// until one runs out or we find the other.
		/// </summary>
		public bool Follows(Box other)
		{
			if (other == null)
				return false;
			for (Box box = other.Next; box != null; box = box.Next)
			{
				if (box == this)
					return true;
			}
			return false; // this does NOT follow other.
		}
Example #6
0
		public Box CommonContainer(Box other)
		{
			Box thisChild;
			Box otherChild;
			return CommonContainer(other, out thisChild, out otherChild);
		}
Example #7
0
		/// <summary>
		/// Answer true if the box is entirely below the clip rectangle.
		/// Enhance JohnT: Could refine this to skip a box if only its margin is visible.
		/// Enhance JohnT: if we do separate page drawing, as in print preview, we may need
		/// a more precise way to eliminate boxes not on the page.
		/// Enhance JohnT: may need to include a box that is just out of sight, in case exceptionally
		/// high stacked diacritics extend above the top of the box?
		/// </summary>
		internal override bool IsAfterVisibleBoxes(Box box, IVwGraphics vg, PaintTransform ptrans)
		{
			int left, top, right, bottom;
			vg.GetClipRect(out left, out top, out right, out bottom);
			return ptrans.ToPaintY(box.Top) > bottom;
		}
Example #8
0
		/// <summary>
		/// This routine and its overrides are used to make sure that the part of the root box between
		/// yTop and yBottom (measured from the top of the root) can be painted successfully. To facilitate
		/// the process of replacing a lazy box with real boxes, it is passed the previous box in its
		/// container (or null if there is none) and returns the next box which the container should
		/// check is prepared to paint. By default this is simply the next box, but if a lazy box expands
		/// (part of) itself, it should answer the replacement box.
		/// Most box classes are always prepared to paint and do nothing. Lazy boxes convert all or part of
		/// themselves to real boxes if they intersect the specified vertical range (relative to the root as
		/// a whole). Boxes (currently DivBoxes only) which might contain lazy boxes pass the message on
		/// to their children, making the appropriate adjustment to the layout transform, just as when
		/// asking their children to Layout.
		/// </summary>
		internal override Box PrepareToPaint(LayoutInfo transform, Box myPrevBox, int dysTop, int dysBottom)
		{
			var childMaxWidth = transform.MaxWidth - GapLeading(transform) - GapTrailing(transform);
			var childTransform = transform.WithMaxWidthOffsetBy(childMaxWidth, Left, Top);
			Box prevBox = null;
			for (Box box = FirstBox; box != null; )
			{
				if (transform.YOffset + box.Top > dysBottom)
				{
					// nothing further down in this can be visible. Possibly we should return null,
					// since presumably nothing further down in the container is visible, either.
					// However, it feels more robust to answer in the usual way and let the container decide
					// for itself.
					return Next;
				}
				if (transform.YOffset + box.Bottom < dysTop)
					box = box.Next; // this box is not visible, but a later one might be
				else
					box = box.PrepareToPaint(childTransform, prevBox, dysTop, dysBottom);
			}
			return Next;
		}
Example #9
0
		/// <summary>
		/// Add a child box after the specified box (one of your children).
		/// </summary>
		public void InsertBox(Box newBox, Box insertAfter)
		{
			if (newBox == null)
				return;
			if (insertAfter == null)
			{
				newBox.Next = FirstBox;
				if(FirstBox != null)
					FirstBox.Previous = newBox;
				FirstBox = newBox;
				FirstBox.Previous = null;
			}
			else
			{
				if (insertAfter.Container != this)
					throw new ArgumentException("InsertBox's insertAfter argument must be a child of the box inserted into");
				newBox.Next = insertAfter.Next;
				insertAfter.Next = newBox;
				newBox.Previous = insertAfter;
			}
			if (newBox.Next == null)
				LastBox = newBox;
			newBox.Container = this;
			NumBoxes++;
		}
Example #10
0
 /// <summary>
 /// Return true if this box contains the other one, that is, is one of its containers.
 /// Only group boxes can contain others.
 /// </summary>
 public virtual bool Contains(Box other)
 {
     return(false);
 }
Example #11
0
		private Box BoxBefore(Box target)
		{
			Box result = null;
			for (Box current = FirstBox; ; current = current.Next)
			{
				if (current == target)
					return result;
				result = current;
			}
		}
Example #12
0
		internal void RemoveBoxes(Box firstGoner, Box lastGoner)
		{
			if (firstGoner.Container != this)
				throw new ArgumentException("firstGoner must be a child");
			if (lastGoner.Container != this)
				throw new ArgumentException("lastGoner must be a child");
			var previous = BoxBefore(firstGoner);
			// link around them
			if (previous == null)
			{
				FirstBox = lastGoner.Next;
				if(FirstBox != null)
					FirstBox.Previous = null;
			}
			else
			{
				previous.Next = lastGoner.Next;
				if(lastGoner.Next != null)
					lastGoner.Next.Previous = previous;
			}
			lastGoner.Next = null; // prevents anything accidentally linking back into the real ones.
			firstGoner.Previous = null;
			if (lastGoner == LastBox)
				LastBox = previous;
			FindNumBoxes();
		}
Example #13
0
		/// <summary>
		/// Return true if this box contains the other one, that is, is one of its containers.
		/// Only group boxes can contain others.
		/// </summary>
		public override bool Contains(Box other)
		{
			for (var container = other.Container; container != null; container = container.Container)
			{
				if (container == this)
					return true;
			}
			return false;
		}
Example #14
0
		/// <summary>
		/// Return true if the argument (child) box and all subsequent boxes need not be painted,
		/// typically because they occur after the end of the clip rectangle specified in the VwGraphics.
		/// It is acceptable to answer false, if no clipping is wanted, or for the first box for which
		/// we answer true to be later than the optimal one; this is an optional optimization.
		/// </summary>
		internal virtual bool IsAfterVisibleBoxes(Box box, IVwGraphics vg, PaintTransform ptrans)
		{
			return false;
		}
Example #15
0
		/// <summary>
		/// Returns the closest container of this and other which is a container of both of them,
		/// and also the child of that container which is or contains each of them.
		/// Special cases:
		/// if they are the same box, all three return values are that box.
		/// if one of the boxes contains the other, the return value and the corresponding child output
		/// are both the containing box.
		/// </summary>
		/// <param name="other">box to search for</param>
		/// <param name="thisChild">this or a container of this</param>
		/// <param name="otherChild">other or a container of other</param>
		/// <returns></returns>
		public Box CommonContainer(Box other, out Box thisChild, out Box otherChild)
		{
			thisChild = this;
			otherChild = other;
			if (other == this)
			{
				return this;
			}
			var otherContainers = new HashSet<Box>(other.AllContainers.Cast<Box>());
			otherContainers.Add(other);
			if (otherContainers.Contains(this))
			{
				// special case: this contains other.
				otherChild = (from box in otherContainers where box.Container == this select box).First();
				return this;
			}
			foreach (var container in AllContainers)
			{
				if (container == other) // other IS the common container.
					return container; // otherChild is already set, and we won't find a box contained by other in the set.
				if (otherContainers.Contains(container))
				{
					// container is the common container.
					otherChild = (from box in otherContainers where box.Container == container select box).First();
					return container;
				}
				thisChild = container; // will be right when we find the true common container.
			}
			return Root; // should never happen, but might be the right answer in such a case??
		}
Example #16
0
		/// <summary>
		/// This routine and its overrides are used to make sure that the part of the root box between
		/// yTop and yBottom (measured from the top of the root) can be painted successfully. To facilitate
		/// the process of replacing a lazy box with real boxes, it is passed the previous box in its
		/// container (or null if there is none) and returns the next box which the container should
		/// check is prepared to paint. By default this is simply the next box, but if a lazy box expands
		/// (part of) itself, it should answer the replacement box.
		/// Most box classes are always prepared to paint and just answer Next. Lazy boxes convert all or part of
		/// themselves to real boxes if they intersect the specified vertical range (relative to the root as
		/// a whole). Boxes (currently DivBoxes only) which might contain lazy boxes pass the message on
		/// to their children, making the appropriate adjustment to the layout transform, just as when
		/// asking their children to Layout.
		/// </summary>
		internal virtual Box PrepareToPaint(LayoutInfo transform, Box prevBox, int yTop, int yBottom)
		{
			return Next;
		}
Example #17
0
 /// <summary>
 /// This routine and its overrides are used to make sure that the part of the root box between
 /// yTop and yBottom (measured from the top of the root) can be painted successfully. To facilitate
 /// the process of replacing a lazy box with real boxes, it is passed the previous box in its
 /// container (or null if there is none) and returns the next box which the container should
 /// check is prepared to paint. By default this is simply the next box, but if a lazy box expands
 /// (part of) itself, it should answer the replacement box.
 /// Most box classes are always prepared to paint and just answer Next. Lazy boxes convert all or part of
 /// themselves to real boxes if they intersect the specified vertical range (relative to the root as
 /// a whole). Boxes (currently DivBoxes only) which might contain lazy boxes pass the message on
 /// to their children, making the appropriate adjustment to the layout transform, just as when
 /// asking their children to Layout.
 /// </summary>
 internal virtual Box PrepareToPaint(LayoutInfo transform, Box prevBox, int yTop, int yBottom)
 {
     return(Next);
 }