--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/mulwidgets/muldatamodel/src/muldatawindow.cpp Wed Sep 01 12:23:18 2010 +0100
@@ -0,0 +1,498 @@
+/*
+* Copyright (c) 2007-2008 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description: Implementation of Data window
+*
+*/
+
+
+//Includes
+#include "muldatawindow.h"
+
+#include <stdexcept>
+#include <e32debug.h>
+
+//Internal includes
+#include "mulassert.h"
+#include "mulmodelimpl.h"
+#include "mullog.h"
+
+using namespace std;
+
+namespace Alf
+ {
+
+// ---------------------------------------------------------------------------
+// MulDataWindow
+// ---------------------------------------------------------------------------
+//
+MulDataWindow::MulDataWindow( MulModelImpl& aMulModel )
+ :mMulModel( aMulModel ),
+ mHighlight(KNotInitialized),
+ mItemIndex(KNotInitialized),
+ mOldItemIndex(KNotInitialized),
+ mBufferSize(KNotInitialized),
+ mWindowSize(KNotInitialized),
+ mWindowOffset(KNotInitialized),
+ mWindowTop(0),
+ mWindowBottom(0),
+ mBufferTop(0),
+ mBufferBottom(0),
+ mOldBufferTop(KNotInitialized),
+ mOldBufferBottom(KNotInitialized),
+ mRearBufferTop(0),
+ mRearBufferBottom(0),
+ mOldRearBufferTop(KNotInitialized),
+ mOldRearBufferBottom(KNotInitialized)
+ {
+ }
+
+// ---------------------------------------------------------------------------
+// SetWindowSize
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::SetWindowSize( int aWindowSize )
+ {
+ MUL_LOG_ENTRY_EXIT("MUL::MulDataWindow::SetWindowSize()");
+
+ __MUL_ASSERT( aWindowSize > 0, KLInvalidArgument );
+
+ if( mWindowSize != aWindowSize )
+ {
+ if( KNotInitialized == mBufferSize )
+ {
+ mBufferSize = aWindowSize;
+ }
+
+ mWindowSize = aWindowSize;
+ //devide window half
+ //Try to keep this much item above highlight and below highlight
+ mWindowOffset = mWindowSize / 2;
+
+ //adjusting window offset
+ //if window size changes then the top and bottom offset should be
+ // adjusted such that highlight remains at the centre
+ //window top and bottom are inclusive
+
+ mWindowTop = mItemIndex - mWindowOffset;
+ mWindowTop = mWindowTop < 0 ? 0 : mWindowTop ;
+ mWindowBottom = mWindowTop + mWindowSize - 1;
+ mWindowBottom = mWindowBottom >= mMulModel.CurrentItemCount() ? (mMulModel.CurrentItemCount() -1) : mWindowBottom;
+
+ MUL_LOG_INFO2("MUL::MulDataWindow::SetWindowSize() mWindowTop:%d,mWindowBottom:%d",mWindowTop,mWindowBottom);
+
+ AdjustBuffer();
+ mMulModel.DataWindowUpdated();
+ }
+ //else nothing needed
+ }
+
+// ---------------------------------------------------------------------------
+// SetBufferSize
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::SetBufferSize( int aBufferSize )
+ {
+ MUL_LOG_ENTRY_EXIT("MUL::MulDataWindow::SetBufferSize()");
+
+ __MUL_ASSERT( aBufferSize > 0, KLInvalidArgument );
+
+ if( mBufferSize != aBufferSize )
+ {
+ mBufferSize = aBufferSize;
+
+ if(mMulModel.CurrentItemCount() > 0)
+ {
+ AdjustBuffer();
+ mMulModel.DataWindowUpdated();
+ }
+ }
+ //else nothing needed
+ }
+
+// ---------------------------------------------------------------------------
+// ~MulDataWindow
+// ---------------------------------------------------------------------------
+//
+MulDataWindow::~MulDataWindow()
+ {
+ // do nothing
+ }
+
+// ---------------------------------------------------------------------------
+// SetHighlight
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::SetHighlight( int aHighlightIndex )
+ {
+ MUL_LOG_INFO2("MUL::MulDataWindow::SetHighlight() mHighlight:%d,modelCount:%d",aHighlightIndex,mMulModel.CurrentItemCount());
+
+ __MUL_ASSERT( aHighlightIndex >= 0 && aHighlightIndex <= mMulModel.CurrentItemCount()-1, KLInvalidArgument );
+
+ if( mHighlight != aHighlightIndex )
+ {
+ mHighlight = aHighlightIndex;
+
+ ScrollWindow( mHighlight );
+ }
+ //else same highlight
+ }
+
+
+// ---------------------------------------------------------------------------
+// UpdateHighlight
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::UpdateHighlight( int aHighlightIndex )
+ {
+ // No need to assert. We should send highlight -1 when all the items are removed.
+ // Widget should handle. to show emty text visualization
+ mHighlight = aHighlightIndex;
+ }
+
+// ---------------------------------------------------------------------------
+// ScrollWindow
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::ScrollWindow( int aItemIndex )
+ {
+ MUL_LOG_INFO2("MUL::MulDataWindow::ScrollWindow() aItemIndex:%d,modelCount:%d",aItemIndex,mMulModel.CurrentItemCount());
+
+ __MUL_ASSERT( aItemIndex >= 0 && aItemIndex <= mMulModel.CurrentItemCount()-1, KLInvalidArgument );
+
+ if( mItemIndex != aItemIndex )
+ {
+ mOldItemIndex = mItemIndex;
+ mItemIndex = aItemIndex;
+
+ if(IsWindowEnabled())
+ {
+ UpdateDataWindow();
+ }
+ }
+ //else same highlight
+ }
+
+
+// ---------------------------------------------------------------------------
+// UpdateDataWindow
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::UpdateDataWindow()
+ {
+#ifdef _DEBUG
+ int diff = mItemIndex - mOldItemIndex;
+#endif //_DEBUG
+
+ //If diffrence is negative than highlight is moved up else down
+ (( mItemIndex - mOldItemIndex ) < 0 ) ? ShiftWindowUp() : ShiftWindowDown() ;
+ }
+
+// ---------------------------------------------------------------------------
+// ShiftWindowDown
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::ShiftWindowDown()
+ {
+ MUL_LOG_ENTRY_EXIT("MUL::MulDataWindow::ShiftWindowDown()");
+ MUL_LOG_INFO2("MUL::MulDataWindow::ShiftWindowDown() mItemIndex:%d,mWindowBottom:%d",mItemIndex,mWindowBottom);
+
+ if( mItemIndex > mWindowBottom )
+ {
+ mWindowTop = mItemIndex - mWindowOffset;
+ mWindowBottom = mWindowTop + mWindowSize -1;
+ //bottom is exceeding model count
+ mWindowBottom = mWindowBottom >= mMulModel.CurrentItemCount() ?
+ mWindowBottom = mMulModel.CurrentItemCount() - 1 : mWindowBottom;
+
+ mWindowTop = mWindowBottom - mWindowSize + 1;
+ //top can't be negative
+ mWindowTop = mWindowTop < 0 ? 0 : mWindowTop ;
+
+ MUL_LOG_INFO2("MUL::MulDataWindow::ShiftWindowDown() mWindowTop:%d,mWindowBottom:%d",mWindowTop,mWindowBottom);
+ SaveOldValues();
+ AdjustBuffer();
+ mMulModel.DataWindowUpdated();
+ }
+ //else nothing needed
+ }
+
+// ---------------------------------------------------------------------------
+// ShiftWindowUp
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::ShiftWindowUp()
+ {
+ MUL_LOG_ENTRY_EXIT("MUL::MulDataWindow::ShiftWindowUp() Start");
+ MUL_LOG_INFO2("MUL::MulDataWindow::ShiftWindowUp() mItemIndex:%d,mWindowBottom:%d",mItemIndex,mWindowBottom);
+
+ if( mItemIndex < mWindowTop )
+ {
+ mWindowTop = mItemIndex - mWindowOffset;
+ //top can't be negative
+ mWindowTop = mWindowTop < 0 ? 0 : mWindowTop ;
+
+ mWindowBottom = mWindowTop + mWindowSize -1;
+
+ //bottom cant exceed model count
+ mWindowBottom = mWindowBottom >= mMulModel.CurrentItemCount() ?
+ mWindowBottom = mMulModel.CurrentItemCount() - 1 : mWindowBottom;
+
+ MUL_LOG_INFO2("MUL::MulDataWindow::ShiftWindowUp() mWindowTop:%d,mWindowBottom:%d",mWindowTop,mWindowBottom);
+
+ SaveOldValues();
+ AdjustBuffer();
+ mMulModel.DataWindowUpdated();
+ }
+ //else nothing needed
+ }
+
+// ---------------------------------------------------------------------------
+// AdjustBuffer
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::AdjustBuffer()
+ {
+ MUL_LOG_ENTRY_EXIT("MUL::MulDataWindow::AdjustBuffer()");
+
+ int modelCount = mMulModel.CurrentItemCount() -1;
+
+ //remove data is new window is smaller/add is new window is bigger
+ if( mWindowTop == 0 && ActualBufferSize() <= modelCount )
+ {
+ MUL_LOG_INFO("MUL::MulDataWindow::AdjustBuffer() mWindowTop == 0 ");
+
+ mBufferTop = mWindowTop;
+ mBufferBottom = mBufferTop + mWindowSize + mBufferSize - 1;
+
+ //Create rear top and rear bottom only in looping case
+ //window top is zero so data at other end should be buffered
+ mRearBufferBottom = modelCount;
+ mRearBufferTop = mRearBufferBottom - mBufferSize +1;
+ }
+ else if( mWindowBottom == modelCount && ActualBufferSize() <= modelCount )
+ {
+ MUL_LOG_INFO("MUL::MulDataWindow::AdjustBuffer() mWindowBottom == modelCount ");
+
+ mBufferBottom = mWindowBottom ;
+ mBufferTop = mBufferBottom - (mWindowSize + mBufferSize) + 1;
+
+ //Create rear top and rear bottom only in looping case
+ //window bottom is equal to model count so data at other end should be buffered
+ mRearBufferTop = 0;
+ mRearBufferBottom = mRearBufferTop + mBufferSize -1;
+ }
+ else
+ {
+ MUL_LOG_INFO("MUL::MulDataWindow::AdjustBuffer() else ");
+
+ mBufferTop = mWindowTop - mBufferSize;
+ mBufferBottom = mWindowBottom + mBufferSize;
+
+ //check if top or bottom is out of bound and update offset accordingly
+ if( mBufferTop < 0 )
+ {
+ MUL_LOG_INFO("MUL::MulDataWindow::AdjustBuffer() mBufferTop < 0 ");
+
+ mBufferTop = 0;
+ mBufferBottom = mBufferTop + ActualBufferSize() - 1;
+ //buffer bottom cant be larger then model count
+ mBufferBottom = mBufferBottom > modelCount ? modelCount : mBufferBottom;
+ }
+ else if( mBufferBottom > modelCount )
+ {
+ MUL_LOG_INFO("MUL::MulDataWindow::AdjustBuffer() mBufferBottom > modelCount");
+
+ mBufferBottom = modelCount ;
+ mBufferTop = mBufferBottom - ActualBufferSize() + 1;
+ //buffer top cant be less then 0
+ mBufferTop = mBufferTop < 0 ? 0 : mBufferTop;
+ }
+
+ //in other case rear top and rear bottom is not use set to -1
+ mRearBufferTop = KNotInitialized;
+ mRearBufferBottom = KNotInitialized;
+ }
+
+ MUL_LOG_INFO2("MUL::MulDataWindow::AdjustBuffer() mOldBufferTop:%d,mOldBufferBottom:%d",mOldBufferTop,mOldBufferBottom);
+ MUL_LOG_INFO2("MUL::MulDataWindow::AdjustBuffer() mOldRearBufferBottom:%d,mOldRearBufferTop:%d",mOldRearBufferBottom,mOldRearBufferTop);
+
+ MUL_LOG_INFO2("MUL::MulDataWindow::AdjustBuffer() mBufferTop:%d,mBufferBottom:%d",mBufferTop,mBufferBottom);
+ MUL_LOG_INFO2("MUL::MulDataWindow::AdjustBuffer() mRearBufferBottom:%d,mRearBufferTop:%d",mRearBufferBottom,mRearBufferTop);
+
+ __MUL_ASSERT_DEBUG( mWindowTop >= 0 && mWindowBottom < mMulModel.CurrentItemCount(), _L("Invlid Window"));
+ __MUL_ASSERT_DEBUG( mBufferTop >= 0 && mBufferBottom < mMulModel.CurrentItemCount(), _L("Invlid Buffer"));
+ }
+
+// ---------------------------------------------------------------------------
+// IsItemInDataWindow
+// ---------------------------------------------------------------------------
+//
+bool MulDataWindow::IsItemInDataWindow(int aItemIndex ) const
+ {
+ //__MUL_ASSERT_DEBUG( aItemIndex >= 0 && aItemIndex <= mMulModel.CurrentItemCount()-1, KLInvalidArgument );
+
+ bool result( false );
+
+ if(mWindowSize == KNotInitialized )
+ {
+ result = false;
+ }
+ //check that rear buffer is on or not in looping case
+ else if( mRearBufferTop != KNotInitialized && mRearBufferBottom != KNotInitialized )
+ {
+ if( ( aItemIndex >= mBufferTop && aItemIndex <= mBufferBottom ) ||
+ ( aItemIndex >= mRearBufferTop && aItemIndex <= mRearBufferBottom ) )
+ {
+ result = true;
+ }
+ }
+ else if( aItemIndex >= mBufferTop && aItemIndex <= mBufferBottom )
+ {
+ result = true;
+ }
+ return result;
+ }
+
+
+// ---------------------------------------------------------------------------
+// RelativeIndex
+// ---------------------------------------------------------------------------
+//
+int MulDataWindow::RelativeIndex( int aAbsoluteIndex ) const
+ {
+ __MUL_ASSERT_DEBUG( aAbsoluteIndex >= 0 && aAbsoluteIndex <= mMulModel.CurrentItemCount()-1, KLInvalidArgument );
+
+ if( !IsItemInDataWindow(aAbsoluteIndex) )
+ {
+ return -1;
+ }
+
+ if( mRearBufferTop != KNotInitialized && mRearBufferBottom != KNotInitialized )
+ {
+ if( mRearBufferBottom == mMulModel.CurrentItemCount() - 1 )
+ {
+ if( aAbsoluteIndex >= mRearBufferTop && aAbsoluteIndex <= mRearBufferBottom )
+ {
+ int bufferSize = BottomOffset() - TopOffset() + 1;
+ int rearDiff = aAbsoluteIndex - mRearBufferTop;
+ int relativeIndex = bufferSize + rearDiff;
+ return relativeIndex;
+ }
+ else
+ {
+ int relativeIndex = aAbsoluteIndex < TopOffset() ?
+ aAbsoluteIndex : aAbsoluteIndex - TopOffset() ;
+ return relativeIndex;
+ }
+ }
+ else
+ {
+ if( aAbsoluteIndex >= mRearBufferTop && aAbsoluteIndex <= mRearBufferBottom )
+ {
+ int relativeIndex = aAbsoluteIndex < TopOffset() ?
+ aAbsoluteIndex : aAbsoluteIndex - TopOffset() ;
+ return relativeIndex;
+ }
+ else
+ {
+ int bufferSize = mRearBufferBottom - mRearBufferTop + 1;
+ int diff = aAbsoluteIndex - TopOffset();
+ int relativeIndex = bufferSize + diff;
+ return relativeIndex;
+ }
+ }
+ }
+ else
+ {
+ int relativeIndex = aAbsoluteIndex < TopOffset() ?
+ aAbsoluteIndex : aAbsoluteIndex - TopOffset() ;
+ return relativeIndex;
+ }
+ }
+
+// ---------------------------------------------------------------------------
+// AbsoluteIndex
+// ---------------------------------------------------------------------------
+//
+int MulDataWindow::AbsoluteIndex( int aRelativeIndex ) const
+ {
+ __MUL_ASSERT_DEBUG( aRelativeIndex >= 0 && aRelativeIndex <= ActualBufferSize(), _L("Invalid Relative Index"));
+
+ if( mRearBufferTop != KNotInitialized && mRearBufferBottom != KNotInitialized )
+ {
+ if( mRearBufferBottom == mMulModel.CurrentItemCount() - 1 )
+ {
+ if( aRelativeIndex > BottomOffset() )
+ {
+ //relative index is in loop buffer
+ int diff = aRelativeIndex - BottomOffset() - 1;
+ int absoluteIndex = RearTopOffset() + diff;
+ return absoluteIndex;
+ }
+ else
+ {
+ int absoluteIndex = TopOffset() + aRelativeIndex;
+ return absoluteIndex;
+ }
+ }
+ else
+ {
+ if( aRelativeIndex <= RearBottomOffset() )
+ {
+ //relative index is in loop buffer
+ int absoluteIndex = RearTopOffset() + aRelativeIndex;
+ return absoluteIndex;
+ }
+ else
+ {
+ int diff = aRelativeIndex - RearBottomOffset() - 1;
+ int absoluteIndex = TopOffset() + diff;
+ return absoluteIndex;
+ }
+ }
+ }
+ else
+ {
+ int absoluteIndex = TopOffset() + aRelativeIndex;
+ return absoluteIndex;
+ }
+ }
+
+// ---------------------------------------------------------------------------
+// SetVisibleWindow
+// ---------------------------------------------------------------------------
+//
+void MulDataWindow::SetVisibleWindow(int aWindowTop, int aWindowBottom)
+ {
+ mWindowTop = aWindowTop;
+ mWindowBottom = aWindowBottom;
+ }
+
+// ---------------------------------------------------------------------------
+// IsBufferOffsetChanged
+// ---------------------------------------------------------------------------
+//
+bool MulDataWindow::IsBufferOffsetChanged()
+ {
+ if(mRearBufferBottom != mOldRearBufferBottom || mRearBufferTop != mOldRearBufferTop
+ || mBufferTop != mOldBufferTop || mBufferBottom != mOldBufferBottom)
+ {
+ return true;
+ }
+ return false;
+ }
+
+ } // namespace Alf
+
+//End of file