Lucian Piros

Since joining Symbian, in January 2006, Lucian has worked with the PIM and Internet team on various releases of contact model architecture and has been involved in the latest contact model architecture design. Before joining Symbian, Lucian worked for two years as independent developer on core Symbian OS applications for a number of UI platforms based on Symbian OS. He has eight years industrial experience, most of them spent as a C programmer writing telecommunications applications. Educated...

Drive Mapping

The emulator maps features of the target machine onto features of the PC environment. For software development, it is particularly important to know how the emulator maps drives and directories onto your PC's file system. On a Symbian OS phone, there are two important drives see Figure 10.1 Z is the ROM, which contains a bootstrap loader and all the EXE, DLL and other files required to boot and run Symbian OS and its applications. All files on Z are read-only program files are executed directly...

The Document Class

The class definition for the Noughts and Crosses document class, listed below, provides the implementation of CreateAppUiL , which is always required. In addition, it implements persistent storage of the game's state in the StoreL and RestoreL functions, using the principles described in Chapter 7. class COandXDocument public CAknDocument static COandXDocument NewL CEikApplication amp aApp virtual COandXDocument From CEikDocument CEikAppUi CreateAppUiL void StoreL CStreamStore amp aStore,...

The Application UI

Starting the application Ul is the final step in bringing up the application framework. The GUI action proper starts with the application Ul, which has two main roles to get commands to the application to distribute keystrokes to controls, including the application's main view, which is owned by the application Ul. A command is simply an instruction without any parameters or any information about where it came from, which the program must execute. The definition is deliberately vague, since...

Using Properties

Property read and write operations are atomic, therefore it is not possible for threads reading a property to get inconsistent data. A property value may be retrieved by specifying its identity each time it needs to be retrieved TInt err RProperty Get KMyPropertyCat, EMyPropertyInteger, propInt Alternatively, it may be retrieved using a handle created by a call to RProperty Attach RProperty tmpProperty TInt propInt -1 TInt err tmpProperty.Attach KMyPropertyCat, EMyPropertyInteger TInt getErr...

Using a Message Queue

You need a handle to a message queue before you can read from, or write to, it. In the case of a global, named message queue, any process can open it by name Tint openErr iQueue.OpenGlobal KMyQueueNameLit To use the other types of message queue, you need to obtain a handle from the process or thread that created the queue. Once you have a handle for a queue, preferably as an RMsgQueue instance, then you can send or receive messages, for example Tint sendErr iQueue.Send iSmallMsgType If you do...

History View Content

Although the topic is not directly related to the MCoeView interface functions, this is a convenient place to discuss the generation of the content for the Noughts and Crosses application's History view. The key function is CreateNewltemsL , whose UIQ implementation is as follows void Clear all existing data TBuf lt KFormatBufSize gt itemName R_HISTORY_VIEW_NO_DATA_TEXT for TInt i 0 i lt KNumDataLines i Insert the data to be displayed TUint played Controller .GamesPlayed Set the title in the...

Compound Controls Prr

We introduced the idea of compound controls in relation to drawing. Compound controls also make it very much easier to implement generalpurpose containers such as dialogs. Figure 18.3 shows a variety of controls within the same dialog captioned control arrays, including numeric editors, text editors and drop down lists a button group, with two buttons Save and Cancel . As these controls are all together it makes it much easier for a change in one control to cause another control to be updated...

Dictionary Stores and INI Files

In addition to an application's document file, the application architecture provides support for an application to open, read and modify a second file. By convention, the file has the same name as the application, but has the extension .ini hence such files are known as INI files. The intention is that an INI file should be used to store global settings and preferences that are independent of the document data that the application is processing. An application can then, in principle, open a...

Sharing File Handles

For file data that may be shared between more than one application there are several approaches you could take. First, the file containing the data could be created in a public area of a file system. This is a legitimate place to store a file, however it offers no protection to the data stored in. Any other application can open the file and read its contents. The second approach is suitable for a set of applications that share data stored in files. The application that 'owns' the data can...

Connecting Two Phones over Bluetooth

