qtmobility/plugins/sensors/symbian/sensorbackendsym.cpp
changeset 4 90517678cc4f
child 5 453da2cfceef
equal deleted inserted replaced
1:2b40d63a9c3d 4:90517678cc4f
       
     1 /****************************************************************************
       
     2 **
       
     3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
       
     4 ** All rights reserved.
       
     5 ** Contact: Nokia Corporation (qt-info@nokia.com)
       
     6 **
       
     7 ** This file is part of the Qt Mobility Components.
       
     8 **
       
     9 ** $QT_BEGIN_LICENSE:LGPL$
       
    10 ** No Commercial Usage
       
    11 ** This file contains pre-release code and may not be distributed.
       
    12 ** You may use this file in accordance with the terms and conditions
       
    13 ** contained in the Technology Preview License Agreement accompanying
       
    14 ** this package.
       
    15 **
       
    16 ** GNU Lesser General Public License Usage
       
    17 ** Alternatively, this file may be used under the terms of the GNU Lesser
       
    18 ** General Public License version 2.1 as published by the Free Software
       
    19 ** Foundation and appearing in the file LICENSE.LGPL included in the
       
    20 ** packaging of this file.  Please review the following information to
       
    21 ** ensure the GNU Lesser General Public License version 2.1 requirements
       
    22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
       
    23 **
       
    24 ** In addition, as a special exception, Nokia gives you certain additional
       
    25 ** rights.  These rights are described in the Nokia Qt LGPL Exception
       
    26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
       
    27 **
       
    28 ** If you have questions regarding the use of this file, please contact
       
    29 ** Nokia at qt-info@nokia.com.
       
    30 **
       
    31 **
       
    32 **
       
    33 **
       
    34 **
       
    35 **
       
    36 **
       
    37 **
       
    38 ** $QT_END_LICENSE$
       
    39 **
       
    40 ****************************************************************************/
       
    41 // Internal Includes
       
    42 #include "sensorbackendsym.h"
       
    43 
       
    44 // Constants
       
    45 const TInt KDesiredReadingCount = 1;
       
    46 const TInt KMaximumReadingCount = 1;
       
    47 const TInt KDefaultBufferingPeriod = 0;
       
    48 
       
    49 ///// Internal Functions
       
    50 
       
    51 /*
       
    52  * FindSensorL is used to find if a specific sensor is available on the
       
    53  * device, if FindSensorL leaves then the sensor is not supported
       
    54  */
       
    55 void CSensorBackendSym::FindSensorL()
       
    56     {
       
    57     // This method scans the device for the availability
       
    58     // of specified sensor using Sensor APIs
       
    59     CSensrvChannelFinder* finder = CSensrvChannelFinder::NewLC();
       
    60     RSensrvChannelInfoList channelList;
       
    61     TSensrvChannelInfo channelInfo;
       
    62     // Retrieve the list of channels available    
       
    63     finder->FindChannelsL( channelList, channelInfo );
       
    64     CleanupStack::PopAndDestroy(finder);
       
    65     // Iterate the channel list and look for required sensor
       
    66     for (TInt i = 0; i<channelList.Count(); i++)
       
    67         {
       
    68         // Iterate the available channels
       
    69         if (channelList[i].iChannelType == iBackendData.iSensorType)
       
    70             {
       
    71             // Required sensor found
       
    72             iBackendData.iChannelInfo = channelList[i];
       
    73             channelList.Close();
       
    74             return;
       
    75             }
       
    76         }
       
    77     // Required sensor not found, leave with error
       
    78     channelList.Close();
       
    79     iBackendData.iSensorAvailable = EFalse;
       
    80     User::Leave(KErrNotFound);
       
    81     }
       
    82 
       
    83 /*
       
    84  * OpenSensorChannelL is used to open the channel for sensor as indicated by
       
    85  * iPrivateData.iChannelInfo
       
    86  */
       
    87 void CSensorBackendSym::OpenSensorChannelL()
       
    88     {
       
    89     // Search if sensor is available on the phone
       
    90     FindSensorL();
       
    91     // Required sensor found
       
    92     if( !(iBackendData.iSensorChannel) )
       
    93         {
       
    94         // Create and Open the Sensor channel
       
    95         iBackendData.iSensorChannel = CSensrvChannel::NewL( iBackendData.iChannelInfo );      
       
    96         // Open the channel for  sensor
       
    97         iBackendData.iSensorChannel->OpenChannelL();        
       
    98         iBackendData.iReadingLock.CreateLocal();
       
    99         iBackendData.iSensorAvailable = ETrue;
       
   100         }
       
   101     else
       
   102         {
       
   103         User::Leave(KErrAlreadyExists);
       
   104         }
       
   105     }
       
   106 
       
   107 /*
       
   108  * CloseSensorChannel is used to close the sensor channel and release the
       
   109  * resources
       
   110  */
       
   111 void CSensorBackendSym::CloseSensorChannelL()
       
   112     {
       
   113     // If the sensor channel is not created nothing to delete
       
   114     if( iBackendData.iSensorChannel )
       
   115         {
       
   116         // Stop listening before closing the channel
       
   117         iBackendData.iSensorAvailable = EFalse;
       
   118         StopListeningL();
       
   119         // Close the channel
       
   120         User::LeaveIfError(iBackendData.iSensorChannel->CloseChannel());
       
   121         iBackendData.iReadingLock.Close();
       
   122         // If close is successful, destroy iSensorChannel
       
   123         delete iBackendData.iSensorChannel;
       
   124         iBackendData.iSensorChannel = NULL;
       
   125         }
       
   126     User::Leave( KErrNotFound );
       
   127     }
       
   128 
       
   129 /*
       
   130  * Used to start listening to the sensor
       
   131  */
       
   132 void CSensorBackendSym::StartListeningL()
       
   133     {
       
   134     // Check if data listening is enabled
       
   135     if(iBackendData.iDataListening)
       
   136         {
       
   137         // Start timer if required i.e. if update interval is more than zero   
       
   138         TInt interval = sensor()->updateInterval();
       
   139         if( interval > 0 )
       
   140             {
       
   141             iBackendData.iTimerId = startTimer(interval);
       
   142             }
       
   143         // Start listening to the sensor 
       
   144         // Before calling this api the channel should be found and opened
       
   145         iBackendData.iSensorChannel->StartDataListeningL( this,
       
   146                 KDesiredReadingCount,
       
   147                 KMaximumReadingCount,
       
   148                 KDefaultBufferingPeriod );
       
   149         }
       
   150     // start property listening if required
       
   151     if ( iBackendData.iPropertyListening )
       
   152         {
       
   153         iBackendData.iSensorChannel->SetPropertyListenerL(this);
       
   154         }
       
   155     }
       
   156 
       
   157 /*
       
   158  * timerEvent is called when timer expires, this is used for supporting time based
       
   159  * sensor update policies
       
   160  */
       
   161 void CSensorBackendSym::timerEvent(QTimerEvent* /*aTimerEvent*/)
       
   162     {
       
   163     // Called upon timer expiry
       
   164     //Use synchronization mechanism and emit the reading value
       
   165     iBackendData.iReadingLock.Wait();
       
   166     newReadingAvailable();
       
   167     iBackendData.iReadingLock.Signal();
       
   168     }
       
   169 
       
   170 /*
       
   171  * Used to stop listening to the sensor
       
   172  */
       
   173 void CSensorBackendSym::StopListeningL()
       
   174     {
       
   175     if(iBackendData.iPropertyListening)
       
   176         {
       
   177         //Stop Property listening
       
   178         iBackendData.iSensorChannel->SetPropertyListenerL(NULL);
       
   179         }
       
   180     if(iBackendData.iDataListening)
       
   181         {
       
   182         // If timer is being used, stop the timer
       
   183         if (iBackendData.iTimerId)
       
   184             {
       
   185             killTimer(iBackendData.iTimerId);
       
   186             iBackendData.iTimerId = 0;
       
   187             }
       
   188         // Stop listening to the sensor channel
       
   189         User::LeaveIfError(iBackendData.iSensorChannel->StopDataListening());
       
   190         }
       
   191     }
       
   192 
       
   193 /*
       
   194  * Default C++ constructor
       
   195  */
       
   196 CSensorBackendSym::CSensorBackendSym(QSensor *sensor):QSensorBackend(sensor)
       
   197     {
       
   198     // By default enabling Data listening     
       
   199     iBackendData.iDataListening = ETrue;
       
   200     // By default disabling Property listening
       
   201     iBackendData.iPropertyListening = EFalse;
       
   202     }
       
   203 
       
   204 /*
       
   205  * Backend Destructor
       
   206  */
       
   207 CSensorBackendSym::~CSensorBackendSym()
       
   208     {
       
   209     // No Implementation
       
   210     }
       
   211 
       
   212 /*
       
   213  * InitializeL is used to create and init the sensor server objects
       
   214  */ 
       
   215 void CSensorBackendSym::InitializeL()
       
   216     {
       
   217     // Initialize Symbian Sensor Framework Objects
       
   218     OpenSensorChannelL();
       
   219     }
       
   220 
       
   221 /*
       
   222  * Close is used to release all the sensor server objects
       
   223  * May change when error handling is supported by mobility apis
       
   224  */
       
   225 TInt CSensorBackendSym::Close()
       
   226     {
       
   227     // Close Symbian Sensor Framework objects
       
   228     TRAPD(err,CloseSensorChannelL());
       
   229     return err;
       
   230     }
       
   231 
       
   232 
       
   233 ///// Derived From QSensorBackend
       
   234 
       
   235 /**
       
   236  *  start is used to start listening to the sensor
       
   237  */
       
   238 void CSensorBackendSym::start()
       
   239     {
       
   240     // Start listening to sensor, after this call DataRecieved will be called
       
   241     // when data is available
       
   242     TRAPD(err,StartListeningL())
       
   243     if( err != KErrNone )
       
   244         {
       
   245         sensorStopped();
       
   246         sensorError(err);        
       
   247         }
       
   248     }
       
   249 
       
   250 /*
       
   251  * stop is used to stop listening to the sensor
       
   252  */
       
   253 void CSensorBackendSym::stop()
       
   254     {
       
   255     // Stop listening to sensor, after this call DataRecieved wont be called
       
   256     TRAPD(err,StopListeningL())
       
   257     if ( err != KErrNone )
       
   258         {
       
   259         sensorError(err);
       
   260         }
       
   261     }
       
   262 
       
   263 //Derived From MSensrvDataListener
       
   264 
       
   265 /*
       
   266  * DataReceived is called by the Sensor Server when ever data is available in the
       
   267  * sensor buffer
       
   268  */
       
   269 void CSensorBackendSym::DataReceived(CSensrvChannel &aChannel, TInt /*aCount*/, TInt /*aDataLost*/)
       
   270     {
       
   271     // Retrieve the data from sensor buffer
       
   272     RecvData(aChannel);
       
   273     // Notify only if no timer present
       
   274     if( !iBackendData.iTimerId )
       
   275         {
       
   276         newReadingAvailable();
       
   277         }
       
   278     }
       
   279 
       
   280 /**
       
   281  * DataError is called to indicate an error, fatal errors are inrecoverable
       
   282  */
       
   283 void CSensorBackendSym::DataError(CSensrvChannel& /*aChannel*/, TSensrvErrorSeverity aError)
       
   284     {
       
   285     // If error is fatal stop the sensor
       
   286     if( aError == ESensrvErrorSeverityFatal )
       
   287         {
       
   288         sensorStopped();
       
   289         }
       
   290     sensorError(KErrGeneral);
       
   291     }
       
   292 
       
   293 /*
       
   294  * GetDataListenerInterfaceL is used to get a pointer to the sensor server backend
       
   295  * It is not required for QT Mobility Sensors API
       
   296  */
       
   297 void CSensorBackendSym::CSensorBackendSym::GetDataListenerInterfaceL (TUid /*aInterfaceUid*/, TAny*&/*aInterface*/)
       
   298     {
       
   299     // No implementation required
       
   300     }
       
   301 
       
   302 // From MSensrvProeprtyListener        
       
   303 
       
   304 /**
       
   305  * Notification about the changed value of a property.
       
   306  */
       
   307 void  CSensorBackendSym::PropertyChanged(CSensrvChannel &aChannel, const TSensrvProperty &aChangedProperty)
       
   308     {
       
   309     TRAP_IGNORE(HandlePropertyChange(aChannel,aChangedProperty))
       
   310     }
       
   311    
       
   312 /**
       
   313  *  Property listening failed.
       
   314  */
       
   315 void  CSensorBackendSym::PropertyError(CSensrvChannel &/*aChannel*/, TSensrvErrorSeverity aError)
       
   316     {
       
   317     if( aError == ESensrvErrorSeverityFatal )
       
   318         {
       
   319         sensorStopped();
       
   320         }
       
   321     sensorError(KErrGeneral);
       
   322     }
       
   323   
       
   324 /**
       
   325  * Set a listener for the indication, if the setting of the property succeeded.
       
   326  */ 
       
   327 void  CSensorBackendSym::SetPropertySuccessIndicationChanged(TSetPropertySuccessIndicator /*aIndication*/)
       
   328     {
       
   329     // No implementation required
       
   330     }
       
   331    
       
   332 /*
       
   333  * Returns a pointer to a specified interface extension - to allow future extension of this class without breaking binary compatibility.
       
   334  */
       
   335 void  CSensorBackendSym::GetPropertyListenerInterfaceL (TUid /*aInterfaceUid*/, TAny *&/*aInterface*/)
       
   336     {
       
   337     // No implementation required
       
   338     }
       
   339 
       
   340 void CSensorBackendSym::SetListening(TBool aDataListening, TBool aPropertyListening)
       
   341     {
       
   342     iBackendData.iDataListening = aDataListening;
       
   343     iBackendData.iPropertyListening = aPropertyListening;
       
   344     }
       
   345 
       
   346 /**
       
   347  * Deriving class implements this if it requires property change notification
       
   348  */
       
   349 void CSensorBackendSym::HandlePropertyChange(CSensrvChannel &/*aChannel*/, const TSensrvProperty &/*aChangedProperty*/)
       
   350     {
       
   351     // No implementation required in this class
       
   352     }
       
   353