function _layout(size, scrollOffset, nested) {

        // Track the number of times the layout-function was executed
        this._debug.layoutCount++;
        //_log.call(this, 'Layout, scrollOffset: ', scrollOffset, ', particle: ', this._scroll.particle.getPosition1D());

        // Determine start & end
        var scrollStart = 0 - Math.max(this.options.extraBoundsSpace[0], 1);
        var scrollEnd = size[this._direction] + Math.max(this.options.extraBoundsSpace[1], 1);
        if (this.options.paginated && (this.options.paginationMode === PaginationMode.PAGE)) {
            scrollStart = scrollOffset - this.options.extraBoundsSpace[0];
            scrollEnd = scrollOffset + size[this._direction] + this.options.extraBoundsSpace[1];
            if ((scrollOffset + size[this._direction]) < 0) {
                scrollStart += size[this._direction];
                scrollEnd += size[this._direction];
            }
            else if ((scrollOffset - size[this._direction]) > 0) {
                scrollStart -= size[this._direction];
                scrollEnd -= size[this._direction];
            }
        }
        if (this.options.layoutAll) {
            scrollStart = -1000000;
            scrollEnd = 1000000;
        }

        // Prepare for layout
        var layoutContext = this._nodes.prepareForLayout(
            this._viewSequence,     // first node to layout
            this._nodesById, {      // so we can do fast id lookups
                size: size,
                direction: this._direction,
                reverse: this.options.alignment ? true : false,
                scrollOffset: this.options.alignment ? (scrollOffset + size[this._direction]) : scrollOffset,
                scrollStart: scrollStart,
                scrollEnd: scrollEnd
            }
        );

        // Layout objects
        if (this._layout._function) {
            this._layout._function(
                layoutContext,          // context which the layout-function can use
                this._layout.options    // additional layout-options
            );
        }
        this._scroll.unnormalizedScrollOffset = scrollOffset;

        // Call post-layout function
        if (this._postLayout) {
            this._postLayout(size, scrollOffset);
        }

        // Mark non-invalidated nodes for removal
        this._nodes.removeNonInvalidatedNodes(this.options.flowOptions.removeSpec);

        // Check whether the bounds have been reached
        //var oldBoundsReached = this._scroll.boundsReached;
        _calcBounds.call(this, size, scrollOffset);
        //if (oldBoundsReached !== this._scroll.boundsReached) {
        //    _log.call(this, 'bounds reached changed (', oldBoundsReached, ' != ', this._scroll.boundsReached, ')');
        //}

        // Update scroll-to spring
        _calcScrollToOffset.call(this, size, scrollOffset);

        // When pagination is enabled, snap to page
        _snapToPage.call(this);

        // If the bounds have changed, and the scroll-offset would be different
        // than before, then re-layout entirely using the new offset.
        var newScrollOffset = _calcScrollOffset.call(this, true);
        if (!nested && (newScrollOffset !== scrollOffset)) {
            //_log.call(this, 'offset changed, re-layouting... (', scrollOffset, ' != ', newScrollOffset, ')');
            return _layout.call(this, size, newScrollOffset, true);
        }

        // Normalize scroll offset so that the current viewsequence node is as close to the
        // top as possible and the layout function will need to process the least amount
        // of renderables.
        scrollOffset = _normalizeViewSequence.call(this, size, scrollOffset);

        // Update spring
        _updateSpring.call(this);

        // Cleanup any nodes in case of a VirtualViewSequence
        this._nodes.removeVirtualViewSequenceNodes();

        // Calculate scroll-length and use that as the true-size (height)
        if (this.options.size && (this.options.size[this._direction] === true)) {
            var scrollLength = 0;
            var node = this._nodes.getStartEnumNode();
            while (node) {
                if (node._invalidated && node.scrollLength) {
                    scrollLength += node.scrollLength;
                }
                node = node._next;
            }
            this._size = this._size || [0, 0];
            this._size[0] = this.options.size[0];
            this._size[1] = this.options.size[1];
            this._size[this._direction] = scrollLength;
        }

        return scrollOffset;
    }
function _layout(size, scrollOffset, nested) {

        
        this._debug.layoutCount++;
        

        
        var scrollStart = 0 - Math.max(this.options.extraBoundsSpace[0], 1);
        var scrollEnd = size[this._direction] + Math.max(this.options.extraBoundsSpace[1], 1);
        if (this.options.paginated && (this.options.paginationMode === PaginationMode.PAGE)) {
            scrollStart = scrollOffset - this.options.extraBoundsSpace[0];
            scrollEnd = scrollOffset + size[this._direction] + this.options.extraBoundsSpace[1];
            if ((scrollOffset + size[this._direction]) < 0) {
                scrollStart += size[this._direction];
                scrollEnd += size[this._direction];
            }
            else if ((scrollOffset - size[this._direction]) > 0) {
                scrollStart -= size[this._direction];
                scrollEnd -= size[this._direction];
            }
        }
        if (this.options.layoutAll) {
            scrollStart = -1000000;
            scrollEnd = 1000000;
        }

        
        var layoutContext = this._nodes.prepareForLayout(
            this._viewSequence,     
            this._nodesById, {      
                size: size,
                direction: this._direction,
                reverse: this.options.alignment ? true : false,
                scrollOffset: this.options.alignment ? (scrollOffset + size[this._direction]) : scrollOffset,
                scrollStart: scrollStart,
                scrollEnd: scrollEnd
            }
        );

        
        if (this._layout._function) {
            this._layout._function(
                layoutContext,          
                this._layout.options    
            );
        }
        this._scroll.unnormalizedScrollOffset = scrollOffset;

        
        if (this._postLayout) {
            this._postLayout(size, scrollOffset);
        }

        
        this._nodes.removeNonInvalidatedNodes(this.options.flowOptions.removeSpec);

        
        
        _calcBounds.call(this, size, scrollOffset);
        
        
        

        
        _calcScrollToOffset.call(this, size, scrollOffset);

        
        _snapToPage.call(this);

        
        
        var newScrollOffset = _calcScrollOffset.call(this, true);
        if (!nested && (newScrollOffset !== scrollOffset)) {
            
            return _layout.call(this, size, newScrollOffset, true);
        }

        
        
        
        scrollOffset = _normalizeViewSequence.call(this, size, scrollOffset);

        
        _updateSpring.call(this);

        
        this._nodes.removeVirtualViewSequenceNodes();

        
        if (this.options.size && (this.options.size[this._direction] === true)) {
            var scrollLength = 0;
            var node = this._nodes.getStartEnumNode();
            while (node) {
                if (node._invalidated && node.scrollLength) {
                    scrollLength += node.scrollLength;
                }
                node = node._next;
            }
            this._size = this._size || [0, 0];
            this._size[0] = this.options.size[0];
            this._size[1] = this.options.size[1];
            this._size[this._direction] = scrollLength;
        }

        return scrollOffset;
    }
