Stephan Veigl wrote:
> I want to prepare my application for plugins.
> This plugins should get a record number to
> the datarecord to work with, and return a
> record number if necessary. The plugins are
> fully responsible for data / database handling,
> UI (full screen), etc.
>
> Is there a standard way of writing plugins / plugin
> managers? Are there sample codes?
>
> First I thought of SysUIAppSwitch(), but than, the
> plugins will be visible as stand alone apps in
> launcher, which they shouldn't. They should be visible
> in my app or a plugin manager only. Any ideas?
Well...as it turns out this is similar to a problem that
I'm working on. I have a main application and a
variety of 'plugins' that are supposed to handle different
services that can be added and removed independently.
The user is able to download plugins, the main app will
find them, add them to a list, the user indicates which
ones should run. The plugins have a consistent API (more
about this later). I would like to hear from other
developers about their opinions about what I am doing.
In general, you are doing something similar to what you
do with shared libraries. There are two ways to do this,
depending on how fancy you want to get.
The first way is to have a single entry
point to your plugin. You define __startup__ to be your
first function. The prc that you end up with is a code
resource, and to use it you open it up using the Dm
manager, cast the pointer to the resource as a function,
and then call it. You pass the function a structure, the
most important element being a 'mode' that says what to do.
If mode is '1', you call 'version'; if mode is '2', you
call open; '3' is close; etc. The rest of the structure
gets used in the lower functions. The good thing about
doing things this way is that the compiler handles the
calling of the other function within your plugin and that
you only have to worry about a single function in your
application.
For examples, first look in the palm os dev site. The particular
one that you are looking for is called Plugin-1.zip. It is
at http://oasis.palm.com/dev/kb/samples/1157.cfm. It is in the
example code, but under the Operating System section, I don't
know why.
To see plugins of this type work in a 'real' application, look
at iKnapsack by Adam Tow. You can see the code (and he's got
a cool little web demo) at http://www.tow.com/software/iknapsack/index.shtml
He's nice enough to provide the source code at:
http://www.tow.com/software/iknapsack/download.shtml
The second way is more complicated. In this case, you are
doing something very similar to doing a shared library.
Essentially, what you do is pretend that your prc is going
to be a library, create a dispatch table, and then handle
all the stuff that the system handles. The advantage to
doing it this way is that you don't have to stuff all your
calls through a single function with a single bloated
structure. As I was building my plugin, I was discovering
more and more diverse things that I wanted to have my
plugin do. Then, I would add a couple more fields to my
structure and adding another mode. After a while, I just
decided that handling everything myself would be easier.
The __startup__ function that you set, and call first,
sets up a dispatch table. Then, when you set a number of
function pointers, using the location of the first function,
plus the appropriate offset from the dispatch table.
Why go through this rather than just make a shared library
out of each of your plugins and letting the OS deal
with the headache? Because it needed to be dynamic and
I wanted to have several plugin's open at the same time.
If your shared libraries all have the same functions, then
there are collisions. With plugins, you use the database
manager to find all your plugins, call a managing function
for each of them that opens them, figures out locations
of functions (I use an array of structures, each of which
has pointers to the functions in the plugin), and can
call them willy-nilly.
(My code is complicated by the fact that my manager of the
plugins is in fact a shared library. I found this to be
necessary in my applications, several of which want to use
the plugin functionalities. Your mileage may vary.)
Another complication is that (of course!) shared libraries
and plugins can't have global memory. The workaround is
to use features. See Aaron Ardiri's Cube 3d example.
http://www.ardiri.com/index.cfm?redir=palm&cat=cube3D
You may, at the point, notice that I have not offered any
web sites that have example code for this method of doing
plugins. That's because I was not able to find any. If
people are very interested, I may be able to take my
original prototype code and create an example. Please let
me know.
Clark
--
For information on using the Palm Developer Forums, or to unsubscribe, please see
http://www.palmos.com/dev/tech/support/forums/