hgcacheproxymodel/src/hgbuffermanager.cpp
changeset 17 a10844a9914d
parent 7 5ebec3429918
child 20 a60f8b6b1d32
equal deleted inserted replaced
15:1ef5359bf0f4 17:a10844a9914d
    11 *
    11 *
    12 * Contributors:
    12 * Contributors:
    13 *
    13 *
    14 * Description:
    14 * Description:
    15 *
    15 *
    16 *  Version     : %version: 7 %
    16 *  Version     : %version: 10 %
    17 */
    17 */
    18 #include "hgbuffermanager.h"
    18 #include "hgbuffermanager.h"
       
    19 #include "hglogger.h"
    19 #include <hgwidgets/hgcacheproxymodel.h>
    20 #include <hgwidgets/hgcacheproxymodel.h>
    20 
    21 
    21 
    22 
    22 HgBufferManager::HgBufferManager(
    23 HgBufferManager::HgBufferManager(
    23     HgBufferManagerObserver* aObserver,
    24     HgBufferManagerObserver* aObserver,
    24 	int aBufferSize,
    25 	int aBufferSize,
    25 	int aBufferTreshold,
    26 	int aBufferTreshold,
    26 	int aInitialPosition,
    27 	int aInitialPosition,
    27 	int aTotalCount )
    28 	int aTotalCount)
    28 :
    29 :
    29 mObserver(aObserver),
    30 mObserver(aObserver),
    30 mBufferSize( aBufferSize ),
    31 mBufferSize(aBufferSize),
    31 mBufferTreshold( aBufferTreshold ),
    32 mBufferTreshold(aBufferTreshold),
    32 mBufferPosition( aInitialPosition ),
    33 mBufferPosition(aInitialPosition),
    33 mDiff(0),
    34 mDiff(0),
    34 mTotalCount( aTotalCount ),
    35 mTotalCount(aTotalCount),
    35 mResetOrdered(false),
    36 mResetOrdered(false),
    36 mRequestStart(0),
    37 mRequestStart(0),
    37 mRequestCount(0),
    38 mRequestCount(0),
    38 mReleaseStart(0),
    39 mReleaseStart(0),
    39 mReleaseCount(0)
    40 mReleaseCount(0)
    40 {
    41 {
    41     ASSERT( mObserver != 0 );
    42     ASSERT(mObserver != 0);
    42     mBufferPosition -= (mBufferSize / 2);
    43     mBufferPosition -= (mBufferSize/2);
    43     
    44     
    44     if( mBufferPosition + mBufferSize > mTotalCount - 1 ){
    45     if (mBufferPosition + mBufferSize > mTotalCount - 1 ) {
    45         mBufferPosition = (mTotalCount - 1) - mBufferSize;
    46         mBufferPosition = (mTotalCount - 1) - mBufferSize;
    46     }
    47     }
    47     
    48     
    48     if(mBufferPosition < 0 ){
    49     if (mBufferPosition < 0 ) {
    49         mBufferPosition = 0;
    50         mBufferPosition = 0;
    50     }
    51     }
    51     
    52     
    52     mDiff = 0;
    53     mDiff = 0;
    53 	//request Initial Buffer
    54 	//request Initial Buffer
    66 {
    67 {
    67     if (newTreshold != mBufferTreshold){
    68     if (newTreshold != mBufferTreshold){
    68         mBufferTreshold = newTreshold;
    69         mBufferTreshold = newTreshold;
    69     }
    70     }
    70     
    71     
    71     if (newSize!=mBufferSize){
    72     if (newSize!=mBufferSize) {
    72 //        int pos = mBufferPosition + (mBufferSize / 2);
       
    73         
       
    74         int a = Max(0, mBufferPosition + mBufferSize/2 - newSize/2);
    73         int a = Max(0, mBufferPosition + mBufferSize/2 - newSize/2);
    75         int b = Min(a + newSize, mTotalCount);
    74         int b = Min(a + newSize, mTotalCount);
    76         if ( b == mTotalCount){
    75         if (b == mTotalCount) {
    77             a = mTotalCount - newSize;
    76             a = mTotalCount - newSize;
    78         }
    77         }
    79         
    78         
    80         int c = Max(0, mBufferPosition);
    79         int c = Max(0, mBufferPosition);
    81         int d = Min(c + mBufferSize, mTotalCount);
    80         int d = Min(c + mBufferSize, mTotalCount);
    82         if ( d == mTotalCount){
    81         if (d == mTotalCount) {
    83             c = mTotalCount - mBufferSize;
    82             c = mTotalCount - mBufferSize;
    84         }
    83         }
    85         
    84         
    86         if ( newSize>mBufferSize){
    85         if (newSize>mBufferSize) {
    87             mObserver->request(a, c-1, HgCacheProxyModel::HgRequestOrderAscending);
    86             mObserver->request(a, c-1, HgCacheProxyModel::HgRequestOrderAscending);
    88             mObserver->request(d, b-1, HgCacheProxyModel::HgRequestOrderAscending);
    87             mObserver->request(d, b-1, HgCacheProxyModel::HgRequestOrderAscending);
    89         }else if ( newSize<mBufferSize){
    88         }else if (newSize<mBufferSize) {
    90             mObserver->release(c, a-1);
    89             mObserver->release(c, a-1);
    91             mObserver->release(b, d);
    90             mObserver->release(b, d);
    92         }
    91         }
    93         mBufferPosition = a;
    92         mBufferPosition = a;
    94         mBufferSize = newSize;
    93         mBufferSize = newSize;
    97 
    96 
    98 void HgBufferManager::calculate()
    97 void HgBufferManager::calculate()
    99 {  
    98 {  
   100     HgCacheProxyModel::HgRequestOrder direction = HgCacheProxyModel::HgRequestOrderAscending;
    99     HgCacheProxyModel::HgRequestOrder direction = HgCacheProxyModel::HgRequestOrderAscending;
   101     
   100     
   102     if(mResetOrdered){
   101     if (mResetOrdered) {
   103         mResetOrdered = false;
   102         mResetOrdered = false;
   104     } else {
   103     } else {
   105         if(mDiff < 0){
   104         if (mDiff < 0) {
   106             mReleaseStart = mBufferPosition;
   105             mReleaseStart = mBufferPosition;
   107             mRequestStart = mBufferPosition + mBufferSize;
   106             mRequestStart = mBufferPosition + mBufferSize;
   108             direction = HgCacheProxyModel::HgRequestOrderAscending; 
   107             direction = HgCacheProxyModel::HgRequestOrderAscending; 
   109         } else if( mDiff > 0) {
   108         } else if( mDiff > 0) {
   110             mReleaseStart = mBufferPosition + mBufferSize - mDiff;
   109             mReleaseStart = mBufferPosition + mBufferSize - mDiff;
   112             direction = HgCacheProxyModel::HgRequestOrderDescending;
   111             direction = HgCacheProxyModel::HgRequestOrderDescending;
   113         }
   112         }
   114     }
   113     }
   115     
   114     
   116     // Release 
   115     // Release 
   117     int end = mReleaseStart + mReleaseCount < mTotalCount ?
   116     int end = (mReleaseStart + mReleaseCount < mTotalCount)?
   118         mReleaseStart + mReleaseCount: mTotalCount; 
   117         (mReleaseStart + mReleaseCount): mTotalCount; 
   119     end--;
   118     end--;
   120     if(end >= mReleaseStart ){
   119     if (end >= mReleaseStart) {
   121         mObserver->release(mReleaseStart, end);
   120         mObserver->release(mReleaseStart, end);
   122     }
   121     }
   123     
   122     
   124     mReleaseCount = 0;
   123     mReleaseCount = 0;
   125     
   124     
   126     // Request
   125     // Request
   127     end = mRequestStart + mRequestCount < mTotalCount ? 
   126     end = (mRequestStart + mRequestCount < mTotalCount)? 
   128         mRequestStart + mRequestCount : mTotalCount;
   127         (mRequestStart + mRequestCount): mTotalCount;
   129     
   128     
   130     end--;
   129     end--;
   131     if(end >= mRequestStart ){
   130     if (end >= mRequestStart) {
   132         mObserver->request(mRequestStart, end, direction);
   131         mObserver->request(mRequestStart, end, direction);
   133 	}
   132 	}
   134       
   133       
   135     mRequestCount = 0;
   134     mRequestCount = 0;
   136     
   135     
   145 // -----------------------------------------------------------------------------
   144 // -----------------------------------------------------------------------------
   146 //
   145 //
   147 void HgBufferManager::setPosition( int aIndex )
   146 void HgBufferManager::setPosition( int aIndex )
   148 {
   147 {
   149     // If all the items fit in the buffer no need to move the buffer
   148     // If all the items fit in the buffer no need to move the buffer
   150     if(mTotalCount <= mBufferSize)
   149     if (mTotalCount <= mBufferSize)
   151         return;
   150         return;
   152 	
   151 	
   153 	bool forceUpdate = false;
   152 	bool forceUpdate = false;
   154     aIndex -= mBufferSize / 2; // normalize index to Buffer start
   153 	int idx = aIndex - mBufferSize / 2; // normalize index to Buffer start
   155     
   154     
   156     if(aIndex < 0){
   155     if (idx < 0) {
   157         aIndex = 0;
   156         idx = 0;
   158         forceUpdate = true;
   157         forceUpdate = true;
   159     }else if( aIndex > mTotalCount - mBufferSize ){
   158     }else if (idx > mTotalCount - mBufferSize) {
   160         aIndex = mTotalCount - mBufferSize;
   159         idx = mTotalCount - mBufferSize;
   161         forceUpdate = true;
   160         forceUpdate = true;
   162     }
   161     }
   163 
   162 
   164     mDiff = mBufferPosition - aIndex; 
   163     mDiff = mBufferPosition - idx; 
   165 
   164 
   166     // Too large change reset whole buffer
   165     // Too large change reset whole buffer
   167     if( mDiff >= mBufferSize || -mDiff >= mBufferSize || mResetOrdered ) {
   166     if (mDiff >= mBufferSize || -mDiff >= mBufferSize || mResetOrdered) {
   168         resetBuffer(aIndex + (mBufferSize/2), mTotalCount);
   167         resetBuffer(aIndex, mTotalCount);
   169     } else if( mDiff >= mBufferTreshold ) { // Move Up
   168     } else if (mDiff >= mBufferTreshold) { // Move Up
   170         mRequestCount = mDiff;
   169         mRequestCount = mDiff;
   171         mReleaseCount = mDiff;
   170         mReleaseCount = mDiff;
   172         calculate();
   171         calculate();
   173     } else if ( -mDiff >= mBufferTreshold ) {// Move Down
   172     } else if (-mDiff >= mBufferTreshold) {// Move Down
   174         mRequestCount = -mDiff;
   173         mRequestCount = -mDiff;
   175         mReleaseCount = -mDiff;
   174         mReleaseCount = -mDiff;
   176         calculate();
   175         calculate();
   177     } else if( forceUpdate && mDiff ) { // Top or bottom has been reached
   176     } else if (forceUpdate && mDiff) { // Top or bottom has been reached
   178         int diff = mDiff < 0 ? -mDiff : mDiff;
   177         int diff = mDiff < 0 ? -mDiff : mDiff;
   179         mRequestCount = diff;
   178         mRequestCount = diff;
   180         mReleaseCount = diff;
   179         mReleaseCount = diff;
   181         calculate();
   180         calculate();
   182     }
   181     }
   184 
   183 
   185 // -----------------------------------------------------------------------------
   184 // -----------------------------------------------------------------------------
   186 // BufferManager::ResetBuffer()
   185 // BufferManager::ResetBuffer()
   187 // -----------------------------------------------------------------------------
   186 // -----------------------------------------------------------------------------
   188 //
   187 //
   189 void HgBufferManager::resetBuffer( int aPosition, int aTotalCount)
   188 void HgBufferManager::resetBuffer(int aPosition, int aTotalCount)
   190 {
   189 {
   191     if( !mResetOrdered ){
   190     int oldPos = mBufferPosition;
       
   191     if (!mResetOrdered) {
   192         // release Old buffer
   192         // release Old buffer
   193         mReleaseStart = mBufferPosition;
   193         mReleaseStart = mBufferPosition;
   194         mReleaseCount = mBufferSize;
   194         mReleaseCount = mBufferSize;
   195     }
   195     }
       
   196 
       
   197     mTotalCount = aTotalCount;
       
   198     mDiff = 0;
   196     
   199     
   197     // set position and count
   200     // set position and count
   198     mBufferPosition = aPosition - (mBufferSize / 2);
   201     mBufferPosition = aPosition - (mBufferSize / 2);
   199     mTotalCount = aTotalCount;
   202 
   200     mDiff = 0;
   203     if (aPosition < 0) {
   201     
   204         aPosition = 0;
   202     if( mBufferPosition + mBufferSize > mTotalCount - 1 ){
   205     } else if (aPosition >= mTotalCount) {
       
   206         aPosition = mTotalCount - 1;    
       
   207     }
       
   208     
       
   209     if (mBufferPosition + mBufferSize > mTotalCount - 1) {
   203         mBufferPosition = mTotalCount - mBufferSize;
   210         mBufferPosition = mTotalCount - mBufferSize;
   204     }
   211     }
   205     
   212     if (mBufferPosition < 0) {
   206     if(mBufferPosition < 0 ){
       
   207         mBufferPosition = 0;
   213         mBufferPosition = 0;
   208     }
   214     }
   209     
   215     
   210     if (mBufferPosition>1){
   216     mObserver->release(0, mTotalCount);
   211         mObserver->release(0, mBufferPosition-1);
   217     
   212     }
   218 //                  size      size       size   
   213     
   219 //  -------------|---------|---------|---------|------------------
   214     mObserver->request( mBufferPosition, 
   220 //             begin    middle1   middle2     end                          
   215                         mBufferPosition + mBufferSize -1 );
   221     int size = mBufferSize/3;
   216 
   222     int begin = mBufferPosition;
   217     if (mBufferPosition + mBufferSize < mTotalCount){
   223     int middle1 = begin + size;
   218         mObserver->release(mBufferPosition + mBufferSize, mTotalCount);
   224     int middle2 = middle1 + size;
       
   225     int end = mBufferPosition + mBufferSize -1;  //Can not be middle2 + size, mBufferSize/3 can be not equal size
       
   226     
       
   227     TX_LOG_ARGS(QString("aPosition:%0 begin:%1 middle1:%2 c:%3 end:%4").arg(aPosition).arg(begin).arg(middle1).arg(c).arg(end) );
       
   228     
       
   229     if (aPosition >=begin && aPosition < middle1) { //aPosition is in begining, let's load from top
       
   230         mObserver->request(begin, end, HgBufferManagerObserver::HgRequestOrderAscending);
       
   231     } else if (aPosition >= middle1 && aPosition < middle2) {//aPosition is in the middle, let's load from middle
       
   232         HgBufferManagerObserver::HgRequestOrder order = HgBufferManagerObserver::HgRequestOrderAscending;
       
   233         if (oldPos > mBufferPosition) {
       
   234             order = HgBufferManagerObserver::HgRequestOrderDescending;
       
   235         }
       
   236         mObserver->request(middle1, middle2, order);
       
   237         if (order == HgBufferManagerObserver::HgRequestOrderAscending) {
       
   238             mObserver->request(middle2, end, order);
       
   239             mObserver->request(begin, middle1 -1, order);
       
   240         } else {
       
   241             mObserver->request(begin, middle1 -1, order);
       
   242             mObserver->request(middle2, end, order);
       
   243         }
       
   244     } else if (aPosition >= middle2 && aPosition <= end) { //aPosition is in end, let's load from bottom
       
   245         mObserver->request(begin, end, HgBufferManagerObserver::HgRequestOrderDescending);    
   219     }
   246     }
   220     
   247     
   221     mDiff = 0;
   248     mDiff = 0;
   222     mResetOrdered = false;
   249     mResetOrdered = false;
   223     mRequestStart = 0;
   250     mRequestStart = 0;
   227     
   254     
   228 }
   255 }
   229 
   256 
   230 void HgBufferManager::aboutToRemoveItem(int pos)
   257 void HgBufferManager::aboutToRemoveItem(int pos)
   231 {
   258 {
   232     if(pos < 0 || pos >= mTotalCount ){
   259     if (pos < 0 || pos >= mTotalCount) {
   233         return;
   260         return;
   234     }
   261     }
   235     
   262     
   236     if ( pos >= mBufferPosition && pos < mBufferPosition + mBufferSize ){
   263     if (pos >= mBufferPosition && pos < mBufferPosition + mBufferSize) {
   237         mObserver->release(pos, pos);
   264         mObserver->release(pos, pos);
   238     }
   265     }
   239 }
   266 }
   240 
   267 
   241 void HgBufferManager::removedItem(int pos)
   268 void HgBufferManager::removedItem(int pos)
   242 {
   269 {
   243     if(pos < 0 || pos >= mTotalCount ){
   270     if (pos < 0 || pos >= mTotalCount) {
   244         return;
   271         return;
   245     }
   272     }
   246     
   273     
   247     mTotalCount--;
   274     mTotalCount--;
   248     if( mTotalCount >= mBufferSize ){
   275     if (mTotalCount >= mBufferSize) {
   249         if (pos < mBufferPosition){ //before buffer pos is >=0
   276         if (pos < mBufferPosition) { //before buffer pos is >=0
   250             mBufferPosition--;
   277             mBufferPosition--;
   251         } else if (pos >= mBufferPosition && pos < mBufferPosition + mBufferSize){
   278         } else if (pos >= mBufferPosition && pos < mBufferPosition + mBufferSize) {
   252             if( mBufferPosition + mBufferSize <= mTotalCount ){
   279             if (mBufferPosition + mBufferSize <= mTotalCount) {
   253                 // Requested from the end
   280                 // Requested from the end
   254                 mObserver->request( mBufferPosition + mBufferSize - 1,
   281                 mObserver->request(mBufferPosition + mBufferSize - 1,
   255                                     mBufferPosition + mBufferSize - 1 );
   282                                    mBufferPosition + mBufferSize - 1);
   256             }else if( mBufferPosition > 0 ){
   283             }else if (mBufferPosition > 0) {
   257                 // Move buffer and request from the beginning 
   284                 // Move buffer and request from the beginning 
   258                 mBufferPosition--;
   285                 mBufferPosition--;
   259                 mObserver->request( mBufferPosition, 
   286                 mObserver->request(mBufferPosition, mBufferPosition);
   260                                     mBufferPosition );
       
   261             }
   287             }
   262         }
   288         }
   263     }
   289     }
   264 }
   290 }
   265 
   291 
   266 void HgBufferManager::aboutToInsertItem(int pos)
   292 void HgBufferManager::aboutToInsertItem(int pos)
   267 {
   293 {
   268     if(pos < 0 || pos > mTotalCount ){
   294     if (pos < 0 || pos > mTotalCount) {
   269         return;
   295         return;
   270     }
   296     }
   271 
   297 
   272     if ( pos >= mBufferPosition && pos < mBufferPosition + mBufferSize ){
   298     if (pos >= mBufferPosition && pos < mBufferPosition + mBufferSize) {
   273         if( mBufferPosition + mBufferSize < mTotalCount ){
   299         if (mBufferPosition + mBufferSize < mTotalCount) {
   274             // Release from the end of the buffer
   300             // Release from the end of the buffer
   275             mObserver->release(mBufferPosition + mBufferSize - 1, mBufferPosition + mBufferSize - 1);
   301             mObserver->release(mBufferPosition + mBufferSize - 1, mBufferPosition + mBufferSize - 1);
   276         }
   302         }
   277     }
   303     }
   278 }
   304 }
   279 
   305 
   280 void HgBufferManager::insertedItem(int pos)
   306 void HgBufferManager::insertedItem(int pos)
   281 {
   307 {
   282     if(pos < 0 || pos > mTotalCount ){
   308     if ( pos < 0 || pos > mTotalCount) {
   283         return;
   309         return;
   284     }
   310     }
   285 
   311 
   286     mTotalCount++;
   312     mTotalCount++;
   287     if ( pos >= mBufferPosition && pos < mBufferPosition + mBufferSize ){
   313     if (pos >= mBufferPosition && pos < mBufferPosition + mBufferSize) {
   288         mObserver->request(pos, pos);
   314         mObserver->request(pos, pos);
   289     }else if (pos<mBufferPosition){ //if we have inserted item before buffer, we should move buffer.
   315     }else if (pos<mBufferPosition) { //if we have inserted item before buffer, we should move buffer.
   290         mBufferPosition++;
   316         mBufferPosition++;
   291     }
   317     }
   292 }
   318 }
   293 
   319 
   294 //eof
   320 //eof