The process for connecting two phones over RFCOMM or L2CAP is an extension of the generic process. Because many services can be offered over Bluetooth, such as Serial Port Profile and Dial-up Networking, the host must advertise which services it provides, and the client must select the service to which they want to connect. A phone that wants to provide services over Bluetooth begins by connecting to the socket server. After that, it creates a listening socket, which is an instance of...

RBuf Descriptors

An RBuf is similar to an HBufC in that it can be created dynamically and its data is stored on the heap. However, as it derives from TDes, it has the benefit that it is directly modifiable, which means you do not have to create a TPtr around the data in order to modify it. Thus RBuf is preferable to HBufC when you know you need to dynamically allocate a descriptor and modify it. An RBuf can create its own buffer. Alternatively, it can take ownership of a pre-allocated HBufC or a pre-allocated...

The Image Conversion Library

The Image Conversion Library, or ICL, is a library based on ECOM plug-ins that supports encoding and decoding of a wide variety of image formats. ICL image encoder and decoder plug-ins for many formats are provided by Symbian. Other plug-ins may be added by phone manufacturers, to support more formats or to take advantage of hardware-accelerated encoding or decoding on a phone. Plug-ins can also be provided by third parties. The ICL also supports scaling and rotating of bitmaps once they have...

Completing a Request after Normal Processing

An asynchronous request is issued, is processed, and an event is signaled some time after the processing is complete. In this common scenario see Figure 6.8 , the request service provider has time to process the client's request. When the service provider is Start asynchronous processing of client request Client decides to cancel original asynchronous operation Client decides to cancel original asynchronous operation Start asynchronous processing of client request Cancel early completion...

Localizable Strings

If you intend to translate your application into one or more different languages, there are some additional things to bear in mind. A translator will not necessarily be a programmer and will probably find it difficult to preserve the general structure of a resource script through the translation process. For this reason alone, it is good practice to store all resource text strings in a separate resource localizable string RLS file, with a .rls extension. An RLS file defines symbolic identifiers...

Casting

Casting is a necessary evil. Old-style C provides casting syntax that enables you to cast any type to any other type. Over time, different casting patterns have emerged, including cast away the const property but don't change anything else cast to a related class rather than an arbitrary cast reinterpret the bit pattern effectively, old-style C casting . C provides individual keywords for each of these types of cast const_cast lt gt , static_cast lt gt and reinterpret_ cast lt gt . These should...

Stock Controls for Dialogs

A basic part of dialog programming is using stock controls in dialogs. The general techniques for using stock controls are specify a control type in the DLG_LINE struct, using type specify initialization data for the control in the dlg_line struct, using control and an appropriate resource STRUCT further initialize the control from PreLayoutDynInitL or Post-LayoutDynInitL extract values from the control when needed, in OkToExitL or other dialog processing functions do other things, such as...

Active Object Cancellation

All asynchronous service providers must implement cancel functions corresponding to their request functions. All active objects that issue request functions must also provide a DoCancel function to cancel the request that they originally issued. A cancel is actually a request for earlycompletion. Every asynchronous request that is issued must be completed precisely once-whether normally or by a cancel method. The contractual obligation of a cancel function is to complete the original...

Filled shapes

You can draw several filled shapes a pie slice, an ellipse, a rectangle, a rectangle with rounded corners or a polygon. These functions use the pen and the brush. Use only the pen to draw an outline use only the brush to draw the shape use both to draw an outlined shape. Here are the functions virtual void DrawPie const TRect amp aRect, const TPoint amp aStart, const TPoint amp aEnd 0 virtual void DrawEllipse const TRect amp aRect 0 virtual void DrawRect const TRect amp aRect 0 virtual void...

Manipulating Descriptors

This section provides a brief summary of the descriptor methods available. It is not possible to describe the API in full here due to its large size. For more information, consult your SDK. The methods use some descriptor-specific naming conventions a method name containing an uppercase F, such as LocateF , indicates folding, a process that sets everything to upper case and removes accents a method name containing LC, such as CopyLC , indicates lower case, provided the descriptor is not a...

SQL Syntax

