     // Event Handlers
     //
     //--------------------------------------------------------------------------
-
+    
+    /**
+     *  @private
+     *  Helper function for viewport_propertyChangeHandler below 
+     */
+    private function checkForInvalidScrollPositions():void
+    {
+        var snapVSP:Number;
+        var snapHSP:Number;
+        var doVerticalSnap:Boolean = false;
+        var doHorizontalSnap:Boolean = false;
+        
+        function updateCompleteHandler(event:FlexEvent):void
+        {
+            viewport.removeEventListener(FlexEvent.UPDATE_COMPLETE, 
+                updateCompleteHandler);
+            
+            if (doHorizontalSnap)
+                viewport.horizontalScrollPosition = snapHSP;
+            
+            if (doVerticalSnap)
+                viewport.verticalScrollPosition = snapVSP;
+        }
+        
+        // There are two cases in which we'll potentially need to fix invalid 
+        // scroll positions...
+        if (throwEffect && throwEffect.isPlaying)
+        {
+            // 1) A throw effect animation is in progress, and may have been 
+            // set up to end at a scroll position that is now invalid.
+            snapVSP = throwFinalVSP;
+            snapHSP = throwFinalHSP;
+        }
+        else if (!inTouchInteraction)
+        {
+            // 2) There's no touch gesture in progress.  The content may be 
+            // at a scroll position that is now invalid.
+            snapVSP = viewport.verticalScrollPosition;
+            snapHSP = viewport.horizontalScrollPosition;
+        } 
+        else
+        {
+            // If we get here we know that a touch gesture is in progress but 
+            // the throw animation portion is not playing.  The user's finger 
+            // is down.  We don't need to worry about the scroll position being 
+            // invalid because when the finger is released the throw animation 
+            // will get us back to a valid position.
+            return;
+        }
+        
+        // Determine the maximum valid scroll positions
+        var maxVSP:Number = viewport.contentHeight > viewport.height ? 
+            viewport.contentHeight-viewport.height : 0; 
+        var maxHSP:Number = viewport.contentWidth > viewport.width ? 
+            viewport.contentWidth-viewport.width : 0; 
+
+        // See whether the current scroll positions are invalid
+        if (snapVSP > maxVSP)
+        {
+            snapVSP = maxVSP;
+            doVerticalSnap = true;
+        }
+        if (snapHSP > maxHSP)
+        {
+            snapHSP = maxHSP;
+            doHorizontalSnap = true;
+        }
+
+        if (doHorizontalSnap || doVerticalSnap)
+        {
+            // One or both scroll positions are invalid
+            
+            // If a throw effect is playing, we need to stop it
+            if (throwEffect && throwEffect.isPlaying)
+                throwEffect.stop();
+            
+            // We need to wait until after the current update to change to the new 
+            // valid scroll positions.
+            viewport.addEventListener(FlexEvent.UPDATE_COMPLETE, 
+                updateCompleteHandler);
+        }
+    }
     
     private function viewport_propertyChangeHandler(event:PropertyChangeEvent):void
     {

            {
                throwEffectMotionPaths.push(verticalMP);
                verticalTime = verticalMP.keyframes[verticalMP.keyframes.length-1].time;
                scrollingVertically = true;
            }
        }

        scrollingHorizontally = false;
        var horizontalTime:Number = 0;
        var finalKeyframe:int;
        throwFinalHSP = 0;
        if (scrollerLayout && scrollerLayout.canScrollHorizontally)
        {
            var hsp:Number = viewport.horizontalScrollPosition;
