private void PageUpDown(ScrollDirection direction)
        {
            if (direction == ScrollDirection.Up)
            {
                //If we scrolled a full page, then the bottom of the first fully visible line will be below
                //the bottom of the view.
                ITextViewLine firstVisibleLine     = TextView.AdvancedTextView.TextViewLines.FirstVisibleLine;
                SnapshotPoint oldFullyVisibleStart = (firstVisibleLine.VisibilityState == VisibilityState.FullyVisible)
                                           ? firstVisibleLine.Start
                                           : firstVisibleLine.EndIncludingLineBreak; //Start of next line.

                if (TextView.AdvancedTextView.ViewScroller.ScrollViewportVerticallyByPage(direction))
                {
                    ITextViewLine newFirstLine = TextView.AdvancedTextView.TextViewLines.GetTextViewLineContainingBufferPosition(oldFullyVisibleStart);

                    //The old fully visible line should -- if we scrolled as much as we could -- be partially
                    //obscured. The shortfall between a full page and what we actually scrolled is the distance
                    //between the bottom of that line and the bottom of the screen.
                    if (TextView.AdvancedTextView.ViewportBottom > newFirstLine.Bottom)
                    {
                        AdvancedCaret.MoveTo(TextView.AdvancedTextView.TextViewLines.FirstVisibleLine);
                    }
                    else
                    {
                        AdvancedCaret.MoveToPreferredCoordinates();
                    }
                }
            }
            else
            {
                //If we scroll a full page, the bottom of the last fully visible line will be
                //positioned at 0.0.
                ITextViewLine lastVisibleLine = TextView.AdvancedTextView.TextViewLines.LastVisibleLine;

                // If the last line in the buffer is fully visible , then just move the caret to
                // the last visible line
                if ((lastVisibleLine.VisibilityState == VisibilityState.FullyVisible) &&
                    (lastVisibleLine.End == lastVisibleLine.Snapshot.Length))
                {
                    AdvancedCaret.MoveTo(lastVisibleLine);

                    // No need to ensure the caret is visible since the line it just moved to is fully visible.
                    return;
                }

                SnapshotPoint oldFullyVisibleStart = ((lastVisibleLine.VisibilityState == VisibilityState.FullyVisible) || (lastVisibleLine.Start == 0))
                                           ? lastVisibleLine.Start
                                           : (lastVisibleLine.Start - 1); //Actually just a point on the previous line.

                if (TextView.AdvancedTextView.ViewScroller.ScrollViewportVerticallyByPage(direction))
                {
                    ITextViewLine newLastLine = TextView.AdvancedTextView.TextViewLines.GetTextViewLineContainingBufferPosition(oldFullyVisibleStart);
                    if (newLastLine.Bottom > TextView.AdvancedTextView.ViewportTop)
                    {
                        AdvancedCaret.MoveTo(TextView.AdvancedTextView.TextViewLines.LastVisibleLine);
                    }
                    else
                    {
                        AdvancedCaret.MoveToPreferredCoordinates();
                    }
                }
            }

            EnsureVisible();
        }