You need at least a basic understanding of SQL syntax to follow the discussions about Symbian OS in Section 12.3. If you are already familiar with SQL syntax, then you can skip over this section. The best way to gain experience with SQL syntax is to experiment with database operations on the command line. In this way, feedback is instantaneous and lessons can be learned rapidly about what works and what does not. In this section, we talk only about how SQLite behaves, although the SQL syntax is...

User Memory and Memory Management

All details of the system's memory and memory manipulations, including low-level memory management, are encapsulated in a kernel component called the memory model. For example, it is the memory model that implements all necessary operations for context switching, while the policy for doing so is implemented in the kernel scheduler. For further details on the internals of the memory model and its usage, see Sales 2005 . Every user-side program on Symbian OS is instantiated in a process that has...

Using Active Objects and Calling UserWaitForRequest

A common mistake is to use TRequestStatus objects outside the active object framework to initiate multiple simultaneous asynchronous requests and then wait for one to complete synchronously. For example, starting a thread and a 5-second timer in parallel. If the thread does not exit within five seconds, then something must have gone wrong. TRequestStatus timerStatus TRequestStatus threadStatus start thread start timer User WaitForRequest timerStatus, threadStatus Symbian OS provides an overload...

Drawing a Rectangle

The next three lines of code draw a rectangular border ten pixels in from the edge of the application view's area on the screen TRect rect Rect rect.Shrink 10, 10 gc.DrawRect rect CCoeControl Rect gives the coordinates of the rectangle occupied by the control from within which Rect is called, in this case the application view. The coordinates are given relative to the window that the control uses. The coordinates used by CWindowGc drawing functions must also be relative to the window, so this...

Always Pass TDes and TDesC Parameters by Reference

When declaring method parameters, you must declare TDesC and TDes as pass-by-reference and not pass-by-value. The reason is that these classes do not contain any actual string data see Figure 5.2 and if you pass them by value, then the rules of C mean that static binding is being used and the consequence is that polymorphism won't work. The end result is that your code compiles but you are not actually passing any data. For example, in the following code the buffer variable contains random...

About the Kernel

As viewed from the perspective of the user and the applications programmer, a kernel manages the machine's hardware resources such as system RAM and hardware devices, while providing mechanisms for other software components to access these resources. For much application programming it is not necessary to know the detailed mechanics of the underlying OS. In this chapter we give an overview of the kernel and what it does. We won't otherwise be covering how to program the kernel side, but Sales...

Descriptors and the Text Console

Symbian OS provides a text console class called CConsoleBase which allows you to output formatted text to the screen and accept keyboard input. This can be useful when first experimenting with descriptors. The following code shows how a literal and stack descriptor can be displayed using CConsoleBase Printf . The code displays 'Hello World ' to the console twice, then pauses until the user presses a key. include lt e32base.h gt include lt e32cons.h gt _LIT KTxtConsoleTitle, Hello Title...

Putting Binary Data into a lit

The x escape sequence can be used to place binary data into a _lit. The following code produces a literal of length five containing the sequence of bytes 0x01 0x02 0x03 0x45 0xEF _LIT8 KNarrowLiteral, x01 x02 x03 x45 xEF TPtrC8 narrowPtr KNarrowLiteral With wide literals, you may need to be concerned with byte ordering depending upon your intended usage, because x12 in a Unicode string actually means 0x0012 on Symbian OS, it is stored as 0x12 0x00. The following code produces a literal of...

Oneshot Grants

It's not possible for users to blanket-grant all capabilities - only a Symbian Signed application can have this authorization. Instead, if you need limited use of a particular capability perhaps to send an SMS , you can use selected APIs on a 'one-shot grant'. To achieve this, because the access is being granted as a one-off, special case, you mustn't request these capabilities in your project definition file like other capabilities otherwise installation will fail as they cannot be authorized...

Calling Leaving Code in a Selfdestructing RunL Method

If your RunL implementation deletes its own active object instance, for example, by calling delete this, then logically this should typically be the last line within the RunL method. Were the RunL method to delete the object and somehow leave, then the active scheduler traps the leave and attempts to call Run Error on the object in question. Since the object has deleted itself, this results in an exception. Using operator to Assign TRequestStatus The CActive iStatus member, an instance of the...

