📄 signedapp.cpp
字号:
//
// SignedApp.cpp - Phase 2 of a signed app
//
// Copyright (C) UIQ Technology AB, 2007
//
// This material is provided "as is" without any warranty to its performance or functionality.
// In no event shall UIQ Technology be liable for any damages whatsoever arising out of the
// use or inabilty to use this material.
//
#include "SignedApp.h"
#include "ListView.h"
#include "DetailsView.h"
#include "SignedAppUids.h"
#include "SignedApp.hrh"
#include <SignedApp_0x20000462.rsg>
#include <eikstart.h>
#include <eikdialg.h>
#include <eiklabel.h>
#include <QikCommand.h>
#include <QikNumberEditor.h>
#include <QikSimpleDialog.h>
#include <Etel3rdParty.h>
////////////////////////////////////////////////////////////////////////////////////////////
class CGetPhoneIMEI : public CActive
{
protected:
void RunL();
void DoCancel();
public:
~CGetPhoneIMEI();
CGetPhoneIMEI(CAppSpecificUi& aAppUi);
void ConstructL();
protected:
CAppSpecificUi& iAppUi;
CTelephony::TPhoneIdV1Pckg iBuf;
CTelephony::TPhoneIdV1 iData;
CTelephony* iTelephony;
};
CGetPhoneIMEI::~CGetPhoneIMEI()
{
Cancel();
delete(iTelephony);
}
CGetPhoneIMEI::CGetPhoneIMEI(CAppSpecificUi& aAppUi) :
CActive(CActive::EPriorityHigh),iAppUi(aAppUi),iBuf(iData)
{
CActiveScheduler::Add(this);
}
void CGetPhoneIMEI::ConstructL()
// Start the request to obtain the IMEI
{
iTelephony=CTelephony::NewL();
iTelephony->GetPhoneId(iStatus,iBuf);
SetActive();
}
void CGetPhoneIMEI::RunL()
{
// for debugging purposes we set up the supplied serial number with debug info. We can leave this
// in production code, this may help support people diagnose problems.
_LIT(KErrNo,"Err %d");
_LIT(KBlank,"Blank");
if (iStatus!=KErrNone)
iData.iSerialNumber.Format(KErrNo,iStatus.Int());
else if (iData.iSerialNumber.Length()==0)
iData.iSerialNumber=KBlank;
// tell the UI about the phones IMEI
iAppUi.SetIMEI(iData.iSerialNumber);
delete(this);
}
void CGetPhoneIMEI::DoCancel()
// If we are currently IsActive() then calling Cancel() will call this to perform the actual
// cancelling before it consumes the generated signal.
{
iTelephony->CancelAsync(CTelephony::EGetPhoneIdCancel);
}
////////////////////////////////////////////////////////////////////////////////////////////
// Display the IMEI of the phone - can help support people when Unlock codes supplied by
// sites either go missing, are wrong or customer enters wrong IMEI.
class CRegistrationDialog : public CQikSimpleDialog
{
protected:
void PreLayoutDynInitL();
void HandleCommandL(CQikCommand& aCommand);
public:
CRegistrationDialog(TInt& aCode,const TDesC& aImei);
protected:
TInt& iCode;
TBuf<32> iImei;
};
CRegistrationDialog::CRegistrationDialog(TInt& aCode,const TDesC& aImei) :
iCode(aCode)
{
iImei=aImei;
}
void CRegistrationDialog::PreLayoutDynInitL()
{
// display the current device IMEI
CEikLabel* lbl=LocateControlByUniqueHandle<CEikLabel>(EAppLabel1);
lbl->SetTextL(iImei);
}
void CRegistrationDialog::HandleCommandL(CQikCommand& aCommand)
{
switch (aCommand.Id())
{
case EAppCmdContinue:
{
// obtain the content entered by the user
CQikNumberEditor* numEd=LocateControlByUniqueHandle<CQikNumberEditor>(EAppEdwin1);
iCode=numEd->Value();
// this value returned as the result to ExecuteLD()..
CloseDialog(EAppCmdContinue);
break;
}
default:
CQikSimpleDialog::HandleCommandL(aCommand);
break;
}
}
//////////////////////////////////////////////////////////////////////////////////
class CAboutDialog : public CQikSimpleDialog
{
protected:
void PreLayoutDynInitL();
};
// These would normally be derived from your in-house version control, this example just
// defines them here to remove such complexity from the example.
const TInt KAppMajorVersion=1;
const TInt KAppMinorVersion=0;
const TInt KAppBuild=1;
void CAboutDialog::PreLayoutDynInitL()
//
// Generate the version text - e.g. Version 1.00 (02) and set the label
//
{
TBuf<128>bb;
iEikonEnv->Format128(bb,R_STR_VERSION,KAppMajorVersion,KAppMinorVersion,KAppBuild);
CEikLabel* lbl=LocateControlByUniqueHandle<CEikLabel>(EAppLabel1);
lbl->SetTextL(bb);
}
//////////////////////////////////////////////////////////////////////////////
CAppSpecificUi::~CAppSpecificUi()
{
delete(iEngine);
}
TBool CAppSpecificUi::CheckRegistration() const
//
// Check to see if the registration code entered by the user is valid or not.
// Used to determine whether we are running is 'Trial' or 'Purchased' mode
//
{
TBuf<32>bb;
bb.Num(iRegistrationCode);
if (iPhoneImei.Length()<5 || bb.Length()!=5 || bb!=iPhoneImei.Right(5))
return(EFalse);
return(ETrue);
}
// It is good practice to prepend streams with a version number - that way if the content has to
// change in the future we can maintain backwards compatibility.
const TInt KIniFileStreamVersion=1;
const TUid KUidIniFilePrefs={0x00000001};
void CAppSpecificUi::LoadIniFilePreferencesL(
// Load the application specific preferences/settings
const TInt aVersion, // which version of the content we are loading
RReadStream& aStream) // where we are loading the content from
{
if (aVersion<=KIniFileStreamVersion)
{
iRegistrationCode=aStream.ReadInt32L();
// our 'engine' contains all the user configuration information. Due to the >> operator definition
// this calls the InternalizeL() method of our engine object.
aStream>>(*iEngine);
}
}
void CAppSpecificUi::SaveIniFilePreferencesL(RWriteStream& aStream) const
// Save the application specific preferences/settings
{
aStream.WriteInt32L(iRegistrationCode);
// our 'engine' contains all the user configuration information. Due to the >> operator definition
// this calls the ExternalizeL() method of our engine object.
aStream<<(*iEngine);
}
void CAppSpecificUi::LoadIniFile()
//
// Load the INI file - all our settings etc
// This code simply implements the framework for INI file loading.
// If the INI file does not exist or the specific stream is missing this code handles it by
// ignoring the 'error'. This is entirely reasonable since this may be the first time the app
// has ever been run.
//
{
TRAPD(err,
CEikApplication* app=(CEikApplication*)Document()->Application();
CDictionaryStore* iniFile=app->OpenIniFileLC(iEikonEnv->FsSession());
if (iniFile->IsPresentL(KUidIniFilePrefs))
{
RDictionaryReadStream readStream;
readStream.OpenLC(*iniFile,KUidIniFilePrefs);
TInt version=readStream.ReadUint8L();
LoadIniFilePreferencesL(version,readStream);
CleanupStack::PopAndDestroy(); // readStream
}
CleanupStack::PopAndDestroy(); // iniFile
);
}
void CAppSpecificUi::SaveIniFileL(const TInt aVersion)
//
// Save the INI file - all our settings etc. Notice we dont actually need to supply any file name
// location, the framework automatically determines that from our application name and private path.
//
{
CEikApplication* app=(CEikApplication*)Document()->Application();
CDictionaryStore* iniFile=app->OpenIniFileLC(iEikonEnv->FsSession());
RDictionaryWriteStream writeStream;
writeStream.AssignLC(*iniFile,KUidIniFilePrefs);
// version
writeStream.WriteUint8L(aVersion);
// now all the content
SaveIniFilePreferencesL(writeStream);
writeStream.CommitL();
CleanupStack::PopAndDestroy(); // writeStream
iniFile->CommitL();
CleanupStack::PopAndDestroy(); // iniFile
}
void CAppSpecificUi::HandleCommandL(TInt aCommand)
//
// If we have commands common across all Views we can implement them here
//
{
switch (aCommand)
{
case EAppCmdAbout:
(new(ELeave)CAboutDialog)->ExecuteLD(R_ABOUT_DIALOG);
break;
case EAppCmdRegister:
{
TInt code;
if ((new(ELeave)CRegistrationDialog(code,iPhoneImei))->ExecuteLD(R_REGISTER_DIALOG)==EAppCmdContinue)
{
// our registration scheme for this app is very simple - the last 5 digits of the
// IMEI need to match the number entered by the user.
TBuf<32>bb;
bb.Num(code);
if (bb.Length()!=5 || bb!=iPhoneImei.Right(5))
iEikonEnv->InfoWinL(R_STR_REG_FAILED_TITLE,R_STR_REG_FAILED_INFO);
else
{ // save the number the user entered. Give some +ve feedback that the registration
// code is correct.
iRegistrationCode=code;
iEikonEnv->InfoMsg(R_STR_REGISTERED);
}
}
break;
}
// in debug modes we have an exit command so we can easily exit app
// on real devices we are sent EEikCmdExit when the Task Manager has been requested to
// end the running application.
// If we 'leave' when handling this command the Task Manager cannot 'End' this app
case EEikCmdExit:
TRAPD(junk,SaveIniFileL(KIniFileStreamVersion));
Exit();
break;
default:
break;
}
}
void CAppSpecificUi::ConstructL()
//
// Normal primary entry point to a Symbian App
//
{
CQikAppUi::ConstructL();
#ifdef __WINS__
_LIT(KPhoneImei,"98765-12345");
iPhoneImei=KPhoneImei;
#else
// set up and start the active object that obtains the phones IMEI
CGetPhoneIMEI* imei=new(ELeave)CGetPhoneIMEI(*this);
CleanupStack::PushL(imei);
imei->ConstructL();
// the CGetPhoneIMEI object will delete itself when it completes (self-ownership !)
CleanupStack::Pop(imei);
#endif
// create and set-up our engine - typically responsble for supplying data the UI renders
iEngine=new(ELeave)CAppEngine(iEikonEnv->FsSession(),EQikCmdZoomLevel2);
iEngine->ConstructL();
// Setup the default category list
TBuf<KCategoryNameMaxLength> bb;
for (TInt i=0;i<EAppCategoryLastItem;i++)
{
iEikonEnv->ReadResourceL(bb,R_STR_CATEGORY_NAME_1+i);
iEngine->AddCategoryL(i,bb);
}
// Locate our private path - were our example files have been installed to
// Private Path is too stupid to report the drive were on... so we have to do that manually.
TFileName installedDrive(Application()->BitmapStoreName());
TFileName path;
iEikonEnv->FsSession().PrivatePath(path);
TParse parse;
parse.Set(path,&installedDrive,NULL);
#ifdef __WINS__
// not unreasonably the OS blocks us creating files in Rom filing system...
// however that is where it thinks we are currently running/installed to in the emulator
// so we need to fix that feature.
path=parse.FullName();
path[0]='C';
parse.Set(path,NULL,NULL);
#endif
// this is only here for the emulator - since it does not create our private data caged folder by default
// or put the example data files in that folder
TRAPD(err,iEngine->SetDefaultPathL(parse.DriveAndPath()));
if (err==KErrNotFound || err==KErrPathNotFound)
{
iEikonEnv->InfoWinL(R_STR_NO_EXAMPLE_FILES,R_STR_PLEASE_COPY_FILES);
}
User::LeaveIfError(err);
// override any default settings with those stored from the previous time we ran the application
LoadIniFile();
// now create our views on the engine data
CListView* list=new(ELeave)CListView(*this,iEngine);
CleanupStack::PushL(list);
list->ConstructL();
AddViewL(*list); // takes ownership
CleanupStack::Pop(list);
CDetailsView* details=new(ELeave)CDetailsView(*this,iEngine);
CleanupStack::PushL(details);
details->ConstructL();
AddViewL(*details); // takes ownership
CleanupStack::Pop(details);
}
/////////////////////////////////////////////////////////////////////////////////////////////
// Standard Symbian application framework code when creating an application
class CAppSpecificDocument : public CQikDocument
{
protected:
CQikAppUi* CreateAppUiL();
public:
CAppSpecificDocument(CQikApplication& aApp);
static CAppSpecificDocument* NewL(CQikApplication& aApp);
protected:
};
CAppSpecificDocument::CAppSpecificDocument(CQikApplication& aApp) :
CQikDocument(aApp)
{
__DECLARE_NAME(_S("CAppSpecificDocument"));
}
CAppSpecificDocument* CAppSpecificDocument::NewL(CQikApplication& aApp)
{
return(new(ELeave)CAppSpecificDocument(aApp));
}
CQikAppUi* CAppSpecificDocument::CreateAppUiL()
{
return(new(ELeave)CAppSpecificUi);
}
//////////////////////////////////////////////////////////////////////////////////
// Standard Symbian application framework code when creating an application
class CAppSpecificApplication : public CQikApplication
{
protected:
TUid AppDllUid() const;
CApaDocument* CreateDocumentL();
};
TUid CAppSpecificApplication::AppDllUid() const
{
return(KAppSpecificUid);
}
CApaDocument* CAppSpecificApplication::CreateDocumentL()
{
return(CAppSpecificDocument::NewL(*this));
}
//////////////////////////////////////////////////////////////////////////////////
// Standard Symbian application start up code
LOCAL_C CApaApplication* NewApplication()
{
return(new CAppSpecificApplication);
}
GLDEF_C TInt E32Main()
{
return(EikStart::RunApplication(NewApplication));
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -