 	//
 	//--------------------------------------------------------------------------
 	
-	override public function updateScrollRect(w:Number, h:Number):void
-	{
-		var g:GroupBase = target;
-		if (!g)
-			return;
-		
-		// Instead of moving the scrollRect position, we reposition the elements
-		if (clipAndEnableScrolling)
-			g.scrollRect = new Rectangle(0, 0, w, h);
-		else
-			g.scrollRect = null;
-	}
-	
 	override protected function scrollPositionChanged():void
-	{
-		if (target)
-		{
-			target.invalidateDisplayList();
-			setIndexInView(0, target.numElements - 1);
-		}
+	{        
+        var g:GroupBase = target;
+        if (!g)
+            return;
+        
+        updateScrollRect(g.width, g.height);
+        
+        var n:int = g.numElements - 1;
+        if (n < 0) 
+        {
+            setIndexInView(-1, -1);
+            return;
+        }
+        
+        var scrollR:Rectangle = getScrollRect();
+        if (!scrollR)
+        {
+            setIndexInView(0, n);
+            return;    
+        }
+        
+        var y0:Number = scrollR.top;
+        var y1:Number = scrollR.bottom - .0001;
+        if (y1 <= y0)
+        {
+            setIndexInView(-1, -1);
+            return;
+        }
+        
+        var i0:int;
+        var i1:int;
+        
+        if (wrapElements)
+        {
+            i0 = normalizeItemIndex(Math.floor(y0 / rowHeight));
+            i1 = normalizeItemIndex(Math.floor(y1 / rowHeight));
+        }
+        else
+        {
+            i0 = Math.min(Math.max(Math.floor(y0 / rowHeight), 0),n);
+            i1 = Math.min(Math.max(Math.floor(y1 / rowHeight), 0),n);
+        }
+        
+        setIndexInView(i0, i1);
+        
+        var firstElement:ILayoutElement = g.getElementAt(firstIndexInView);
+        var lastElement:ILayoutElement = g.getElementAt(lastIndexInView);
+        
+        if (wrapElements)
+        {
+            if (!firstElement || !lastElement || 
+                scrollR.top < firstElement.getLayoutBoundsY() || 
+                scrollR.bottom >= (lastElement.getLayoutBoundsY() + lastElement.getLayoutBoundsHeight()))
+            {
+                g.invalidateDisplayList();
+            }
+        }
+        else
+        {
+            if (!firstElement || !lastElement || 
+                (scrollR.top < firstElement.getLayoutBoundsY() && firstIndexInView != 0) || 
+                (scrollR.bottom >= (lastElement.getLayoutBoundsY() + lastElement.getLayoutBoundsHeight()) && lastIndexInView != n))
+            {
+                g.invalidateDisplayList();
+            }
+        }
 	}
 	
 	override public function getHorizontalScrollPositionDelta(navigationUnit:uint):Number

	override mx_internal function getElementNearestScrollPosition(
		position:Point,elementComparePoint:String = "center"):int
	{
		
		var index:int = Math.floor(position.y / rowHeight); // may be larger than numElements to indicate wrapping
		
		var element:ILayoutElement;

                
                // If we are using virtual layout, only size and position 
                // the visible elements
                if (yPos > yPosMax && !foundLastVisibleElement)
                {
                    foundLastVisibleElement = true;
                    // Keep track of the number of elements visible in the viewing area
