PALM PROGRAMMING: Putting it all
together.
Palm Source Code
This section details the two separate source
syntaxes required for palm applications. While it is not a
tutorial on event driven programming, it supplies just enough
detail to get you oriented. For the purposes: a 'hello world'
example is given
Palm source is very Windowsesque in style. It is this
author's guess, that the original concept and initial
development of the Palm, was on a NeXt style, windows gui,
interface. For those of you familiar with the Microsoft Windows
API, the so-called WIN32 SDK, the palm source will be very
familiar territory.
For those of you more familiar with straight c programming
using main(), here is the fundamental difference:
As a Palm Programmer, you are driven by events [a button
pushed] rather than driving the event [looking for a button
push aka kbhit()].
This schema is known as event driven, or 'callback'
programming. The Palm OS (as in the SDK) will send you a
continous blizzard of signals, only a handfull of which you
will utilise, the others you will ignore and tell the
underlying OS that you have, in fact, ignored them.
If you understand this fundamental concept, then the only
agony you will endure is 'discovering' the name of the signal
you want to respond to. ButtonClick? or Button_click or
ClickPen or Penclick? Who knows? The full answer to that of
course is the Palm OS SDK documentation. You really do need to
download and print it out for reference, because, despite any
protests to the contrary, the naming conventions used,
ultimately rely on what that programmer ate on friday and
whether his Uncle phoned that weekend.
Palm Source consists of two disticntly different parts
C source code. (albiet, written in event-driven style)
AND
Pascal Resource statements.
Resource statements are contained in a (dot)rcp file. They
describe such items as the popups (if any), menu shortcuts, the
use of icons, importantly, text messages, and, the position and
size of these elements (I hesitate to call them objects).
Taken as a whole, the resource statements (written in a very
Pascalish language) and known collectively as the User
Interface, or UI for short. You will come accross this acronym
frequently in Palm documentation, so, don't be alarmed or
confused by it. More on resources later....
One final note, is that if you are familiar with the Borland C
product, eg, the later versions of TurboC, then the Palm way of
doing things will be very familiar ground.
C Source Code In the
beginning.....
Life begins for all Plam applications with PilotMain().
'normal' C programs begin with main(). In PilotMain you will
loop forever, processing events, targeted at you, from the OS.
One such event, is to tell you to cease and desist. (exit).
Without further ado
#include "PalmOS.h"
#include "resource.h" // definition of HelloForm
static Boolean ApplicationEventHandler(EventPtr event) ;
static Boolean HelloFormEventHandler(EventPtr event) ;
UInt32 PilotMain(UInt16 launchCode, MemPtr cmdPBP, UInt16
launchFlags)
{
EventType event;
UInt16 error;
if (launchCode != sysAppLaunchCmdNormalLaunch) return
0;
FrmGotoForm(HelloForm);
do
{
EvtGetEvent(&event, evtWaitForever);
if (!SysHandleEvent(&event))
if (!MenuHandleEvent(0, &event,
&error))
if (!MyOverallEventHandler(&event))
FrmDispatchEvent(&event);
} while (event.eType != appStopEvent);
FrmCloseAllForms();
return 0;
}
FrmGotoForm(HelloForm);
instantiates whatever shape size, color, and sense of smell
that you have declared in the resource (rcp) file.
The 'blizzard of signals' are obtained via EvtGetEvent(). Each
event, whatever it is, is passed to a cascading chain of
control elements (ie the system, menu handler, you). If none of
these elements process that event it is consigned to
FrmDispatchEvent(), which will, ultimately, pass control into
one of your callback functions [declared below].
The ONLY function here that is of your making is
MyOverallEventHandler()
Be aware that returning boolean false in any of this function
chain can be more subtle than "I did / didn't handle it". In
reality, the meaning of false is, "further processing
required".
static Boolean
MyOverallEventHandler(EventPtr event)
{
switch (event->eType)
{
case frmLoadEvent:
{
FormPtr pForm =
FrmInitForm(event->data.frmLoad.formID);
FrmSetActiveForm(pForm);
FrmSetEventHandler(pForm, HelloFormEventHandler);
return true;
}
case menuEvent:
switch (event->data.menu.itemID)
{
case HelpMenuAbout:
FrmAlert(AboutAlert);
break;
}
return true;
default: return false;
}
}
For simplicity's sake, the only items
MyOverallEventHandler() handles, is instantiating a form to
display, and, reacting to a menu pop up.
The only function() of your own making in the above is HelloFormEventHandler(). Which is your
first introduction to callback programming. It is not called
directly, it is called when the OS chooses to [and indirectly
by you via FrmDispatchEvent()]. Heady stuff.
static Boolean
HelloFormEventHandler(EventPtr event)
{
// Pointer to the currently-active form
static FormPtr gpForm;
switch (event->eType)
{
default: return false;
case frmOpenEvent: FrmDrawForm(gpForm =
FrmGetActiveForm()); return true;
case frmCloseEvent:
FrmEraseForm(gpForm); FrmDeleteForm(gpForm);
return true;
}
}
Here, the only 'events' you are responding to are the OS's
calls for you to in fact, display, and, ultimately, destroy
THIS form. There could be many more.
Printout the SDK documentation, and discover the class types
of the various signals you can receive within the event->
struct.
Enjoy