function _layout ( size , scrollOffset , nested ) { // Track the number of times the layout-function was executed this . _debug . layoutCount ++ ; //_log.call(this, 'Layout, scrollOffset: ', scrollOffset, ', particle: ', this._scroll.particle.getPosition1D()); // Determine start & end var scrollStart = 0 - Math . max ( this . options . extraBoundsSpace [ 0 ] , 1 ) ; var scrollEnd = size [ this . _direction ] + Math . max ( this . options . extraBoundsSpace [ 1 ] , 1 ) ; if ( this . options . paginated && ( this . options . paginationMode === PaginationMode . PAGE ) ) { scrollStart = scrollOffset - this . options . extraBoundsSpace [ 0 ] ; scrollEnd = scrollOffset + size [ this . _direction ] + this . options . extraBoundsSpace [ 1 ] ; if ( ( scrollOffset + size [ this . _direction ] ) < 0 ) { scrollStart += size [ this . _direction ] ; scrollEnd += size [ this . _direction ] ; } else if ( ( scrollOffset - size [ this . _direction ] ) > 0 ) { scrollStart -= size [ this . _direction ] ; scrollEnd -= size [ this . _direction ] ; } } if ( this . options . layoutAll ) { scrollStart = - 1000000 ; scrollEnd = 1000000 ; } // Prepare for layout var layoutContext = this . _nodes . prepareForLayout ( this . _viewSequence , // first node to layout this . _nodesById , { // so we can do fast id lookups size : size , direction : this . _direction , reverse : this . options . alignment ? true : false , scrollOffset : this . options . alignment ? ( scrollOffset + size [ this . _direction ] ) : scrollOffset , scrollStart : scrollStart , scrollEnd : scrollEnd } ) ; // Layout objects if ( this . _layout . _function ) { this . _layout . _function ( layoutContext , // context which the layout-function can use this . _layout . options // additional layout-options ) ; } this . _scroll . unnormalizedScrollOffset = scrollOffset ; // Call post-layout function if ( this . _postLayout ) { this . _postLayout ( size , scrollOffset ) ; } // Mark non-invalidated nodes for removal this . _nodes . removeNonInvalidatedNodes ( this . options . flowOptions . removeSpec ) ; // Check whether the bounds have been reached //var oldBoundsReached = this._scroll.boundsReached; _calcBounds . call ( this , size , scrollOffset ) ; //if (oldBoundsReached !== this._scroll.boundsReached) { //    _log.call(this, 'bounds reached changed (', oldBoundsReached, ' != ', this._scroll.boundsReached, ')'); //} // Update scroll-to spring _calcScrollToOffset . call ( this , size , scrollOffset ) ; // When pagination is enabled, snap to page _snapToPage . call ( this ) ; // If the bounds have changed, and the scroll-offset would be different // than before, then re-layout entirely using the new offset. var newScrollOffset = _calcScrollOffset . call ( this , true ) ; if ( ! nested && ( newScrollOffset !== scrollOffset ) ) { //_log.call(this, 'offset changed, re-layouting... (', scrollOffset, ' != ', newScrollOffset, ')'); return _layout . call ( this , size , newScrollOffset , true ) ; } // Normalize scroll offset so that the current viewsequence node is as close to the // top as possible and the layout function will need to process the least amount // of renderables. scrollOffset = _normalizeViewSequence . call ( this , size , scrollOffset ) ; // Update spring _updateSpring . call ( this ) ; // Cleanup any nodes in case of a VirtualViewSequence this . _nodes . removeVirtualViewSequenceNodes ( ) ; // Calculate scroll-length and use that as the true-size (height) if ( this . options . size && ( this . options . size [ this . _direction ] === true ) ) { var scrollLength = 0 ; var node = this . _nodes . getStartEnumNode ( ) ; while ( node ) { if ( node . _invalidated && node . scrollLength ) { scrollLength += node . scrollLength ; } node = node . _next ; } this . _size = this . _size || [ 0 , 0 ] ; this . _size [ 0 ] = this . options . size [ 0 ] ; this . _size [ 1 ] = this . options . size [ 1 ] ; this . _size [ this . _direction ] = scrollLength ; } return scrollOffset ; }
Executes the layout and updates the state of the scrollview.
Executes the layout and updates the state of the scrollview .