--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/javauis/lcdui_akn/lcdui/src/CMIDTicker.cpp Wed Sep 01 12:33:18 2010 +0100
@@ -0,0 +1,1235 @@
+/*
+* Copyright (c) 2006 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 the Ticker component
+*
+*/
+
+
+#include <eikenv.h>
+#include <coecntrl.h>
+#include <coeccntx.h>
+#include <coecobs.h>
+// needed API for iAvkonAppUi
+#include <aknappui.h>
+#include <AknsUtils.h>
+#include <aknconsts.h>
+
+//#include <aknlayoutdef.h>
+//#include <aknlayout.lag>
+// CAknLayoutFont API for font layouting
+#include <AknLayoutFont.h>
+
+#include <aknenv.h>
+// CAknIndicatorContainer API for updating text capacity indicator
+#include <AknIndicatorContainer.h>
+// MAknEditingStateIndicator API for updating text capacity indicator
+// and setting state to edit indicators
+#include <aknEditStateIndicator.h>
+#include <aknnavi.h>
+// CAknNavigationDecorator* iNaviDecorator
+#include <aknnavide.h>
+
+#include <AknsDrawUtils.h>
+#include <j2me/jdebug.h>
+#include "CMIDTicker.h"
+// needed for setting and removing displayables (iDisplayableRArray)
+#include "CMIDDisplayable.h"
+// CMIDUtils::MapJavaToETextChars in CMIDScrollingText::SetTextL
+#include "CMIDUtils.h"
+#include "CMIDUIManager.h"
+
+/**
+ * To enable ticker tracing, uncomment the follwing two lines and link
+ * to estlib.lib:
+ *
+ *#include <stdio.h>
+ *#define TRACE_TICKER 1
+ */
+
+/** Time between each tick.*/
+const TInt KTickPeriod = 40000;
+
+/** Scrolling width in pixels where increment increases*/
+const TInt KScrollingWidthLimit = 200;
+
+/** Increment values for two different scrolling widths*/
+const TInt KOnePixel = 1;
+const TInt KTwoPixels = 2;
+
+_LIT(KLeftSquareBracket, "[");
+_LIT(KRightSquareBracket, "]");
+_LIT(KTextCapacity, "(999) ");
+
+_LIT(KLeftSmalllBracket, "(");
+_LIT(KRightSmallBracket, ")");
+
+#ifdef _DEBUG
+#define DEBUG_ARG(x) x
+#else
+#define DEBUG_ARG(x)
+#endif
+
+//
+// Private helper functions
+//
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CleanupTicker(TAny* aTicker)
+{
+ static_cast< CMIDTicker* >(aTicker)->Dispose();
+}
+
+
+// ---------------------------------------------------------------------------
+// Return the navi pane container. The method trapped should not leave.
+// ---------------------------------------------------------------------------
+//
+CAknNavigationControlContainer* NaviContainerL()
+{
+ CEikStatusPane *sp = iAvkonAppUi->StatusPane();
+ CAknNavigationControlContainer* naviC =
+ static_cast<CAknNavigationControlContainer*>(sp->ControlL(TUid::Uid(EEikStatusPaneUidNavi)));
+
+ return naviC;
+}
+
+// ---------------------------------------------------------------------------
+// Return a text layout defined in the platform LAF
+// for text to be shown in the navi pane. According to the
+// type of navi pane control the text layout may be different.
+// We have chosen to use the same layout as the edit indicator
+// text (the text showing how many chars are left in an editor).
+// To use the layout used by navi pane labels use
+// Navi_pane_texts_Line_1. This layout information determines the
+// font and the text color. Text positioning is not taken from
+// layout, the text is vertically centered and scrolled horizontally
+// instead, h aligned to the left or right of the navi pane according
+// to the directionality.
+// ---------------------------------------------------------------------------
+//
+const TAknTextLineLayout Layout()
+{
+ return AknLayout::Small_status_pane_texts_Line_1(0);
+}
+
+// ---------------------------------------------------------------------------
+// Return the text alignment according to locale alignment
+// ---------------------------------------------------------------------------
+//
+CGraphicsContext::TTextAlign TextAlign()
+{
+ return AknLayoutUtils::LayoutMirrored() ? CGraphicsContext::ERight : CGraphicsContext::ELeft;
+}
+
+//
+// class CMIDTickerController
+//
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+CMIDNaviPaneController* CMIDNaviPaneController::NewL()
+{
+ CMIDNaviPaneController* self=new(ELeave) CMIDNaviPaneController();
+ CleanupStack::PushL(self);
+ self->ConstructL();
+ CleanupStack::Pop(self);
+ return self;
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+CMIDNaviPaneController::~CMIDNaviPaneController()
+{
+ delete iTickerTimer;
+ iTickerTimer = NULL;
+ delete iEditCapacityText;
+ iTickerObservers.Close();
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+CMIDNaviPaneController::CMIDNaviPaneController()
+{
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::ConstructL()
+{
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::UpdateTextInputIndicatorL(TInt aCount)
+{
+ delete iEditCapacityText;
+ iEditCapacityText = NULL;
+
+ if (aCount >= 0 && aCount <= 999)
+ {
+ const CFont* font = AknLayoutUtils::FontFromId(Layout().FontId());
+ TBuf<10> text;
+
+ text.Append(KLeftSmalllBracket);
+ text.AppendNum(aCount);
+ text.Append(KRightSmallBracket);
+
+ // set text localized (non Latin numbers)
+ AknTextUtils::LanguageSpecificNumberConversion(text);
+
+ iEditCapacityText = TBidiText::NewL(text,1);
+ iEditCapacityText->WrapText(font->TextWidthInPixels(KTextCapacity), *font, NULL);
+
+ AddEditCapacityTextToNaviPaneL();
+ }
+ else
+ {
+ // to prevent panic if state indicator is NULL (it can happen when 3rd party FEP is active)
+ MAknEditingStateIndicator* indicator = CAknEnv::Static()->EditingStateIndicator();
+ if (indicator)
+ {
+ indicator->IndicatorContainer()->SetIndicatorState(
+ TUid::Uid(EAknNaviPaneEditorIndicatorMessageLength),
+ EAknIndicatorStateOff);
+ }
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+TBidiText* CMIDNaviPaneController::EditCapacityText() const
+{
+ return iEditCapacityText;
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::AddTickerObserverL(
+ MMIDTickerObserver* aObserver)
+{
+ ASSERT(aObserver);
+ if (iTickerObservers.Find(aObserver) == KErrNotFound)
+ {
+ User::LeaveIfError(iTickerObservers.Append(aObserver));
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::RemoveTickerObserver(
+ MMIDTickerObserver* aObserver)
+{
+ ASSERT(aObserver);
+ TInt index = iTickerObservers.Find(aObserver);
+ if (index != KErrNotFound)
+ {
+ iTickerObservers.Remove(index);
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::SetTickerL(CMIDTicker* aTicker)
+{
+ if (!iTickerTimer && !aTicker)
+ {
+ // CMIDTickerTimer instance is created only when
+ // a ticker object is set
+ return;
+ }
+ if (!iTickerTimer)
+ {
+ iTickerTimer = CMIDTickerTimer::NewL(this);
+ }
+ iTickerTimer->SetTickerL(aTicker);
+}
+
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::ShowTickerL(TBool aShow)
+{
+ if (iTickerTimer)
+ {
+ iTickerTimer->ShowTickerL(aShow);
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::PauseTickerL(
+ TInt aInterval, MMIDTickerObserver* aPausingObserver)
+{
+ if (aInterval > 0)
+ {
+ // Set last observer to pause the ticker
+ iPausingObserver = aPausingObserver;
+ }
+ if (iTickerTimer)
+ {
+ iTickerTimer->PauseTickerL(aInterval, aPausingObserver);
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::TickerChangedL(CMIDTicker* aTicker, TTickerEvent aEvent)
+{
+ if (iTickerTimer)
+ {
+ iTickerTimer->TickerChangedL(aTicker, aEvent);
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::LayoutTickerL()
+{
+ if (iTickerTimer)
+ {
+ iTickerTimer->LayoutTickerL();
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::ResetTickerScrollingSpeedL()
+{
+ if (iTickerTimer)
+ {
+ iTickerTimer->ResetScrollingSpeedL();
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::NotifyTickerObservers(TBool aShowing)
+{
+ TInt numObservers = iTickerObservers.Count();
+ for (TInt index = 0; index < numObservers; index++)
+ {
+ iTickerObservers[ index ]->TickerShowing(aShowing);
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDNaviPaneController::AddEditCapacityTextToNaviPaneL()
+{
+ if (iEditCapacityText != NULL &&
+ (!iTickerTimer ||
+ !iTickerTimer->iEnabled ||
+ !iTickerTimer->iTicker))
+ {
+ // to prevent panic if state indicator is NULL (it can happen when 3rd party FEP is active)
+ MAknEditingStateIndicator* indicator = CAknEnv::Static()->EditingStateIndicator();
+ if (indicator)
+ {
+ indicator->IndicatorContainer()->SetIndicatorState(
+ TUid::Uid(EAknNaviPaneEditorIndicatorMessageLength), EAknIndicatorStateOn);
+ indicator->IndicatorContainer()->SetIndicatorValueL(
+ TUid::Uid(EAknNaviPaneEditorIndicatorMessageLength), iEditCapacityText->Text());
+ }
+ }
+}
+
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+CMIDTickerTimer* CMIDTickerTimer::NewL(CMIDNaviPaneController* aController)
+{
+ CMIDTickerTimer* self=new(ELeave) CMIDTickerTimer(aController);
+ CleanupStack::PushL(self);
+ self->ConstructL();
+ CleanupStack::Pop(self);
+ return self;
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+CMIDTickerTimer::~CMIDTickerTimer()
+{
+ DEBUG("CMIDTickerTimer::~CMIDTickerTimer - calling StopL");
+ TRAPD(ignore,StopL());
+ if (ignore != KErrNone)
+ {
+ DEBUG_INT("CMIDTickerTimer::~CMIDTickerTimer - Exception from StopL. Error = %d", ignore);
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+CMIDTickerTimer::CMIDTickerTimer(CMIDNaviPaneController* aCtrl)
+ : CTimer(CActive::EPriorityHigh)
+ , iCtrl(aCtrl)
+ , iTicker(NULL)
+ , iEnabled(EFalse)
+ , iIncrement(KOnePixel)
+{
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::ConstructL()
+{
+ CTimer::ConstructL();
+ ResetScrollingSpeedL();
+ CActiveScheduler::Add(this);
+}
+
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::RunL()
+{
+ if (iIsPaused)
+ {
+ iIsPaused = EFalse;
+ StartL();
+ return;
+ }
+
+ if (iTicker)
+ {
+ iTicker->TickL(iIncrement);
+ Kick();
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::TickerChangedL(
+ CMIDTicker* aTicker, CMIDNaviPaneController::TTickerEvent aEvent)
+{
+ ASSERT(aTicker == iTicker);
+ (void)aTicker; // Just to suppress warning in release build
+ switch (aEvent)
+ {
+ case CMIDNaviPaneController::ENone:
+ case CMIDNaviPaneController::EModelChanged:
+ // ignore
+ break;
+ case CMIDNaviPaneController::ETextChanged:
+ break;
+
+ case CMIDNaviPaneController::EPositionChanged:
+ iTicker->RenderL();
+ break;
+ }
+}
+
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::ShowTickerL(TBool aShow)
+{
+ if (aShow)
+ {
+ StartL();
+ }
+ else
+ {
+ StopL();
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::SetTickerL(CMIDTicker* aTicker)
+{
+ if (iTicker != aTicker)
+ {
+ if (iTicker)
+ {
+ iTicker->StopL();
+ iTicker->SetController(NULL);
+ iTicker->RemoveRef();
+ }
+
+ iTicker = aTicker;
+
+ if (iTicker)
+ {
+ iTicker->AddRef();
+ iTicker->SetController(iCtrl);
+ }
+ }
+ else
+ {
+ if (iTicker)
+ {
+ iTicker->PauseL();
+ }
+ }
+
+ // If the ticker is paused for textfield and textbox and displayable is changed
+ // cancel the pause timer and start the ticker
+ if (iIsPaused)
+ {
+ Cancel();
+ }
+
+ CheckedStart();
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::PauseTickerL(TInt aInterval, MMIDTickerObserver* aPausingObserver)
+{
+ if (aInterval <= 0)
+ {
+ if (iCtrl->iPausingObserver == aPausingObserver)
+ { //only last requesting pausing observer can annulate request
+ iIsPaused = EFalse;
+ StartL();
+ }
+ }
+ else
+ {
+ PauseL();
+ After(aInterval);
+ iIsPaused = ETrue;
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::StartL()
+{
+ Cancel();
+
+ iEnabled = ETrue;
+ iCtrl->NotifyTickerObservers(iEnabled && iTicker);
+
+ if (iTicker)
+ {
+ iTicker->StartL();
+ }
+
+ iCtrl->iPausingObserver = NULL;
+ iIsPaused = EFalse;
+
+ CheckedStart();
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::PauseL()
+{
+ Cancel();
+
+ iEnabled = EFalse;
+ iCtrl->NotifyTickerObservers(iEnabled);
+
+ if (iTicker)
+ {
+ iTicker->PauseL();
+ }
+
+ iCtrl->AddEditCapacityTextToNaviPaneL();
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::StopL()
+{
+ iEnabled = EFalse;
+ iCtrl->NotifyTickerObservers(iEnabled);
+
+ if (iTicker)
+ {
+ iTicker->StopL();
+ }
+
+ iCtrl->AddEditCapacityTextToNaviPaneL();
+
+ Cancel();
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::CheckedStart()
+{
+ if (!iEnabled)
+ {
+ return;
+ }
+ if (NULL == iTicker)
+ {
+ return;
+ }
+
+ if (!IsActive())
+ {
+ Kick();
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::Kick()
+{
+ ASSERT(iEnabled);
+ ASSERT(iTicker);
+ if (!IsActive())
+ {
+ After(KTickPeriod);
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::LayoutTickerL()
+{
+ ResetScrollingSpeedL();
+ if (iTicker)
+ {
+ iTicker->LayoutL();
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTickerTimer::ResetScrollingSpeedL()
+{
+ if (CMIDScrollingText::ScrollingWidthL() <= KScrollingWidthLimit)
+ {
+ iIncrement = KOnePixel;
+ }
+ else
+ {
+ iIncrement = KTwoPixels;
+ }
+}
+
+//
+// class CMIDTicker
+//
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+MMIDTicker* CMIDTicker::NewL(const TDesC& aText)
+{
+ CMIDTicker* ticker = new(ELeave) CMIDTicker;
+ CleanupStack::PushL(TCleanupItem(CleanupTicker, ticker));
+ ticker->ConstructL(aText);
+ CleanupStack::Pop();
+ return ticker;
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+CMIDTicker::CMIDTicker() :
+ iRefCount(1)
+{
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+CMIDTicker::~CMIDTicker()
+{
+ DEBUG("CMIDTicker::~CMIDTicker - calling StopL and RemoveDisplayableFromArrayL");
+ TRAPD(ignore, StopL(); RemoveDisplayableFromArrayL(NULL));
+ if (ignore != KErrNone)
+ {
+ DEBUG_INT("CMIDTicker::~CMIDTicker - Exception from StopL or RemoveDisplayableFromArrayL. Error = %d", ignore);
+ }
+ iDisplayableRArray.Reset();
+ iDisplayableRArray.Close();
+
+ delete iNaviDecorator;
+ iNaviScrollingText = NULL; //deleted by navi decorator
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::ConstructL(const TDesC& aText)
+{
+ CAknNavigationControlContainer* naviC = NaviContainerL();
+
+ iNaviScrollingText = CMIDScrollingText::NewL(this,aText);
+ iNaviScrollingText->SetContainerWindowL(*naviC);
+ iNaviScrollingText->SetExtent(TPoint(0,0), naviC->Size());
+
+ iNaviDecorator = CAknNavigationDecorator::NewL(naviC, iNaviScrollingText, CAknNavigationDecorator::ENotSpecified);
+ iNaviDecorator->SetContainerWindowL(*naviC);
+ iNaviDecorator->MakeScrollButtonVisible(EFalse);
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::Dispose()
+{
+ if (iController)
+ {
+ TRAPD(ignore, iController->SetTickerL(NULL));
+ if (ignore != KErrNone)
+ {
+ DEBUG_INT("CMIDTicker::Dispose - Exception from CMIDNaviPaneController::SetTickerL(NULL). Error = %d", ignore);
+ }
+ }
+ delete this;
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::SetTextL(const TDesC& aText)
+{
+ iNaviScrollingText->SetTextL(aText);
+}
+
+void CMIDTicker::AddRef()
+{
+ ++iRefCount;
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::RemoveRef()
+{
+ ASSERT(iRefCount);
+ --iRefCount;
+ if (0 == iRefCount)
+ {
+ delete this;
+ }
+}
+
+// ---------------------------------------------------------------------------
+//
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::SetDisplayableL(CMIDDisplayable* aDisplayable, TInt aAdd)
+{
+ ASSERT(aDisplayable);
+
+ if (aAdd)
+ { //KAddDisplayable:
+ iDisplayableRArray.AppendL(aDisplayable);
+ }
+ else
+ {
+ RemoveDisplayableFromArrayL(aDisplayable);
+ }
+}
+
+// ---------------------------------------------------------------------------
+// if aDisplayable is not null then remove it
+// if aDisplayable is NULL mean remove all
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::RemoveDisplayableFromArrayL(CMIDDisplayable* aDisplayable)
+{
+ // if aDisplayable is not null then remove it.
+ if (aDisplayable)
+ {
+ TInt index = iDisplayableRArray.Find(aDisplayable);
+ if (index != KErrNotFound)
+ {
+ CMIDDisplayable* displayable = iDisplayableRArray[index];
+ iDisplayableRArray.Remove(index);
+ displayable->SetTickerL(NULL);
+ }
+ }
+ else
+ {// if aDisplayable is null mean remove all
+ TInt count = iDisplayableRArray.Count();
+ for (TInt ii = 0; ii<count; ii++)
+ {
+ // Always remove the Zeroth element as we are removing
+ // the element array size is changing (reducing).
+ CMIDDisplayable* displayable = iDisplayableRArray[0]; // index zero is required
+ iDisplayableRArray.Remove(0);// index zero is required
+ displayable->SetTickerL(NULL);
+ }
+ }
+}
+
+// ---------------------------------------------------------------------------
+// Start the ticker: we must disable any edit indicators (this is done by observers
+// but there is an observer, CDateFieldItem, which uses an editor (CEikMfne) which is not
+// FEP aware and hence cannot disable the edit indicators at the right time. So we have to
+// do it in here instead. The push the navi decorator on the navi pane. This will assure
+// our scrolling text will be drawn. */
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::StartL()
+{
+ if (iNaviScrollingText->Size() == TSize(0,0))
+ {
+ iNaviScrollingText->SetExtent(TPoint(0,0), NaviContainerL()->Size());
+ iNaviScrollingText->UpdateTickerLayoutL();
+ }
+
+ // to prevent panic if state indicator is NULL (it can happen when 3rd party FEP is active)
+ MAknEditingStateIndicator* indicator = CAknEnv::Static()->EditingStateIndicator();
+ if (indicator)
+ {
+ indicator->SetState(EStateNone);
+ }
+ NaviContainerL()->PushL(*iNaviDecorator);
+ iNaviScrollingText->SetPaused(EFalse);
+}
+
+// ---------------------------------------------------------------------------
+// Pause the ticker, inform ScrollingText about pause mode, and remove our
+// navi decorator from the navi pane. */
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::PauseL()
+{
+ iNaviScrollingText->SetPaused(ETrue);
+ NaviContainerL()->Pop(iNaviDecorator);
+}
+
+
+// ---------------------------------------------------------------------------
+// Stop the ticker: just remove our navi decorator from the navi pane. */
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::StopL()
+{
+ NaviContainerL()->Pop(iNaviDecorator);
+ iNaviScrollingText->SetPaused(EFalse);
+}
+
+// ---------------------------------------------------------------------------
+// The text position is updated every tick, this achieves text scrolling. */
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::TickL(TInt aIncrement)
+{
+ iNaviScrollingText->UpdateTextPositionL(aIncrement);
+}
+
+void CMIDTicker::SetController(CMIDNaviPaneController* aController)
+{
+ iController = aController;
+}
+
+CMIDNaviPaneController* CMIDTicker::Controller() const
+{
+ return iController;
+}
+
+void CMIDTicker::ReportEventL(CMIDNaviPaneController::TTickerEvent aEvent)
+{
+ if (iController)
+ {
+ iController->TickerChangedL(this, aEvent);
+ }
+}
+
+// ---------------------------------------------------------------------------
+// Relayout ScrollingText, cancel pause mode.
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::LayoutL()
+{
+ iNaviScrollingText->SetPaused(EFalse);
+ iNaviScrollingText->UpdateTickerLayoutL();
+}
+
+// ---------------------------------------------------------------------------
+// Redraw the status pane (out scrolling text is transparent so we need
+// the status pane to draw the navi pane background for us)
+// ---------------------------------------------------------------------------
+//
+void CMIDTicker::RenderL()
+{
+ iAvkonAppUi->StatusPane()->DrawNow();
+}
+
+//
+// CMIDScrollingText
+//
+
+CMIDScrollingText* CMIDScrollingText::NewL(CMIDTicker* aParent, const TDesC& aText)
+{
+ CMIDScrollingText* self = new(ELeave) CMIDScrollingText(aParent);
+ CleanupStack::PushL(self);
+ self->ConstructL(aText);
+ CleanupStack::Pop(self);
+ return self;
+}
+
+CMIDScrollingText::~CMIDScrollingText()
+{
+ delete iPictographInterface;
+ delete iText;
+}
+
+void CMIDScrollingText::UpdateTickerLayoutL()
+{
+ const CFont* font = AknLayoutUtils::FontFromId(Layout().FontId());
+ const CAknLayoutFont* layoutFont = CAknLayoutFont::AsCAknLayoutFontOrNull(font);
+
+ if (layoutFont)
+ {
+ iBaseLineOffset = (iSize.iHeight - layoutFont->TextPaneHeight())/2 + layoutFont->TextPaneTopToBaseline();
+ }
+ else
+ {
+ iBaseLineOffset = (iSize.iHeight - font->HeightInPixels())/2 + font->AscentInPixels();
+ }
+
+ iTextWidth = font->TextWidthInPixels(iText->Text());
+
+ if (!iPaused)
+ {
+ InitialiseScrollingTextPosition();
+ }
+}
+
+void CMIDScrollingText::SetPaused(TBool aPause)
+{
+ iPaused = aPause;
+}
+
+void CMIDScrollingText::SetTextL(const TDesC& aText)
+{
+ HBufC* buf = aText.AllocL();
+ CMIDUtils::MapJavaToETextChars(buf,EFalse);
+ delete iText;
+ iText = NULL;
+ iText = TBidiText::NewL(buf->Des(),1);
+
+ UpdateTickerLayoutL();
+}
+
+// ---------------------------------------------------------------------------
+// Static method returning an estimate of the scrolling width -
+// this must be the same for all tickers
+// ---------------------------------------------------------------------------
+//
+TInt CMIDScrollingText::ScrollingWidthL()
+{
+ const CFont* font = AknLayoutUtils::FontFromId(Layout().FontId());
+
+ TInt w = NaviContainerL()->Size().iWidth;
+ w -= (font->TextWidthInPixels(KLeftSquareBracket) + font->TextWidthInPixels(KRightSquareBracket));
+
+ return w;
+}
+
+CMIDScrollingText::CMIDScrollingText(CMIDTicker* aParent) : iParent(aParent)
+{
+}
+
+void CMIDScrollingText::ConstructL(const TDesC& aText)
+{
+ SetTextL(aText);
+
+ iPictographInterface = CAknPictographInterface::NewL(*this,*this);
+}
+
+// ---------------------------------------------------------------------------
+// Draw the text. Either "[ ... ]" or "(999) [ .. ]" where ... or .. is the
+// scrolling text. Or if device is Right to Left: either "[ ... ]" or "[..] (999)" */
+// ---------------------------------------------------------------------------
+//
+void CMIDScrollingText::Draw(const TRect& aRect) const
+{
+ TAknTextLineLayout layout = Layout();
+
+ CMIDNaviPaneController* controller = iParent->Controller();
+ const CFont* font = AknLayoutUtils::FontFromId(layout.FontId());
+ CWindowGc& gc = SystemGc();
+
+ gc.SetPenColor(TextColor());
+ gc.UseFont(font);
+
+
+ //draw edit capacity text, eg "(999)" if needed
+ if (controller && controller->EditCapacityText() != NULL)
+ {
+ gc.DrawText(controller->EditCapacityText()->Text(), aRect, iBaseLineOffset, TextAlign(), 0);
+ }
+
+ //draw "["
+ gc.DrawText(KLeftSquareBracket, TPoint(LeftTextPosition(font)
+ - font->TextWidthInPixels(KLeftSquareBracket),iBaseLineOffset));
+
+ //draw "]"
+ gc.DrawText(KRightSquareBracket,TPoint(RightTextPosition(font),iBaseLineOffset));
+
+
+ //clip area for scrolling text
+ gc.SetClippingRect(TRect(TPoint(LeftTextPosition(font), 0), TPoint(RightTextPosition(font), iSize.iHeight)));
+
+ //draw scrolling text
+ iText->WrapText(iTextWidth, *font,0);
+ if (iPictographInterface)
+ {
+ MAknPictographDrawer* aknPictographDrawer = iPictographInterface->Interface();
+ aknPictographDrawer->DrawText(gc, *font, iText->DisplayText(),
+ TPoint(iTextPosition,iBaseLineOffset));
+ }
+ else
+ {
+ iText->DrawText(gc, TPoint(iTextPosition,iBaseLineOffset));
+ }
+
+ gc.CancelClippingRect();
+}
+
+void CMIDScrollingText::HandleResourceChange(TInt aType)
+{
+ CCoeControl::HandleResourceChange(aType);
+ if (aType==KEikDynamicLayoutVariantSwitch || aType == KEikColorResourceChange)
+ {
+ if (aType == KEikDynamicLayoutVariantSwitch && iParent && iParent->Controller())
+ {//change scrolling velocity if needed
+ DEBUG("CMIDScrollingText::HandleResourceChange - calling iParent->Controller()->ResetScrollingSpeedL");
+
+ TRAPD(ignore, iParent->Controller()->ResetTickerScrollingSpeedL());
+ if (ignore != KErrNone)
+ {
+ DEBUG_INT("CMIDScrollingText::HandleResourceChange - Exception from iParent->Controller()->ResetScrollingSpeedL. Error = %d", ignore);
+ }
+ }
+
+ //reset position and layout
+ iPaused = false;
+ DEBUG("CMIDScrollingText::HandleResourceChange - calling UpdateTickerLayoutL");
+ TRAPD(ignore,UpdateTickerLayoutL());
+ if (ignore != KErrNone)
+ {
+ DEBUG_INT("CMIDScrollingText::HandleResourceChange - Exception from UpdateTickerLayoutL. Error = %d", ignore);
+ }
+
+ //and finally draw
+ DrawNow();
+ }
+}
+
+void CMIDScrollingText::SizeChanged()
+{
+ // call parent implementation
+ CCoeControl::SizeChanged();
+
+ // update layout
+ TRAP_IGNORE(UpdateTickerLayoutL());
+}
+
+void CMIDScrollingText::DrawPictographArea()
+{
+ // Does nothing - Ticker is updating himself
+}
+
+// ---------------------------------------------------------------------------
+// Scroll the text of aScrollAmount, the direction depends on the text directionality. The min
+// and max text position are given by LeftTextPosition() and RightTextPosition().
+// ---------------------------------------------------------------------------
+//
+void CMIDScrollingText::UpdateTextPositionL(TInt aScrollAmount)
+{
+ const CFont* font = AknLayoutUtils::FontFromId(Layout().FontId());
+
+ if (iPaused)
+ {
+ return;
+ }
+
+ if (iText->Directionality() == TBidiText::ELeftToRight)
+ {
+ iTextPosition -= aScrollAmount;
+ if (iTextPosition < LeftTextPosition(font) - iTextWidth)
+ {
+ iTextPosition = RightTextPosition(font);
+ }
+ }
+ else
+ {
+ iTextPosition += aScrollAmount;
+ if (iTextPosition > RightTextPosition(font))
+ {
+ iTextPosition = LeftTextPosition(font) - iTextWidth;
+ }
+ }
+
+ iParent->ReportEventL(CMIDNaviPaneController::EPositionChanged);
+}
+
+
+// ---------------------------------------------------------------------------
+// The text color, this is taken from the layout + any skinning should be taken into account.
+// ---------------------------------------------------------------------------
+//
+inline TRgb CMIDScrollingText::TextColor() const
+{
+ TRgb color = AKN_LAF_COLOR(Layout().iC);
+
+ MAknsSkinInstance* skin = AknsUtils::SkinInstance();
+ // Ignore error, color is not updated if it not found from the skin
+ AknsUtils::GetCachedColor(skin, color, KAknsIIDQsnTextColors, EAknsCIQsnTextColorsCG2);
+
+ return color;
+}
+
+// ---------------------------------------------------------------------------
+// The space needed to draw "(999) " in pixels.
+// ---------------------------------------------------------------------------
+//
+inline TInt CMIDScrollingText::EditCapacityWidth(const CFont* aFont) const
+{
+ CMIDNaviPaneController* controller = iParent->Controller();
+
+ if (controller && controller->EditCapacityText() != NULL)
+ {
+ return aFont->TextWidthInPixels(KTextCapacity);
+ }
+ return 0;
+}
+
+// ---------------------------------------------------------------------------
+// The left position for scrolling text. According to the device directionality
+// we must add or not the edit capacity width.
+// ---------------------------------------------------------------------------
+//
+inline TInt CMIDScrollingText::LeftTextPosition(const CFont* aFont) const
+{
+ return aFont->TextWidthInPixels(KLeftSquareBracket) +
+ (TextAlign() == CGraphicsContext::ELeft ? EditCapacityWidth(aFont) : 0);
+}
+
+// ---------------------------------------------------------------------------
+// The right position for scrolling text. According to the device directionality
+// must add or not the edit capacity width.
+// ---------------------------------------------------------------------------
+//
+inline TInt CMIDScrollingText::RightTextPosition(const CFont* aFont) const
+{
+ return iSize.iWidth - aFont->TextWidthInPixels(KRightSquareBracket) -
+ (TextAlign() == CGraphicsContext::ELeft ? 0 : EditCapacityWidth(aFont));
+}
+
+// ---------------------------------------------------------------------------
+// Sets the initial scrolling text position
+// ---------------------------------------------------------------------------
+//
+void CMIDScrollingText::InitialiseScrollingTextPosition()
+{
+ const CFont* font = AknLayoutUtils::FontFromId(Layout().FontId());
+ if (iText->Directionality() == TBidiText::ELeftToRight)
+ {
+ iTextPosition = RightTextPosition(font);
+ }
+ else
+ {
+ iTextPosition = LeftTextPosition(font) - iTextWidth;
+ }
+}
+
+// End of File
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+