Using eshell

eshell is a simple command-line shell, available on both the emulator and on some target hardware, which you may find quite useful. You can run it directly from the UIQ 3 emulator see Figure 10.8 or change to the emulator's startup directory epoc32 release winscw udeb from the Windows command line and type eshell. Information on available commands can be accessed by typing help in eshell. The ps command provides you with many options to view the current running processes, threads, etc. During...

Platform security limitations

Prior to Symbian OS v9.1, third-party controller plug-ins could be added to phones to allow new formats to be supported in the built-in media player applications, and to allow those new formats to be used as ringtones and other system sounds. However, due to the capability-based DLL loading restrictions introduced in Symbian OS v9.1, many of these use cases are not available to the majority of third-party developers. A built-in media player application typically has a DRM capability and the...

Setting the Status of a Completed Request to KRequestPending

Normally in Symbian OS, asynchronous requests are made within the context of calls between a client and a server. In this situation, the service provider's client API should provide an asynchronous request function that the client can call. The implementation of the service provider's client-side asynchronous request function should ultimately end up calling either RSessionBase SendReceive TInt aFunction, TRequestStatus amp aStatus const RSessionBase SendReceive TInt aFunction, const TIpcArgs...

Reading a Persistent Store

The following code opens and reads the direct file store that was created in the previous section. void ReadDirectFileStoreL RFs amp aFs, TDesC amp aFileName, TUid aAppUid CFileStore store CDirectFileStore OpenLC aFs, aFileName, EFileRead CStreamDictionary dictionary CStreamDictionary NewLC RStoreReadStream rootStream rootStream.OpenLC store, store- gt Root rootStream gt gt dictionary CleanupStack PopAndDestroy rootStream TStreamId id dictionary- gt At aAppUid CleanupStack PopAndDestroy...

Cleaning up

When a client has finished with a client-server session, it should end the session with a call to RSessionBase Close . This sends a disconnection message to the server, which responds by calling the destructor of the CSession2-derived object to destroy its end of the session. This action also causes the kernel to destroy its own representation of the session and sets the handle of the client-side RSessionBase class to zero. It is safe for a client to call Close on the RSessionBase again in this...

Creating a Message Queue

You must create a message queue before it can be opened by participating threads that wish to read from, or write to, it. A message queue is created with a fixed number of message slots, and a fixed number of bytes for each message. Note that the message size must be a nonzero multiple of 4 bytes and must not exceed KMaxLength, otherwise the creation operation panics the client. You can create global or local message queues. A global message queue can be named and is publicly visible from other...

The View Class 1

The majority of the remaining source code differences that are needed in a UIQ version of the application stem from the differences between CQikViewBase and CCoeControl. So, while both forms of the view own their component controls, the mechanisms of ownership and access are different. A view that derives from CCoeControl, as in the S60 version, creates its component controls normally in its ConstructL function and stores pointers to them in specific items of member data. In the S60 version,...

The Control Stack

In the UIQ environment, there are typically five types of control on the control stack other user interfaces work in a similar way the debug keys control this is an invisible control that consumes all Ctrl Alt Shift keys for instance, Ctrl Alt Shift R causes the current screen to be completely redrawn if the debug keys control doesn't consume the key, it gets offered further down the stack active FEPs that need to intercept key events most FEPs own a control that is added to the control stack...

Loggmg

In order to examine the dynamic behavior of your programs, you can add logging in your code. Logging is very useful when debugging active objects and client-server framework applications as well as other interprocess communication mechanisms. While testing on the emulator, RFileLogger is a client-server API that can be used for logging messages into a file. The logging message contains a time stamp, a thread ID, severity, location file name and line number as well as the message. Two formats...

Commands

UIQ 3 views are primarily designed for use in applications with multiple views, each with its own set of commands, so they are not seen at their best in an application such as the Noughts and Crosses application, which only has a single view. The application does, however, allow the basic differences to be illustrated. A major difference in UIQ is that commands are treated in a more abstract way than in S60. A UIQ device may be set up to access its commands by means of either a pointer device...

The Application Entry Point

