Whilst I'm developing OPL programs for EPOC based machines I will keep note of any useful tips I discover and make them available on this page.
There should be a copy of the OPL manual on the CD that came with your machine; try looking in the EXTRAS folder. If you would like a copy in EPOC Word format then see my OPL Manual page. You can also download a useful help file for use on an EPOC machine from EPOC World.
It is a good idea to read all of the manual, though probably in small chunks :o) Even though a lot of it may not sink in on first reading, at least when you want to do something new you may have a vague recollection of some useful in a certain chapter and be able to find it again.
For an excellent introduction to OPL programming see Steve Litchfields Programming features
The UseNet newsgroup for EPOC programmers is comp.sys.psion.programmer You may want to read this regularly to see if you can pick up some tips from what other people are talking about.
You can post questions there asking for help, but please make sure first that the answer is not in the manual. :o)
Also; it's good form to prefix the subject line of a posting with something like "[EPOC OPL]", this means that people who don't program for EPOC or in OPL can quickly skip the post. It also means you are more likely to get an relevant answer to your query.
There is a style guide for EPOC programs. This is produced by Symbian and is used by both Symbian employees and external developers to help give all programs the same look and feel. It is a good idea to follow these style suggestions where possible so that any user of the programs that you write will have a familiar way of interacting with it.
Unfortunately, this style guide no longer appears to be available on the EpocWorld web site, however it is contained in the documentation which comes with the various SDKs available.
You can produce graphics files for use in OPL programs by exporting a picture from sketch as an 'EPOC Picture'. This will produce a Multiple BitMap (MBM) file that contains a single picture. If you want to produce files on your EPOC machine which contain more than one picture then Lieuwe de Vrie has produced an excellent program called MBMView which lets you view and edit MBM files. Check out his web site.
Use gUPDATE OFF at the start of any code that
draws several items to the screen. This will queue up
all the graphics commands until you use gUPDATE ON,
when they will all be processed together.
Note: if your program spends a lot of time between a pair
of gUPDATE OFF and gUPDATE ONs
then you may need to use IOYIELD occasionally.
(See the OPL manual.) This allows the operating system
time to process events such as key presses.
If you use CaptureKey& then you will
need to set the compute mode up correctly so that a
program can react immediately to a key press.
The following code will ensure this by making a program
run at full speed even whilst it is in the background.
REM Give program a high priority SetComputeMode:(KComputeModeOff&) REM Prevent program from changing to low priority REM when it gets sent to the background SetComputeMode:(KComputeModeDisabled&)
If you use the above then it is important that your
program gives up time to the CPU to process other tasks.
This is usually done with IOWait or
GetEvent32 which suspend a program until
it receives an event. If you don't then your program
will significantly slow down the foreground program
that the user is trying to use.
There are several different screen sizes used by various EPOC devices and no doubt more variations will appear in the future. Therefore a program should not assume anything about the screen size. E.g. if a program were to be written assuming a 640x480 sized Series 5 screen, then part the program's display wouldn't be visible on a Revo and it would only use half the available screen space on a Series 7. Neither of these looks very professional.
There are also other differences which need to be considered, including toolbars and screen colours available.
It is possible to write a one-size-fits-all program and the first step in achieving this is for the program to determine what size screen is available to it. Fortunately when an OPL program is run it is given a default window to use which is the full size of the screen. Therefore some code like the following can be used at the start of a program.
GLOBAL ScreenWidth%,ScreenHeight% ScreenWidth% = gWIDTH ScreenHeight% = gHEIGHT
This provides two global variables that a program can use as a basis to calculate all screen positions and window sizes.
If the program uses a toolbar then it can be initialised so that it always appears at the right-hand edge of the screen by:
TBarInit:("Program Name",ScreenWidth%,ScreenHeight%)
As the toolbar may also have a different size on different
machines the total size of screen available to a program
should be calculated using the TBWidth% variable and not
a fixed number. E.g.
IF MyToolbarIsVisible
MyMainWindowWidth% = ScreenWidth%-TBWidth%
ELSE
MyMainWindowWidth% = ScreenWidth%
ENDIF
MyMainWindowHeight% = ScreenHeight%
The rest of the program should now use these new variables as the screen size available. E.g. to draw a box around the border:
gAT 0,0 gBOX MyMainWindowWidth%,MyMainWindowHeight%
The smaller EPOC machines like the Psion Revo don't have enough space on the toolbar buttons for both icons and text, so it is best to not to give them an icon when initialising a button. E.g.
IF TBWidth% >= 64 REM Toolbar wide enough for icons?
TBarButt:("k",1,"Text label",0,Icon&,IconMask&,0)
ELSE
TBarButt:("k",1,"Text label",0,0,0,0)
ENDIF
The number of toolbar buttons also varies from machine to machine; the Revo has three, the Series 5 has four and the Series 7 has six.
One option is to play safe and only specify four buttons, - the Revo is OK with this though it only displays three of them. However, it is possible to make use of the extra buttons, but first the maximum number available needs to be found. (Because trying to initialise more than are available can result in a run-time error.)
The number of toolbar buttons can be determined with the
statement PEEKW(ADDR(TbBtFlags%())-2). This
trick works because after Toolbar.opo has been initialised
a global array called TbBtFlags% is created
which has a dimension equal to the maximum number of
buttons. The PEEK statement reads this
dimension. Example:
LOCAL numButtons% = PEEKW(ADDR(TbBtFlags%())-2)
TBarButt:("a",1,"Text label 1",0,Icon1&,IconMask1&,0)
TBarButt:("b",2,"Text label 2",0,Icon2&,IconMask2&,0)
TBarButt:("c",3,"Text label 3",0,Icon3&,IconMask3&,0)
TBarButt:("d",4,"Text label 4",0,Icon4&,IconMask4&,0)
IF numButtons% >= 5
TBarButt:("e",5,"Text label 5",0,Icon5&,IconMask5&,0)
IF numButtons% >= 6
TBarButt:("f",6,"Text label 6",0,Icon6&,IconMask6&,0)
ENDIF
ENDIF
When deciding which functions should appear on the toolbar, it is obviously a good idea to order them so that the most useful appear first, because buttons 4,5,6... wont be available on all EPOC machines.
If dFILE is used with the System folder
in the seed path then a crash will happen if the user taps
the 'Folder' box in a dialog. e.g.
file$ = "C:\System\Apps" ... dFILE file$,"File,Folder,Disk",770
To get around this I check for the System folder in the seed path and if it is present I set the path to the root folder. e.g.
IF LEN(file$)>=10 REM is file$ long enough
IF UPPER$(MID$(file$,4,7))="SYSTEM\" REM are chars 4 thru 10 = "SYSTEM\"
file$=LEFT$(file$,3) REM file$ = left 3 chars e.g. "C:\"
ENDIF
ENDIF
dFILE file$,"File,Folder,Disk",770
If the seed path you give to dFILE contains
a file extension then it is not possible for the user to
change this to a name without an extension. This is because
dFILE will add it back in. E.g.
path$ = "C:\ABC.XYZ" ... dFILE path$,"File,Folder,Disk",1 REM [user changes 'ABC.XYZ' to 'NAME'] ... REM path$ is now "C:\NAME.XYZ" not "C:\NAME"
This may not be a bug, but it can be a very annoying feature.
To avoid this you can use SaveAsFileDialog&:
or CreateFileDialog&: which are in SYSTEM.OPX. These
do not suffer from this problem.
There is a bug in the Toolbar.opo, at least on ROM 1.00.
When you call SetToolbarTitle: it tries to
do the sensible thing and print the title centred in its
box if it will fit, or left aligned if it won't. However,
when it calculates the size of the title, it does so before
it has set the font. This can lead to some titles being
clipped on the left and right.
To get around this problem, call SetToolbarTitle
twice in a row. The first may get it wrong but the font
will then be set, so the second call will get things
right.
MediaType&: returns flash cards in drive D:
as type 'hard disk' not 'flash' as I would have expected.
It also returns some very funny values for non-existent
drives instead of the 'not present' code.
VolumeSpaceFree&: returns free space in
kilobytes not bytes as the OPL manual says.