Welcome to the workshop

"Easy plugins with Borland Delphi" for beginners

Note: All products are registered trademarks of the software-produce and depend on their copyrights!

and sorry for my english...

 

Content:

Dispositions

Installation of the SDK

Skeletal structures

Write a simple function

Implement a DLL-funktion into a WDL

Traps and errors

Addendum (some Acknex-types, -structures and functions)


Dispositions

To write a plugin for the Conitec 3DGS you'll need a supported version of Borland Delphi (in this workshop we use Delphi 7/personal edition).
The necessary resources are available from version 3 to 7 for Delphi and for Borland C 5.5 and Borland C++ Builder 3.x.
The sdk will be used here for 3DGS version 6.31.
All shown pictures are screenshots from Borland Delphi 7.0 personal edition. The shown areas and topics are within other Delphi-versions named different and/or at other locations.


Installation of the SDK

At the internetpage from CONITEC (http://www.acknex.com/) you can find within the topic Downloads under Software / Updates the A5 Delphi Plugin SDK.

1. Load the sdk and unzip it to a directory on your computer.

2. Create within the lib-directory (e.g.: c:\programme\entwicklung\borland\delphi7\lib\) of your Delphi-Installation a subdirectory with the name 3dgs and copy all files from the sdk-directory of your Delphi-version (e.g. delphi7\).

3. Now you must also copy the file A5DLL2.PAS from the sdk-directory Delphi_DX8  in your lib\3dgs-subdirectory.

It should look like this:

 

4. Start Borland Delphi and install a new package in the component administration:

Press ADD..., change to the \Lib\3dgs-directory and select the file A5SDK70.bpl.

The option "Build with runtime package" have not to be selected because the generated dll's wouldn't have necessary parts!

So then installation is completed!


Skeletal structures

To design a plugin is a very simple one:

1. Start Borland Delphi and create a ne dll-projekt:

 

2. Automatically the skeletal structure will be generated and should look like this:

Beneath this library-Definition we need an separate unit within we write our functions.
Therefor we create a new unit: (menu [File]-[New]-[Unit].

To correspond with the Acknex-engine we have to implement a header file with the types and structures from the engine: the unit A5dll2.pas.
Just expand the uses-clause of the interface-declaration with A5DLL2:

The skeletal structure now is finished and it's time to save our hard work.
I name my library "dll_3dgs.dpr" ans my unit "my_plugin.pas".


Write a simple function

The above created skeletal structure now is the frame for all our functions we want to write for expanding the Acknex-engine.

Just as n simple example I want to create a function which returns the version of our dll.
We add some lines to out unit (I've called "my_plugin.pas") with the necessary code-lines for our dll (these lines are highlighted):

That's it!
Compile/build the project and copy the dll into your 3DGS-direcory. 

Informations:
  1. Within the interface have to be a prototyp (funktionhead) of the function. The parameter cdecl; creates a c-conform interface for the DLL, exports defies the name of the dll-function.
  2. At the implemention your write the code for your functuions.
  3. The types and formates such as important conversion routines are part of the unit A5DLL2.PAS; the most important are listed at the appendix of this workshop.


Implement a DLL-funktion into a WDL

If you reached this point - I'm shure - you are able to understand this WDL-script (world-definition-language).
Here is also a very simple script how to use plugin-functions::
(The most interested parts are highlighted)

Info:
  1. It is necessary to open the dll with a handle for later closing.
  2. You can open several dll's at the same time.
  3. Before you can use a function of a plugin, you must declare it with dllfunction <fktname>.
  4. Function names are case sensitive!


Traps and errors

There are just a few things that can happen while the installation and creation of plugin.
Here is a list of errors/problems:

  1. The right versions of sdk-files have to be used and to be stored in the Delphi-LIB-Path.
  2. The more actual version of the Acknex A5 DLL interface header (A5DLL2.PAS) from the SDK-directory Delphi_8DX must be used.
  3. The package A5SDK70.bpl must be importied and no runtime-packete have to be create!
    1. If you get a version-conflict while compiling your first dll,  just  create the runtime-packet once a time.
    2. A new generated dll with just one simple function should have the size about 86kByte. If it is smaller -> uncheck runtime-packet.
  4. The dll must be reached from your WDL-script.So place it in your 3DGS-project or store the path in the dll_open()-action.
  5. Open the dll with dll_handle=dll_open(...);, before you use a function.
  6. A dll is in memory until you unload (close_dll()) it: All global dll-variables are (just) that long alive!


Appendix

Acknex-types: (for detailed information refer to A5DLL2.PAS)

Typ

3DGS-Typ

Delphi-example

GSFixed

Numbers

A longint or a double -> see helperfunction:

function GetVersion() : gsfixed;
begin
  result:=INT2FIX(5);
end;

PA4_STRING

string

Struktur mit chars und Länge:

 str_pascal:=StrPas(str_3dgs^.chars);

PA4_ENTITY

entity

Struktur see A5DLL2.PAS

PA4_TEX

textur

Struktur see A5DLL2.PAS

PA4_BMAP

bitmap (bmp, pcx, tga)

Struktur see A5DLL2.PAS

PA4_PARTICLE

particle

Struktur see A5DLL2.PAS

PA4_FONT

font

Struktur see A5DLL2.PAS

PA4_TEXT

text

Struktur see A5DLL2.PAS

PA4_PANEL

panel

Struktur see A5DLL2.PAS

PA4_VIEW

view

Struktur see A5DLL2.PAS

 

Helperfunction

To work with the type gsfixed Conitec has spent a hand full funktions,
to convert the pascal-type Longint  and double to the Acknex-format:

function INT2FIX(i : LongInt) : GSFixed;

Converts a Pascal-Longint into Acknex-Fixtype

ack_fix = INT2FIX(pas_long);

function FIX2INT(x : GSFixed) : LongInt;

Converts a Acknex-Fixtype into pascal-Longint

pas_int := FIX2INT(ack_fix);

function FIX2FLOAT(x : GSFixed) : Double;

Converts a Acknex-Kommazahl to a Pascal-Double-value

pas_double := FIX2FLOAT(ack_fix);pas_double := FIX2FLOAT(ack_fix);

function FLOAT2FIX(f : double) : GSFixed;

Converts a Pascal-Double-Wert into an Acknex-float

ack_fix = FLOAT2FIX(pas_double);

 

version: 10.2005
Author: Ulrich Seiffert (3dgs@ulrich-seiffert.de)