emailuis/nmhswidget/src/nmhswidget.cpp
changeset 54 997a02608b3a
parent 30 759dc5235cdb
child 65 478bc57ad291
equal deleted inserted replaced
53:bf7eb7911fc5 54:997a02608b3a
    15  *
    15  *
    16  */
    16  */
    17 #include <QtGui>
    17 #include <QtGui>
    18 #include <QGraphicsLinearLayout>
    18 #include <QGraphicsLinearLayout>
    19 #include <hbcolorscheme.h>
    19 #include <hbcolorscheme.h>
       
    20 #include <hbdocumentloader.h>
    20 #include <QTranslator>
    21 #include <QTranslator>
    21 #include <hbframedrawer.h>
    22 #include <hbframedrawer.h>
    22 #include <hbframeitem.h>
    23 #include <hbframeitem.h>
       
    24 #include <hblabel.h>
    23 #include "nmcommon.h"
    25 #include "nmcommon.h"
    24 #include "nmhswidget.h"
    26 #include "nmhswidget.h"
    25 #include "nmhswidgetemailengine.h"
    27 #include "nmhswidgetemailengine.h"
    26 #include "nmmessageenvelope.h"
    28 #include "nmmessageenvelope.h"
    27 #include "nmhswidgettitlerow.h"
    29 #include "nmhswidgettitlerow.h"
    31 #include "emailtrace.h"
    33 #include "emailtrace.h"
    32 
    34 
    33 NmHsWidget::NmHsWidget(QGraphicsItem *parent, Qt::WindowFlags flags)
    35 NmHsWidget::NmHsWidget(QGraphicsItem *parent, Qt::WindowFlags flags)
    34     : HbWidget(parent, flags), 
    36     : HbWidget(parent, flags), 
    35       mEngine(0),
    37       mEngine(0),
    36       mRowLayout(0),
       
    37       mTitleRow(0),
    38       mTitleRow(0),
    38       mAccountId(0),
    39       mAccountId(0),
    39       mAccountIconName(),
    40       mAccountIconName(),
    40       mTranslator(0),
    41       mTranslator(0),
    41       mBackgroundFrameDrawer(0),
    42       mBackgroundFrameDrawer(0),
    42       mIsExpanded(false),
    43       mIsExpanded(false),
    43       mStaticWidget(true),
    44       mDateObserver(0),
    44       mDateObserver(0)
    45       mNoMailsLabel(0),
    45 {
    46       mWidgetContainer(0),
    46     NM_FUNCTION;
    47       mContentContainer(0),
    47 }
    48       mContentLayout(0)
    48 
    49 {
    49 /*!
    50     NM_FUNCTION;
    50     Destructor
    51 }
    51 */
    52 
       
    53 /*!
       
    54  Destructor
       
    55  */
    52 NmHsWidget::~NmHsWidget()
    56 NmHsWidget::~NmHsWidget()
    53 {
    57 {
    54     NM_FUNCTION;
    58     NM_FUNCTION;
    55 
    59 
    56     delete mTranslator;
    60     delete mTranslator;
    65     delete mDateObserver;
    69     delete mDateObserver;
    66     mDateObserver = NULL;
    70     mDateObserver = NULL;
    67 }
    71 }
    68 
    72 
    69 /*!
    73 /*!
    70     \fn void NmHsWidget::onShow()
    74  \fn QPainterPath NmHsWidget::shape()
    71 
    75 
    72     called by home screen fw when widget gets visible
    76  Called by home screen fw to check widget boundaries, needed to draw
    73 */
    77  outside widget boundingRect.
       
    78  /return QPainterPath path describing actual boundaries of widget 
       
    79   including child items
       
    80  */
       
    81 QPainterPath NmHsWidget::shape() const
       
    82 {
       
    83     NM_FUNCTION;
       
    84     
       
    85     QPainterPath path;
       
    86     path.setFillRule(Qt::WindingFill);
       
    87     
       
    88     path.addRect(this->rect());
       
    89     if (mTitleRow){
       
    90         path.addPath(mTitleRow->shape());
       
    91     }
       
    92     return path.simplified();
       
    93 }
       
    94 
       
    95 /*!
       
    96  \fn void NmHsWidget::onShow()
       
    97 
       
    98  called by home screen fw when widget gets visible
       
    99  */
    74 void NmHsWidget::onShow()
   100 void NmHsWidget::onShow()
    75 {
   101 {
    76     NM_FUNCTION;
   102     NM_FUNCTION;
    77     if (mEngine)
   103     if (mEngine) {
    78         {
       
    79         mEngine->activate();
   104         mEngine->activate();
    80         }
   105     }
    81 }
   106 }
    82 
   107 
    83 /*!
   108 /*!
    84     \fn void NmHsWidget::onHide()
   109  \fn void NmHsWidget::onHide()
    85 
   110 
    86     called by home screen fw when widget gets hidden
   111  called by home screen fw when widget gets hidden
    87 */
   112  */
    88 void NmHsWidget::onHide()
   113 void NmHsWidget::onHide()
    89 {
   114 {
    90     NM_FUNCTION;
   115     NM_FUNCTION;
    91     if (mEngine)
   116     if (mEngine) {
    92         {
       
    93         mEngine->suspend();
   117         mEngine->suspend();
    94         }
   118     }
    95 }
   119 }
    96 
   120 
    97 /*!
   121 /*!
    98     Initializes Localization.
   122  \fn bool NmHsWidget::loadDocML(HbDocumentLoader &loader)
    99     /post mTranslator constructed & localization file loaded
   123  
   100     returns false in failure, otherwise true
   124  loads layout data and child items from docml file. Must be called after constructor.
   101 */
   125  /return true if loading succeeded, otherwise false. False indicates that object is unusable
   102 bool NmHsWidget::setupLocalization()
   126  */
   103 {
   127 bool NmHsWidget::loadDocML(HbDocumentLoader &loader)
   104     NM_FUNCTION;
   128 {
   105     
   129     NM_FUNCTION;
       
   130     
       
   131     bool ok(false);
       
   132     loader.load(KNmHsWidgetDocML, &ok);
       
   133     
       
   134     if(ok) {
       
   135         mWidgetContainer = static_cast<HbWidget*> (loader.findWidget(KNmHsWidgetContainer));        
       
   136         mContentContainer = static_cast<HbWidget*> (loader.findWidget(KNmHsWidgetContentContainer));
       
   137         mNoMailsLabel = static_cast<HbLabel*> (loader.findWidget(KNmHsWidgetNoMailsLabel));
       
   138         if (!mWidgetContainer || !mContentContainer || !mNoMailsLabel) {
       
   139             //something failed in documentloader, no point to continue
       
   140             NM_ERROR(1,"NmHsWidget::loadDocML fail @ containers or label");
       
   141             ok = false;
       
   142         }
       
   143     }
       
   144     return ok;
       
   145 }
       
   146 
       
   147 /*!
       
   148  Initializes Localization.
       
   149  /post mTranslator constructed & localization file loaded
       
   150  */
       
   151 void NmHsWidget::setupLocalization()
       
   152 {
       
   153     NM_FUNCTION;
       
   154 
   106     //Use correct localisation
   155     //Use correct localisation
   107     bool ret(false); 
       
   108     mTranslator = new QTranslator();
   156     mTranslator = new QTranslator();
   109     QString lang = QLocale::system().name();
   157     QString lang = QLocale::system().name();
   110     ret = mTranslator->load(KNmHsWidgetLocFileName + lang, KNmHsWidgetLocLocation);
   158     mTranslator->load(KNmHsWidgetLocFileName + lang, KNmHsWidgetLocLocation);
   111     QCoreApplication::installTranslator(mTranslator);
   159     QCoreApplication::installTranslator(mTranslator);
   112 
   160 }
   113     return ret;
   161 
   114 }
   162 /*!
   115 
   163  Initializes UI. Everything that is not done in docml files should be here.
   116 /*!
   164  return true if ok, in error false.
   117     Initializes UI. Everything that is not done in docml files should be here.
   165  */
   118     return true if ok, in error false.
       
   119 */
       
   120 void NmHsWidget::setupUi()
   166 void NmHsWidget::setupUi()
   121 {
   167 {
   122     NM_FUNCTION;
   168     NM_FUNCTION;
   123     
   169 
   124     setContentsMargins( KNmHsWidgetContentsMargin, KNmHsWidgetContentsMargin,
   170     //main level layout needed to control docml objects
       
   171     QGraphicsLinearLayout *widgetLayout = new QGraphicsLinearLayout(Qt::Vertical);
       
   172     widgetLayout->setContentsMargins(KNmHsWidgetContentsMargin, KNmHsWidgetContentsMargin,
   125             KNmHsWidgetContentsMargin, KNmHsWidgetContentsMargin);
   173             KNmHsWidgetContentsMargin, KNmHsWidgetContentsMargin);
   126     
   174     widgetLayout->setSpacing(KNmHsWidgetContentsMargin);
   127     //Setup layout
   175     widgetLayout->addItem(mWidgetContainer);
   128     mRowLayout = new QGraphicsLinearLayout(Qt::Vertical);
   176     this->setLayout(widgetLayout);
   129 
   177 
   130     mRowLayout->setContentsMargins(KNmHsWidgetContentsMargin, KNmHsWidgetContentsMargin,
   178     //fetch pointer to content container layout
   131             KNmHsWidgetContentsMargin, KNmHsWidgetContentsMargin);
   179     //to be able to add/remove email rows and no mails label
   132     mRowLayout->setSpacing(KNmHsWidgetContentsMargin);
   180     mContentLayout = (QGraphicsLinearLayout*) mContentContainer->layout();
   133     setLayout(mRowLayout);
   181     
   134    
   182     //set noMailsLabel properties not supported by doc loader 
   135    //background
   183     QColor newFontColor;
   136    mBackgroundFrameDrawer = new HbFrameDrawer( KNmHsWidgetBackgroundImage, HbFrameDrawer::NinePieces );
   184     newFontColor = HbColorScheme::color("qtc_hs_list_item_content_normal");
   137    HbFrameItem* backgroundLayoutItem = new HbFrameItem( mBackgroundFrameDrawer );
   185     mNoMailsLabel->setTextColor(newFontColor);
   138    //set to NULL to indicate that ownership transferred
   186     mNoMailsLabel->setVisible(true);   
   139    mBackgroundFrameDrawer = NULL;
   187     
   140    setBackgroundItem( backgroundLayoutItem );
   188     mContentLayout->removeItem(mNoMailsLabel);
   141 }
   189     
   142 
   190     //widget background
   143 /*!
   191     mBackgroundFrameDrawer = new HbFrameDrawer(KNmHsWidgetBackgroundImage,
   144     Initializes the widget.
   192         HbFrameDrawer::NinePieces);
   145     
   193     HbFrameItem* backgroundLayoutItem = new HbFrameItem(mBackgroundFrameDrawer);
   146     called by home screen fw when widget is added to home screen
   194     //set to NULL to indicate that ownership transferred
   147 */
   195     mBackgroundFrameDrawer = NULL;
       
   196     setBackgroundItem(backgroundLayoutItem);   
       
   197 }
       
   198 
       
   199 
       
   200 /*!
       
   201  Initializes the widget.
       
   202  
       
   203  called by home screen fw when widget is added to home screen
       
   204  */
   148 void NmHsWidget::onInitialize()
   205 void NmHsWidget::onInitialize()
   149 {
   206 {
   150     NM_FUNCTION;
   207     NM_FUNCTION;
   151     
   208 
   152     QT_TRY{       
   209     QT_TRY {
       
   210         
       
   211 	    // Use document loader to load the contents
       
   212 	    HbDocumentLoader loader;
       
   213 		
       
   214 	    //load containers and mNoMailsLabel
       
   215         if (!loadDocML(loader)) {
       
   216             NM_ERROR(1,"NmHsWidget::onInitialize Fail @ loader");
       
   217             emit error(); //failure, no point to continue
       
   218             return;
       
   219         }
       
   220 
       
   221         //construct title row
       
   222         mTitleRow = new NmHsWidgetTitleRow(this);
       
   223         if (!mTitleRow->setupUI(loader)) {
       
   224             //title row creation failed
       
   225             NM_ERROR(1,"NmHsWidget::onInitialize fail @ titlerow");
       
   226             emit error(); //failure, no point to continue
       
   227             return;            
       
   228         }
       
   229 				
   153         setupUi();
   230         setupUi();
   154         //emit error if localization fails
   231         setupLocalization();
   155         if(!setupLocalization()){
   232 
       
   233         //Engine construction is 2 phased. 
       
   234         mEngine = new NmHsWidgetEmailEngine(mAccountId);
       
   235         //Client must connect to exception signals before calling the initialize function
       
   236         //because we don't want to miss any signals.
       
   237         connect(mEngine, SIGNAL( exceptionOccured(const int&) ), this,
       
   238             SLOT( onEngineException(const int&) ));
       
   239         if (!mEngine->initialize()) {
       
   240             //engine construction failed. Give up.
       
   241             NM_ERROR(1,"NmHsWidget::onInitialize fail @ engine");
   156             emit error();
   242             emit error();
   157             return;
   243             return;
   158         }
   244         }
   159         
   245 
   160         //Engine construction is 2 phased. 
   246 
   161         mEngine = new NmHsWidgetEmailEngine( mAccountId );
       
   162         //Client must connect to exception signals before calling the initialize function
       
   163         //because we don't want to miss any signals.
       
   164         connect(mEngine, SIGNAL( exceptionOccured(const int&) )
       
   165                 ,this, SLOT( onEngineException(const int&) ) );
       
   166         if(!mEngine->initialize())
       
   167             {
       
   168             //engine construction failed. Give up.
       
   169             emit error();
       
   170             return;
       
   171             }
       
   172 
       
   173         //construct and load docml for title row
       
   174         mTitleRow = new NmHsWidgetTitleRow(); 
       
   175         if( !mTitleRow->loadDocML()){
       
   176             //if docml loading fails no point to proceed
       
   177             //but memoryleak must be prevented
       
   178             delete mTitleRow;
       
   179             mTitleRow = NULL;
       
   180             emit error();
       
   181             return;
       
   182         }
       
   183         mRowLayout->addItem(mTitleRow);
       
   184         mTitleRow->updateAccountName(mEngine->accountName());
   247         mTitleRow->updateAccountName(mEngine->accountName());
   185     
   248 
   186 	    //create observer for date/time change events
   249         //create observer for date/time change events
   187 	    mDateObserver = new NmHsWidgetDateTimeObserver();
   250         mDateObserver = new NmHsWidgetDateTimeObserver();
   188     
   251 
       
   252         //Crete MailRows and associated connections
       
   253         createMailRowsList();
       
   254 
   189         updateMailData();
   255         updateMailData();
   190         mTitleRow->updateUnreadCount(mEngine->unreadCount());
   256         mTitleRow->updateUnreadCount(mEngine->unreadCount());
   191         mTitleRow->setAccountIcon(mAccountIconName);
   257         mTitleRow->setAccountIcon(mAccountIconName);
   192         mTitleRow->setExpandCollapseIcon(mIsExpanded);
   258         mTitleRow->setExpandCollapseIcon(mIsExpanded);
   193         
   259 
   194         //Get signals about changes in mail data
   260         //Get signals about changes in mail data
   195         connect(mEngine, SIGNAL( mailDataChanged() )
   261         connect(mEngine, SIGNAL( mailDataChanged() ), this, SLOT( updateMailData() ));
   196                 ,this, SLOT( updateMailData() ) );
   262 
   197         
       
   198         //Get Signals about changes in unread count
   263         //Get Signals about changes in unread count
   199         connect(mEngine, SIGNAL( unreadCountChanged(const int&) )
   264         connect(mEngine, SIGNAL( unreadCountChanged(const int&) )
   200                 ,mTitleRow, SLOT( updateUnreadCount(const int&) ) );
   265                 ,mTitleRow, SLOT( updateUnreadCount(const int&) ) );
   201         
   266         
   202         //Get signals about account name changes
   267         //Get signals about account name changes
   206 	    //Get signals about user actions
   271 	    //Get signals about user actions
   207 	    connect(mTitleRow, SIGNAL( mailboxLaunchTriggered() )
   272 	    connect(mTitleRow, SIGNAL( mailboxLaunchTriggered() )
   208 	            ,mEngine, SLOT( launchMailAppInboxView() ) );
   273 	            ,mEngine, SLOT( launchMailAppInboxView() ) );
   209 	    connect(mTitleRow, SIGNAL( expandCollapseButtonPressed() )
   274 	    connect(mTitleRow, SIGNAL( expandCollapseButtonPressed() )
   210 	            ,this, SLOT( handleExpandCollapseEvent() ) );
   275 	            ,this, SLOT( handleExpandCollapseEvent() ) );
   211 
   276 	    
   212 	    //resize here so homescreen will place widget correctly on screen
   277 	    setMinimumSize(mTitleRow->minimumSize());
   213 	    setPreferredSize( mRowLayout->preferredSize() );
   278     }
   214 	    if (parentWidget()) {
   279     QT_CATCH(...) {
   215 	        //to place widget properly after adding to homescreen
   280         NM_ERROR(1,"NmHsWidget::onInitialize fail @ catch");
   216 	        parentWidget()->resize(preferredSize()); 
       
   217 		}
       
   218     }
       
   219     QT_CATCH(...){
       
   220         emit error();
   281         emit error();
   221     }
   282     }
   222 
   283 }
   223 }
   284 
   224 
   285 
   225 /*!
   286 /*!
   226     Uninitializes the widget.
   287  updateMailData slot
   227     
   288  */
   228     called by home screen fw when widget is removed from home screen
       
   229 */
       
   230 void NmHsWidget::onUninitialize()
       
   231 {
       
   232     NM_FUNCTION;
       
   233 }
       
   234 
       
   235 /*!
       
   236     updateMailData slot
       
   237 */
       
   238 void NmHsWidget::updateMailData()
   289 void NmHsWidget::updateMailData()
   239 {
   290 {
   240     NM_FUNCTION;
   291     NM_FUNCTION;
   241     
   292 
   242     QList<NmMessageEnvelope> envelopes;
   293     QList<NmMessageEnvelope> envelopes;
   243     int count = 0;
   294     int count = 0;
   244     if (mIsExpanded) {
   295     if (mIsExpanded) {
   245         count = mEngine->getEnvelopes(envelopes, KMaxNumberOfMailsShown);
   296         count = mEngine->getEnvelopes(envelopes, KMaxNumberOfMailsShown);
   246         }
   297     }
   247 
   298 
   248     updateMailRowsList(count);
   299     updateLayout(count);
   249     
   300     //count is safe for envelopes and mMailRows
   250     for(int i=0; i<envelopes.count(); i++)
   301     for (int i = 0; i < count; i++) {
   251         {
   302         mMailRows.at(i)->updateMailData(envelopes.at(i));
   252         mMailRows[i]->updateMailData( envelopes[i] );
   303     }
   253         }
   304 }
   254 }
   305 
   255 
   306 /*!
   256 /*!
   307  Sets monitored account id from given string
   257     Sets monitored account id from given string
   308  Needed for home screen framework which supports only QString type properties
   258     Needed for home screen framework which supports only QString type properties
   309  */
   259 */
       
   260 void NmHsWidget::setAccountId(const QString &text)
   310 void NmHsWidget::setAccountId(const QString &text)
   261 {
   311 {
   262     NM_FUNCTION;
   312     NM_FUNCTION;
   263     
   313 
   264     bool ok;
   314     bool ok;
   265     quint64 id = text.toULongLong(&ok);
   315     quint64 id = text.toULongLong(&ok);
   266     if (!ok)
   316     if (!ok) {
   267         {
   317         NM_ERROR(1, "NmHsWidget::setAccountId: invalid account ID data, signal finished()!!!");
   268         NM_ERROR(1,"NmHsWidget::setAccountId: invalid account ID data, signal finished()!!!"); 
       
   269         //No valid account id so give up
   318         //No valid account id so give up
   270         emit finished();
   319         emit finished();
   271         }
   320         return;
   272     else
   321     }
   273         {
   322 
   274         mAccountId.setId(id);
   323     mAccountId.setId(id);
   275         }
   324 }
   276 }
   325 
   277 
   326 /*!
   278 /*!
   327  Returns monitored account id as a string
   279     Returns monitored account id as a string
   328  Needed for home screen framework which supports only QString type properties
   280     Needed for home screen framework which supports only QString type properties
   329  */
   281 */
       
   282 QString NmHsWidget::accountId() const
   330 QString NmHsWidget::accountId() const
   283 {
   331 {
   284     NM_FUNCTION;
   332     NM_FUNCTION;
   285     return QString::number(mAccountId.id());
   333     return QString::number(mAccountId.id());
   286 }
   334 }
   287 
   335 
   288 /*!
   336 /*!
   289     Sets monitored account icon name from given string
   337  Sets monitored account icon name from given string
   290 */
   338  */
   291 void NmHsWidget::setAccountIconName(const QString &text)
   339 void NmHsWidget::setAccountIconName(const QString &text)
   292 {
   340 {
   293     NM_FUNCTION;
   341     NM_FUNCTION;
   294     mAccountIconName = text;
   342     mAccountIconName = text;
   295 }
   343 }
   296 
   344 
   297 /*!
   345 /*!
   298     Returns monitored account icon name
   346  Returns monitored account icon name
   299 */
   347  */
   300 QString NmHsWidget::accountIconName() const
   348 QString NmHsWidget::accountIconName() const
   301 {
   349 {
   302     NM_FUNCTION;
   350     NM_FUNCTION;
   303     return mAccountIconName;
   351     return mAccountIconName;
   304 }
   352 }
   305 
   353 
   306 /*!
   354 /*!
   307     Slot to handle expand/collapse trigger event
   355  Slot to handle expand/collapse trigger event
   308 */
   356  */
   309 void NmHsWidget::handleExpandCollapseEvent()
   357 void NmHsWidget::handleExpandCollapseEvent()
   310 {
   358 {
   311     NM_FUNCTION;
   359     NM_FUNCTION;
   312     toggleExpansionState();
   360     toggleExpansionState();
   313 }
   361 }
   314 
   362 
   315 /*!
   363 /*!
   316     Sets widget expand/collapse state
   364  Sets widget expand/collapse state
   317     /post widget expansion state is changed
   365  /post widget expansion state is changed
   318 */
   366  */
   319 void NmHsWidget::toggleExpansionState()
   367 void NmHsWidget::toggleExpansionState()
   320 {
   368 {
   321     NM_FUNCTION;
   369     NM_FUNCTION;
   322 
   370 
   323     mIsExpanded = !mIsExpanded;
   371     mIsExpanded = !mIsExpanded;
   324     
   372 
   325     //save new state to home screen
   373     //save new state to home screen
   326     QStringList propertiesList;
   374     QStringList propertiesList;
   327     propertiesList.append("widgetState");
   375     propertiesList.append("widgetState");
   328     emit setPreferences(propertiesList);
   376     emit setPreferences(propertiesList);
   329     
   377 
   330     //handle state change drawing
   378     //handle state change drawing
   331     updateMailData();
   379     updateMailData();
   332     
   380 
   333     mTitleRow->setExpandCollapseIcon(mIsExpanded);
   381     mTitleRow->setExpandCollapseIcon(mIsExpanded);
   334 }
   382 }
   335 
   383 
   336 /*!
   384 /*!
   337     Sets expand/collapse state from given string (needed by homescreen)
   385  Sets expand/collapse state from given string (needed by homescreen)
   338 */
   386  */
   339 void NmHsWidget::setWidgetStateProperty(QString value)
   387 void NmHsWidget::setWidgetStateProperty(QString value)
   340 {
   388 {
   341     NM_FUNCTION;
   389     NM_FUNCTION;
   342     if (value == KNmHsWidgetStateCollapsed)
   390     if (value == KNmHsWidgetStateCollapsed) {
       
   391         mIsExpanded = false;
       
   392     }
       
   393     else {
       
   394         mIsExpanded = true;
       
   395     }
       
   396 }
       
   397 
       
   398 /*!
       
   399  Returns widget expand/collapse state as string (needed by homescreen) 
       
   400  */
       
   401 QString NmHsWidget::widgetStateProperty()
       
   402 {
       
   403     NM_FUNCTION;
       
   404     if (mIsExpanded) {
       
   405         return KNmHsWidgetStateExpanded;
       
   406     }
       
   407     else {
       
   408         return KNmHsWidgetStateCollapsed;
       
   409     }
       
   410 }
       
   411 
       
   412 /*!
       
   413  Updates mMailRows list to include KMaxNumberOfMailsShown mail row widgets
       
   414  /post mMailRows contains KMaxNumberOfMailsShown mailRows 
       
   415  */
       
   416 void NmHsWidget::createMailRowsList()
       
   417 {
       
   418     NM_FUNCTION;
       
   419 
       
   420     //make sure that there are as many email rows as needed
       
   421     while (mMailRows.count() < KMaxNumberOfMailsShown) {
       
   422         NmHsWidgetEmailRow *row = new NmHsWidgetEmailRow(this);
       
   423         if (!row->setupUI()) {
       
   424             NM_ERROR(1, "NmHsWidget::createMailRowsList row->setUpUI() fails");
       
   425             //if setupUI fails no point to proceed
       
   426             emit error();
       
   427             return;
       
   428         }
       
   429         connect(row, SIGNAL(mailViewerLaunchTriggered(const NmId&)), mEngine,
       
   430             SLOT(launchMailAppMailViewer(const NmId&)));
       
   431         connect(mDateObserver, SIGNAL(dateTimeChanged()), row, SLOT(updateDateTime()));
       
   432         mMailRows.append(row);
       
   433     }
       
   434 
       
   435 }
       
   436 
       
   437 /*!
       
   438  Updates the Layout to contain the right items
       
   439  /param mailCount defines how many emails is to be shown
       
   440  /post If widget is collapsed, the layout contains only titleRow widget.
       
   441  If widget is expanded and mailCount is 0 layout will contain
       
   442  titlerow & noMailsLabel. 
       
   443  If widget is expanded and mailCount is greter
       
   444  than zero, layout will contain titlerow and KMaxNumberOfMailsShown times
       
   445  emailrow(s)
       
   446  */
       
   447 void NmHsWidget::updateLayout(const int mailCount)
       
   448 {
       
   449     NM_FUNCTION;
       
   450 
       
   451     if (mIsExpanded) {
       
   452         //set container height to content height 
       
   453         qreal contentHeight = KMaxNumberOfMailsShown
       
   454                 * mMailRows.first()->maximumHeight();
       
   455         mContentContainer->setMaximumHeight(contentHeight);
       
   456         mContentContainer->setVisible(true);
       
   457         if (mailCount == 0) {
       
   458             addNoMailsLabelToLayout();
       
   459             removeEmailRowsFromLayout();
       
   460         }
       
   461         else {
       
   462             removeNoMailsLabelFromLayout();
       
   463             addEmailRowsToLayout();
       
   464         }
       
   465     }
       
   466     else {
       
   467         removeNoMailsLabelFromLayout();
       
   468         removeEmailRowsFromLayout();
       
   469         mContentContainer->setVisible(false);
       
   470         mContentContainer->setMaximumHeight(0);        
       
   471     }
       
   472 
       
   473     //resize the widget to new layout size
       
   474     qreal totalHeight = mTitleRow->preferredHeight() + mContentContainer->maximumHeight();
       
   475     //set maximum size, otherwise widget will stay huge also when collapsed
       
   476     this->setMaximumHeight(totalHeight);
       
   477     //resize here or widget cannot draw mail rows when expanding
       
   478     this->resize(mTitleRow->preferredWidth(), totalHeight);
       
   479 
       
   480     updateMailRowsVisibility(mailCount);
       
   481 }
       
   482 
       
   483 /*!
       
   484  Updates mNoMailsLabel visibility based on widget state
       
   485  /param mailCount defines how many mail rows is needed
       
   486  /post if mail count is 0 and mIsExpanded equals true, then
       
   487  the mNoMailLabel is added to the mContentLayout. 
       
   488  */
       
   489 void NmHsWidget::addNoMailsLabelToLayout()
       
   490 {
       
   491     NM_FUNCTION;
       
   492 
       
   493     if (mNoMailsLabel->isVisible() || mMailRows.isEmpty()) {
       
   494         return;
       
   495     }
       
   496     //Add mNoMailsLabel to layout if not yet there and show it
       
   497     mContentLayout->addItem(mNoMailsLabel);
       
   498     //resize the widget to new layout size
       
   499     mNoMailsLabel->show();
       
   500 }
       
   501 
       
   502 /*!
       
   503  removeNoMailsLabelFromLayout removes mNoMailsLabel from the layout
       
   504  /post mNoMailsLabel is not in mContentLayout
       
   505  */
       
   506 void NmHsWidget::removeNoMailsLabelFromLayout()
       
   507 {
       
   508     NM_FUNCTION;
       
   509     //remove mNoMailsLabel from Layout and hide it
       
   510     mContentLayout->removeItem(mNoMailsLabel);
       
   511     mNoMailsLabel->hide();
       
   512 }
       
   513 
       
   514 /*!
       
   515  addEmailRowsToLayout adds every emailrow to the layout
       
   516  /post all elements in mMailRows are added to mContentLayout
       
   517  */
       
   518 void NmHsWidget::addEmailRowsToLayout()
       
   519 {
       
   520     NM_FUNCTION;
       
   521     foreach(NmHsWidgetEmailRow *row, mMailRows)
   343         {
   522         {
   344         mIsExpanded = false;
   523             mContentLayout->addItem(row);
   345         }
   524         }
   346     else
   525 }
       
   526 
       
   527 /*!
       
   528  removeEmailRowsFromLayout removes every emailrow from the layout
       
   529  /post none of the elements in mMailRows are in mContentLayout
       
   530  */
       
   531 void NmHsWidget::removeEmailRowsFromLayout()
       
   532 {
       
   533     NM_FUNCTION;
       
   534     foreach(NmHsWidgetEmailRow *row, mMailRows)
   347         {
   535         {
   348         mIsExpanded = true;
   536             mContentLayout->removeItem(row);
   349         }
   537         }
   350 }
   538 }
   351 
   539 
   352 /*!
   540 /*!
   353     Returns widget expand/collapse state as string (needed by homescreen) 
   541  Updates mail row visibilities in static widget
   354 */
   542  /param visibleCount defines how many items do have mail data
   355 QString NmHsWidget::widgetStateProperty()
   543  /post all row items having mail data are visible, other rows are hidden
   356 {
   544  */
   357     NM_FUNCTION;
       
   358     if (mIsExpanded)
       
   359         {
       
   360         return KNmHsWidgetStateExpanded;
       
   361         }
       
   362     else
       
   363         {
       
   364         return KNmHsWidgetStateCollapsed;
       
   365         }
       
   366 }
       
   367 
       
   368 /*!
       
   369     Updates mMailRows list to include correct amount of mail row widgets
       
   370     /param mailCount defines how many mail rows is needed
       
   371     /post mMailRows list includes NmHsWidgetEmailRow for each mail item 
       
   372 */
       
   373 void NmHsWidget::updateMailRowsList(const int mailCount)
       
   374 {
       
   375     NM_FUNCTION;
       
   376     
       
   377     int neededRowsCount = mailCount;
       
   378     //force size when static and expanded
       
   379     if (mStaticWidget && mIsExpanded)
       
   380         {
       
   381         neededRowsCount = KMaxNumberOfMailsShown;
       
   382         }
       
   383     
       
   384     while (mMailRows.count() != neededRowsCount)
       
   385         {
       
   386         //more mails to show than rows
       
   387         if (mMailRows.count() < neededRowsCount)
       
   388             {
       
   389             NmHsWidgetEmailRow *row = new NmHsWidgetEmailRow();
       
   390             if( !row->loadDocML()){
       
   391                 NM_ERROR(1,"NmHsWidget::updateMailRowsList row->loadDocML() fails");
       
   392                 //if docml loading fails no point to proceed
       
   393                 //but memoryleak must be prevented
       
   394                 delete row;
       
   395                 row = NULL;
       
   396                 emit error();
       
   397                 return;
       
   398             }
       
   399             connect(row, SIGNAL(mailViewerLaunchTriggered(const NmId&))
       
   400                     ,mEngine, SLOT(launchMailAppMailViewer(const NmId&)));
       
   401             connect( mDateObserver, SIGNAL(dateTimeChanged())
       
   402                     ,row, SLOT(updateDateTime()) );
       
   403             mMailRows.append(row);
       
   404             mRowLayout->addItem(row);            
       
   405             }
       
   406         //too many rows
       
   407         else if (mMailRows.count() > neededRowsCount)
       
   408             {
       
   409             mRowLayout->removeItem(mMailRows.last());
       
   410             delete mMailRows.takeLast();
       
   411             }
       
   412         }
       
   413     __ASSERT_ALWAYS( mMailRows.count() == neededRowsCount, User::Panic(_L("Invalid"), 500) );
       
   414     
       
   415     //resize the widget to new layout size
       
   416     setPreferredSize( mRowLayout->preferredSize() );
       
   417     
       
   418     if (mStaticWidget)
       
   419         {
       
   420         this->updateMailRowsVisibility(mailCount);
       
   421         }
       
   422 }
       
   423 
       
   424 /*!
       
   425     Updates mail row visibilities in static widget
       
   426     /param visibleCount defines how many items do have mail data
       
   427     /post all row items having mail data are visible, other rows are hidden
       
   428 */
       
   429 void NmHsWidget::updateMailRowsVisibility(const int visibleCount)
   545 void NmHsWidget::updateMailRowsVisibility(const int visibleCount)
   430 {
   546 {
   431     NM_FUNCTION;
   547     NM_FUNCTION;
   432   
   548 
   433     // set visible as many rows as requested by visibleCount param
   549     // set visible as many rows as requested by visibleCount param
   434     bool isVisible;
   550     bool isVisible;
   435     for (int i=0; i < mMailRows.count(); i++) 
   551 
   436         {
   552     for (int i = 0; i < mMailRows.count(); i++) {
   437         isVisible = false;
   553         isVisible = false;
   438         if ((mIsExpanded) && (i < visibleCount)) 
   554         if ((mIsExpanded) && (i < visibleCount)) {
   439             {
       
   440             isVisible = true;
   555             isVisible = true;
   441             }
   556         }
   442         mMailRows.at(i)->setVisible(isVisible);
   557         mMailRows.at(i)->setVisible(isVisible);
   443         }
   558     }
   444 }
   559 }
   445 
   560 
   446 /*!
   561 /*!
   447     onEngineException (NmHsWidgetEmailEngineExceptionCode exc)
   562  onEngineException (NmHsWidgetEmailEngineExceptionCode exc)
   448     signals widget to be finalized
   563  signals widget to be finalized
   449     /param exc exception type
   564  /param exc exception type
   450 */
   565  */
   451 void NmHsWidget::onEngineException(const int& exc)
   566 void NmHsWidget::onEngineException(const int& exc)
   452     {
   567 {
   453     NM_FUNCTION;
   568     NM_FUNCTION;
   454     switch (exc)
   569     switch (exc) {
   455         {
       
   456         case (NmEngineExcAccountDeleted):
   570         case (NmEngineExcAccountDeleted):
   457              emit finished(); //succesful ending
   571             emit finished(); //succesful ending
   458              break;
   572             break;
   459         case (NmEngineExcFailure):
   573         case (NmEngineExcFailure):
   460              emit error(); //failure
   574             emit error(); //failure
   461              break;
   575             break;
   462         default: 
   576         default:
   463             break; 
   577             break;
   464         }
   578     }
   465     }
   579 }