Every Symbian OS application must implement two functions that are called by the framework as it starts the application. Note that the Carbide.C wizard puts the functions discussed in this section into files specific to the GUI - for HelloS60, they are in HelloS60. cpp, whereas for HelloUIQ, they are in HelloUlQAp-plication.cpp. The first is a non-leaving function which creates a new instance of the application class. This function is similar for both the HelloS60 and HelloUIQ applications. For...

Threading and Process Model

As discussed already, Symbian OS is a pre-emptive multitasking operating system whose kernel runs in privileged mode, while all other tasks run in non-privileged mode Furber 2000 . All access to memory and memory-mapped hardware is protected through use of the MMU by the operating system. Kernel-side code can access all the memory belonging to any program, whereas a non-privileged program can directly access only the memory specifically mapped to it. In Symbian OS the unit of memory protection...

Active Object Priorities

As we have now seen, the active-scheduler framework provides non-preemptive multitasking within the context of a single thread. Whilst one RunL call is being processed, no other RunL call within the same thread can execute or be pre-empted. This means that it is important to understand the importance of choosing priorities for active objects. If the thread's request semaphore is signaled more than once i.e. two or more events occur simultaneously , before the active scheduler can dispatch an...

Audio Streaming

The audio streaming APIs allow you to provide or receive audio data while it is being played or recorded respectively. This allows you to generate audio data for playback while it is being played and process audio data while it is being recorded. When streaming, you are using a client utility API that interfaces directly to the MDF layer. Hence, no MMF controller plug-in is used and the subthread associated with controllers is not used either. The streaming takes place directly in the...

Inserting dynamic values

Let's suppose that we want to insert some values into a table. So far, we have plugged the values directly into the statement descriptor _LIT KStatement, INSERT INTO tab VALUES 123 17 The underlying database engine imposes a limit of ten attached databases. 18 This only applies to a given client. This has the value 123 hard coded into the statement, which is not very useful if we don't know the values in advance. We could build the statement programmatically by building up strings as we figure...

Opening a Serial Connection

To use a serial cable on the emulator, or an emulated infrared connection on a phone, the application loads the required logical and physical device drivers LDDs and PDDs . Logical and physical drivers are discussed at length in Sales 2005, Chapter 12 . To use a serial cable or an emulated serial connection over infrared, the application must load the required drivers. The LDD is called ecomm on both the emulator and an actual phone. The PDD is ECDRV on the emulator and EUART on hardware. Name...

Narrow Wide and Neutral Descriptors

So far the descriptors we have seen are known as neutral descriptors. They are neutral in that their class names do not indicate if they store wide or narrow data. There are actually two sets of descriptor classes a set of narrow classes for storing 8-bit data and a set of wide classes for storing 16-bit data. Their names end in either 8 or 16 to explicitly indicate what type of data they store, narrow or wide. If you specifically need to use narrow or wide data, you can use the narrow or wide...

The Application Class

The application class represents the properties that are the same for every instance of the application. This includes the information specified in the registration file, for instance, the caption and the capabilities, and the UID. At a minimum, it must also implement two functions AppDllUid and CreateDocumentL . AppDllUid returns the application's UID. The implementations for HelloS60 and HelloUIQ are similar. S60 implementation of AppDllUid TUid CHelloS60Application AppDllUid const Return the...

Compound Controls

To illustrate some of the differences between simple and compound controls, we use the Noughts and Crosses example application that was introduced in Chapter 12. As a reminder, the appearance of the application is shown in Figure 15.1. The implementation uses an array of tiles, derived from CCoeControl, as component controls in the application view. The tiles supply all the mechanisms for displaying their content and focusing them, using either the cursor keys or the pointer. In this chapter we...

Publish and Subscribe IPC

Publish and subscribe P amp S is an IPC mechanism, also known as 'properties', that provides a means to define and publish system-wide global variables. Such properties are communicated to more than one interested peer asynchronously. The publish and subscribe API can be used by both user- and kernelside programs, via similar APIs, and thus can also provide asynchronous communication between user- and kernel-side components. Only userside usage is discussed in this text. As shown in Figure 8.2,...